关于TS流的封装和解析

一:MPEG2_TS_H264_AAC_Mux 代码分析

该代码是把H264裸流和AAC(有ADTS头)封装为TS流。
读取本地的H264裸流文件和AAC文件,封装为TS流。 还有一点bug,没有bug的版本在tsmux文件中。

主要是两个函数

int Take_Out_Pes( TsPes * tspes ,unsigned long time_pts,unsigned int frametype,unsigned int * videoframetype )

1:是把原始码流(H264和AAC)封装为PES头的码流。

int PES2TS( TsPes * ts_pes, unsigned int Video_Audio_PID , Ts_Adaptation_field * ts_adaptation_field_Head , Ts_Adaptation_field * ts_adaptation_field_Tail,
            unsigned long  Videopts, unsigned long Adudiopts )

2:是把PES头的码流(H264和AAC)封装为TS头的TS标准流。

二:封装H264(AAC)为TS流
一般情况下,一个nal一个帧。H264的码流组成,我省略了。
1:把码流封装为pes头
H264—>读取一个个的nal,然后把一个个的nal封装为pes头的形式,不懂怎么封装为pes头的,看前面的代码就可以很清晰了。
AAC—>读取AAC音频包,去掉ADTS头,然后给音频包封装为pes头的形式。

2:pes -> ts。把pes头的码流,封装为TS标准流。
在封装成ts流的时候,还需要打入pat和pmt。怎么打入,请看代码。

这里需要注意给pts的赋值:
这里以视频帧率为25HZ,90Khz的视频频率为例:
pts==1/25*90000 = 3600 个clk。

三: TS流的格式
TS流是基于Packet的位流格式,每个包是188个字节(或204个字节,在188个字节后加上了16字节的CRC校验数据,其他格式一样)。整个TS流组成形式如下:
关于TS流的封装和解析_第1张图片

TS流是由一个个Packet(包)构成的,每个包都是由Packet Header(包头)和Packet Data(包数据)组成的。其中Packet Header指示了该Packet是什么属性的,并给出了该Packet Data的数据的唯一网络标识符PID。

Packet Header的说明
关于TS流的封装和解析_第2张图片

PID的值
关于TS流的封装和解析_第3张图片

Packet Header的例子:
关于TS流的封装和解析_第4张图片

关于PAT表
PAT表定义了当前TS流中所有的节目,其PID为0x0000,它是PSI的根节点,要查寻找节目必须从PAT表开始查找。PAT表主要包含频道号码和每一个频道对应的PMT的PID号码。
PAT表的结构体:

typedef struct TS_PAT_Program  
{  
    unsigned program_number   :  16;  //节目号  
    unsigned program_map_PID :  13; // 节目映射表的PID,节目号大于0时对应的PID,每个节目对应一个  
}TS_PAT_Program  

typedef struct TS_PAT  
{  
    unsigned table_id                     : 8; //固定为0x00 ,标志是该表是PAT表  
    unsigned section_syntax_indicator     : 1; //段语法标志位,固定为1  
    unsigned zero                         : 1; //0  
    unsigned reserved_1                   : 2; // 保留位  
     unsigned section_length               : 12; //表示从下一个字段开始到CRC32(含)之间有用的字节数  
    unsigned transport_stream_id          : 16; //该传输流的ID,区别于一个网络中其它多路复用的流  
    unsigned reserved_2                   : 2;// 保留位  
    unsigned version_number               : 5; //范围0-31,表示PAT的版本号  
    unsigned current_next_indicator       : 1; //发送的PAT是当前有效还是下一个PAT有效  
    unsigned section_number               : 8; //分段的号码。PAT可能分为多段传输,第一段为00,以后每个分段加1,最多可能有256个分段  
    unsigned last_section_number          : 8;  //最后一个分段的号码  

    std::vector program;  
    unsigned reserved_3                    : 3; // 保留位  
    unsigned network_PID                    : 13; //网络信息表(NIT)的PID,节目号为0时对应的PID为network_PID  
    unsigned CRC_32                        : 32;  //CRC32校验码  
} TS_PAT;   

关于PMT表
如果一个TS流中含有多个频道,那么就会包含多个PID不同的PMT表。
PMT表中包含的数据如下:
(1) 当前频道中包含的所有Video数据的PID
(2) 当前频道中包含的所有Audio数据的PID
(3) 和当前频道关联在一起的其他数据的PID(如数字广播,数据通讯等使用的PID)

第四:打包流程图
关于TS流的封装和解析_第5张图片

http://blog.csdn.net/zxh821112/article/details/17587215
http://blog.csdn.net/bingqingsuimeng/article/details/9942829
http://blog.csdn.net/max_min_go/article/details/39463675

你可能感兴趣的:(综合)