解码ffmpeg从mp4文件中转储的单个(H264)数据包

时间:2019-04-03 23:50:42

标签: c ffmpeg h.264 libavcodec

我用ffmpeg从mp4内的h264视频中转储代表单个帧的数据包

ffmpeg -i video.mp4 -c copy -vframes 1 -map 0:v:0 -f data frame.bin

frame.bin中的数据似乎很好,并且似乎由与mdat中的第一个块/数据包(我不确定正确的术语)完全相同的字节组成原子。

现在我要解码该帧。由于我知道用于创建该数据包的编解码器(h264),因此我认为我可以简单地准备一个编解码器上下文,将所有数据加载到一个数据包中,并使用传统的avcodec_send_packet(codecContext, packet)avcodec_receive_frame()组合。

很遗憾,对avcodec_send_packet的呼叫失败,并且我收到以下错误消息

(-1094995529) Invalid data found when processing input

由于数据包数据的前4个字节是数据包本身的大小,因此我尝试在将缓冲区传递给数据包之前跳过这些字节,但这也失败了。

我跳过某些步骤还是做错了什么?我尝试做的事情甚至可能吗? (请说是:)

1 个答案:

答案 0 :(得分:1)

ITU-T建议书H.264和附件B

推荐H.264是由国际电信联盟 T 电信标准化部门(ITU- T )定义的视频编解码器标准。 免费can be downloaded from their website可用。

该标准定义了一种字节流格式,其最低抽象级别为NALU(网络层抽象单元)。

可以存在32种类型的NALU,尽管大约11种是保留或未使用的。有些带有视频切片数据,有些则没有。 在本讨论的后面部分,两种NALU类型将很重要:SPS(序列参数集)和PPS(图片参数集)。两者都需要对视频片段进行解码,并提供有关流的重要信息,例如流的大小和原始数据的解释。

H.264没有定义如何传输和构建这些NALU。但是,它的确在标准自己的附件B中描述了一种可能的方案。由于缺乏更好的名称,该方案通常称为附件B

该方案包括在NALU的前面加上易于同步的起始代码,这些代码在NALU中不能出现:3字节或4字节模式00 00 0100 00 00 01。然后是NALU的其余部分。此方案在硬件和/或流媒体情况中很流行,因为它可以轻松获取位锁定和字节对齐,定期“带内”发送SPS / PPS,从而允许在任意点调谐到流中以开始解码,并且具有有趣的性质,即可以在NALU之间有效地发送任意数量的0位或字节。

ISO / IEC 14496 MPEG-4和AVCC

MPEG-4是由国际标准组织(ISO)和国际电工委员会(IEC)组成的联合组织,称为运动图像专家组( MPEG)。仅有MPEG-4系列的一些部分是相关的:

    MPEG-4第10部分/高级视频编码(AVC),技术上与ITU-T H.264相同。 免费。 MPEG-4第12部分,ISO基本媒体文件格式(BMFF),定义了可以专用的通用二进制容器文件格式。 免费。 MPEG-4第14部分(MP4),通常专门针对视频的第12部分,并定义了.mp4文件扩展名和格式。这部分非常昂贵( 88瑞士法郎),并且不向公众提供。 MPEG-4第15部分,定义了如何将NALU结构的视频数据(例如第10 / H.264视频)存储在第12部分ISO BMFF中。这部分价格非常昂贵( 198瑞士法郎),并且不向公众提供,但是第14、12和10部分是常用{ {1}}容器,其中包含H.264编码的视频。

AVCC

不幸的是,第15部分还是定义了NALU的新框架的部分。该方案建议将所有SPS / PPS NALU提取到称为“ AVCC ”的“带外”结构中,并用(几乎总是)剥离并替换NALU前面的起始代码前缀。 4个字节的数字,表示以下NALU的大小(以字节为单位)。

此方案在通过视频数据进行快速和随机查找时很流行,并且通过将所有视频解码器配置数据(SPS / PPS)收集在一个标准化的位置,可以在开始时配置一次视频解码器,此后便不必担心有关视频帧大小的动态变化(附件B允许的变化)的意外惊喜。

幸运的是,关于AVCC结构的提示在线存在,并且在AVCC和附件B之间进行翻译的代码也是如此。

您的需求

您似乎需要AVCC->附件B转换。可以使用FFmpeg的位流过滤器h264_mp4toannexb

.mp4