From 672237b86f1afee98ed1eaf975257106fa97bef3 Mon Sep 17 00:00:00 2001
From: Martin Vignali <martin.vignali@gmail.com>
Date: Sat, 13 Oct 2018 18:51:29 +0200
Subject: [PATCH] avfilter/vsrc_testsrc : add allgray generator

generate a picture of 256 pix in width
and height depend of the target pix_fmt

gray8, 9, 10, have duplicate line in order to have 16 pixel height
gray12 output size : 256x16
gray14 output size : 256x64
gray16 output size : 256x256
---
 doc/filters.texi                       |   6 ++
 libavfilter/Makefile                   |   1 +
 libavfilter/allfilters.c               |   1 +
 libavfilter/version.h                  |   4 +-
 libavfilter/vsrc_testsrc.c             | 131 +++++++++++++++++++++++++++++++++
 tests/fate/filter-video.mak            |  10 +++
 tests/ref/fate/filter-allgray-gray10be |   6 ++
 tests/ref/fate/filter-allgray-gray10le |   6 ++
 tests/ref/fate/filter-allgray-gray12be |   6 ++
 tests/ref/fate/filter-allgray-gray12le |   6 ++
 tests/ref/fate/filter-allgray-gray14be |   6 ++
 tests/ref/fate/filter-allgray-gray14le |   6 ++
 tests/ref/fate/filter-allgray-gray16be |   6 ++
 tests/ref/fate/filter-allgray-gray16le |   6 ++
 tests/ref/fate/filter-allgray-gray8    |   6 ++
 tests/ref/fate/filter-allgray-gray9be  |   6 ++
 tests/ref/fate/filter-allgray-gray9le  |   6 ++
 17 files changed, 217 insertions(+), 2 deletions(-)
 create mode 100644 tests/ref/fate/filter-allgray-gray10be
 create mode 100644 tests/ref/fate/filter-allgray-gray10le
 create mode 100644 tests/ref/fate/filter-allgray-gray12be
 create mode 100644 tests/ref/fate/filter-allgray-gray12le
 create mode 100644 tests/ref/fate/filter-allgray-gray14be
 create mode 100644 tests/ref/fate/filter-allgray-gray14le
 create mode 100644 tests/ref/fate/filter-allgray-gray16be
 create mode 100644 tests/ref/fate/filter-allgray-gray16le
 create mode 100644 tests/ref/fate/filter-allgray-gray8
 create mode 100644 tests/ref/fate/filter-allgray-gray9be
 create mode 100644 tests/ref/fate/filter-allgray-gray9le

diff --git a/doc/filters.texi b/doc/filters.texi
index c327b2c22b..dd1a243ef3 100644
--- a/doc/filters.texi
+++ b/doc/filters.texi
@@ -18529,6 +18529,7 @@ ffplay -f lavfi life=s=300x200:mold=10:r=60:ratio=0.1:death_color=#C83232:life_c
 @end example
 @end itemize
 
+@anchor{allgray}
 @anchor{allrgb}
 @anchor{allyuv}
 @anchor{color}
@@ -18544,6 +18545,11 @@ ffplay -f lavfi life=s=300x200:mold=10:r=60:ratio=0.1:death_color=#C83232:life_c
 @anchor{yuvtestsrc}
 @section allrgb, allyuv, color, haldclutsrc, nullsrc, pal75bars, pal100bars, rgbtestsrc, smptebars, smptehdbars, testsrc, testsrc2, yuvtestsrc
 
+The @code{allgray} source returns frames of all gray value for the target pixel format.
+The width of the target frame is 256 pixels.
+Height depend of the target pixel format (to store all the values)
+For gray8, 9, 10 output have duplicate lines (in order to have an height of 16 pixels).
+
 The @code{allrgb} source returns frames of size 4096x4096 of all rgb colors.
 
 The @code{allyuv} source returns frames of size 4096x4096 of all yuv colors.
diff --git a/libavfilter/Makefile b/libavfilter/Makefile
index 62cc2f561f..1133546875 100644
--- a/libavfilter/Makefile
+++ b/libavfilter/Makefile
@@ -406,6 +406,7 @@ OBJS-$(CONFIG_ZMQ_FILTER)                    += f_zmq.o
 OBJS-$(CONFIG_ZOOMPAN_FILTER)                += vf_zoompan.o
 OBJS-$(CONFIG_ZSCALE_FILTER)                 += vf_zscale.o
 
