AVFrame:如何获取/替换平面数据缓冲区和大小?

时间:2018-07-18 12:17:14

标签: ffmpeg h.264 libavcodec libav gstreamer-1.0

我正在研究gstreamer1.0-libav(1.6.3),试图从gstreamer 0.10移植基于定制FPGA的H264视频加速。

过去曾经由gstreamer 0.10中的一个简单的malloc分配数据平面(YUV),因此我们只需将AVFrame.data [i]指针替换为视频加速核心中的内存指针即可。在gstreamer 1.12中似乎更加复杂。

对于初学者,我尝试将YUV平面从AVFrame.data [i]复制到单独的缓冲区-很好!因为我还没有看到获取AVFrame.data [i]大小的直接方法,并且我认识到data [0],data [1],data [2]似乎在单个连续缓冲区中,所以我简单地使用了Y平面的大小为(data [1]-数据[0]),U / V平面的大小为(data [2]-data [1])。效果很好,预计会出现以下一种情况:

  • 输入分辨率为800x600或更高的H264流
  • 相机被遮盖(夹克,手...)

使用如上所述确定的大小,这会在V平面(数据[2])的内存中产生SEGFAULT。在遮盖相机之前,流将显示为完全正常...出于某种原因,黑屏会更改平面尺寸?

我的最终目标是用我的自定义内存分配(用于进一步处理)替换gstreamer分配的data [i]指针...这些缓冲区的确切分配位置,我可以更改它们以及如何获取每个缓冲区的大小平面(数据[0],数据[1],数据[2])?

1 个答案:

答案 0 :(得分:0)

请勿使用骇客之类的东西,例如(data [1]-data [0])飞机可能会有填充物。
您可以这样获得缓冲区大小:

Y = data[0]  
U = data[1]  
V = data[2]

YUV444/422 Format:
Size of data[0] is linesize[0] * AVFrame::height
Size of data[1] is linesize[1] * AVFrame::height
Size of data[2] is linesize[2] * AVFrame::height

YUV420 Format:
Size of data[0] is linesize[0] * AVFrame::height
Size of data[1] is linesize[1] * (AVFrame::height / 2)
Size of data[2] is linesize[2] * (AVFrame::height / 2)

如果存在 alpha通道,请使用与Y相同的公式。
希望有帮助。