FFmpeg
dnn-layer-avgpool.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2020
3  *
4  * This file is part of FFmpeg.
5  *
6  * FFmpeg is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * FFmpeg is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with FFmpeg; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19  */
20 
21 #include <stdio.h>
23 
24 #define EPSON 0.00001
25 
26 static int test_with_same(void)
27 {
28  // the input data and expected data are generated with below python code.
29  /*
30  import tensorflow as tf
31  import numpy as np
32 
33  x = tf.placeholder(tf.float32, shape=[1, None, None, 3])
34  y = tf.layers.average_pooling2d(x, pool_size=[2,2], strides=[1,1], padding='VALID')
35  data = np.random.rand(1, 5, 6, 3);
36 
37  sess=tf.Session()
38  sess.run(tf.global_variables_initializer())
39 
40  output = sess.run(y, feed_dict={x: data})
41 
42  print("input:")
43  print(data.shape)
44  print(list(data.flatten()))
45 
46  print("output:")
47  print(output.shape)
48  print(list(output.flatten()))
49  */
50 
51  AvgPoolParams params;
52  DnnOperand operands[2];
53  int32_t input_indexes[1];
54  float input[1*5*6*3] = {
55  0.7461309859908424, 0.7567538372797069, 0.07662743569678687, 0.8882112610336333, 0.9720443314026668, 0.3337200343220823, 0.4421032129780248,
56  0.14940809044964876, 0.6773177061961277, 0.9778844630669781, 0.6522650522626998, 0.0317651530878591, 0.31259897552911364, 0.6235936821891896,
57  0.40016094349542775, 0.4599222930032276, 0.7893807222960093, 0.8475986363538283, 0.5058802717647394, 0.7827005363222633, 0.3032188123727916,
58  0.8983728631302361, 0.20622408444965523, 0.22966072303869878, 0.09535751273161308, 0.8760709100995375, 0.9982324154558745, 0.7904595468621013,
59  0.13883671508879347, 0.9332751439533138, 0.0010861680752152214, 0.3607210449251048, 0.6600652759586171, 0.7629572058138805, 0.29441975810476106,
60  0.2683471432889405, 0.22574580829831536, 0.8893251976212904, 0.3907737043801005, 0.6421829842863968, 0.6670373870457297, 0.9383850793160277,
61  0.4120458907436003, 0.3589847212711481, 0.48047736550128983, 0.6428192648418949, 0.0313661686292348, 0.429357100401472, 0.5123413386514056,
62  0.8492446404097114, 0.9045286128486804, 0.8123708563814285, 0.3943245008451698, 0.9576713003177785, 0.5985610965938726, 0.9350833279543561,
63  0.8010079897491659, 0.45882114217642866, 0.35275037908941487, 0.4555844661432271, 0.12352455940255314, 0.37801756635035544, 0.2824056214573083,
64  0.6229462823245029, 0.7235305681391472, 0.5408259266122064, 0.12142224381781208, 0.34431198802873686, 0.7112823816321276, 0.6307144385115417,
65  0.8136734589018082, 0.842095618140585, 0.8602767724004784, 0.6649236853766185, 0.5184782829419623, 0.9119607270982825, 0.3084111974561645,
66  0.39460705638161364, 0.17710447526170836, 0.1715485945814199, 0.17277563576521882, 0.40188232428735704, 0.22847985411491878, 0.4135361701550696,
67  0.24621846601980057, 0.6576588108454774, 0.6063336087333997, 0.6452342242996931, 0.7071689702737508, 0.1973416063225648
68  };
69  float expected_output[] = {
70  0.75964886, 0.6794307, 0.23580676, 0.5810112, 0.5509369, 0.55973274, 0.5764512, 0.45414522, 0.6601476, 0.52050734, 0.44385415,
71  0.50631666, 0.38414115, 0.5170288, 0.544043, 0.61143976, 0.5419003, 0.5579729, 0.5680455, 0.6363218, 0.4655096, 0.51198983,
72  0.5270792, 0.66168886, 0.48517057, 0.3513146, 0.7103355, 0.48667657, 0.34504217, 0.7318065, 0.5221889, 0.4746775, 0.69765306,
73  0.78766406, 0.34437215, 0.6130092, 0.48132777, 0.7110491, 0.6464378, 0.40914366, 0.4391975, 0.5392131, 0.45033398, 0.37297475,
74  0.43326652, 0.4748823, 0.48711336, 0.64649844, 0.51921225, 0.60038865, 0.8538945, 0.7215426, 0.60399896, 0.89988345, 0.707405,
75  0.5652921, 0.54241943, 0.41785273, 0.30268195, 0.3263432, 0.3313644, 0.37539417, 0.35238582, 0.34811732, 0.48849532, 0.56799453,
76  0.41089734, 0.63070333, 0.5892633, 0.6379743, 0.7604212, 0.5197186, 0.88611877, 0.48666745, 0.45654267, 0.5445326, 0.2399799,
77  0.28369135, 0.28949338, 0.20001422, 0.2931559, 0.3240504, 0.44306934, 0.5099349, 0.44572634, 0.68241394, 0.40183762, 0.6452342,
78  0.707169, 0.1973416
79  };
80  float *output;
81 
82  params.strides = 1;
83  params.kernel_size = 2;
84  params.padding_method = SAME;
85 
86  operands[0].data = input;
87  operands[0].dims[0] = 1;
88  operands[0].dims[1] = 5;
89  operands[0].dims[2] = 6;
90  operands[0].dims[3] = 3;
91  operands[1].data = NULL;
92 
93  input_indexes[0] = 0;
94  ff_dnn_execute_layer_avg_pool(operands, input_indexes, 1, &params, NULL);
95 
96  output = operands[1].data;
97  for (int i = 0; i < sizeof(expected_output) / sizeof(float); ++i) {
98  if (fabs(output[i] - expected_output[i]) > EPSON) {
99  printf("at index %d, output: %f, expected_output: %f\n", i, output[i], expected_output[i]);
100  av_freep(&output);
101  return 1;
102  }
103  }
104 
105  av_freep(&output);
106  return 0;
107 }
108 
109 static int test_with_valid(void)
110 {
111  // the input data and expected data are generated with below python code.
112  /*
113  import tensorflow as tf
114  import numpy as np
115 
116  x = tf.placeholder(tf.float32, shape=[1, None, None, 3])
117  y = tf.layers.average_pooling2d(x, pool_size=[2,2], strides=[1,1], padding='VALID')
118  data = np.random.rand(1, 5, 6, 3);
119 
120  sess=tf.Session()
121  sess.run(tf.global_variables_initializer())
122 
123  output = sess.run(y, feed_dict={x: data})
124 
125  print("input:")
126  print(data.shape)
127  print(list(data.flatten()))
128 
129  print("output:")
130  print(output.shape)
131  print(list(output.flatten()))
132  */
133 
134  AvgPoolParams params;
135  DnnOperand operands[2];
136  int32_t input_indexes[1];
137  float input[1*5*6*3] = {
138  0.5046741692941682, 0.9273653202485155, 0.8193878359859937, 0.1904059431360905, 0.8664919633253656, 0.7484625128286059, 0.984534184632278,
139  0.31900804890072254, 0.3259426099940872, 0.05388974903570376, 0.7356610151331133, 0.46710858713311965, 0.718553768817036, 0.062478421853278676,
140  0.7813224786584609, 0.4826837517658389, 0.9748095400220147, 0.8078547703898341, 0.11976750668368585, 0.8713586777195065, 0.41447321551284355,
141  0.9818788239089807, 0.4335715767584073, 0.4059793452147419, 0.3677205907204525, 0.47919995923571, 0.8341395256258882, 0.7059726374074609,
142  0.5478504551919791, 0.8622900484790175, 0.8343709722511167, 0.05089827275068537, 0.6465283980840416, 0.544539116066677, 0.39812057257884337,
143  0.9578115576866337, 0.25012888117580145, 0.579333516024662, 0.5556732133051457, 0.6119862111181243, 0.0018736758772316398, 0.9795490254040474,
144  0.4488085008883018, 0.28947489777011737, 0.4834108668633247, 0.9280490084385024, 0.9895821458049648, 0.31777618554697606, 0.42679693258977847,
145  0.74447844466923, 0.9752225305081498, 0.17564130841849335, 0.22382692067314292, 0.009602884447469373, 0.5144884415025782, 0.031622570708844555,
146  0.8277532752502512, 0.4111593210409763, 0.5272084646575664, 0.28856508082905297, 0.11317726946036655, 0.7203328275540273, 0.8310055019972384,
147  0.8535951508685228, 0.40230347305233227, 0.2819703265132867, 0.6243143957791139, 0.7512463693822311, 0.7523056340495644, 0.8838077258040928,
148  0.5472240664033092, 0.2550538284454935, 0.5560317774456567, 0.8966847087518931, 0.6728358284165321, 0.30361297147530875, 0.464343925441822,
149  0.34507695659461224, 0.6333175615390685, 0.26661369038523497, 0.9926748632253231, 0.9994267301382666, 0.8684917986974414, 0.3598754806113009,
150  0.49550268625464666, 0.03652458679973214, 0.13469081713137177, 0.4579424049273835, 0.48641107969110353, 0.9670250266945365
151  };
152  float expected_output[1*4*5*3] = {
153  0.44918162, 0.7746969, 0.5970757, 0.63113487, 0.5245679, 0.578631, 0.52802926, 0.52042985, 0.6223702, 0.57819676, 0.34922206,
154  0.6893124, 0.64503694, 0.37157673, 0.7983793, 0.49094033, 0.47153437, 0.5889187, 0.6025985, 0.30103004, 0.6757697, 0.6126377,
155  0.5765268, 0.62440413, 0.7237974, 0.5832023, 0.7004543, 0.49533707, 0.35433105, 0.6472913, 0.44694072, 0.28500956, 0.6628852,
156  0.39628282, 0.38472247, 0.6456326, 0.58590746, 0.60042334, 0.47854072, 0.7081889, 0.7219026, 0.5818187, 0.5276401, 0.56669396,
157  0.49804622, 0.4463231, 0.4799649, 0.5335578, 0.36531678, 0.4946247, 0.6143306, 0.6498792, 0.5644355, 0.6163815, 0.7432098,
158  0.5146416, 0.38221055, 0.6153918, 0.45535153, 0.5272688
159  };
160  float *output;
161 
162  params.strides = 1;
163  params.kernel_size = 2;
164  params.padding_method = VALID;
165 
166  operands[0].data = input;
167  operands[0].dims[0] = 1;
168  operands[0].dims[1] = 5;
169  operands[0].dims[2] = 6;
170  operands[0].dims[3] = 3;
171  operands[1].data = NULL;
172 
173  input_indexes[0] = 0;
174  ff_dnn_execute_layer_avg_pool(operands, input_indexes, 1, &params, NULL);
175 
176  output = operands[1].data;
177  for (int i = 0; i < sizeof(expected_output) / sizeof(float); ++i) {
178  if (fabs(output[i] - expected_output[i]) > EPSON) {
179  printf("at index %d, output: %f, expected_output: %f\n", i, output[i], expected_output[i]);
180  av_freep(&output);
181  return 1;
182  }
183  }
184 
185  av_freep(&output);
186  return 0;
187 }
188 
189 int main(int argc, char **argv)
190 {
191  if (test_with_same())
192  return 1;
193  if (test_with_valid())
194  return 1;
195 
196  return 0;
197 }
output
filter_frame For filters that do not use the this method is called when a frame is pushed to the filter s input It can be called at any time except in a reentrant way If the input frame is enough to produce output
Definition: filter_design.txt:225
AvgPoolParams::strides
int32_t strides
Definition: dnn_backend_native_layer_avgpool.h:32
AvgPoolParams::kernel_size
int32_t kernel_size
Definition: dnn_backend_native_layer_avgpool.h:32
ff_dnn_execute_layer_avg_pool
int ff_dnn_execute_layer_avg_pool(DnnOperand *operands, const int32_t *input_operand_indexes, int32_t output_operand_index, const void *parameters, NativeContext *ctx)
Execute the Average Pooling Layer.
Definition: dnn_backend_native_layer_avgpool.c:58
test_with_valid
static int test_with_valid(void)
Definition: dnn-layer-avgpool.c:109
EPSON
#define EPSON
Definition: dnn-layer-avgpool.c:24
DnnOperand::data
void * data
data pointer with data length in bytes.
Definition: dnn_backend_native.h:104
fabs
static __device__ float fabs(float a)
Definition: cuda_runtime.h:182
NULL
#define NULL
Definition: coverity.c:32
DnnOperand::dims
int32_t dims[4]
there are two memory layouts, NHWC or NCHW, so we use dims, dims[0] is Number.
Definition: dnn_backend_native.h:74
SAME
@ SAME
Definition: dnn_backend_native.h:54
test_with_same
static int test_with_same(void)
Definition: dnn-layer-avgpool.c:26
VALID
@ VALID
Definition: dnn_backend_native.h:54
printf
printf("static const uint8_t my_array[100] = {\n")
input
and forward the test the status of outputs and forward it to the corresponding return FFERROR_NOT_READY If the filters stores internally one or a few frame for some input
Definition: filter_design.txt:172
dnn_backend_native_layer_avgpool.h
i
#define i(width, name, range_min, range_max)
Definition: cbs_h2645.c:271
AvgPoolParams::padding_method
DNNPaddingParam padding_method
Definition: dnn_backend_native_layer_avgpool.h:33
DnnOperand
Definition: dnn_backend_native.h:69
AvgPoolParams
Definition: dnn_backend_native_layer_avgpool.h:31
av_freep
#define av_freep(p)
Definition: tableprint_vlc.h:35
int32_t
int32_t
Definition: audioconvert.c:56
main
int main(int argc, char **argv)
Definition: dnn-layer-avgpool.c:189