+OBJS-$(CONFIG_ALLGRAY_FILTER)                += vsrc_testsrc.o
 OBJS-$(CONFIG_ALLRGB_FILTER)                 += vsrc_testsrc.o
 OBJS-$(CONFIG_ALLYUV_FILTER)                 += vsrc_testsrc.o
 OBJS-$(CONFIG_CELLAUTO_FILTER)               += vsrc_cellauto.o
diff --git a/libavfilter/allfilters.c b/libavfilter/allfilters.c
index 5e72803b13..76f26f7aaa 100644
--- a/libavfilter/allfilters.c
+++ b/libavfilter/allfilters.c
@@ -387,6 +387,7 @@ extern AVFilter ff_vf_zmq;
 extern AVFilter ff_vf_zoompan;
 extern AVFilter ff_vf_zscale;
 
+extern AVFilter ff_vsrc_allgray;
 extern AVFilter ff_vsrc_allrgb;
 extern AVFilter ff_vsrc_allyuv;
 extern AVFilter ff_vsrc_cellauto;
diff --git a/libavfilter/version.h b/libavfilter/version.h
index 30e961b999..bb57c5fbed 100644
--- a/libavfilter/version.h
+++ b/libavfilter/version.h
@@ -30,8 +30,8 @@
 #include "libavutil/version.h"
 
 #define LIBAVFILTER_VERSION_MAJOR   7
-#define LIBAVFILTER_VERSION_MINOR  33
-#define LIBAVFILTER_VERSION_MICRO 101
+#define LIBAVFILTER_VERSION_MINOR  34
+#define LIBAVFILTER_VERSION_MICRO 100
 
 #define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \
                                                LIBAVFILTER_VERSION_MINOR, \
diff --git a/libavfilter/vsrc_testsrc.c b/libavfilter/vsrc_testsrc.c
index f06714807f..edf739e56b 100644
--- a/libavfilter/vsrc_testsrc.c
+++ b/libavfilter/vsrc_testsrc.c
@@ -1809,3 +1809,134 @@ AVFilter ff_vsrc_allrgb = {
 };
 
 #endif /* CONFIG_ALLRGB_FILTER */
