首页 > 解决方案 > H.264 MP4 文件中存储的像素格式在哪里?

问题描述

我正在开发一种将 H.264/AAC RTMP 流转换为有效 MP4 文件的转换器。我基本上完成了。我正在解析 AMF 标签,读取 AVCDecoderConfigurationRecord 和 AACSpecificConfig,我正在生成一个有效的 moov atom 等。

在我的代码中发现并修复了一些错误之后,我得到了一个大部分有效的 MP4 文件。但是,当我尝试阅读视频时,ffprobe出现以下错误:

[mov,mp4,m4a,3gp,3g2,mj2 @ 0x7f9fb4000b80] Failed to open codec in avformat_find_stream_info
    Last message repeated 1 times
[mov,mp4,m4a,3gp,3g2,mj2 @ 0x7f9fb4000b80] Could not find codec parameters for stream 1 (Video: h264 (avc1 / 0x31637661), none, 640x360): unspecified pixel format
Consider increasing the value for the 'analyzeduration' and 'probesize' options

它无法找到像素格式。浏览我的 AVCDecoderConfigurationRecord 解析逻辑(用于生成avcC原子作为原子的一部分avc1),我有以下内容:

// Parsed per: https://github.com/LiminWang/simple-rtmp-server/blob/master/trunk/doc/H.264-AVC-ISO_IEC_14496-15.pdf
var info = parseAVCConfig(packet);

// Fortunately my video sample has one of each of these
// I may need to concatenate multiple in the future
var sps = info.sps[0];
var pps = info.pps[0];

var avcc = box(
    types.avcC,
    new Uint8Array([
        // Version
        0x01,
        // Profile
        info.profile,
        // Profile Compat
        info.compat,
        // Level
        info.level,
        // LengthSizeMinusOne, hard-coded to 4 bytes (copied HLS.js)
        0xfc | 3,
        // 3bit reserved (111) + numOfSequenceParameterSets
        0xE0 | sps.byteLength
    ]
        .concat(Array.from(sps))
        .concat([
            // NumOfPictureParametersets
            pps.byteLength
        ])
        .concat(Array.from(pps))
    )
);

如您所见,avcc原子包含配置文件、兼容性和级别——但之后我只是直接从 AVCDecoderConfigurationRecord 复制 SPS 和 PPS。我没有在原子中定义像素格式,所以我假设它是 SPS 或 PPS 的一部分。

查看 AVCDecoderConfigurationRecord 的规范,没有什么特别称为“像素格式”,但有“chroma_format”、“bit_depth_luma_minus8”和“bit_depth_chroma_minus_8”——但这些仅在配置文件为 100、110、122 或244. 我的个人资料是 66(这些字节对我来说不存在)

目前我正在做的这个概念证明只需要支持一个视频,所以最坏的情况下我可以将像素格式硬编码为yuv420. 但我什至不知道将这些信息放在输出 MP4 中的哪个位置。它进入avcC原子吗?还是avc1原子?还是mvhd原子?

链接:

标签: mp4h.264

解决方案


看看chroma_format_idcRec。ITU-T H.264 (04/2017) - 7.3.2.1.1 序列参数集数据语法。chroma_format_idc是 SPS 的一部分。对于profile_idc 100、110、122、244、44、83、86、118、128、138、139、134 或 135,chroma_format_idc存储在 SPS 内。否则,您假设 1 (= 4:2:0)。

7.4.2.1.1 序列参数集数据语义

chroma_format_idc specifies the chroma sampling relative to the luma sampling as specified in clause 6.2. The value of
chroma_format_idc shall be in the range of 0 to 3, inclusive. When chroma_format_idc is not present, it shall be inferred
to be equal to 1 (4:2:0 chroma format).

推荐阅读