X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavfilter%2Fbuffersrc.c;h=29c01285cd2ef98a5cb4c58fdf9ad78324aed0db;hb=bd96c54fe4819b3ca9a975e2083d67f4443c559b;hp=e0ff7e4dd84c9c2a72cf9e4cc9d5dab7d60c294f;hpb=94346ab593f3fc0822f11d3e3f378f9944ad2d40;p=ffmpeg diff --git a/libavfilter/buffersrc.c b/libavfilter/buffersrc.c index e0ff7e4dd84..29c01285cd2 100644 --- a/libavfilter/buffersrc.c +++ b/libavfilter/buffersrc.c @@ -25,9 +25,9 @@ #include +#include "libavutil/avassert.h" #include "libavutil/channel_layout.h" #include "libavutil/common.h" -#include "libavutil/fifo.h" #include "libavutil/frame.h" #include "libavutil/imgutils.h" #include "libavutil/internal.h" @@ -43,17 +43,17 @@ typedef struct BufferSourceContext { const AVClass *class; - AVFifoBuffer *fifo; AVRational time_base; ///< time_base to set in the output link AVRational frame_rate; ///< frame_rate to set in the output link unsigned nb_failed_requests; - unsigned warning_limit; /* video only */ int w, h; enum AVPixelFormat pix_fmt; AVRational pixel_aspect; +#if FF_API_SWS_PARAM_OPTION char *sws_param; +#endif AVBufferRef *hw_frames_ctx; @@ -64,7 +64,6 @@ typedef struct BufferSourceContext { uint64_t channel_layout; char *channel_layout_str; - int got_format_from_params; int eof; } BufferSourceContext; @@ -106,7 +105,6 @@ int av_buffersrc_parameters_set(AVFilterContext *ctx, AVBufferSrcParameters *par switch (ctx->filter->outputs[0].type) { case AVMEDIA_TYPE_VIDEO: if (param->format != AV_PIX_FMT_NONE) { - s->got_format_from_params = 1; s->pix_fmt = param->format; } if (param->width > 0) @@ -126,7 +124,6 @@ int av_buffersrc_parameters_set(AVFilterContext *ctx, AVBufferSrcParameters *par break; case AVMEDIA_TYPE_AUDIO: if (param->format != AV_SAMPLE_FMT_NONE) { - s->got_format_from_params = 1; s->sample_fmt = param->format; } if (param->sample_rate > 0) @@ -152,33 +149,6 @@ int attribute_align_arg av_buffersrc_add_frame(AVFilterContext *ctx, AVFrame *fr return av_buffersrc_add_frame_flags(ctx, frame, 0); } -static int av_buffersrc_add_frame_internal(AVFilterContext *ctx, - AVFrame *frame, int flags); - -int attribute_align_arg av_buffersrc_add_frame_flags(AVFilterContext *ctx, AVFrame *frame, int flags) -{ - AVFrame *copy = NULL; - int ret = 0; - - if (frame && frame->channel_layout && - av_get_channel_layout_nb_channels(frame->channel_layout) != frame->channels) { - av_log(ctx, AV_LOG_ERROR, "Layout indicates a different number of channels than actually present\n"); - return AVERROR(EINVAL); - } - - if (!(flags & AV_BUFFERSRC_FLAG_KEEP_REF) || !frame) - return av_buffersrc_add_frame_internal(ctx, frame, flags); - - if (!(copy = av_frame_alloc())) - return AVERROR(ENOMEM); - ret = av_frame_ref(copy, frame); - if (ret >= 0) - ret = av_buffersrc_add_frame_internal(ctx, copy, flags); - - av_frame_free(©); - return ret; -} - static int push_frame(AVFilterGraph *graph) { int ret; @@ -193,13 +163,18 @@ static int push_frame(AVFilterGraph *graph) return 0; } -static int av_buffersrc_add_frame_internal(AVFilterContext *ctx, - AVFrame *frame, int flags) +int attribute_align_arg av_buffersrc_add_frame_flags(AVFilterContext *ctx, AVFrame *frame, int flags) { BufferSourceContext *s = ctx->priv; AVFrame *copy; int refcounted, ret; + if (frame && frame->channel_layout && + av_get_channel_layout_nb_channels(frame->channel_layout) != frame->channels) { + av_log(ctx, AV_LOG_ERROR, "Layout indicates a different number of channels than actually present\n"); + return AVERROR(EINVAL); + } + s->nb_failed_requests = 0; if (!frame) @@ -229,15 +204,10 @@ static int av_buffersrc_add_frame_internal(AVFilterContext *ctx, } - if (!av_fifo_space(s->fifo) && - (ret = av_fifo_realloc2(s->fifo, av_fifo_size(s->fifo) + - sizeof(copy))) < 0) - return ret; - if (!(copy = av_frame_alloc())) return AVERROR(ENOMEM); - if (refcounted) { + if (refcounted && !(flags & AV_BUFFERSRC_FLAG_KEEP_REF)) { av_frame_move_ref(copy, frame); } else { ret = av_frame_ref(copy, frame); @@ -247,14 +217,8 @@ static int av_buffersrc_add_frame_internal(AVFilterContext *ctx, } } - if ((ret = av_fifo_generic_write(s->fifo, ©, sizeof(copy), NULL)) < 0) { - if (refcounted) - av_frame_move_ref(frame, copy); - av_frame_free(©); - return ret; - } - - if ((ret = ctx->output_pads[0].request_frame(ctx->outputs[0])) < 0) + ret = ff_filter_frame(ctx->outputs[0], copy); + if (ret < 0) return ret; if ((flags & AV_BUFFERSRC_FLAG_PUSH)) { @@ -279,20 +243,22 @@ static av_cold int init_video(AVFilterContext *ctx) { BufferSourceContext *c = ctx->priv; - if (!(c->pix_fmt != AV_PIX_FMT_NONE || c->got_format_from_params) || !c->w || !c->h || + if (c->pix_fmt == AV_PIX_FMT_NONE || !c->w || !c->h || av_q2d(c->time_base) <= 0) { av_log(ctx, AV_LOG_ERROR, "Invalid parameters provided.\n"); return AVERROR(EINVAL); } - if (!(c->fifo = av_fifo_alloc(sizeof(AVFrame*)))) - return AVERROR(ENOMEM); - - av_log(ctx, AV_LOG_VERBOSE, "w:%d h:%d pixfmt:%s tb:%d/%d fr:%d/%d sar:%d/%d sws_param:%s\n", + av_log(ctx, AV_LOG_VERBOSE, "w:%d h:%d pixfmt:%s tb:%d/%d fr:%d/%d sar:%d/%d\n", c->w, c->h, av_get_pix_fmt_name(c->pix_fmt), c->time_base.num, c->time_base.den, c->frame_rate.num, c->frame_rate.den, - c->pixel_aspect.num, c->pixel_aspect.den, (char *)av_x_if_null(c->sws_param, "")); - c->warning_limit = 100; + c->pixel_aspect.num, c->pixel_aspect.den); + +#if FF_API_SWS_PARAM_OPTION + if (c->sws_param) + av_log(ctx, AV_LOG_WARNING, "sws_param option is deprecated and ignored\n"); +#endif + return 0; } @@ -314,7 +280,9 @@ static const AVOption buffer_options[] = { { "pixel_aspect", "sample aspect ratio", OFFSET(pixel_aspect), AV_OPT_TYPE_RATIONAL, { .dbl = 0 }, 0, DBL_MAX, V }, { "time_base", NULL, OFFSET(time_base), AV_OPT_TYPE_RATIONAL, { .dbl = 0 }, 0, DBL_MAX, V }, { "frame_rate", NULL, OFFSET(frame_rate), AV_OPT_TYPE_RATIONAL, { .dbl = 0 }, 0, DBL_MAX, V }, +#if FF_API_SWS_PARAM_OPTION { "sws_param", NULL, OFFSET(sws_param), AV_OPT_TYPE_STRING, .flags = V }, +#endif { NULL }, }; @@ -336,7 +304,7 @@ static av_cold int init_audio(AVFilterContext *ctx) BufferSourceContext *s = ctx->priv; int ret = 0; - if (!(s->sample_fmt != AV_SAMPLE_FMT_NONE || s->got_format_from_params)) { + if (s->sample_fmt == AV_SAMPLE_FMT_NONE) { av_log(ctx, AV_LOG_ERROR, "Sample format was not set or was invalid\n"); return AVERROR(EINVAL); } @@ -369,9 +337,6 @@ static av_cold int init_audio(AVFilterContext *ctx) return AVERROR(EINVAL); } - if (!(s->fifo = av_fifo_alloc(sizeof(AVFrame*)))) - return AVERROR(ENOMEM); - if (!s->time_base.num) s->time_base = (AVRational){1, s->sample_rate}; @@ -379,7 +344,6 @@ static av_cold int init_audio(AVFilterContext *ctx) "tb:%d/%d samplefmt:%s samplerate:%d chlayout:%s\n", s->time_base.num, s->time_base.den, av_get_sample_fmt_name(s->sample_fmt), s->sample_rate, s->channel_layout_str); - s->warning_limit = 100; return ret; } @@ -387,13 +351,7 @@ static av_cold int init_audio(AVFilterContext *ctx) static av_cold void uninit(AVFilterContext *ctx) { BufferSourceContext *s = ctx->priv; - while (s->fifo && av_fifo_size(s->fifo)) { - AVFrame *frame; - av_fifo_generic_read(s->fifo, &frame, sizeof(frame), NULL); - av_frame_free(&frame); - } av_buffer_unref(&s->hw_frames_ctx); - av_fifo_freep(&s->fifo); } static int query_formats(AVFilterContext *ctx) @@ -463,29 +421,11 @@ static int config_props(AVFilterLink *link) static int request_frame(AVFilterLink *link) { BufferSourceContext *c = link->src->priv; - AVFrame *frame; - int ret; - - if (!av_fifo_size(c->fifo)) { - if (c->eof) - return AVERROR_EOF; - c->nb_failed_requests++; - return AVERROR(EAGAIN); - } - av_fifo_generic_read(c->fifo, &frame, sizeof(frame), NULL); - - ret = ff_filter_frame(link, frame); - return ret; -} - -static int poll_frame(AVFilterLink *link) -{ - BufferSourceContext *c = link->src->priv; - int size = av_fifo_size(c->fifo); - if (!size && c->eof) + if (c->eof) return AVERROR_EOF; - return size/sizeof(AVFrame*); + c->nb_failed_requests++; + return AVERROR(EAGAIN); } static const AVFilterPad avfilter_vsrc_buffer_outputs[] = { @@ -493,13 +433,12 @@ static const AVFilterPad avfilter_vsrc_buffer_outputs[] = { .name = "default", .type = AVMEDIA_TYPE_VIDEO, .request_frame = request_frame, - .poll_frame = poll_frame, .config_props = config_props, }, { NULL } }; -AVFilter ff_vsrc_buffer = { +const AVFilter ff_vsrc_buffer = { .name = "buffer", .description = NULL_IF_CONFIG_SMALL("Buffer video frames, and make them accessible to the filterchain."), .priv_size = sizeof(BufferSourceContext), @@ -518,13 +457,12 @@ static const AVFilterPad avfilter_asrc_abuffer_outputs[] = { .name = "default", .type = AVMEDIA_TYPE_AUDIO, .request_frame = request_frame, - .poll_frame = poll_frame, .config_props = config_props, }, { NULL } }; -AVFilter ff_asrc_abuffer = { +const AVFilter ff_asrc_abuffer = { .name = "abuffer", .description = NULL_IF_CONFIG_SMALL("Buffer audio frames, and make them accessible to the filterchain."), .priv_size = sizeof(BufferSourceContext),