2012-07-04 222 views
19

最近我有机会使用两台通过RTSP流式传输H264的设备。 而我遇到了一些问题,试图使用FFmpeg库来解压缩这个流。FFmpeg无法解码H264流/帧数据

每次 “avcodec_decode_video2” 之称 - FFmpeg的只是说是这样的:

[H264 @ 00339220]无框架!

我原H264流帧数据开始是这样的: “ 88 84 21 3F F8 F8 0D ......” (据我了解这0x65表示它是一个IDR帧? )

用于一个装置的其它的帧开始,如: “ 9A 22 07 F3 48 4E CC ....”

和用于其它装置 - 这样的:“ 9A 25 C1 45 1C 62 39 ....“

  • 我在这里丢失了一些帧数据吗?
  • FFmpeg是否需要设置一些额外的参数?

我原以为至少“”字节处开始的帧数据......但是这是我的本钱..

回答

21

好,设法把事情加工。

  • 我需要包括序列(SPS)和图像参数集 (PPS),用于我的帧数据发送帧到FFmpeg的之前。
  • 我需要在SPS和PPS数据后添加4个额外字节“00 00 00 01”。

这里是在我的意思是一点点的画面: enter image description here

字节“65 88 ......”是我原来的帧数据开始的地方。

此SPS和PPS信息未包括在RTP数据包中。我正在使用Live555库进行RTSP流式传输,因此我使用了子会话“fmtp_spropparametersets”函数来获取我需要的内容。这些信息是Base64编码的。 (示例:类似这样的“Z0KAKNoC0EkQ,aM48gA ==”)请注意,“”有两个“参数”SPS和PPS,并且这些参数没有包含“00 00 00 01”,所以您需要添加它们。

一些示例代码(我在这里使用Qt库):

QByteArray  ba   = pSubSession->fmtp_spropparametersets(); 
QList<QByteArray> recordsList = ba.split(','); 

for (int i = 0; i < recordsList.size(); i++) 
{ 
    mExtraData.append(char(0x00)); 
    mExtraData.append(char(0x00)); 
    mExtraData.append(char(0x00)); 
    mExtraData.append(char(0x01)); 

    mExtraData += QByteArray::fromBase64(recordsList.at(i)); 
} 

现在每帧我做这样的事情:

QByteArray ba = QByteArray(4, 0); // Prepare the "00 00 00 01" 
      ba[3] = 0x01; 

mpTrackVideo->buffer.insert(0, mExtraData); 
mpTrackVideo->buffer.insert(mExtraData.size(), ba); 

年前我原本以为H264流支持集成到我的项目中,直到我有机会用其他设备测试它...... 因此,您需要记住,某些设备可能会为每个I帧发送SPS和PPS数据......有些设备可能不会!