[FFmpeg-devel] [PATCH] lavf: add avformat_transfer_internal_stream_timing_info() and use it in ffmpeg

James Almer jamrial at gmail.com
Tue Sep 13 20:36:46 EEST 2016


On 9/13/2016 5:44 AM, Clément Bœsch wrote:
> From: Clément Bœsch <clement at stupeflix.com>
> 
> In lavf we have access to st->internal->avctx so it's a better place
> than in ffmpeg*.c and will allow moving to codecpar.
> ---
>  doc/APIchanges         |  4 ++++
>  ffmpeg.c               | 52 ++++--------------------------------------
>  libavformat/avformat.h | 21 +++++++++++++++++
>  libavformat/utils.c    | 61 ++++++++++++++++++++++++++++++++++++++++++++++++++
>  libavformat/version.h  |  4 ++--
>  5 files changed, 92 insertions(+), 50 deletions(-)
> 
> diff --git a/doc/APIchanges b/doc/APIchanges
> index 7ac809c..158a0b2 100644
> --- a/doc/APIchanges
> +++ b/doc/APIchanges
> @@ -15,6 +15,10 @@ libavutil:     2015-08-28
>  
>  API changes, most recent first:
>  
> +2016-09-xx - xxxxxxx - lavf 57.49.100 - avformat.h
> +  Add avformat_transfer_internal_stream_timing_info helper to help with stream
> +  copy.
> +
>  2016-08-29 - 4493390 - lavfi 6.58.100 - avfilter.h
>    Add AVFilterContext.nb_threads.
>  
> diff --git a/ffmpeg.c b/ffmpeg.c
> index d858407..b16b4ad 100644
> --- a/ffmpeg.c
> +++ b/ffmpeg.c
> @@ -2909,57 +2909,13 @@ static int transcode_init(void)
>              enc_ctx->bits_per_coded_sample  = dec_ctx->bits_per_coded_sample;
>              enc_ctx->bits_per_raw_sample    = dec_ctx->bits_per_raw_sample;
>  
> -            enc_ctx->time_base = ist->st->time_base;
> -            /*
> -             * Avi is a special case here because it supports variable fps but
> -             * having the fps and timebase differe significantly adds quite some
> -             * overhead
> -             */
> -            if(!strcmp(oc->oformat->name, "avi")) {
> -                if ( copy_tb<0 && ist->st->r_frame_rate.num
> -                               && av_q2d(ist->st->r_frame_rate) >= av_q2d(ist->st->avg_frame_rate)
> -                               && 0.5/av_q2d(ist->st->r_frame_rate) > av_q2d(ist->st->time_base)
> -                               && 0.5/av_q2d(ist->st->r_frame_rate) > av_q2d(dec_ctx->time_base)
> -                               && av_q2d(ist->st->time_base) < 1.0/500 && av_q2d(dec_ctx->time_base) < 1.0/500
> -                     || copy_tb==2){
> -                    enc_ctx->time_base.num = ist->st->r_frame_rate.den;
> -                    enc_ctx->time_base.den = 2*ist->st->r_frame_rate.num;
> -                    enc_ctx->ticks_per_frame = 2;
> -                } else if (   copy_tb<0 && av_q2d(dec_ctx->time_base)*dec_ctx->ticks_per_frame > 2*av_q2d(ist->st->time_base)
> -                                 && av_q2d(ist->st->time_base) < 1.0/500
> -                    || copy_tb==0){
> -                    enc_ctx->time_base = dec_ctx->time_base;
> -                    enc_ctx->time_base.num *= dec_ctx->ticks_per_frame;
> -                    enc_ctx->time_base.den *= 2;
> -                    enc_ctx->ticks_per_frame = 2;
> -                }
> -            } else if(!(oc->oformat->flags & AVFMT_VARIABLE_FPS)
> -                      && strcmp(oc->oformat->name, "mov") && strcmp(oc->oformat->name, "mp4") && strcmp(oc->oformat->name, "3gp")
> -                      && strcmp(oc->oformat->name, "3g2") && strcmp(oc->oformat->name, "psp") && strcmp(oc->oformat->name, "ipod")
> -                      && strcmp(oc->oformat->name, "f4v")
> -            ) {
> -                if(   copy_tb<0 && dec_ctx->time_base.den
> -                                && av_q2d(dec_ctx->time_base)*dec_ctx->ticks_per_frame > av_q2d(ist->st->time_base)
> -                                && av_q2d(ist->st->time_base) < 1.0/500
> -                   || copy_tb==0){
> -                    enc_ctx->time_base = dec_ctx->time_base;
> -                    enc_ctx->time_base.num *= dec_ctx->ticks_per_frame;
> -                }
> -            }
> -            if (   enc_ctx->codec_tag == AV_RL32("tmcd")
> -                && dec_ctx->time_base.num < dec_ctx->time_base.den
> -                && dec_ctx->time_base.num > 0
> -                && 121LL*dec_ctx->time_base.num > dec_ctx->time_base.den) {
> -                enc_ctx->time_base = dec_ctx->time_base;
> -            }
> -
>              if (!ost->frame_rate.num)
>                  ost->frame_rate = ist->framerate;
> -            if(ost->frame_rate.num)
> -                enc_ctx->time_base = av_inv_q(ost->frame_rate);
> +            ost->st->avg_frame_rate = ost->frame_rate;
>  
> -            av_reduce(&enc_ctx->time_base.num, &enc_ctx->time_base.den,
> -                        enc_ctx->time_base.num, enc_ctx->time_base.den, INT_MAX);
> +            ret = avformat_transfer_internal_stream_timing_info(oc->oformat, ost->st, ist->st, copy_tb);
> +            if (ret < 0)
> +                return ret;
>  
>              if (ist->st->nb_side_data) {
>                  ost->st->side_data = av_realloc_array(NULL, ist->st->nb_side_data,
> diff --git a/libavformat/avformat.h b/libavformat/avformat.h
> index 74915a1..389d985 100644
> --- a/libavformat/avformat.h
> +++ b/libavformat/avformat.h
> @@ -2894,6 +2894,27 @@ int av_apply_bitstream_filters(AVCodecContext *codec, AVPacket *pkt,
>                                 AVBitStreamFilterContext *bsfc);
>  #endif
>  
> +enum AVTimebaseCopyFrom {

AVTimebaseSource? CopySource? CopyFrom sounds kinda weird.

> +    AVFMT_TBCF_AUTO = -1,
> +    AVFMT_TBCF_DECODER,
> +    AVFMT_TBCF_DEMUXER,
> +    AVFMT_TBCF_R_FRAMERATE,

What's the deal with r_frame_rate anyway? There's an FF_API define for it as
if it were deprecated, yet the field is not tagged as such and said define is
not wrapping all its uses.


LGTM with or without taking the above nit into consideration. Thanks a lot.



More information about the ffmpeg-devel mailing list