History

avfilter/vf_convolution: add 16-column operation for filter_column()

Based on patch by Xu Jun <xujunzz@sjtu.edu.cn>

Paul B Mahol committed 6 years ago

Commit c6ce18b1 parent 63231fa3 files · +48 −39Browse files

Unified · Split

3 files
  1. libavfilter/convolution.h +1 −1
  2. libavfilter/vf_convolution.c +46 −37
  3. libavfilter/x86/vf_convolution_init.c +1 −1
libavfilter/convolution.h+1−1
@@ -57,7 +57,7 @@ typedef struct ConvolutionContext { · 56 unmodified lines
5757 void (*filter[4])(uint8_t *dst, int width,
5858 float rdiv, float bias, const int *const matrix,
5959 const uint8_t *c[], int peak, int radius,
60− int dstride, int stride);
60+ int dstride, int stride, int size);
6161 } ConvolutionContext;
6262
6363 void ff_convolution_init_x86(ConvolutionContext *s);
libavfilter/vf_convolution.c+46−37
@@ -110,7 +110,7 @@ typedef struct ThreadData { · 109 unmodified lines
110110 static void filter16_prewitt(uint8_t *dstp, int width,
111111 float scale, float delta, const int *const matrix,
112112 const uint8_t *c[], int peak, int radius,
113− int dstride, int stride)
113+ int dstride, int stride, int size)
114114 {
115115 uint16_t *dst = (uint16_t *)dstp;
116116 int x;
@@ -128,7 +128,7 @@ static void filter16_prewitt(uint8_t *dstp, int width, · 11 unmodified lines
128128 static void filter16_roberts(uint8_t *dstp, int width,
129129 float scale, float delta, const int *const matrix,
130130 const uint8_t *c[], int peak, int radius,
131− int dstride, int stride)
131+ int dstride, int stride, int size)
132132 {
133133 uint16_t *dst = (uint16_t *)dstp;
134134 int x;
@@ -144,7 +144,7 @@ static void filter16_roberts(uint8_t *dstp, int width, · 9 unmodified lines
144144 static void filter16_sobel(uint8_t *dstp, int width,
145145 float scale, float delta, const int *const matrix,
146146 const uint8_t *c[], int peak, int radius,
147− int dstride, int stride)
147+ int dstride, int stride, int size)
148148 {
149149 uint16_t *dst = (uint16_t *)dstp;
150150 int x;
@@ -162,7 +162,7 @@ static void filter16_sobel(uint8_t *dstp, int width, · 11 unmodified lines
162162 static void filter16_kirsch(uint8_t *dstp, int width,
163163 float scale, float delta, const int *const matrix,
164164 const uint8_t *c[], int peak, int radius,
165− int dstride, int stride)
165+ int dstride, int stride, int size)
166166 {
167167 uint16_t *dst = (uint16_t *)dstp;
168168 const uint16_t *c0 = (const uint16_t *)c[0], *c1 = (const uint16_t *)c[1], *c2 = (const uint16_t *)c[2];
@@ -211,7 +211,7 @@ static void filter16_kirsch(uint8_t *dstp, int width, · 42 unmodified lines
211211 static void filter_prewitt(uint8_t *dst, int width,
212212 float scale, float delta, const int *const matrix,
213213 const uint8_t *c[], int peak, int radius,
214− int dstride, int stride)
214+ int dstride, int stride, int size)
215215 {
216216 const uint8_t *c0 = c[0], *c1 = c[1], *c2 = c[2];
217217 const uint8_t *c3 = c[3], *c5 = c[5];
@@ -231,7 +231,7 @@ static void filter_prewitt(uint8_t *dst, int width, · 13 unmodified lines
231231 static void filter_roberts(uint8_t *dst, int width,
232232 float scale, float delta, const int *const matrix,
233233 const uint8_t *c[], int peak, int radius,
234− int dstride, int stride)
234+ int dstride, int stride, int size)
235235 {
236236 int x;
237237
@@ -246,7 +246,7 @@ static void filter_roberts(uint8_t *dst, int width, · 8 unmodified lines
246246 static void filter_sobel(uint8_t *dst, int width,
247247 float scale, float delta, const int *const matrix,
248248 const uint8_t *c[], int peak, int radius,
249− int dstride, int stride)
249+ int dstride, int stride, int size)
250250 {
251251 const uint8_t *c0 = c[0], *c1 = c[1], *c2 = c[2];
252252 const uint8_t *c3 = c[3], *c5 = c[5];
@@ -266,7 +266,7 @@ static void filter_sobel(uint8_t *dst, int width, · 13 unmodified lines
266266 static void filter_kirsch(uint8_t *dst, int width,
267267 float scale, float delta, const int *const matrix,
268268 const uint8_t *c[], int peak, int radius,
269− int dstride, int stride)
269+ int dstride, int stride, int size)
270270 {
271271 const uint8_t *c0 = c[0], *c1 = c[1], *c2 = c[2];
272272 const uint8_t *c3 = c[3], *c5 = c[5];
@@ -314,7 +314,7 @@ static void filter_kirsch(uint8_t *dst, int width, · 41 unmodified lines
314314 static void filter16_3x3(uint8_t *dstp, int width,
315315 float rdiv, float bias, const int *const matrix,
316316 const uint8_t *c[], int peak, int radius,
317− int dstride, int stride)
317+ int dstride, int stride, int size)
318318 {
319319 uint16_t *dst = (uint16_t *)dstp;
320320 int x;
@@ -337,7 +337,7 @@ static void filter16_3x3(uint8_t *dstp, int width, · 16 unmodified lines
337337 static void filter16_5x5(uint8_t *dstp, int width,
338338 float rdiv, float bias, const int *const matrix,
339339 const uint8_t *c[], int peak, int radius,
340− int dstride, int stride)
340+ int dstride, int stride, int size)
341341 {
342342 uint16_t *dst = (uint16_t *)dstp;
343343 int x;
@@ -356,7 +356,7 @@ static void filter16_5x5(uint8_t *dstp, int width, · 12 unmodified lines
356356 static void filter16_7x7(uint8_t *dstp, int width,
357357 float rdiv, float bias, const int *const matrix,
358358 const uint8_t *c[], int peak, int radius,
359− int dstride, int stride)
359+ int dstride, int stride, int size)
360360 {
361361 uint16_t *dst = (uint16_t *)dstp;
362362 int x;
@@ -375,7 +375,7 @@ static void filter16_7x7(uint8_t *dstp, int width, · 12 unmodified lines
375375 static void filter16_row(uint8_t *dstp, int width,
376376 float rdiv, float bias, const int *const matrix,
377377 const uint8_t *c[], int peak, int radius,
378− int dstride, int stride)
378+ int dstride, int stride, int size)
379379 {
380380 uint16_t *dst = (uint16_t *)dstp;
381381 int x;
@@ -394,19 +394,24 @@ static void filter16_row(uint8_t *dstp, int width, · 12 unmodified lines
394394 static void filter16_column(uint8_t *dstp, int height,
395395 float rdiv, float bias, const int *const matrix,
396396 const uint8_t *c[], int peak, int radius,
397− int dstride, int stride)
397+ int dstride, int stride, int size)
398398 {
399+ DECLARE_ALIGNED(64, int, sum)[16];
399400 uint16_t *dst = (uint16_t *)dstp;
400− int y;
401+ const int width = FFMIN(16, size);
401402
402− for (y = 0; y < height; y++) {
403− int i, sum = 0;
403+ for (int y = 0; y < height; y++) {
404404
405− for (i = 0; i < 2 * radius + 1; i++)
406− sum += AV_RN16A(&c[i][0 + y * stride]) * matrix[i];
405+ memset(sum, 0, sizeof(sum));
406+ for (int i = 0; i < 2 * radius + 1; i++) {
407+ for (int off16 = 0; off16 < width; off16++)
408+ sum[off16] += AV_RN16A(&c[i][0 + y * stride + off16 * 2]) * matrix[i];
409+ }
407410
408− sum = (int)(sum * rdiv + bias + 0.5f);
409− dst[0] = av_clip(sum, 0, peak);
411+ for (int off16 = 0; off16 < width; off16++) {
412+ sum[off16] = (int)(sum[off16] * rdiv + bias + 0.5f);
413+ dst[off16] = av_clip(sum[off16], 0, peak);
414+ }
410415 dst += dstride / 2;
411416 }
412417 }
@@ -414,7 +419,7 @@ static void filter16_column(uint8_t *dstp, int height, · 1 unmodified line
414419 static void filter_7x7(uint8_t *dst, int width,
415420 float rdiv, float bias, const int *const matrix,
416421 const uint8_t *c[], int peak, int radius,
417− int dstride, int stride)
422+ int dstride, int stride, int size)
418423 {
419424 int x;
420425
@@ -432,7 +437,7 @@ static void filter_7x7(uint8_t *dst, int width, · 11 unmodified lines
432437 static void filter_5x5(uint8_t *dst, int width,
433438 float rdiv, float bias, const int *const matrix,
434439 const uint8_t *c[], int peak, int radius,
435− int dstride, int stride)
440+ int dstride, int stride, int size)
436441 {
437442 int x;
438443
@@ -450,7 +455,7 @@ static void filter_5x5(uint8_t *dst, int width, · 11 unmodified lines
450455 static void filter_3x3(uint8_t *dst, int width,
451456 float rdiv, float bias, const int *const matrix,
452457 const uint8_t *c[], int peak, int radius,
453− int dstride, int stride)
458+ int dstride, int stride, int size)
454459 {
455460 const uint8_t *c0 = c[0], *c1 = c[1], *c2 = c[2];
456461 const uint8_t *c3 = c[3], *c4 = c[4], *c5 = c[5];
@@ -469,7 +474,7 @@ static void filter_3x3(uint8_t *dst, int width, · 12 unmodified lines
469474 static void filter_row(uint8_t *dst, int width,
470475 float rdiv, float bias, const int *const matrix,
471476 const uint8_t *c[], int peak, int radius,
472− int dstride, int stride)
477+ int dstride, int stride, int size)
473478 {
474479 int x;
475480
@@ -487,18 +492,22 @@ static void filter_row(uint8_t *dst, int width, · 11 unmodified lines
487492 static void filter_column(uint8_t *dst, int height,
488493 float rdiv, float bias, const int *const matrix,
489494 const uint8_t *c[], int peak, int radius,
490− int dstride, int stride)
495+ int dstride, int stride, int size)
491496 {
492− int y;
497+ DECLARE_ALIGNED(64, int, sum)[16];
493498
494− for (y = 0; y < height; y++) {
495− int i, sum = 0;
499+ for (int y = 0; y < height; y++) {
500+ memset(sum, 0, sizeof(sum));
496501
497− for (i = 0; i < 2 * radius + 1; i++)
498− sum += c[i][0 + y * stride] * matrix[i];
502+ for (int i = 0; i < 2 * radius + 1; i++) {
503+ for (int off16 = 0; off16 < 16; off16++)
504+ sum[off16] += c[i][0 + y * stride + off16] * matrix[i];
505+ }
499506
500− sum = (int)(sum * rdiv + bias + 0.5f);
501− dst[0] = av_clip_uint8(sum);
507+ for (int off16 = 0; off16 < 16; off16++) {
508+ sum[off16] = (int)(sum[off16] * rdiv + bias + 0.5f);
509+ dst[off16] = av_clip_uint8(sum[off16]);
510+ }
502511 dst += dstride;
503512 }
504513 }
@@ -605,6 +614,7 @@ static int filter_slice(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs) · 100 unmodified lines
605614 const int dst_pos = slice_start * (mode == MATRIX_COLUMN ? bpc : dstride);
606615 uint8_t *dst = out->data[plane] + dst_pos;
607616 const int *matrix = s->matrix[plane];
617+ const int step = mode == MATRIX_COLUMN ? 16 : 1;
608618 const uint8_t *c[49];
609619 int y, x;
610620
@@ -617,8 +627,7 @@ static int filter_slice(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs) · 6 unmodified lines
617627 width * bpc, slice_end - slice_start);
618628 continue;
619629 }
620−
621− for (y = slice_start; y < slice_end; y++) {
630+ for (y = slice_start; y < slice_end; y += step) {
622631 const int xoff = mode == MATRIX_COLUMN ? (y - slice_start) * bpc : radius * bpc;
623632 const int yoff = mode == MATRIX_COLUMN ? radius * dstride : 0;
624633
@@ -629,12 +638,12 @@ static int filter_slice(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs) · 4 unmodified lines
629638 s->setup[plane](radius, c, src, stride, x, width, y, height, bpc);
630639 s->filter[plane](dst + yoff + xoff, 1, rdiv,
631640 bias, matrix, c, s->max, radius,
632− dstride, stride);
641+ dstride, stride, slice_end - step);
633642 }
634643 s->setup[plane](radius, c, src, stride, radius, width, y, height, bpc);
635644 s->filter[plane](dst + yoff + xoff, sizew - 2 * radius,
636645 rdiv, bias, matrix, c, s->max, radius,
637− dstride, stride);
646+ dstride, stride, slice_end - step);
638647 for (x = sizew - radius; x < sizew; x++) {
639648 const int xoff = mode == MATRIX_COLUMN ? (y - slice_start) * bpc : x * bpc;
640649 const int yoff = mode == MATRIX_COLUMN ? x * dstride : 0;
@@ -642,7 +651,7 @@ static int filter_slice(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs) · 1 unmodified line
642651 s->setup[plane](radius, c, src, stride, x, width, y, height, bpc);
643652 s->filter[plane](dst + yoff + xoff, 1, rdiv,
644653 bias, matrix, c, s->max, radius,
645− dstride, stride);
654+ dstride, stride, slice_end - step);
646655 }
647656 if (mode != MATRIX_COLUMN)
648657 dst += dstride;
libavfilter/x86/vf_convolution_init.c+1−1
@@ -27,7 +27,7 @@ · 26 unmodified lines
2727 void ff_filter_3x3_sse4(uint8_t *dst, int width,
2828 float rdiv, float bias, const int *const matrix,
2929 const uint8_t *c[], int peak, int radius,
30− int dstride, int stride);
30+ int dstride, int stride, int size);
3131
3232 av_cold void ff_convolution_init_x86(ConvolutionContext *s)
3333 {

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t