首页 > 代码库 > H.264码流格式

H.264码流格式

H.264码流格式

SODB: String Of Data Bits 原始数据比特流, 熵编码输出结果, 以bit为单位。
RBSP: Raw Byte Sequence Payload 原始字节序列负载, 在SODB最后加上trailing bits.
EBSP: Extent Byte Sequence Payload 扩展字节序列负载, RBSP里面加入防伪起始码字节(0x03)
NALU: Network Abstraction Layer Units. 网络抽象层单元, 在EBSP前面加上一个字节的NALU type.

H264起始码

一个H.264码流就是很多个NALU的串接,NALU之间靠起始码分隔,找不到起始码就找不到下一个NALU的开始,也就找不到当前NALU的结束。因此起始码对于H.264码流非常重要。
在264码流里面一般会用到两种起始码,4字节 0x00 00 00 01或者3字节 0x00 00 01. 有说用4字节起始码用于SPS,PPS和每帧的第一个Slice,3字节起始码用于其他的NALU。
由于起始码起到分隔NALU的作用,因此如果RBSP里面恰好也出现了0x00 00 01的字节组合,解码端就会误认为是下一个NALU的开始,这样会造成解码错误。因此要破坏掉RBSP里面的这种字节组合,这就是RBSP到EBSP的过程。


SODB -> RBSP
RBSP = SODB + trailing bits, 以字节为单位
SODB是以比特为单位的,熵编码的最后一个比特可能是一个字节的任意位,这时候要先增加1个rbsp_stop_one_bit, 然后是n个rbsp_alignement_zero_bit.例如SODB写到一个字节的2比特,会补1个"1",5个"0"比特,写满这个字节。


RBSP -> EBSP
EBSP = RBSP 加入防伪起始码字节(0x03)
遍历RBSP找 0x00 00 0z z=1,2,3的字节组合,如果发现有这样的组合,就在0z之前强行插入0x03字节,破坏掉类似起始码的字节组合.
具体点说就是做一下的操作。(为什么对02/03也做这个操作?这点不理解)
0x00 00 00 -----> 0x00 00 03 00
0x00 00 01 -----> 0x00 00 03 01
0x00 00 02 -----> 0x00 00 03 02
0x00 00 03 -----> 0x00 00 03 03
而解码段,在接收到一个NALU后,对于EBSP,扫描一遍剔除 0x 00 00 03 0z (z=0,1,2,3)之间的03字节,生成RBSP。

EBSP -> NALU  
NALU = 1字节 NALU type | EBSP
NALU type:    1 bit        |      2bits         |     5bits
            禁止比特 恒为0     nalu重要性比特    nalu类型比特

H.264码流格式