[FFmpeg-devel] [PATCH 3/4] fftools/ffmpeg: support variable dimension encode
James Almer
jamrial at gmail.com
Mon Jul 29 19:43:51 EEST 2019
On 7/29/2019 11:44 AM, Linjie Fu wrote:
> Flush encoders when dimension change happens, reset draining to resume
> encode.
>
> If encoder doesn't support variable dimension, stop encoding and
> report errors.
>
> Signed-off-by: Linjie Fu <linjie.fu at intel.com>
> ---
> fftools/ffmpeg.c | 13 +++++++++++++
> libavcodec/encode.c | 4 ++++
> 2 files changed, 17 insertions(+)
>
> diff --git a/fftools/ffmpeg.c b/fftools/ffmpeg.c
> index 5d52430..8ceeaaa 100644
> --- a/fftools/ffmpeg.c
> +++ b/fftools/ffmpeg.c
> @@ -130,6 +130,7 @@ static void do_video_stats(OutputStream *ost, int frame_size);
> static BenchmarkTimeStamps get_benchmark_time_stamps(void);
> static int64_t getmaxrss(void);
> static int ifilter_has_all_input_formats(FilterGraph *fg);
> +static void flush_encoders(void);
>
> static int run_as_daemon = 0;
> static int nb_frames_dup = 0;
> @@ -1067,6 +1068,18 @@ static void do_video_out(OutputFile *of,
> InputStream *ist = NULL;
> AVFilterContext *filter = ost->filter->filter;
>
> + /* flush encoders in dynamic resolution encode */
> + if (next_picture && (enc->width != next_picture->width ||
> + enc->height != next_picture->height)) {
> + flush_encoders();
> +
> + if (!(enc->codec->capabilities & AV_CODEC_CAP_VARIABLE_DIMENSIONS)) {
> + av_log(NULL, AV_LOG_ERROR, "Dynamic resolution encode "
> + "is not supported by %s.\n", enc->codec->name);
> + goto error;
> + }
> + }
> +
> if (ost->source_index >= 0)
> ist = input_streams[ost->source_index];
>
> diff --git a/libavcodec/encode.c b/libavcodec/encode.c
> index d12c425..9303bc9 100644
> --- a/libavcodec/encode.c
> +++ b/libavcodec/encode.c
> @@ -389,6 +389,10 @@ int attribute_align_arg avcodec_send_frame(AVCodecContext *avctx, const AVFrame
> if (!avcodec_is_open(avctx) || !av_codec_is_encoder(avctx->codec))
> return AVERROR(EINVAL);
>
> + /* reset draining when encoder is flushed in variable dimensions encoding */
> + if (frame)
> + avctx->internal->draining = 0;
This is an API change that can break some workflows.
avcodec_flush_buffers() is the public function meant to flush an
AVCodecContext.
> +
> if (avctx->internal->draining)
> return AVERROR_EOF;
>
>
More information about the ffmpeg-devel
mailing list