1 /*
2 * Copyright (c) 2018 Danil Iashchenko
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 "config_components.h"
22
29
30
36
39
43
45
51
55
57
59 {
61 const char *kernel_name;
62 cl_int cle;
63 int err;
64
66 if (err < 0)
68
69 ctx->command_queue = clCreateCommandQueue(
ctx->ocf.hwctx->context,
70 ctx->ocf.hwctx->device_id,
71 0, &cle);
73 "command queue %d.\n", cle);
74
75 if (!strcmp(avctx->
filter->
name,
"convolution_opencl")) {
76 kernel_name = "convolution_global";
77 }
else if (!strcmp(avctx->
filter->
name,
"sobel_opencl")) {
78 kernel_name = "sobel_global";
79 }
else if (!strcmp(avctx->
filter->
name,
"prewitt_opencl")){
80 kernel_name = "prewitt_global";
81 }
else if (!strcmp(avctx->
filter->
name,
"roberts_opencl")){
82 kernel_name = "roberts_global";
83 }
84 ctx->kernel = clCreateKernel(
ctx->ocf.program, kernel_name, &cle);
86 "kernel %d.\n", cle);
87
89 return 0;
90
92 if (
ctx->command_queue)
93 clReleaseCommandQueue(
ctx->command_queue);
95 clReleaseKernel(
ctx->kernel);
96 return err;
97 }
98
99
100
102 {
105 size_t matrix_bytes;
107 cl_int cle;
109 int sscanf_err;
110 char *p, *
arg, *saveptr =
NULL;
111 float input_matrix[4][49];
112
113 for (
i = 0;
i < 4;
i++) {
114 ctx->biases[
i] =
ctx->biases[
i] / 255.0;
115 }
116
117 for (
i = 0;
i < 4;
i++) {
118 p =
ctx->matrix_str[
i];
119 while (
ctx->matrix_sizes[
i] < 49) {
122 break;
123 }
125 sscanf_err = sscanf(
arg,
"%f", &input_matrix[
i][
ctx->matrix_sizes[
i]]);
126 if (sscanf_err != 1) {
129 }
130 ctx->matrix_sizes[
i]++;
131 }
132 if (
ctx->matrix_sizes[
i] == 9) {
134 }
else if (
ctx->matrix_sizes[
i] == 25) {
136 }
else if (
ctx->matrix_sizes[
i] == 49) {
138 } else {
141 }
142
143 }
144
145 for (j = 0; j < 4; j++) {
146 matrix_bytes =
sizeof(
float)*
ctx->matrix_sizes[j];
151 }
152
153 for (
i = 0;
i <
ctx->matrix_sizes[j];
i++)
155
156 buffer = clCreateBuffer(
ctx->ocf.hwctx->context,
157 CL_MEM_READ_ONLY |
158 CL_MEM_COPY_HOST_PTR |
159 CL_MEM_HOST_NO_ACCESS,
160 matrix_bytes,
matrix, &cle);
163 "%d.\n", cle);
166 }
169 }
170
171 return 0;
172 }
173
175 {
180 cl_int cle;
181 size_t global_work[2];
183 int err, p;
184 size_t origin[3] = {0, 0, 0};
185 size_t region[3] = {0, 0, 1};
186
190
191 if (!
input->hw_frames_ctx)
193
194 if (!
ctx->initialised) {
196 if (err < 0)
198
199 if (!strcmp(avctx->
filter->
name,
"convolution_opencl")) {
201 if (err < 0)
203 } else {
205 }
206
207 }
208
213 }
214
217 dst = (cl_mem)
output->data[p];
218
219 if (!dst)
220 break;
221
222 if (!strcmp(avctx->
filter->
name,
"convolution_opencl")) {
229
231 if (err < 0)
233
236 p, global_work[0], global_work[1]);
237
238 cle = clEnqueueNDRangeKernel(
ctx->command_queue,
ctx->kernel, 2,
NULL,
242 "kernel: %d.\n", cle);
243 } else {
244 if (!(
ctx->planes & (1 << p))) {
246 if (err < 0)
248
249 cle = clEnqueueCopyImage(
ctx->command_queue,
src, dst,
250 origin, origin, region, 0,
NULL,
NULL);
252 p, cle);
253 } else {
258
260 if (err < 0)
262
265 p, global_work[0], global_work[1]);
266
267 cle = clEnqueueNDRangeKernel(
ctx->command_queue,
ctx->kernel, 2,
NULL,
271 "kernel: %d.\n", cle);
272 }
273 }
274 }
275
276 cle = clFinish(
ctx->command_queue);
278
280 if (err < 0)
282
284
288
290
292 clFinish(
ctx->command_queue);
295 return err;
296 }
297
299 {
301 cl_int cle;
303
304 for (
i = 0;
i < 4;
i++) {
305 clReleaseMemObject(
ctx->matrix[
i]);
306 }
307
309 cle = clReleaseKernel(
ctx->kernel);
310 if (cle != CL_SUCCESS)
312 "kernel: %d.\n", cle);
313 }
314
315 if (
ctx->command_queue) {
316 cle = clReleaseCommandQueue(
ctx->command_queue);
317 if (cle != CL_SUCCESS)
319 "command queue: %d.\n", cle);
320 }
321
323 }
324
326 {
331 },
332 };
333
335 {
339 },
340 };
341
342 #define OFFSET(x) offsetof(ConvolutionOpenCLContext, x)
343 #define FLAGS (AV_OPT_FLAG_FILTERING_PARAM | AV_OPT_FLAG_VIDEO_PARAM)
344
345 #if CONFIG_CONVOLUTION_OPENCL_FILTER
346
347 static const AVOption convolution_opencl_options[] = {
361 };
362
364
366 .
name =
"convolution_opencl",
369 .priv_class = &convolution_opencl_class,
376 };
377
378 #endif /* CONFIG_CONVOLUTION_OPENCL_FILTER */
379
380 #if CONFIG_SOBEL_OPENCL_FILTER
381
382 static const AVOption sobel_opencl_options[] = {
387 };
388
390
392 .
name =
"sobel_opencl",
395 .priv_class = &sobel_opencl_class,
402 };
403
404 #endif /* CONFIG_SOBEL_OPENCL_FILTER */
405
406 #if CONFIG_PREWITT_OPENCL_FILTER
407
408 static const AVOption prewitt_opencl_options[] = {
413 };
414
416
418 .
name =
"prewitt_opencl",
421 .priv_class = &prewitt_opencl_class,
428 };
429
430 #endif /* CONFIG_PREWITT_OPENCL_FILTER */
431
432 #if CONFIG_ROBERTS_OPENCL_FILTER
433
434 static const AVOption roberts_opencl_options[] = {
439 };
440
442
444 .
name =
"roberts_opencl",
447 .priv_class = &roberts_opencl_class,
454 };
455
456 #endif /* CONFIG_ROBERTS_OPENCL_FILTER */