aboutsummaryrefslogtreecommitdiffstats
path: root/libavfilter/sink_buffer.c
diff options
context:
space:
mode:
authorStefano Sabatini <stefasab@gmail.com>2011-12-20 13:08:57 +0100
committerStefano Sabatini <stefasab@gmail.com>2011-12-22 10:09:42 +0100
commit386aee6864c5cfc438785d2421b2f056450da014 (patch)
treeb18e4771036f3dc6bd01271a7fa4d6c7bc1197d7 /libavfilter/sink_buffer.c
parentab6603b1d8d7d15542a9e1bafa580c4f3798c428 (diff)
downloadffmpeg-386aee6864c5cfc438785d2421b2f056450da014.tar.gz
sink_buffer: copy list of provided formats in the context
A list of formats may have been dynamically created by the calling code, and thus should not be referenced by the sink buffer context. Avoid possible invalid data reference.
Diffstat (limited to 'libavfilter/sink_buffer.c')
-rw-r--r--libavfilter/sink_buffer.c49
1 files changed, 38 insertions, 11 deletions
diff --git a/libavfilter/sink_buffer.c b/libavfilter/sink_buffer.c
index e572385419..926362bef8 100644
--- a/libavfilter/sink_buffer.c
+++ b/libavfilter/sink_buffer.c
@@ -26,6 +26,7 @@
#include "libavutil/fifo.h"
#include "avfilter.h"
#include "buffersink.h"
+#include "internal.h"
AVBufferSinkParams *av_buffersink_params_alloc(void)
{
@@ -58,12 +59,12 @@ typedef struct {
AVFifoBuffer *fifo; ///< FIFO buffer of video frame references
/* only used for video */
- const enum PixelFormat *pixel_fmts; ///< list of accepted pixel formats, must be terminated with -1
+ enum PixelFormat *pixel_fmts; ///< list of accepted pixel formats, must be terminated with -1
/* only used for audio */
- const enum AVSampleFormat *sample_fmts; ///< list of accepted sample formats, terminated by AV_SAMPLE_FMT_NONE
- const int64_t *channel_layouts; ///< list of accepted channel layouts, terminated by -1
- const int *packing_fmts; ///< list of accepted packing formats, terminated by -1
+ enum AVSampleFormat *sample_fmts; ///< list of accepted sample formats, terminated by AV_SAMPLE_FMT_NONE
+ int64_t *channel_layouts; ///< list of accepted channel layouts, terminated by -1
+ int *packing_fmts; ///< list of accepted packing formats, terminated by -1
} BufferSinkContext;
#define FIFO_INIT_SIZE 8
@@ -169,16 +170,26 @@ static av_cold int vsink_init(AVFilterContext *ctx, const char *args, void *opaq
return AVERROR(EINVAL);
} else {
#if FF_API_OLD_VSINK_API
- buf->pixel_fmts = (const enum PixelFormat *)opaque;
+ const int *pixel_fmts = (const enum PixelFormat *)opaque;
#else
params = (AVBufferSinkParams *)opaque;
- buf->pixel_fmts = params->pixel_fmts;
+ const int *pixel_fmts = params->pixel_fmts;
#endif
+ buf->pixel_fmts = ff_copy_int_list(pixel_fmts);
+ if (!buf->pixel_fmts)
+ return AVERROR(ENOMEM);
}
return common_init(ctx);
}
+static av_cold void vsink_uninit(AVFilterContext *ctx)
+{
+ BufferSinkContext *buf = ctx->priv;
+ av_freep(&buf->pixel_fmts);
+ return common_uninit(ctx);
+}
+
static int vsink_query_formats(AVFilterContext *ctx)
{
BufferSinkContext *buf = ctx->priv;
@@ -192,7 +203,7 @@ AVFilter avfilter_vsink_buffersink = {
.description = NULL_IF_CONFIG_SMALL("Buffer video frames, and make them available to the end of the filter graph."),
.priv_size = sizeof(BufferSinkContext),
.init = vsink_init,
- .uninit = common_uninit,
+ .uninit = vsink_uninit,
.query_formats = vsink_query_formats,
@@ -225,13 +236,29 @@ static av_cold int asink_init(AVFilterContext *ctx, const char *args, void *opaq
} else
params = (AVABufferSinkParams *)opaque;
- buf->sample_fmts = params->sample_fmts;
- buf->channel_layouts = params->channel_layouts;
- buf->packing_fmts = params->packing_fmts;
+ buf->sample_fmts = ff_copy_int_list (params->sample_fmts);
+ buf->channel_layouts = ff_copy_int64_list(params->channel_layouts);
+ buf->packing_fmts = ff_copy_int_list (params->packing_fmts);
+ if (!buf->sample_fmts || !buf->channel_layouts || !buf->sample_fmts) {
+ av_freep(&buf->sample_fmts);
+ av_freep(&buf->channel_layouts);
+ av_freep(&buf->packing_fmts);
+ return AVERROR(ENOMEM);
+ }
return common_init(ctx);
}
+static av_cold void asink_uninit(AVFilterContext *ctx)
+{
+ BufferSinkContext *buf = ctx->priv;
+
+ av_freep(&buf->sample_fmts);
+ av_freep(&buf->channel_layouts);
+ av_freep(&buf->packing_fmts);
+ return common_uninit(ctx);
+}
+
static int asink_query_formats(AVFilterContext *ctx)
{
BufferSinkContext *buf = ctx->priv;
@@ -256,7 +283,7 @@ AVFilter avfilter_asink_abuffersink = {
.name = "abuffersink",
.description = NULL_IF_CONFIG_SMALL("Buffer audio frames, and make them available to the end of the filter graph."),
.init = asink_init,
- .uninit = common_uninit,
+ .uninit = asink_uninit,
.priv_size = sizeof(BufferSinkContext),
.query_formats = asink_query_formats,