FFmpeg
Loading...
Searching...
No Matches
ops.h
Go to the documentation of this file.
1/**
2 * Copyright (C) 2025 Niklas Haas
3 *
4 * This file is part of FFmpeg.
5 *
6 * FFmpeg is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * FFmpeg is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with FFmpeg; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21#ifndef SWSCALE_OPS_H
22#define SWSCALE_OPS_H
23
24#include <assert.h>
25#include <stdbool.h>
26#include <stdalign.h>
27
28#include "libavutil/bprint.h"
29
30#include "graph.h"
31#include "filters.h"
32#include "lut3d.h"
33#include "rational64.h"
34#include "uops.h"
35
36typedef enum SwsOpType {
38
39 /* Defined for all types; but implemented for integers only */
40 SWS_OP_READ, /* gather raw pixels from planes */
41 SWS_OP_WRITE, /* write raw pixels to planes */
42 SWS_OP_SWAP_BYTES, /* swap byte order (for differing endianness) */
43 SWS_OP_SWIZZLE, /* rearrange channel order, or duplicate channels */
44
45 /* Bit manipulation operations. Defined for integers only. */
46 SWS_OP_UNPACK, /* split tightly packed data into components */
47 SWS_OP_PACK, /* compress components into tightly packed data */
48 SWS_OP_LSHIFT, /* logical left shift of raw pixel values */
49 SWS_OP_RSHIFT, /* right shift of raw pixel values */
50
51 /* Generic arithmetic. Defined and implemented for all types */
52 SWS_OP_CLEAR, /* clear pixel values */
53 SWS_OP_CONVERT, /* convert (cast) between formats */
54 SWS_OP_MIN, /* numeric minimum */
55 SWS_OP_MAX, /* numeric maximum */
56 SWS_OP_SCALE, /* multiplication by scalar */
57
58 /* Floating-point only arithmetic operations. */
59 SWS_OP_LINEAR, /* generalized linear affine transform */
60 SWS_OP_DITHER, /* add dithering noise */
61
62 /* Filtering operations. */
63 SWS_OP_FILTER_H, /* horizontal filtering */
64 SWS_OP_FILTER_V, /* vertical filtering */
65
66 /* Table-based operations. Defined for floating point types only. */
67 SWS_OP_LUT_3D, /* apply a SwsLut3D */
68
70} SwsOpType;
71
73
74/* Compute SwsCompMask from values with denominator != 0 */
76
77typedef enum SwsCompFlags {
78 SWS_COMP_GARBAGE = 1 << 0, /* contents are undefined / garbage data */
79 SWS_COMP_EXACT = 1 << 1, /* value is an exact integer */
80 SWS_COMP_ZERO = 1 << 2, /* known to be a constant zero */
81 SWS_COMP_SWAPPED = 1 << 3, /* byte order is swapped */
82 SWS_COMP_COPY = 1 << 4, /* value is unmodified from the source plane */
83 SWS_COMP_CONST = 1 << 5, /* value is a fixed constant */
85
86typedef struct SwsComps {
87 SwsCompFlags flags[4]; /* knowledge about (output) component contents */
88
89 /* Keeps track of the known possible value range, or {0, 0} for undefined
90 * or (unknown range) floating point inputs */
92
93 /* Keeps track of input (forward) and output (reverse) dependencies */
95} SwsComps;
96
97typedef enum SwsReadWriteMode {
98 /**
99 * Note: 1-component reads are either SWS_RW_PLANAR or SWS_RW_PACKED,
100 * depending on the underlying interpretation. If multiple components are
101 * packed into one element (e.g. rgb10a2 -> u16), they are marked as
102 * SWS_RW_PACKED. Otherwise (e.g. gray16le), they are SWS_RW_PLANAR.
103 *
104 * This is a purely semantic/informative difference; the underlying code
105 * treats 1-components reads/writes the same regardless of mode.
106 */
107 SWS_RW_PLANAR, /* one plane per component */
108 SWS_RW_PACKED, /* all components on a single plane */
109 SWS_RW_PALETTE, /* plane 0 is 8-bit index, plane 1 is packed palette */
111
112typedef struct SwsReadWriteOp {
113 /**
114 * Examples:
115 * rgba = 4x u8 packed
116 * yuv444p = 3x u8
117 * rgb565 = 1x u16 <- use SWS_OP_UNPACK to unpack
118 * monow = 1x u8 (frac 3)
119 * rgb4 = 1x u8 (frac 1)
120 * pal8 = 4x u8 (palette)
121 */
122 SwsReadWriteMode mode; /* how data is laid out in memory */
123 uint8_t elems; /* number of elements (of type `op.type`) to read/write */
124 uint8_t frac; /* fractional pixel step factor (log2) */
125
126 /**
127 * Filter kernel to apply to each plane while sampling. Currently, only
128 * one shared filter kernel is supported for all planes. (Optional)
129 *
130 * Note: As with SWS_OP_FILTER_*, if a filter kernel is in use, the read
131 * operation will always output floating point values.
132 */
133 struct {
134 SwsOpType op; /* some value of SWS_OP_FILTER_* */
135 SwsFilterWeights *kernel; /* (refstruct) */
136 SwsPixelType type; /* pixel type to store result as */
139
140typedef struct SwsPackOp {
141 /**
142 * Packed bits are assumed to be LSB-aligned within the underlying
143 * integer type; i.e. (msb) 0 ... X Y Z W (lsb).
144 */
145 uint8_t pattern[4]; /* bit depth pattern, from MSB to LSB */
146} SwsPackOp;
147
148typedef struct SwsSwizzleOp {
149 /**
150 * Input component for each output component:
151 * Out[x] := In[swizzle.in[x]]
152 */
153 union {
154 uint32_t mask;
155 uint8_t in[4];
156 struct { uint8_t x, y, z, w; };
157 };
159
160#define SWS_SWIZZLE(X,Y,Z,W) ((SwsSwizzleOp) { .in = {X, Y, Z, W} })
162
163typedef struct SwsShiftOp {
164 uint8_t amount; /* number of bits to shift */
165} SwsShiftOp;
166
167typedef struct SwsClearOp {
168 SwsCompMask mask; /* mask of components to clear */
169 AVRational64 value[4]; /* value to set */
170} SwsClearOp;
171
172typedef struct SwsConvertOp {
173 SwsPixelType to; /* type of pixel to convert to */
174 bool expand; /* if true, integers are expanded to the full range */
176
177typedef struct SwsClampOp {
178 AVRational64 limit[4]; /* per-component min/max value */
179} SwsClampOp;
180
181typedef struct SwsScaleOp {
182 AVRational64 factor; /* scalar multiplication factor */
183} SwsScaleOp;
184
185typedef struct SwsDitherOp {
186 AVRational64 *matrix; /* tightly packed dither matrix (refstruct) */
187 AVRational64 min, max; /* minimum/maximum value in `matrix` */
188 int size_log2; /* size (in bits) of the dither matrix */
189 int8_t y_offset[4]; /* row offset for each component, or -1 for ignored */
191
192typedef struct SwsLinearOp {
193 /**
194 * Generalized 5x5 affine transformation:
195 * [ Out.x ] = [ A B C D E ]
196 * [ Out.y ] = [ F G H I J ] * [ x y z w 1 ]
197 * [ Out.z ] = [ K L M N O ]
198 * [ Out.w ] = [ P Q R S T ]
199 */
202
203/* m[i][j] <-> 1 << (5 * i + j) */
204uint32_t ff_sws_linear_mask(const SwsLinearOp *c);
205
206typedef struct SwsFilterOp {
207 SwsFilterWeights *kernel; /* filter kernel (refstruct) */
208 SwsPixelType type; /* pixel type to store result as */
210
211typedef struct SwsLut3dOp {
212 /**
213 * Reference to the external LUT3D to apply. This is managed by the caller,
214 * and must remain valid for the lifetime of the SwsOp and any compiled
215 * functions derived from it.
216 *
217 * *lut is never dereferenced by the SwsOp code itself, only at runtime by
218 * the actual dispatched implementation, and may be freely modified even
219 * after op compilation to place new values for dynamic tone-mapping.
220 *
221 * The reference algorithm for this operation lives in lut3d.c, and
222 * includes a tetrahedral interpolation component for the input LUT, and
223 * then an optional linear tone mapping LUT plus trilinear output LUT
224 * (when lut->dynamic is true).
225 *
226 * All linear interpolations are performed in the pixel value's native
227 * representation, even though the LUTs themselves are stored as unsigned
228 * packed 16-bit integers. The input value range is assumed to be scaled
229 * and clamped to the LUT's domain (i.e. [0, INPUT_LUT_SIZE - 1]), and the
230 * output value range will be [0, 2^16-1], except for the alpha channel,
231 * which is passed through untouched.
232 */
233 const SwsLut3D *lut; /* refstruct */
235} SwsLut3dOp;
236
237typedef struct SwsOp {
238 SwsOpType op; /* operation to perform */
239 SwsPixelType type; /* pixel type to operate on */
240 union {
253 };
254
255 /**
256 * Metadata about the operation's input/output components. Discarded
257 * and regenerated automatically by `ff_sws_op_list_update_comps()`.
258 *
259 * Note that backends may rely on the presence and accuracy of this
260 * metadata for all operations, during ff_sws_ops_compile().
261 */
263} SwsOp;
264
265#define SWS_OP_NEEDED(op, idx) (!((op)->comps.flags[idx] & SWS_COMP_GARBAGE))
266
267/* Compute SwsCompMask from a mask of needed components */
269
270/**
271 * Return the number of planes involved in a read/write operation.
272 */
273int ff_sws_rw_op_planes(const SwsOp *op);
274
275/**
276 * Describe an operation in human-readable form.
277 */
278void ff_sws_op_desc(AVBPrint *bp, const SwsOp *op);
279
280/**
281 * Frees any allocations associated with an SwsOp and sets it to {0}.
282 */
284
285/**
286 * Apply an operation to an AVRational64. No-op for read/write operations.
287 */
288void ff_sws_apply_op_q(const SwsOp *op, AVRational64 x[4]);
289
290/**
291 * Helper struct for representing a list of operations.
292 */
293typedef struct SwsOpList {
296
297 /* Metadata associated with this operation list */
299
300 /* Input/output plane indices */
301 uint8_t plane_src[4], plane_dst[4];
302
303 /**
304 * Source component metadata associated with pixel values from each
305 * corresponding component (in plane/memory order, i.e. not affected by
306 * `plane_src`). Lets the optimizer know additional information about
307 * the value range and/or pixel data to expect.
308 *
309 * The default value of {0} is safe to pass in the case that no additional
310 * information is known.
311 */
313} SwsOpList;
314
317
318/**
319 * Returns a duplicate of `ops`, or NULL on OOM.
320 */
322
323/**
324 * Returns the input operation for a given op list, or NULL if there is none
325 * (e.g. for a pure CLEAR-only operation list).
326 *
327 * This will always be an op of type SWS_OP_READ.
328 */
329const SwsOp *ff_sws_op_list_input(const SwsOpList *ops);
330
331/**
332 * Returns the output operation for a given op list, or NULL if there is none.
333 *
334 * This will always be an op of type SWS_OP_WRITE.
335 */
336const SwsOp *ff_sws_op_list_output(const SwsOpList *ops);
337
338/**
339 * Returns whether an op list represents a true no-op operation, i.e. may be
340 * eliminated entirely from an execution graph.
341 */
342bool ff_sws_op_list_is_noop(const SwsOpList *ops);
343
344/**
345 * Returns the size of the largest pixel type used in `ops`.
346 */
347int ff_sws_op_list_max_size(const SwsOpList *ops);
348
349/**
350 * These will take over ownership of `op` and set it to {0}, even on failure.
351 */
354
355void ff_sws_op_list_remove_at(SwsOpList *ops, int index, int count);
356
357/**
358 * Print out the contents of an operation list.
359 */
360void ff_sws_op_list_print(void *log_ctx, int log_level, int log_level_extra,
361 const SwsOpList *ops);
362
363/**
364 * Infer + propagate known information about components. Called automatically
365 * when needed by the optimizer and compiler.
366 */
368
369/**
370 * Fuse compatible and eliminate redundant operations, as well as replacing
371 * some operations with more efficient alternatives.
372 */
374
375#endif
AVBPrint public header.
int index
Definition gxfenc.c:90
static int op(uint8_t **dst, const uint8_t *dst_end, GetByteContext *gb, int pixel, int count, int *x, int width, int linesize)
Perform decode operation.
Definition anm.c:76
static const uint16_t mask[17]
Definition lzw.c:38
int ff_sws_op_list_max_size(const SwsOpList *ops)
Returns the size of the largest pixel type used in ops.
Definition ops.c:791
void ff_sws_op_list_update_comps(SwsOpList *ops)
Infer + propagate known information about components.
Definition ops.c:315
void ff_sws_op_desc(AVBPrint *bp, const SwsOp *op)
Describe an operation in human-readable form.
Definition ops.c:877
int ff_sws_op_list_optimize(SwsOpList *ops)
Fuse compatible and eliminate redundant operations, as well as replacing some operations with more ef...
uint32_t ff_sws_linear_mask(const SwsLinearOp *c)
Definition ops.c:802
int ff_sws_op_list_insert_at(SwsOpList *ops, int index, SwsOp *op)
Definition ops.c:742
void ff_sws_op_list_print(void *log_ctx, int log_level, int log_level_extra, const SwsOpList *ops)
Print out the contents of an operation list.
Definition ops.c:987
const SwsOp * ff_sws_op_list_input(const SwsOpList *ops)
Returns the input operation for a given op list, or NULL if there is none (e.g.
Definition ops.c:713
void ff_sws_op_uninit(SwsOp *op)
Frees any allocations associated with an SwsOp and sets it to {0}.
int ff_sws_op_list_append(SwsOpList *ops, SwsOp *op)
These will take over ownership of op and set it to {0}, even on failure.
Definition ops.c:756
void ff_sws_comp_mask_swizzle(SwsCompMask *mask, const SwsSwizzleOp *swiz)
Definition ops.c:110
SwsOpList * ff_sws_op_list_alloc(void)
Definition ops.c:646
const char * ff_sws_op_type_name(SwsOpType op)
Definition ops.c:71
SwsCompMask ff_sws_comp_mask_needed(const SwsOp *op)
Definition ops.c:123
SwsCompMask ff_sws_comp_mask_q4(const AVRational64 q[4])
Definition ops.c:100
int ff_sws_rw_op_planes(const SwsOp *op)
Return the number of planes involved in a read/write operation.
Definition ops.c:133
const SwsOp * ff_sws_op_list_output(const SwsOpList *ops)
Returns the output operation for a given op list, or NULL if there is none.
Definition ops.c:722
bool ff_sws_op_list_is_noop(const SwsOpList *ops)
Returns whether an op list represents a true no-op operation, i.e.
Definition ops.c:761
SwsOpType
Copyright (C) 2025 Niklas Haas.
Definition ops.h:36
@ SWS_OP_TYPE_NB
Definition ops.h:69
@ SWS_OP_INVALID
Definition ops.h:37
@ SWS_OP_RSHIFT
Definition ops.h:49
@ SWS_OP_SWIZZLE
Definition ops.h:43
@ SWS_OP_LSHIFT
Definition ops.h:48
@ SWS_OP_FILTER_V
Definition ops.h:64
@ SWS_OP_SCALE
Definition ops.h:56
@ SWS_OP_FILTER_H
Definition ops.h:63
@ SWS_OP_WRITE
Definition ops.h:41
@ SWS_OP_READ
Definition ops.h:40
@ SWS_OP_CLEAR
Definition ops.h:52
@ SWS_OP_SWAP_BYTES
Definition ops.h:42
@ SWS_OP_MIN
Definition ops.h:54
@ SWS_OP_UNPACK
Definition ops.h:46
@ SWS_OP_LINEAR
Definition ops.h:59
@ SWS_OP_PACK
Definition ops.h:47
@ SWS_OP_DITHER
Definition ops.h:60
@ SWS_OP_MAX
Definition ops.h:55
@ SWS_OP_LUT_3D
Definition ops.h:67
@ SWS_OP_CONVERT
Definition ops.h:53
SwsReadWriteMode
Definition ops.h:97
@ SWS_RW_PALETTE
Definition ops.h:109
@ SWS_RW_PLANAR
Note: 1-component reads are either SWS_RW_PLANAR or SWS_RW_PACKED, depending on the underlying interp...
Definition ops.h:107
@ SWS_RW_PACKED
Definition ops.h:108
SwsCompFlags
Definition ops.h:77
@ SWS_COMP_CONST
Definition ops.h:83
@ SWS_COMP_ZERO
Definition ops.h:80
@ SWS_COMP_EXACT
Definition ops.h:79
@ SWS_COMP_SWAPPED
Definition ops.h:81
@ SWS_COMP_COPY
Definition ops.h:82
@ SWS_COMP_GARBAGE
Definition ops.h:78
void ff_sws_apply_op_q(const SwsOp *op, AVRational64 x[4])
Apply an operation to an AVRational64.
Definition ops.c:157
void ff_sws_op_list_remove_at(SwsOpList *ops, int index, int count)
Definition ops.c:731
SwsOpList * ff_sws_op_list_duplicate(const SwsOpList *ops)
Returns a duplicate of ops, or NULL on OOM.
Definition ops.c:673
void ff_sws_op_list_free(SwsOpList **ops)
Definition ops.c:659
64-bit extension of AVRational.
64-bit Rational number (pair of numerator and denominator).
Definition rational64.h:52
AVRational64 limit[4]
Definition ops.h:178
SwsCompMask mask
Definition ops.h:168
AVRational64 value[4]
Definition ops.h:169
Definition ops.h:86
SwsCompMask dep_in[4]
Definition ops.h:94
SwsCompFlags flags[4]
Definition ops.h:87
SwsCompMask dep_out[4]
Definition ops.h:94
AVRational64 min[4]
Definition ops.h:91
AVRational64 max[4]
Definition ops.h:91
bool expand
Definition ops.h:174
SwsPixelType to
Definition ops.h:173
AVRational64 min
Definition ops.h:187
AVRational64 * matrix
Definition ops.h:186
AVRational64 max
Definition ops.h:187
int size_log2
Definition ops.h:188
int8_t y_offset[4]
Definition ops.h:189
SwsPixelType type
Definition ops.h:208
SwsFilterWeights * kernel
Definition ops.h:207
Represents a computed filter kernel.
Definition filters.h:85
AVRational64 m[4][5]
Generalized 5x5 affine transformation: [ Out.x ] = [ A B C D E ] [ Out.y ] = [ F G H I J ] * [ x y z ...
Definition ops.h:200
Append a set of operations for applying a gamut/tone mapping 3D LUT to the pixels.
Definition lut3d.h:50
const SwsLut3D * lut
Reference to the external LUT3D to apply.
Definition ops.h:233
bool dynamic
Definition ops.h:234
Helper struct for representing a list of operations.
Definition ops.h:293
SwsFormat dst
Definition ops.h:298
SwsComps comps_src
Source component metadata associated with pixel values from each corresponding component (in plane/me...
Definition ops.h:312
uint8_t plane_src[4]
Definition ops.h:301
uint8_t plane_dst[4]
Definition ops.h:301
SwsOp * ops
Definition ops.h:294
int num_ops
Definition ops.h:295
SwsFormat src
Definition ops.h:298
Definition ops.h:237
SwsClampOp clamp
Definition ops.h:248
SwsScaleOp scale
Definition ops.h:249
SwsSwizzleOp swizzle
Definition ops.h:244
SwsComps comps
Metadata about the operation's input/output components.
Definition ops.h:262
SwsPixelType type
Definition ops.h:239
SwsOpType op
Definition ops.h:238
SwsConvertOp convert
Definition ops.h:247
SwsPackOp pack
Definition ops.h:243
SwsClearOp clear
Definition ops.h:246
SwsLinearOp lin
Definition ops.h:241
SwsReadWriteOp rw
Definition ops.h:242
SwsFilterOp filter
Definition ops.h:251
SwsLut3dOp lut3d
Definition ops.h:252
SwsShiftOp shift
Definition ops.h:245
SwsDitherOp dither
Definition ops.h:250
uint8_t pattern[4]
Packed bits are assumed to be LSB-aligned within the underlying integer type; i.e.
Definition ops.h:145
SwsFilterWeights * kernel
Definition ops.h:135
SwsReadWriteMode mode
Examples: rgba = 4x u8 packed yuv444p = 3x u8 rgb565 = 1x u16 <- use SWS_OP_UNPACK to unpack monow = ...
Definition ops.h:122
SwsPixelType type
Definition ops.h:136
SwsOpType op
Definition ops.h:134
uint8_t frac
Definition ops.h:124
uint8_t elems
Definition ops.h:123
AVRational64 factor
Definition ops.h:182
uint8_t amount
Definition ops.h:164
uint8_t x
Definition ops.h:156
uint8_t z
Definition ops.h:156
uint8_t w
Definition ops.h:156
uint8_t in[4]
Definition ops.h:155
uint32_t mask
Definition ops.h:154
uint8_t y
Definition ops.h:156
void(* filter)(uint8_t *src, ptrdiff_t stride, int qscale)
Definition h263dsp.c:29
SwsPixelType
Definition uops.h:39
uint8_t SwsCompMask
Bit-mask of components.
Definition uops.h:93
static double c[64]