简体   繁体   English

解码H264 / RTSP流后未设置PTS

[英]PTS not set after decoding H264/RTSP stream

Question : What does the Libav/FFmpeg decoding pipeline need in order to produce valid presentation timestamps (PTS) in the decoded AVFrames? 问题为了在解码的AVFrame中生成有效的演示时间戳(PTS),Libav / FFmpeg解码流水线需要什么?

I'm decoding an H264 stream received via RTSP. 我正在解码通过RTSP收到的H264流。 I use Live555 to parse H264 and feed the stream to my LibAV decoder. 我使用Live555解析H264并将流提供给我的LibAV解码器。 Decoding and displaying is working fine, except I'm not using timestamp info and get some stuttering. 解码和显示工作正常,除了我没有使用时间戳信息并得到一些口吃。

After getting a frame with avcodec_decode_video2 , the presentation timestamp (PTS) is not set. 使用avcodec_decode_video2获取帧后,未设置演示时间戳(PTS)。

I need the PTS in order to find out for how long each frame needs to be displayed, and avoid any stuttering. 我需要PTS才能找出每帧需要显示多长时间,并避免任何口吃。

Notes on my pipeline 关于我的管道的说明

  • I get the SPS/PPS information via Live555, I copy these values to my AVCodecContext->extradata . 我通过AVCodecContext->extradata获取SPS / PPS信息,我将这些值复制到我的AVCodecContext->extradata
  • I also send the SPS and PPS to my decoder as NAL units, with the appended {0,0,0,1} startcode. 我还将SPS和PPS作为NAL单元发送到我的解码器,附加{0,0,0,1}起始码。
  • Live555 provides presentation timestamps for each packet, these are in most cases not monotonically increasing. Live555为每个数据包提供演示时间戳,在大多数情况下,这些时间戳不会单调增加。 The stream contains B-frames. 该流包含B帧。
  • My AVCodecContext->time_base is not valid, value is 0/2. 我的AVCodecContext->time_base无效,值为0/2。

Unclear: 目前还不清楚:

  • Where exactly should I set the NAL PTS coming from my H264 sink (Live555)? 我应该在哪里设置来自H264接收器(Live555)的NAL PTS? As the AVPacket->dts, pts, none, or both? 作为AVPacket-> dts,pts,none或两者兼而有之?
  • Why is my time_base value not valid? 为什么我的time_base值无效? Where is this information? 这些信息在哪里?
  • According to the RTP payload spec . 根据RTP有效载荷规范 It seems that 看起来

The RTP timestamp is set to the sampling timestamp of the content. RTP时间戳设置为内容的采样时间戳。 A 90 kHz clock rate MUST be used. 必须使用90 kHz时钟速率。

  • Does this mean that I must always asume a 1/90000 timebase for the decoder? 这是否意味着我必须始终为解码器设置1/90000时基? What if some other value is specified in the SPS? 如果在SPS中指定了其他值,该怎么办?

Copy the live555 pts into the avpacket pts. 将live555 pts复制到avpacket pts。 Process the packet with avcodec_decode_video2, and then retrieve the pts from avframe->pkt_pts, these will be monotonically increasing. 使用avcodec_decode_video2处理数据包,然后从avframe-> pkt_pts中检索pts,这些将单调增加。

There is no need to set anything in the codec context, apart from setting the SPS and PPS in the AVCodecContex extradata 除了在AVCodecContex extradata中设置SPS和PPS之外,无需在编解码器上下文中设置任何内容

You can find a good example in VLC's github: Setting AVPacket pts: https://github.com/videolan/vlc/blob/master/modules/codec/avcodec/video.c#L983 你可以在VLC的github中找到一个很好的例子:设置AVPacket点: https//github.com/videolan/vlc/blob/master/modules/codec/avcodec/video.c#L983

Decoding AVPacket into AVFrame: https://github.com/videolan/vlc/blob/master/modules/codec/avcodec/video.c#L1014 将AVPacket解码为AVFrame: https//github.com/videolan/vlc/blob/master/modules/codec/avcodec/video.c#L1014

Retrieving from AVFrame pts: https://github.com/videolan/vlc/blob/master/modules/codec/avcodec/video.c#L1078 从AVFrame中检索: https//github.com/videolan/vlc/blob/master/modules/codec/avcodec/video.c#L1078

avcodec_decode_video2() reorders the frames so that decode order and presentation order is the same. avcodec_decode_video2()重新排序帧,使解码顺序和呈现顺序相同。 Even if you somehow convince ffmpeg to give you PTS on the decoded frame it should be the same as DTS. 即使你以某种方式说服ffmpeg在解码帧上给你PTS它应该和DTS一样。

//
// decode a video frame
//

avcodec_decode_video2
(
    ctxt->video_st->codec,
    frame,
    &is_finished,
    buffer
);

if (buffer->dts != AV_NOPTS_VALUE)
{
    //
    // you should end up here
    //
    pts = buffer->dts;
}
else
{
    pts = 0;
}

//
// adjust time base
//
pts *= av_q2d(ctxt->video_st->time_base);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM