乡下人产国偷v产偷v自拍,国产午夜片在线观看,婷婷成人亚洲综合国产麻豆,久久综合给合久久狠狠狠9

  • <output id="e9wm2"></output>
    <s id="e9wm2"><nobr id="e9wm2"><ins id="e9wm2"></ins></nobr></s>

    • 分享

      將H264與AAC打包Ipad可播放的TS流的總結(jié)

       rookie 2013-05-12

      將H264與AAC打包Ipad可播放的TS流的總結(jié)

      由于要在crtmpserver中實(shí)現(xiàn)Http Live Streaming ,本人花了接近3個(gè)星期的時(shí)間,研究將H264與AAC打包為TS流并能在Ipad上通過HTML5播放,由于沒有任何現(xiàn)成代碼可供參考,打包代碼全部手寫,打包格式主要參考ISO/ICE 18318-1.pdf。期間碰到很多問題,走了不少彎路,符合標(biāo)準(zhǔn)的TS不一定能在Ipad上播放,但是Ipad上播放的TS一定是符合標(biāo)準(zhǔn)的,可以說是TS標(biāo)準(zhǔn)中的特例?,F(xiàn)將遇到的主要問題以及要點(diǎn)總結(jié)如下:

      【打包流程以及相關(guān)圖:】

      【視頻H264到TS注意要點(diǎn):】

      <1>. 如果h264的包大于 65535  的話,可以設(shè)置PES_packet_length為0 ,具體參見ISO/ICE 13818-1.pdf  49 / 174 中關(guān)于PES_packet_length的描述
      打包PES, 直接讀取一幀h264的內(nèi)容, 此時(shí)我們?cè)O(shè)置PES_packet_length的值為0000
      表示不指定PES包的長度,ISO/ICE 13818-1.pdf 49 / 174 有說明,這主要是方便
      當(dāng)一幀H264的長度大于PES_packet_length(2個(gè)字節(jié))能表示的最大長度65535
      的時(shí)候分包的問題, 這里我們?cè)O(shè)置PES_packet_length的長度為0000之后 ,  那么即使該H264視頻幀的長度
      大于65535個(gè)字節(jié)也不需要分多個(gè)PES包存放, 事實(shí)證明這樣做是可以的, ipad可播放
      -----------------

      <2>. PES頭中的stream_id 好像是無所謂,隨便改了幾個(gè)都可以。  不過找到的幾個(gè)可以ipad播放的樣本文件中都設(shè)置的是0xe0
      而在蘋果的http://developer.apple.com/library/ios/#documentation/AudioVideo/Conceptual/HTTP_Live_Streaming_Metadata_Spec/2/2.html
      里面的2.4 PES Stream Format 提供的表里面,使用的是0xbd 表示的是private_stream_id_1,不知道這個(gè)說明是否專門針對(duì)ID3,但是建議設(shè)置為0xeo,我看到的幾個(gè)TS樣本文件都是這么設(shè)置的。
      -----------------

      <3>. 對(duì)于視頻來說PTS和DTS都需要,可以設(shè)置為一樣的,如果只有PTS,沒有DTS是不行的。可以將pts的值賦值給dts,pts_dts_flag的值應(yīng)該設(shè)置為0x03,也就是二進(jìn)制的'11'
      -----------------

      <4>. pmt中的  stream_type = 0x1b 表示 H264  , stream_type = 0x0f 表示AAC
      -----------------

      <5>. ipad不需要pcr都可以播放,可以將pmt頭中的 PCR_PID設(shè)置為0x1fff 表示沒有PCR ,參考ISO/ICE 13818-1.pdf 65 / 174,  在之后的所有關(guān)于adaptation_field中設(shè)置PCR_flag: 00 就可以了,并且在adaptation_field中也不需要寫入pcr部分的值
      -----------------

      <6>. 在每一幀的視頻幀被打包到pes的時(shí)候,其開頭一定要加上 00 00 00 01 09 xx  這個(gè)nal。否則就有問題
      蘋果官網(wǎng)有如下說明:
      https://developer.apple.com/library/ios/#documentation/networkinginternet/conceptual/streamingmediaguide/FrequentlyAskedQuestions/FrequentlyAskedQuestions.html

      10.These settings are the current recommendations. There are also certain requirements.
      The current mediastreamsegmenter tool works only with MPEG-2 Transport Streams as defined in ISO/IEC 13818.
      The transport stream must contain H.264 (MPEG-4, part 10) video and AAC or MPEG audio.
      If AAC audio is used, it must have ADTS headers. H.264 video access units must use Access Unit Delimiter NALs,
      and must be in unique PES packets.

      其中 H.264 video access units must use Access Unit Delimiter NALs  中的 Access Unit Delimiter NAL 在H264的文檔中是09 ,但是有什么用,我也不太清楚。根據(jù)我的實(shí)驗(yàn)09后面的一個(gè)字節(jié)好像設(shè)置成什么都可以,但是不能設(shè)置為00
      -----------------

      <7>. 關(guān)于pts的計(jì)算方法

      // 1s = 90000 time scale , 一幀就應(yīng)該是  90000/video_frame_rate 個(gè)timescale
      static uint32_t video_frame_rate = 30;
      static uint32_t video_pts_increment = 90000 / video_frame_rate;   //用一秒鐘除以幀率,得到每一幀應(yīng)該耗時(shí)是多少,單位是 timescale單位
      static uint64_t video_pts = 0;

      在以后的計(jì)算中,每生成一幀的ts,該幀的pts值應(yīng)該是 video_pts += video_pts_increment; 偽代碼如下:

      while(..)
      {
         ReadH264(h264_buffer)
         PacketTS(h264_buffer,out_ts_buffer,video_pts);
         video_pts += video_pts_increment;
      }


      <8>. 音頻應(yīng)該是只需要pts,不需要dts。
      音頻pts的計(jì)算方法同上,只不過不是通過幀率,而是通過采樣率。
      uint32_t audio_pts_increment = (90000 * audio_samples_per_frame) / audio_sample_rate;
      上面的偽代碼就不貼了。

      <9>. 關(guān)于pat,pmt的插入時(shí)間,實(shí)際上pat,pmt是要連續(xù)插入到ts流中的,并不是開始插入之后就完了。因?yàn)閠s要保證從任何時(shí)候都可以開始播放。目前我是每4幀視頻(這4幀H264可能被打包成很多的ts包,而不止4包)插入一次pat,pmt包。

      <10>. PES音視頻數(shù)據(jù)包的ts頭中的continuity_counter 必須是連續(xù)的,從小到大的,當(dāng)增長到15之后再從0開始循環(huán)。第一包可以不從0開始。但是之后的continuity_counter 必須是連續(xù)的,并且是按照步長1增長的。continuity_counter的增長相對(duì)于所有PID相同的包他們的增長是獨(dú)立的,例如第一個(gè)PAT包其continuity_counter值是0,那么第二個(gè)PAT包的continuity_counter是1。  第一個(gè)PMT包其continuity_counter值是2,第二個(gè)PMT包其continuity_counter值是3。  

      【音頻AAC到TS注意要點(diǎn):】

      aac不需要設(shè)置DTS,只要PTS就可以了,加上DTS可能還播放不了

      aac打包成PES的時(shí)候,要想在ipad上播放必須設(shè)置PES_packet_length的長度,而視頻可以設(shè)置為0,但是音頻必須設(shè)置為正確的長度值,aac的長度不可能超過65535,所以也不可能導(dǎo)致PES_packet_length溢出。
      否則ipad播放不了。但是QQ影音可以播放。這也許是ipad的特性。

       //data_len:AAC音頻裸流的長度
       // 3:PES頭
       //5: 如果是音頻的話會(huì)有5個(gè)字節(jié)的PTS
      _ts_packet_pes_header.PES_packet_length_16bit = data_len + 3 + 5 ;

      【關(guān)于CRC32校驗(yàn)算法:】
      static uint32_t crc32table[256] = {   
      0x00000000, 0x04c11db7, 0x09823b6e, 0x0d4326d9, 0x130476dc, 0x17c56b6b,   
      0x1a864db2, 0x1e475005, 0x2608edb8, 0x22c9f00f, 0x2f8ad6d6, 0x2b4bcb61,   
      0x350c9b64, 0x31cd86d3, 0x3c8ea00a, 0x384fbdbd, 0x4c11db70, 0x48d0c6c7,   
      0x4593e01e, 0x4152fda9, 0x5f15adac, 0x5bd4b01b, 0x569796c2, 0x52568b75,   
      0x6a1936c8, 0x6ed82b7f, 0x639b0da6, 0x675a1011, 0x791d4014, 0x7ddc5da3,   
      0x709f7b7a, 0x745e66cd, 0x9823b6e0, 0x9ce2ab57, 0x91a18d8e, 0x95609039,   
      0x8b27c03c, 0x8fe6dd8b, 0x82a5fb52, 0x8664e6e5, 0xbe2b5b58, 0xbaea46ef,   
      0xb7a96036, 0xb3687d81, 0xad2f2d84, 0xa9ee3033, 0xa4ad16ea, 0xa06c0b5d,   
      0xd4326d90, 0xd0f37027, 0xddb056fe, 0xd9714b49, 0xc7361b4c, 0xc3f706fb,   
      0xceb42022, 0xca753d95, 0xf23a8028, 0xf6fb9d9f, 0xfbb8bb46, 0xff79a6f1,   
      0xe13ef6f4, 0xe5ffeb43, 0xe8bccd9a, 0xec7dd02d, 0x34867077, 0x30476dc0,   
      0x3d044b19, 0x39c556ae, 0x278206ab, 0x23431b1c, 0x2e003dc5, 0x2ac12072,   
      0x128e9dcf, 0x164f8078, 0x1b0ca6a1, 0x1fcdbb16, 0x018aeb13, 0x054bf6a4,   
      0x0808d07d, 0x0cc9cdca, 0x7897ab07, 0x7c56b6b0, 0x71159069, 0x75d48dde,   
      0x6b93dddb, 0x6f52c06c, 0x6211e6b5, 0x66d0fb02, 0x5e9f46bf, 0x5a5e5b08,   
      0x571d7dd1, 0x53dc6066, 0x4d9b3063, 0x495a2dd4, 0x44190b0d, 0x40d816ba,   
      0xaca5c697, 0xa864db20, 0xa527fdf9, 0xa1e6e04e, 0xbfa1b04b, 0xbb60adfc,   
      0xb6238b25, 0xb2e29692, 0x8aad2b2f, 0x8e6c3698, 0x832f1041, 0x87ee0df6,   
      0x99a95df3, 0x9d684044, 0x902b669d, 0x94ea7b2a, 0xe0b41de7, 0xe4750050,   
      0xe9362689, 0xedf73b3e, 0xf3b06b3b, 0xf771768c, 0xfa325055, 0xfef34de2,   
      0xc6bcf05f, 0xc27dede8, 0xcf3ecb31, 0xcbffd686, 0xd5b88683, 0xd1799b34,   
      0xdc3abded, 0xd8fba05a, 0x690ce0ee, 0x6dcdfd59, 0x608edb80, 0x644fc637,   
      0x7a089632, 0x7ec98b85, 0x738aad5c, 0x774bb0eb, 0x4f040d56, 0x4bc510e1,   
      0x46863638, 0x42472b8f, 0x5c007b8a, 0x58c1663d, 0x558240e4, 0x51435d53,   
      0x251d3b9e, 0x21dc2629, 0x2c9f00f0, 0x285e1d47, 0x36194d42, 0x32d850f5,   
      0x3f9b762c, 0x3b5a6b9b, 0x0315d626, 0x07d4cb91, 0x0a97ed48, 0x0e56f0ff,   
      0x1011a0fa, 0x14d0bd4d, 0x19939b94, 0x1d528623, 0xf12f560e, 0xf5ee4bb9,   
      0xf8ad6d60, 0xfc6c70d7, 0xe22b20d2, 0xe6ea3d65, 0xeba91bbc, 0xef68060b,   
      0xd727bbb6, 0xd3e6a601, 0xdea580d8, 0xda649d6f, 0xc423cd6a, 0xc0e2d0dd,   
      0xcda1f604, 0xc960ebb3, 0xbd3e8d7e, 0xb9ff90c9, 0xb4bcb610, 0xb07daba7,   
      0xae3afba2, 0xaafbe615, 0xa7b8c0cc, 0xa379dd7b, 0x9b3660c6, 0x9ff77d71,   
      0x92b45ba8, 0x9675461f, 0x8832161a, 0x8cf30bad, 0x81b02d74, 0x857130c3,   
      0x5d8a9099, 0x594b8d2e, 0x5408abf7, 0x50c9b640, 0x4e8ee645, 0x4a4ffbf2,   
      0x470cdd2b, 0x43cdc09c, 0x7b827d21, 0x7f436096, 0x7200464f, 0x76c15bf8,   
      0x68860bfd, 0x6c47164a, 0x61043093, 0x65c52d24, 0x119b4be9, 0x155a565e,   
      0x18197087, 0x1cd86d30, 0x029f3d35, 0x065e2082, 0x0b1d065b, 0x0fdc1bec,   
      0x3793a651, 0x3352bbe6, 0x3e119d3f, 0x3ad08088, 0x2497d08d, 0x2056cd3a,   
      0x2d15ebe3, 0x29d4f654, 0xc5a92679, 0xc1683bce, 0xcc2b1d17, 0xc8ea00a0,   
      0xd6ad50a5, 0xd26c4d12, 0xdf2f6bcb, 0xdbee767c, 0xe3a1cbc1, 0xe760d676,   
      0xea23f0af, 0xeee2ed18, 0xf0a5bd1d, 0xf464a0aa, 0xf9278673, 0xfde69bc4,   
      0x89b8fd09, 0x8d79e0be, 0x803ac667, 0x84fbdbd0, 0x9abc8bd5, 0x9e7d9662,   
      0x933eb0bb, 0x97ffad0c, 0xafb010b1, 0xab710d06, 0xa6322bdf, 0xa2f33668,   
      0xbcb4666d, 0xb8757bda, 0xb5365d03, 0xb1f740b4
      };

      uint32_t CRC32(const uint8_t *data, int len)
      {   
          int i;   
          uint32_t crc = 0xFFFFFFFF;       
          for(i = 0; i < len; i++)
          crc = (crc << 8) ^ crc32table[((crc >> 24) ^ *data++) & 0xFF];       
          return crc;
      }

      【關(guān)于TS流中的填充字節(jié)】

      TS流中有2中不同的填充形式,因?yàn)門S每一包要求是188個(gè)字節(jié),當(dāng)不足188個(gè)字節(jié)的時(shí)候, 必須要補(bǔ)充到188個(gè)字節(jié),這就涉及到填充的問題。

      <1>. 如果TS包中承載的是PSI數(shù)據(jù)(PAT,PMT等),那么其填充是在該包的最后一個(gè)有效字節(jié)的后面填充0xFF直到滿足188個(gè)字節(jié)為止。
      解碼器會(huì)丟棄這些字節(jié),具體說明參考 ISO_IEC 13818-1.pdf   60 / 174

      <2>. 如果TS包中承載的是PES數(shù)據(jù),那么當(dāng)不足188個(gè)字節(jié)的時(shí)候,需要使用adaptation_field 這個(gè)域,也就是指定TS包中的adaptation_field_control的值來控制payload與adaptation_field的承載關(guān)系,同時(shí)指定PES中的adaptation_field_length指定填充多少字節(jié),具體的填充字節(jié)值應(yīng)該是隨意的建議使用FF,并且此adaptation_field的使用好像只能在PES中使用。   ISO_IEC 13818-1.pdf   39 / 174

        本站是提供個(gè)人知識(shí)管理的網(wǎng)絡(luò)存儲(chǔ)空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點(diǎn)。請(qǐng)注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊一鍵舉報(bào)。
        轉(zhuǎn)藏 分享 獻(xiàn)花(0

        0條評(píng)論

        發(fā)表

        請(qǐng)遵守用戶 評(píng)論公約

        類似文章 更多