+
+#if CONFIG_ALLGRAY_FILTER
+
+static const AVOption allgray_options[] = {
+    COMMON_OPTIONS_NOSIZE
+    { NULL }
+};
+
+AVFILTER_DEFINE_CLASS(allgray);
+
+static void allgray_fill_picture8(AVFilterContext *ctx, AVFrame *frame)
+{
+    unsigned x, i;
+    const int linesize = frame->linesize[0];
+    uint8_t *line = frame->data[0];
+    uint8_t *dst = line;
+
+    for (x = 0; x < 256; x++)
+        *dst++ = x;
+
+    line += linesize;
+    for (i = 0; i < 16; i++){
+        memcpy(line, frame->data[0], linesize);
+        line += linesize;
+    }
+}
+
+static void allgray_fill_picture16(AVFilterContext *ctx, AVFrame *frame)
+{
+    unsigned x, y, i, duplicate_count, copy_size;
+    const AVPixFmtDescriptor *desc = av_pix_fmt_desc_get(frame->format);
+    unsigned nb_lines = 1 << (desc->comp[0].depth - 8);
+    const int linesize = frame->linesize[0];
+    uint8_t *line = frame->data[0];
+    uint16_t v = 0;
+
+#if HAVE_BIGENDIAN
+    if (desc->flags & AV_PIX_FMT_FLAG_BE){
+#else
+    if (!(desc->flags & AV_PIX_FMT_FLAG_BE)){
+#endif
+        /* no swap */
+        for (y = 0; y < nb_lines; y++) {
+            uint16_t *dst = (uint16_t *)line;
+
+            for (x = 0; x < 256; x++) {
+                *dst++ = v;
+                v += 1;
+            }
+            line += linesize;
+        }
+    } else { /* swap */
+        for (y = 0; y < nb_lines; y++) {
+            uint16_t *dst = (uint16_t *)line;
+
+            for (x = 0; x < 256; x++) {
+                *dst++ = av_bswap16(v);
+                v += 1;
+            }
+            line += linesize;
+        }
+    }
+    if (nb_lines < 16) { /* copy lines to have at least 16 pixel height */
+        duplicate_count = 16/nb_lines;
+        copy_size = linesize * nb_lines;
+        for (i = 0; i < duplicate_count; i++) {
+            memcpy(line, frame->data[0], copy_size);
+            line += copy_size;
+        }
+    }
+}
+
+static av_cold int allgray_init(AVFilterContext *ctx)
+{
+    TestSourceContext *test = ctx->priv;
+
+    test->draw_once = 1;
+    return init(ctx);
+}
+
+static int allgray_config_props(AVFilterLink *outlink)
+{
+    TestSourceContext *test = outlink->src->priv;
+    const AVPixFmtDescriptor *desc = av_pix_fmt_desc_get(outlink->format);
+
+    test->fill_picture_fn = desc->comp[0].depth > 8 ? allgray_fill_picture16 : allgray_fill_picture8;
+
+    test->w = 256;
+    test->h = FFMAX(1 << (desc->comp[0].depth - 8), 16); /* use at least 16 pixel for the height */
+    return config_props(outlink);
+}
+
+static int allgray_query_formats(AVFilterContext *ctx)
+{
+    static const enum AVPixelFormat pix_fmts[] = {
+        AV_PIX_FMT_GRAY8, AV_PIX_FMT_GRAY9LE, AV_PIX_FMT_GRAY9BE,
+        AV_PIX_FMT_GRAY10LE, AV_PIX_FMT_GRAY10BE,
+        AV_PIX_FMT_GRAY12LE, AV_PIX_FMT_GRAY12BE,
+        AV_PIX_FMT_GRAY14LE, AV_PIX_FMT_GRAY14BE,
+        AV_PIX_FMT_GRAY16LE, AV_PIX_FMT_GRAY16BE, AV_PIX_FMT_NONE
+    };
+
+    AVFilterFormats *fmts_list = ff_make_format_list(pix_fmts);
+    if (!fmts_list)
+        return AVERROR(ENOMEM);
+    return ff_set_common_formats(ctx, fmts_list);
+}
+
+static const AVFilterPad avfilter_vsrc_allgray_outputs[] = {
+    {
+        .name          = "default",
+        .type          = AVMEDIA_TYPE_VIDEO,
+        .request_frame = request_frame,
+        .config_props  = allgray_config_props,
+    },
+    { NULL }
+};
+
+AVFilter ff_vsrc_allgray = {
+    .name          = "allgray",
+    .description   = NULL_IF_CONFIG_SMALL("Generate all gray values."),
+    .priv_size     = sizeof(TestSourceContext),
+    .priv_class    = &allgray_class,
+    .init          = allgray_init,
+    .uninit        = uninit,
+    .query_formats = allgray_query_formats,
+    .inputs        = NULL,
+    .outputs       = avfilter_vsrc_allgray_outputs,
+};
+
+#endif /* CONFIG_ALLGRAY_FILTER */
diff --git a/tests/fate/filter-video.mak b/tests/fate/filter-video.mak
index 8bbdc04896..1b247df35e 100644
--- a/tests/fate/filter-video.mak
+++ b/tests/fate/filter-video.mak
@@ -83,6 +83,16 @@ fate-filter-testsrc2-rgb24: CMD = framecrc -lavfi testsrc2=r=7:d=10 -pix_fmt rgb
 FATE_FILTER-$(call ALLYES, LAVFI_INDEV TESTSRC2_FILTER) += fate-filter-testsrc2-rgba
 fate-filter-testsrc2-rgba: CMD = framecrc -lavfi testsrc2=r=7:d=10 -pix_fmt rgba
 
+
+define FATE_FILTER_PIXFMTSUITE_ALLGRAY
+FATE_ALLGRAY += fate-filter-allgray-$(1)
+fate-filter-allgray-$(1): CMD = framecrc -lavfi allgray=rate=5,format=$(1) -vframes 1 -pix_fmt $(1)
+endef
+
+GRAY_PIX_FMT = gray8 gray9le gray9be gray10le gray10be gray12le gray12be gray14le gray14be gray16le gray16be
+$(foreach PIX_FMT,$(GRAY_PIX_FMT),$(eval $(call FATE_FILTER_PIXFMTSUITE_ALLGRAY,$(PIX_FMT))))
+FATE_FILTER-$(call ALLYES, LAVFI_INDEV ALLGRAY_FILTER) += $(FATE_ALLGRAY)
+
 FATE_FILTER-$(call ALLYES, LAVFI_INDEV ALLRGB_FILTER) += fate-filter-allrgb
 fate-filter-allrgb: CMD = framecrc -lavfi allrgb=rate=5:duration=1 -pix_fmt rgb24
 
diff --git a/tests/ref/fate/filter-allgray-gray10be b/tests/ref/fate/filter-allgray-gray10be
new file mode 100644
index 0000000000..ba171817c0
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray10be
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x16
+#sar 0: 1/1
+0,          0,          0,        1,     8192, 0xd50c1078
diff --git a/tests/ref/fate/filter-allgray-gray10le b/tests/ref/fate/filter-allgray-gray10le
new file mode 100644
index 0000000000..495b1526d7
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray10le
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x16
+#sar 0: 1/1
+0,          0,          0,        1,     8192, 0xb5841078
diff --git a/tests/ref/fate/filter-allgray-gray12be b/tests/ref/fate/filter-allgray-gray12be
new file mode 100644
index 0000000000..9f45cc2dd6
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray12be
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x16
+#sar 0: 1/1
+0,          0,          0,        1,     8192, 0x699b7078
diff --git a/tests/ref/fate/filter-allgray-gray12le b/tests/ref/fate/filter-allgray-gray12le
new file mode 100644
index 0000000000..83730f1e3f
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray12le
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x16
+#sar 0: 1/1
+0,          0,          0,        1,     8192, 0xea047078
diff --git a/tests/ref/fate/filter-allgray-gray14be b/tests/ref/fate/filter-allgray-gray14be
new file mode 100644
index 0000000000..0c95c83aa5
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray14be
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x64
+#sar 0: 1/1
+0,          0,          0,        1,    32768, 0xb929c249
diff --git a/tests/ref/fate/filter-allgray-gray14le b/tests/ref/fate/filter-allgray-gray14le
new file mode 100644
index 0000000000..95ef4f872c
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray14le
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x64
+#sar 0: 1/1
+0,          0,          0,        1,    32768, 0xba91c249
diff --git a/tests/ref/fate/filter-allgray-gray16be b/tests/ref/fate/filter-allgray-gray16be
new file mode 100644
index 0000000000..1c85bbb14e
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray16be
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x256
+#sar 0: 1/1
+0,          0,          0,        1,   131072, 0x447c0ef1
diff --git a/tests/ref/fate/filter-allgray-gray16le b/tests/ref/fate/filter-allgray-gray16le
new file mode 100644
index 0000000000..1c85bbb14e
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray16le
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x256
+#sar 0: 1/1
+0,          0,          0,        1,   131072, 0x447c0ef1
diff --git a/tests/ref/fate/filter-allgray-gray8 b/tests/ref/fate/filter-allgray-gray8
new file mode 100644
index 0000000000..17cf910d73
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray8
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x16
+#sar 0: 1/1
+0,          0,          0,        1,     4096, 0x50aef869
diff --git a/tests/ref/fate/filter-allgray-gray9be b/tests/ref/fate/filter-allgray-gray9be
new file mode 100644
index 0000000000..1c68033c3c
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray9be
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x16
+#sar 0: 1/1
+0,          0,          0,        1,     8192, 0xb7ec0078
diff --git a/tests/ref/fate/filter-allgray-gray9le b/tests/ref/fate/filter-allgray-gray9le
new file mode 100644
index 0000000000..40d6e03b3b
--- /dev/null
+++ b/tests/ref/fate/filter-allgray-gray9le
@@ -0,0 +1,6 @@
+#tb 0: 1/5
+#media_type 0: video
+#codec_id 0: rawvideo
+#dimensions 0: 256x16
+#sar 0: 1/1
+0,          0,          0,        1,     8192, 0xa8640078
-- 
2.14.3 (Apple Git-98)

