-12909 使用帧内刷新解码 h264 流时出错
-12909 error decoding h264 stream with intra-refresh
我正在制作一个 iOS 应用程序,它使用视频工具箱解码 h264 流。我在 PC 上使用 ffmpeg 创建流并使用 RTP 将其发送到 iPhone。当我使用此命令创建它时,它运行良好:
ffmpeg -y -f:v rawvideo -c:v rawvideo -s 1280x720 -pix_fmt bgra -r 30 -an -i - -pix_fmt yuv420p -c:v libx264 -tune zerolatency -preset fast -b:v 5M -refs 1 -g 30 -profile:v high -level 4.1 -f rtp rtp://192.168.1.100:5678
iPhone接收并显示所有帧。但是,当我启用帧内刷新时
-intra-refresh 1
调用 VTDecompressionSessionDecodeFrame()
时解码失败,错误代码为 -12909
(模拟器上为 -8969
)。
我负责处理 UDP 数据包以提取 NAL 单元,因此我对这个过程进行了三重检查并丢弃了这部分代码的问题。
我没有找到任何关于Video-toolbox不支持帧内刷新的信息,所以问题是,Video-toolbox支持帧内刷新吗?如果是这样,我是否在 ffmpeg 端遗漏了一些导致视频工具箱不支持流的内容?
除了使用 CMVideoFormatDescriptionCreateFromH264ParameterSets()
使用 SPS 和 PPS 数据创建它之外,我是否必须向 CMVideoFormatDescriptionRef
添加一些内容?
- 是的,视频工具箱支持帧内刷新
- 不,与ffmpeg无关
- 不,不需要对
CMVideoFormatDescriptionRef
做任何特别的事情
我想通了,每次接收 SPS 和 PPS NALU 时我都在创建一个新的 VTDecompressionSession
,因此解码器正在丢失上下文。
它在没有帧内刷新的情况下工作,因为在那种情况下,在 SPS 和 PPS 之后立即接收到完整的 I 帧,因此它不需要来自先前帧的上下文。
启用帧内刷新后,只有第一帧是完整的 I 帧,然后解码器依赖于先前帧的上下文并且必须使用相同的 VTDecompressionSession
。
我正在制作一个 iOS 应用程序,它使用视频工具箱解码 h264 流。我在 PC 上使用 ffmpeg 创建流并使用 RTP 将其发送到 iPhone。当我使用此命令创建它时,它运行良好:
ffmpeg -y -f:v rawvideo -c:v rawvideo -s 1280x720 -pix_fmt bgra -r 30 -an -i - -pix_fmt yuv420p -c:v libx264 -tune zerolatency -preset fast -b:v 5M -refs 1 -g 30 -profile:v high -level 4.1 -f rtp rtp://192.168.1.100:5678
iPhone接收并显示所有帧。但是,当我启用帧内刷新时
-intra-refresh 1
调用 VTDecompressionSessionDecodeFrame()
时解码失败,错误代码为 -12909
(模拟器上为 -8969
)。
我负责处理 UDP 数据包以提取 NAL 单元,因此我对这个过程进行了三重检查并丢弃了这部分代码的问题。
我没有找到任何关于Video-toolbox不支持帧内刷新的信息,所以问题是,Video-toolbox支持帧内刷新吗?如果是这样,我是否在 ffmpeg 端遗漏了一些导致视频工具箱不支持流的内容?
除了使用 CMVideoFormatDescriptionCreateFromH264ParameterSets()
使用 SPS 和 PPS 数据创建它之外,我是否必须向 CMVideoFormatDescriptionRef
添加一些内容?
- 是的,视频工具箱支持帧内刷新
- 不,与ffmpeg无关
- 不,不需要对
CMVideoFormatDescriptionRef
做任何特别的事情
我想通了,每次接收 SPS 和 PPS NALU 时我都在创建一个新的 VTDecompressionSession
,因此解码器正在丢失上下文。
它在没有帧内刷新的情况下工作,因为在那种情况下,在 SPS 和 PPS 之后立即接收到完整的 I 帧,因此它不需要来自先前帧的上下文。
启用帧内刷新后,只有第一帧是完整的 I 帧,然后解码器依赖于先前帧的上下文并且必须使用相同的 VTDecompressionSession
。