From 1c481df1164ff720e6a472c0643829aa07c88cd3 Mon Sep 17 00:00:00 2001 From: MrDave Date: Sat, 29 Jul 2017 21:09:02 -0600 Subject: [PATCH] Additional PTS Changes 1. Revise the PTS to allow for the capture of the first image by revising the initialization of last_pts 2. Elminate the incrementing by 1 when we have timing issues since this puts all subsequent frames out of sync with timing/pts problems 3. Unref the packets when encode and PTS functions return errors to prevent leaks. 4. Revise logging to report more values when in test mode. --- event.c | 6 +++--- ffmpeg.c | 20 ++++++++++++-------- 2 files changed, 15 insertions(+), 11 deletions(-) diff --git a/event.c b/event.c index f2cb3ea2..bffdb204 100644 --- a/event.c +++ b/event.c @@ -732,7 +732,7 @@ static void event_ffmpeg_newfile(struct context *cnt, cnt->ffmpeg_output->vbr = cnt->conf.ffmpeg_vbr; cnt->ffmpeg_output->start_time.tv_sec = currenttime_tv->tv_sec; cnt->ffmpeg_output->start_time.tv_usec = currenttime_tv->tv_usec; - cnt->ffmpeg_output->last_pts = 0; + cnt->ffmpeg_output->last_pts = -1; cnt->ffmpeg_output->base_pts = 0; cnt->ffmpeg_output->gop_cnt = 0; cnt->ffmpeg_output->codec_name = codec; @@ -763,7 +763,7 @@ static void event_ffmpeg_newfile(struct context *cnt, cnt->ffmpeg_output_debug->vbr = cnt->conf.ffmpeg_vbr; cnt->ffmpeg_output_debug->start_time.tv_sec = currenttime_tv->tv_sec; cnt->ffmpeg_output_debug->start_time.tv_usec = currenttime_tv->tv_usec; - cnt->ffmpeg_output_debug->last_pts = 0; + cnt->ffmpeg_output_debug->last_pts = -1; cnt->ffmpeg_output_debug->base_pts = 0; cnt->ffmpeg_output_debug->gop_cnt = 0; cnt->ffmpeg_output_debug->codec_name = codec; @@ -819,7 +819,7 @@ static void event_ffmpeg_timelapse(struct context *cnt, cnt->ffmpeg_timelapse->vbr = cnt->conf.ffmpeg_vbr; cnt->ffmpeg_timelapse->start_time.tv_sec = currenttime_tv->tv_sec; cnt->ffmpeg_timelapse->start_time.tv_usec = currenttime_tv->tv_usec; - cnt->ffmpeg_timelapse->last_pts = 0; + cnt->ffmpeg_timelapse->last_pts = -1; cnt->ffmpeg_timelapse->base_pts = 0; cnt->ffmpeg_timelapse->test_mode = 0; cnt->ffmpeg_timelapse->gop_cnt = 0; diff --git a/ffmpeg.c b/ffmpeg.c index 1cde3a9d..edec2af0 100644 --- a/ffmpeg.c +++ b/ffmpeg.c @@ -425,22 +425,21 @@ static int ffmpeg_set_pts(struct ffmpeg *ffmpeg, const struct timeval *tv1){ pts_interval = ((1000000L * (tv1->tv_sec - ffmpeg->start_time.tv_sec)) + tv1->tv_usec - ffmpeg->start_time.tv_usec); if (pts_interval < 0){ /* This can occur when we have pre-capture frames. Reset start time of video. */ - ffmpeg->start_time.tv_sec = tv1->tv_sec ; - ffmpeg->start_time.tv_usec = tv1->tv_usec ; + ffmpeg_reset_movie_start_time(ffmpeg, tv1); pts_interval = 0; } ffmpeg->pkt.pts = av_rescale_q(pts_interval,(AVRational){1, 1000000L},ffmpeg->video_st->time_base) + ffmpeg->base_pts; if (ffmpeg->test_mode == 1){ - MOTION_LOG(INF, TYPE_ENCODER, NO_ERRNO, "%s: ms interval %d PTS %d timebase %d-%d",pts_interval,ffmpeg->pkt.pts,ffmpeg->video_st->time_base.num,ffmpeg->video_st->time_base.den); + MOTION_LOG(INF, TYPE_ENCODER, NO_ERRNO, "%s: PTS %d Base PTS %d ms interval %d timebase %d-%d",ffmpeg->pkt.pts,ffmpeg->base_pts,pts_interval,ffmpeg->video_st->time_base.num,ffmpeg->video_st->time_base.den); } if (ffmpeg->pkt.pts <= ffmpeg->last_pts){ - //We have a problem with our motion loop timing and sending frames. Increment by just 1 to at least keep frame in movie. - ffmpeg->pkt.pts = ffmpeg->last_pts + 1; + //We have a problem with our motion loop timing and sending frames or the rounding into the PTS. if (ffmpeg->test_mode == 1){ - MOTION_LOG(INF, TYPE_ENCODER, NO_ERRNO, "%s: BAD TIMING!! PTS reset to incremental counter new PTS %d ",ffmpeg->pkt.pts); + MOTION_LOG(INF, TYPE_ENCODER, NO_ERRNO, "%s: BAD TIMING!! Frame skipped."); } + return -1; } ffmpeg->pkt.dts = ffmpeg->pkt.pts; ffmpeg->last_pts = ffmpeg->pkt.pts; @@ -703,11 +702,16 @@ static int ffmpeg_put_frame(struct ffmpeg *ffmpeg, const struct timeval *tv1){ ffmpeg->pkt.size = 0; retcd = ffmpeg_encode_video(ffmpeg); - if (retcd != 0) return retcd; + if (retcd != 0){ + MOTION_LOG(ERR, TYPE_ENCODER, NO_ERRNO, "%s: Error while encoding picture"); + my_packet_unref(ffmpeg->pkt); + return retcd; + } retcd = ffmpeg_set_pts(ffmpeg, tv1); if (retcd < 0) { - MOTION_LOG(ERR, TYPE_ENCODER, NO_ERRNO, "%s: Error while setting PTS"); + //If there is an error, it has already been reported. + my_packet_unref(ffmpeg->pkt); return -1; }