... | ... |
@@ -1,5 +1,6 @@ |
1 | 1 |
# libavcodec tests |
2 | 2 |
AVCODECOBJS-$(CONFIG_ALAC_DECODER) += alacdsp.o |
3 |
+AVCODECOBJS-$(CONFIG_BLEND_FILTER) += vf_blend.o |
|
3 | 4 |
AVCODECOBJS-$(CONFIG_BSWAPDSP) += bswapdsp.o |
4 | 5 |
AVCODECOBJS-$(CONFIG_DCA_DECODER) += synth_filter.o |
5 | 6 |
AVCODECOBJS-$(CONFIG_FLACDSP) += flacdsp.o |
... | ... |
@@ -68,6 +68,9 @@ static const struct { |
68 | 68 |
#if CONFIG_ALAC_DECODER |
69 | 69 |
{ "alacdsp", checkasm_check_alacdsp }, |
70 | 70 |
#endif |
71 |
+ #if CONFIG_BLEND_FILTER |
|
72 |
+ { "vf_blend", checkasm_check_blend }, |
|
73 |
+ #endif |
|
71 | 74 |
#if CONFIG_BSWAPDSP |
72 | 75 |
{ "bswapdsp", checkasm_check_bswapdsp }, |
73 | 76 |
#endif |
37 | 38 |
new file mode 100644 |
... | ... |
@@ -0,0 +1,130 @@ |
0 |
+/* |
|
1 |
+ * Copyright (c) 2016 Tiancheng "Timothy" Gu |
|
2 |
+ * |
|
3 |
+ * This file is part of FFmpeg. |
|
4 |
+ * |
|
5 |
+ * FFmpeg is free software; you can redistribute it and/or modify |
|
6 |
+ * it under the terms of the GNU General Public License as published by |
|
7 |
+ * the Free Software Foundation; either version 2 of the License, or |
|
8 |
+ * (at your option) any later version. |
|
9 |
+ * |
|
10 |
+ * FFmpeg is distributed in the hope that it will be useful, |
|
11 |
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
12 |
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
|
13 |
+ * GNU General Public License for more details. |
|
14 |
+ * |
|
15 |
+ * You should have received a copy of the GNU General Public License along |
|
16 |
+ * with FFmpeg; if not, write to the Free Software Foundation, Inc., |
|
17 |
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. |
|
18 |
+ */ |
|
19 |
+ |
|
20 |
+#include <string.h> |
|
21 |
+#include "checkasm.h" |
|
22 |
+#include "libavfilter/blend.h" |
|
23 |
+#include "libavutil/common.h" |
|
24 |
+#include "libavutil/internal.h" |
|
25 |
+#include "libavutil/intreadwrite.h" |
|
26 |
+ |
|
27 |
+#define WIDTH 256 |
|
28 |
+#define HEIGHT 256 |
|
29 |
+#define BUF_UNITS 9 |
|
30 |
+#define SIZE_PER_UNIT (WIDTH * HEIGHT) |
|
31 |
+#define BUF_SIZE (BUF_UNITS * SIZE_PER_UNIT) |
|
32 |
+ |
|
33 |
+#define randomize_buffers() \ |
|
34 |
+ do { \ |
|
35 |
+ int i, j; \ |
|
36 |
+ for (i = 0; i < HEIGHT; i++) { \ |
|
37 |
+ for (j = 0; j < WIDTH; j++) { \ |
|
38 |
+ top1[i * WIDTH + j] = \ |
|
39 |
+ top2[i * WIDTH + j] = i; \ |
|
40 |
+ bot1[i * WIDTH + j] = \ |
|
41 |
+ bot2[i * WIDTH + j] = j; \ |
|
42 |
+ } \ |
|
43 |
+ } \ |
|
44 |
+ for (i = 0; i < SIZE_PER_UNIT; i += 4) { \ |
|
45 |
+ uint32_t r = rnd(); \ |
|
46 |
+ AV_WN32A(dst1 + i, r); \ |
|
47 |
+ AV_WN32A(dst2 + i, r); \ |
|
48 |
+ } \ |
|
49 |
+ for (; i < BUF_SIZE; i += 4) { \ |
|
50 |
+ uint32_t r = rnd(); \ |
|
51 |
+ AV_WN32A(top1 + i, r); \ |
|
52 |
+ AV_WN32A(top2 + i, r); \ |
|
53 |
+ r = rnd(); \ |
|
54 |
+ AV_WN32A(bot1 + i, r); \ |
|
55 |
+ AV_WN32A(bot2 + i, r); \ |
|
56 |
+ r = rnd(); \ |
|
57 |
+ AV_WN32A(dst1 + i, r); \ |
|
58 |
+ AV_WN32A(dst2 + i, r); \ |
|
59 |
+ } \ |
|
60 |
+ } while (0) |
|
61 |
+ |
|
62 |
+#define check_blend_func() \ |
|
63 |
+ do { \ |
|
64 |
+ int i; \ |
|
65 |
+ declare_func(void, const uint8_t *top, ptrdiff_t top_linesize, \ |
|
66 |
+ const uint8_t *bottom, ptrdiff_t bottom_linesize, \ |
|
67 |
+ uint8_t *dst, ptrdiff_t dst_linesize, \ |
|
68 |
+ ptrdiff_t width, ptrdiff_t height, \ |
|
69 |
+ struct FilterParams *param, double *values); \ |
|
70 |
+ \ |
|
71 |
+ for (i = 0; i < BUF_UNITS - 1; i++) { \ |
|
72 |
+ int src_offset = i * SIZE_PER_UNIT + i; /* Test various alignments */ \ |
|
73 |
+ int dst_offset = i * SIZE_PER_UNIT; /* dst must be aligned */ \ |
|
74 |
+ randomize_buffers(); \ |
|
75 |
+ call_ref(top1 + src_offset, WIDTH, bot1 + src_offset, WIDTH, \ |
|
76 |
+ dst1 + dst_offset, WIDTH, WIDTH, HEIGHT, ¶m, NULL); \ |
|
77 |
+ call_new(top2 + src_offset, WIDTH, bot2 + src_offset, WIDTH, \ |
|
78 |
+ dst2 + dst_offset, WIDTH, WIDTH, HEIGHT, ¶m, NULL); \ |
|
79 |
+ if (memcmp(top1, top2, BUF_SIZE) || memcmp(bot1, bot2, BUF_SIZE) || memcmp(dst1, dst2, BUF_SIZE)) \ |
|
80 |
+ fail(); \ |
|
81 |
+ bench_new(top2 + src_offset, WIDTH, bot2 + src_offset, WIDTH, \ |
|
82 |
+ dst2, WIDTH, WIDTH, HEIGHT, ¶m, NULL); \ |
|
83 |
+ } \ |
|
84 |
+ } while (0) |
|
85 |
+ |
|
86 |
+void checkasm_check_blend(void) |
|
87 |
+{ |
|
88 |
+ uint8_t *top1 = av_malloc(BUF_SIZE); |
|
89 |
+ uint8_t *top2 = av_malloc(BUF_SIZE); |
|
90 |
+ uint8_t *bot1 = av_malloc(BUF_SIZE); |
|
91 |
+ uint8_t *bot2 = av_malloc(BUF_SIZE); |
|
92 |
+ uint8_t *dst1 = av_malloc(BUF_SIZE); |
|
93 |
+ uint8_t *dst2 = av_malloc(BUF_SIZE); |
|
94 |
+ FilterParams param = { |
|
95 |
+ .opacity = 1.0, |
|
96 |
+ }; |
|
97 |
+ |
|
98 |
+#define check_and_report(name, val) \ |
|
99 |
+ param.mode = val; \ |
|
100 |
+ ff_blend_init(¶m, 0); \ |
|
101 |
+ if (check_func(param.blend, #name)) \ |
|
102 |
+ check_blend_func(); |
|
103 |
+ |
|
104 |
+ check_and_report(addition, BLEND_ADDITION) |
|
105 |
+ check_and_report(addition128, BLEND_ADDITION128) |
|
106 |
+ check_and_report(and, BLEND_AND) |
|
107 |
+ check_and_report(average, BLEND_AVERAGE) |
|
108 |
+ check_and_report(darken, BLEND_DARKEN) |
|
109 |
+ check_and_report(difference128, BLEND_DIFFERENCE128) |
|
110 |
+ check_and_report(hardmix, BLEND_HARDMIX) |
|
111 |
+ check_and_report(lighten, BLEND_LIGHTEN) |
|
112 |
+ check_and_report(multiply, BLEND_MULTIPLY) |
|
113 |
+ check_and_report(or, BLEND_OR) |
|
114 |
+ check_and_report(phoenix, BLEND_PHOENIX) |
|
115 |
+ check_and_report(screen, BLEND_SCREEN) |
|
116 |
+ check_and_report(subtract, BLEND_SUBTRACT) |
|
117 |
+ check_and_report(xor, BLEND_XOR) |
|
118 |
+ check_and_report(difference, BLEND_DIFFERENCE) |
|
119 |
+ check_and_report(negation, BLEND_NEGATION) |
|
120 |
+ |
|
121 |
+ report("8bit"); |
|
122 |
+ |
|
123 |
+ av_freep(&top1); |
|
124 |
+ av_freep(&top2); |
|
125 |
+ av_freep(&bot1); |
|
126 |
+ av_freep(&bot2); |
|
127 |
+ av_freep(&dst1); |
|
128 |
+ av_freep(&dst2); |
|
129 |
+} |