+static int maskedclamp_slice(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs)
+{
+ MaskedClampContext *s = ctx->priv;
+ ThreadData *td = arg;
+ int p;
+
+ for (p = 0; p < s->nb_planes; p++) {
+ const ptrdiff_t blinesize = td->b->linesize[p];
+ const ptrdiff_t brightlinesize = td->m->linesize[p];
+ const ptrdiff_t darklinesize = td->o->linesize[p];
+ const ptrdiff_t dlinesize = td->d->linesize[p];
+ const int w = s->width[p];
+ const int h = s->height[p];
+ const int slice_start = (h * jobnr) / nb_jobs;
+ const int slice_end = (h * (jobnr+1)) / nb_jobs;
+ const uint8_t *bsrc = td->b->data[p] + slice_start * blinesize;
+ const uint8_t *darksrc = td->o->data[p] + slice_start * darklinesize;
+ const uint8_t *brightsrc = td->m->data[p] + slice_start * brightlinesize;
+ uint8_t *dst = td->d->data[p] + slice_start * dlinesize;
+ const int undershoot = s->undershoot;
+ const int overshoot = s->overshoot;
+ int y;
+
+ if (!((1 << p) & s->planes)) {
+ av_image_copy_plane(dst, dlinesize, bsrc, blinesize,
+ s->linesize[p], slice_end - slice_start);
+ continue;
+ }
+
+ for (y = slice_start; y < slice_end; y++) {
+ s->dsp.maskedclamp(bsrc, dst, darksrc, brightsrc, w, undershoot, overshoot);
+
+ dst += dlinesize;
+ bsrc += blinesize;
+ darksrc += darklinesize;
+ brightsrc += brightlinesize;
+ }
+ }
+
+ return 0;
+}
+