Since we do not support "standalone" filters not attached to an AVFilterGraph, we should not have a public function to create such filters. In addition that function is horribly named, the action it does cannot be possibly described as "opening" a filter.tags/n2.0
| @@ -16,6 +16,7 @@ API changes, most recent first: | |||||
| 2013-xx-xx - lavfi 3.8.0 | 2013-xx-xx - lavfi 3.8.0 | ||||
| Move all content from avfiltergraph.h to avfilter.h. Deprecate | Move all content from avfiltergraph.h to avfilter.h. Deprecate | ||||
| avfilterhraph.h, user applications should include just avfilter.h | avfilterhraph.h, user applications should include just avfilter.h | ||||
| Add avfilter_graph_alloc_filter(), deprecate avfilter_open(). | |||||
| 2013-xx-xx - lavfi 3.7.0 - avfilter.h | 2013-xx-xx - lavfi 3.7.0 - avfilter.h | ||||
| Add AVFilter.priv_class for exporting filter options through the AVOptions API | Add AVFilter.priv_class for exporting filter options through the AVOptions API | ||||
| @@ -352,17 +352,16 @@ static const AVClass avfilter_class = { | |||||
| .child_class_next = filter_child_class_next, | .child_class_next = filter_child_class_next, | ||||
| }; | }; | ||||
| int avfilter_open(AVFilterContext **filter_ctx, AVFilter *filter, const char *inst_name) | |||||
| AVFilterContext *ff_filter_alloc(const AVFilter *filter, const char *inst_name) | |||||
| { | { | ||||
| AVFilterContext *ret; | AVFilterContext *ret; | ||||
| *filter_ctx = NULL; | |||||
| if (!filter) | if (!filter) | ||||
| return AVERROR(EINVAL); | |||||
| return NULL; | |||||
| ret = av_mallocz(sizeof(AVFilterContext)); | ret = av_mallocz(sizeof(AVFilterContext)); | ||||
| if (!ret) | if (!ret) | ||||
| return AVERROR(ENOMEM); | |||||
| return NULL; | |||||
| ret->av_class = &avfilter_class; | ret->av_class = &avfilter_class; | ||||
| ret->filter = filter; | ret->filter = filter; | ||||
| @@ -404,8 +403,7 @@ int avfilter_open(AVFilterContext **filter_ctx, AVFilter *filter, const char *in | |||||
| ret->input_count = ret->nb_inputs; | ret->input_count = ret->nb_inputs; | ||||
| #endif | #endif | ||||
| *filter_ctx = ret; | |||||
| return 0; | |||||
| return ret; | |||||
| err: | err: | ||||
| av_freep(&ret->inputs); | av_freep(&ret->inputs); | ||||
| @@ -416,9 +414,17 @@ err: | |||||
| ret->nb_outputs = 0; | ret->nb_outputs = 0; | ||||
| av_freep(&ret->priv); | av_freep(&ret->priv); | ||||
| av_free(ret); | av_free(ret); | ||||
| return AVERROR(ENOMEM); | |||||
| return NULL; | |||||
| } | } | ||||
| #if FF_API_AVFILTER_OPEN | |||||
| int avfilter_open(AVFilterContext **filter_ctx, AVFilter *filter, const char *inst_name) | |||||
| { | |||||
| *filter_ctx = ff_filter_alloc(filter, inst_name); | |||||
| return *filter_ctx ? 0 : AVERROR(ENOMEM); | |||||
| } | |||||
| #endif | |||||
| void avfilter_free(AVFilterContext *filter) | void avfilter_free(AVFilterContext *filter) | ||||
| { | { | ||||
| int i; | int i; | ||||
| @@ -602,8 +602,8 @@ void avfilter_uninit(void); | |||||
| /** | /** | ||||
| * Register a filter. This is only needed if you plan to use | * Register a filter. This is only needed if you plan to use | ||||
| * avfilter_get_by_name later to lookup the AVFilter structure by name. A | * avfilter_get_by_name later to lookup the AVFilter structure by name. A | ||||
| * filter can still by instantiated with avfilter_open even if it is not | |||||
| * registered. | |||||
| * filter can still by instantiated with avfilter_graph_alloc_filter even if it | |||||
| * is not registered. | |||||
| * | * | ||||
| * @param filter the filter to register | * @param filter the filter to register | ||||
| * @return 0 if the registration was succesfull, a negative value | * @return 0 if the registration was succesfull, a negative value | ||||
| @@ -628,6 +628,7 @@ AVFilter *avfilter_get_by_name(const char *name); | |||||
| */ | */ | ||||
| AVFilter **av_filter_next(AVFilter **filter); | AVFilter **av_filter_next(AVFilter **filter); | ||||
| #if FF_API_AVFILTER_OPEN | |||||
| /** | /** | ||||
| * Create a filter instance. | * Create a filter instance. | ||||
| * | * | ||||
| @@ -636,8 +637,11 @@ AVFilter **av_filter_next(AVFilter **filter); | |||||
| * @param filter the filter to create an instance of | * @param filter the filter to create an instance of | ||||
| * @param inst_name Name to give to the new instance. Can be NULL for none. | * @param inst_name Name to give to the new instance. Can be NULL for none. | ||||
| * @return >= 0 in case of success, a negative error code otherwise | * @return >= 0 in case of success, a negative error code otherwise | ||||
| * @deprecated use avfilter_graph_alloc_filter() instead | |||||
| */ | */ | ||||
| attribute_deprecated | |||||
| int avfilter_open(AVFilterContext **filter_ctx, AVFilter *filter, const char *inst_name); | int avfilter_open(AVFilterContext **filter_ctx, AVFilter *filter, const char *inst_name); | ||||
| #endif | |||||
| /** | /** | ||||
| * Initialize a filter. | * Initialize a filter. | ||||
| @@ -720,6 +724,24 @@ typedef struct AVFilterGraph { | |||||
| */ | */ | ||||
| AVFilterGraph *avfilter_graph_alloc(void); | AVFilterGraph *avfilter_graph_alloc(void); | ||||
| /** | |||||
| * Create a new filter instance in a filter graph. | |||||
| * | |||||
| * @param graph graph in which the new filter will be used | |||||
| * @param filter the filter to create an instance of | |||||
| * @param name Name to give to the new instance (will be copied to | |||||
| * AVFilterContext.name). This may be used by the caller to identify | |||||
| * different filters, libavfilter itself assigns no semantics to | |||||
| * this parameter. May be NULL. | |||||
| * | |||||
| * @return the context of the newly created filter instance (note that it is | |||||
| * also retrievable directly through AVFilterGraph.filters or with | |||||
| * avfilter_graph_get_filter()) on success or NULL or failure. | |||||
| */ | |||||
| AVFilterContext *avfilter_graph_alloc_filter(AVFilterGraph *graph, | |||||
| const AVFilter *filter, | |||||
| const char *name); | |||||
| /** | /** | ||||
| * Get a filter instance with name name from graph. | * Get a filter instance with name name from graph. | ||||
| * | * | ||||
| @@ -81,12 +81,12 @@ int avfilter_graph_create_filter(AVFilterContext **filt_ctx, AVFilter *filt, | |||||
| { | { | ||||
| int ret; | int ret; | ||||
| if ((ret = avfilter_open(filt_ctx, filt, name)) < 0) | |||||
| goto fail; | |||||
| *filt_ctx = avfilter_graph_alloc_filter(graph_ctx, filt, name); | |||||
| if (!*filt_ctx) | |||||
| return AVERROR(ENOMEM); | |||||
| if ((ret = avfilter_init_filter(*filt_ctx, args, opaque)) < 0) | if ((ret = avfilter_init_filter(*filt_ctx, args, opaque)) < 0) | ||||
| goto fail; | goto fail; | ||||
| if ((ret = avfilter_graph_add_filter(graph_ctx, *filt_ctx)) < 0) | |||||
| goto fail; | |||||
| return 0; | return 0; | ||||
| fail: | fail: | ||||
| @@ -96,6 +96,32 @@ fail: | |||||
| return ret; | return ret; | ||||
| } | } | ||||
| AVFilterContext *avfilter_graph_alloc_filter(AVFilterGraph *graph, | |||||
| const AVFilter *filter, | |||||
| const char *name) | |||||
| { | |||||
| AVFilterContext **filters, *s; | |||||
| s = ff_filter_alloc(filter, name); | |||||
| if (!s) | |||||
| return NULL; | |||||
| filters = av_realloc(graph->filters, sizeof(*filters) * (graph->nb_filters + 1)); | |||||
| if (!filters) { | |||||
| avfilter_free(s); | |||||
| return NULL; | |||||
| } | |||||
| graph->filters = filters; | |||||
| graph->filters[graph->nb_filters++] = s; | |||||
| #if FF_API_FOO_COUNT | |||||
| graph->filter_count = graph->nb_filters; | |||||
| #endif | |||||
| return s; | |||||
| } | |||||
| /** | /** | ||||
| * Check for the validity of graph. | * Check for the validity of graph. | ||||
| * | * | ||||
| @@ -109,16 +109,11 @@ static int create_filter(AVFilterContext **filt_ctx, AVFilterGraph *ctx, int ind | |||||
| return AVERROR(EINVAL); | return AVERROR(EINVAL); | ||||
| } | } | ||||
| ret = avfilter_open(filt_ctx, filt, inst_name); | |||||
| *filt_ctx = avfilter_graph_alloc_filter(ctx, filt, inst_name); | |||||
| if (!*filt_ctx) { | if (!*filt_ctx) { | ||||
| av_log(log_ctx, AV_LOG_ERROR, | av_log(log_ctx, AV_LOG_ERROR, | ||||
| "Error creating filter '%s'\n", filt_name); | "Error creating filter '%s'\n", filt_name); | ||||
| return ret; | |||||
| } | |||||
| if ((ret = avfilter_graph_add_filter(ctx, *filt_ctx)) < 0) { | |||||
| avfilter_free(*filt_ctx); | |||||
| return ret; | |||||
| return AVERROR(ENOMEM); | |||||
| } | } | ||||
| if (!strcmp(filt_name, "scale") && args && !strstr(args, "flags") && | if (!strcmp(filt_name, "scale") && args && !strstr(args, "flags") && | ||||
| @@ -196,4 +196,14 @@ int ff_request_frame(AVFilterLink *link); | |||||
| */ | */ | ||||
| int ff_filter_frame(AVFilterLink *link, AVFrame *frame); | int ff_filter_frame(AVFilterLink *link, AVFrame *frame); | ||||
| /** | |||||
| * Allocate a new filter context and return it. | |||||
| * | |||||
| * @param filter what filter to create an instance of | |||||
| * @param inst_name name to give to the new filter context | |||||
| * | |||||
| * @return newly created filter context or NULL on failure | |||||
| */ | |||||
| AVFilterContext *ff_filter_alloc(const AVFilter *filter, const char *inst_name); | |||||
| #endif /* AVFILTER_INTERNAL_H */ | #endif /* AVFILTER_INTERNAL_H */ | ||||
| @@ -58,5 +58,8 @@ | |||||
| #ifndef FF_API_OLD_FILTER_OPTS | #ifndef FF_API_OLD_FILTER_OPTS | ||||
| #define FF_API_OLD_FILTER_OPTS (LIBAVFILTER_VERSION_MAJOR < 4) | #define FF_API_OLD_FILTER_OPTS (LIBAVFILTER_VERSION_MAJOR < 4) | ||||
| #endif | #endif | ||||
| #ifndef FF_API_AVFILTER_OPEN | |||||
| #define FF_API_AVFILTER_OPEN (LIBAVFILTER_VERSION_MAJOR < 4) | |||||
| #endif | |||||
| #endif /* AVFILTER_VERSION_H */ | #endif /* AVFILTER_VERSION_H */ | ||||