FLV文件格式解析

FLV文件格式解析

FLV 是FLASH VIDEO的简称,FLV流媒体格式是随着Flash MX的推出发展而来的视频格式。由于它形成的文件极小、加载速度极快,使得网络观看视频文件成为可能,它的出现有效地解决了视频文件导入Flash后,使导出的SWF文件体积庞大,不能在网络上很好的使用等问题。

FLV由FLV头+tagSize+tag....构成,如图:

 

每个PreviousTagSize表示前一个tag的长度,占32bits。

FLV Header

 

FLV头的长度为固定的9字节:Signature(3 Byte)+Version(1 Byte)+Flags(1 Bypte)+DataOffset(4 Byte)

  • 前3字节是标识符,固定为0x46,0x4C,0x56,是’FLV‘的ASSIC码。

  • 第4字节是version,表示版本号,一般为1。

  • 第5字节,前5位保留置为0,第6位表示audio是否存在(1表示存在,0表示不存在),第7位保留置为0,第8位表示video是否存在(1表示存在,0表示不存在)。

  • 第6、7、8、9字节DataOffset表示FLV header长度,固定为0x 00 00 00 09。

FLV Body

FLV的body由一系列PreviousTagSize+tag组成

  • PreviousTagSize占4个字节,表示前一个tag的size。由于PreviousTagSize0前面没有tag所以PreviousTagSize0=0x 00 00 00 00。

  • tag分三种类型video,audio,scripts(或称meta)

Tag

tag结构如下图:

 

  • tag类型,1个字节。8表示audio,9表示video,18表示script。ffmpeg关于tag type定义如下:

    enum FlvTagType {
        FLV_TAG_TYPE_AUDIO = 0x08,
        FLV_TAG_TYPE_VIDEO = 0x09,
        FLV_TAG_TYPE_META  = 0x12,
    };
  • tag data size 3个字节。表示tag data的长度。从streamd id 后算起。

  • Timestreamp时间戳 3个字节。

  • TimestampExtended 时间戳扩展字段1个字节,可将时间戳扩展为32bits,此字段为高8位。

  • stream id 3个字节。总是0。

  • tag数据部分。

Audio Tag

 

紧跟着stream id后结算tag的具体数据,如果TAG包中的TagType==8时,就表示这个TAG是audio。StreamID之后的数据就表示是AudioTagHeaderAudioTagHeader如上图所示,占1个字节,包含audio的各种信息。其后就是audio tag的data部分。

这里有一个特例,如果音频格式(SoundFormat)是10 = AAC,AudioTagHeader中会多出1个字节的数据AACPacketType,这个字段来表示AACAUDIODATA的类型:0 = AAC sequence header,1 = AAC raw。

 

AAC sequence header也就是包含了AudioSpecificConfigAudioSpecificConfig包含着一些更加详细音频的信息,AudioSpecificConfig的定义在ISO14496-31.6.2.1 AudioSpecificConfig。在FLV的文件中,一般情况下 AAC sequence header 这种包只出现1次,而且是第一个audio tag

AAC raw 这种包含的就是音频ES流了,也就是audio payload。

Video Tag

 

如果TAG包中的TagType==9时,就表示这个TAG是video。StreamID之后的数据就表示是VideoTagHeaderVideoTagHeader结构如图。

VideoTagHeader的头1个字节,也就是接跟着StreamID的1个字节包含着视频帧类型及视频CodecID最基本信息。VideoTagHeader之后跟着的就是VIDEODATA数据。

这里也有一个特例,如果视频的格式是AVC(H.264)的话,VideoTagHeader会多出4个字节的信息AVCPacketTypeCompositionTime

IF AVCPacketType == 0 AVCDecoderConfigurationRecord(AVC sequence header) IF AVCPacketType == 1 One or more NALUs (Full frames are required)

IF AVCPacketType == 2 end of squence(lower level NALU sequence ender is not required or supported)

AVCDecoderConfigurationRecord包含着是H.264解码相关的sps和pps信息,给AVC解码器发送数据流之前一定要把sps和pps信息送出,否则的话解码器不能正常解码。AVCDecoderConfigurationRecord在FLV文件中一般情况只出现1次,也就是第一个video tag。

 

Script Tag

 

如果TAG包中的TagType==18时,就表示这个TAG是script

Script Tag一般只有一个,是flv的第一个Tag,用于存放flv的信息,比如duration、audiodatarate、creator、width等。

所有数据都是以数据类型+(数据长度)+数据的格式出现的,数据类型占1byte,数据长度看数据类型是否存在,后面才是数据。

一般来说,该Tag Data结构包含两个AMF包。AMF(Action Message Format)是Adobe设计的一种通用数据封装格式,第一个AMF包封装字符串类型数据,用来装入一个“onMetaData”标志,第二个AMF包封装一个数组类型,这个数组中包含了音视频信息项的名称和值。

示例:

下图是一个FLV文件示例

 

 

可以看见文件前3个字节是'FLV'的ASSIC码0x46 4C 56,第一个绿框表示PreviousTagSize0值为0,第二个绿框PreviousTagSize1 = 0x 00 00 0B FC。PreviousTagSize0之后是第一个tag,紫色框为0x12=18表示这是一个script tag,黄色框0x 00 0B F1表示tag data长为3057字节(从stream id后算起)。可以看到stream id后第一个字节地址为0x18,所以tag结束的地址为0xBF1+0x18-1=0xC08,所以PreviousTagSize1首地址为0xC09,由上图可知PreviousTagSize1 = 0x 00 00 0B FC=3068=tag header length(11) + tag data length(3057)。

PreviousTagSize1 后是第2个tag,tag type = 0x09表示是视频。

感兴趣的可以关注微信公众号Video Coding

 

发布了88 篇原创文章 · 获赞 108 · 访问量 25万+
展开阅读全文

没有更多推荐了,返回首页

©️2019 CSDN 皮肤主题: 像素格子 设计师: CSDN官方博客

分享到微信朋友圈

×

扫一扫,手机浏览