FFMPEG:SPS和PPS

使用RTP传输H264的时候,需要用到sdp协议描述,其中有两项:Sequence Parameter Sets (SPS) 和Picture Parameter Set (PPS)需要用到,那么这两项从哪里获取呢?答案是从H264码流中获取.在H264码流中,都是以"0x00 0x00 0x01"或者"0x00 0x00 0x00 0x01"为开始码的,找到开始码之后,使用开始码之后的第一个字节的低5位判断是否为7(sps)或者8(pps), 及data[4] & 0x1f == 7 || data[4] & 0x1f == 8.然后对获取的nal去掉开始码之后进行base64编码,得到的信息就可以用于sdp.sps和pps需要用逗号分隔开来.


SDP中的H.264的SPS和PPS串,包含了初始化H.264解码器所需要的信息参数,包括编码所用的profile,level,图像的宽和高,deblock滤波器等。

由于SDP中的SPS和PPS都是BASE64编码形式的,不容易理解,附件有一个工具软件可以对SDP中的SPS和PPS进行解析。

用法是在命令行中输入:

spsparser sps.txt pps.txt output.txt

例如sps.txt中的内容为:

Z0LgFNoFglE=

pps.txt中的内容为:

aM4wpIA=

最终解析的到的结果为:

  • Start dumping SPS:

Start dumping SPS
profile_idc = 66
​
constrained_set0_flag = 1
​
constrained_set1_flag = 1
​
constrained_set2_flag = 1
​
constrained_set3_flag = 0
​
level_idc = 20
​
seq_parameter_set_id = 0
​
chroma_format_idc = 1
​
bit_depth_luma_minus8 = 0
​
bit_depth_chroma_minus8 = 0
​
seq_scaling_matrix_present_flag = 0
​
log2_max_frame_num_minus4 = 0
​
pic_order_cnt_type = 2
​
log2_max_pic_order_cnt_lsb_minus4 = 0
​
delta_pic_order_always_zero_flag = 0
​
offset_for_non_ref_pic = 0
​
offset_for_top_to_bottom_field = 0
​
num_ref_frames_in_pic_order_cnt_cycle = 0
​
num_ref_frames = 1
​
gaps_in_frame_num_value_allowed_flag = 0
​
pic_width_in_mbs_minus1 = 21
​
pic_height_in_mbs_minus1 = 17
​
frame_mbs_only_flag = 1
​
mb_adaptive_frame_field_flag = 0
​
direct_8x8_interence_flag = 0
​
frame_cropping_flag = 0
​
frame_cropping_rect_left_offset = 0
​
frame_cropping_rect_right_offset = 0
​
frame_cropping_rect_top_offset = 0
​
frame_cropping_rect_bottom_offset = 0
​
vui_parameters_present_flag = 0

【学习地址】:FFmpeg/WebRTC/RTMP/NDK/Android音视频流媒体高级开发

【文章福利】:免费领取更多音视频学习资料包、大厂面试题、技术视频和学习路线图,资料包括(C/C++,Linux,FFmpeg webRTC rtmp hls rtsp ffplay srs 等等)有需要的可以点击1079654574加群领取哦~

  • Start dumping PPS:

Start dumping PPS
pic_parameter_set_id = 0
​
seq_parameter_set_id = 0
​
entropy_coding_mode_flag = 0
​
pic_order_present_flag = 0
​
num_slice_groups_minus1 = 0
​
slice_group_map_type = 0
​
num_ref_idx_l0_active_minus1 = 0
​
num_ref_idx_l1_active_minus1 = 0
​
weighted_pref_flag = 0
​
weighted_bipred_idc = 0
​
pic_init_qp_minus26 = 0
​
pic_init_qs_minus26 = 0
​
chroma_qp_index_offset = 10
​
deblocking_filter_control_present_flag = 1
​
constrained_intra_pred_flag = 0
​
redundant_pic_cnt_present_flag = 0
​
transform_8x8_mode_flag = 0
​
pic_scaling_matrix_present_flag = 0
​
second_chroma_qp_index_offset = 10

/

这里需要特别提一下这两个参数

pic_width_in_mbs_minus1 = 21
pic_height_in_mbs_minus1 = 17

分别表示图像的宽和高,以宏块(16x16)为单位的值减1

因此,实际的宽为 (21+1)*16 = 352

原文链接:[FFMPEG]SPS和PPS - 简书

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
SPS(Sequence Parameter Set)和PPS(Picture Parameter Set)是H.264视频编码标准中的两个重要参数集,包含了视频编码的一些基本参数信息,比如视频的分辨率、码率、帧率、GOP大小等等。 在使用ffmpeg进行视频推流时,如果服务器报告“没有SPSPPS”错误,通常是因为推送的视频流中没有包含SPSPPS参数集。这种情况下,需要在代码中手动添加SPSPPS参数集。 具体的做法是: 1. 在代码中获取到视频编码器的AVCodecContext结构体。 2. 从AVCodecContext中获取到AVCodecParameters结构体。 3. 从AVCodecParameters中获取SPSPPS参数集的数据。 4. 将SPSPPS数据分别打包成NALU单元并发送给服务器。 以下是参考代码: ``` AVCodecContext* codec_ctx = ...;//获取到编码器的AVCodecContext结构体 AVCodecParameters* codec_params = codec_ctx->codecpar;//获取到编码器的AVCodecParameters结构体 //获取SPSPPS数据 uint8_t* sps_data = codec_params->extradata + 4; uint32_t sps_size = (codec_params->extradata[0] << 8) | codec_params->extradata[1]; uint8_t* pps_data = sps_data + sps_size + 1; uint32_t pps_size = ((pps_data[0] << 8) | pps_data[1]) & 0x00FFFFFF; //打包SPS数据 uint8_t* sps_nalu = new uint8_t[4 + sps_size]; sps_nalu[0] = 0x00; sps_nalu[1] = 0x00; sps_nalu[2] = 0x00; sps_nalu[3] = 0x01; memcpy(sps_nalu + 4, sps_data, sps_size); //打包PPS数据 uint8_t* pps_nalu = new uint8_t[4 + pps_size]; pps_nalu[0] = 0x00; pps_nalu[1] = 0x00; pps_nalu[2] = 0x00; pps_nalu[3] = 0x01; memcpy(pps_nalu + 4, pps_data, pps_size); //发送SPSPPS数据 send_to_server(sps_nalu, 4 + sps_size); send_to_server(pps_nalu, 4 + pps_size); delete[] sps_nalu; delete[] pps_nalu; ``` 其中,send_to_server函数用于将数据发送给服务器,具体实现可以根据自己的需求进行编写。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值