• fmp4打包H265视频流


    1 fmp4打包H265视频流


    本文只介绍H265/HEVC的fmp4封包与fmp4封包H264不通的地方,其他有关mp4基础知识及fmp4封装和264视频流相关内容参照:
    fmp4打包H264详解

    1.1 码流存储和传输格式介绍

    这里主要介绍下H264和H265存储和传输格式的基本知识介绍,如果知识想了解如何fmp4封装,本节可以跳过。

    H265和H265标准中指定了视频如何编码成独立的包,但如何存储和传输这些包却未作规范,虽然标准中包含了一个Annex附件,里面描述了一种可能的格式Annex B,但这并不是一个必须要求的格式,为了针对不同的存储传输需求,出现了两种打包方法:一种即Annex B格式,另一种称为AVCC/HVCC格式。

    1.1.1 Annex B封装格式

    Annex B格式及我们厂家的HECVC或者H264码流封装格式,其格式如下:
    [StartCode][NALU Header][NALU PAYLOAD]
    起始码一般为00000001或者000001开头,通过定位起始码,解码器就可以识别NALU的边界,为了防止编码数据中存在与起始码相同的数据,在构建NALU时,需要将数据中的0x000000,0x000001,0x000002,0x000003中插入防竞争字节(Emulation Prevention Bytes)0x03,使其变为:

    0x000000 = 0x0000 03 00
    0x000001 = 0x0000 03 01
    0x000002 = 0x0000 03 02
    0x000003 = 0x0000 03 03
    
    • 1
    • 2
    • 3
    • 4

    因此,解码器在检测到0x000003时,将0x03抛弃,恢复原始数据。

    1.1.2 AVCC封装格式

    AVCC格式不使用StartCode作为NALU的分界,而是在每个NALU前都加上一个指定NALU长度的大端格式表示的前缀,这个前缀可以是1、2或4个字节,所以在解析AVCC格式的时候需要将指定的前缀字节数的值保存在一个头部对象中,通常称为extradata或者sequence header,其中SPS和PPS数据也需要保存在extradata中。这里需要注意SPS和PPS都是去掉起始头的
    H.264 extradata语法如下:
    extradata

    其中第5字节的后2位NALULengthSizeMinusOne表示的就是NALU size的字节数,NALU前缀长度减1,假设前缀长度为4,那么这个值应该为3。如果此之为3表示此码流所有nalu前需要加上四字节size,去掉起始码。

    fmp4打包H264详解文章中我们已经使用过此种封装方式来打包程avcc的box,详见此文章中的avcC box解释:moov->trak->media->minf->stbl->stsd->avc1->avcC,需要trak带有此box表示mp4封装的H264码流,此trackID的流中mdat的box中封装的是去除起00000001始码的码流,解码时需要注意这里虽然去掉了起始码,但是但防竞争字节还是有的,需要转换一下。

    1.1.2 HVCC封装格式

    与H.264类似,H.265(HEVC)码流也有两种封装格式,一种是用起始码作为分界的Annex B格式,另一种则是在NALU头添加NALU长度前缀的格式称为HVCC,与AVCC类似,需要通过extradata来保存视频流的编解码参数,其格式定义如下:
    extradata

    表示extradata后半段是一段格式重复的数组数据,其中numOfArrays表示数组的个数,一般为0x03,表示包含VPS/SPS/PPS,
    封装方式示意如下(《ISO-14496-15 AVC file format》中有详细说明):

    // The CodecPrivate syntax shall follow the
    // syntax of HEVCDecoderConfigurationRecord
    // defined in ISO/IEC 14496-15.
    //
    // The number zero (0) shall be written to
    // the configurationVersion variable until
    // official finalization of 14496-15, 3rd ed.
    //
    // After its finalization, this field and the
    // following CodecPrivate structure shall
    // follow the definition of the
    // HEVCDecoderConfigurationRecord in 14496-15.
    
    unsigned int(8)  configurationVersion;
    unsigned int(2)  general_profile_space;
    unsigned int(1)  general_tier_flag;
    unsigned int(5)  general_profile_idc;
    unsigned int(32) general_profile_compatibility_flags;
    unsigned int(48) general_constraint_indicator_flags;
    unsigned int(8)  general_level_idc;
    bit(4) reserved = ‘1111’b;
    unsigned int(12) min_spatial_segmentation_idc;
    bit(6) reserved = ‘111111’b;
    unsigned int(2)  parallelismType;
    bit(6) reserved = ‘111111’b;
    unsigned int(2)  chromaFormat;
    bit(5) reserved = ‘11111’b;
    unsigned int(3)  bitDepthLumaMinus8;
    bit(5) reserved = ‘11111’b;
    unsigned int(3)  bitDepthChromaMinus8;
    bit(16) avgFrameRate;
    bit(2)  constantFrameRate;
    bit(3)  numTemporalLayers;
    bit(1)  temporalIdNested;
    unsigned int(2) lengthSizeMinusOne;
    unsigned int(8) numOfArrays;
    for (j=0; j < numOfArrays; j++) {
      bit(1) array_completeness;
      unsigned int(1)  reserved = 0;
      unsigned int(6)  NAL_unit_type;
      unsigned int(16) numNalus;
      for (i=0; i< numNalus; i++) {
        unsigned int(16) nalUnitLength;
        bit(8*nalUnitLength) nalUnit;
      }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    bits描述备注
    1array_completeness默认0
    1reserved默认0
    6NAL_unit_type帧类型
    16numNalus此种类型的帧个数,一般为1,如果大于1,下面进入循环
    16nalUnitLength2字节表示附加帧的长度
    NNALU data附加帧的数据

    一般在fmp4封装时,hvcC box的box负载采用此种方式封装,其中相关的编码参数获取是从HEVC的SPS帧中分析出来的,附加帧数据VPS/SPS/PPS。

    1.2 fmp4封装H265

    fmp4封装H265,仅有两个box需要修改ftyp box和stsd box

    1.2.1 ftyp box

    ftyp box格式与H264封装一样,其中compatible brands赋值为isom、iso2、mp41,HEVC ftype示例如下:

    0x00,0x00,0x00,0x1C,//box size
    0x66,0x74,0x79,0x70,//ftyp的ascii 
    0x69, 0x73, 0x6f, 0x6d, // major_brand: isom
    0x0, 0x0, 0x02, 0x0, // minor_version: 0x01
    0x69, 0x73, 0x6F, 0x6D, // isom
    0x69, 0x73, 0x6F, 0x32, // iso2
    0x6d, 0x70, 0x34, 0x31, // mp41
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    经过验证,这里直接用isom也能够正常播放,所以此box可与H264保持一致。

    1.2.2 stsd box

    有关H265的fmp4打包,此box需要把avc1 box替换成hvc1 box,hvc1 box的封装格式与avc1类似,只是把avcC子box替换程hvcC,其格式如下:
    [4字节size][4字节type][6字节预留][2字节data_reference_index][2字节pre_defined][2字节预留][12字节pre_defined][2字节宽][2字节高][4字节horizresolution][四字节 vertresolution][4字节预留][2字节视频帧数量][Compression name长度][Compression name][Compression name预留位(32-Compression name长度-1)][2字节深度][2字节pre_defined][hvcC box][btrt box]

    这里主要对与H264不同的hvcC box进行说明,其结构如下:
    [4字节size][4字节type][hevc extradata]

    其中hevc extradata格式见1.1.2 HVCC封装格式,其后半段附加了VPS、SPS、PPS帧数据,HVCC附加的解码信息字段可从SPS中解析得到,具体解析方式参照文章:
    https://www.cnblogs.com/sddai/p/14366110.html

    sps1
    sps2
    sps3

    示例及详解如下:

    00 00 00 6E 68 76 63 43 01 01 60 00 00 00 B0 00 00 00 00 00 7B F0 00 FC FD F8 F8 00 00 03 03 20 00 01 00 17 40 01 0C 01 FF FF 01 60 00 00 03 00 B0 00 00 03 00 00 03 00 7B AC 09 21 00 01 00 22 42 01 01 01 60 00 00 03 00 B0 00 00 03 00 00 03 00 7B A0 03 C0 80 10 E5 8D AE 49 32 F4 DC 04 04 04 02 22 00 01 00 07 44 01 C0 F2 F0 3C 90 
    
    • 1
    • 00 00 00 6E:box长度为110
    • 68 76 63 43: boxtype=hvcC
    • 后续为hevc extradata,具体解释按照上文方式解析

    以下是用mp4reader解析的结果,有关fmp4示例文件及mp4reader安装包获取,请关注微信公众号壹零仓,发送fmp4,获取:
    hvcC

  • 相关阅读:
    C# 图解教程 第5版 —— 第7章 深入理解类
    【DesignMode】设计模式简介
    基于ssm的商场管理信息系统的设计与实现
    C++opencv 色彩空间转换和保存
    USACO Training 1.5 Arithmetic Progressions
    让Python更优雅更易读(第一集)
    Java之文件流(26个Demo)
    Vue 实现拖拽模块(二)自定义拖拽组件位置
    ~/.bashrc配置文件说明
    sed与awk
  • 原文地址:https://blog.csdn.net/water1209/article/details/126889172