| @@ -29,7 +29,7 @@ · 28 unmodified lines |
| 29 | #include "libavutil/imgutils.h" | 29 | #include "libavutil/imgutils.h" |
| 30 | #include "libavutil/opt.h" | 30 | #include "libavutil/opt.h" |
| 31 | #include "libavutil/pixdesc.h" | 31 | #include "libavutil/pixdesc.h" |
| 32 | #include "libavcodec/avfft.h" | 32 | #include "libavutil/tx.h" |
| 33 | #include "libavutil/eval.h" | 33 | #include "libavutil/eval.h" |
| 34 | | 34 | |
| 35 | #define MAX_THREADS 32 | 35 | #define MAX_THREADS 32 |
| @@ -51,16 +51,24 @@ typedef struct FFTFILTContext { · 15 unmodified lines |
| 51 | int planewidth[MAX_PLANES]; | 51 | int planewidth[MAX_PLANES]; |
| 52 | int planeheight[MAX_PLANES]; | 52 | int planeheight[MAX_PLANES]; |
| 53 | | 53 | |
| 54 | RDFTContext *hrdft[MAX_THREADS][MAX_PLANES]; | 54 | AVTXContext *hrdft[MAX_THREADS][MAX_PLANES]; |
| 55 | RDFTContext *vrdft[MAX_THREADS][MAX_PLANES]; | 55 | AVTXContext *vrdft[MAX_THREADS][MAX_PLANES]; |
| 56 | RDFTContext *ihrdft[MAX_THREADS][MAX_PLANES]; | 56 | AVTXContext *ihrdft[MAX_THREADS][MAX_PLANES]; |
| 57 | RDFTContext *ivrdft[MAX_THREADS][MAX_PLANES]; | 57 | AVTXContext *ivrdft[MAX_THREADS][MAX_PLANES]; |
| | 58 | |
| | 59 | av_tx_fn htx_fn, ihtx_fn; |
| | 60 | av_tx_fn vtx_fn, ivtx_fn; |
| | 61 | |
| 58 | int rdft_hbits[MAX_PLANES]; | 62 | int rdft_hbits[MAX_PLANES]; |
| 59 | int rdft_vbits[MAX_PLANES]; | 63 | int rdft_vbits[MAX_PLANES]; |
| | 64 | size_t rdft_hstride[MAX_PLANES]; |
| | 65 | size_t rdft_vstride[MAX_PLANES]; |
| 60 | size_t rdft_hlen[MAX_PLANES]; | 66 | size_t rdft_hlen[MAX_PLANES]; |
| 61 | size_t rdft_vlen[MAX_PLANES]; | 67 | size_t rdft_vlen[MAX_PLANES]; |
| 62 | FFTSample *rdft_hdata[MAX_PLANES]; | 68 | float *rdft_hdata_in[MAX_PLANES]; |
| 63 | FFTSample *rdft_vdata[MAX_PLANES]; | 69 | float *rdft_vdata_in[MAX_PLANES]; |
| | 70 | float *rdft_hdata_out[MAX_PLANES]; |
| | 71 | float *rdft_vdata_out[MAX_PLANES]; |
| 64 | | 72 | |
| 65 | int dc[MAX_PLANES]; | 73 | int dc[MAX_PLANES]; |
| 66 | char *weight_str[MAX_PLANES]; | 74 | char *weight_str[MAX_PLANES]; |
| @@ -97,14 +105,14 @@ AVFILTER_DEFINE_CLASS(fftfilt); · 30 unmodified lines |
| 97 | static inline double lum(void *priv, double x, double y, int plane) | 105 | static inline double lum(void *priv, double x, double y, int plane) |
| 98 | { | 106 | { |
| 99 | FFTFILTContext *s = priv; | 107 | FFTFILTContext *s = priv; |
| 100 | return s->rdft_vdata[plane][(int)x * s->rdft_vlen[plane] + (int)y]; | 108 | return s->rdft_vdata_out[plane][(int)x * s->rdft_vstride[plane] + (int)y]; |
| 101 | } | 109 | } |
| 102 | | 110 | |
| 103 | static double weight_Y(void *priv, double x, double y) { return lum(priv, x, y, Y); } | 111 | static double weight_Y(void *priv, double x, double y) { return lum(priv, x, y, Y); } |
| 104 | static double weight_U(void *priv, double x, double y) { return lum(priv, x, y, U); } | 112 | static double weight_U(void *priv, double x, double y) { return lum(priv, x, y, U); } |
| 105 | static double weight_V(void *priv, double x, double y) { return lum(priv, x, y, V); } | 113 | static double weight_V(void *priv, double x, double y) { return lum(priv, x, y, V); } |
| 106 | | 114 | |
| 107 | static void copy_rev(FFTSample *dest, int w, int w2) | 115 | static void copy_rev(float *dest, int w, int w2) |
| 108 | { | 116 | { |
| 109 | int i; | 117 | int i; |
| 110 | | 118 | |
| @@ -128,16 +136,19 @@ static int rdft_horizontal8(AVFilterContext *ctx, void *arg, int jobnr, int nb_j · 17 unmodified lines |
| 128 | | 136 | |
| 129 | for (int i = slice_start; i < slice_end; i++) { | 137 | for (int i = slice_start; i < slice_end; i++) { |
| 130 | const uint8_t *src = in->data[plane] + i * in->linesize[plane]; | 138 | const uint8_t *src = in->data[plane] + i * in->linesize[plane]; |
| 131 | float *hdata = s->rdft_hdata[plane] + i * s->rdft_hlen[plane]; | 139 | float *hdata_in = s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane]; |
| 132 | | 140 | |
| 133 | for (int j = 0; j < w; j++) | 141 | for (int j = 0; j < w; j++) |
| 134 | hdata[j] = src[j]; | 142 | hdata_in[j] = src[j]; |
| 135 | | 143 | |
| 136 | copy_rev(s->rdft_hdata[plane] + i * s->rdft_hlen[plane], w, s->rdft_hlen[plane]); | 144 | copy_rev(s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane], w, s->rdft_hlen[plane]); |
| 137 | } | 145 | } |
| 138 | | 146 | |
| 139 | for (int i = slice_start; i < slice_end; i++) | 147 | for (int i = slice_start; i < slice_end; i++) |
| 140 | av_rdft_calc(s->hrdft[jobnr][plane], s->rdft_hdata[plane] + i * s->rdft_hlen[plane]); | 148 | s->htx_fn(s->hrdft[jobnr][plane], |
| | 149 | s->rdft_hdata_out[plane] + i * s->rdft_hstride[plane], |
| | 150 | s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane], |
| | 151 | sizeof(float)); |
| 141 | } | 152 | } |
| 142 | | 153 | |
| 143 | return 0; | 154 | return 0; |
| @@ -156,16 +167,19 @@ static int rdft_horizontal16(AVFilterContext *ctx, void *arg, int jobnr, int nb_ · 12 unmodified lines |
| 156 | | 167 | |
| 157 | for (int i = slice_start; i < slice_end; i++) { | 168 | for (int i = slice_start; i < slice_end; i++) { |
| 158 | const uint16_t *src = (const uint16_t *)(in->data[plane] + i * in->linesize[plane]); | 169 | const uint16_t *src = (const uint16_t *)(in->data[plane] + i * in->linesize[plane]); |
| 159 | float *hdata = s->rdft_hdata[plane] + i * s->rdft_hlen[plane]; | 170 | float *hdata_in = s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane]; |
| 160 | | 171 | |
| 161 | for (int j = 0; j < w; j++) | 172 | for (int j = 0; j < w; j++) |
| 162 | hdata[j] = src[j]; | 173 | hdata_in[j] = src[j]; |
| 163 | | 174 | |
| 164 | copy_rev(s->rdft_hdata[plane] + i * s->rdft_hlen[plane], w, s->rdft_hlen[plane]); | 175 | copy_rev(s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane], w, s->rdft_hlen[plane]); |
| 165 | } | 176 | } |
| 166 | | 177 | |
| 167 | for (int i = slice_start; i < slice_end; i++) | 178 | for (int i = slice_start; i < slice_end; i++) |
| 168 | av_rdft_calc(s->hrdft[jobnr][plane], s->rdft_hdata[plane] + i * s->rdft_hlen[plane]); | 179 | s->htx_fn(s->hrdft[jobnr][plane], |
| | 180 | s->rdft_hdata_out[plane] + i * s->rdft_hstride[plane], |
| | 181 | s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane], |
| | 182 | sizeof(float)); |
| 169 | } | 183 | } |
| 170 | | 184 | |
| 171 | return 0; | 185 | return 0; |
| @@ -183,11 +197,14 @@ static int irdft_horizontal8(AVFilterContext *ctx, void *arg, int jobnr, int nb_ · 11 unmodified lines |
| 183 | const int slice_end = (h * (jobnr+1)) / nb_jobs; | 197 | const int slice_end = (h * (jobnr+1)) / nb_jobs; |
| 184 | | 198 | |
| 185 | for (int i = slice_start; i < slice_end; i++) | 199 | for (int i = slice_start; i < slice_end; i++) |
| 186 | av_rdft_calc(s->ihrdft[jobnr][plane], s->rdft_hdata[plane] + i * s->rdft_hlen[plane]); | 200 | s->ihtx_fn(s->ihrdft[jobnr][plane], |
| | 201 | s->rdft_hdata_out[plane] + i * s->rdft_hstride[plane], |
| | 202 | s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane], |
| | 203 | sizeof(float)); |
| 187 | | 204 | |
| 188 | for (int i = slice_start; i < slice_end; i++) { | 205 | for (int i = slice_start; i < slice_end; i++) { |
| 189 | const float scale = 4.f / (s->rdft_hlen[plane] * s->rdft_vlen[plane]); | 206 | const float scale = 1.f / (s->rdft_hlen[plane] * s->rdft_vlen[plane]); |
| 190 | const float *src = s->rdft_hdata[plane] + i * s->rdft_hlen[plane]; | 207 | const float *src = s->rdft_hdata_out[plane] + i * s->rdft_hstride[plane]; |
| 191 | uint8_t *dst = out->data[plane] + i * out->linesize[plane]; | 208 | uint8_t *dst = out->data[plane] + i * out->linesize[plane]; |
| 192 | | 209 | |
| 193 | for (int j = 0; j < w; j++) | 210 | for (int j = 0; j < w; j++) |
| @@ -211,11 +228,14 @@ static int irdft_horizontal16(AVFilterContext *ctx, void *arg, int jobnr, int nb · 17 unmodified lines |
| 211 | const int slice_end = (h * (jobnr+1)) / nb_jobs; | 228 | const int slice_end = (h * (jobnr+1)) / nb_jobs; |
| 212 | | 229 | |
| 213 | for (int i = slice_start; i < slice_end; i++) | 230 | for (int i = slice_start; i < slice_end; i++) |
| 214 | av_rdft_calc(s->ihrdft[jobnr][plane], s->rdft_hdata[plane] + i * s->rdft_hlen[plane]); | 231 | s->ihtx_fn(s->ihrdft[jobnr][plane], |
| | 232 | s->rdft_hdata_out[plane] + i * s->rdft_hstride[plane], |
| | 233 | s->rdft_hdata_in[plane] + i * s->rdft_hstride[plane], |
| | 234 | sizeof(float)); |
| 215 | | 235 | |
| 216 | for (int i = slice_start; i < slice_end; i++) { | 236 | for (int i = slice_start; i < slice_end; i++) { |
| 217 | const float scale = 4.f / (s->rdft_hlen[plane] * s->rdft_vlen[plane]); | 237 | const float scale = 1.f / (s->rdft_hlen[plane] * s->rdft_vlen[plane]); |
| 218 | const float *src = s->rdft_hdata[plane] + i * s->rdft_hlen[plane]; | 238 | const float *src = s->rdft_hdata_out[plane] + i * s->rdft_hstride[plane]; |
| 219 | uint16_t *dst = (uint16_t *)(out->data[plane] + i * out->linesize[plane]); | 239 | uint16_t *dst = (uint16_t *)(out->data[plane] + i * out->linesize[plane]); |
| 220 | | 240 | |
| 221 | for (int j = 0; j < w; j++) | 241 | for (int j = 0; j < w; j++) |
| @@ -303,34 +323,50 @@ static int config_props(AVFilterLink *inlink) · 81 unmodified lines |
| 303 | | 323 | |
| 304 | /* RDFT - Array initialization for Horizontal pass*/ | 324 | /* RDFT - Array initialization for Horizontal pass*/ |
| 305 | s->rdft_hlen[i] = 1 << (32 - ff_clz(w)); | 325 | s->rdft_hlen[i] = 1 << (32 - ff_clz(w)); |
| | 326 | s->rdft_hstride[i] = FFALIGN(s->rdft_hlen[i] + 2, av_cpu_max_align()); |
| 306 | s->rdft_hbits[i] = av_log2(s->rdft_hlen[i]); | 327 | s->rdft_hbits[i] = av_log2(s->rdft_hlen[i]); |
| 307 | if (!(s->rdft_hdata[i] = av_malloc_array(h, s->rdft_hlen[i] * sizeof(FFTSample)))) | 328 | if (!(s->rdft_hdata_in[i] = av_calloc(h, s->rdft_hstride[i] * sizeof(float)))) |
| | 329 | return AVERROR(ENOMEM); |
| | 330 | |
| | 331 | if (!(s->rdft_hdata_out[i] = av_calloc(h, s->rdft_hstride[i] * sizeof(float)))) |
| 308 | return AVERROR(ENOMEM); | 332 | return AVERROR(ENOMEM); |
| 309 | | 333 | |
| 310 | for (int j = 0; j < s->nb_threads; j++) { | 334 | for (int j = 0; j < s->nb_threads; j++) { |
| 311 | if (!(s->hrdft[j][i] = av_rdft_init(s->rdft_hbits[i], DFT_R2C))) | 335 | float scale = 1.f, iscale = 1.f; |
| | 336 | |
| | 337 | av_tx_init(&s->hrdft[j][i], &s->htx_fn, AV_TX_FLOAT_RDFT, 0, 1 << s->rdft_hbits[i], &scale, 0); |
| | 338 | if (!s->hrdft[j][i]) |
| 312 | return AVERROR(ENOMEM); | 339 | return AVERROR(ENOMEM); |
| 313 | if (!(s->ihrdft[j][i] = av_rdft_init(s->rdft_hbits[i], IDFT_C2R))) | 340 | av_tx_init(&s->ihrdft[j][i], &s->ihtx_fn, AV_TX_FLOAT_RDFT, 1, 1 << s->rdft_hbits[i], &iscale, 0); |
| | 341 | if (!s->ihrdft[j][i]) |
| 314 | return AVERROR(ENOMEM); | 342 | return AVERROR(ENOMEM); |
| 315 | } | 343 | } |
| 316 | | 344 | |
| 317 | /* RDFT - Array initialization for Vertical pass*/ | 345 | /* RDFT - Array initialization for Vertical pass*/ |
| 318 | s->rdft_vlen[i] = 1 << (32 - ff_clz(h)); | 346 | s->rdft_vlen[i] = 1 << (32 - ff_clz(h)); |
| | 347 | s->rdft_vstride[i] = FFALIGN(s->rdft_vlen[i] + 2, av_cpu_max_align()); |
| 319 | s->rdft_vbits[i] = av_log2(s->rdft_vlen[i]); | 348 | s->rdft_vbits[i] = av_log2(s->rdft_vlen[i]); |
| 320 | if (!(s->rdft_vdata[i] = av_malloc_array(s->rdft_hlen[i], s->rdft_vlen[i] * sizeof(FFTSample)))) | 349 | if (!(s->rdft_vdata_in[i] = av_calloc(s->rdft_hstride[i], s->rdft_vstride[i] * sizeof(float)))) |
| | 350 | return AVERROR(ENOMEM); |
| | 351 | |
| | 352 | if (!(s->rdft_vdata_out[i] = av_calloc(s->rdft_hstride[i], s->rdft_vstride[i] * sizeof(float)))) |
| 321 | return AVERROR(ENOMEM); | 353 | return AVERROR(ENOMEM); |
| 322 | | 354 | |
| 323 | for (int j = 0; j < s->nb_threads; j++) { | 355 | for (int j = 0; j < s->nb_threads; j++) { |
| 324 | if (!(s->vrdft[j][i] = av_rdft_init(s->rdft_vbits[i], DFT_R2C))) | 356 | float scale = 1.f, iscale = 1.f; |
| | 357 | |
| | 358 | av_tx_init(&s->vrdft[j][i], &s->vtx_fn, AV_TX_FLOAT_RDFT, 0, 1 << s->rdft_vbits[i], &scale, 0); |
| | 359 | if (!s->vrdft[j][i]) |
| 325 | return AVERROR(ENOMEM); | 360 | return AVERROR(ENOMEM); |
| 326 | if (!(s->ivrdft[j][i] = av_rdft_init(s->rdft_vbits[i], IDFT_C2R))) | 361 | av_tx_init(&s->ivrdft[j][i], &s->ivtx_fn, AV_TX_FLOAT_RDFT, 1, 1 << s->rdft_vbits[i], &iscale, 0); |
| | 362 | if (!s->ivrdft[j][i]) |
| 327 | return AVERROR(ENOMEM); | 363 | return AVERROR(ENOMEM); |
| 328 | } | 364 | } |
| 329 | } | 365 | } |
| 330 | | 366 | |
| 331 | /*Luminance value - Array initialization*/ | 367 | /*Luminance value - Array initialization*/ |
| 332 | for (plane = 0; plane < 3; plane++) { | 368 | for (plane = 0; plane < 3; plane++) { |
| 333 | if(!(s->weight[plane] = av_malloc_array(s->rdft_hlen[plane], s->rdft_vlen[plane] * sizeof(double)))) | 369 | if(!(s->weight[plane] = av_calloc(s->rdft_hlen[plane], s->rdft_vlen[plane] * sizeof(double)))) |
| 334 | return AVERROR(ENOMEM); | 370 | return AVERROR(ENOMEM); |
| 335 | | 371 | |
| 336 | if (s->eval_mode == EVAL_MODE_INIT) | 372 | if (s->eval_mode == EVAL_MODE_INIT) |
| @@ -360,7 +396,7 @@ static int multiply_data(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs · 23 unmodified lines |
| 360 | /*Change user defined parameters*/ | 396 | /*Change user defined parameters*/ |
| 361 | for (int i = slice_start; i < slice_end; i++) { | 397 | for (int i = slice_start; i < slice_end; i++) { |
| 362 | const double *weight = s->weight[plane] + i * s->rdft_vlen[plane]; | 398 | const double *weight = s->weight[plane] + i * s->rdft_vlen[plane]; |
| 363 | float *vdata = s->rdft_vdata[plane] + i * s->rdft_vlen[plane]; | 399 | float *vdata = s->rdft_vdata_out[plane] + i * s->rdft_vstride[plane]; |
| 364 | | 400 | |
| 365 | for (int j = 0; j < s->rdft_vlen[plane]; j++) | 401 | for (int j = 0; j < s->rdft_vlen[plane]; j++) |
| 366 | vdata[j] *= weight[j]; | 402 | vdata[j] *= weight[j]; |
| @@ -377,16 +413,18 @@ static int copy_vertical(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs · 10 unmodified lines |
| 377 | for (int plane = 0; plane < s->nb_planes; plane++) { | 413 | for (int plane = 0; plane < s->nb_planes; plane++) { |
| 378 | const int hlen = s->rdft_hlen[plane]; | 414 | const int hlen = s->rdft_hlen[plane]; |
| 379 | const int vlen = s->rdft_vlen[plane]; | 415 | const int vlen = s->rdft_vlen[plane]; |
| | 416 | const int hstride = s->rdft_hstride[plane]; |
| | 417 | const int vstride = s->rdft_vstride[plane]; |
| 380 | const int slice_start = (hlen * jobnr) / nb_jobs; | 418 | const int slice_start = (hlen * jobnr) / nb_jobs; |
| 381 | const int slice_end = (hlen * (jobnr+1)) / nb_jobs; | 419 | const int slice_end = (hlen * (jobnr+1)) / nb_jobs; |
| 382 | const int h = s->planeheight[plane]; | 420 | const int h = s->planeheight[plane]; |
| 383 | FFTSample *hdata = s->rdft_hdata[plane]; | 421 | float *hdata = s->rdft_hdata_out[plane]; |
| 384 | FFTSample *vdata = s->rdft_vdata[plane]; | 422 | float *vdata = s->rdft_vdata_in[plane]; |
| 385 | | 423 | |
| 386 | for (int i = slice_start; i < slice_end; i++) { | 424 | for (int i = slice_start; i < slice_end; i++) { |
| 387 | for (int j = 0; j < h; j++) | 425 | for (int j = 0; j < h; j++) |
| 388 | vdata[i * vlen + j] = hdata[j * hlen + i]; | 426 | vdata[i * vstride + j] = hdata[j * hstride + i]; |
| 389 | copy_rev(vdata + i * vlen, h, vlen); | 427 | copy_rev(vdata + i * vstride, h, vlen); |
| 390 | } | 428 | } |
| 391 | } | 429 | } |
| 392 | | 430 | |
| @@ -403,7 +441,10 @@ static int rdft_vertical(AVFilterContext *ctx, void *arg, int jobnr, int nb_jobs · 10 unmodified lines |
| 403 | const int slice_end = (height * (jobnr+1)) / nb_jobs; | 441 | const int slice_end = (height * (jobnr+1)) / nb_jobs; |
| 404 | | 442 | |
| 405 | for (int i = slice_start; i < slice_end; i++) | 443 | for (int i = slice_start; i < slice_end; i++) |
| 406 | av_rdft_calc(s->vrdft[jobnr][plane], s->rdft_vdata[plane] + i * s->rdft_vlen[plane]); | 444 | s->vtx_fn(s->vrdft[jobnr][plane], |
| | 445 | s->rdft_vdata_out[plane] + i * s->rdft_vstride[plane], |
| | 446 | s->rdft_vdata_in[plane] + i * s->rdft_vstride[plane], |
| | 447 | sizeof(float)); |
| 407 | } | 448 | } |
| 408 | | 449 | |
| 409 | return 0; | 450 | return 0; |
| @@ -419,7 +460,10 @@ static int irdft_vertical(AVFilterContext *ctx, void *arg, int jobnr, int nb_job · 9 unmodified lines |
| 419 | const int slice_end = (height * (jobnr+1)) / nb_jobs; | 460 | const int slice_end = (height * (jobnr+1)) / nb_jobs; |
| 420 | | 461 | |
| 421 | for (int i = slice_start; i < slice_end; i++) | 462 | for (int i = slice_start; i < slice_end; i++) |
| 422 | av_rdft_calc(s->ivrdft[jobnr][plane], s->rdft_vdata[plane] + i * s->rdft_vlen[plane]); | 463 | s->ivtx_fn(s->ivrdft[jobnr][plane], |
| | 464 | s->rdft_vdata_in[plane] + i * s->rdft_vstride[plane], |
| | 465 | s->rdft_vdata_out[plane] + i * s->rdft_vstride[plane], |
| | 466 | sizeof(float)); |
| 423 | } | 467 | } |
| 424 | | 468 | |
| 425 | return 0; | 469 | return 0; |
| @@ -431,16 +475,17 @@ static int copy_horizontal(AVFilterContext *ctx, void *arg, int jobnr, int nb_jo · 5 unmodified lines |
| 431 | | 475 | |
| 432 | for (int plane = 0; plane < s->nb_planes; plane++) { | 476 | for (int plane = 0; plane < s->nb_planes; plane++) { |
| 433 | const int hlen = s->rdft_hlen[plane]; | 477 | const int hlen = s->rdft_hlen[plane]; |
| 434 | const int vlen = s->rdft_vlen[plane]; | 478 | const int hstride = s->rdft_hstride[plane]; |
| | 479 | const int vstride = s->rdft_vstride[plane]; |
| 435 | const int slice_start = (hlen * jobnr) / nb_jobs; | 480 | const int slice_start = (hlen * jobnr) / nb_jobs; |
| 436 | const int slice_end = (hlen * (jobnr+1)) / nb_jobs; | 481 | const int slice_end = (hlen * (jobnr+1)) / nb_jobs; |
| 437 | const int h = s->planeheight[plane]; | 482 | const int h = s->planeheight[plane]; |
| 438 | FFTSample *hdata = s->rdft_hdata[plane]; | 483 | float *hdata = s->rdft_hdata_in[plane]; |
| 439 | FFTSample *vdata = s->rdft_vdata[plane]; | 484 | float *vdata = s->rdft_vdata_in[plane]; |
| 440 | | 485 | |
| 441 | for (int i = slice_start; i < slice_end; i++) | 486 | for (int i = slice_start; i < slice_end; i++) |
| 442 | for (int j = 0; j < h; j++) | 487 | for (int j = 0; j < h; j++) |
| 443 | hdata[j * hlen + i] = vdata[i * vlen + j]; | 488 | hdata[j * hstride + i] = vdata[i * vstride + j]; |
| 444 | } | 489 | } |
| 445 | | 490 | |
| 446 | return 0; | 491 | return 0; |
| @@ -461,11 +506,6 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in) · 14 unmodified lines |
| 461 | | 506 | |
| 462 | av_frame_copy_props(out, in); | 507 | av_frame_copy_props(out, in); |
| 463 | | 508 | |
| 464 | for (int plane = 0; plane < s->nb_planes; plane++) { | | |
| 465 | if (s->eval_mode == EVAL_MODE_FRAME) | | |
| 466 | do_eval(s, inlink, plane); | | |
| 467 | } | | |
| 468 | | | |
| 469 | ff_filter_execute(ctx, s->rdft_horizontal, in, NULL, | 509 | ff_filter_execute(ctx, s->rdft_horizontal, in, NULL, |
| 470 | FFMIN(s->planeheight[1], s->nb_threads)); | 510 | FFMIN(s->planeheight[1], s->nb_threads)); |
| 471 | | 511 | |
| @@ -475,11 +515,16 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in) · 3 unmodified lines |
| 475 | ff_filter_execute(ctx, rdft_vertical, NULL, NULL, | 515 | ff_filter_execute(ctx, rdft_vertical, NULL, NULL, |
| 476 | FFMIN(s->planeheight[1], s->nb_threads)); | 516 | FFMIN(s->planeheight[1], s->nb_threads)); |
| 477 | | 517 | |
| | 518 | for (int plane = 0; plane < s->nb_planes; plane++) { |
| | 519 | if (s->eval_mode == EVAL_MODE_FRAME) |
| | 520 | do_eval(s, inlink, plane); |
| | 521 | } |
| | 522 | |
| 478 | ff_filter_execute(ctx, multiply_data, NULL, NULL, | 523 | ff_filter_execute(ctx, multiply_data, NULL, NULL, |
| 479 | FFMIN(s->planeheight[1], s->nb_threads)); | 524 | FFMIN(s->planeheight[1], s->nb_threads)); |
| 480 | | 525 | |
| 481 | for (int plane = 0; plane < s->nb_planes; plane++) | 526 | for (int plane = 0; plane < s->nb_planes; plane++) |
| 482 | s->rdft_vdata[plane][0] += s->rdft_hlen[plane] * s->rdft_vlen[plane] * s->dc[plane]; | 527 | s->rdft_vdata_out[plane][0] += s->rdft_hlen[plane] * s->rdft_vlen[plane] * s->dc[plane] * (1 << (s->depth - 8)); |
| 483 | | 528 | |
| 484 | ff_filter_execute(ctx, irdft_vertical, NULL, NULL, | 529 | ff_filter_execute(ctx, irdft_vertical, NULL, NULL, |
| 485 | FFMIN(s->planeheight[1], s->nb_threads)); | 530 | FFMIN(s->planeheight[1], s->nb_threads)); |
| @@ -497,17 +542,19 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in) · 11 unmodified lines |
| 497 | static av_cold void uninit(AVFilterContext *ctx) | 542 | static av_cold void uninit(AVFilterContext *ctx) |
| 498 | { | 543 | { |
| 499 | FFTFILTContext *s = ctx->priv; | 544 | FFTFILTContext *s = ctx->priv; |
| 500 | int i; | 545 | |
| 501 | for (i = 0; i < MAX_PLANES; i++) { | 546 | for (int i = 0; i < MAX_PLANES; i++) { |
| 502 | av_free(s->rdft_hdata[i]); | 547 | av_freep(&s->rdft_hdata_in[i]); |
| 503 | av_free(s->rdft_vdata[i]); | 548 | av_freep(&s->rdft_vdata_in[i]); |
| | 549 | av_freep(&s->rdft_hdata_out[i]); |
| | 550 | av_freep(&s->rdft_vdata_out[i]); |
| 504 | av_expr_free(s->weight_expr[i]); | 551 | av_expr_free(s->weight_expr[i]); |
| 505 | av_free(s->weight[i]); | 552 | av_freep(&s->weight[i]); |
| 506 | for (int j = 0; j < s->nb_threads; j++) { | 553 | for (int j = 0; j < s->nb_threads; j++) { |
| 507 | av_rdft_end(s->hrdft[j][i]); | 554 | av_tx_uninit(&s->hrdft[j][i]); |
| 508 | av_rdft_end(s->ihrdft[j][i]); | 555 | av_tx_uninit(&s->ihrdft[j][i]); |
| 509 | av_rdft_end(s->vrdft[j][i]); | 556 | av_tx_uninit(&s->vrdft[j][i]); |
| 510 | av_rdft_end(s->ivrdft[j][i]); | 557 | av_tx_uninit(&s->ivrdft[j][i]); |
| 511 | } | 558 | } |
| 512 | } | 559 | } |
| 513 | } | 560 | } |