From 5c0d8bc4cea23cfe85c082a03871cf73190813fb Mon Sep 17 00:00:00 2001
From: Stefano Sabatini <stefasab@gmail.com>
Date: Thu, 9 Aug 2012 14:59:10 +0200
Subject: [PATCH] lavfi: add avfilter_get_class() and iteration callbacks

Allow iteration over filter options.
---
 doc/APIchanges         |  4 ++++
 libavfilter/avfilter.c | 35 +++++++++++++++++++++++++++++++++++
 libavfilter/avfilter.h |  6 ++++++
 libavfilter/version.h  |  2 +-
 4 files changed, 46 insertions(+), 1 deletion(-)

diff --git a/doc/APIchanges b/doc/APIchanges
index fd0abf5414e..67b120d02af 100644
--- a/doc/APIchanges
+++ b/doc/APIchanges
@@ -15,6 +15,10 @@ libavutil:     2011-04-18
 
 API changes, most recent first:
 
+2012-08-13 - xxxxxxx - lavfi 3.8.100 - avfilter.h
+  Add avfilter_get_class() function, and priv_class field to AVFilter
+  struct.
+
 2012-08-13 - xxxxxxx - lavu 51.69.100 - opt.h
   Add AV_OPT_FLAG_FILTERING_PARAM symbol in opt.h.
 
diff --git a/libavfilter/avfilter.c b/libavfilter/avfilter.c
index c698d8aa578..e87a78abe9d 100644
--- a/libavfilter/avfilter.c
+++ b/libavfilter/avfilter.c
@@ -432,13 +432,48 @@ static const char *default_filter_name(void *filter_ctx)
     return ctx->name ? ctx->name : ctx->filter->name;
 }
 
+static void *filter_child_next(void *obj, void *prev)
+{
+    AVFilterContext *ctx = obj;
+    if (!prev && ctx->filter && ctx->filter->priv_class)
+        return ctx->priv;
+    return NULL;
+}
+
+static const AVClass *filter_child_class_next(const AVClass *prev)
+{
+    AVFilter **filter_ptr = NULL;
+
+    /* find the filter that corresponds to prev */
+    while (prev && *(filter_ptr = av_filter_next(filter_ptr)))
+        if ((*filter_ptr)->priv_class == prev)
+            break;
+
+    /* could not find filter corresponding to prev */
+    if (prev && !(*filter_ptr))
+        return NULL;
+
+    /* find next filter with specific options */
+    while (*(filter_ptr = av_filter_next(filter_ptr)))
+        if ((*filter_ptr)->priv_class)
+            return (*filter_ptr)->priv_class;
+    return NULL;
+}
+
 static const AVClass avfilter_class = {
     .class_name = "AVFilter",
     .item_name  = default_filter_name,
     .version    = LIBAVUTIL_VERSION_INT,
     .category   = AV_CLASS_CATEGORY_FILTER,
+    .child_next = filter_child_next,
+    .child_class_next = filter_child_class_next,
 };
 
+const AVClass *avfilter_get_class(void)
+{
+    return &avfilter_class;
+}
+
 int avfilter_open(AVFilterContext **filter_ctx, AVFilter *filter, const char *inst_name)
 {
     AVFilterContext *ret;
diff --git a/libavfilter/avfilter.h b/libavfilter/avfilter.h
index 54a0b978973..07bc5a986b4 100644
--- a/libavfilter/avfilter.h
+++ b/libavfilter/avfilter.h
@@ -47,6 +47,10 @@ const char *avfilter_configuration(void);
  */
 const char *avfilter_license(void);
 
+/**
+ * Get the class for the AVFilterContext struct.
+ */
+const AVClass *avfilter_get_class(void);
 
 typedef struct AVFilterContext AVFilterContext;
 typedef struct AVFilterLink    AVFilterLink;
@@ -469,6 +473,8 @@ typedef struct AVFilter {
      * used for providing binary data.
      */
     int (*init_opaque)(AVFilterContext *ctx, const char *args, void *opaque);
+
+    const AVClass *priv_class;      ///< private class, containing filter specific options
 } AVFilter;
 
 /** An instance of a filter */
diff --git a/libavfilter/version.h b/libavfilter/version.h
index a47262fb65f..daed93a0825 100644
--- a/libavfilter/version.h
+++ b/libavfilter/version.h
@@ -29,7 +29,7 @@
 #include "libavutil/avutil.h"
 
 #define LIBAVFILTER_VERSION_MAJOR  3
-#define LIBAVFILTER_VERSION_MINOR  7
+#define LIBAVFILTER_VERSION_MINOR  8
 #define LIBAVFILTER_VERSION_MICRO 100
 
 #define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \
-- 
GitLab