FFmpeg
utils.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2024 Niklas Haas
3  * Copyright (C) 2001-2003 Michael Niedermayer <michaelni@gmx.at>
4  *
5  * This file is part of FFmpeg.
6  *
7  * FFmpeg is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * FFmpeg is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with FFmpeg; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20  */
21 
22 #include "config.h"
23 
24 #define _DEFAULT_SOURCE
25 #define _SVID_SOURCE // needed for MAP_ANONYMOUS
26 #define _DARWIN_C_SOURCE // needed for MAP_ANON
27 #include <inttypes.h>
28 #include <math.h>
29 #include <stdio.h>
30 #include <string.h>
31 #if HAVE_MMAP
32 #include <sys/mman.h>
33 #if defined(MAP_ANON) && !defined(MAP_ANONYMOUS)
34 #define MAP_ANONYMOUS MAP_ANON
35 #endif
36 #endif
37 #if HAVE_VIRTUALALLOC
38 #include <windows.h>
39 #endif
40 
41 #include "libavutil/attributes.h"
42 #include "libavutil/avassert.h"
43 #include "libavutil/cpu.h"
44 #include "libavutil/csp.h"
45 #include "libavutil/emms.h"
46 #include "libavutil/imgutils.h"
47 #include "libavutil/intreadwrite.h"
48 #include "libavutil/libm.h"
49 #include "libavutil/mathematics.h"
50 #include "libavutil/mem.h"
51 #include "libavutil/opt.h"
52 #include "libavutil/pixdesc.h"
53 #include "libavutil/refstruct.h"
54 #include "libavutil/slicethread.h"
55 #include "libavutil/thread.h"
56 #include "libavutil/aarch64/cpu.h"
57 #include "libavutil/ppc/cpu.h"
58 #include "libavutil/x86/asm.h"
59 #include "libavutil/x86/cpu.h"
61 
62 #include "rgb2rgb.h"
63 #include "swscale.h"
64 #include "swscale_internal.h"
65 #include "graph.h"
66 
67 #if CONFIG_VULKAN
68 #include "vulkan/ops.h"
69 #endif
70 
72 {
73  if (ctx->backends)
74  return ctx->backends;
75 
76  SwsBackend fallback = SWS_BACKEND_STABLE;
77  if (ctx->flags & SWS_UNSTABLE)
78  fallback |= SWS_BACKEND_UNSTABLE;
79 
80  return fallback;
81 }
82 
83 /**
84  * Allocate and return an SwsContext without performing initialization.
85  */
86 static SwsContext *alloc_set_opts(int srcW, int srcH, enum AVPixelFormat srcFormat,
87  int dstW, int dstH, enum AVPixelFormat dstFormat,
88  int flags, const double *param)
89 {
91  if (!sws)
92  return NULL;
93 
94  sws->flags = flags;
95  sws->src_w = srcW;
96  sws->src_h = srcH;
97  sws->dst_w = dstW;
98  sws->dst_h = dstH;
99  sws->src_format = srcFormat;
100  sws->dst_format = dstFormat;
101 
102  for (int i = 0; param && i < SWS_NUM_SCALER_PARAMS; i++)
103  sws->scaler_params[i] = param[i];
104 
105  return sws;
106 }
107 
109  int filterSize, int16_t *filter,
110  int dstW)
111 {
112 #if ARCH_X86_64
113  int i, j, k;
114  int cpu_flags = av_get_cpu_flags();
115  if (!filter)
116  return 0;
118  if ((c->srcBpc == 8) && (c->dstBpc <= 14)) {
119  int16_t *filterCopy = NULL;
120  if (filterSize > 4) {
121  filterCopy = av_malloc_array(dstW, filterSize * sizeof(*filterCopy));
122  if (!filterCopy)
123  return AVERROR(ENOMEM);
124  memcpy(filterCopy, filter, dstW * filterSize * sizeof(int16_t));
125  }
126  // Do not swap filterPos for pixels which won't be processed by
127  // the main loop.
128  for (i = 0; i + 16 <= dstW; i += 16) {
129  FFSWAP(int, filterPos[i + 2], filterPos[i + 4]);
130  FFSWAP(int, filterPos[i + 3], filterPos[i + 5]);
131  FFSWAP(int, filterPos[i + 10], filterPos[i + 12]);
132  FFSWAP(int, filterPos[i + 11], filterPos[i + 13]);
133  }
134  if (filterSize > 4) {
135  // 16 pixels are processed at a time.
136  for (i = 0; i + 16 <= dstW; i += 16) {
137  // 4 filter coeffs are processed at a time.
138  for (k = 0; k + 4 <= filterSize; k += 4) {
139  for (j = 0; j < 16; ++j) {
140  int from = (i + j) * filterSize + k;
141  int to = i * filterSize + j * 4 + k * 16;
142  memcpy(&filter[to], &filterCopy[from], 4 * sizeof(int16_t));
143  }
144  }
145  }
146  // 4 pixels are processed at a time in the tail.
147  for (; i < dstW; i += 4) {
148  // 4 filter coeffs are processed at a time.
149  int rem = dstW - i >= 4 ? 4 : dstW - i;
150  for (k = 0; k + 4 <= filterSize; k += 4) {
151  for (j = 0; j < rem; ++j) {
152  int from = (i + j) * filterSize + k;
153  int to = i * filterSize + j * 4 + k * 4;
154  memcpy(&filter[to], &filterCopy[from], 4 * sizeof(int16_t));
155  }
156  }
157  }
158  }
159  av_free(filterCopy);
160  }
161  }
162 #endif
163  return 0;
164 }
165 
166 static double getSplineCoeff(double a, double b, double c, double d,
167  double dist)
168 {
169  if (dist <= 1.0)
170  return ((d * dist + c) * dist + b) * dist + a;
171  else
172  return getSplineCoeff(0.0,
173  b + 2.0 * c + 3.0 * d,
174  c + 3.0 * d,
175  -b - 3.0 * c - 6.0 * d,
176  dist - 1.0);
177 }
178 
179 static av_cold int get_local_pos(SwsInternal *s, int chr_subsample, int pos, int dir)
180 {
181  if (pos == -1 || pos <= -513) {
182  pos = (128 << chr_subsample) - 128;
183  }
184  pos += 128; // relative to ideal left edge
185  return pos >> chr_subsample;
186 }
187 
188 typedef struct {
189  int flag; ///< flag associated to the algorithm
190  const char *description; ///< human-readable description
191  int size_factor; ///< size factor used when initing the filters
193 
195  { SWS_AREA, "area averaging", 1 /* downscale only, for upscale it is bilinear */ },
196  { SWS_BICUBIC, "bicubic", 4 },
197  { SWS_BICUBLIN, "luma bicubic / chroma bilinear", -1 },
198  { SWS_BILINEAR, "bilinear", 2 },
199  { SWS_FAST_BILINEAR, "fast bilinear", -1 },
200  { SWS_GAUSS, "Gaussian", 8 /* infinite ;) */ },
201  { SWS_LANCZOS, "Lanczos", -1 /* custom */ },
202  { SWS_POINT, "nearest neighbor / point", -1 },
203  { SWS_SINC, "sinc", 20 /* infinite ;) */ },
204  { SWS_SPLINE, "bicubic spline", 20 /* infinite :)*/ },
205  { SWS_X, "experimental", 8 },
206 };
207 
208 static av_cold int initFilter(int16_t **outFilter, int32_t **filterPos,
209  int *outFilterSize, int xInc, int srcW,
210  int dstW, int filterAlign, int one,
211  int scaler, int flags, int cpu_flags,
212  SwsVector *srcFilter, SwsVector *dstFilter,
213  double param[SWS_NUM_SCALER_PARAMS], int srcPos, int dstPos)
214 {
215  int i;
216  int filterSize;
217  int filter2Size;
218  int minFilterSize;
219  int64_t *filter = NULL;
220  int64_t *filter2 = NULL;
221  const int64_t fone = 1LL << (54 - FFMIN(av_log2(srcW/dstW), 8));
222  int ret = -1;
223 
224  emms_c(); // FIXME should not be required but IS (even for non-MMX versions)
225 
226  // NOTE: the +3 is for the MMX(+1) / SSE(+3) scaler which reads over the end
227  if (!FF_ALLOC_TYPED_ARRAY(*filterPos, dstW + 3))
228  goto nomem;
229 
230  if (FFABS(xInc - 0x10000) < 10 && srcPos == dstPos) { // unscaled
231  int i;
232  filterSize = 1;
233  if (!FF_ALLOCZ_TYPED_ARRAY(filter, dstW * filterSize))
234  goto nomem;
235 
236  for (i = 0; i < dstW; i++) {
237  filter[i * filterSize] = fone;
238  (*filterPos)[i] = i;
239  }
240  } else if (scaler == SWS_POINT) { // lame looking point sampling mode
241  int i;
242  int64_t xDstInSrc;
243  filterSize = 1;
244  if (!FF_ALLOC_TYPED_ARRAY(filter, dstW * filterSize))
245  goto nomem;
246 
247  xDstInSrc = ((dstPos*(int64_t)xInc)>>8) - ((srcPos*0x8000LL)>>7);
248  for (i = 0; i < dstW; i++) {
249  int xx = (xDstInSrc - ((filterSize - 1) << 15) + (1 << 15)) >> 16;
250 
251  (*filterPos)[i] = xx;
252  filter[i] = fone;
253  xDstInSrc += xInc;
254  }
255  } else if ((xInc <= (1 << 16) && (scaler == SWS_AREA)) ||
256  (scaler == SWS_FAST_BILINEAR)) { // bilinear upscale
257  int i;
258  int64_t xDstInSrc;
259  filterSize = 2;
260  if (!FF_ALLOC_TYPED_ARRAY(filter, dstW * filterSize))
261  goto nomem;
262 
263  xDstInSrc = ((dstPos*(int64_t)xInc)>>8) - ((srcPos*0x8000LL)>>7);
264  for (i = 0; i < dstW; i++) {
265  int xx = (xDstInSrc - ((filterSize - 1) << 15) + (1 << 15)) >> 16;
266  int j;
267 
268  (*filterPos)[i] = xx;
269  // bilinear upscale / linear interpolate / area averaging
270  for (j = 0; j < filterSize; j++) {
271  int64_t coeff = fone - FFABS((int64_t)xx * (1 << 16) - xDstInSrc) * (fone >> 16);
272  if (coeff < 0)
273  coeff = 0;
274  filter[i * filterSize + j] = coeff;
275  xx++;
276  }
277  xDstInSrc += xInc;
278  }
279  } else {
280  int64_t xDstInSrc;
281  int sizeFactor = -1;
282 
283  for (i = 0; i < FF_ARRAY_ELEMS(scale_algorithms); i++) {
284  if (scaler == scale_algorithms[i].flag && scale_algorithms[i].size_factor > 0) {
285  sizeFactor = scale_algorithms[i].size_factor;
286  break;
287  }
288  }
289  if (scaler == SWS_LANCZOS)
290  sizeFactor = param[0] != SWS_PARAM_DEFAULT ? ceil(2 * param[0]) : 6;
291  av_assert0(sizeFactor > 0);
292 
293  if (sizeFactor > 50) {
294  ret = AVERROR(EINVAL);
295  goto fail;
296  }
297 
298  if (xInc <= 1 << 16)
299  filterSize = 1 + sizeFactor; // upscale
300  else
301  filterSize = 1 + (sizeFactor * srcW + dstW - 1) / dstW;
302 
303  filterSize = FFMIN(filterSize, srcW - 2);
304  filterSize = FFMAX(filterSize, 1);
305 
306  filter = av_malloc_array(dstW, filterSize * sizeof(*filter));
307  if (!filter)
308  goto nomem;
309  xDstInSrc = ((dstPos*(int64_t)xInc)>>7) - ((srcPos*0x10000LL)>>7);
310  for (i = 0; i < dstW; i++) {
311  int xx = (xDstInSrc - (filterSize - 2) * (1LL<<16)) / (1 << 17);
312  int j;
313  (*filterPos)[i] = xx;
314  for (j = 0; j < filterSize; j++) {
315  int64_t d = (FFABS(((int64_t)xx * (1 << 17)) - xDstInSrc)) << 13;
316  double floatd;
317  int64_t coeff;
318 
319  if (xInc > 1 << 16)
320  d = d * dstW / srcW;
321  floatd = d * (1.0 / (1 << 30));
322 
323  if (scaler == SWS_BICUBIC) {
324  int64_t B = (param[0] != SWS_PARAM_DEFAULT ? param[0] : 0) * (1 << 24);
325  int64_t C = (param[1] != SWS_PARAM_DEFAULT ? param[1] : 0.6) * (1 << 24);
326 
327  if (d >= 1LL << 31) {
328  coeff = 0.0;
329  } else {
330  int64_t dd = (d * d) >> 30;
331  int64_t ddd = (dd * d) >> 30;
332 
333  if (d < 1LL << 30)
334  coeff = (12 * (1 << 24) - 9 * B - 6 * C) * ddd +
335  (-18 * (1 << 24) + 12 * B + 6 * C) * dd +
336  (6 * (1 << 24) - 2 * B) * (1 << 30);
337  else
338  coeff = (-B - 6 * C) * ddd +
339  (6 * B + 30 * C) * dd +
340  (-12 * B - 48 * C) * d +
341  (8 * B + 24 * C) * (1 << 30);
342  }
343  coeff /= (1LL<<54)/fone;
344  } else if (scaler == SWS_X) {
345  double A = param[0] != SWS_PARAM_DEFAULT ? param[0] : 1.0;
346  double c;
347 
348  if (floatd < 1.0)
349  c = cos(floatd * M_PI);
350  else
351  c = -1.0;
352  if (c < 0.0)
353  c = -pow(-c, A);
354  else
355  c = pow(c, A);
356  coeff = (c * 0.5 + 0.5) * fone;
357  } else if (scaler == SWS_AREA) {
358  int64_t d2 = d - (1 << 29);
359  if (d2 * xInc < -(1LL << (29 + 16)))
360  coeff = 1.0 * (1LL << (30 + 16));
361  else if (d2 * xInc < (1LL << (29 + 16)))
362  coeff = -d2 * xInc + (1LL << (29 + 16));
363  else
364  coeff = 0.0;
365  coeff *= fone >> (30 + 16);
366  } else if (scaler == SWS_GAUSS) {
367  double p = param[0] != SWS_PARAM_DEFAULT ? param[0] : 3.0;
368  coeff = exp2(-p * floatd * floatd) * fone;
369  } else if (scaler == SWS_SINC) {
370  coeff = (d ? sin(floatd * M_PI) / (floatd * M_PI) : 1.0) * fone;
371  } else if (scaler == SWS_LANCZOS) {
372  double p = param[0] != SWS_PARAM_DEFAULT ? param[0] : 3.0;
373  coeff = (d ? sin(floatd * M_PI) * sin(floatd * M_PI / p) /
374  (floatd * floatd * M_PI * M_PI / p) : 1.0) * fone;
375  if (floatd > p)
376  coeff = 0;
377  } else if (scaler == SWS_BILINEAR) {
378  coeff = (1 << 30) - d;
379  if (coeff < 0)
380  coeff = 0;
381  coeff *= fone >> 30;
382  } else if (scaler == SWS_SPLINE) {
383  double p = -2.196152422706632;
384  coeff = getSplineCoeff(1.0, 0.0, p, -p - 1.0, floatd) * fone;
385  } else {
386  av_assert0(0);
387  }
388 
389  filter[i * filterSize + j] = coeff;
390  xx++;
391  }
392  xDstInSrc += 2LL * xInc;
393  }
394  }
395 
396  /* apply src & dst Filter to filter -> filter2
397  * av_free(filter);
398  */
399  av_assert0(filterSize > 0);
400  filter2Size = filterSize;
401  if (srcFilter)
402  filter2Size += srcFilter->length - 1;
403  if (dstFilter)
404  filter2Size += dstFilter->length - 1;
405  av_assert0(filter2Size > 0);
406  filter2 = av_calloc(dstW, filter2Size * sizeof(*filter2));
407  if (!filter2)
408  goto nomem;
409  for (i = 0; i < dstW; i++) {
410  int j, k;
411 
412  if (srcFilter) {
413  for (k = 0; k < srcFilter->length; k++) {
414  for (j = 0; j < filterSize; j++)
415  filter2[i * filter2Size + k + j] +=
416  srcFilter->coeff[k] * filter[i * filterSize + j];
417  }
418  } else {
419  for (j = 0; j < filterSize; j++)
420  filter2[i * filter2Size + j] = filter[i * filterSize + j];
421  }
422  // FIXME dstFilter
423 
424  (*filterPos)[i] += (filterSize - 1) / 2 - (filter2Size - 1) / 2;
425  }
426  av_freep(&filter);
427 
428  /* try to reduce the filter-size (step1 find size and shift left) */
429  // Assume it is near normalized (*0.5 or *2.0 is OK but * 0.001 is not).
430  minFilterSize = 0;
431  for (i = dstW - 1; i >= 0; i--) {
432  int min = filter2Size;
433  int j;
434  int64_t cutOff = 0.0;
435 
436  /* get rid of near zero elements on the left by shifting left */
437  for (j = 0; j < filter2Size; j++) {
438  int k;
439  cutOff += FFABS(filter2[i * filter2Size]);
440 
441  if (cutOff > SWS_MAX_REDUCE_CUTOFF * fone)
442  break;
443 
444  /* preserve monotonicity because the core can't handle the
445  * filter otherwise */
446  if (i < dstW - 1 && (*filterPos)[i] >= (*filterPos)[i + 1])
447  break;
448 
449  // move filter coefficients left
450  for (k = 1; k < filter2Size; k++)
451  filter2[i * filter2Size + k - 1] = filter2[i * filter2Size + k];
452  filter2[i * filter2Size + k - 1] = 0;
453  (*filterPos)[i]++;
454  }
455 
456  cutOff = 0;
457  /* count near zeros on the right */
458  for (j = filter2Size - 1; j > 0; j--) {
459  cutOff += FFABS(filter2[i * filter2Size + j]);
460 
461  if (cutOff > SWS_MAX_REDUCE_CUTOFF * fone)
462  break;
463  min--;
464  }
465 
466  if (min > minFilterSize)
467  minFilterSize = min;
468  }
469 
470  if (PPC_ALTIVEC(cpu_flags)) {
471  // we can handle the special case 4, so we don't want to go the full 8
472  if (minFilterSize < 5)
473  filterAlign = 4;
474 
475  /* We really don't want to waste our time doing useless computation, so
476  * fall back on the scalar C code for very small filters.
477  * Vectorizing is worth it only if you have a decent-sized vector. */
478  if (minFilterSize < 3)
479  filterAlign = 1;
480  }
481 
482  if (HAVE_MMX && cpu_flags & AV_CPU_FLAG_MMX || have_neon(cpu_flags)) {
483  // special case for unscaled vertical filtering
484  if (minFilterSize == 1 && filterAlign == 2)
485  filterAlign = 1;
486  }
487 
489  int reNum = minFilterSize & (0x07);
490 
491  if (minFilterSize < 5)
492  filterAlign = 4;
493  if (reNum < 3)
494  filterAlign = 1;
495  }
496 
497  av_assert0(minFilterSize > 0);
498  filterSize = (minFilterSize + (filterAlign - 1)) & (~(filterAlign - 1));
499  av_assert0(filterSize > 0);
500  filter = av_malloc_array(dstW, filterSize * sizeof(*filter));
501  if (!filter)
502  goto nomem;
503  if (filterSize >= MAX_FILTER_SIZE * 16 /
504  ((flags & SWS_ACCURATE_RND) ? APCK_SIZE : 16)) {
506  goto fail;
507  }
508  *outFilterSize = filterSize;
509 
510  if (flags & SWS_PRINT_INFO)
512  "SwScaler: reducing / aligning filtersize %d -> %d\n",
513  filter2Size, filterSize);
514  /* try to reduce the filter-size (step2 reduce it) */
515  for (i = 0; i < dstW; i++) {
516  int j;
517 
518  for (j = 0; j < filterSize; j++) {
519  if (j >= filter2Size)
520  filter[i * filterSize + j] = 0;
521  else
522  filter[i * filterSize + j] = filter2[i * filter2Size + j];
523  if ((flags & SWS_BITEXACT) && j >= minFilterSize)
524  filter[i * filterSize + j] = 0;
525  }
526  }
527 
528  // FIXME try to align filterPos if possible
529 
530  // fix borders
531  for (i = 0; i < dstW; i++) {
532  int j;
533  if ((*filterPos)[i] < 0) {
534  // move filter coefficients left to compensate for filterPos
535  for (j = 1; j < filterSize; j++) {
536  int left = FFMAX(j + (*filterPos)[i], 0);
537  filter[i * filterSize + left] += filter[i * filterSize + j];
538  filter[i * filterSize + j] = 0;
539  }
540  (*filterPos)[i]= 0;
541  }
542 
543  if ((*filterPos)[i] + filterSize > srcW) {
544  int shift = (*filterPos)[i] + FFMIN(filterSize - srcW, 0);
545  int64_t acc = 0;
546 
547  for (j = filterSize - 1; j >= 0; j--) {
548  if ((*filterPos)[i] + j >= srcW) {
549  acc += filter[i * filterSize + j];
550  filter[i * filterSize + j] = 0;
551  }
552  }
553  for (j = filterSize - 1; j >= 0; j--) {
554  if (j < shift) {
555  filter[i * filterSize + j] = 0;
556  } else {
557  filter[i * filterSize + j] = filter[i * filterSize + j - shift];
558  }
559  }
560 
561  (*filterPos)[i]-= shift;
562  filter[i * filterSize + srcW - 1 - (*filterPos)[i]] += acc;
563  }
564  av_assert0((*filterPos)[i] >= 0);
565  av_assert0((*filterPos)[i] < srcW);
566  if ((*filterPos)[i] + filterSize > srcW) {
567  for (j = 0; j < filterSize; j++) {
568  av_assert0((*filterPos)[i] + j < srcW || !filter[i * filterSize + j]);
569  }
570  }
571  }
572 
573  // Note the +1 is for the MMX scaler which reads over the end
574  /* align at 16 for AltiVec (needed by hScale_altivec_real) */
575  *outFilter = av_calloc(dstW + 3, *outFilterSize * sizeof(**outFilter));
576  if (!*outFilter)
577  goto nomem;
578 
579  /* normalize & store in outFilter */
580  for (i = 0; i < dstW; i++) {
581  int j;
582  int64_t error = 0;
583  int64_t sum = 0;
584 
585  for (j = 0; j < filterSize; j++) {
586  sum += filter[i * filterSize + j];
587  }
588  sum = (sum + one / 2) / one;
589  if (!sum) {
590  av_log(NULL, AV_LOG_WARNING, "SwScaler: zero vector in scaling\n");
591  sum = 1;
592  }
593  for (j = 0; j < *outFilterSize; j++) {
594  int64_t v = filter[i * filterSize + j] + error;
595  int intV = ROUNDED_DIV(v, sum);
596  (*outFilter)[i * (*outFilterSize) + j] = intV;
597  error = v - intV * sum;
598  }
599  }
600 
601  (*filterPos)[dstW + 0] =
602  (*filterPos)[dstW + 1] =
603  (*filterPos)[dstW + 2] = (*filterPos)[dstW - 1]; /* the MMX/SSE scaler will
604  * read over the end */
605  for (i = 0; i < *outFilterSize; i++) {
606  int k = (dstW - 1) * (*outFilterSize) + i;
607  (*outFilter)[k + 1 * (*outFilterSize)] =
608  (*outFilter)[k + 2 * (*outFilterSize)] =
609  (*outFilter)[k + 3 * (*outFilterSize)] = (*outFilter)[k];
610  }
611 
612  ret = 0;
613  goto done;
614 nomem:
615  ret = AVERROR(ENOMEM);
616 fail:
617  if(ret < 0)
618  av_log(NULL, ret == RETCODE_USE_CASCADE ? AV_LOG_DEBUG : AV_LOG_ERROR, "sws: initFilter failed\n");
619 done:
620  av_free(filter);
621  av_free(filter2);
622  return ret;
623 }
624 
625 static void fill_rgb2yuv_table(SwsInternal *c, const int table[4], int dstRange)
626 {
627  int64_t W, V, Z, Cy, Cu, Cv;
628  int64_t vr = table[0];
629  int64_t ub = table[1];
630  int64_t ug = -table[2];
631  int64_t vg = -table[3];
632  int64_t ONE = 65536;
633  int64_t cy = ONE;
634  uint8_t *p = (uint8_t*)c->input_rgb2yuv_table;
635  int i;
636  static const int8_t map[] = {
637  BY_IDX, GY_IDX, -1 , BY_IDX, BY_IDX, GY_IDX, -1 , BY_IDX,
638  RY_IDX, -1 , GY_IDX, RY_IDX, RY_IDX, -1 , GY_IDX, RY_IDX,
639  RY_IDX, GY_IDX, -1 , RY_IDX, RY_IDX, GY_IDX, -1 , RY_IDX,
640  BY_IDX, -1 , GY_IDX, BY_IDX, BY_IDX, -1 , GY_IDX, BY_IDX,
641  BU_IDX, GU_IDX, -1 , BU_IDX, BU_IDX, GU_IDX, -1 , BU_IDX,
642  RU_IDX, -1 , GU_IDX, RU_IDX, RU_IDX, -1 , GU_IDX, RU_IDX,
643  RU_IDX, GU_IDX, -1 , RU_IDX, RU_IDX, GU_IDX, -1 , RU_IDX,
644  BU_IDX, -1 , GU_IDX, BU_IDX, BU_IDX, -1 , GU_IDX, BU_IDX,
645  BV_IDX, GV_IDX, -1 , BV_IDX, BV_IDX, GV_IDX, -1 , BV_IDX,
646  RV_IDX, -1 , GV_IDX, RV_IDX, RV_IDX, -1 , GV_IDX, RV_IDX,
647  RV_IDX, GV_IDX, -1 , RV_IDX, RV_IDX, GV_IDX, -1 , RV_IDX,
648  BV_IDX, -1 , GV_IDX, BV_IDX, BV_IDX, -1 , GV_IDX, BV_IDX,
651  GY_IDX, -1 , GY_IDX, -1 , GY_IDX, -1 , GY_IDX, -1 ,
652  -1 , GY_IDX, -1 , GY_IDX, -1 , GY_IDX, -1 , GY_IDX,
655  GU_IDX, -1 , GU_IDX, -1 , GU_IDX, -1 , GU_IDX, -1 ,
656  -1 , GU_IDX, -1 , GU_IDX, -1 , GU_IDX, -1 , GU_IDX,
659  GV_IDX, -1 , GV_IDX, -1 , GV_IDX, -1 , GV_IDX, -1 ,
660  -1 , GV_IDX, -1 , GV_IDX, -1 , GV_IDX, -1 , GV_IDX, //23
661  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //24
662  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //25
663  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //26
664  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //27
665  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //28
666  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //29
667  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //30
668  -1 , -1 , -1 , -1 , -1 , -1 , -1 , -1 , //31
669  BY_IDX, GY_IDX, RY_IDX, -1 , -1 , -1 , -1 , -1 , //32
670  BU_IDX, GU_IDX, RU_IDX, -1 , -1 , -1 , -1 , -1 , //33
671  BV_IDX, GV_IDX, RV_IDX, -1 , -1 , -1 , -1 , -1 , //34
672  };
673 
674  dstRange = 0; //FIXME range = 1 is handled elsewhere
675 
676  if (!dstRange) {
677  cy = cy * 255 / 219;
678  } else {
679  vr = vr * 224 / 255;
680  ub = ub * 224 / 255;
681  ug = ug * 224 / 255;
682  vg = vg * 224 / 255;
683  }
684  W = ROUNDED_DIV(ONE*ONE*ug, ub);
685  V = ROUNDED_DIV(ONE*ONE*vg, vr);
686  Z = ONE*ONE-W-V;
687 
688  Cy = ROUNDED_DIV(cy*Z, ONE);
689  Cu = ROUNDED_DIV(ub*Z, ONE);
690  Cv = ROUNDED_DIV(vr*Z, ONE);
691 
692  c->input_rgb2yuv_table[RY_IDX] = -ROUNDED_DIV((1 << RGB2YUV_SHIFT)*V , Cy);
693  c->input_rgb2yuv_table[GY_IDX] = ROUNDED_DIV((1 << RGB2YUV_SHIFT)*ONE*ONE , Cy);
694  c->input_rgb2yuv_table[BY_IDX] = -ROUNDED_DIV((1 << RGB2YUV_SHIFT)*W , Cy);
695 
696  c->input_rgb2yuv_table[RU_IDX] = ROUNDED_DIV((1 << RGB2YUV_SHIFT)*V , Cu);
697  c->input_rgb2yuv_table[GU_IDX] = -ROUNDED_DIV((1 << RGB2YUV_SHIFT)*ONE*ONE , Cu);
698  c->input_rgb2yuv_table[BU_IDX] = ROUNDED_DIV((1 << RGB2YUV_SHIFT)*(Z+W) , Cu);
699 
700  c->input_rgb2yuv_table[RV_IDX] = ROUNDED_DIV((1 << RGB2YUV_SHIFT)*(V+Z) , Cv);
701  c->input_rgb2yuv_table[GV_IDX] = -ROUNDED_DIV((1 << RGB2YUV_SHIFT)*ONE*ONE , Cv);
702  c->input_rgb2yuv_table[BV_IDX] = ROUNDED_DIV((1 << RGB2YUV_SHIFT)*W , Cv);
703 
704  if(/*!dstRange && */!memcmp(table, ff_yuv2rgb_coeffs[SWS_CS_DEFAULT], sizeof(ff_yuv2rgb_coeffs[SWS_CS_DEFAULT]))) {
705  c->input_rgb2yuv_table[BY_IDX] = ((int)(0.114 * 219 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
706  c->input_rgb2yuv_table[BV_IDX] = (-(int)(0.081 * 224 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
707  c->input_rgb2yuv_table[BU_IDX] = ((int)(0.500 * 224 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
708  c->input_rgb2yuv_table[GY_IDX] = ((int)(0.587 * 219 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
709  c->input_rgb2yuv_table[GV_IDX] = (-(int)(0.419 * 224 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
710  c->input_rgb2yuv_table[GU_IDX] = (-(int)(0.331 * 224 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
711  c->input_rgb2yuv_table[RY_IDX] = ((int)(0.299 * 219 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
712  c->input_rgb2yuv_table[RV_IDX] = ((int)(0.500 * 224 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
713  c->input_rgb2yuv_table[RU_IDX] = (-(int)(0.169 * 224 / 255 * (1 << RGB2YUV_SHIFT) + 0.5));
714  }
715  for(i=0; i<FF_ARRAY_ELEMS(map); i++)
716  AV_WL16(p + 16*4 + 2*i, map[i] >= 0 ? c->input_rgb2yuv_table[map[i]] : 0);
717 }
718 
719 #if CONFIG_SMALL
720 static void init_xyz_tables(uint16_t xyzgamma_tab[4096], uint16_t xyzgammainv_tab[65536],
721  uint16_t rgbgamma_tab[65536], uint16_t rgbgammainv_tab[4096])
722 #else
723 static uint16_t xyzgamma_tab[4096], rgbgammainv_tab[4096];
724 static uint16_t rgbgamma_tab[65536], xyzgammainv_tab[65536];
725 static av_cold void init_xyz_tables(void)
726 #endif
727 {
728  double xyzgamma = XYZ_GAMMA;
729  double rgbgamma = 1.0 / RGB_GAMMA;
730  double xyzgammainv = 1.0 / XYZ_GAMMA;
731  double rgbgammainv = RGB_GAMMA;
732 
733  /* set input gamma vectors */
734  for (int i = 0; i < 4096; i++) {
735  xyzgamma_tab[i] = lrint(pow(i / 4095.0, xyzgamma) * 65535.0);
736  rgbgammainv_tab[i] = lrint(pow(i / 4095.0, rgbgammainv) * 65535.0);
737  }
738 
739  /* set output gamma vectors */
740  for (int i = 0; i < 65536; i++) {
741  rgbgamma_tab[i] = lrint(pow(i / 65535.0, rgbgamma) * 4095.0);
742  xyzgammainv_tab[i] = lrint(pow(i / 65535.0, xyzgammainv) * 4095.0);
743  }
744 }
745 
747 {
748  static const int16_t xyz2rgb_matrix[3][3] = {
749  {13270, -6295, -2041},
750  {-3969, 7682, 170},
751  { 228, -835, 4329} };
752  static const int16_t rgb2xyz_matrix[3][3] = {
753  {1689, 1464, 739},
754  { 871, 2929, 296},
755  { 79, 488, 3891} };
756 
757  if (c->xyz2rgb.gamma.in)
758  return 0;
759 
760  memcpy(c->xyz2rgb.mat, xyz2rgb_matrix, sizeof(c->xyz2rgb.mat));
761  memcpy(c->rgb2xyz.mat, rgb2xyz_matrix, sizeof(c->rgb2xyz.mat));
762 
763 #if CONFIG_SMALL
764  c->xyz2rgb.gamma.in = av_malloc(sizeof(uint16_t) * 2 * (4096 + 65536));
765  if (!c->xyz2rgb.gamma.in)
766  return AVERROR(ENOMEM);
767  c->rgb2xyz.gamma.in = c->xyz2rgb.gamma.in + 4096;
768  c->xyz2rgb.gamma.out = c->rgb2xyz.gamma.in + 4096;
769  c->rgb2xyz.gamma.out = c->xyz2rgb.gamma.out + 65536;
770  init_xyz_tables(c->xyz2rgb.gamma.in, c->rgb2xyz.gamma.out,
771  c->xyz2rgb.gamma.out, c->rgb2xyz.gamma.in);
772 #else
773  c->xyz2rgb.gamma.in = xyzgamma_tab;
774  c->xyz2rgb.gamma.out = rgbgamma_tab;
775  c->rgb2xyz.gamma.in = rgbgammainv_tab;
776  c->rgb2xyz.gamma.out = xyzgammainv_tab;
777 
778  static AVOnce xyz_init_static_once = AV_ONCE_INIT;
779  ff_thread_once(&xyz_init_static_once, init_xyz_tables);
780 #endif
781  return 0;
782 }
783 
784 static int handle_jpeg(/* enum AVPixelFormat */ int *format)
785 {
786  switch (*format) {
787  case AV_PIX_FMT_YUVJ420P:
789  return 1;
790  case AV_PIX_FMT_YUVJ411P:
792  return 1;
793  case AV_PIX_FMT_YUVJ422P:
795  return 1;
796  case AV_PIX_FMT_YUVJ444P:
798  return 1;
799  case AV_PIX_FMT_YUVJ440P:
801  return 1;
802  case AV_PIX_FMT_GRAY8:
803  case AV_PIX_FMT_YA8:
804  case AV_PIX_FMT_GRAY9LE:
805  case AV_PIX_FMT_GRAY9BE:
806  case AV_PIX_FMT_GRAY10LE:
807  case AV_PIX_FMT_GRAY10BE:
808  case AV_PIX_FMT_GRAY12LE:
809  case AV_PIX_FMT_GRAY12BE:
810  case AV_PIX_FMT_GRAY14LE:
811  case AV_PIX_FMT_GRAY14BE:
812  case AV_PIX_FMT_GRAY16LE:
813  case AV_PIX_FMT_GRAY16BE:
814  case AV_PIX_FMT_YA16BE:
815  case AV_PIX_FMT_YA16LE:
816  return 1;
817  default:
818  return 0;
819  }
820 }
821 
822 static int handle_0alpha(/* enum AVPixelFormat */ int *format)
823 {
824  switch (*format) {
825  case AV_PIX_FMT_0BGR : *format = AV_PIX_FMT_ABGR ; return 1;
826  case AV_PIX_FMT_BGR0 : *format = AV_PIX_FMT_BGRA ; return 4;
827  case AV_PIX_FMT_0RGB : *format = AV_PIX_FMT_ARGB ; return 1;
828  case AV_PIX_FMT_RGB0 : *format = AV_PIX_FMT_RGBA ; return 4;
829  default: return 0;
830  }
831 }
832 
833 static int handle_xyz(/* enum AVPixelFormat */ int *format)
834 {
835  switch (*format) {
836  case AV_PIX_FMT_XYZ12BE : *format = AV_PIX_FMT_RGB48BE; return 1;
837  case AV_PIX_FMT_XYZ12LE : *format = AV_PIX_FMT_RGB48LE; return 1;
838  default: return 0;
839  }
840 }
841 
842 static int handle_formats(SwsContext *sws)
843 {
844  SwsInternal *c = sws_internal(sws);
845  c->src0Alpha |= handle_0alpha(&sws->src_format);
846  c->dst0Alpha |= handle_0alpha(&sws->dst_format);
847  c->srcXYZ |= handle_xyz(&sws->src_format);
848  c->dstXYZ |= handle_xyz(&sws->dst_format);
849  if (c->srcXYZ || c->dstXYZ)
850  return ff_sws_fill_xyztables(c);
851  else
852  return 0;
853 }
854 
856 {
857  return !isYUV(format) && !isGray(format);
858 }
859 
860 int sws_setColorspaceDetails(SwsContext *sws, const int inv_table[4],
861  int srcRange, const int table[4], int dstRange,
862  int brightness, int contrast, int saturation)
863 {
864  SwsInternal *c = sws_internal(sws);
865  const AVPixFmtDescriptor *desc_dst;
866  const AVPixFmtDescriptor *desc_src;
867  int ret, need_reinit = 0;
868 
869  if (c->nb_slice_ctx) {
870  int parent_ret = 0;
871  for (int i = 0; i < c->nb_slice_ctx; i++) {
872  int ret = sws_setColorspaceDetails(c->slice_ctx[i], inv_table,
873  srcRange, table, dstRange,
874  brightness, contrast, saturation);
875  if (ret < 0)
876  parent_ret = ret;
877  }
878 
879  return parent_ret;
880  }
881 
882  ret = handle_formats(sws);
883  if (ret < 0)
884  return ret;
885  desc_dst = av_pix_fmt_desc_get(sws->dst_format);
886  desc_src = av_pix_fmt_desc_get(sws->src_format);
887 
889  dstRange = 0;
891  srcRange = 0;
892 
893  if (sws->src_range != srcRange ||
894  sws->dst_range != dstRange ||
895  c->brightness != brightness ||
896  c->contrast != contrast ||
897  c->saturation != saturation ||
898  memcmp(c->srcColorspaceTable, inv_table, sizeof(int) * 4) ||
899  memcmp(c->dstColorspaceTable, table, sizeof(int) * 4)
900  )
901  need_reinit = 1;
902 
903  memmove(c->srcColorspaceTable, inv_table, sizeof(int) * 4);
904  memmove(c->dstColorspaceTable, table, sizeof(int) * 4);
905 
906 
907 
908  c->brightness = brightness;
909  c->contrast = contrast;
910  c->saturation = saturation;
911  sws->src_range = srcRange;
912  sws->dst_range = dstRange;
913 
914  if (need_reinit)
916 
917  c->dstFormatBpp = av_get_bits_per_pixel(desc_dst);
918  c->srcFormatBpp = av_get_bits_per_pixel(desc_src);
919 
920  if (c->cascaded_context[c->cascaded_mainindex])
921  return sws_setColorspaceDetails(c->cascaded_context[c->cascaded_mainindex],inv_table, srcRange,table, dstRange, brightness, contrast, saturation);
922 
923  if (!need_reinit)
924  return 0;
925 
926  if ((isYUV(sws->dst_format) || isGray(sws->dst_format)) && (isYUV(sws->src_format) || isGray(sws->src_format))) {
927  if (!c->cascaded_context[0] &&
928  memcmp(c->dstColorspaceTable, c->srcColorspaceTable, sizeof(int) * 4) &&
929  sws->src_w && sws->src_h && sws->dst_w && sws->dst_h) {
930  enum AVPixelFormat tmp_format;
931  int tmp_width, tmp_height;
932  int srcW = sws->src_w;
933  int srcH = sws->src_h;
934  int dstW = sws->dst_w;
935  int dstH = sws->dst_h;
936  int ret;
937  av_log(c, AV_LOG_VERBOSE, "YUV color matrix differs for YUV->YUV, using intermediate RGB to convert\n");
938 
939  if (isNBPS(sws->dst_format) || is16BPS(sws->dst_format)) {
940  if (isALPHA(sws->src_format) && isALPHA(sws->dst_format)) {
941  tmp_format = AV_PIX_FMT_BGRA64;
942  } else {
943  tmp_format = AV_PIX_FMT_BGR48;
944  }
945  } else {
946  if (isALPHA(sws->src_format) && isALPHA(sws->dst_format)) {
947  tmp_format = AV_PIX_FMT_BGRA;
948  } else {
949  tmp_format = AV_PIX_FMT_BGR24;
950  }
951  }
952 
953  if (srcW*srcH > dstW*dstH) {
954  tmp_width = dstW;
955  tmp_height = dstH;
956  } else {
957  tmp_width = srcW;
958  tmp_height = srcH;
959  }
960 
961  ret = av_image_alloc(c->cascaded_tmp[0], c->cascaded_tmpStride[0],
962  tmp_width, tmp_height, tmp_format, 64);
963  if (ret < 0)
964  return ret;
965 
966  c->cascaded_context[0] = alloc_set_opts(srcW, srcH, sws->src_format,
967  tmp_width, tmp_height, tmp_format,
968  sws->flags, sws->scaler_params);
969  if (!c->cascaded_context[0])
970  return -1;
971 
972  c->cascaded_context[0]->alpha_blend = sws->alpha_blend;
973  ret = sws_init_context(c->cascaded_context[0], NULL , NULL);
974  if (ret < 0)
975  return ret;
976  //we set both src and dst depending on that the RGB side will be ignored
977  sws_setColorspaceDetails(c->cascaded_context[0], inv_table,
978  srcRange, table, dstRange,
979  brightness, contrast, saturation);
980 
981  c->cascaded_context[1] = alloc_set_opts(tmp_width, tmp_height, tmp_format,
982  dstW, dstH, sws->dst_format,
983  sws->flags, sws->scaler_params);
984  if (!c->cascaded_context[1])
985  return -1;
986  c->cascaded_context[1]->src_range = srcRange;
987  c->cascaded_context[1]->dst_range = dstRange;
988  ret = sws_init_context(c->cascaded_context[1], NULL , NULL);
989  if (ret < 0)
990  return ret;
991  sws_setColorspaceDetails(c->cascaded_context[1], inv_table,
992  srcRange, table, dstRange,
993  0, 1 << 16, 1 << 16);
994  return 0;
995  }
996  //We do not support this combination currently, we need to cascade more contexts to compensate
997  if (c->cascaded_context[0] && memcmp(c->dstColorspaceTable, c->srcColorspaceTable, sizeof(int) * 4))
998  return -1; //AVERROR_PATCHWELCOME;
999  return 0;
1000  }
1001 
1002  if (!isYUV(sws->dst_format) && !isGray(sws->dst_format)) {
1003  ff_yuv2rgb_c_init_tables(c, inv_table, srcRange, brightness,
1004  contrast, saturation);
1005  // FIXME factorize
1006 
1007 #if ARCH_PPC
1008  ff_yuv2rgb_init_tables_ppc(c, inv_table, brightness,
1009  contrast, saturation);
1010 #endif
1011  }
1012 
1013  fill_rgb2yuv_table(c, table, dstRange);
1014 
1015  return 0;
1016 }
1017 
1018 int sws_getColorspaceDetails(SwsContext *sws, int **inv_table,
1019  int *srcRange, int **table, int *dstRange,
1020  int *brightness, int *contrast, int *saturation)
1021 {
1022  SwsInternal *c = sws_internal(sws);
1023  if (!c)
1024  return -1;
1025 
1026  if (c->nb_slice_ctx) {
1027  return sws_getColorspaceDetails(c->slice_ctx[0], inv_table, srcRange,
1028  table, dstRange, brightness, contrast,
1029  saturation);
1030  }
1031 
1032  *inv_table = c->srcColorspaceTable;
1033  *table = c->dstColorspaceTable;
1034  *srcRange = range_override_needed(sws->src_format) ? 1 : sws->src_range;
1035  *dstRange = range_override_needed(sws->dst_format) ? 1 : sws->dst_range;
1036  *brightness = c->brightness;
1037  *contrast = c->contrast;
1038  *saturation = c->saturation;
1039 
1040  return 0;
1041 }
1042 
1044 {
1046  if (!c)
1047  return NULL;
1048 
1049  c->opts.av_class = &ff_sws_context_class;
1051  atomic_init(&c->stride_unaligned_warned, 0);
1052  atomic_init(&c->data_unaligned_warned, 0);
1053 
1054  return &c->opts;
1055 }
1056 
1057 static uint16_t * alloc_gamma_tbl(double e)
1058 {
1059  int i = 0;
1060  uint16_t * tbl;
1061  tbl = (uint16_t*)av_malloc(sizeof(uint16_t) * 1 << 16);
1062  if (!tbl)
1063  return NULL;
1064 
1065  for (i = 0; i < 65536; ++i) {
1066  tbl[i] = pow(i / 65535.0, e) * 65535.0;
1067  }
1068  return tbl;
1069 }
1070 
1072 {
1073  switch(fmt) {
1074  case AV_PIX_FMT_ARGB: return AV_PIX_FMT_RGB24;
1075  case AV_PIX_FMT_RGBA: return AV_PIX_FMT_RGB24;
1076  case AV_PIX_FMT_ABGR: return AV_PIX_FMT_BGR24;
1077  case AV_PIX_FMT_BGRA: return AV_PIX_FMT_BGR24;
1078  case AV_PIX_FMT_YA8: return AV_PIX_FMT_GRAY8;
1079 
1083 
1084  case AV_PIX_FMT_GBRAP: return AV_PIX_FMT_GBRP;
1085 
1088 
1091 
1094 
1097 
1102 
1103  case AV_PIX_FMT_YA16BE: return AV_PIX_FMT_GRAY16;
1104  case AV_PIX_FMT_YA16LE: return AV_PIX_FMT_GRAY16;
1105 
1124 
1125 // case AV_PIX_FMT_AYUV64LE:
1126 // case AV_PIX_FMT_AYUV64BE:
1127 // case AV_PIX_FMT_PAL8:
1128  default: return AV_PIX_FMT_NONE;
1129  }
1130 }
1131 
1132 static int scaler_flag(SwsScaler scaler, int fallback)
1133 {
1134  switch (scaler) {
1135  case SWS_SCALE_BILINEAR: return SWS_BILINEAR; break;
1136  case SWS_SCALE_BICUBIC: return SWS_BICUBIC; break;
1137  case SWS_SCALE_POINT: return SWS_POINT; break;
1138  case SWS_SCALE_AREA: return SWS_AREA; break;
1139  case SWS_SCALE_GAUSSIAN: return SWS_GAUSS; break;
1140  case SWS_SCALE_SINC: return SWS_SINC; break;
1141  case SWS_SCALE_LANCZOS: return SWS_LANCZOS; break;
1142  case SWS_SCALE_SPLINE: return SWS_SPLINE; break;
1143  default:
1144  return fallback;
1145  }
1146 }
1147 
1149  SwsFilter *dstFilter)
1150 {
1151  int i;
1152  int usesVFilter, usesHFilter;
1153  int unscaled;
1154  SwsInternal *c = sws_internal(sws);
1155  SwsFilter dummyFilter = { NULL, NULL, NULL, NULL };
1156  int srcW = sws->src_w;
1157  int srcH = sws->src_h;
1158  int dstW = sws->dst_w;
1159  int dstH = sws->dst_h;
1160  int dst_stride = FFALIGN(dstW * sizeof(int16_t) + 66, 16);
1161  int flags, cpu_flags;
1162  enum AVPixelFormat srcFormat, dstFormat;
1163  const AVPixFmtDescriptor *desc_src;
1164  const AVPixFmtDescriptor *desc_dst;
1165  int ret = 0;
1166  enum AVPixelFormat tmpFmt;
1167  static const float float_mult = 1.0f / 255.0f;
1168 
1170  flags = sws->flags;
1171  emms_c();
1172 
1173  unscaled = (srcW == dstW && srcH == dstH);
1174 
1175  if (!c->contrast && !c->saturation && !c->dstFormatBpp)
1178  sws->dst_range, 0, 1 << 16, 1 << 16);
1179 
1180  ret = handle_formats(sws);
1181  if (ret < 0)
1182  return ret;
1183  srcFormat = sws->src_format;
1184  dstFormat = sws->dst_format;
1185  desc_src = av_pix_fmt_desc_get(srcFormat);
1186  desc_dst = av_pix_fmt_desc_get(dstFormat);
1187 
1188  // If the source has no alpha then disable alpha blendaway
1189  if (c->src0Alpha)
1191 
1192  if (!(unscaled && sws_isSupportedEndiannessConversion(srcFormat) &&
1193  av_pix_fmt_swap_endianness(srcFormat) == dstFormat)) {
1194  if (!sws_isSupportedInput(srcFormat)) {
1195  av_log(c, AV_LOG_ERROR, "%s is not supported as input pixel format\n",
1196  av_get_pix_fmt_name(srcFormat));
1197  return AVERROR(EINVAL);
1198  }
1199  if (!sws_isSupportedOutput(dstFormat)) {
1200  av_log(c, AV_LOG_ERROR, "%s is not supported as output pixel format\n",
1201  av_get_pix_fmt_name(dstFormat));
1202  return AVERROR(EINVAL);
1203  }
1204  }
1205  av_assert2(desc_src && desc_dst);
1206 
1207  i = flags & (SWS_POINT |
1208  SWS_AREA |
1209  SWS_BILINEAR |
1211  SWS_BICUBIC |
1212  SWS_X |
1213  SWS_GAUSS |
1214  SWS_LANCZOS |
1215  SWS_SINC |
1216  SWS_SPLINE |
1217  SWS_BICUBLIN);
1218 
1219  /* provide a default scaler if not set by caller */
1220  if (!i) {
1221  if (dstW < srcW && dstH < srcH)
1222  i = SWS_BICUBIC;
1223  else if (dstW > srcW && dstH > srcH)
1224  i = SWS_BICUBIC;
1225  else
1226  i = SWS_BICUBIC;
1227  flags |= i;
1228  sws->flags = flags;
1229  } else if (i & (i - 1)) {
1231  "Exactly one scaler algorithm must be chosen, got %X\n", i);
1232  return AVERROR(EINVAL);
1233  }
1234 
1235  if (i == SWS_FAST_BILINEAR) {
1236  if (srcW < 8 || dstW <= 8) {
1237  i = SWS_BILINEAR;
1238  flags ^= SWS_FAST_BILINEAR | i;
1239  sws->flags = flags;
1240  }
1241  }
1242 
1243  SwsScaler scaler_sub = sws->scaler_sub ? sws->scaler_sub : sws->scaler;
1244  int lum_scaler = scaler_flag(sws->scaler, i == SWS_BICUBLIN ? SWS_BICUBIC : i);
1245  int chr_scaler = scaler_flag(scaler_sub, i == SWS_BICUBLIN ? SWS_BILINEAR : i);
1246 
1247  /* sanity check */
1248  if (srcW < 1 || srcH < 1 || dstW < 1 || dstH < 1) {
1249  /* FIXME check if these are enough and try to lower them after
1250  * fixing the relevant parts of the code */
1251  av_log(c, AV_LOG_ERROR, "%dx%d -> %dx%d is invalid scaling dimension\n",
1252  srcW, srcH, dstW, dstH);
1253  return AVERROR(EINVAL);
1254  }
1255 
1256  if (!dstFilter)
1257  dstFilter = &dummyFilter;
1258  if (!srcFilter)
1259  srcFilter = &dummyFilter;
1260 
1261  int64_t lumXInc = (((int64_t)srcW << 16) + (dstW >> 1)) / dstW;
1262  int64_t lumYInc = (((int64_t)srcH << 16) + (dstH >> 1)) / dstH;
1263  c->dstFormatBpp = av_get_bits_per_pixel(desc_dst);
1264  c->srcFormatBpp = av_get_bits_per_pixel(desc_src);
1265  c->vRounder = 4 * 0x0001000100010001ULL;
1266 
1267  usesVFilter = (srcFilter->lumV && srcFilter->lumV->length > 1) ||
1268  (srcFilter->chrV && srcFilter->chrV->length > 1) ||
1269  (dstFilter->lumV && dstFilter->lumV->length > 1) ||
1270  (dstFilter->chrV && dstFilter->chrV->length > 1);
1271  usesHFilter = (srcFilter->lumH && srcFilter->lumH->length > 1) ||
1272  (srcFilter->chrH && srcFilter->chrH->length > 1) ||
1273  (dstFilter->lumH && dstFilter->lumH->length > 1) ||
1274  (dstFilter->chrH && dstFilter->chrH->length > 1);
1275 
1276  av_pix_fmt_get_chroma_sub_sample(srcFormat, &c->chrSrcHSubSample, &c->chrSrcVSubSample);
1277  av_pix_fmt_get_chroma_sub_sample(dstFormat, &c->chrDstHSubSample, &c->chrDstVSubSample);
1278 
1279  c->dst_slice_align = 1 << c->chrDstVSubSample;
1280 
1281  if (isAnyRGB(dstFormat) && !(flags&SWS_FULL_CHR_H_INT)) {
1282  if (dstW&1) {
1283  av_log(c, AV_LOG_DEBUG, "Forcing full internal H chroma due to odd output size\n");
1285  sws->flags = flags;
1286  }
1287 
1288  if ( c->chrSrcHSubSample == 0
1289  && c->chrSrcVSubSample == 0
1290  && sws->dither != SWS_DITHER_BAYER //SWS_FULL_CHR_H_INT is currently not supported with SWS_DITHER_BAYER
1291  && !(sws->flags & SWS_FAST_BILINEAR)
1292  ) {
1293  av_log(c, AV_LOG_DEBUG, "Forcing full internal H chroma due to input having non subsampled chroma\n");
1295  sws->flags = flags;
1296  }
1297  }
1298 
1299  if (sws->dither == SWS_DITHER_AUTO) {
1300  if (flags & SWS_ERROR_DIFFUSION)
1301  sws->dither = SWS_DITHER_ED;
1302  }
1303 
1304  if(dstFormat == AV_PIX_FMT_BGR4_BYTE ||
1305  dstFormat == AV_PIX_FMT_RGB4_BYTE ||
1306  dstFormat == AV_PIX_FMT_BGR8 ||
1307  dstFormat == AV_PIX_FMT_RGB8) {
1308  if (sws->dither == SWS_DITHER_AUTO)
1310  if (!(flags & SWS_FULL_CHR_H_INT)) {
1311  if (sws->dither == SWS_DITHER_ED || sws->dither == SWS_DITHER_A_DITHER || sws->dither == SWS_DITHER_X_DITHER || sws->dither == SWS_DITHER_NONE) {
1313  "Desired dithering only supported in full chroma interpolation for destination format '%s'\n",
1314  av_get_pix_fmt_name(dstFormat));
1316  sws->flags = flags;
1317  }
1318  }
1319  if (flags & SWS_FULL_CHR_H_INT) {
1320  if (sws->dither == SWS_DITHER_BAYER) {
1322  "Ordered dither is not supported in full chroma interpolation for destination format '%s'\n",
1323  av_get_pix_fmt_name(dstFormat));
1324  sws->dither = SWS_DITHER_ED;
1325  }
1326  }
1327  }
1328  if (isPlanarRGB(dstFormat)) {
1329  if (!(flags & SWS_FULL_CHR_H_INT)) {
1331  "%s output is not supported with half chroma resolution, switching to full\n",
1332  av_get_pix_fmt_name(dstFormat));
1334  sws->flags = flags;
1335  }
1336  }
1337 
1338  /* reuse chroma for 2 pixels RGB/BGR unless user wants full
1339  * chroma interpolation */
1340  if (flags & SWS_FULL_CHR_H_INT &&
1341  isAnyRGB(dstFormat) &&
1342  !isPlanarRGB(dstFormat) &&
1343  dstFormat != AV_PIX_FMT_RGBA64LE &&
1344  dstFormat != AV_PIX_FMT_RGBA64BE &&
1345  dstFormat != AV_PIX_FMT_BGRA64LE &&
1346  dstFormat != AV_PIX_FMT_BGRA64BE &&
1347  dstFormat != AV_PIX_FMT_RGB48LE &&
1348  dstFormat != AV_PIX_FMT_RGB48BE &&
1349  dstFormat != AV_PIX_FMT_BGR48LE &&
1350  dstFormat != AV_PIX_FMT_BGR48BE &&
1351  dstFormat != AV_PIX_FMT_RGBA &&
1352  dstFormat != AV_PIX_FMT_ARGB &&
1353  dstFormat != AV_PIX_FMT_BGRA &&
1354  dstFormat != AV_PIX_FMT_ABGR &&
1355  dstFormat != AV_PIX_FMT_RGB24 &&
1356  dstFormat != AV_PIX_FMT_BGR24 &&
1357  dstFormat != AV_PIX_FMT_BGR4_BYTE &&
1358  dstFormat != AV_PIX_FMT_RGB4_BYTE &&
1359  dstFormat != AV_PIX_FMT_BGR8 &&
1360  dstFormat != AV_PIX_FMT_RGB8 &&
1361  dstFormat != AV_PIX_FMT_X2RGB10LE &&
1362  dstFormat != AV_PIX_FMT_X2BGR10LE
1363  ) {
1365  "full chroma interpolation for destination format '%s' not yet implemented\n",
1366  av_get_pix_fmt_name(dstFormat));
1368  sws->flags = flags;
1369  }
1370  if (isAnyRGB(dstFormat) && !(flags & SWS_FULL_CHR_H_INT))
1371  c->chrDstHSubSample = 1;
1372 
1373  // drop some chroma lines if the user wants it
1374  c->vChrDrop = (flags & SWS_SRC_V_CHR_DROP_MASK) >>
1376  c->chrSrcVSubSample += c->vChrDrop;
1377 
1378  /* drop every other pixel for chroma calculation unless user
1379  * wants full chroma */
1380  if (isAnyRGB(srcFormat) && !(srcW & 1) && !(flags & SWS_FULL_CHR_H_INP) &&
1381  srcFormat != AV_PIX_FMT_RGB8 && srcFormat != AV_PIX_FMT_BGR8 &&
1382  srcFormat != AV_PIX_FMT_RGB4 && srcFormat != AV_PIX_FMT_BGR4 &&
1383  srcFormat != AV_PIX_FMT_RGB4_BYTE && srcFormat != AV_PIX_FMT_BGR4_BYTE &&
1384  srcFormat != AV_PIX_FMT_GBRP9BE && srcFormat != AV_PIX_FMT_GBRP9LE &&
1385  srcFormat != AV_PIX_FMT_GBRP10BE && srcFormat != AV_PIX_FMT_GBRP10LE &&
1386  srcFormat != AV_PIX_FMT_GBRP10MSBBE && srcFormat != AV_PIX_FMT_GBRP10MSBLE &&
1387  srcFormat != AV_PIX_FMT_GBRAP10BE && srcFormat != AV_PIX_FMT_GBRAP10LE &&
1388  srcFormat != AV_PIX_FMT_GBRP12BE && srcFormat != AV_PIX_FMT_GBRP12LE &&
1389  srcFormat != AV_PIX_FMT_GBRP12MSBBE && srcFormat != AV_PIX_FMT_GBRP12MSBLE &&
1390  srcFormat != AV_PIX_FMT_GBRAP12BE && srcFormat != AV_PIX_FMT_GBRAP12LE &&
1391  srcFormat != AV_PIX_FMT_GBRAP14BE && srcFormat != AV_PIX_FMT_GBRAP14LE &&
1392  srcFormat != AV_PIX_FMT_GBRP14BE && srcFormat != AV_PIX_FMT_GBRP14LE &&
1393  srcFormat != AV_PIX_FMT_GBRP16BE && srcFormat != AV_PIX_FMT_GBRP16LE &&
1394  srcFormat != AV_PIX_FMT_GBRAP16BE && srcFormat != AV_PIX_FMT_GBRAP16LE &&
1395  srcFormat != AV_PIX_FMT_GBRPF32BE && srcFormat != AV_PIX_FMT_GBRPF32LE &&
1396  srcFormat != AV_PIX_FMT_GBRAPF32BE && srcFormat != AV_PIX_FMT_GBRAPF32LE &&
1397  srcFormat != AV_PIX_FMT_GBRPF16BE && srcFormat != AV_PIX_FMT_GBRPF16LE &&
1398  srcFormat != AV_PIX_FMT_GBRAPF16BE && srcFormat != AV_PIX_FMT_GBRAPF16LE &&
1399  ((dstW >> c->chrDstHSubSample) <= (srcW >> 1) ||
1400  (flags & SWS_FAST_BILINEAR)))
1401  c->chrSrcHSubSample = 1;
1402 
1403  // Note the AV_CEIL_RSHIFT is so that we always round toward +inf.
1404  c->chrSrcW = AV_CEIL_RSHIFT(srcW, c->chrSrcHSubSample);
1405  c->chrSrcH = AV_CEIL_RSHIFT(srcH, c->chrSrcVSubSample);
1406  c->chrDstW = AV_CEIL_RSHIFT(dstW, c->chrDstHSubSample);
1407  c->chrDstH = AV_CEIL_RSHIFT(dstH, c->chrDstVSubSample);
1408 
1409  if (!FF_ALLOCZ_TYPED_ARRAY(c->formatConvBuffer, FFALIGN(srcW * 2 + 78, 16) * 2))
1410  goto nomem;
1411 
1412  c->srcBpc = desc_src->comp[0].depth;
1413  if (c->srcBpc < 8)
1414  c->srcBpc = 8;
1415  c->dstBpc = desc_dst->comp[0].depth;
1416  if (c->dstBpc < 8)
1417  c->dstBpc = 8;
1418  if (isAnyRGB(srcFormat) || srcFormat == AV_PIX_FMT_PAL8)
1419  c->srcBpc = 16;
1420  if (c->dstBpc == 16)
1421  dst_stride <<= 1;
1422 
1423  if (INLINE_MMXEXT(cpu_flags) && c->srcBpc == 8 && c->dstBpc <= 14) {
1424  c->canMMXEXTBeUsed = dstW >= srcW && (dstW & 31) == 0 &&
1425  c->chrDstW >= c->chrSrcW &&
1426  (srcW & 15) == 0;
1427  if (!c->canMMXEXTBeUsed && dstW >= srcW && c->chrDstW >= c->chrSrcW && (srcW & 15) == 0
1428 
1429  && (flags & SWS_FAST_BILINEAR)) {
1430  if (flags & SWS_PRINT_INFO)
1431  av_log(c, AV_LOG_INFO,
1432  "output width is not a multiple of 32 -> no MMXEXT scaler\n");
1433  }
1434  if (usesHFilter || isNBPS(sws->src_format) || is16BPS(sws->src_format) || isAnyRGB(sws->src_format))
1435  c->canMMXEXTBeUsed = 0;
1436  } else
1437  c->canMMXEXTBeUsed = 0;
1438 
1439  int64_t chrXInc = (((int64_t)c->chrSrcW << 16) + (c->chrDstW >> 1)) / c->chrDstW;
1440  int64_t chrYInc = (((int64_t)c->chrSrcH << 16) + (c->chrDstH >> 1)) / c->chrDstH;
1441 
1442  /* Match pixel 0 of the src to pixel 0 of dst and match pixel n-2 of src
1443  * to pixel n-2 of dst, but only for the FAST_BILINEAR mode otherwise do
1444  * correct scaling.
1445  * n-2 is the last chrominance sample available.
1446  * This is not perfect, but no one should notice the difference, the more
1447  * correct variant would be like the vertical one, but that would require
1448  * some special code for the first and last pixel */
1449  if (flags & SWS_FAST_BILINEAR) {
1450  if (c->canMMXEXTBeUsed) {
1451  lumXInc += 20;
1452  chrXInc += 20;
1453  }
1454  // we don't use the x86 asm scaler if MMX is available
1455  else if (INLINE_MMX(cpu_flags) && c->dstBpc <= 14) {
1456  lumXInc = ((int64_t)(srcW - 2) << 16) / (dstW - 2) - 20;
1457  chrXInc = ((int64_t)(c->chrSrcW - 2) << 16) / (c->chrDstW - 2) - 20;
1458  }
1459  }
1460  if (chrXInc < 10 || chrXInc > INT_MAX ||
1461  chrYInc < 10 || chrYInc > INT_MAX ||
1462  lumXInc < 10 || lumXInc > INT_MAX ||
1463  lumYInc < 10 || lumYInc > INT_MAX)
1464  return AVERROR_PATCHWELCOME;
1465 
1466  c->lumXInc = lumXInc;
1467  c->lumYInc = lumYInc;
1468  c->chrXInc = chrXInc;
1469  c->chrYInc = chrYInc;
1470 
1471 
1472  // hardcoded for now
1473  c->gamma_value = 2.2;
1474  tmpFmt = AV_PIX_FMT_RGBA64LE;
1475 
1476  if (!unscaled && sws->gamma_flag && (srcFormat != tmpFmt || dstFormat != tmpFmt)) {
1477  SwsInternal *c2;
1478  c->cascaded_context[0] = NULL;
1479 
1480  ret = av_image_alloc(c->cascaded_tmp[0], c->cascaded_tmpStride[0],
1481  srcW, srcH, tmpFmt, 64);
1482  if (ret < 0)
1483  return ret;
1484 
1485  c->cascaded_context[0] = sws_getContext(srcW, srcH, srcFormat,
1486  srcW, srcH, tmpFmt,
1487  flags, NULL, NULL,
1488  sws->scaler_params);
1489  if (!c->cascaded_context[0]) {
1490  return AVERROR(ENOMEM);
1491  }
1492 
1493  c->cascaded_context[1] = sws_getContext(srcW, srcH, tmpFmt,
1494  dstW, dstH, tmpFmt,
1495  flags, srcFilter, dstFilter,
1496  sws->scaler_params);
1497 
1498  if (!c->cascaded_context[1])
1499  return AVERROR(ENOMEM);
1500 
1501  c2 = sws_internal(c->cascaded_context[1]);
1502  c2->is_internal_gamma = 1;
1503  c2->gamma = alloc_gamma_tbl( c->gamma_value);
1504  c2->inv_gamma = alloc_gamma_tbl(1.f/c->gamma_value);
1505  if (!c2->gamma || !c2->inv_gamma)
1506  return AVERROR(ENOMEM);
1507 
1508  // is_internal_flag is set after creating the context
1509  // to properly create the gamma convert FilterDescriptor
1510  // we have to re-initialize it
1512  if ((ret = ff_init_filters(c2)) < 0) {
1513  sws_freeContext(c->cascaded_context[1]);
1514  c->cascaded_context[1] = NULL;
1515  return ret;
1516  }
1517 
1518  c->cascaded_context[2] = NULL;
1519  if (dstFormat != tmpFmt) {
1520  ret = av_image_alloc(c->cascaded_tmp[1], c->cascaded_tmpStride[1],
1521  dstW, dstH, tmpFmt, 64);
1522  if (ret < 0)
1523  return ret;
1524 
1525  c->cascaded_context[2] = sws_getContext(dstW, dstH, tmpFmt,
1526  dstW, dstH, dstFormat,
1527  flags, NULL, NULL,
1528  sws->scaler_params);
1529  if (!c->cascaded_context[2])
1530  return AVERROR(ENOMEM);
1531  }
1532  return 0;
1533  }
1534 
1535  if (isBayer(srcFormat)) {
1536  if (!unscaled ||
1537  (dstFormat != AV_PIX_FMT_RGB24 && dstFormat != AV_PIX_FMT_YUV420P &&
1538  dstFormat != AV_PIX_FMT_RGB48)) {
1539  enum AVPixelFormat tmpFormat = isBayer16BPS(srcFormat) ? AV_PIX_FMT_RGB48 : AV_PIX_FMT_RGB24;
1540 
1541  ret = av_image_alloc(c->cascaded_tmp[0], c->cascaded_tmpStride[0],
1542  srcW, srcH, tmpFormat, 64);
1543  if (ret < 0)
1544  return ret;
1545 
1546  c->cascaded_context[0] = sws_getContext(srcW, srcH, srcFormat,
1547  srcW, srcH, tmpFormat,
1548  flags, srcFilter, NULL,
1549  sws->scaler_params);
1550  if (!c->cascaded_context[0])
1551  return AVERROR(ENOMEM);
1552 
1553  c->cascaded_context[1] = sws_getContext(srcW, srcH, tmpFormat,
1554  dstW, dstH, dstFormat,
1555  flags, NULL, dstFilter,
1556  sws->scaler_params);
1557  if (!c->cascaded_context[1])
1558  return AVERROR(ENOMEM);
1559  return 0;
1560  }
1561  }
1562 
1563  if (unscaled && c->srcBpc == 8 && dstFormat == AV_PIX_FMT_GRAYF32){
1564  for (i = 0; i < 256; ++i){
1565  c->uint2float_lut[i] = (float)i * float_mult;
1566  }
1567  }
1568 
1569  // float will be converted to uint16_t
1570  if (isFloat(srcFormat) && !isAnyRGB(srcFormat) &&
1571  (!unscaled || unscaled && dstFormat != srcFormat && (srcFormat != AV_PIX_FMT_GRAYF32 ||
1572  dstFormat != AV_PIX_FMT_GRAY8))){
1573  c->srcBpc = 16;
1574  }
1575 
1576  if (CONFIG_SWSCALE_ALPHA && isALPHA(srcFormat) && !isALPHA(dstFormat)) {
1577  enum AVPixelFormat tmpFormat = alphaless_fmt(srcFormat);
1578 
1579  if (tmpFormat != AV_PIX_FMT_NONE && sws->alpha_blend != SWS_ALPHA_BLEND_NONE) {
1580  if (!unscaled ||
1581  dstFormat != tmpFormat ||
1582  usesHFilter || usesVFilter ||
1583  sws->src_range != sws->dst_range
1584  ) {
1585  c->cascaded_mainindex = 1;
1586  ret = av_image_alloc(c->cascaded_tmp[0], c->cascaded_tmpStride[0],
1587  srcW, srcH, tmpFormat, 64);
1588  if (ret < 0)
1589  return ret;
1590 
1591  c->cascaded_context[0] = alloc_set_opts(srcW, srcH, srcFormat,
1592  srcW, srcH, tmpFormat,
1593  flags, sws->scaler_params);
1594  if (!c->cascaded_context[0])
1595  return AVERROR(EINVAL);
1596  c->cascaded_context[0]->alpha_blend = sws->alpha_blend;
1597  ret = sws_init_context(c->cascaded_context[0], NULL , NULL);
1598  if (ret < 0)
1599  return ret;
1600 
1601  c->cascaded_context[1] = alloc_set_opts(srcW, srcH, tmpFormat,
1602  dstW, dstH, dstFormat,
1603  flags, sws->scaler_params);
1604  if (!c->cascaded_context[1])
1605  return AVERROR(EINVAL);
1606 
1607  c->cascaded_context[1]->src_range = sws->src_range;
1608  c->cascaded_context[1]->dst_range = sws->dst_range;
1609  ret = sws_init_context(c->cascaded_context[1], srcFilter , dstFilter);
1610  if (ret < 0)
1611  return ret;
1612 
1613  return 0;
1614  }
1615  }
1616  }
1617 
1618  /* alpha blend special case, note this has been split via cascaded contexts if its scaled */
1619  if (unscaled && !usesHFilter && !usesVFilter &&
1621  isALPHA(srcFormat) &&
1622  (sws->src_range == sws->dst_range || isAnyRGB(dstFormat)) &&
1623  alphaless_fmt(srcFormat) == dstFormat
1624  ) {
1625  c->convert_unscaled = ff_sws_alphablendaway;
1626 
1627  if (flags & SWS_PRINT_INFO)
1628  av_log(c, AV_LOG_INFO,
1629  "using alpha blendaway %s -> %s special converter\n",
1630  av_get_pix_fmt_name(srcFormat), av_get_pix_fmt_name(dstFormat));
1631  return 0;
1632  }
1633 
1634  /* unscaled special cases */
1635  if (unscaled && !usesHFilter && !usesVFilter &&
1636  (sws->src_range == sws->dst_range || isAnyRGB(dstFormat) ||
1637  isFloat(srcFormat) || isFloat(dstFormat) || isBayer(srcFormat))){
1638 
1640 
1641  if (c->convert_unscaled) {
1642  if (flags & SWS_PRINT_INFO)
1643  av_log(c, AV_LOG_INFO,
1644  "using unscaled %s -> %s special converter\n",
1645  av_get_pix_fmt_name(srcFormat), av_get_pix_fmt_name(dstFormat));
1646  return 0;
1647  }
1648  }
1649 
1650 #if HAVE_MMAP && HAVE_MPROTECT && defined(MAP_ANONYMOUS)
1651 #define USE_MMAP 1
1652 #else
1653 #define USE_MMAP 0
1654 #endif
1655 
1656  /* precalculate horizontal scaler filter coefficients */
1657  {
1658 #if HAVE_MMXEXT_INLINE
1659 // can't downscale !!!
1660  if (c->canMMXEXTBeUsed && (flags & SWS_FAST_BILINEAR)) {
1661  c->lumMmxextFilterCodeSize = ff_init_hscaler_mmxext(dstW, c->lumXInc, NULL,
1662  NULL, NULL, 8);
1663  c->chrMmxextFilterCodeSize = ff_init_hscaler_mmxext(c->chrDstW, c->chrXInc,
1664  NULL, NULL, NULL, 4);
1665 
1666 #if USE_MMAP
1667  c->lumMmxextFilterCode = mmap(NULL, c->lumMmxextFilterCodeSize,
1668  PROT_READ | PROT_WRITE,
1669  MAP_PRIVATE | MAP_ANONYMOUS,
1670  -1, 0);
1671  c->chrMmxextFilterCode = mmap(NULL, c->chrMmxextFilterCodeSize,
1672  PROT_READ | PROT_WRITE,
1673  MAP_PRIVATE | MAP_ANONYMOUS,
1674  -1, 0);
1675 #elif HAVE_VIRTUALALLOC
1676  c->lumMmxextFilterCode = VirtualAlloc(NULL,
1677  c->lumMmxextFilterCodeSize,
1678  MEM_COMMIT,
1679  PAGE_EXECUTE_READWRITE);
1680  c->chrMmxextFilterCode = VirtualAlloc(NULL,
1681  c->chrMmxextFilterCodeSize,
1682  MEM_COMMIT,
1683  PAGE_EXECUTE_READWRITE);
1684 #else
1685  c->lumMmxextFilterCode = av_malloc(c->lumMmxextFilterCodeSize);
1686  c->chrMmxextFilterCode = av_malloc(c->chrMmxextFilterCodeSize);
1687 #endif
1688 
1689 #ifdef MAP_ANONYMOUS
1690  if (c->lumMmxextFilterCode == MAP_FAILED || c->chrMmxextFilterCode == MAP_FAILED)
1691 #else
1692  if (!c->lumMmxextFilterCode || !c->chrMmxextFilterCode)
1693 #endif
1694  {
1695  av_log(c, AV_LOG_ERROR, "Failed to allocate MMX2FilterCode\n");
1696  return AVERROR(ENOMEM);
1697  }
1698 
1699  if (!FF_ALLOCZ_TYPED_ARRAY(c->hLumFilter, dstW / 8 + 8) ||
1700  !FF_ALLOCZ_TYPED_ARRAY(c->hChrFilter, c->chrDstW / 4 + 8) ||
1701  !FF_ALLOCZ_TYPED_ARRAY(c->hLumFilterPos, dstW / 2 / 8 + 8) ||
1702  !FF_ALLOCZ_TYPED_ARRAY(c->hChrFilterPos, c->chrDstW / 2 / 4 + 8))
1703  goto nomem;
1704 
1705  ff_init_hscaler_mmxext( dstW, c->lumXInc, c->lumMmxextFilterCode,
1706  c->hLumFilter, (uint32_t*)c->hLumFilterPos, 8);
1707  ff_init_hscaler_mmxext(c->chrDstW, c->chrXInc, c->chrMmxextFilterCode,
1708  c->hChrFilter, (uint32_t*)c->hChrFilterPos, 4);
1709 
1710 #if USE_MMAP
1711  if ( mprotect(c->lumMmxextFilterCode, c->lumMmxextFilterCodeSize, PROT_EXEC | PROT_READ) == -1
1712  || mprotect(c->chrMmxextFilterCode, c->chrMmxextFilterCodeSize, PROT_EXEC | PROT_READ) == -1) {
1713  av_log(c, AV_LOG_ERROR, "mprotect failed, cannot use fast bilinear scaler\n");
1714  ret = AVERROR(EINVAL);
1715  goto fail;
1716  }
1717 #endif
1718  } else
1719 #endif /* HAVE_MMXEXT_INLINE */
1720  {
1721  const int filterAlign = X86_MMX(cpu_flags) ? 4 :
1722  PPC_ALTIVEC(cpu_flags) ? 8 :
1723  have_neon(cpu_flags) ? 4 :
1724  have_lsx(cpu_flags) ? 8 :
1725  have_lasx(cpu_flags) ? 8 : 1;
1726 
1727  if ((ret = initFilter(&c->hLumFilter, &c->hLumFilterPos,
1728  &c->hLumFilterSize, c->lumXInc,
1729  srcW, dstW, filterAlign, 1 << 14,
1730  lum_scaler, flags,
1731  cpu_flags, srcFilter->lumH, dstFilter->lumH,
1732  sws->scaler_params,
1733  get_local_pos(c, 0, 0, 0),
1734  get_local_pos(c, 0, 0, 0))) < 0)
1735  goto fail;
1736  if (ff_shuffle_filter_coefficients(c, c->hLumFilterPos, c->hLumFilterSize, c->hLumFilter, dstW) < 0)
1737  goto nomem;
1738  if ((ret = initFilter(&c->hChrFilter, &c->hChrFilterPos,
1739  &c->hChrFilterSize, c->chrXInc,
1740  c->chrSrcW, c->chrDstW, filterAlign, 1 << 14,
1741  chr_scaler, flags,
1742  cpu_flags, srcFilter->chrH, dstFilter->chrH,
1743  sws->scaler_params,
1744  get_local_pos(c, c->chrSrcHSubSample, sws->src_h_chr_pos, 0),
1745  get_local_pos(c, c->chrDstHSubSample, sws->dst_h_chr_pos, 0))) < 0)
1746  goto fail;
1747  if (ff_shuffle_filter_coefficients(c, c->hChrFilterPos, c->hChrFilterSize, c->hChrFilter, c->chrDstW) < 0)
1748  goto nomem;
1749  }
1750  } // initialize horizontal stuff
1751 
1752  /* precalculate vertical scaler filter coefficients */
1753  {
1754  const int filterAlign = X86_MMX(cpu_flags) ? 2 :
1755  PPC_ALTIVEC(cpu_flags) ? 8 :
1756  have_neon(cpu_flags) ? 2 : 1;
1757 
1758  ret = initFilter(&c->vLumFilter, &c->vLumFilterPos, &c->vLumFilterSize,
1759  c->lumYInc, srcH, dstH, filterAlign, (1 << 12),
1760  lum_scaler, flags,
1761  cpu_flags, srcFilter->lumV, dstFilter->lumV,
1762  sws->scaler_params,
1763  get_local_pos(c, 0, 0, 1),
1764  get_local_pos(c, 0, 0, 1));
1765  int usecascade = (ret == RETCODE_USE_CASCADE);
1766  if (ret < 0 && !usecascade)
1767  goto fail;
1768  if ((ret = initFilter(&c->vChrFilter, &c->vChrFilterPos, &c->vChrFilterSize,
1769  c->chrYInc, c->chrSrcH, c->chrDstH,
1770  filterAlign, (1 << 12),
1771  chr_scaler, flags,
1772  cpu_flags, srcFilter->chrV, dstFilter->chrV,
1773  sws->scaler_params,
1774  get_local_pos(c, c->chrSrcVSubSample, sws->src_v_chr_pos, 1),
1775  get_local_pos(c, c->chrDstVSubSample, sws->dst_v_chr_pos, 1))) < 0)
1776 
1777  goto fail;
1778  if (usecascade) {
1780  goto fail;
1781  }
1782 
1783 #if HAVE_ALTIVEC
1785  if (ret < 0)
1786  goto fail;
1787 #endif
1788  }
1789 
1790  for (i = 0; i < 4; i++)
1791  if (!FF_ALLOCZ_TYPED_ARRAY(c->dither_error[i], sws->dst_w + 3))
1792  goto nomem;
1793 
1794  c->needAlpha = (CONFIG_SWSCALE_ALPHA && isALPHA(sws->src_format) && isALPHA(sws->dst_format)) ? 1 : 0;
1795 
1796  // 64 / c->scalingBpp is the same as 16 / sizeof(scaling_intermediate)
1797  c->uv_off = (dst_stride>>1) + 64 / (c->dstBpc &~ 7);
1798  c->uv_offx2 = dst_stride + 16;
1799 
1800  av_assert0(c->chrDstH <= dstH);
1801 
1802  if (flags & SWS_PRINT_INFO) {
1803  const char *scaler = NULL, *cpucaps;
1804 
1805  for (i = 0; i < FF_ARRAY_ELEMS(scale_algorithms); i++) {
1806  if (flags & scale_algorithms[i].flag) {
1807  scaler = scale_algorithms[i].description;
1808  break;
1809  }
1810  }
1811  if (!scaler)
1812  scaler = "ehh flags invalid?!";
1813  av_log(c, AV_LOG_INFO, "%s scaler, from %s to %s%s ",
1814  scaler,
1815  av_get_pix_fmt_name(srcFormat),
1816  dstFormat == AV_PIX_FMT_BGR555 || dstFormat == AV_PIX_FMT_BGR565 ||
1817  dstFormat == AV_PIX_FMT_RGB444BE || dstFormat == AV_PIX_FMT_RGB444LE ||
1818  dstFormat == AV_PIX_FMT_BGR444BE || dstFormat == AV_PIX_FMT_BGR444LE ?
1819  "dithered " : "",
1820  av_get_pix_fmt_name(dstFormat));
1821 
1822  if (INLINE_MMXEXT(cpu_flags))
1823  cpucaps = "MMXEXT";
1824  else if (INLINE_MMX(cpu_flags))
1825  cpucaps = "MMX";
1826  else if (PPC_ALTIVEC(cpu_flags))
1827  cpucaps = "AltiVec";
1828  else
1829  cpucaps = "C";
1830 
1831  av_log(c, AV_LOG_INFO, "using %s\n", cpucaps);
1832 
1833  av_log(c, AV_LOG_VERBOSE, "%dx%d -> %dx%d\n", srcW, srcH, dstW, dstH);
1835  "lum srcW=%d srcH=%d dstW=%d dstH=%d xInc=%d yInc=%d\n",
1836  sws->src_w, sws->src_h, sws->dst_w, sws->dst_h, c->lumXInc, c->lumYInc);
1838  "chr srcW=%d srcH=%d dstW=%d dstH=%d xInc=%d yInc=%d\n",
1839  c->chrSrcW, c->chrSrcH, c->chrDstW, c->chrDstH,
1840  c->chrXInc, c->chrYInc);
1841  }
1842 
1844 
1845  return ff_init_filters(c);
1846 nomem:
1847  ret = AVERROR(ENOMEM);
1848 fail: // FIXME replace things by appropriate error codes
1849  if (ret == RETCODE_USE_CASCADE) {
1850  int tmpW = sqrt(srcW * (int64_t)dstW);
1851  int tmpH = sqrt(srcH * (int64_t)dstH);
1852  enum AVPixelFormat tmpFormat = AV_PIX_FMT_YUV420P;
1853 
1854  if (isALPHA(srcFormat))
1855  tmpFormat = AV_PIX_FMT_YUVA420P;
1856 
1857  if (srcW*(int64_t)srcH <= 4LL*dstW*dstH)
1858  return AVERROR(EINVAL);
1859 
1860  ret = av_image_alloc(c->cascaded_tmp[0], c->cascaded_tmpStride[0],
1861  tmpW, tmpH, tmpFormat, 64);
1862  if (ret < 0)
1863  return ret;
1864 
1865  c->cascaded_context[0] = sws_getContext(srcW, srcH, srcFormat,
1866  tmpW, tmpH, tmpFormat,
1867  flags, srcFilter, NULL,
1868  sws->scaler_params);
1869  if (!c->cascaded_context[0])
1870  return AVERROR(ENOMEM);
1871 
1872  c->cascaded_context[1] = sws_getContext(tmpW, tmpH, tmpFormat,
1873  dstW, dstH, dstFormat,
1874  flags, NULL, dstFilter,
1875  sws->scaler_params);
1876  if (!c->cascaded_context[1])
1877  return AVERROR(ENOMEM);
1878  return 0;
1879  }
1880  return ret;
1881 }
1882 
1884  SwsFilter *src_filter, SwsFilter *dst_filter)
1885 {
1886  SwsInternal *c = sws_internal(sws);
1887  int ret;
1888 
1889  ret = avpriv_slicethread_create(&c->slicethread, (void*) sws,
1890  ff_sws_slice_worker, NULL, sws->threads);
1891  if (ret == AVERROR(ENOSYS)) {
1892  sws->threads = 1;
1893  return 0;
1894  } else if (ret < 0)
1895  return ret;
1896 
1897  sws->threads = ret;
1898 
1899  c->slice_ctx = av_calloc(sws->threads, sizeof(*c->slice_ctx));
1900  c->slice_err = av_calloc(sws->threads, sizeof(*c->slice_err));
1901  if (!c->slice_ctx || !c->slice_err)
1902  return AVERROR(ENOMEM);
1903 
1904  for (int i = 0; i < sws->threads; i++) {
1905  SwsContext *slice;
1906  slice = c->slice_ctx[i] = sws_alloc_context();
1907  if (!slice)
1908  return AVERROR(ENOMEM);
1909  sws_internal(slice)->parent = sws;
1910  c->nb_slice_ctx++;
1911 
1912  ret = av_opt_copy(slice, sws);
1913  if (ret < 0)
1914  return ret;
1915  slice->threads = 1;
1916 
1917  ret = ff_sws_init_single_context(slice, src_filter, dst_filter);
1918  if (ret < 0)
1919  return ret;
1920 
1921  if (slice->dither == SWS_DITHER_ED) {
1923  "Error-diffusion dither is in use, scaling will be single-threaded.");
1924  break;
1925  }
1926  }
1927 
1928  return 0;
1929 }
1930 
1932  SwsFilter *dstFilter)
1933 {
1934  SwsInternal *c = sws_internal(sws);
1935  static AVOnce rgb2rgb_once = AV_ONCE_INIT;
1936  enum AVPixelFormat src_format, dst_format;
1937  int ret;
1938 
1939  c->is_legacy_init = 1;
1940  c->frame_src = av_frame_alloc();
1941  c->frame_dst = av_frame_alloc();
1942  if (!c->frame_src || !c->frame_dst)
1943  return AVERROR(ENOMEM);
1944 
1945  if (ff_thread_once(&rgb2rgb_once, ff_sws_rgb2rgb_init) != 0)
1946  return AVERROR_UNKNOWN;
1947 
1948  src_format = sws->src_format;
1949  dst_format = sws->dst_format;
1950  sws->src_range |= handle_jpeg(&sws->src_format);
1951  sws->dst_range |= handle_jpeg(&sws->dst_format);
1952 
1953  if (src_format != sws->src_format || dst_format != sws->dst_format)
1954  av_log(c, AV_LOG_WARNING, "deprecated pixel format used, make sure you did set range correctly\n");
1955 
1956  if (sws->threads != 1) {
1957  ret = context_init_threaded(sws, srcFilter, dstFilter);
1958  if (ret < 0 || sws->threads > 1)
1959  return ret;
1960  // threading disabled in this build, init as single-threaded
1961  }
1962 
1963  return ff_sws_init_single_context(sws, srcFilter, dstFilter);
1964 }
1965 
1966 SwsContext *sws_getContext(int srcW, int srcH, enum AVPixelFormat srcFormat,
1967  int dstW, int dstH, enum AVPixelFormat dstFormat,
1968  int flags, SwsFilter *srcFilter,
1969  SwsFilter *dstFilter, const double *param)
1970 {
1971  SwsContext *sws;
1972 
1973  sws = alloc_set_opts(srcW, srcH, srcFormat,
1974  dstW, dstH, dstFormat,
1975  flags, param);
1976  if (!sws)
1977  return NULL;
1978 
1979  if (sws_init_context(sws, srcFilter, dstFilter) < 0) {
1980  sws_freeContext(sws);
1981  return NULL;
1982  }
1983 
1984  return sws;
1985 }
1986 
1987 static int isnan_vec(SwsVector *a)
1988 {
1989  int i;
1990  for (i=0; i<a->length; i++)
1991  if (isnan(a->coeff[i]))
1992  return 1;
1993  return 0;
1994 }
1995 
1996 static void makenan_vec(SwsVector *a)
1997 {
1998  int i;
1999  for (i=0; i<a->length; i++)
2000  a->coeff[i] = NAN;
2001 }
2002 
2004 {
2005  SwsVector *vec;
2006 
2007  if(length <= 0 || length > INT_MAX/ sizeof(double))
2008  return NULL;
2009 
2010  vec = av_malloc(sizeof(SwsVector));
2011  if (!vec)
2012  return NULL;
2013  vec->length = length;
2014  vec->coeff = av_malloc(sizeof(double) * length);
2015  if (!vec->coeff)
2016  av_freep(&vec);
2017  return vec;
2018 }
2019 
2020 SwsVector *sws_getGaussianVec(double variance, double quality)
2021 {
2022  const int length = (int)(variance * quality + 0.5) | 1;
2023  int i;
2024  double middle = (length - 1) * 0.5;
2025  SwsVector *vec;
2026 
2027  if(variance < 0 || quality < 0)
2028  return NULL;
2029 
2030  vec = sws_allocVec(length);
2031 
2032  if (!vec)
2033  return NULL;
2034 
2035  for (i = 0; i < length; i++) {
2036  double dist = i - middle;
2037  vec->coeff[i] = exp(-dist * dist / (2 * variance * variance)) /
2038  sqrt(2 * variance * M_PI);
2039  }
2040 
2041  sws_normalizeVec(vec, 1.0);
2042 
2043  return vec;
2044 }
2045 
2046 /**
2047  * Allocate and return a vector with length coefficients, all
2048  * with the same value c.
2049  */
2050 static
2051 SwsVector *sws_getConstVec(double c, int length)
2052 {
2053  int i;
2054  SwsVector *vec = sws_allocVec(length);
2055 
2056  if (!vec)
2057  return NULL;
2058 
2059  for (i = 0; i < length; i++)
2060  vec->coeff[i] = c;
2061 
2062  return vec;
2063 }
2064 
2065 /**
2066  * Allocate and return a vector with just one coefficient, with
2067  * value 1.0.
2068  */
2069 static
2071 {
2072  return sws_getConstVec(1.0, 1);
2073 }
2074 
2075 static double sws_dcVec(SwsVector *a)
2076 {
2077  int i;
2078  double sum = 0;
2079 
2080  for (i = 0; i < a->length; i++)
2081  sum += a->coeff[i];
2082 
2083  return sum;
2084 }
2085 
2086 void sws_scaleVec(SwsVector *a, double scalar)
2087 {
2088  int i;
2089 
2090  for (i = 0; i < a->length; i++)
2091  a->coeff[i] *= scalar;
2092 }
2093 
2095 {
2097 }
2098 
2100 {
2101  int length = FFMAX(a->length, b->length);
2102  int i;
2103  SwsVector *vec = sws_getConstVec(0.0, length);
2104 
2105  if (!vec)
2106  return NULL;
2107 
2108  for (i = 0; i < a->length; i++)
2109  vec->coeff[i + (length - 1) / 2 - (a->length - 1) / 2] += a->coeff[i];
2110  for (i = 0; i < b->length; i++)
2111  vec->coeff[i + (length - 1) / 2 - (b->length - 1) / 2] += b->coeff[i];
2112 
2113  return vec;
2114 }
2115 
2116 /* shift left / or right if "shift" is negative */
2118 {
2119  int length = a->length + FFABS(shift) * 2;
2120  int i;
2121  SwsVector *vec = sws_getConstVec(0.0, length);
2122 
2123  if (!vec)
2124  return NULL;
2125 
2126  for (i = 0; i < a->length; i++) {
2127  vec->coeff[i + (length - 1) / 2 -
2128  (a->length - 1) / 2 - shift] = a->coeff[i];
2129  }
2130 
2131  return vec;
2132 }
2133 
2134 static
2136 {
2137  SwsVector *shifted = sws_getShiftedVec(a, shift);
2138  if (!shifted) {
2139  makenan_vec(a);
2140  return;
2141  }
2142  av_free(a->coeff);
2143  a->coeff = shifted->coeff;
2144  a->length = shifted->length;
2145  av_free(shifted);
2146 }
2147 
2148 static
2150 {
2151  SwsVector *sum = sws_sumVec(a, b);
2152  if (!sum) {
2153  makenan_vec(a);
2154  return;
2155  }
2156  av_free(a->coeff);
2157  a->coeff = sum->coeff;
2158  a->length = sum->length;
2159  av_free(sum);
2160 }
2161 
2162 /**
2163  * Print with av_log() a textual representation of the vector a
2164  * if log_level <= av_log_level.
2165  */
2166 static
2167 void sws_printVec2(SwsVector *a, AVClass *log_ctx, int log_level)
2168 {
2169  int i;
2170  double max = 0;
2171  double min = 0;
2172  double range;
2173 
2174  for (i = 0; i < a->length; i++)
2175  if (a->coeff[i] > max)
2176  max = a->coeff[i];
2177 
2178  for (i = 0; i < a->length; i++)
2179  if (a->coeff[i] < min)
2180  min = a->coeff[i];
2181 
2182  range = max - min;
2183 
2184  for (i = 0; i < a->length; i++) {
2185  int x = (int)((a->coeff[i] - min) * 60.0 / range + 0.5);
2186  av_log(log_ctx, log_level, "%1.3f ", a->coeff[i]);
2187  for (; x > 0; x--)
2188  av_log(log_ctx, log_level, " ");
2189  av_log(log_ctx, log_level, "|\n");
2190  }
2191 }
2192 
2194 {
2195  if (!a)
2196  return;
2197  av_freep(&a->coeff);
2198  a->length = 0;
2199  av_free(a);
2200 }
2201 
2203 {
2204  if (!filter)
2205  return;
2206 
2207  sws_freeVec(filter->lumH);
2208  sws_freeVec(filter->lumV);
2209  sws_freeVec(filter->chrH);
2210  sws_freeVec(filter->chrV);
2211  av_free(filter);
2212 }
2213 
2214 SwsFilter *sws_getDefaultFilter(float lumaGBlur, float chromaGBlur,
2215  float lumaSharpen, float chromaSharpen,
2216  float chromaHShift, float chromaVShift,
2217  int verbose)
2218 {
2219  SwsFilter *filter = av_malloc(sizeof(SwsFilter));
2220  if (!filter)
2221  return NULL;
2222 
2223  if (lumaGBlur != 0.0) {
2224  filter->lumH = sws_getGaussianVec(lumaGBlur, 3.0);
2225  filter->lumV = sws_getGaussianVec(lumaGBlur, 3.0);
2226  } else {
2227  filter->lumH = sws_getIdentityVec();
2228  filter->lumV = sws_getIdentityVec();
2229  }
2230 
2231  if (chromaGBlur != 0.0) {
2232  filter->chrH = sws_getGaussianVec(chromaGBlur, 3.0);
2233  filter->chrV = sws_getGaussianVec(chromaGBlur, 3.0);
2234  } else {
2235  filter->chrH = sws_getIdentityVec();
2236  filter->chrV = sws_getIdentityVec();
2237  }
2238 
2239  if (!filter->lumH || !filter->lumV || !filter->chrH || !filter->chrV)
2240  goto fail;
2241 
2242  if (chromaSharpen != 0.0) {
2243  SwsVector *id = sws_getIdentityVec();
2244  if (!id)
2245  goto fail;
2246  sws_scaleVec(filter->chrH, -chromaSharpen);
2247  sws_scaleVec(filter->chrV, -chromaSharpen);
2248  sws_addVec(filter->chrH, id);
2249  sws_addVec(filter->chrV, id);
2250  sws_freeVec(id);
2251  }
2252 
2253  if (lumaSharpen != 0.0) {
2254  SwsVector *id = sws_getIdentityVec();
2255  if (!id)
2256  goto fail;
2257  sws_scaleVec(filter->lumH, -lumaSharpen);
2258  sws_scaleVec(filter->lumV, -lumaSharpen);
2259  sws_addVec(filter->lumH, id);
2260  sws_addVec(filter->lumV, id);
2261  sws_freeVec(id);
2262  }
2263 
2264  if (chromaHShift != 0.0)
2265  sws_shiftVec(filter->chrH, (int)(chromaHShift + 0.5));
2266 
2267  if (chromaVShift != 0.0)
2268  sws_shiftVec(filter->chrV, (int)(chromaVShift + 0.5));
2269 
2270  sws_normalizeVec(filter->chrH, 1.0);
2271  sws_normalizeVec(filter->chrV, 1.0);
2272  sws_normalizeVec(filter->lumH, 1.0);
2273  sws_normalizeVec(filter->lumV, 1.0);
2274 
2275  if (isnan_vec(filter->chrH) ||
2276  isnan_vec(filter->chrV) ||
2277  isnan_vec(filter->lumH) ||
2278  isnan_vec(filter->lumV))
2279  goto fail;
2280 
2281  if (verbose)
2283  if (verbose)
2285 
2286  return filter;
2287 
2288 fail:
2289  sws_freeVec(filter->lumH);
2290  sws_freeVec(filter->lumV);
2291  sws_freeVec(filter->chrH);
2292  sws_freeVec(filter->chrV);
2293  av_freep(&filter);
2294  return NULL;
2295 }
2296 
2298 {
2299  SwsInternal *c = sws_internal(sws);
2300  int i;
2301  if (!c)
2302  return;
2303 
2304  av_refstruct_unref(&c->hw_priv);
2305 
2306  for (i = 0; i < FF_ARRAY_ELEMS(c->graph); i++)
2307  ff_sws_graph_free(&c->graph[i]);
2308  ff_frame_pool_uninit(&c->frame_pool);
2309 
2310  for (i = 0; i < c->nb_slice_ctx; i++)
2311  sws_freeContext(c->slice_ctx[i]);
2312  av_freep(&c->slice_ctx);
2313  av_freep(&c->slice_err);
2314 
2315  avpriv_slicethread_free(&c->slicethread);
2316 
2317  for (i = 0; i < 4; i++)
2318  av_freep(&c->dither_error[i]);
2319 
2320  av_frame_free(&c->frame_src);
2321  av_frame_free(&c->frame_dst);
2322 
2323  av_freep(&c->src_ranges.ranges);
2324 
2325  av_freep(&c->vLumFilter);
2326  av_freep(&c->vChrFilter);
2327  av_freep(&c->hLumFilter);
2328  av_freep(&c->hChrFilter);
2329 #if HAVE_ALTIVEC
2331 #endif
2332 
2333  av_freep(&c->vLumFilterPos);
2334  av_freep(&c->vChrFilterPos);
2335  av_freep(&c->hLumFilterPos);
2336  av_freep(&c->hChrFilterPos);
2337 
2338 #if HAVE_MMX_INLINE
2339 #if USE_MMAP
2340  if (c->lumMmxextFilterCode)
2341  munmap(c->lumMmxextFilterCode, c->lumMmxextFilterCodeSize);
2342  if (c->chrMmxextFilterCode)
2343  munmap(c->chrMmxextFilterCode, c->chrMmxextFilterCodeSize);
2344 #elif HAVE_VIRTUALALLOC
2345  if (c->lumMmxextFilterCode)
2346  VirtualFree(c->lumMmxextFilterCode, 0, MEM_RELEASE);
2347  if (c->chrMmxextFilterCode)
2348  VirtualFree(c->chrMmxextFilterCode, 0, MEM_RELEASE);
2349 #else
2350  av_free(c->lumMmxextFilterCode);
2351  av_free(c->chrMmxextFilterCode);
2352 #endif
2353  c->lumMmxextFilterCode = NULL;
2354  c->chrMmxextFilterCode = NULL;
2355 #endif /* HAVE_MMX_INLINE */
2356 
2357  av_freep(&c->yuvTable);
2358  av_freep(&c->formatConvBuffer);
2359 
2360  sws_freeContext(c->cascaded_context[0]);
2361  sws_freeContext(c->cascaded_context[1]);
2362  sws_freeContext(c->cascaded_context[2]);
2363  memset(c->cascaded_context, 0, sizeof(c->cascaded_context));
2364  av_freep(&c->cascaded_tmp[0][0]);
2365  av_freep(&c->cascaded_tmp[1][0]);
2366 
2367  av_freep(&c->gamma);
2368  av_freep(&c->inv_gamma);
2369 #if CONFIG_SMALL
2370  av_freep(&c->xyz2rgb.gamma.in);
2371 #endif
2372 
2373  av_freep(&c->rgb0_scratch);
2374  av_freep(&c->xyz_scratch);
2375 
2376  ff_free_filters(c);
2377 
2378  av_free(c);
2379 }
2380 
2382 {
2383  SwsContext *ctx = *pctx;
2384  if (!ctx)
2385  return;
2386 
2388  *pctx = NULL;
2389 }
2390 
2392  int srcH, enum AVPixelFormat srcFormat,
2393  int dstW, int dstH,
2394  enum AVPixelFormat dstFormat, int flags,
2395  SwsFilter *srcFilter,
2396  SwsFilter *dstFilter,
2397  const double *param)
2398 {
2399  SwsContext *sws;
2400  static const double default_param[2] = { SWS_PARAM_DEFAULT,
2402 
2403  if (!param)
2404  param = default_param;
2405 
2406  if (prev && (prev->src_w == srcW &&
2407  prev->src_h == srcH &&
2408  prev->src_format == srcFormat &&
2409  prev->dst_w == dstW &&
2410  prev->dst_h == dstH &&
2411  prev->dst_format == dstFormat &&
2412  prev->flags == flags &&
2413  !memcmp(prev->scaler_params, param,
2414  sizeof(prev->scaler_params)))) {
2415  return prev;
2416  }
2417 
2418  if (!(sws = sws_alloc_context())) {
2419  sws_free_context(&prev);
2420  return NULL;
2421  }
2422 
2423  if (prev) {
2424  av_opt_copy(sws, prev);
2425  sws_free_context(&prev);
2426  }
2427 
2428  sws->src_w = srcW;
2429  sws->src_h = srcH;
2430  sws->src_format = srcFormat;
2431  sws->dst_w = dstW;
2432  sws->dst_h = dstH;
2433  sws->dst_format = dstFormat;
2434  sws->flags = flags;
2435  for (int i = 0; i < SWS_NUM_SCALER_PARAMS; i++)
2436  sws->scaler_params[i] = param[i];
2437 
2438  if (sws_init_context(sws, srcFilter, dstFilter) < 0)
2439  sws_free_context(&sws);
2440 
2441  return sws;
2442 }
2443 
2444 int ff_range_add(RangeList *rl, unsigned int start, unsigned int len)
2445 {
2446  Range *tmp;
2447  unsigned int idx;
2448 
2449  /* find the first existing range after the new one */
2450  for (idx = 0; idx < rl->nb_ranges; idx++)
2451  if (rl->ranges[idx].start > start)
2452  break;
2453 
2454  /* check for overlap */
2455  if (idx > 0) {
2456  Range *prev = &rl->ranges[idx - 1];
2457  if (prev->start + prev->len > start)
2458  return AVERROR(EINVAL);
2459  }
2460  if (idx < rl->nb_ranges) {
2461  Range *next = &rl->ranges[idx];
2462  if (start + len > next->start)
2463  return AVERROR(EINVAL);
2464  }
2465 
2467  (rl->nb_ranges + 1) * sizeof(*rl->ranges));
2468  if (!tmp)
2469  return AVERROR(ENOMEM);
2470  rl->ranges = tmp;
2471 
2472  memmove(rl->ranges + idx + 1, rl->ranges + idx,
2473  sizeof(*rl->ranges) * (rl->nb_ranges - idx));
2474  rl->ranges[idx].start = start;
2475  rl->ranges[idx].len = len;
2476  rl->nb_ranges++;
2477 
2478  /* merge ranges */
2479  if (idx > 0) {
2480  Range *prev = &rl->ranges[idx - 1];
2481  Range *cur = &rl->ranges[idx];
2482  if (prev->start + prev->len == cur->start) {
2483  prev->len += cur->len;
2484  memmove(rl->ranges + idx - 1, rl->ranges + idx,
2485  sizeof(*rl->ranges) * (rl->nb_ranges - idx));
2486  rl->nb_ranges--;
2487  idx--;
2488  }
2489  }
2490  if (idx < rl->nb_ranges - 1) {
2491  Range *cur = &rl->ranges[idx];
2492  Range *next = &rl->ranges[idx + 1];
2493  if (cur->start + cur->len == next->start) {
2494  cur->len += next->len;
2495  memmove(rl->ranges + idx, rl->ranges + idx + 1,
2496  sizeof(*rl->ranges) * (rl->nb_ranges - idx - 1));
2497  rl->nb_ranges--;
2498  }
2499  }
2500 
2501  return 0;
2502 }
FF_ALLOCZ_TYPED_ARRAY
#define FF_ALLOCZ_TYPED_ARRAY(p, nelem)
Definition: internal.h:78
error
static void error(const char *err)
Definition: target_bsf_fuzzer.c:32
isBayer
static av_always_inline int isBayer(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:862
flags
const SwsFlags flags[]
Definition: swscale.c:85
A
#define A(x)
Definition: vpx_arith.h:28
AV_PIX_FMT_XYZ12LE
@ AV_PIX_FMT_XYZ12LE
packed XYZ 4:4:4, 36 bpp, (msb) 12X, 12Y, 12Z (lsb), the 2-byte value for each X/Y/Z is stored as lit...
Definition: pixfmt.h:196
av_pix_fmt_swap_endianness
enum AVPixelFormat av_pix_fmt_swap_endianness(enum AVPixelFormat pix_fmt)
Utility function to swap the endianness of a pixel format.
Definition: pixdesc.c:3511
sws_setColorspaceDetails
int sws_setColorspaceDetails(SwsContext *sws, const int inv_table[4], int srcRange, const int table[4], int dstRange, int brightness, int contrast, int saturation)
Definition: utils.c:860
AV_LOG_WARNING
#define AV_LOG_WARNING
Something somehow does not look correct.
Definition: log.h:216
AV_PIX_FMT_GRAY10BE
@ AV_PIX_FMT_GRAY10BE
Y , 10bpp, big-endian.
Definition: pixfmt.h:320
INLINE_MMXEXT
#define INLINE_MMXEXT(flags)
Definition: cpu.h:81
AVPixelFormat
AVPixelFormat
Pixel format.
Definition: pixfmt.h:71
AV_PIX_FMT_BGR48LE
@ AV_PIX_FMT_BGR48LE
packed RGB 16:16:16, 48bpp, 16B, 16G, 16R, the 2-byte value for each R/G/B component is stored as lit...
Definition: pixfmt.h:146
isPlanarRGB
static av_always_inline int isPlanarRGB(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:930
SWS_DITHER_AUTO
@ SWS_DITHER_AUTO
Definition: swscale.h:81
av_opt_set_defaults
void av_opt_set_defaults(void *s)
Set the values of all AVOption fields to their default values.
Definition: opt.c:1672
AVERROR
Filter the word “frame” indicates either a video frame or a group of audio as stored in an AVFrame structure Format for each input and each output the list of supported formats For video that means pixel format For audio that means channel sample they are references to shared objects When the negotiation mechanism computes the intersection of the formats supported at each end of a all references to both lists are replaced with a reference to the intersection And when a single format is eventually chosen for a link amongst the remaining all references to the list are updated That means that if a filter requires that its input and output have the same format amongst a supported all it has to do is use a reference to the same list of formats query_formats can leave some formats unset and return AVERROR(EAGAIN) to cause the negotiation mechanism toagain later. That can be used by filters with complex requirements to use the format negotiated on one link to set the formats supported on another. Frame references ownership and permissions
opt.h
AV_PIX_FMT_YA8
@ AV_PIX_FMT_YA8
8 bits gray, 8 bits alpha
Definition: pixfmt.h:140
PPC_ALTIVEC
#define PPC_ALTIVEC(flags)
Definition: cpu.h:25
flag
int flag
Definition: cpu.c:40
AV_PIX_FMT_BGRA64BE
@ AV_PIX_FMT_BGRA64BE
packed RGBA 16:16:16:16, 64bpp, 16B, 16G, 16R, 16A, the 2-byte value for each R/G/B/A component is st...
Definition: pixfmt.h:204
sws_getIdentityVec
static SwsVector * sws_getIdentityVec(void)
Allocate and return a vector with just one coefficient, with value 1.0.
Definition: utils.c:2070
libm.h
sws_isSupportedOutput
#define sws_isSupportedOutput(x)
AV_PIX_FMT_RGB444LE
@ AV_PIX_FMT_RGB444LE
packed RGB 4:4:4, 16bpp, (msb)4X 4R 4G 4B(lsb), little-endian, X=unused/undefined
Definition: pixfmt.h:136
AV_PIX_FMT_GBRP16BE
@ AV_PIX_FMT_GBRP16BE
planar GBR 4:4:4 48bpp, big-endian
Definition: pixfmt.h:171
AV_PIX_FMT_GBRP10BE
@ AV_PIX_FMT_GBRP10BE
planar GBR 4:4:4 30bpp, big-endian
Definition: pixfmt.h:169
thread.h
av_pix_fmt_desc_get
const AVPixFmtDescriptor * av_pix_fmt_desc_get(enum AVPixelFormat pix_fmt)
Definition: pixdesc.c:3456
SwsContext::src_w
int src_w
Deprecated frame property overrides, for the legacy API only.
Definition: swscale.h:276
SWS_SCALE_BILINEAR
@ SWS_SCALE_BILINEAR
bilinear filtering
Definition: swscale.h:98
Z
#define Z
Definition: uops_tmpl.h:83
saturation
static IPT saturation(const CmsCtx *ctx, IPT ipt)
Definition: cms.c:559
av_cold
#define av_cold
Definition: attributes.h:119
int64_t
long long int64_t
Definition: coverity.c:34
RangeList::ranges_allocated
int ranges_allocated
Definition: swscale_internal.h:94
MAX_FILTER_SIZE
#define MAX_FILTER_SIZE
Definition: af_dynaudnorm.c:36
sws_freeContext
void sws_freeContext(SwsContext *sws)
Free the swscaler context swsContext.
Definition: utils.c:2297
cpu.h
av_frame_free
void av_frame_free(AVFrame **frame)
Free the frame and any dynamically allocated objects in it, e.g.
Definition: frame.c:64
AV_PIX_FMT_YUVA444P10BE
@ AV_PIX_FMT_YUVA444P10BE
planar YUV 4:4:4 40bpp, (1 Cr & Cb sample per 1x1 Y & A samples, big-endian)
Definition: pixfmt.h:185
pixdesc.h
RV_IDX
#define RV_IDX
Definition: swscale_internal.h:475
alphaless_fmt
static enum AVPixelFormat alphaless_fmt(enum AVPixelFormat fmt)
Definition: utils.c:1071
AV_PIX_FMT_RGBA64BE
@ AV_PIX_FMT_RGBA64BE
packed RGBA 16:16:16:16, 64bpp, 16R, 16G, 16B, 16A, the 2-byte value for each R/G/B/A component is st...
Definition: pixfmt.h:202
AV_PIX_FMT_GBRAPF32LE
@ AV_PIX_FMT_GBRAPF32LE
IEEE-754 single precision planar GBRA 4:4:4:4, 128bpp, little-endian.
Definition: pixfmt.h:344
SWS_DITHER_NONE
@ SWS_DITHER_NONE
Definition: swscale.h:80
isGray
static av_always_inline int isGray(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:807
SWSINTERNAL_ADDITIONAL_ASM_SIZE
#define SWSINTERNAL_ADDITIONAL_ASM_SIZE
Definition: swscale_internal.h:47
RU_IDX
#define RU_IDX
Definition: swscale_internal.h:472
AV_PIX_FMT_GBRPF32BE
@ AV_PIX_FMT_GBRPF32BE
IEEE-754 single precision planar GBR 4:4:4, 96bpp, big-endian.
Definition: pixfmt.h:341
AVComponentDescriptor::depth
int depth
Number of bits in the component.
Definition: pixdesc.h:57
SWS_BILINEAR
@ SWS_BILINEAR
bilinear filtering
Definition: swscale.h:200
SWS_BITEXACT
@ SWS_BITEXACT
Definition: swscale.h:180
b
#define b
Definition: input.c:43
table
static const uint16_t table[]
Definition: prosumer.c:203
GV_IDX
#define GV_IDX
Definition: swscale_internal.h:476
BV_IDX
#define BV_IDX
Definition: swscale_internal.h:477
AV_PIX_FMT_YUV420P10
#define AV_PIX_FMT_YUV420P10
Definition: pixfmt.h:539
SwsContext::flags
unsigned flags
Bitmask of SWS_*.
Definition: swscale.h:242
AV_LOG_VERBOSE
#define AV_LOG_VERBOSE
Detailed information.
Definition: log.h:226
filter
void(* filter)(uint8_t *src, int stride, int qscale)
Definition: h263dsp.c:29
AV_PIX_FMT_GBRP14BE
@ AV_PIX_FMT_GBRP14BE
planar GBR 4:4:4 42bpp, big-endian
Definition: pixfmt.h:281
AV_PIX_FMT_BGR24
@ AV_PIX_FMT_BGR24
packed RGB 8:8:8, 24bpp, BGRBGR...
Definition: pixfmt.h:76
AV_PIX_FMT_BGRA
@ AV_PIX_FMT_BGRA
packed BGRA 8:8:8:8, 32bpp, BGRABGRA...
Definition: pixfmt.h:102
av_get_bits_per_pixel
int av_get_bits_per_pixel(const AVPixFmtDescriptor *pixdesc)
Return the number of bits per pixel used by the pixel format described by pixdesc.
Definition: pixdesc.c:3408
AV_PIX_FMT_YUV440P
@ AV_PIX_FMT_YUV440P
planar YUV 4:4:0 (1 Cr & Cb sample per 1x2 Y samples)
Definition: pixfmt.h:106
max
#define max(a, b)
Definition: cuda_runtime.h:33
mathematics.h
FFMAX
#define FFMAX(a, b)
Definition: macros.h:47
AV_PIX_FMT_YUVA444P9BE
@ AV_PIX_FMT_YUVA444P9BE
planar YUV 4:4:4 36bpp, (1 Cr & Cb sample per 1x1 Y & A samples), big-endian
Definition: pixfmt.h:179
sws_getShiftedVec
static SwsVector * sws_getShiftedVec(SwsVector *a, int shift)
Definition: utils.c:2117
AVERROR_UNKNOWN
#define AVERROR_UNKNOWN
Unknown error, typically from an external library.
Definition: error.h:73
SWS_BICUBLIN
@ SWS_BICUBLIN
bicubic luma, bilinear chroma
Definition: swscale.h:205
AV_PIX_FMT_GRAY10LE
@ AV_PIX_FMT_GRAY10LE
Y , 10bpp, little-endian.
Definition: pixfmt.h:321
AV_PIX_FMT_GBRAP14BE
@ AV_PIX_FMT_GBRAP14BE
planar GBR 4:4:4:4 56bpp, big-endian
Definition: pixfmt.h:432
SWS_ALPHA_BLEND_NONE
@ SWS_ALPHA_BLEND_NONE
Definition: swscale.h:89
cpu.h
scaler_flag
static int scaler_flag(SwsScaler scaler, int fallback)
Definition: utils.c:1132
quality
trying all byte sequences megabyte in length and selecting the best looking sequence will yield cases to try But a word about quality
Definition: rate_distortion.txt:12
sws_freeVec
void sws_freeVec(SwsVector *a)
Definition: utils.c:2193
isnan_vec
static int isnan_vec(SwsVector *a)
Definition: utils.c:1987
AV_PIX_FMT_GBRAP12LE
@ AV_PIX_FMT_GBRAP12LE
planar GBR 4:4:4:4 48bpp, little-endian
Definition: pixfmt.h:311
SWS_FAST_BILINEAR
@ SWS_FAST_BILINEAR
Scaler selection options.
Definition: swscale.h:199
initFilter
static av_cold int initFilter(int16_t **outFilter, int32_t **filterPos, int *outFilterSize, int xInc, int srcW, int dstW, int filterAlign, int one, int scaler, int flags, int cpu_flags, SwsVector *srcFilter, SwsVector *dstFilter, double param[SWS_NUM_SCALER_PARAMS], int srcPos, int dstPos)
Definition: utils.c:208
ff_sws_fill_xyztables
av_cold int ff_sws_fill_xyztables(SwsInternal *c)
Definition: utils.c:746
AV_PIX_FMT_GRAY16BE
@ AV_PIX_FMT_GRAY16BE
Y , 16bpp, big-endian.
Definition: pixfmt.h:104
is16BPS
static av_always_inline int is16BPS(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:747
ub
#define ub(width, name)
Definition: cbs_apv.c:125
AV_PIX_FMT_GBRP14
#define AV_PIX_FMT_GBRP14
Definition: pixfmt.h:560
AV_PIX_FMT_GBRAP
@ AV_PIX_FMT_GBRAP
planar GBRA 4:4:4:4 32bpp
Definition: pixfmt.h:212
SWS_FULL_CHR_H_INP
@ SWS_FULL_CHR_H_INP
Perform full chroma interpolation when downscaling RGB sources.
Definition: swscale.h:169
avpriv_slicethread_create
int avpriv_slicethread_create(AVSliceThread **pctx, void *priv, void(*worker_func)(void *priv, int jobnr, int threadnr, int nb_jobs, int nb_threads), void(*main_func)(void *priv), int nb_threads)
Create slice threading context.
Definition: slicethread.c:261
SwsContext::src_v_chr_pos
int src_v_chr_pos
Source vertical chroma position in luma grid / 256.
Definition: swscale.h:282
AV_PIX_FMT_GBRP10
#define AV_PIX_FMT_GBRP10
Definition: pixfmt.h:558
Range::len
unsigned int len
Definition: swscale_internal.h:88
ONE
@ ONE
Definition: vc1_parser.c:50
AV_PIX_FMT_YUV422P9
#define AV_PIX_FMT_YUV422P9
Definition: pixfmt.h:537
sws_getCachedContext
SwsContext * sws_getCachedContext(SwsContext *prev, int srcW, int srcH, enum AVPixelFormat srcFormat, int dstW, int dstH, enum AVPixelFormat dstFormat, int flags, SwsFilter *srcFilter, SwsFilter *dstFilter, const double *param)
Check if context can be reused, otherwise reallocate a new one.
Definition: utils.c:2391
AV_PIX_FMT_GRAY9LE
@ AV_PIX_FMT_GRAY9LE
Y , 9bpp, little-endian.
Definition: pixfmt.h:339
sws_init_context
av_cold int sws_init_context(SwsContext *sws, SwsFilter *srcFilter, SwsFilter *dstFilter)
Initialize the swscaler context sws_context.
Definition: utils.c:1931
ff_sws_alphablendaway
int ff_sws_alphablendaway(SwsInternal *c, const uint8_t *const src[], const int srcStride[], int srcSliceY, int srcSliceH, uint8_t *const dst[], const int dstStride[])
Definition: alphablend.c:23
av_pix_fmt_get_chroma_sub_sample
int av_pix_fmt_get_chroma_sub_sample(enum AVPixelFormat pix_fmt, int *h_shift, int *v_shift)
Utility function to access log2_chroma_w log2_chroma_h from the pixel format AVPixFmtDescriptor.
Definition: pixdesc.c:3484
isNBPS
static av_always_inline int isNBPS(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:761
FF_ALLOC_TYPED_ARRAY
#define FF_ALLOC_TYPED_ARRAY(p, nelem)
Definition: internal.h:77
AV_PIX_FMT_GRAY16
#define AV_PIX_FMT_GRAY16
Definition: pixfmt.h:522
SWS_DITHER_X_DITHER
@ SWS_DITHER_X_DITHER
Definition: swscale.h:85
AV_PIX_FMT_YUVA444P16BE
@ AV_PIX_FMT_YUVA444P16BE
planar YUV 4:4:4 64bpp, (1 Cr & Cb sample per 1x1 Y & A samples, big-endian)
Definition: pixfmt.h:191
xyzgammainv_tab
static uint16_t xyzgammainv_tab[65536]
Definition: utils.c:724
refstruct.h
av_frame_alloc
AVFrame * av_frame_alloc(void)
Allocate an AVFrame and set its fields to default values.
Definition: frame.c:52
AV_PIX_FMT_YUV444P10
#define AV_PIX_FMT_YUV444P10
Definition: pixfmt.h:542
AV_PIX_FMT_YUVJ411P
@ AV_PIX_FMT_YUVJ411P
planar YUV 4:1:1, 12bpp, (1 Cr & Cb sample per 4x1 Y samples) full scale (JPEG), deprecated in favor ...
Definition: pixfmt.h:283
SwsBackend
SwsBackend
Definition: swscale.h:110
C
s EdgeDetect Foobar g libavfilter vf_edgedetect c libavfilter vf_foobar c edit libavfilter and add an entry for foobar following the pattern of the other filters edit libavfilter allfilters and add an entry for foobar following the pattern of the other filters configure make j< whatever > ffmpeg ffmpeg i you should get a foobar png with Lena edge detected That s your new playground is ready Some little details about what s going which in turn will define variables for the build system and the C
Definition: writing_filters.txt:58
SWS_SCALE_BICUBIC
@ SWS_SCALE_BICUBIC
2-tap cubic BC-spline
Definition: swscale.h:99
AV_PIX_FMT_BGR8
@ AV_PIX_FMT_BGR8
packed RGB 3:3:2, 8bpp, (msb)2B 3G 3R(lsb)
Definition: pixfmt.h:90
avassert.h
ceil
static __device__ float ceil(float a)
Definition: cuda_runtime.h:176
lrint
#define lrint
Definition: tablegen.h:53
handle_jpeg
static int handle_jpeg(int *format)
Definition: utils.c:784
ff_thread_once
static int ff_thread_once(char *control, void(*routine)(void))
Definition: thread.h:205
AV_LOG_ERROR
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:210
SWS_AREA
@ SWS_AREA
area averaging
Definition: swscale.h:204
FF_ARRAY_ELEMS
#define FF_ARRAY_ELEMS(a)
Definition: sinewin_tablegen.c:29
AV_PIX_FMT_YUV422P16
#define AV_PIX_FMT_YUV422P16
Definition: pixfmt.h:551
SwsContext::dither
SwsDither dither
Dither mode.
Definition: swscale.h:258
AV_PIX_FMT_YUVJ422P
@ AV_PIX_FMT_YUVJ422P
planar YUV 4:2:2, 16bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV422P and setting col...
Definition: pixfmt.h:86
SWS_MAX_REDUCE_CUTOFF
#define SWS_MAX_REDUCE_CUTOFF
Filter kernel cut-off value.
Definition: swscale.h:449
emms_c
#define emms_c()
Definition: emms.h:89
float
float
Definition: af_crystalizer.c:122
ff_range_add
int ff_range_add(RangeList *rl, unsigned int start, unsigned int len)
Definition: utils.c:2444
AV_PIX_FMT_GBRAP16BE
@ AV_PIX_FMT_GBRAP16BE
planar GBRA 4:4:4:4 64bpp, big-endian
Definition: pixfmt.h:213
sws_printVec2
static void sws_printVec2(SwsVector *a, AVClass *log_ctx, int log_level)
Print with av_log() a textual representation of the vector a if log_level <= av_log_level.
Definition: utils.c:2167
av_fast_realloc
void * av_fast_realloc(void *ptr, unsigned int *size, size_t min_size)
Reallocate the given buffer if it is not large enough, otherwise do nothing.
Definition: mem.c:497
W
#define W(a, i, v)
Definition: jpegls.h:119
intreadwrite.h
s
#define s(width, name)
Definition: cbs_vp9.c:198
AV_PIX_FMT_GBRP16LE
@ AV_PIX_FMT_GBRP16LE
planar GBR 4:4:4 48bpp, little-endian
Definition: pixfmt.h:172
AV_PIX_FMT_YUVA420P
@ AV_PIX_FMT_YUVA420P
planar YUV 4:2:0, 20bpp, (1 Cr & Cb sample per 2x2 Y & A samples)
Definition: pixfmt.h:108
SwsContext::threads
int threads
How many threads to use for processing, or 0 for automatic selection.
Definition: swscale.h:253
AV_PIX_FMT_YUV444P16
#define AV_PIX_FMT_YUV444P16
Definition: pixfmt.h:552
AV_CEIL_RSHIFT
#define AV_CEIL_RSHIFT(a, b)
Definition: common.h:60
SWS_SCALE_LANCZOS
@ SWS_SCALE_LANCZOS
3-tap sinc/sinc
Definition: swscale.h:104
height
static int height
Definition: utils.c:158
AVFormatContext::flags
int flags
Flags modifying the (de)muxer behaviour.
Definition: avformat.h:1465
SwsVector::length
int length
number of coefficients in the vector
Definition: swscale.h:482
ops.h
sws_allocVec
SwsVector * sws_allocVec(int length)
Allocate and return an uninitialized vector with length coefficients.
Definition: utils.c:2003
cpu.h
SWS_DITHER_BAYER
@ SWS_DITHER_BAYER
Definition: swscale.h:82
from
const char * from
Definition: jacosubdec.c:64
AV_PIX_FMT_GBRP12LE
@ AV_PIX_FMT_GBRP12LE
planar GBR 4:4:4 36bpp, little-endian
Definition: pixfmt.h:280
av_assert0
#define av_assert0(cond)
assert() equivalent, that is always enabled.
Definition: avassert.h:42
ff_yuv2rgb_c_init_tables
int ff_yuv2rgb_c_init_tables(SwsInternal *c, const int inv_table[4], int fullRange, int brightness, int contrast, int saturation)
B
#define B
Definition: huffyuv.h:42
av_get_cpu_flags
int av_get_cpu_flags(void)
Return the flags which specify extensions supported by the CPU.
Definition: cpu.c:109
AV_PIX_FMT_YUV420P9
#define AV_PIX_FMT_YUV420P9
Definition: pixfmt.h:536
AV_PIX_FMT_YUVA420P16BE
@ AV_PIX_FMT_YUVA420P16BE
planar YUV 4:2:0 40bpp, (1 Cr & Cb sample per 2x2 Y & A samples, big-endian)
Definition: pixfmt.h:187
AV_LOG_DEBUG
#define AV_LOG_DEBUG
Stuff which is only useful for libav* developers.
Definition: log.h:231
ff_sws_enabled_backends
SwsBackend ff_sws_enabled_backends(const SwsContext *ctx)
Definition: utils.c:71
AV_PIX_FMT_YUV420P16
#define AV_PIX_FMT_YUV420P16
Definition: pixfmt.h:550
ff_get_unscaled_swscale
void ff_get_unscaled_swscale(SwsInternal *c)
Set c->convert_unscaled to an unscaled converter if one exists for the specific source and destinatio...
Definition: swscale_unscaled.c:2392
ff_yuv2rgb_init_tables_ppc
av_cold void ff_yuv2rgb_init_tables_ppc(SwsInternal *c, const int inv_table[4], int brightness, int contrast, int saturation)
Definition: yuv2rgb_altivec.c:638
ctx
static AVFormatContext * ctx
Definition: movenc.c:49
scale_algorithms
static const ScaleAlgorithm scale_algorithms[]
Definition: utils.c:194
ScaleAlgorithm::flag
int flag
flag associated to the algorithm
Definition: utils.c:189
AV_PIX_FMT_RGB4
@ AV_PIX_FMT_RGB4
packed RGB 1:2:1 bitstream, 4bpp, (msb)1R 2G 1B(lsb), a byte contains two pixels, the first pixel in ...
Definition: pixfmt.h:94
AV_PIX_FMT_GBRP10LE
@ AV_PIX_FMT_GBRP10LE
planar GBR 4:4:4 30bpp, little-endian
Definition: pixfmt.h:170
AV_PIX_FMT_YUV420P
@ AV_PIX_FMT_YUV420P
planar YUV 4:2:0, 12bpp, (1 Cr & Cb sample per 2x2 Y samples)
Definition: pixfmt.h:73
sws_getGaussianVec
SwsVector * sws_getGaussianVec(double variance, double quality)
Return a normalized Gaussian curve used to filter stuff quality = 3 is high quality,...
Definition: utils.c:2020
av_mallocz
#define av_mallocz(s)
Definition: tableprint_vlc.h:31
AV_PIX_FMT_GBRAPF16LE
@ AV_PIX_FMT_GBRAPF16LE
IEEE-754 half precision planar GBRA 4:4:4:4, 64bpp, little-endian.
Definition: pixfmt.h:469
AV_PIX_FMT_GRAYF32
#define AV_PIX_FMT_GRAYF32
Definition: pixfmt.h:582
GY_IDX
#define GY_IDX
Definition: swscale_internal.h:470
NAN
#define NAN
Definition: mathematics.h:115
tmp
static uint8_t tmp[40]
Definition: aes_ctr.c:52
AV_PIX_FMT_RGBA
@ AV_PIX_FMT_RGBA
packed RGBA 8:8:8:8, 32bpp, RGBARGBA...
Definition: pixfmt.h:100
AV_PIX_FMT_YUVJ444P
@ AV_PIX_FMT_YUVJ444P
planar YUV 4:4:4, 24bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV444P and setting col...
Definition: pixfmt.h:87
ff_init_hscaler_mmxext
int ff_init_hscaler_mmxext(int dstW, int xInc, uint8_t *filterCode, int16_t *filter, int32_t *filterPos, int numSplits)
Definition: hscale_fast_bilinear_simd.c:30
AV_PIX_FMT_YUVA422P10LE
@ AV_PIX_FMT_YUVA422P10LE
planar YUV 4:2:2 30bpp, (1 Cr & Cb sample per 2x1 Y & A samples, little-endian)
Definition: pixfmt.h:184
FFABS
#define FFABS(a)
Absolute value, Note, INT_MIN / INT64_MIN result in undefined behavior as they are not representable ...
Definition: common.h:74
if
if(ret)
Definition: filter_design.txt:179
AV_PIX_FMT_GBRP10MSBLE
@ AV_PIX_FMT_GBRP10MSBLE
planar GBR 4:4:4 30bpp, lowest bits zero, little-endian
Definition: pixfmt.h:496
fail
#define fail
Definition: test.h:478
alloc_gamma_tbl
static uint16_t * alloc_gamma_tbl(double e)
Definition: utils.c:1057
AV_PIX_FMT_GBRP16
#define AV_PIX_FMT_GBRP16
Definition: pixfmt.h:561
AV_ONCE_INIT
#define AV_ONCE_INIT
Definition: thread.h:203
SWS_SRC_V_CHR_DROP_SHIFT
#define SWS_SRC_V_CHR_DROP_SHIFT
Definition: swscale.h:456
AVClass
Describe the class of an AVClass context structure.
Definition: log.h:76
ff_free_filters
int ff_free_filters(SwsInternal *c)
Definition: slice.c:386
AV_PIX_FMT_GBRAPF32BE
@ AV_PIX_FMT_GBRAPF32BE
IEEE-754 single precision planar GBRA 4:4:4:4, 128bpp, big-endian.
Definition: pixfmt.h:343
AV_PIX_FMT_GBRAP12BE
@ AV_PIX_FMT_GBRAP12BE
planar GBR 4:4:4:4 48bpp, big-endian
Definition: pixfmt.h:310
AV_PIX_FMT_BGR48
#define AV_PIX_FMT_BGR48
Definition: pixfmt.h:530
NULL
#define NULL
Definition: coverity.c:32
RETCODE_USE_CASCADE
#define RETCODE_USE_CASCADE
Definition: swscale_internal.h:75
SWS_BACKEND_STABLE
@ SWS_BACKEND_STABLE
Definition: swscale.h:113
AVERROR_PATCHWELCOME
#define AVERROR_PATCHWELCOME
Not yet implemented in FFmpeg, patches welcome.
Definition: error.h:64
format
New swscale design to change SwsGraph is what coordinates multiple passes These can include cascaded scaling error diffusion and so on Or we could have separate passes for the vertical and horizontal scaling In between each SwsPass lies a fully allocated image buffer Graph passes may have different levels of e g we can have a single threaded error diffusion pass following a multi threaded scaling pass SwsGraph is internally recreated whenever the image format
Definition: swscale-v2.txt:14
AV_PIX_FMT_GBRAPF16BE
@ AV_PIX_FMT_GBRAPF16BE
IEEE-754 half precision planar GBRA 4:4:4:4, 64bpp, big-endian.
Definition: pixfmt.h:468
asm.h
SWS_BICUBIC
@ SWS_BICUBIC
2-tap cubic B-spline
Definition: swscale.h:201
SwsContext::gamma_flag
int gamma_flag
Use gamma correct scaling.
Definition: swscale.h:268
isnan
#define isnan(x)
Definition: libm.h:342
AV_PIX_FMT_RGB48LE
@ AV_PIX_FMT_RGB48LE
packed RGB 16:16:16, 48bpp, 16R, 16G, 16B, the 2-byte value for each R/G/B component is stored as lit...
Definition: pixfmt.h:110
AV_PIX_FMT_YA16LE
@ AV_PIX_FMT_YA16LE
16 bits gray, 16 bits alpha (little-endian)
Definition: pixfmt.h:210
AV_PIX_FMT_YUVJ420P
@ AV_PIX_FMT_YUVJ420P
planar YUV 4:2:0, 12bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV420P and setting col...
Definition: pixfmt.h:85
sws_getDefaultFilter
SwsFilter * sws_getDefaultFilter(float lumaGBlur, float chromaGBlur, float lumaSharpen, float chromaSharpen, float chromaHShift, float chromaVShift, int verbose)
Definition: utils.c:2214
EXTERNAL_AVX2_FAST
#define EXTERNAL_AVX2_FAST(flags)
Definition: cpu.h:73
RangeList
Definition: swscale_internal.h:91
ROUNDED_DIV
#define ROUNDED_DIV(a, b)
Definition: common.h:58
V
#define V
Definition: avdct.c:32
rgbgamma_tab
static uint16_t rgbgamma_tab[65536]
Definition: utils.c:724
AV_PIX_FMT_RGBA64LE
@ AV_PIX_FMT_RGBA64LE
packed RGBA 16:16:16:16, 64bpp, 16R, 16G, 16B, 16A, the 2-byte value for each R/G/B/A component is st...
Definition: pixfmt.h:203
RangeList::nb_ranges
unsigned int nb_ranges
Definition: swscale_internal.h:93
makenan_vec
static void makenan_vec(SwsVector *a)
Definition: utils.c:1996
AV_PIX_FMT_YUVA444P9LE
@ AV_PIX_FMT_YUVA444P9LE
planar YUV 4:4:4 36bpp, (1 Cr & Cb sample per 1x1 Y & A samples), little-endian
Definition: pixfmt.h:180
SwsContext::src_range
int src_range
Source is full range.
Definition: swscale.h:280
AV_PIX_FMT_YUVA420P16LE
@ AV_PIX_FMT_YUVA420P16LE
planar YUV 4:2:0 40bpp, (1 Cr & Cb sample per 2x2 Y & A samples, little-endian)
Definition: pixfmt.h:188
SwsScaler
SwsScaler
Definition: swscale.h:96
AV_PIX_FMT_RGB8
@ AV_PIX_FMT_RGB8
packed RGB 3:3:2, 8bpp, (msb)3R 3G 2B(lsb)
Definition: pixfmt.h:93
AV_PIX_FMT_BGR0
@ AV_PIX_FMT_BGR0
packed BGR 8:8:8, 32bpp, BGRXBGRX... X=unused/undefined
Definition: pixfmt.h:265
ff_sws_rgb2rgb_init
av_cold void ff_sws_rgb2rgb_init(void)
Definition: rgb2rgb.c:127
AV_PIX_FMT_BGR4
@ AV_PIX_FMT_BGR4
packed RGB 1:2:1 bitstream, 4bpp, (msb)1B 2G 1R(lsb), a byte contains two pixels, the first pixel in ...
Definition: pixfmt.h:91
attributes.h
AV_PIX_FMT_YUV422P10
#define AV_PIX_FMT_YUV422P10
Definition: pixfmt.h:540
ff_sws_init_range_convert
av_cold void ff_sws_init_range_convert(SwsInternal *c)
Definition: swscale.c:626
sws_addVec
static void sws_addVec(SwsVector *a, SwsVector *b)
Definition: utils.c:2149
SwsVector::coeff
double * coeff
pointer to the list of coefficients
Definition: swscale.h:481
AV_PIX_FMT_GRAY8
@ AV_PIX_FMT_GRAY8
Y , 8bpp.
Definition: pixfmt.h:81
range_override_needed
static int range_override_needed(enum AVPixelFormat format)
Definition: utils.c:855
AV_PIX_FMT_YUVA420P9LE
@ AV_PIX_FMT_YUVA420P9LE
planar YUV 4:2:0 22.5bpp, (1 Cr & Cb sample per 2x2 Y & A samples), little-endian
Definition: pixfmt.h:176
AV_PIX_FMT_GBRP12MSBLE
@ AV_PIX_FMT_GBRP12MSBLE
planar GBR 4:4:4 36bpp, lowest bits zero, little-endian
Definition: pixfmt.h:498
ff_sws_context_class
const AVClass ff_sws_context_class
Definition: options.c:125
exp
int8_t exp
Definition: eval.c:76
have_neon
#define have_neon(flags)
Definition: cpu.h:26
AV_PIX_FMT_ABGR
@ AV_PIX_FMT_ABGR
packed ABGR 8:8:8:8, 32bpp, ABGRABGR...
Definition: pixfmt.h:101
AVOnce
#define AVOnce
Definition: thread.h:202
SwsContext::dst_h_chr_pos
int dst_h_chr_pos
Destination horizontal chroma position.
Definition: swscale.h:285
Range
Definition: vf_colorbalance.c:37
sws_scaleVec
void sws_scaleVec(SwsVector *a, double scalar)
Scale all the coefficients of a by the scalar value.
Definition: utils.c:2086
c
Undefined Behavior In the C some operations are like signed integer dereferencing freed accessing outside allocated Undefined Behavior must not occur in a C it is not safe even if the output of undefined operations is unused The unsafety may seem nit picking but Optimizing compilers have in fact optimized code on the assumption that no undefined Behavior occurs Optimizing code based on wrong assumptions can and has in some cases lead to effects beyond the output of computations The signed integer overflow problem in speed critical code Code which is highly optimized and works with signed integers sometimes has the problem that often the output of the computation does not c
Definition: undefined.txt:32
sws_getConstVec
static SwsVector * sws_getConstVec(double c, int length)
Allocate and return a vector with length coefficients, all with the same value c.
Definition: utils.c:2051
AV_PIX_FMT_BGR4_BYTE
@ AV_PIX_FMT_BGR4_BYTE
packed RGB 1:2:1, 8bpp, (msb)1B 2G 1R(lsb)
Definition: pixfmt.h:92
av_opt_copy
int av_opt_copy(void *dst, const void *src)
Copy options from src object into dest object.
Definition: opt.c:2145
SWS_SCALE_SINC
@ SWS_SCALE_SINC
unwindowed sinc
Definition: swscale.h:103
AV_PIX_FMT_X2RGB10LE
@ AV_PIX_FMT_X2RGB10LE
packed RGB 10:10:10, 30bpp, (msb)2X 10R 10G 10B(lsb), little-endian, X=unused/undefined
Definition: pixfmt.h:384
SWS_PARAM_DEFAULT
#define SWS_PARAM_DEFAULT
Definition: swscale.h:458
av_image_alloc
int av_image_alloc(uint8_t *pointers[4], int linesizes[4], int w, int h, enum AVPixelFormat pix_fmt, int align)
Allocate an image with size w and h and pixel format pix_fmt, and fill pointers and linesizes accordi...
Definition: imgutils.c:218
ff_sws_graph_free
void ff_sws_graph_free(SwsGraph **pgraph)
Uninitialize any state associate with this filter graph and free it.
Definition: graph.c:916
ff_sws_slice_worker
void ff_sws_slice_worker(void *priv, int jobnr, int threadnr, int nb_jobs, int nb_threads)
Definition: swscale.c:1605
handle_0alpha
static int handle_0alpha(int *format)
Definition: utils.c:822
SwsFilter::chrV
SwsVector * chrV
Definition: swscale.h:490
f
f
Definition: af_crystalizer.c:122
AV_PIX_FMT_RGB24
@ AV_PIX_FMT_RGB24
packed RGB 8:8:8, 24bpp, RGBRGB...
Definition: pixfmt.h:75
RY_IDX
#define RY_IDX
Definition: swscale_internal.h:469
SwsInternal::parent
SwsContext * parent
Definition: swscale_internal.h:342
to
const char * to
Definition: webvttdec.c:35
AV_PIX_FMT_GBRP10MSBBE
@ AV_PIX_FMT_GBRP10MSBBE
planar GBR 4:4:4 30bpp, lowest bits zero, big-endian
Definition: pixfmt.h:495
sws_alloc_context
SwsContext * sws_alloc_context(void)
Allocate an empty SwsContext and set its fields to default values.
Definition: utils.c:1043
SwsVector
Definition: swscale.h:480
shift
static int shift(int a, int b)
Definition: bonk.c:261
ff_sws_init_single_context
av_cold int ff_sws_init_single_context(SwsContext *sws, SwsFilter *srcFilter, SwsFilter *dstFilter)
Definition: utils.c:1148
i
#define i(width, name, range_min, range_max)
Definition: cbs_h264.c:63
isAnyRGB
static av_always_inline int isAnyRGB(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:876
AV_PIX_FMT_RGB444BE
@ AV_PIX_FMT_RGB444BE
packed RGB 4:4:4, 16bpp, (msb)4X 4R 4G 4B(lsb), big-endian, X=unused/undefined
Definition: pixfmt.h:137
for
for(k=2;k<=8;++k)
Definition: h264pred_template.c:424
AV_PIX_FMT_YA16BE
@ AV_PIX_FMT_YA16BE
16 bits gray, 16 bits alpha (big-endian)
Definition: pixfmt.h:209
AV_PIX_FMT_RGB48
#define AV_PIX_FMT_RGB48
Definition: pixfmt.h:525
SWS_POINT
@ SWS_POINT
nearest neighbor
Definition: swscale.h:203
SwsContext::alpha_blend
SwsAlphaBlend alpha_blend
Alpha blending mode.
Definition: swscale.h:263
AV_PIX_FMT_GRAY12LE
@ AV_PIX_FMT_GRAY12LE
Y , 12bpp, little-endian.
Definition: pixfmt.h:319
AV_PIX_FMT_BGR555
#define AV_PIX_FMT_BGR555
Definition: pixfmt.h:532
SWS_SPLINE
@ SWS_SPLINE
unwindowed natural cubic spline
Definition: swscale.h:209
isYUV
static av_always_inline int isYUV(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:775
SwsContext::src_h
int src_h
Width and height of the source frame.
Definition: swscale.h:276
AV_PIX_FMT_GBRP9BE
@ AV_PIX_FMT_GBRP9BE
planar GBR 4:4:4 27bpp, big-endian
Definition: pixfmt.h:167
AV_PIX_FMT_GBRP12MSBBE
@ AV_PIX_FMT_GBRP12MSBBE
planar GBR 4:4:4 36bpp, lowest bits zero, big-endian
Definition: pixfmt.h:497
range
enum AVColorRange range
Definition: mediacodec_wrapper.c:2594
ff_shuffle_filter_coefficients
int ff_shuffle_filter_coefficients(SwsInternal *c, int *filterPos, int filterSize, int16_t *filter, int dstW)
Definition: utils.c:108
sws_getColorspaceDetails
int sws_getColorspaceDetails(SwsContext *sws, int **inv_table, int *srcRange, int **table, int *dstRange, int *brightness, int *contrast, int *saturation)
Definition: utils.c:1018
AV_PIX_FMT_BGR444BE
@ AV_PIX_FMT_BGR444BE
packed BGR 4:4:4, 16bpp, (msb)4X 4B 4G 4R(lsb), big-endian, X=unused/undefined
Definition: pixfmt.h:139
AV_PIX_FMT_GBRP9LE
@ AV_PIX_FMT_GBRP9LE
planar GBR 4:4:4 27bpp, little-endian
Definition: pixfmt.h:168
have_lsx
#define have_lsx(flags)
Definition: cpu.h:28
SwsFilter
Definition: swscale.h:486
AV_WL16
#define AV_WL16(p, v)
Definition: intreadwrite.h:408
cpu_flags
CheckasmCpu cpu_flags
Definition: checkasm.c:84
a
The reader does not expect b to be semantically here and if the code is changed by maybe adding a a division or other the signedness will almost certainly be mistaken To avoid this confusion a new type was SUINT is the C unsigned type but it holds a signed int to use the same example SUINT a
Definition: undefined.txt:41
AV_PIX_FMT_YUVA444P
@ AV_PIX_FMT_YUVA444P
planar YUV 4:4:4 32bpp, (1 Cr & Cb sample per 1x1 Y & A samples)
Definition: pixfmt.h:174
AV_PIX_FMT_GBRAP10LE
@ AV_PIX_FMT_GBRAP10LE
planar GBR 4:4:4:4 40bpp, little-endian
Definition: pixfmt.h:314
csp.h
SwsFilter::lumV
SwsVector * lumV
Definition: swscale.h:488
have_lasx
#define have_lasx(flags)
Definition: cpu.h:29
AV_PIX_FMT_RGB0
@ AV_PIX_FMT_RGB0
packed RGB 8:8:8, 32bpp, RGBXRGBX... X=unused/undefined
Definition: pixfmt.h:263
SwsContext::dst_format
int dst_format
Destination pixel format.
Definition: swscale.h:279
sws_isSupportedInput
#define sws_isSupportedInput(x)
AV_PIX_FMT_YUVA420P10LE
@ AV_PIX_FMT_YUVA420P10LE
planar YUV 4:2:0 25bpp, (1 Cr & Cb sample per 2x2 Y & A samples, little-endian)
Definition: pixfmt.h:182
M_PI
#define M_PI
Definition: mathematics.h:67
slicethread.h
AV_LOG_INFO
#define AV_LOG_INFO
Standard information.
Definition: log.h:221
BY_IDX
#define BY_IDX
Definition: swscale_internal.h:471
ff_frame_pool_uninit
av_cold void ff_frame_pool_uninit(FFFramePool *pool)
Deallocate the frame pool.
Definition: framepool.c:215
av_refstruct_unref
void av_refstruct_unref(void *objp)
Decrement the reference count of the underlying object and automatically free the object if there are...
Definition: refstruct.c:120
AV_PIX_FMT_ARGB
@ AV_PIX_FMT_ARGB
packed ARGB 8:8:8:8, 32bpp, ARGBARGB...
Definition: pixfmt.h:99
AV_PIX_FMT_BGRA64LE
@ AV_PIX_FMT_BGRA64LE
packed RGBA 16:16:16:16, 64bpp, 16B, 16G, 16R, 16A, the 2-byte value for each R/G/B/A component is st...
Definition: pixfmt.h:205
AV_PIX_FMT_YUVA422P10BE
@ AV_PIX_FMT_YUVA422P10BE
planar YUV 4:2:2 30bpp, (1 Cr & Cb sample per 2x1 Y & A samples, big-endian)
Definition: pixfmt.h:183
handle_xyz
static int handle_xyz(int *format)
Definition: utils.c:833
emms.h
AV_PIX_FMT_YUVA422P9BE
@ AV_PIX_FMT_YUVA422P9BE
planar YUV 4:2:2 27bpp, (1 Cr & Cb sample per 2x1 Y & A samples), big-endian
Definition: pixfmt.h:177
SWS_SCALE_POINT
@ SWS_SCALE_POINT
nearest neighbor (point sampling)
Definition: swscale.h:100
av_assert2
#define av_assert2(cond)
assert() equivalent, that does lie in speed critical code.
Definition: avassert.h:68
AV_PIX_FMT_BGRA64
#define AV_PIX_FMT_BGRA64
Definition: pixfmt.h:534
sws_isSupportedEndiannessConversion
int sws_isSupportedEndiannessConversion(enum AVPixelFormat pix_fmt)
Definition: format.c:303
AV_PIX_FMT_RGB48BE
@ AV_PIX_FMT_RGB48BE
packed RGB 16:16:16, 48bpp, 16R, 16G, 16B, the 2-byte value for each R/G/B component is stored as big...
Definition: pixfmt.h:109
ff_yuv2rgb_coeffs
const int32_t ff_yuv2rgb_coeffs[11][4]
Definition: yuv2rgb.c:47
av_malloc
#define av_malloc(s)
Definition: ops_asmgen.c:44
sws_shiftVec
static void sws_shiftVec(SwsVector *a, int shift)
Definition: utils.c:2135
SWS_X
@ SWS_X
experimental
Definition: swscale.h:202
ff_sws_init_scale
void ff_sws_init_scale(SwsInternal *c)
Definition: swscale.c:697
AV_PIX_FMT_GBRP12
#define AV_PIX_FMT_GBRP12
Definition: pixfmt.h:559
av_malloc_array
#define av_malloc_array(a, b)
Definition: tableprint_vlc.h:32
AV_PIX_FMT_GRAY9BE
@ AV_PIX_FMT_GRAY9BE
Y , 9bpp, big-endian.
Definition: pixfmt.h:338
SwsContext::scaler
SwsScaler scaler
Scaling filter.
Definition: swscale.h:298
exp2
#define exp2(x)
Definition: libm.h:290
getSplineCoeff
static double getSplineCoeff(double a, double b, double c, double d, double dist)
Definition: utils.c:166
swscale_internal.h
graph.h
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
INLINE_MMX
#define INLINE_MMX(flags)
Definition: cpu.h:80
AV_PIX_FMT_YUVJ440P
@ AV_PIX_FMT_YUVJ440P
planar YUV 4:4:0 full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV440P and setting color_range
Definition: pixfmt.h:107
AV_PIX_FMT_XYZ12BE
@ AV_PIX_FMT_XYZ12BE
packed XYZ 4:4:4, 36 bpp, (msb) 12X, 12Y, 12Z (lsb), the 2-byte value for each X/Y/Z is stored as big...
Definition: pixfmt.h:197
SwsContext::scaler_sub
SwsScaler scaler_sub
Scaler used specifically for up/downsampling subsampled (chroma) planes.
Definition: swscale.h:306
len
int len
Definition: vorbis_enc_data.h:426
AV_PIX_FMT_BGR565
#define AV_PIX_FMT_BGR565
Definition: pixfmt.h:531
SwsContext::dst_h
int dst_h
Width and height of the destination frame.
Definition: swscale.h:277
AV_PIX_FMT_RGB4_BYTE
@ AV_PIX_FMT_RGB4_BYTE
packed RGB 1:2:1, 8bpp, (msb)1R 2G 1B(lsb)
Definition: pixfmt.h:95
AV_PIX_FMT_GBRPF32LE
@ AV_PIX_FMT_GBRPF32LE
IEEE-754 single precision planar GBR 4:4:4, 96bpp, little-endian.
Definition: pixfmt.h:342
av_calloc
void * av_calloc(size_t nmemb, size_t size)
Definition: mem.c:264
AV_PIX_FMT_YUV444P9
#define AV_PIX_FMT_YUV444P9
Definition: pixfmt.h:538
ff_sws_init_altivec_bufs
int ff_sws_init_altivec_bufs(SwsInternal *c)
sws_freeFilter
void sws_freeFilter(SwsFilter *filter)
Definition: utils.c:2202
isFloat
static av_always_inline int isFloat(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:884
RangeList::ranges
Range * ranges
Definition: swscale_internal.h:92
SWS_CS_DEFAULT
#define SWS_CS_DEFAULT
Definition: swscale.h:466
SWS_SCALE_GAUSSIAN
@ SWS_SCALE_GAUSSIAN
2-tap gaussian approximation
Definition: swscale.h:102
AV_PIX_FMT_GBRAP16LE
@ AV_PIX_FMT_GBRAP16LE
planar GBRA 4:4:4:4 64bpp, little-endian
Definition: pixfmt.h:214
SWS_DITHER_ED
@ SWS_DITHER_ED
Definition: swscale.h:83
AV_PIX_FMT_PAL8
@ AV_PIX_FMT_PAL8
8 bits with AV_PIX_FMT_RGB32 palette
Definition: pixfmt.h:84
AV_PIX_FMT_GRAY12BE
@ AV_PIX_FMT_GRAY12BE
Y , 12bpp, big-endian.
Definition: pixfmt.h:318
AV_CPU_FLAG_MMX
#define AV_CPU_FLAG_MMX
standard MMX
Definition: cpu.h:32
SwsInternal
Definition: swscale_internal.h:337
ret
ret
Definition: filter_design.txt:187
XYZ_GAMMA
#define XYZ_GAMMA
Definition: swscale_internal.h:557
AV_PIX_FMT_0BGR
@ AV_PIX_FMT_0BGR
packed BGR 8:8:8, 32bpp, XBGRXBGR... X=unused/undefined
Definition: pixfmt.h:264
FFSWAP
#define FFSWAP(type, a, b)
Definition: macros.h:52
rgbgammainv_tab
static uint16_t rgbgammainv_tab[4096]
Definition: utils.c:723
pos
unsigned int pos
Definition: spdifenc.c:414
SWS_FULL_CHR_H_INT
@ SWS_FULL_CHR_H_INT
Perform full chroma upsampling when upscaling to RGB.
Definition: swscale.h:156
sws_getContext
SwsContext * sws_getContext(int srcW, int srcH, enum AVPixelFormat srcFormat, int dstW, int dstH, enum AVPixelFormat dstFormat, int flags, SwsFilter *srcFilter, SwsFilter *dstFilter, const double *param)
Allocate and return an SwsContext.
Definition: utils.c:1966
left
Tag MUST be and< 10hcoeff half pel interpolation filter coefficients, hcoeff[0] are the 2 middle coefficients[1] are the next outer ones and so on, resulting in a filter like:...eff[2], hcoeff[1], hcoeff[0], hcoeff[0], hcoeff[1], hcoeff[2] ... the sign of the coefficients is not explicitly stored but alternates after each coeff and coeff[0] is positive, so ...,+,-,+,-,+,+,-,+,-,+,... hcoeff[0] is not explicitly stored but found by subtracting the sum of all stored coefficients with signs from 32 hcoeff[0]=32 - hcoeff[1] - hcoeff[2] - ... a good choice for hcoeff and htaps is htaps=6 hcoeff={40,-10, 2} an alternative which requires more computations at both encoder and decoder side and may or may not be better is htaps=8 hcoeff={42,-14, 6,-2}ref_frames minimum of the number of available reference frames and max_ref_frames for example the first frame after a key frame always has ref_frames=1spatial_decomposition_type wavelet type 0 is a 9/7 symmetric compact integer wavelet 1 is a 5/3 symmetric compact integer wavelet others are reserved stored as delta from last, last is reset to 0 if always_reset||keyframeqlog quality(logarithmic quantizer scale) stored as delta from last, last is reset to 0 if always_reset||keyframemv_scale stored as delta from last, last is reset to 0 if always_reset||keyframe FIXME check that everything works fine if this changes between framesqbias dequantization bias stored as delta from last, last is reset to 0 if always_reset||keyframeblock_max_depth maximum depth of the block tree stored as delta from last, last is reset to 0 if always_reset||keyframequant_table quantization tableHighlevel bitstream structure:==============================--------------------------------------------|Header|--------------------------------------------|------------------------------------|||Block0||||split?||||yes no||||......... intra?||||:Block01 :yes no||||:Block02 :....... ..........||||:Block03 ::y DC ::ref index:||||:Block04 ::cb DC ::motion x :||||......... :cr DC ::motion y :||||....... ..........|||------------------------------------||------------------------------------|||Block1|||...|--------------------------------------------|------------ ------------ ------------|||Y subbands||Cb subbands||Cr subbands||||--- ---||--- ---||--- ---|||||LL0||HL0||||LL0||HL0||||LL0||HL0|||||--- ---||--- ---||--- ---||||--- ---||--- ---||--- ---|||||LH0||HH0||||LH0||HH0||||LH0||HH0|||||--- ---||--- ---||--- ---||||--- ---||--- ---||--- ---|||||HL1||LH1||||HL1||LH1||||HL1||LH1|||||--- ---||--- ---||--- ---||||--- ---||--- ---||--- ---|||||HH1||HL2||||HH1||HL2||||HH1||HL2|||||...||...||...|||------------ ------------ ------------|--------------------------------------------Decoding process:=================------------|||Subbands|------------||||------------|Intra DC||||LL0 subband prediction ------------|\ Dequantization ------------------- \||Reference frames|\ IDWT|------- -------|Motion \|||Frame 0||Frame 1||Compensation . OBMC v -------|------- -------|--------------. \------> Frame n output Frame Frame<----------------------------------/|...|------------------- Range Coder:============Binary Range Coder:------------------- The implemented range coder is an adapted version based upon "Range encoding: an algorithm for removing redundancy from a digitised message." by G. N. N. Martin. The symbols encoded by the Snow range coder are bits(0|1). The associated probabilities are not fix but change depending on the symbol mix seen so far. bit seen|new state ---------+----------------------------------------------- 0|256 - state_transition_table[256 - old_state];1|state_transition_table[old_state];state_transition_table={ 0, 0, 0, 0, 0, 0, 0, 0, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, 150, 151, 152, 152, 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 171, 172, 173, 174, 175, 176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 190, 191, 192, 194, 194, 195, 196, 197, 198, 199, 200, 201, 202, 202, 204, 205, 206, 207, 208, 209, 209, 210, 211, 212, 213, 215, 215, 216, 217, 218, 219, 220, 220, 222, 223, 224, 225, 226, 227, 227, 229, 229, 230, 231, 232, 234, 234, 235, 236, 237, 238, 239, 240, 241, 242, 243, 244, 245, 246, 247, 248, 248, 0, 0, 0, 0, 0, 0, 0};FIXME Range Coding of integers:------------------------- FIXME Neighboring Blocks:===================left and top are set to the respective blocks unless they are outside of the image in which case they are set to the Null block top-left is set to the top left block unless it is outside of the image in which case it is set to the left block if this block has no larger parent block or it is at the left side of its parent block and the top right block is not outside of the image then the top right block is used for top-right else the top-left block is used Null block y, cb, cr are 128 level, ref, mx and my are 0 Motion Vector Prediction:=========================1. the motion vectors of all the neighboring blocks are scaled to compensate for the difference of reference frames scaled_mv=(mv *(256 *(current_reference+1)/(mv.reference+1))+128)> the median of the scaled left
Definition: snow.txt:386
AV_PIX_FMT_GBRP12BE
@ AV_PIX_FMT_GBRP12BE
planar GBR 4:4:4 36bpp, big-endian
Definition: pixfmt.h:279
init_xyz_tables
static av_cold void init_xyz_tables(void)
Definition: utils.c:725
SWS_DITHER_A_DITHER
@ SWS_DITHER_A_DITHER
Definition: swscale.h:84
c2
static const uint64_t c2
Definition: murmur3.c:53
ScaleAlgorithm
Definition: utils.c:188
SWS_NUM_SCALER_PARAMS
#define SWS_NUM_SCALER_PARAMS
Extra parameters for fine-tuning certain scalers.
Definition: swscale.h:247
fill_rgb2yuv_table
static void fill_rgb2yuv_table(SwsInternal *c, const int table[4], int dstRange)
Definition: utils.c:625
SWS_PRINT_INFO
@ SWS_PRINT_INFO
Emit verbose log of scaling parameters.
Definition: swscale.h:143
AV_PIX_FMT_NONE
@ AV_PIX_FMT_NONE
Definition: pixfmt.h:72
RGB_GAMMA
#define RGB_GAMMA
Definition: swscale_internal.h:558
SWS_BACKEND_UNSTABLE
@ SWS_BACKEND_UNSTABLE
Definition: swscale.h:122
SWS_SCALE_SPLINE
@ SWS_SCALE_SPLINE
unwindowned natural cubic spline
Definition: swscale.h:105
SWS_ERROR_DIFFUSION
@ SWS_ERROR_DIFFUSION
Set SwsContext.dither instead.
Definition: swscale.h:193
SWS_GAUSS
@ SWS_GAUSS
gaussian approximation
Definition: swscale.h:206
AVPixFmtDescriptor::comp
AVComponentDescriptor comp[4]
Parameters that describe how pixels are packed.
Definition: pixdesc.h:105
ScaleAlgorithm::description
const char * description
human-readable description
Definition: utils.c:190
Windows::Graphics::DirectX::Direct3D11::p
IDirect3DDxgiInterfaceAccess _COM_Outptr_ void ** p
Definition: vsrc_gfxcapture_winrt.hpp:53
AV_PIX_FMT_YUVA420P10BE
@ AV_PIX_FMT_YUVA420P10BE
planar YUV 4:2:0 25bpp, (1 Cr & Cb sample per 2x2 Y & A samples, big-endian)
Definition: pixfmt.h:181
AV_PIX_FMT_YUV444P
@ AV_PIX_FMT_YUV444P
planar YUV 4:4:4, 24bpp, (1 Cr & Cb sample per 1x1 Y samples)
Definition: pixfmt.h:78
Range::start
AVRational start
Definition: vf_pseudocolor.c:118
AV_PIX_FMT_GBRP
@ AV_PIX_FMT_GBRP
planar GBR 4:4:4 24bpp
Definition: pixfmt.h:165
AV_PIX_FMT_GRAY16LE
@ AV_PIX_FMT_GRAY16LE
Y , 16bpp, little-endian.
Definition: pixfmt.h:105
AV_PIX_FMT_X2BGR10LE
@ AV_PIX_FMT_X2BGR10LE
packed BGR 10:10:10, 30bpp, (msb)2X 10B 10G 10R(lsb), little-endian, X=unused/undefined
Definition: pixfmt.h:386
isBayer16BPS
static av_always_inline int isBayer16BPS(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:869
AV_PIX_FMT_YUV422P
@ AV_PIX_FMT_YUV422P
planar YUV 4:2:2, 16bpp, (1 Cr & Cb sample per 2x1 Y samples)
Definition: pixfmt.h:77
mem.h
ff_init_filters
int ff_init_filters(SwsInternal *c)
Definition: slice.c:246
BU_IDX
#define BU_IDX
Definition: swscale_internal.h:474
SwsContext::dst_w
int dst_w
Definition: swscale.h:277
AV_PIX_FMT_YUVA444P10LE
@ AV_PIX_FMT_YUVA444P10LE
planar YUV 4:4:4 40bpp, (1 Cr & Cb sample per 1x1 Y & A samples, little-endian)
Definition: pixfmt.h:186
AV_CPU_FLAG_SLOW_GATHER
#define AV_CPU_FLAG_SLOW_GATHER
CPU has slow gathers.
Definition: cpu.h:62
cpu.h
SwsContext::src_format
int src_format
Source pixel format.
Definition: swscale.h:278
AVPixFmtDescriptor
Descriptor that unambiguously describes how the bits of a pixel are stored in the up to 4 data planes...
Definition: pixdesc.h:69
map
const VDPAUPixFmtMap * map
Definition: hwcontext_vdpau.c:71
ScaleAlgorithm::size_factor
int size_factor
size factor used when initing the filters
Definition: utils.c:191
av_free
#define av_free(p)
Definition: tableprint_vlc.h:34
FFALIGN
#define FFALIGN(x, a)
Definition: macros.h:78
SwsContext::dst_range
int dst_range
Destination is full range.
Definition: swscale.h:281
AV_PIX_FMT_GRAY14LE
@ AV_PIX_FMT_GRAY14LE
Y , 14bpp, little-endian.
Definition: pixfmt.h:361
SwsFilter::lumH
SwsVector * lumH
Definition: swscale.h:487
av_freep
#define av_freep(p)
Definition: tableprint_vlc.h:35
cpu.h
sws_sumVec
static SwsVector * sws_sumVec(SwsVector *a, SwsVector *b)
Definition: utils.c:2099
AV_PIX_FMT_YUV411P
@ AV_PIX_FMT_YUV411P
planar YUV 4:1:1, 12bpp, (1 Cr & Cb sample per 4x1 Y samples)
Definition: pixfmt.h:80
AV_PIX_FMT_GRAY14BE
@ AV_PIX_FMT_GRAY14BE
Y , 14bpp, big-endian.
Definition: pixfmt.h:360
AV_PIX_FMT_YUVA422P16BE
@ AV_PIX_FMT_YUVA422P16BE
planar YUV 4:2:2 48bpp, (1 Cr & Cb sample per 2x1 Y & A samples, big-endian)
Definition: pixfmt.h:189
AV_PIX_FMT_YUVA422P16LE
@ AV_PIX_FMT_YUVA422P16LE
planar YUV 4:2:2 48bpp, (1 Cr & Cb sample per 2x1 Y & A samples, little-endian)
Definition: pixfmt.h:190
sws_free_context
void sws_free_context(SwsContext **pctx)
Free the context and everything associated with it, and write NULL to the provided pointer.
Definition: utils.c:2381
AV_PIX_FMT_GBRP14LE
@ AV_PIX_FMT_GBRP14LE
planar GBR 4:4:4 42bpp, little-endian
Definition: pixfmt.h:282
ff_sws_free_altivec_bufs
void ff_sws_free_altivec_bufs(SwsInternal *c)
int32_t
int32_t
Definition: audioconvert.c:56
imgutils.h
X86_MMX
#define X86_MMX(flags)
Definition: cpu.h:25
AV_PIX_FMT_0RGB
@ AV_PIX_FMT_0RGB
packed RGB 8:8:8, 32bpp, XRGBXRGB... X=unused/undefined
Definition: pixfmt.h:262
avpriv_slicethread_free
void avpriv_slicethread_free(AVSliceThread **pctx)
Destroy slice threading context.
Definition: slicethread.c:275
alloc_set_opts
static SwsContext * alloc_set_opts(int srcW, int srcH, enum AVPixelFormat srcFormat, int dstW, int dstH, enum AVPixelFormat dstFormat, int flags, const double *param)
Allocate and return an SwsContext without performing initialization.
Definition: utils.c:86
coeff
static const double coeff[2][5]
Definition: vf_owdenoise.c:80
av_log
#define av_log(a,...)
Definition: tableprint_vlc.h:27
SwsContext::src_h_chr_pos
int src_h_chr_pos
Source horizontal chroma position.
Definition: swscale.h:283
SWS_SCALE_AREA
@ SWS_SCALE_AREA
area averaging
Definition: swscale.h:101
sws_internal
static SwsInternal * sws_internal(const SwsContext *sws)
Definition: swscale_internal.h:79
AV_PIX_FMT_GBRAP10BE
@ AV_PIX_FMT_GBRAP10BE
planar GBR 4:4:4:4 40bpp, big-endian
Definition: pixfmt.h:313
SWS_ACCURATE_RND
@ SWS_ACCURATE_RND
Force bit-exact output.
Definition: swscale.h:179
SWS_LANCZOS
@ SWS_LANCZOS
3-tap sinc/sinc
Definition: swscale.h:208
atomic_init
#define atomic_init(obj, value)
Definition: stdatomic.h:33
GU_IDX
#define GU_IDX
Definition: swscale_internal.h:473
AV_PIX_FMT_YUVA444P16LE
@ AV_PIX_FMT_YUVA444P16LE
planar YUV 4:4:4 64bpp, (1 Cr & Cb sample per 1x1 Y & A samples, little-endian)
Definition: pixfmt.h:192
AV_PIX_FMT_GBRPF16BE
@ AV_PIX_FMT_GBRPF16BE
IEEE-754 half precision planer GBR 4:4:4, 48bpp, big-endian.
Definition: pixfmt.h:466
SwsContext::dst_v_chr_pos
int dst_v_chr_pos
Destination vertical chroma position.
Definition: swscale.h:284
SWS_SINC
@ SWS_SINC
unwindowed sinc
Definition: swscale.h:207
SwsContext
Main external API structure.
Definition: swscale.h:229
AV_PIX_FMT_BGR444LE
@ AV_PIX_FMT_BGR444LE
packed BGR 4:4:4, 16bpp, (msb)4X 4B 4G 4R(lsb), little-endian, X=unused/undefined
Definition: pixfmt.h:138
handle_formats
static int handle_formats(SwsContext *sws)
Definition: utils.c:842
SwsFilter::chrH
SwsVector * chrH
Definition: swscale.h:489
SWS_SRC_V_CHR_DROP_MASK
#define SWS_SRC_V_CHR_DROP_MASK
Definition: swscale.h:455
sws_dcVec
static double sws_dcVec(SwsVector *a)
Definition: utils.c:2075
av_log2
int av_log2(unsigned v)
Definition: intmath.c:26
sws_normalizeVec
void sws_normalizeVec(SwsVector *a, double height)
Scale all the coefficients of a so that their sum equals height.
Definition: utils.c:2094
AV_PIX_FMT_YUVA420P9BE
@ AV_PIX_FMT_YUVA420P9BE
planar YUV 4:2:0 22.5bpp, (1 Cr & Cb sample per 2x2 Y & A samples), big-endian
Definition: pixfmt.h:175
APCK_SIZE
#define APCK_SIZE
Definition: swscale_internal.h:72
xyzgamma_tab
static uint16_t xyzgamma_tab[4096]
Definition: utils.c:723
SWS_UNSTABLE
@ SWS_UNSTABLE
Allow/prefer using experimental new code paths.
Definition: swscale.h:187
rgb2rgb.h
SwsContext::scaler_params
double scaler_params[SWS_NUM_SCALER_PARAMS]
Definition: swscale.h:248
get_local_pos
static av_cold int get_local_pos(SwsInternal *s, int chr_subsample, int pos, int dir)
Definition: utils.c:179
AV_PIX_FMT_GBRAP14LE
@ AV_PIX_FMT_GBRAP14LE
planar GBR 4:4:4:4 56bpp, little-endian
Definition: pixfmt.h:433
swscale.h
AV_PIX_FMT_YUVA422P
@ AV_PIX_FMT_YUVA422P
planar YUV 4:2:2 24bpp, (1 Cr & Cb sample per 2x1 Y & A samples)
Definition: pixfmt.h:173
AV_PIX_FMT_GBRPF16LE
@ AV_PIX_FMT_GBRPF16LE
IEEE-754 half precision planer GBR 4:4:4, 48bpp, little-endian.
Definition: pixfmt.h:467
av_get_pix_fmt_name
const char * av_get_pix_fmt_name(enum AVPixelFormat pix_fmt)
Return the short name for a pixel format, NULL in case pix_fmt is unknown.
Definition: pixdesc.c:3376
isALPHA
static av_always_inline int isALPHA(enum AVPixelFormat pix_fmt)
Definition: swscale_internal.h:898
RGB2YUV_SHIFT
#define RGB2YUV_SHIFT
Definition: swscale_internal.h:478
AV_PIX_FMT_BGR48BE
@ AV_PIX_FMT_BGR48BE
packed RGB 16:16:16, 48bpp, 16B, 16G, 16R, the 2-byte value for each R/G/B component is stored as big...
Definition: pixfmt.h:145
min
float min
Definition: vorbis_enc_data.h:429
AV_PIX_FMT_YUVA422P9LE
@ AV_PIX_FMT_YUVA422P9LE
planar YUV 4:2:2 27bpp, (1 Cr & Cb sample per 2x1 Y & A samples), little-endian
Definition: pixfmt.h:178
context_init_threaded
static int context_init_threaded(SwsContext *sws, SwsFilter *src_filter, SwsFilter *dst_filter)
Definition: utils.c:1883