FFmpeg coverage


Directory: ../../../ffmpeg/
File: src/libavutil/opt.c
Date: 2026-10-19 01:23:10
Exec Total Coverage
Lines: 1333 1745 76.4%
Functions: 85 101 84.2%
Branches: 901 1421 63.4%

Line Branch Exec Source
1 /*
2 * AVOptions
3 * Copyright (c) 2005 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 /**
23 * @file
24 * AVOptions
25 * @author Michael Niedermayer <michaelni@gmx.at>
26 */
27
28 #include "avutil.h"
29 #include "avassert.h"
30 #include "avstring.h"
31 #include "channel_layout.h"
32 #include "dict.h"
33 #include "eval.h"
34 #include "log.h"
35 #include "mem.h"
36 #include "parseutils.h"
37 #include "pixdesc.h"
38 #include "mathematics.h"
39 #include "opt.h"
40 #include "samplefmt.h"
41 #include "bprint.h"
42
43 #include <float.h>
44
45 #define TYPE_BASE(type) ((type) & ~AV_OPT_TYPE_FLAG_ARRAY)
46
47 683222815 const AVOption *av_opt_next(const void *obj, const AVOption *last)
48 {
49 const AVClass *class;
50
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 683222815 times.
683222815 if (!obj)
51 ✗ return NULL;
52 683222815 class = *(const AVClass**)obj;
53
7/8
✓ Branch 0 taken 53225359 times.
✓ Branch 1 taken 629997456 times.
✓ Branch 2 taken 53225359 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 52851467 times.
✓ Branch 5 taken 373892 times.
✓ Branch 6 taken 52726935 times.
✓ Branch 7 taken 124532 times.
683222815 if (!last && class && class->option && class->option[0].name)
54 52726935 return class->option;
55
4/4
✓ Branch 0 taken 629997456 times.
✓ Branch 1 taken 498424 times.
✓ Branch 2 taken 577951863 times.
✓ Branch 3 taken 52045593 times.
630495880 if (last && last[1].name)
56 577951863 return ++last;
57 52544017 return NULL;
58 }
59
60 static const struct {
61 size_t size;
62 const char *name;
63 } opt_type_desc[] = {
64 [AV_OPT_TYPE_FLAGS] = { sizeof(unsigned), "<flags>" },
65 [AV_OPT_TYPE_INT] = { sizeof(int), "<int>" },
66 [AV_OPT_TYPE_INT64] = { sizeof(int64_t), "<int64>" },
67 [AV_OPT_TYPE_UINT] = { sizeof(unsigned), "<unsigned>" },
68 [AV_OPT_TYPE_UINT64] = { sizeof(uint64_t), "<uint64>" },
69 [AV_OPT_TYPE_DOUBLE] = { sizeof(double), "<double>" },
70 [AV_OPT_TYPE_FLOAT] = { sizeof(float), "<float>" },
71 [AV_OPT_TYPE_STRING] = { sizeof(char *), "<string>" },
72 [AV_OPT_TYPE_RATIONAL] = { sizeof(AVRational), "<rational>" },
73 [AV_OPT_TYPE_BINARY] = { sizeof(uint8_t *), "<binary>" },
74 [AV_OPT_TYPE_DICT] = { sizeof(AVDictionary *), "<dictionary>" },
75 [AV_OPT_TYPE_IMAGE_SIZE] = { sizeof(int[2]), "<image_size>" },
76 [AV_OPT_TYPE_VIDEO_RATE] = { sizeof(AVRational), "<video_rate>" },
77 [AV_OPT_TYPE_PIXEL_FMT] = { sizeof(enum AVPixelFormat), "<pix_fmt>" },
78 [AV_OPT_TYPE_SAMPLE_FMT] = { sizeof(enum AVSampleFormat), "<sample_fmt>" },
79 [AV_OPT_TYPE_DURATION] = { sizeof(int64_t), "<duration>" },
80 [AV_OPT_TYPE_COLOR] = { sizeof(uint8_t[4]), "<color>" },
81 [AV_OPT_TYPE_CHLAYOUT] = { sizeof(AVChannelLayout),"<channel_layout>" },
82 [AV_OPT_TYPE_BOOL] = { sizeof(int), "<boolean>" },
83 };
84
85 // option is plain old data
86 2009701 static int opt_is_pod(enum AVOptionType type)
87 {
88
1/2
✓ Branch 0 taken 2009701 times.
✗ Branch 1 not taken.
2009701 switch (type) {
89 2009701 case AV_OPT_TYPE_FLAGS:
90 case AV_OPT_TYPE_INT:
91 case AV_OPT_TYPE_INT64:
92 case AV_OPT_TYPE_DOUBLE:
93 case AV_OPT_TYPE_FLOAT:
94 case AV_OPT_TYPE_RATIONAL:
95 case AV_OPT_TYPE_UINT64:
96 case AV_OPT_TYPE_IMAGE_SIZE:
97 case AV_OPT_TYPE_PIXEL_FMT:
98 case AV_OPT_TYPE_SAMPLE_FMT:
99 case AV_OPT_TYPE_VIDEO_RATE:
100 case AV_OPT_TYPE_DURATION:
101 case AV_OPT_TYPE_COLOR:
102 case AV_OPT_TYPE_BOOL:
103 case AV_OPT_TYPE_UINT:
104 2009701 return 1;
105 }
106 ✗ return 0;
107 }
108
109 127432 static uint8_t opt_array_sep(const AVOption *o)
110 {
111 127432 const AVOptionArrayDef *d = o->default_val.arr;
112 av_assert1(o->type & AV_OPT_TYPE_FLAG_ARRAY);
113
4/4
✓ Branch 0 taken 16196 times.
✓ Branch 1 taken 111236 times.
✓ Branch 2 taken 16162 times.
✓ Branch 3 taken 34 times.
127432 return (d && d->sep) ? d->sep : ',';
114 }
115
116 9643 static void *opt_array_pelem(const AVOption *o, void *array, unsigned idx)
117 {
118 av_assert1(o->type & AV_OPT_TYPE_FLAG_ARRAY);
119 9643 return (uint8_t *)array + idx * opt_type_desc[TYPE_BASE(o->type)].size;
120 }
121
122 188145 static unsigned *opt_array_pcount(const void *parray)
123 {
124 188145 return (unsigned *)((const void * const *)parray + 1);
125 }
126
127 30201706 static void opt_free_elem(enum AVOptionType type, void *ptr)
128 {
129
4/4
✓ Branch 0 taken 1048293 times.
✓ Branch 1 taken 70310 times.
✓ Branch 2 taken 72479 times.
✓ Branch 3 taken 29010624 times.
30201706 switch (TYPE_BASE(type)) {
130 1048293 case AV_OPT_TYPE_STRING:
131 case AV_OPT_TYPE_BINARY:
132 1048293 av_freep(ptr);
133 1048293 break;
134
135 70310 case AV_OPT_TYPE_DICT:
136 70310 av_dict_free((AVDictionary **)ptr);
137 70310 break;
138
139 72479 case AV_OPT_TYPE_CHLAYOUT:
140 72479 av_channel_layout_uninit((AVChannelLayout *)ptr);
141 72479 break;
142
143 29010624 default:
144 29010624 break;
145 }
146 30201706 }
147
148 143365 static void opt_free_array(const AVOption *o, void *parray, unsigned *count)
149 {
150
2/2
✓ Branch 0 taken 4838 times.
✓ Branch 1 taken 143365 times.
148203 for (unsigned i = 0; i < *count; i++)
151 4838 opt_free_elem(o->type, opt_array_pelem(o, *(void **)parray, i));
152
153 143365 av_freep(parray);
154 143365 *count = 0;
155 143365 }
156
157 /**
158 * Perform common setup for option-setting functions.
159 *
160 * @param require_type when non-0, require the option to be of this type
161 * @param ptgt target object is written here
162 * @param po the option is written here
163 * @param pdst pointer to option value is written here
164 */
165 334566 static int opt_set_init(void *obj, const char *name, int search_flags,
166 int require_type,
167 void **ptgt, const AVOption **po, void **pdst)
168 {
169 void *logctx;
170 const AVOption *o;
171 void *tgt;
172
173 334566 o = av_opt_find2(obj, name, NULL, 0, search_flags, &tgt);
174
3/6
✓ Branch 0 taken 265576 times.
✓ Branch 1 taken 68990 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 265576 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
334566 if (!o || (!tgt && !(search_flags & AV_OPT_SEARCH_FAKE_OBJ)))
175 68990 return AVERROR_OPTION_NOT_FOUND;
176
177
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 265576 times.
265576 if (o->flags & AV_OPT_FLAG_READONLY)
178 ✗ return AVERROR(EINVAL);
179
180
1/2
✓ Branch 0 taken 265576 times.
✗ Branch 1 not taken.
265576 logctx = tgt ? obj : NULL;
181
182
3/4
✓ Branch 0 taken 7771 times.
✓ Branch 1 taken 257805 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 7771 times.
265576 if (require_type && (o->type != require_type)) {
183 ✗ av_log(logctx, AV_LOG_ERROR,
184 "Tried to set option '%s' of type %s from value of type %s, "
185 ✗ "this is not supported\n", o->name, opt_type_desc[o->type].name,
186 ✗ opt_type_desc[require_type].name);
187 ✗ return AVERROR(EINVAL);
188 }
189
190
2/2
✓ Branch 0 taken 238441 times.
✓ Branch 1 taken 27135 times.
265576 if (!(o->flags & AV_OPT_FLAG_RUNTIME_PARAM)) {
191 238441 unsigned *state_flags = NULL;
192 const AVClass *class;
193
194 // try state flags first from the target (child), then from its parent
195 238441 class = *(const AVClass**)tgt;
196
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 238441 times.
238441 if (class->state_flags_offset)
197 ✗ state_flags = (unsigned*)((uint8_t*)tgt + class->state_flags_offset);
198
199
3/4
✓ Branch 0 taken 238441 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 53598 times.
✓ Branch 3 taken 184843 times.
238441 if (!state_flags && obj != tgt) {
200 53598 class = *(const AVClass**)obj;
201
2/2
✓ Branch 0 taken 52217 times.
✓ Branch 1 taken 1381 times.
53598 if (class->state_flags_offset)
202 52217 state_flags = (unsigned*)((uint8_t*)obj + class->state_flags_offset);
203 }
204
205
3/4
✓ Branch 0 taken 52217 times.
✓ Branch 1 taken 186224 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 52217 times.
238441 if (state_flags && (*state_flags & AV_CLASS_STATE_INITIALIZED)) {
206 ✗ av_log(logctx, AV_LOG_ERROR, "Option '%s' is not a runtime option and "
207 "so cannot be set after the object has been initialized\n",
208 ✗ o->name);
209 ✗ return AVERROR(EINVAL);
210 }
211 }
212
213
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 265574 times.
265576 if (o->flags & AV_OPT_FLAG_DEPRECATED)
214 2 av_log(logctx, AV_LOG_WARNING, "The \"%s\" option is deprecated: %s\n", name, o->help);
215
216
2/2
✓ Branch 0 taken 257808 times.
✓ Branch 1 taken 7768 times.
265576 if (po)
217 257808 *po = o;
218
2/2
✓ Branch 0 taken 235737 times.
✓ Branch 1 taken 29839 times.
265576 if (ptgt)
219 235737 *ptgt = tgt;
220
1/2
✓ Branch 0 taken 265576 times.
✗ Branch 1 not taken.
265576 if (pdst)
221
1/2
✓ Branch 0 taken 265576 times.
✗ Branch 1 not taken.
265576 *pdst = tgt ? ((uint8_t *)tgt) + o->offset : NULL;
222
223 265576 return 0;
224 }
225
226 2 static AVRational double_to_rational(double d)
227 {
228 2 AVRational r = av_d2q(d, 1 << 24);
229
2/6
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
2 if ((!r.num || !r.den) && d)
230 ✗ r = av_d2q(d, INT_MAX);
231 2 return r;
232 }
233
234 25584 static int read_number(const AVOption *o, const void *dst, double *num, int *den, int64_t *intnum)
235 {
236
6/11
✓ Branch 0 taken 22 times.
✓ Branch 1 taken 6 times.
✓ Branch 2 taken 186 times.
✓ Branch 3 taken 25298 times.
✓ Branch 4 taken 48 times.
✓ Branch 5 taken 24 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
25584 switch (TYPE_BASE(o->type)) {
237 22 case AV_OPT_TYPE_FLAGS:
238 22 *intnum = *(unsigned int*)dst;
239 22 return 0;
240 6 case AV_OPT_TYPE_PIXEL_FMT:
241 6 *intnum = *(enum AVPixelFormat *)dst;
242 6 return 0;
243 186 case AV_OPT_TYPE_SAMPLE_FMT:
244 186 *intnum = *(enum AVSampleFormat *)dst;
245 186 return 0;
246 25298 case AV_OPT_TYPE_BOOL:
247 case AV_OPT_TYPE_INT:
248 25298 *intnum = *(int *)dst;
249 25298 return 0;
250 48 case AV_OPT_TYPE_UINT:
251 48 *intnum = *(unsigned int *)dst;
252 48 return 0;
253 24 case AV_OPT_TYPE_DURATION:
254 case AV_OPT_TYPE_INT64:
255 case AV_OPT_TYPE_UINT64:
256 24 *intnum = *(int64_t *)dst;
257 24 return 0;
258 ✗ case AV_OPT_TYPE_FLOAT:
259 ✗ *num = *(float *)dst;
260 ✗ return 0;
261 ✗ case AV_OPT_TYPE_DOUBLE:
262 ✗ *num = *(double *)dst;
263 ✗ return 0;
264 ✗ case AV_OPT_TYPE_RATIONAL:
265 ✗ *intnum = ((AVRational *)dst)->num;
266 ✗ *den = ((AVRational *)dst)->den;
267 ✗ return 0;
268 ✗ case AV_OPT_TYPE_CONST:
269 ✗ *intnum = o->default_val.i64;
270 ✗ return 0;
271 }
272 ✗ return AVERROR(EINVAL);
273 }
274
275 11396142 static int write_number(void *obj, const AVOption *o, void *dst,
276 double num, int den, int64_t intnum,
277 int ignore_range)
278 {
279
1/2
✓ Branch 0 taken 11396142 times.
✗ Branch 1 not taken.
11396142 void *logctx = dst ? obj : NULL;
280 11396142 const enum AVOptionType type = TYPE_BASE(o->type);
281
282
6/6
✓ Branch 0 taken 238581 times.
✓ Branch 1 taken 11157561 times.
✓ Branch 2 taken 114582 times.
✓ Branch 3 taken 123999 times.
✓ Branch 4 taken 114581 times.
✓ Branch 5 taken 1 times.
11396142 if (!ignore_range && type != AV_OPT_TYPE_FLAGS &&
283
4/4
✓ Branch 0 taken 114573 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 7 times.
✓ Branch 3 taken 114566 times.
114581 (!den || o->max * den < num * intnum || o->min * den > num * intnum)) {
284
4/6
✓ Branch 0 taken 15 times.
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 1 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
16 num = den ? num * intnum / den : (num && intnum ? INFINITY : NAN);
285 16 av_log(obj, AV_LOG_ERROR, "Value %f for parameter '%s' out of range [%g - %g]\n",
286 16 num, o->name, o->min, o->max);
287 16 return AVERROR(ERANGE);
288 }
289
4/4
✓ Branch 0 taken 238565 times.
✓ Branch 1 taken 11157561 times.
✓ Branch 2 taken 123999 times.
✓ Branch 3 taken 114566 times.
11396126 if (!ignore_range && type == AV_OPT_TYPE_FLAGS) {
290 123999 double d = num*intnum/den;
291
3/6
✓ Branch 0 taken 123999 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 123999 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 123999 times.
123999 if (d < -1.5 || d > 0xFFFFFFFF+0.5 || (llrint(d*256) & 255)) {
292 ✗ av_log(logctx, AV_LOG_ERROR,
293 "Value %f for parameter '%s' is not a valid set of 32bit integer flags\n",
294 ✗ num*intnum/den, o->name);
295 ✗ return AVERROR(ERANGE);
296 }
297 }
298
299
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 11396126 times.
11396126 if (!dst)
300 ✗ return 0;
301
302
7/9
✓ Branch 0 taken 290562 times.
✓ Branch 1 taken 61157 times.
✓ Branch 2 taken 9149784 times.
✓ Branch 3 taken 532900 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 864054 times.
✓ Branch 6 taken 281412 times.
✓ Branch 7 taken 216257 times.
✗ Branch 8 not taken.
11396126 switch (type) {
303 290562 case AV_OPT_TYPE_PIXEL_FMT:
304 290562 *(enum AVPixelFormat *)dst = llrint(num / den) * intnum;
305 290562 break;
306 61157 case AV_OPT_TYPE_SAMPLE_FMT:
307 61157 *(enum AVSampleFormat *)dst = llrint(num / den) * intnum;
308 61157 break;
309 9149784 case AV_OPT_TYPE_BOOL:
310 case AV_OPT_TYPE_FLAGS:
311 case AV_OPT_TYPE_INT:
312 case AV_OPT_TYPE_UINT:
313 9149784 *(int *)dst = llrint(num / den) * intnum;
314 9149784 break;
315 532900 case AV_OPT_TYPE_DURATION:
316 case AV_OPT_TYPE_INT64:{
317 532900 double d = num / den;
318
3/4
✓ Branch 0 taken 1892 times.
✓ Branch 1 taken 531008 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 1892 times.
532900 if (intnum == 1 && d == (double)INT64_MAX) {
319 ✗ *(int64_t *)dst = INT64_MAX;
320 } else
321 532900 *(int64_t *)dst = llrint(d) * intnum;
322 532900 break;}
323 ✗ case AV_OPT_TYPE_UINT64:{
324 ✗ double d = num / den;
325 // We must special case uint64_t here as llrint() does not support values
326 // outside the int64_t range and there is no portable function which does
327 // "INT64_MAX + 1ULL" is used as it is representable exactly as IEEE double
328 // while INT64_MAX is not
329 ✗ if (intnum == 1 && d == (double)UINT64_MAX) {
330 ✗ *(uint64_t *)dst = UINT64_MAX;
331 ✗ } else if (d > INT64_MAX + 1ULL) {
332 ✗ *(uint64_t *)dst = (llrint(d - (INT64_MAX + 1ULL)) + (INT64_MAX + 1ULL))*intnum;
333 } else {
334 ✗ *(uint64_t *)dst = llrint(d) * intnum;
335 }
336 ✗ break;}
337 864054 case AV_OPT_TYPE_FLOAT:
338 864054 *(float *)dst = num * intnum / den;
339 864054 break;
340 281412 case AV_OPT_TYPE_DOUBLE:
341 281412 *(double *)dst = num * intnum / den;
342 281412 break;
343 216257 case AV_OPT_TYPE_RATIONAL:
344 case AV_OPT_TYPE_VIDEO_RATE:
345
2/2
✓ Branch 0 taken 216255 times.
✓ Branch 1 taken 2 times.
216257 if ((int) num == num)
346 216255 *(AVRational *)dst = (AVRational) { num *intnum, den };
347 else
348 2 *(AVRational *)dst = double_to_rational(num * intnum / den);
349 216257 break;
350 ✗ default:
351 ✗ return AVERROR(EINVAL);
352 }
353 11396126 return 0;
354 }
355
356 20998 static int hexchar2int(char c) {
357
3/4
✓ Branch 0 taken 20998 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 15124 times.
✓ Branch 3 taken 5874 times.
20998 if (c >= '0' && c <= '9')
358 15124 return c - '0';
359
4/4
✓ Branch 0 taken 5863 times.
✓ Branch 1 taken 11 times.
✓ Branch 2 taken 5862 times.
✓ Branch 3 taken 1 times.
5874 if (c >= 'a' && c <= 'f')
360 5862 return c - 'a' + 10;
361
3/4
✓ Branch 0 taken 12 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 11 times.
✓ Branch 3 taken 1 times.
12 if (c >= 'A' && c <= 'F')
362 11 return c - 'A' + 10;
363 1 return -1;
364 }
365
366 21149 static int set_string_binary(void *obj, const AVOption *o, const char *val, uint8_t **dst)
367 {
368 int *lendst;
369 uint8_t *bin, *ptr;
370 int len;
371
372
1/2
✓ Branch 0 taken 21149 times.
✗ Branch 1 not taken.
21149 if (dst) {
373 21149 lendst = (int *)(dst + 1);
374 21149 av_freep(dst);
375 21149 *lendst = 0;
376 }
377
378
4/4
✓ Branch 0 taken 685 times.
✓ Branch 1 taken 20464 times.
✓ Branch 2 taken 14 times.
✓ Branch 3 taken 671 times.
21149 if (!val || !(len = strlen(val)))
379 20478 return 0;
380
381
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 670 times.
671 if (len & 1)
382 1 return AVERROR(EINVAL);
383 670 len /= 2;
384
385 670 ptr = bin = av_malloc(len);
386
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 670 times.
670 if (!ptr)
387 ✗ return AVERROR(ENOMEM);
388
2/2
✓ Branch 0 taken 10499 times.
✓ Branch 1 taken 669 times.
11168 while (*val) {
389 10499 int a = hexchar2int(*val++);
390 10499 int b = hexchar2int(*val++);
391
3/4
✓ Branch 0 taken 10499 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 10498 times.
10499 if (a < 0 || b < 0) {
392 1 av_free(bin);
393 1 return AVERROR(EINVAL);
394 }
395 10498 *ptr++ = (a << 4) | b;
396 }
397
398
1/2
✓ Branch 0 taken 669 times.
✗ Branch 1 not taken.
669 if (dst) {
399 669 *dst = bin;
400 669 *lendst = len;
401 } else {
402 ✗ av_free(bin);
403 }
404
405 669 return 0;
406 }
407
408 597523 static int set_string(void *obj, const AVOption *o, const char *val, uint8_t **dst)
409 {
410
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 597523 times.
597523 if (!dst)
411 ✗ return 0;
412 597523 av_freep(dst);
413
2/2
✓ Branch 0 taken 492799 times.
✓ Branch 1 taken 104724 times.
597523 if (!val)
414 492799 return 0;
415 104724 *dst = av_strdup(val);
416
1/2
✓ Branch 0 taken 104724 times.
✗ Branch 1 not taken.
104724 return *dst ? 0 : AVERROR(ENOMEM);
417 }
418
419 #define DEFAULT_NUMVAL(opt) ((opt->type == AV_OPT_TYPE_INT64 || \
420 opt->type == AV_OPT_TYPE_UINT64 || \
421 opt->type == AV_OPT_TYPE_CONST || \
422 opt->type == AV_OPT_TYPE_FLAGS || \
423 opt->type == AV_OPT_TYPE_UINT || \
424 opt->type == AV_OPT_TYPE_INT) \
425 ? opt->default_val.i64 \
426 : opt->default_val.dbl)
427
428 162049 static int set_string_number(void *obj, void *target_obj, const AVOption *o, const char *val, void *dst)
429 {
430
1/2
✓ Branch 0 taken 162049 times.
✗ Branch 1 not taken.
162049 void *logctx = dst ? obj : NULL;
431 162049 const enum AVOptionType type = TYPE_BASE(o->type);
432 162049 int ret = 0;
433
434
3/4
✓ Branch 0 taken 160537 times.
✓ Branch 1 taken 1512 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 160537 times.
162049 if (type == AV_OPT_TYPE_RATIONAL || type == AV_OPT_TYPE_VIDEO_RATE) {
435 int num, den;
436 char c;
437
2/2
✓ Branch 0 taken 1482 times.
✓ Branch 1 taken 30 times.
1512 if (sscanf(val, "%d%*1[:/]%d%c", &num, &den, &c) == 2) {
438
2/2
✓ Branch 1 taken 1480 times.
✓ Branch 2 taken 2 times.
1482 if ((ret = write_number(obj, o, dst, 1, den, num, 0)) >= 0)
439 1480 return ret;
440 2 ret = 0;
441 }
442 }
443
444 54121 for (;;) {
445 214690 int i = 0;
446 char buf[256];
447 214690 int cmd = 0;
448 double d;
449 214690 int64_t intnum = 1;
450
451
2/2
✓ Branch 0 taken 123999 times.
✓ Branch 1 taken 90691 times.
214690 if (type == AV_OPT_TYPE_FLAGS) {
452
4/4
✓ Branch 0 taken 24063 times.
✓ Branch 1 taken 99936 times.
✓ Branch 2 taken 29 times.
✓ Branch 3 taken 24034 times.
123999 if (*val == '+' || *val == '-')
453 99965 cmd = *(val++);
454
7/8
✓ Branch 0 taken 1043778 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 973900 times.
✓ Branch 3 taken 69878 times.
✓ Branch 4 taken 919780 times.
✓ Branch 5 taken 54120 times.
✓ Branch 6 taken 919779 times.
✓ Branch 7 taken 1 times.
1043778 for (; i < sizeof(buf) - 1 && val[i] && val[i] != '+' && val[i] != '-'; i++)
455 919779 buf[i] = val[i];
456 123999 buf[i] = 0;
457 }
458
459 {
460 int res;
461 214690 int ci = 0;
462 double const_values[64];
463 const char * const_names[64];
464 214690 int search_flags = (o->flags & AV_OPT_FLAG_CHILD_CONSTS) ? AV_OPT_SEARCH_CHILDREN : 0;
465
2/2
✓ Branch 0 taken 123999 times.
✓ Branch 1 taken 90691 times.
214690 const AVOption *o_named = av_opt_find(target_obj, i ? buf : val, o->unit, 0, search_flags);
466
3/4
✓ Branch 0 taken 159167 times.
✓ Branch 1 taken 55523 times.
✓ Branch 2 taken 159167 times.
✗ Branch 3 not taken.
214690 if (o_named && o_named->type == AV_OPT_TYPE_CONST) {
467
3/12
✓ Branch 0 taken 159167 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 159167 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 159167 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
159167 d = DEFAULT_NUMVAL(o_named);
468
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 159166 times.
159167 if (o_named->flags & AV_OPT_FLAG_DEPRECATED)
469 1 av_log(logctx, AV_LOG_WARNING, "The \"%s\" option is deprecated: %s\n",
470 1 o_named->name, o_named->help);
471 } else {
472
2/2
✓ Branch 0 taken 37976 times.
✓ Branch 1 taken 17547 times.
55523 if (o->unit) {
473
2/2
✓ Branch 1 taken 10728932 times.
✓ Branch 2 taken 37976 times.
10766908 for (o_named = NULL; o_named = av_opt_next(target_obj, o_named); ) {
474
2/2
✓ Branch 0 taken 7536965 times.
✓ Branch 1 taken 3191967 times.
10728932 if (o_named->type == AV_OPT_TYPE_CONST &&
475
1/2
✓ Branch 0 taken 7536965 times.
✗ Branch 1 not taken.
7536965 o_named->unit &&
476
2/2
✓ Branch 0 taken 349195 times.
✓ Branch 1 taken 7187770 times.
7536965 !strcmp(o_named->unit, o->unit)) {
477
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 349195 times.
349195 if (ci + 6 >= FF_ARRAY_ELEMS(const_values)) {
478 ✗ av_log(logctx, AV_LOG_ERROR, "const_values array too small for %s\n", o->unit);
479 8 return AVERROR_PATCHWELCOME;
480 }
481 349195 const_names [ci ] = o_named->name;
482
3/12
✓ Branch 0 taken 349195 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 349195 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 349195 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
349195 const_values[ci++] = DEFAULT_NUMVAL(o_named);
483 }
484 }
485 }
486 55523 const_names [ci ] = "default";
487
10/12
✓ Branch 0 taken 53628 times.
✓ Branch 1 taken 1895 times.
✓ Branch 2 taken 53628 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 53628 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 44776 times.
✓ Branch 7 taken 8852 times.
✓ Branch 8 taken 44669 times.
✓ Branch 9 taken 107 times.
✓ Branch 10 taken 42830 times.
✓ Branch 11 taken 1839 times.
55523 const_values[ci++] = DEFAULT_NUMVAL(o);
488 55523 const_names [ci ] = "max";
489 55523 const_values[ci++] = o->max;
490 55523 const_names [ci ] = "min";
491 55523 const_values[ci++] = o->min;
492 55523 const_names [ci ] = "none";
493 55523 const_values[ci++] = 0;
494 55523 const_names [ci ] = "all";
495 55523 const_values[ci++] = ~0;
496 55523 const_names [ci] = NULL;
497 55523 const_values[ci] = 0;
498
499
2/2
✓ Branch 0 taken 8852 times.
✓ Branch 1 taken 46671 times.
55523 res = av_expr_parse_and_eval(&d, i ? buf : val, const_names,
500 const_values, NULL, NULL, NULL, NULL, NULL, 0, obj);
501
2/2
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 55515 times.
55523 if (res < 0) {
502 8 av_log(logctx, AV_LOG_ERROR, "Unable to parse \"%s\" option value \"%s\"\n", o->name, val);
503 8 return res;
504 }
505 }
506 }
507
3/4
✓ Branch 0 taken 123999 times.
✓ Branch 1 taken 90683 times.
✓ Branch 2 taken 123999 times.
✗ Branch 3 not taken.
214682 if (type == AV_OPT_TYPE_FLAGS && dst) {
508 123999 intnum = *(unsigned int*)dst;
509
2/2
✓ Branch 0 taken 99936 times.
✓ Branch 1 taken 24063 times.
123999 if (cmd == '+')
510 99936 d = intnum | (int64_t)d;
511
2/2
✓ Branch 0 taken 29 times.
✓ Branch 1 taken 24034 times.
24063 else if (cmd == '-')
512 29 d = intnum &~(int64_t)d;
513 }
514
515
2/2
✓ Branch 1 taken 14 times.
✓ Branch 2 taken 214668 times.
214682 if ((ret = write_number(obj, o, dst, d, 1, 1, 0)) < 0)
516 14 return ret;
517 214668 val += i;
518
4/4
✓ Branch 0 taken 123999 times.
✓ Branch 1 taken 90669 times.
✓ Branch 2 taken 69878 times.
✓ Branch 3 taken 54121 times.
214668 if (!i || !*val)
519 160547 return 0;
520 }
521 }
522
523 56153 static int set_string_image_size(void *obj, const AVOption *o, const char *val, int *dst)
524 {
525
1/2
✓ Branch 0 taken 56153 times.
✗ Branch 1 not taken.
56153 void *logctx = dst ? obj : NULL;
526 int tmp[2];
527 int ret;
528
529
3/4
✓ Branch 0 taken 8090 times.
✓ Branch 1 taken 48063 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 8090 times.
56153 if (!val || !strcmp(val, "none")) {
530
1/2
✓ Branch 0 taken 48063 times.
✗ Branch 1 not taken.
48063 if (dst) {
531 48063 dst[0] =
532 48063 dst[1] = 0;
533 }
534 48063 return 0;
535 }
536 8090 ret = av_parse_video_size(&tmp[0], &tmp[1], val);
537
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 8089 times.
8090 if (ret < 0)
538 1 av_log(logctx, AV_LOG_ERROR, "Unable to parse \"%s\" option value \"%s\" as image size\n", o->name, val);
539
1/2
✓ Branch 0 taken 8090 times.
✗ Branch 1 not taken.
8090 if (dst)
540 8090 memcpy(dst, tmp, sizeof(tmp));
541 8090 return ret;
542 }
543
544 10177 static int set_string_video_rate(void *obj, const AVOption *o, const char *val, AVRational *dst)
545 {
546
1/2
✓ Branch 0 taken 10177 times.
✗ Branch 1 not taken.
10177 void *logctx = dst ? obj : NULL;
547 AVRational tmp;
548 10177 int ret = av_parse_video_rate(&tmp, val);
549
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 10176 times.
10177 if (ret < 0)
550 1 av_log(logctx, AV_LOG_ERROR, "Unable to parse \"%s\" option value \"%s\" as video rate\n", o->name, val);
551
1/2
✓ Branch 0 taken 10177 times.
✗ Branch 1 not taken.
10177 if (dst)
552 10177 *dst = tmp;
553 10177 return ret;
554 }
555
556 517 static int set_string_color(void *obj, const AVOption *o, const char *val, uint8_t *dst)
557 {
558
1/2
✓ Branch 0 taken 517 times.
✗ Branch 1 not taken.
517 void *logctx = dst ? obj : NULL;
559 int ret;
560
561
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 517 times.
517 if (!val) {
562 ✗ return 0;
563 } else {
564 uint8_t tmp[4];
565 517 ret = av_parse_color(tmp, val, -1, obj);
566
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 517 times.
517 if (ret < 0)
567 ✗ av_log(logctx, AV_LOG_ERROR, "Unable to parse \"%s\" option value \"%s\" as color\n", o->name, val);
568
1/2
✓ Branch 0 taken 517 times.
✗ Branch 1 not taken.
517 if (dst)
569 517 memcpy(dst, tmp, sizeof(tmp));
570 517 return ret;
571 }
572 return 0;
573 }
574
575 75 static const char *get_bool_name(int val)
576 {
577
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 70 times.
75 if (val < 0)
578 5 return "auto";
579
2/2
✓ Branch 0 taken 22 times.
✓ Branch 1 taken 48 times.
70 return val ? "true" : "false";
580 }
581
582 10361 static int set_string_bool(void *obj, const AVOption *o, const char *val, int *dst)
583 {
584
1/2
✓ Branch 0 taken 10361 times.
✗ Branch 1 not taken.
10361 void *logctx = dst ? obj : NULL;
585 int n;
586
587
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10361 times.
10361 if (!val)
588 ✗ return 0;
589
590
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 10358 times.
10361 if (!strcmp(val, "auto")) {
591 3 n = -1;
592
2/2
✓ Branch 1 taken 1269 times.
✓ Branch 2 taken 9089 times.
10358 } else if (av_match_name(val, "true,y,yes,enable,enabled,on")) {
593 1269 n = 1;
594
2/2
✓ Branch 1 taken 141 times.
✓ Branch 2 taken 8948 times.
9089 } else if (av_match_name(val, "false,n,no,disable,disabled,off")) {
595 141 n = 0;
596 } else {
597 8948 char *end = NULL;
598 8948 n = strtol(val, &end, 10);
599
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 8948 times.
8948 if (val + strlen(val) != end)
600 ✗ goto fail;
601 }
602
603
2/4
✓ Branch 0 taken 10361 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 10361 times.
10361 if (n < o->min || n > o->max)
604 ✗ goto fail;
605
606
1/2
✓ Branch 0 taken 10361 times.
✗ Branch 1 not taken.
10361 if (dst)
607 10361 *dst = n;
608 10361 return 0;
609
610 ✗ fail:
611 ✗ av_log(logctx, AV_LOG_ERROR, "Unable to parse \"%s\" option value \"%s\" as boolean\n", o->name, val);
612 ✗ return AVERROR(EINVAL);
613 }
614
615 5653 static int set_string_fmt(void *obj, const AVOption *o, const char *val, uint8_t *dst,
616 int fmt_nb, int ((*get_fmt)(const char *)), const char *desc,
617 enum AVOptionType type)
618 {
619
1/2
✓ Branch 0 taken 5653 times.
✗ Branch 1 not taken.
5653 void *logctx = dst ? obj : NULL;
620 int fmt, min, max;
621
622
2/4
✓ Branch 0 taken 5653 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 5653 times.
5653 if (!val || !strcmp(val, "none")) {
623 ✗ fmt = -1;
624 } else {
625 5653 fmt = get_fmt(val);
626
2/2
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 5649 times.
5653 if (fmt == -1) {
627 char *tail;
628 4 fmt = strtol(val, &tail, 0);
629
3/4
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
4 if (*tail || (unsigned)fmt >= fmt_nb) {
630 2 av_log(logctx, AV_LOG_ERROR,
631 2 "Unable to parse \"%s\" option value \"%s\" as %s\n", o->name, val, desc);
632 2 return AVERROR(EINVAL);
633 }
634 }
635 }
636
637
2/2
✓ Branch 0 taken 2913 times.
✓ Branch 1 taken 2738 times.
5651 min = FFMAX(o->min, -1);
638
2/2
✓ Branch 0 taken 3319 times.
✓ Branch 1 taken 2332 times.
5651 max = FFMIN(o->max, fmt_nb-1);
639
640 // hack for compatibility with old ffmpeg
641
4/4
✓ Branch 0 taken 2913 times.
✓ Branch 1 taken 2738 times.
✓ Branch 2 taken 2332 times.
✓ Branch 3 taken 581 times.
5651 if(min == 0 && max == 0) {
642 2332 min = -1;
643 2332 max = fmt_nb-1;
644 }
645
646
2/4
✓ Branch 0 taken 5651 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 5651 times.
5651 if (fmt < min || fmt > max) {
647 ✗ av_log(logctx, AV_LOG_ERROR,
648 "Value %d for parameter '%s' out of %s format range [%d - %d]\n",
649 ✗ fmt, o->name, desc, min, max);
650 ✗ return AVERROR(ERANGE);
651 }
652
653
1/2
✓ Branch 0 taken 5651 times.
✗ Branch 1 not taken.
5651 if (dst)
654
2/3
✓ Branch 0 taken 585 times.
✓ Branch 1 taken 5066 times.
✗ Branch 2 not taken.
5651 switch (type) {
655 585 case AV_OPT_TYPE_PIXEL_FMT: *(enum AVPixelFormat *)dst = fmt; break;
656 5066 case AV_OPT_TYPE_SAMPLE_FMT: *(enum AVSampleFormat*)dst = fmt; break;
657 ✗ default: av_unreachable("set_string_fmt() is only called for pixel and sample formats");
658 }
659 5651 return 0;
660 }
661
662 586 static int get_pix_fmt(const char *name)
663 {
664 586 return av_get_pix_fmt(name);
665 }
666
667 586 static int set_string_pixel_fmt(void *obj, const AVOption *o, const char *val, uint8_t *dst)
668 {
669 586 return set_string_fmt(obj, o, val, dst,
670 AV_PIX_FMT_NB, get_pix_fmt,
671 "pixel format", AV_OPT_TYPE_PIXEL_FMT);
672 }
673
674 5067 static int get_sample_fmt(const char *name)
675 {
676 5067 return av_get_sample_fmt(name);
677 }
678
679 5067 static int set_string_sample_fmt(void *obj, const AVOption *o, const char *val, uint8_t *dst)
680 {
681 5067 return set_string_fmt(obj, o, val, dst,
682 AV_SAMPLE_FMT_NB, get_sample_fmt,
683 "sample format", AV_OPT_TYPE_SAMPLE_FMT);
684 }
685
686 64306 static int set_string_dict(void *obj, const AVOption *o, const char *val, uint8_t **dst)
687 {
688 64306 AVDictionary *options = NULL;
689
690
2/2
✓ Branch 0 taken 79 times.
✓ Branch 1 taken 64227 times.
64306 if (val) {
691 79 int ret = av_dict_parse_string(&options, val, "=", ":", 0);
692
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 79 times.
79 if (ret < 0) {
693 ✗ av_dict_free(&options);
694 ✗ return ret;
695 }
696 }
697
698
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 64306 times.
64306 if (!dst) {
699 ✗ av_dict_free(&options);
700 ✗ return 0;
701 }
702
703 64306 av_dict_free((AVDictionary **)dst);
704 64306 *dst = (uint8_t *)options;
705
706 64306 return 0;
707 }
708
709 65369 static int set_string_channel_layout(void *obj, const AVOption *o,
710 const char *val, void *dst)
711 {
712 AVChannelLayout tmp;
713 65369 AVChannelLayout *channel_layout = dst;
714 int ret;
715
1/2
✓ Branch 0 taken 65369 times.
✗ Branch 1 not taken.
65369 if (dst)
716 65369 av_channel_layout_uninit(channel_layout);
717 else
718 ✗ channel_layout = &tmp;
719
2/2
✓ Branch 0 taken 62808 times.
✓ Branch 1 taken 2561 times.
65369 if (!val)
720 62808 return 0;
721 2561 ret = av_channel_layout_from_string(channel_layout, val);
722
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 2560 times.
2561 if (ret < 0)
723 1 return ret;
724
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2560 times.
2560 if (!dst)
725 ✗ av_channel_layout_uninit(channel_layout);
726 2560 return 0;
727 }
728
729 237476 static int opt_set_elem(void *obj, void *target_obj, const AVOption *o,
730 const char *val, void *dst)
731 {
732
1/2
✓ Branch 0 taken 237476 times.
✗ Branch 1 not taken.
237476 void *logctx = dst ? obj : NULL;
733 237476 const enum AVOptionType type = TYPE_BASE(o->type);
734 int ret;
735
736
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 237476 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
237476 if (!val && (type != AV_OPT_TYPE_STRING &&
737 ✗ type != AV_OPT_TYPE_PIXEL_FMT && type != AV_OPT_TYPE_SAMPLE_FMT &&
738 ✗ type != AV_OPT_TYPE_IMAGE_SIZE &&
739 ✗ type != AV_OPT_TYPE_DURATION && type != AV_OPT_TYPE_COLOR &&
740 type != AV_OPT_TYPE_BOOL))
741 ✗ return AVERROR(EINVAL);
742
743
12/13
✓ Branch 0 taken 10361 times.
✓ Branch 1 taken 67624 times.
✓ Branch 2 taken 33 times.
✓ Branch 3 taken 147340 times.
✓ Branch 4 taken 2986 times.
✓ Branch 5 taken 350 times.
✓ Branch 6 taken 586 times.
✓ Branch 7 taken 5067 times.
✓ Branch 8 taken 515 times.
✓ Branch 9 taken 87 times.
✓ Branch 10 taken 2458 times.
✓ Branch 11 taken 69 times.
✗ Branch 12 not taken.
237476 switch (type) {
744 10361 case AV_OPT_TYPE_BOOL:
745 10361 return set_string_bool(obj, o, val, dst);
746 67624 case AV_OPT_TYPE_STRING:
747 67624 return set_string(obj, o, val, dst);
748 33 case AV_OPT_TYPE_BINARY:
749 33 return set_string_binary(obj, o, val, dst);
750 147340 case AV_OPT_TYPE_FLAGS:
751 case AV_OPT_TYPE_INT:
752 case AV_OPT_TYPE_UINT:
753 case AV_OPT_TYPE_INT64:
754 case AV_OPT_TYPE_UINT64:
755 case AV_OPT_TYPE_FLOAT:
756 case AV_OPT_TYPE_DOUBLE:
757 case AV_OPT_TYPE_RATIONAL:
758 147340 return set_string_number(obj, target_obj, o, val, dst);
759 2986 case AV_OPT_TYPE_IMAGE_SIZE:
760 2986 return set_string_image_size(obj, o, val, dst);
761 350 case AV_OPT_TYPE_VIDEO_RATE: {
762 AVRational tmp;
763 350 ret = set_string_video_rate(obj, o, val, &tmp);
764
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 349 times.
350 if (ret < 0)
765 1 return ret;
766 349 return write_number(obj, o, dst, 1, tmp.den, tmp.num, 0);
767 }
768 586 case AV_OPT_TYPE_PIXEL_FMT:
769 586 return set_string_pixel_fmt(obj, o, val, dst);
770 5067 case AV_OPT_TYPE_SAMPLE_FMT:
771 5067 return set_string_sample_fmt(obj, o, val, dst);
772 515 case AV_OPT_TYPE_DURATION:
773 {
774 515 int64_t usecs = 0;
775
1/2
✓ Branch 0 taken 515 times.
✗ Branch 1 not taken.
515 if (val) {
776
2/2
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 514 times.
515 if ((ret = av_parse_time(&usecs, val, 1)) < 0) {
777 1 av_log(logctx, AV_LOG_ERROR, "Unable to parse \"%s\" option value \"%s\" as duration\n", o->name, val);
778 1 return ret;
779 }
780 }
781
2/4
✓ Branch 0 taken 514 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 514 times.
514 if (usecs < o->min || usecs > o->max) {
782 ✗ av_log(logctx, AV_LOG_ERROR, "Value %f for parameter '%s' out of range [%g - %g]\n",
783 ✗ usecs / 1000000.0, o->name, o->min / 1000000.0, o->max / 1000000.0);
784 ✗ return AVERROR(ERANGE);
785 }
786
1/2
✓ Branch 0 taken 514 times.
✗ Branch 1 not taken.
514 if (dst)
787 514 *(int64_t *)dst = usecs;
788 514 return 0;
789 }
790 87 case AV_OPT_TYPE_COLOR:
791 87 return set_string_color(obj, o, val, dst);
792 2458 case AV_OPT_TYPE_CHLAYOUT:
793 2458 ret = set_string_channel_layout(obj, o, val, dst);
794
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 2457 times.
2458 if (ret < 0) {
795 1 av_log(logctx, AV_LOG_ERROR, "Unable to parse \"%s\" option value \"%s\" as channel layout\n", o->name, val);
796 1 ret = AVERROR(EINVAL);
797 }
798 2458 return ret;
799 69 case AV_OPT_TYPE_DICT:
800 69 return set_string_dict(obj, o, val, dst);
801 }
802
803 ✗ av_log(logctx, AV_LOG_ERROR, "Invalid option type.\n");
804 ✗ return AVERROR(EINVAL);
805 }
806
807 2711 static int opt_set_array(void *obj, void *target_obj, const AVOption *o,
808 const char *val, void *dst)
809 {
810 2711 const AVOptionArrayDef *arr = o->default_val.arr;
811 2711 const size_t elem_size = opt_type_desc[TYPE_BASE(o->type)].size;
812 2711 const uint8_t sep = opt_array_sep(o);
813 2711 uint8_t *str = NULL;
814
815
1/2
✓ Branch 0 taken 2711 times.
✗ Branch 1 not taken.
2711 void *logctx = dst ? obj : NULL;
816 2711 void *elems = NULL;
817 2711 unsigned nb_elems = 0;
818 int ret;
819
820
4/4
✓ Branch 0 taken 2699 times.
✓ Branch 1 taken 12 times.
✓ Branch 2 taken 2697 times.
✓ Branch 3 taken 2 times.
2711 if (val && *val) {
821 2697 str = av_malloc(strlen(val) + 1);
822
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2697 times.
2697 if (!str)
823 ✗ return AVERROR(ENOMEM);
824 }
825
826 // split and unescape the string
827
4/4
✓ Branch 0 taken 7175 times.
✓ Branch 1 taken 12 times.
✓ Branch 2 taken 4477 times.
✓ Branch 3 taken 2698 times.
7187 while (val && *val) {
828 4477 uint8_t *p = str;
829 void *tmp;
830
831
5/6
✓ Branch 0 taken 4464 times.
✓ Branch 1 taken 13 times.
✓ Branch 2 taken 32 times.
✓ Branch 3 taken 4432 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 32 times.
4477 if (arr && arr->size_max && nb_elems >= arr->size_max) {
832 ✗ av_log(logctx, AV_LOG_ERROR,
833 "Cannot assign more than %u elements to array option %s\n",
834 ✗ arr->size_max, o->name);
835 ✗ ret = AVERROR(EINVAL);
836 ✗ goto fail;
837 }
838
839
2/2
✓ Branch 0 taken 21252 times.
✓ Branch 1 taken 2697 times.
23949 for (; *val; val++, p++) {
840
3/4
✓ Branch 0 taken 84 times.
✓ Branch 1 taken 21168 times.
✓ Branch 2 taken 84 times.
✗ Branch 3 not taken.
21252 if (*val == '\\' && val[1])
841 84 val++;
842
2/2
✓ Branch 0 taken 1780 times.
✓ Branch 1 taken 19388 times.
21168 else if (*val == sep) {
843 1780 val++;
844 1780 break;
845 }
846 19472 *p = *val;
847 }
848 4477 *p = 0;
849
850 4477 tmp = av_realloc_array(elems, nb_elems + 1, elem_size);
851
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4477 times.
4477 if (!tmp) {
852 ✗ ret = AVERROR(ENOMEM);
853 ✗ goto fail;
854 }
855 4477 elems = tmp;
856
857 4477 tmp = opt_array_pelem(o, elems, nb_elems);
858 4477 memset(tmp, 0, elem_size);
859
860 4477 ret = opt_set_elem(obj, target_obj, o, str, tmp);
861
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 4476 times.
4477 if (ret < 0)
862 1 goto fail;
863 4476 nb_elems++;
864 }
865 2710 av_freep(&str);
866
867
1/2
✓ Branch 0 taken 2710 times.
✗ Branch 1 not taken.
2710 if (dst)
868 2710 opt_free_array(o, dst, opt_array_pcount(dst));
869
870
3/4
✓ Branch 0 taken 2691 times.
✓ Branch 1 taken 19 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 2691 times.
2710 if (arr && nb_elems < arr->size_min) {
871 ✗ av_log(logctx, AV_LOG_ERROR,
872 "Cannot assign fewer than %u elements to array option %s\n",
873 ✗ arr->size_min, o->name);
874 ✗ ret = AVERROR(EINVAL);
875 ✗ goto fail;
876 }
877
878
1/2
✓ Branch 0 taken 2710 times.
✗ Branch 1 not taken.
2710 if (dst) {
879 2710 *((void **)dst) = elems;
880 2710 *opt_array_pcount(dst) = nb_elems;
881 } else
882 ✗ opt_free_array(o, &elems, &nb_elems);
883
884 2710 return 0;
885 1 fail:
886 1 av_freep(&str);
887 1 opt_free_array(o, &elems, &nb_elems);
888 1 return ret;
889 }
890
891 288098 int av_opt_set(void *obj, const char *name, const char *val, int search_flags)
892 {
893 void *dst, *target_obj;
894 const AVOption *o;
895 int ret;
896
897 288098 ret = opt_set_init(obj, name, search_flags, 0, &target_obj, &o, &dst);
898
2/2
✓ Branch 0 taken 52408 times.
✓ Branch 1 taken 235690 times.
288098 if (ret < 0)
899 52408 return ret;
900
901 235690 return ((o->type & AV_OPT_TYPE_FLAG_ARRAY) ?
902
2/2
✓ Branch 0 taken 2691 times.
✓ Branch 1 taken 232999 times.
235690 opt_set_array : opt_set_elem)(obj, target_obj, o, val, dst);
903 }
904
905 #define OPT_EVAL_NUMBER(name, opttype, vartype) \
906 int av_opt_eval_ ## name(void *obj, const AVOption *o, \
907 const char *val, vartype *name ## _out) \
908 { \
909 if (!o || o->type != opttype || o->flags & AV_OPT_FLAG_READONLY) \
910 return AVERROR(EINVAL); \
911 return set_string_number(obj, obj, o, val, name ## _out); \
912 }
913
914
3/6
✓ Branch 0 taken 14676 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 14676 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 14676 times.
14676 OPT_EVAL_NUMBER(flags, AV_OPT_TYPE_FLAGS, int)
915
3/6
✓ Branch 0 taken 33 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 33 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 33 times.
33 OPT_EVAL_NUMBER(int, AV_OPT_TYPE_INT, int)
916 ✗ OPT_EVAL_NUMBER(uint, AV_OPT_TYPE_UINT, unsigned)
917 ✗ OPT_EVAL_NUMBER(int64, AV_OPT_TYPE_INT64, int64_t)
918 ✗ OPT_EVAL_NUMBER(float, AV_OPT_TYPE_FLOAT, float)
919 ✗ OPT_EVAL_NUMBER(double, AV_OPT_TYPE_DOUBLE, double)
920 ✗ OPT_EVAL_NUMBER(q, AV_OPT_TYPE_RATIONAL, AVRational)
921
922 38650 static int set_number(void *obj, const char *name, double num, int den, int64_t intnum,
923 int search_flags, int require_type)
924 {
925 void *dst;
926 const AVOption *o;
927 int ret;
928
929 38650 ret = opt_set_init(obj, name, search_flags, require_type, NULL, &o, &dst);
930
2/2
✓ Branch 0 taken 16582 times.
✓ Branch 1 taken 22068 times.
38650 if (ret < 0)
931 16582 return ret;
932
1/2
✓ Branch 0 taken 22068 times.
✗ Branch 1 not taken.
22068 if (dst)
933 22068 ret = write_number(obj, o, dst, num, den, intnum, 0);
934
935 22068 return ret;
936 }
937
938 38612 int av_opt_set_int(void *obj, const char *name, int64_t val, int search_flags)
939 {
940 38612 return set_number(obj, name, 1, 1, val, search_flags, 0);
941 }
942
943 24 int av_opt_set_double(void *obj, const char *name, double val, int search_flags)
944 {
945 24 return set_number(obj, name, val, 1, 1, search_flags, 0);
946 }
947
948 14 int av_opt_set_q(void *obj, const char *name, AVRational val, int search_flags)
949 {
950 14 return set_number(obj, name, val.num, val.den, 1, search_flags, 0);
951 }
952
953 ✗ int av_opt_set_bin(void *obj, const char *name, const uint8_t *val, int len, int search_flags)
954 {
955 uint8_t *ptr;
956 uint8_t **dst;
957 int *lendst;
958 int ret;
959
960 ✗ ret = opt_set_init(obj, name, search_flags, AV_OPT_TYPE_BINARY,
961 NULL, NULL, (void**)&dst);
962 ✗ if (ret < 0)
963 ✗ return ret;
964
965 ✗ if (dst) {
966 ✗ ptr = len ? av_malloc(len) : NULL;
967 ✗ if (len && !ptr)
968 ✗ return AVERROR(ENOMEM);
969
970 ✗ lendst = (int *)(dst + 1);
971
972 ✗ av_free(*dst);
973 ✗ *dst = ptr;
974 ✗ *lendst = len;
975 ✗ if (len)
976 ✗ memcpy(ptr, val, len);
977 }
978
979 ✗ return 0;
980 }
981
982 ✗ int av_opt_set_image_size(void *obj, const char *name, int w, int h, int search_flags)
983 {
984 const AVOption *o;
985 void *logctx;
986 int *dst;
987 int ret;
988
989 ✗ ret = opt_set_init(obj, name, search_flags, AV_OPT_TYPE_IMAGE_SIZE,
990 NULL, &o, (void**)&dst);
991 ✗ if (ret < 0)
992 ✗ return ret;
993
994 ✗ logctx = dst ? obj : NULL;
995
996 ✗ if (w<0 || h<0) {
997 ✗ av_log(logctx, AV_LOG_ERROR,
998 ✗ "Invalid negative size value %dx%d for size '%s'\n", w, h, o->name);
999 ✗ return AVERROR(EINVAL);
1000 }
1001
1002 ✗ if (dst) {
1003 ✗ dst[0] = w;
1004 ✗ dst[1] = h;
1005 }
1006
1007 ✗ return 0;
1008 }
1009
1010 ✗ int av_opt_set_video_rate(void *obj, const char *name, AVRational val, int search_flags)
1011 {
1012 ✗ return set_number(obj, name, val.num, val.den, 1, search_flags, AV_OPT_TYPE_VIDEO_RATE);
1013 }
1014
1015 3 static int set_format(void *obj, const char *name, int fmt, int search_flags,
1016 enum AVOptionType type, const char *desc, int nb_fmts)
1017 {
1018 const AVOption *o;
1019 void *logctx;
1020 int *dst;
1021 int min, max, ret;
1022
1023 3 ret = opt_set_init(obj, name, search_flags, type, NULL, &o, (void**)&dst);
1024
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3 times.
3 if (ret < 0)
1025 ✗ return ret;
1026
1027
1/2
✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
3 logctx = dst ? obj : NULL;
1028
1029
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3 times.
3 min = FFMAX(o->min, -1);
1030
1/2
✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
3 max = FFMIN(o->max, nb_fmts-1);
1031
1032
2/4
✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 3 times.
3 if (fmt < min || fmt > max) {
1033 ✗ av_log(logctx, AV_LOG_ERROR,
1034 "Value %d for parameter '%s' out of %s format range [%d - %d]\n",
1035 fmt, name, desc, min, max);
1036 ✗ return AVERROR(ERANGE);
1037 }
1038
1/2
✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
3 if (dst)
1039 3 *dst = fmt;
1040 3 return 0;
1041 }
1042
1043 ✗ int av_opt_set_pixel_fmt(void *obj, const char *name, enum AVPixelFormat fmt, int search_flags)
1044 {
1045 ✗ return set_format(obj, name, fmt, search_flags, AV_OPT_TYPE_PIXEL_FMT, "pixel", AV_PIX_FMT_NB);
1046 }
1047
1048 3 int av_opt_set_sample_fmt(void *obj, const char *name, enum AVSampleFormat fmt, int search_flags)
1049 {
1050 3 return set_format(obj, name, fmt, search_flags, AV_OPT_TYPE_SAMPLE_FMT, "sample", AV_SAMPLE_FMT_NB);
1051 }
1052
1053 ✗ int av_opt_set_dict_val(void *obj, const char *name, const AVDictionary *val,
1054 int search_flags)
1055 {
1056 AVDictionary **dst;
1057 int ret;
1058
1059 ✗ ret = opt_set_init(obj, name, search_flags, AV_OPT_TYPE_DICT, NULL, NULL,
1060 (void**)&dst);
1061 ✗ if (ret < 0)
1062 ✗ return ret;
1063
1064 ✗ if (dst) {
1065 ✗ av_dict_free(dst);
1066
1067 ✗ ret = av_dict_copy(dst, val, 0);
1068 }
1069
1070 ✗ return ret;
1071 }
1072
1073 7768 int av_opt_set_chlayout(void *obj, const char *name,
1074 const AVChannelLayout *channel_layout,
1075 int search_flags)
1076 {
1077 AVChannelLayout *dst;
1078 int ret;
1079
1080 7768 ret = opt_set_init(obj, name, search_flags, AV_OPT_TYPE_CHLAYOUT, NULL, NULL,
1081 (void**)&dst);
1082
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7768 times.
7768 if (ret < 0)
1083 ✗ return ret;
1084
1085
1/2
✓ Branch 0 taken 7768 times.
✗ Branch 1 not taken.
7768 if (dst)
1086 7768 ret = av_channel_layout_copy(dst, channel_layout);
1087
1088 7768 return ret;
1089 }
1090
1091 5 static void format_duration(char *buf, size_t size, int64_t d)
1092 {
1093 char *e;
1094
1095
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 av_assert0(size >= 25);
1096
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
5 if (d < 0 && d != INT64_MIN) {
1097 ✗ *(buf++) = '-';
1098 ✗ size--;
1099 ✗ d = -d;
1100 }
1101
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 if (d == INT64_MAX)
1102 ✗ snprintf(buf, size, "INT64_MAX");
1103
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 else if (d == INT64_MIN)
1104 ✗ snprintf(buf, size, "INT64_MIN");
1105
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 else if (d > (int64_t)3600*1000000)
1106 ✗ snprintf(buf, size, "%"PRId64":%02d:%02d.%06d", d / 3600000000,
1107 ✗ (int)((d / 60000000) % 60),
1108 ✗ (int)((d / 1000000) % 60),
1109 ✗ (int)(d % 1000000));
1110
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 else if (d > 60*1000000)
1111 ✗ snprintf(buf, size, "%d:%02d.%06d",
1112 ✗ (int)(d / 60000000),
1113 ✗ (int)((d / 1000000) % 60),
1114 ✗ (int)(d % 1000000));
1115 else
1116 5 snprintf(buf, size, "%d.%06d",
1117 5 (int)(d / 1000000),
1118 5 (int)(d % 1000000));
1119 5 e = buf + strlen(buf);
1120
3/4
✓ Branch 0 taken 20 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 15 times.
✓ Branch 3 taken 5 times.
20 while (e > buf && e[-1] == '0')
1121 15 *(--e) = 0;
1122
2/4
✓ Branch 0 taken 5 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 5 times.
5 if (e > buf && e[-1] == '.')
1123 ✗ *(--e) = 0;
1124 5 }
1125
1126 7367 static int opt_get_elem(const AVOption *o, uint8_t **pbuf, size_t buf_len,
1127 const void *dst, int search_flags)
1128 {
1129 int ret;
1130
1131
17/20
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 6883 times.
✓ Branch 2 taken 126 times.
✓ Branch 3 taken 31 times.
✓ Branch 4 taken 36 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 48 times.
✓ Branch 7 taken 8 times.
✓ Branch 8 taken 48 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 35 times.
✓ Branch 11 taken 12 times.
✓ Branch 12 taken 6 times.
✓ Branch 13 taken 4 times.
✓ Branch 14 taken 4 times.
✓ Branch 15 taken 4 times.
✓ Branch 16 taken 4 times.
✓ Branch 17 taken 14 times.
✓ Branch 18 taken 32 times.
✗ Branch 19 not taken.
7367 switch (TYPE_BASE(o->type)) {
1132 72 case AV_OPT_TYPE_BOOL:
1133 72 ret = snprintf(*pbuf, buf_len, "%s", get_bool_name(*(int *)dst));
1134 72 break;
1135 6883 case AV_OPT_TYPE_FLAGS:
1136 6883 ret = snprintf(*pbuf, buf_len, "0x%08X", *(int *)dst);
1137 6883 break;
1138 126 case AV_OPT_TYPE_INT:
1139 126 ret = snprintf(*pbuf, buf_len, "%d", *(int *)dst);
1140 126 break;
1141 31 case AV_OPT_TYPE_UINT:
1142 31 ret = snprintf(*pbuf, buf_len, "%u", *(unsigned *)dst);
1143 31 break;
1144 36 case AV_OPT_TYPE_INT64:
1145 36 ret = snprintf(*pbuf, buf_len, "%"PRId64, *(int64_t *)dst);
1146 36 break;
1147 ✗ case AV_OPT_TYPE_UINT64:
1148 ✗ ret = snprintf(*pbuf, buf_len, "%"PRIu64, *(uint64_t *)dst);
1149 ✗ break;
1150 48 case AV_OPT_TYPE_FLOAT:
1151 48 ret = snprintf(*pbuf, buf_len, "%f", *(float *)dst);
1152 48 break;
1153 8 case AV_OPT_TYPE_DOUBLE:
1154 8 ret = snprintf(*pbuf, buf_len, "%f", *(double *)dst);
1155 8 break;
1156 48 case AV_OPT_TYPE_VIDEO_RATE:
1157 case AV_OPT_TYPE_RATIONAL:
1158 48 ret = snprintf(*pbuf, buf_len, "%d/%d", ((AVRational *)dst)->num, ((AVRational *)dst)->den);
1159 48 break;
1160 ✗ case AV_OPT_TYPE_CONST:
1161 ✗ ret = snprintf(*pbuf, buf_len, "%"PRId64, o->default_val.i64);
1162 ✗ break;
1163 35 case AV_OPT_TYPE_STRING:
1164
1/2
✓ Branch 0 taken 35 times.
✗ Branch 1 not taken.
35 if (*(uint8_t **)dst) {
1165 35 *pbuf = av_strdup(*(uint8_t **)dst);
1166 ✗ } else if (search_flags & AV_OPT_ALLOW_NULL) {
1167 ✗ *pbuf = NULL;
1168 ✗ return 0;
1169 } else {
1170 ✗ *pbuf = av_strdup("");
1171 }
1172
1/2
✓ Branch 0 taken 35 times.
✗ Branch 1 not taken.
35 return *pbuf ? 0 : AVERROR(ENOMEM);
1173 12 case AV_OPT_TYPE_BINARY: {
1174 const uint8_t *bin;
1175 int len;
1176
1177
3/4
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 4 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 8 times.
12 if (!*(uint8_t **)dst && (search_flags & AV_OPT_ALLOW_NULL)) {
1178 ✗ *pbuf = NULL;
1179 ✗ return 0;
1180 }
1181 12 len = *(int *)(((uint8_t *)dst) + sizeof(uint8_t *));
1182
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 12 times.
12 if ((uint64_t)len * 2 + 1 > INT_MAX)
1183 ✗ return AVERROR(EINVAL);
1184
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 12 times.
12 if (!(*pbuf = av_malloc(len * 2 + 1)))
1185 ✗ return AVERROR(ENOMEM);
1186
2/2
✓ Branch 0 taken 8 times.
✓ Branch 1 taken 4 times.
12 if (!len) {
1187 8 *pbuf[0] = '\0';
1188 8 return 0;
1189 }
1190 4 bin = *(uint8_t **)dst;
1191
2/2
✓ Branch 0 taken 16 times.
✓ Branch 1 taken 4 times.
20 for (int i = 0; i < len; i++)
1192 16 snprintf(*pbuf + i * 2, 3, "%02X", bin[i]);
1193 4 return 0;
1194 }
1195 6 case AV_OPT_TYPE_IMAGE_SIZE:
1196 6 ret = snprintf(*pbuf, buf_len, "%dx%d", ((int *)dst)[0], ((int *)dst)[1]);
1197 6 break;
1198 4 case AV_OPT_TYPE_PIXEL_FMT:
1199 4 ret = snprintf(*pbuf, buf_len, "%s", (char *)av_x_if_null(av_get_pix_fmt_name(*(enum AVPixelFormat *)dst), "none"));
1200 4 break;
1201 4 case AV_OPT_TYPE_SAMPLE_FMT:
1202 4 ret = snprintf(*pbuf, buf_len, "%s", (char *)av_x_if_null(av_get_sample_fmt_name(*(enum AVSampleFormat *)dst), "none"));
1203 4 break;
1204 4 case AV_OPT_TYPE_DURATION: {
1205 4 int64_t i64 = *(int64_t *)dst;
1206 4 format_duration(*pbuf, buf_len, i64);
1207 4 ret = strlen(*pbuf); // no overflow possible, checked by an assert
1208 4 break;
1209 }
1210 4 case AV_OPT_TYPE_COLOR:
1211 4 ret = snprintf(*pbuf, buf_len, "0x%02x%02x%02x%02x",
1212 4 (int)((uint8_t *)dst)[0], (int)((uint8_t *)dst)[1],
1213 4 (int)((uint8_t *)dst)[2], (int)((uint8_t *)dst)[3]);
1214 4 break;
1215 14 case AV_OPT_TYPE_CHLAYOUT:
1216 14 ret = av_channel_layout_describe(dst, *pbuf, buf_len);
1217 14 break;
1218 32 case AV_OPT_TYPE_DICT:
1219
3/4
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 28 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 4 times.
32 if (!*(AVDictionary **)dst && (search_flags & AV_OPT_ALLOW_NULL)) {
1220 ✗ *pbuf = NULL;
1221 ✗ return 0;
1222 }
1223 32 return av_dict_get_string(*(AVDictionary **)dst, (char **)pbuf, '=', ':');
1224 ✗ default:
1225 ✗ return AVERROR(EINVAL);
1226 }
1227
1228 7288 return ret;
1229 }
1230
1231 110 static int opt_get_array(const AVOption *o, void *dst, uint8_t **out_val)
1232 {
1233 110 const unsigned count = *opt_array_pcount(dst);
1234 110 const uint8_t sep = opt_array_sep(o);
1235
1236 110 uint8_t *str = NULL;
1237 110 size_t str_len = 0;
1238 int ret;
1239
1240 110 *out_val = NULL;
1241
1242
2/2
✓ Branch 0 taken 77 times.
✓ Branch 1 taken 110 times.
187 for (unsigned i = 0; i < count; i++) {
1243 77 uint8_t buf[128], *out = buf;
1244 size_t out_len;
1245
1246 77 ret = opt_get_elem(o, &out, sizeof(buf),
1247 77 opt_array_pelem(o, *(void **)dst, i), 0);
1248
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 77 times.
77 if (ret < 0)
1249 ✗ goto fail;
1250
1251 77 out_len = strlen(out);
1252
3/4
✓ Branch 0 taken 57 times.
✓ Branch 1 taken 20 times.
✓ Branch 2 taken 77 times.
✗ Branch 3 not taken.
77 if (out_len > SIZE_MAX / 2 - !!i ||
1253
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 77 times.
77 !!i + out_len * 2 > SIZE_MAX - str_len - 1) {
1254 ✗ ret = AVERROR(ERANGE);
1255 ✗ goto fail;
1256 }
1257
1258 // terminator escaping separator
1259 // ↓ ↓ ↓
1260 77 ret = av_reallocp(&str, str_len + 1 + out_len * 2 + !!i);
1261
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 77 times.
77 if (ret < 0)
1262 ✗ goto fail;
1263
1264 // add separator if needed
1265
2/2
✓ Branch 0 taken 57 times.
✓ Branch 1 taken 20 times.
77 if (i)
1266 57 str[str_len++] = sep;
1267
1268 // escape the element
1269
2/2
✓ Branch 0 taken 643 times.
✓ Branch 1 taken 77 times.
720 for (unsigned j = 0; j < out_len; j++) {
1270 643 uint8_t val = out[j];
1271
4/4
✓ Branch 0 taken 625 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 45 times.
✓ Branch 3 taken 580 times.
643 if (val == sep || val == '\\')
1272 63 str[str_len++] = '\\';
1273 643 str[str_len++] = val;
1274 }
1275 77 str[str_len] = 0;
1276
1277 77 fail:
1278
2/2
✓ Branch 0 taken 45 times.
✓ Branch 1 taken 32 times.
77 if (out != buf)
1279 45 av_freep(&out);
1280
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 77 times.
77 if (ret < 0) {
1281 ✗ av_freep(&str);
1282 ✗ return ret;
1283 }
1284 }
1285
1286 110 *out_val = str;
1287
1288 110 return 0;
1289 }
1290
1291 12368 int av_opt_get(void *obj, const char *name, int search_flags, uint8_t **out_val)
1292 {
1293 void *dst, *target_obj;
1294 12368 const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
1295 uint8_t *out, buf[128];
1296 int ret;
1297
1298
4/8
✓ Branch 0 taken 7373 times.
✓ Branch 1 taken 4995 times.
✓ Branch 2 taken 7373 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 7373 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
12368 if (!o || !target_obj || (o->offset<=0 && o->type != AV_OPT_TYPE_CONST))
1299 4995 return AVERROR_OPTION_NOT_FOUND;
1300
1301
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7373 times.
7373 if (o->flags & AV_OPT_FLAG_DEPRECATED)
1302 ✗ av_log(obj, AV_LOG_WARNING, "The \"%s\" option is deprecated: %s\n", name, o->help);
1303
1304 7373 dst = (uint8_t *)target_obj + o->offset;
1305
1306
2/2
✓ Branch 0 taken 88 times.
✓ Branch 1 taken 7285 times.
7373 if (o->type & AV_OPT_TYPE_FLAG_ARRAY) {
1307 88 ret = opt_get_array(o, dst, out_val);
1308
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 88 times.
88 if (ret < 0)
1309 ✗ return ret;
1310
4/4
✓ Branch 0 taken 79 times.
✓ Branch 1 taken 9 times.
✓ Branch 2 taken 78 times.
✓ Branch 3 taken 1 times.
88 if (!*out_val && !(search_flags & AV_OPT_ALLOW_NULL)) {
1311 78 *out_val = av_strdup("");
1312
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 78 times.
78 if (!*out_val)
1313 ✗ return AVERROR(ENOMEM);
1314 }
1315 88 return 0;
1316 }
1317
1318 7285 buf[0] = 0;
1319 7285 out = buf;
1320 7285 ret = opt_get_elem(o, &out, sizeof(buf), dst, search_flags);
1321
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7285 times.
7285 if (ret < 0)
1322 ✗ return ret;
1323
2/2
✓ Branch 0 taken 34 times.
✓ Branch 1 taken 7251 times.
7285 if (out != buf) {
1324 34 *out_val = out;
1325 34 return 0;
1326 }
1327
1328
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7251 times.
7251 if (ret >= sizeof(buf))
1329 ✗ return AVERROR(EINVAL);
1330 7251 *out_val = av_strdup(out);
1331
1/2
✓ Branch 0 taken 7251 times.
✗ Branch 1 not taken.
7251 return *out_val ? 0 : AVERROR(ENOMEM);
1332 }
1333
1334 25240 static int get_number(void *obj, const char *name, double *num, int *den, int64_t *intnum,
1335 int search_flags)
1336 {
1337 void *dst, *target_obj;
1338 25240 const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
1339
3/4
✓ Branch 0 taken 25226 times.
✓ Branch 1 taken 14 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 25226 times.
25240 if (!o || !target_obj)
1340 14 return AVERROR_OPTION_NOT_FOUND;
1341
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 25226 times.
25226 if (o->type & AV_OPT_TYPE_FLAG_ARRAY)
1342 ✗ return AVERROR(EINVAL);
1343
1344 25226 dst = ((uint8_t *)target_obj) + o->offset;
1345
1346 25226 return read_number(o, dst, num, den, intnum);
1347 }
1348
1349 25240 int av_opt_get_int(void *obj, const char *name, int search_flags, int64_t *out_val)
1350 {
1351 25240 int64_t intnum = 1;
1352 25240 double num = 1;
1353 25240 int ret, den = 1;
1354
1355
2/2
✓ Branch 1 taken 14 times.
✓ Branch 2 taken 25226 times.
25240 if ((ret = get_number(obj, name, &num, &den, &intnum, search_flags)) < 0)
1356 14 return ret;
1357
1/2
✓ Branch 0 taken 25226 times.
✗ Branch 1 not taken.
25226 if (num == den)
1358 25226 *out_val = intnum;
1359 else
1360 ✗ *out_val = num * intnum / den;
1361 25226 return 0;
1362 }
1363
1364 ✗ int av_opt_get_double(void *obj, const char *name, int search_flags, double *out_val)
1365 {
1366 ✗ int64_t intnum = 1;
1367 ✗ double num = 1;
1368 ✗ int ret, den = 1;
1369
1370 ✗ if ((ret = get_number(obj, name, &num, &den, &intnum, search_flags)) < 0)
1371 ✗ return ret;
1372 ✗ *out_val = num * intnum / den;
1373 ✗ return 0;
1374 }
1375
1376 ✗ int av_opt_get_q(void *obj, const char *name, int search_flags, AVRational *out_val)
1377 {
1378 ✗ int64_t intnum = 1;
1379 ✗ double num = 1;
1380 ✗ int ret, den = 1;
1381
1382 ✗ if ((ret = get_number(obj, name, &num, &den, &intnum, search_flags)) < 0)
1383 ✗ return ret;
1384
1385 ✗ if (num == 1.0 && (int)intnum == intnum)
1386 ✗ *out_val = (AVRational){intnum, den};
1387 else
1388 ✗ *out_val = double_to_rational(num*intnum/den);
1389 ✗ return 0;
1390 }
1391
1392 ✗ int av_opt_get_image_size(void *obj, const char *name, int search_flags, int *w_out, int *h_out)
1393 {
1394 void *dst, *target_obj;
1395 ✗ const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
1396 ✗ if (!o || !target_obj)
1397 ✗ return AVERROR_OPTION_NOT_FOUND;
1398 ✗ if (o->type != AV_OPT_TYPE_IMAGE_SIZE) {
1399 ✗ av_log(obj, AV_LOG_ERROR,
1400 "The value for option '%s' is not a image size.\n", name);
1401 ✗ return AVERROR(EINVAL);
1402 }
1403
1404 ✗ dst = ((uint8_t*)target_obj) + o->offset;
1405 ✗ if (w_out) *w_out = *(int *)dst;
1406 ✗ if (h_out) *h_out = *((int *)dst+1);
1407 ✗ return 0;
1408 }
1409
1410 ✗ int av_opt_get_video_rate(void *obj, const char *name, int search_flags, AVRational *out_val)
1411 {
1412 ✗ return av_opt_get_q(obj, name, search_flags, out_val);
1413 }
1414
1415 3400 static int get_format(void *obj, const char *name, int search_flags, void *out_fmt,
1416 enum AVOptionType type, const char *desc)
1417 {
1418 void *dst, *target_obj;
1419 3400 const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
1420
2/4
✓ Branch 0 taken 3400 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 3400 times.
3400 if (!o || !target_obj)
1421 ✗ return AVERROR_OPTION_NOT_FOUND;
1422
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3400 times.
3400 if (o->type != type) {
1423 ✗ av_log(obj, AV_LOG_ERROR,
1424 "The value for option '%s' is not a %s format.\n", desc, name);
1425 ✗ return AVERROR(EINVAL);
1426 }
1427
1428 3400 dst = ((uint8_t*)target_obj) + o->offset;
1429
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3400 times.
3400 if (type == AV_OPT_TYPE_PIXEL_FMT)
1430 ✗ *(enum AVPixelFormat *)out_fmt = *(enum AVPixelFormat *)dst;
1431 else
1432 3400 *(enum AVSampleFormat*)out_fmt = *(enum AVSampleFormat*)dst;
1433
1434 3400 return 0;
1435 }
1436
1437 ✗ int av_opt_get_pixel_fmt(void *obj, const char *name, int search_flags, enum AVPixelFormat *out_fmt)
1438 {
1439 ✗ return get_format(obj, name, search_flags, out_fmt, AV_OPT_TYPE_PIXEL_FMT, "pixel");
1440 }
1441
1442 3400 int av_opt_get_sample_fmt(void *obj, const char *name, int search_flags, enum AVSampleFormat *out_fmt)
1443 {
1444 3400 return get_format(obj, name, search_flags, out_fmt, AV_OPT_TYPE_SAMPLE_FMT, "sample");
1445 }
1446
1447 3400 int av_opt_get_chlayout(void *obj, const char *name, int search_flags, AVChannelLayout *cl)
1448 {
1449 void *dst, *target_obj;
1450 3400 const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
1451
2/4
✓ Branch 0 taken 3400 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 3400 times.
3400 if (!o || !target_obj)
1452 ✗ return AVERROR_OPTION_NOT_FOUND;
1453
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3400 times.
3400 if (o->type != AV_OPT_TYPE_CHLAYOUT) {
1454 ✗ av_log(obj, AV_LOG_ERROR,
1455 "The value for option '%s' is not a channel layout.\n", name);
1456 ✗ return AVERROR(EINVAL);
1457 }
1458
1459 3400 dst = ((uint8_t*)target_obj) + o->offset;
1460 3400 return av_channel_layout_copy(cl, dst);
1461 }
1462
1463 8339 int av_opt_get_dict_val(void *obj, const char *name, int search_flags, AVDictionary **out_val)
1464 {
1465 void *target_obj;
1466 AVDictionary *src;
1467 8339 const AVOption *o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
1468
1469
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 8339 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
8339 if (!o || !target_obj)
1470 8339 return AVERROR_OPTION_NOT_FOUND;
1471 ✗ if (o->type != AV_OPT_TYPE_DICT)
1472 ✗ return AVERROR(EINVAL);
1473
1474 ✗ src = *(AVDictionary **)(((uint8_t *)target_obj) + o->offset);
1475
1476 ✗ return av_dict_copy(out_val, src, 0);
1477 }
1478
1479 ✗ int av_opt_flag_is_set(void *obj, const char *field_name, const char *flag_name)
1480 {
1481 ✗ const AVOption *field = av_opt_find(obj, field_name, NULL, 0, 0);
1482 ✗ const AVOption *flag = av_opt_find(obj, flag_name,
1483 field ? field->unit : NULL, 0, 0);
1484 int64_t res;
1485
1486 ✗ if (!field || !flag || flag->type != AV_OPT_TYPE_CONST ||
1487 ✗ av_opt_get_int(obj, field_name, 0, &res) < 0)
1488 ✗ return 0;
1489 ✗ return res & flag->default_val.i64;
1490 }
1491
1492 4 static void log_int_value(void *av_log_obj, int level, int64_t i)
1493 {
1494
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 if (i == INT_MAX) {
1495 ✗ av_log(av_log_obj, level, "INT_MAX");
1496
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 } else if (i == INT_MIN) {
1497 ✗ av_log(av_log_obj, level, "INT_MIN");
1498
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 } else if (i == UINT32_MAX) {
1499 ✗ av_log(av_log_obj, level, "UINT32_MAX");
1500
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 } else if (i == INT64_MAX) {
1501 ✗ av_log(av_log_obj, level, "I64_MAX");
1502
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 } else if (i == INT64_MIN) {
1503 ✗ av_log(av_log_obj, level, "I64_MIN");
1504 } else {
1505 4 av_log(av_log_obj, level, "%"PRId64, i);
1506 }
1507 4 }
1508
1509 16 static void log_value(void *av_log_obj, int level, double d)
1510 {
1511
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 if (d == INT_MAX) {
1512 ✗ av_log(av_log_obj, level, "INT_MAX");
1513
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == INT_MIN) {
1514 ✗ av_log(av_log_obj, level, "INT_MIN");
1515
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == UINT32_MAX) {
1516 ✗ av_log(av_log_obj, level, "UINT32_MAX");
1517
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == (double)INT64_MAX) {
1518 ✗ av_log(av_log_obj, level, "I64_MAX");
1519
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == INT64_MIN) {
1520 ✗ av_log(av_log_obj, level, "I64_MIN");
1521
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == FLT_MAX) {
1522 ✗ av_log(av_log_obj, level, "FLT_MAX");
1523
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == FLT_MIN) {
1524 ✗ av_log(av_log_obj, level, "FLT_MIN");
1525
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == -FLT_MAX) {
1526 ✗ av_log(av_log_obj, level, "-FLT_MAX");
1527
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == -FLT_MIN) {
1528 ✗ av_log(av_log_obj, level, "-FLT_MIN");
1529
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == DBL_MAX) {
1530 ✗ av_log(av_log_obj, level, "DBL_MAX");
1531
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == DBL_MIN) {
1532 ✗ av_log(av_log_obj, level, "DBL_MIN");
1533
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == -DBL_MAX) {
1534 ✗ av_log(av_log_obj, level, "-DBL_MAX");
1535
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 } else if (d == -DBL_MIN) {
1536 ✗ av_log(av_log_obj, level, "-DBL_MIN");
1537 } else {
1538 16 av_log(av_log_obj, level, "%g", d);
1539 }
1540 16 }
1541
1542 4 static const char *get_opt_const_name(void *obj, const char *unit, int64_t value)
1543 {
1544 4 const AVOption *opt = NULL;
1545
1546
1/2
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
4 if (!unit)
1547 4 return NULL;
1548 ✗ while ((opt = av_opt_next(obj, opt)))
1549 ✗ if (opt->type == AV_OPT_TYPE_CONST && !strcmp(opt->unit, unit) &&
1550 ✗ opt->default_val.i64 == value)
1551 ✗ return opt->name;
1552 ✗ return NULL;
1553 }
1554
1555 1 static char *get_opt_flags_string(void *obj, const char *unit, int64_t value)
1556 {
1557 1 const AVOption *opt = NULL;
1558 char flags[512];
1559
1560 1 flags[0] = 0;
1561
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
1 if (!unit)
1562 ✗ return NULL;
1563
2/2
✓ Branch 1 taken 31 times.
✓ Branch 2 taken 1 times.
32 while ((opt = av_opt_next(obj, opt))) {
1564
3/4
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 28 times.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
31 if (opt->type == AV_OPT_TYPE_CONST && !strcmp(opt->unit, unit) &&
1565
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 2 times.
3 opt->default_val.i64 & value) {
1566
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
1 if (flags[0])
1567 ✗ av_strlcatf(flags, sizeof(flags), "+");
1568 1 av_strlcatf(flags, sizeof(flags), "%s", opt->name);
1569 }
1570 }
1571
1/2
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
1 if (flags[0])
1572 1 return av_strdup(flags);
1573 ✗ return NULL;
1574 }
1575
1576 31 static void log_type(void *av_log_obj, const AVOption *o,
1577 enum AVOptionType parent_type)
1578 {
1579 31 const enum AVOptionType type = TYPE_BASE(o->type);
1580
1581
4/6
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 28 times.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 3 times.
31 if (o->type == AV_OPT_TYPE_CONST && (TYPE_BASE(parent_type) == AV_OPT_TYPE_INT || TYPE_BASE(parent_type) == AV_OPT_TYPE_INT64))
1582 ✗ av_log(av_log_obj, AV_LOG_INFO, "%-12"PRId64" ", o->default_val.i64);
1583
3/4
✓ Branch 0 taken 31 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 28 times.
✓ Branch 3 taken 3 times.
31 else if (type < FF_ARRAY_ELEMS(opt_type_desc) && opt_type_desc[type].name) {
1584
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 25 times.
28 if (o->type & AV_OPT_TYPE_FLAG_ARRAY)
1585 3 av_log(av_log_obj, AV_LOG_INFO, "[%-10s]", opt_type_desc[type].name);
1586 else
1587 25 av_log(av_log_obj, AV_LOG_INFO, "%-12s ", opt_type_desc[type].name);
1588 }
1589 else
1590 3 av_log(av_log_obj, AV_LOG_INFO, "%-12s ", "");
1591 31 }
1592
1593 31 static void log_default(void *obj, void *av_log_obj, const AVOption *opt)
1594 {
1595
4/4
✓ Branch 0 taken 28 times.
✓ Branch 1 taken 3 times.
✓ Branch 2 taken 3 times.
✓ Branch 3 taken 25 times.
31 if (opt->type == AV_OPT_TYPE_CONST || opt->type == AV_OPT_TYPE_BINARY)
1596 6 return;
1597
2/2
✓ Branch 0 taken 24 times.
✓ Branch 1 taken 1 times.
25 if ((opt->type == AV_OPT_TYPE_COLOR ||
1598
2/2
✓ Branch 0 taken 23 times.
✓ Branch 1 taken 1 times.
24 opt->type == AV_OPT_TYPE_IMAGE_SIZE ||
1599
2/2
✓ Branch 0 taken 21 times.
✓ Branch 1 taken 2 times.
23 opt->type == AV_OPT_TYPE_STRING ||
1600
2/2
✓ Branch 0 taken 19 times.
✓ Branch 1 taken 2 times.
21 opt->type == AV_OPT_TYPE_DICT ||
1601
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 1 times.
19 opt->type == AV_OPT_TYPE_CHLAYOUT ||
1602
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 17 times.
18 opt->type == AV_OPT_TYPE_VIDEO_RATE) &&
1603
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 7 times.
8 !opt->default_val.str)
1604 1 return;
1605
1606
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 21 times.
24 if (opt->type & AV_OPT_TYPE_FLAG_ARRAY) {
1607 3 const AVOptionArrayDef *arr = opt->default_val.arr;
1608
3/4
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
3 if (arr && arr->def)
1609 2 av_log(av_log_obj, AV_LOG_INFO, " (default %s)", arr->def);
1610 3 return;
1611 }
1612
1613 21 av_log(av_log_obj, AV_LOG_INFO, " (default ");
1614
9/10
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 4 times.
✓ Branch 4 taken 2 times.
✓ Branch 5 taken 1 times.
✓ Branch 6 taken 1 times.
✓ Branch 7 taken 1 times.
✓ Branch 8 taken 7 times.
✗ Branch 9 not taken.
21 switch (opt->type) {
1615 3 case AV_OPT_TYPE_BOOL:
1616 3 av_log(av_log_obj, AV_LOG_INFO, "%s", get_bool_name(opt->default_val.i64));
1617 3 break;
1618 1 case AV_OPT_TYPE_FLAGS: {
1619 1 char *def_flags = get_opt_flags_string(obj, opt->unit, opt->default_val.i64);
1620
1/2
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
1 if (def_flags) {
1621 1 av_log(av_log_obj, AV_LOG_INFO, "%s", def_flags);
1622 1 av_freep(&def_flags);
1623 } else {
1624 ✗ av_log(av_log_obj, AV_LOG_INFO, "%"PRIX64, opt->default_val.i64);
1625 }
1626 1 break;
1627 }
1628 1 case AV_OPT_TYPE_DURATION: {
1629 char buf[25];
1630 1 format_duration(buf, sizeof(buf), opt->default_val.i64);
1631 1 av_log(av_log_obj, AV_LOG_INFO, "%s", buf);
1632 1 break;
1633 }
1634 4 case AV_OPT_TYPE_UINT:
1635 case AV_OPT_TYPE_INT:
1636 case AV_OPT_TYPE_UINT64:
1637 case AV_OPT_TYPE_INT64: {
1638 4 const char *def_const = get_opt_const_name(obj, opt->unit, opt->default_val.i64);
1639
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
4 if (def_const)
1640 ✗ av_log(av_log_obj, AV_LOG_INFO, "%s", def_const);
1641 else
1642 4 log_int_value(av_log_obj, AV_LOG_INFO, opt->default_val.i64);
1643 4 break;
1644 }
1645 2 case AV_OPT_TYPE_DOUBLE:
1646 case AV_OPT_TYPE_FLOAT:
1647 2 log_value(av_log_obj, AV_LOG_INFO, opt->default_val.dbl);
1648 2 break;
1649 1 case AV_OPT_TYPE_RATIONAL: {
1650 1 AVRational q = av_d2q(opt->default_val.dbl, INT_MAX);
1651 1 av_log(av_log_obj, AV_LOG_INFO, "%d/%d", q.num, q.den); }
1652 1 break;
1653 1 case AV_OPT_TYPE_PIXEL_FMT:
1654 1 av_log(av_log_obj, AV_LOG_INFO, "%s", (char *)av_x_if_null(av_get_pix_fmt_name(opt->default_val.i64), "none"));
1655 1 break;
1656 1 case AV_OPT_TYPE_SAMPLE_FMT:
1657 1 av_log(av_log_obj, AV_LOG_INFO, "%s", (char *)av_x_if_null(av_get_sample_fmt_name(opt->default_val.i64), "none"));
1658 1 break;
1659 7 case AV_OPT_TYPE_COLOR:
1660 case AV_OPT_TYPE_IMAGE_SIZE:
1661 case AV_OPT_TYPE_STRING:
1662 case AV_OPT_TYPE_DICT:
1663 case AV_OPT_TYPE_VIDEO_RATE:
1664 case AV_OPT_TYPE_CHLAYOUT:
1665 7 av_log(av_log_obj, AV_LOG_INFO, "\"%s\"", opt->default_val.str);
1666 7 break;
1667 }
1668 21 av_log(av_log_obj, AV_LOG_INFO, ")");
1669 }
1670
1671 2 static void opt_list(void *obj, void *av_log_obj, const char *unit,
1672 int req_flags, int rej_flags, enum AVOptionType parent_type)
1673 {
1674 2 const AVOption *opt = NULL;
1675 AVOptionRanges *r;
1676 int i;
1677
1678
2/2
✓ Branch 1 taken 62 times.
✓ Branch 2 taken 2 times.
64 while ((opt = av_opt_next(obj, opt))) {
1679
2/4
✓ Branch 0 taken 62 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 62 times.
62 if (!(opt->flags & req_flags) || (opt->flags & rej_flags))
1680 ✗ continue;
1681
1682 /* Don't print CONST's on level one.
1683 * Don't print anything but CONST's on level two.
1684 * Only print items from the requested unit.
1685 */
1686
4/4
✓ Branch 0 taken 31 times.
✓ Branch 1 taken 31 times.
✓ Branch 2 taken 3 times.
✓ Branch 3 taken 28 times.
62 if (!unit && opt->type == AV_OPT_TYPE_CONST)
1687 3 continue;
1688
4/4
✓ Branch 0 taken 31 times.
✓ Branch 1 taken 28 times.
✓ Branch 2 taken 28 times.
✓ Branch 3 taken 3 times.
59 else if (unit && opt->type != AV_OPT_TYPE_CONST)
1689 28 continue;
1690
4/6
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 28 times.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 3 times.
31 else if (unit && opt->type == AV_OPT_TYPE_CONST && strcmp(unit, opt->unit))
1691 ✗ continue;
1692
3/4
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 28 times.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
31 else if (unit && opt->type == AV_OPT_TYPE_CONST)
1693 3 av_log(av_log_obj, AV_LOG_INFO, " %-15s ", opt->name);
1694 else
1695 28 av_log(av_log_obj, AV_LOG_INFO, " %s%-17s ",
1696 28 (opt->flags & AV_OPT_FLAG_FILTERING_PARAM) ? " " : "-",
1697
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 28 times.
28 opt->name);
1698
1699 31 log_type(av_log_obj, opt, parent_type);
1700
1701 341 av_log(av_log_obj, AV_LOG_INFO, "%c%c%c%c%c%c%c%c%c%c%c",
1702
2/2
✓ Branch 0 taken 28 times.
✓ Branch 1 taken 3 times.
31 (opt->flags & AV_OPT_FLAG_ENCODING_PARAM) ? 'E' : '.',
1703
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_DECODING_PARAM) ? 'D' : '.',
1704
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_FILTERING_PARAM) ? 'F' : '.',
1705
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_VIDEO_PARAM) ? 'V' : '.',
1706
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_AUDIO_PARAM) ? 'A' : '.',
1707
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_SUBTITLE_PARAM) ? 'S' : '.',
1708
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_EXPORT) ? 'X' : '.',
1709
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_READONLY) ? 'R' : '.',
1710
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_BSF_PARAM) ? 'B' : '.',
1711
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 28 times.
31 (opt->flags & AV_OPT_FLAG_RUNTIME_PARAM) ? 'T' : '.',
1712
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
31 (opt->flags & AV_OPT_FLAG_DEPRECATED) ? 'P' : '.');
1713
1714
1/2
✓ Branch 0 taken 31 times.
✗ Branch 1 not taken.
31 if (opt->help)
1715 31 av_log(av_log_obj, AV_LOG_INFO, " %s", opt->help);
1716
1717
2/2
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 13 times.
31 if (av_opt_query_ranges(&r, obj, opt->name, AV_OPT_SEARCH_FAKE_OBJ) >= 0) {
1718
2/2
✓ Branch 0 taken 7 times.
✓ Branch 1 taken 11 times.
18 switch (opt->type) {
1719 7 case AV_OPT_TYPE_INT:
1720 case AV_OPT_TYPE_UINT:
1721 case AV_OPT_TYPE_INT64:
1722 case AV_OPT_TYPE_UINT64:
1723 case AV_OPT_TYPE_DOUBLE:
1724 case AV_OPT_TYPE_FLOAT:
1725 case AV_OPT_TYPE_RATIONAL:
1726
2/2
✓ Branch 0 taken 7 times.
✓ Branch 1 taken 7 times.
14 for (i = 0; i < r->nb_ranges; i++) {
1727 7 av_log(av_log_obj, AV_LOG_INFO, " (from ");
1728 7 log_value(av_log_obj, AV_LOG_INFO, r->range[i]->value_min);
1729 7 av_log(av_log_obj, AV_LOG_INFO, " to ");
1730 7 log_value(av_log_obj, AV_LOG_INFO, r->range[i]->value_max);
1731 7 av_log(av_log_obj, AV_LOG_INFO, ")");
1732 }
1733 7 break;
1734 }
1735 18 av_opt_freep_ranges(&r);
1736 }
1737
1738 31 log_default(obj, av_log_obj, opt);
1739
1740 31 av_log(av_log_obj, AV_LOG_INFO, "\n");
1741
4/4
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 27 times.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 3 times.
31 if (opt->unit && opt->type != AV_OPT_TYPE_CONST)
1742 1 opt_list(obj, av_log_obj, opt->unit, req_flags, rej_flags, opt->type);
1743 }
1744 2 }
1745
1746 1 int av_opt_show2(void *obj, void *av_log_obj, int req_flags, int rej_flags)
1747 {
1748
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
1 if (!obj)
1749 ✗ return -1;
1750
1751 1 av_log(av_log_obj, AV_LOG_INFO, "%s AVOptions:\n", (*(AVClass **)obj)->class_name);
1752
1753 1 opt_list(obj, av_log_obj, NULL, req_flags, rej_flags, -1);
1754
1755 1 return 0;
1756 }
1757
1758 495326 void av_opt_set_defaults(void *s)
1759 {
1760 495326 av_opt_set_defaults2(s, 0, 0);
1761 495326 }
1762
1763 564650 void av_opt_set_defaults2(void *s, int mask, int flags)
1764 {
1765 564650 const AVOption *opt = NULL;
1766
2/2
✓ Branch 1 taken 39229481 times.
✓ Branch 2 taken 564650 times.
39794131 while ((opt = av_opt_next(s, opt))) {
1767 39229481 void *dst = ((uint8_t*)s) + opt->offset;
1768
1769
2/2
✓ Branch 0 taken 3657256 times.
✓ Branch 1 taken 35572225 times.
39229481 if ((opt->flags & mask) != flags)
1770 3657256 continue;
1771
1772
2/2
✓ Branch 0 taken 33241 times.
✓ Branch 1 taken 35538984 times.
35572225 if (opt->flags & AV_OPT_FLAG_READONLY)
1773 33241 continue;
1774
1775
2/2
✓ Branch 0 taken 124611 times.
✓ Branch 1 taken 35414373 times.
35538984 if (opt->type & AV_OPT_TYPE_FLAG_ARRAY) {
1776 124611 const AVOptionArrayDef *arr = opt->default_val.arr;
1777 124611 const char sep = opt_array_sep(opt);
1778
1779
11/16
✓ Branch 0 taken 124611 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 124611 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 13469 times.
✓ Branch 5 taken 111142 times.
✓ Branch 6 taken 13469 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 13469 times.
✓ Branch 9 taken 111142 times.
✓ Branch 10 taken 13469 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 13469 times.
✓ Branch 13 taken 111142 times.
✗ Branch 14 not taken.
✓ Branch 15 taken 13469 times.
124611 av_assert0(sep && sep != '\\' &&
1780 (sep < 'a' || sep > 'z') &&
1781 (sep < 'A' || sep > 'Z') &&
1782 (sep < '0' || sep > '9'));
1783
1784
4/4
✓ Branch 0 taken 13479 times.
✓ Branch 1 taken 111132 times.
✓ Branch 2 taken 20 times.
✓ Branch 3 taken 13459 times.
124611 if (arr && arr->def)
1785 20 opt_set_array(s, s, opt, arr->def, dst);
1786
1787 124611 continue;
1788 }
1789
1790
11/12
✓ Branch 0 taken 23515230 times.
✓ Branch 1 taken 9798274 times.
✓ Branch 2 taken 1144903 times.
✓ Branch 3 taken 214384 times.
✓ Branch 4 taken 430 times.
✓ Branch 5 taken 529899 times.
✓ Branch 6 taken 53167 times.
✓ Branch 7 taken 9827 times.
✓ Branch 8 taken 21111 times.
✓ Branch 9 taken 62911 times.
✓ Branch 10 taken 64237 times.
✗ Branch 11 not taken.
35414373 switch (opt->type) {
1791 23515230 case AV_OPT_TYPE_CONST:
1792 /* Nothing to be done here */
1793 23515230 break;
1794 9798274 case AV_OPT_TYPE_BOOL:
1795 case AV_OPT_TYPE_FLAGS:
1796 case AV_OPT_TYPE_INT:
1797 case AV_OPT_TYPE_UINT:
1798 case AV_OPT_TYPE_INT64:
1799 case AV_OPT_TYPE_UINT64:
1800 case AV_OPT_TYPE_DURATION:
1801 case AV_OPT_TYPE_PIXEL_FMT:
1802 case AV_OPT_TYPE_SAMPLE_FMT:
1803 9798274 write_number(s, opt, dst, 1, 1, opt->default_val.i64, 1);
1804 9798274 break;
1805 1144903 case AV_OPT_TYPE_DOUBLE:
1806 case AV_OPT_TYPE_FLOAT: {
1807 double val;
1808 1144903 val = opt->default_val.dbl;
1809 1144903 write_number(s, opt, dst, val, 1, 1, 1);
1810 }
1811 1144903 break;
1812 214384 case AV_OPT_TYPE_RATIONAL: {
1813 AVRational val;
1814 214384 val = av_d2q(opt->default_val.dbl, INT_MAX);
1815 214384 write_number(s, opt, dst, 1, val.den, val.num, 1);
1816 }
1817 214384 break;
1818 430 case AV_OPT_TYPE_COLOR:
1819 430 set_string_color(s, opt, opt->default_val.str, dst);
1820 430 break;
1821 529899 case AV_OPT_TYPE_STRING:
1822 529899 set_string(s, opt, opt->default_val.str, dst);
1823 529899 break;
1824 53167 case AV_OPT_TYPE_IMAGE_SIZE:
1825 53167 set_string_image_size(s, opt, opt->default_val.str, dst);
1826 53167 break;
1827 9827 case AV_OPT_TYPE_VIDEO_RATE:
1828 9827 set_string_video_rate(s, opt, opt->default_val.str, dst);
1829 9827 break;
1830 21111 case AV_OPT_TYPE_BINARY:
1831 21111 set_string_binary(s, opt, opt->default_val.str, dst);
1832 21111 break;
1833 62911 case AV_OPT_TYPE_CHLAYOUT:
1834 62911 set_string_channel_layout(s, opt, opt->default_val.str, dst);
1835 62911 break;
1836 64237 case AV_OPT_TYPE_DICT:
1837 64237 set_string_dict(s, opt, opt->default_val.str, dst);
1838 64237 break;
1839 ✗ default:
1840 ✗ av_log(s, AV_LOG_DEBUG, "AVOption type %d of option %s not implemented yet\n",
1841 ✗ opt->type, opt->name);
1842 }
1843 }
1844 564650 }
1845
1846 /**
1847 * Store the value in the field in ctx that is named like key.
1848 * ctx must be an AVClass context, storing is done using AVOptions.
1849 *
1850 * @param buf the string to parse, buf will be updated to point at the
1851 * separator just after the parsed key/value pair
1852 * @param key_val_sep a 0-terminated list of characters used to
1853 * separate key from value
1854 * @param pairs_sep a 0-terminated list of characters used to separate
1855 * two pairs from each other
1856 * @return 0 if the key/value pair has been successfully parsed and
1857 * set, or a negative value corresponding to an AVERROR code in case
1858 * of error:
1859 * AVERROR(EINVAL) if the key/value pair cannot be parsed,
1860 * the error code issued by av_opt_set() if the key/value pair
1861 * cannot be set
1862 */
1863 3275 static int parse_key_value_pair(void *ctx, const char **buf,
1864 const char *key_val_sep, const char *pairs_sep)
1865 {
1866 3275 char *key = av_get_token(buf, key_val_sep);
1867 char *val;
1868 int ret;
1869
1870
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3275 times.
3275 if (!key)
1871 ✗ return AVERROR(ENOMEM);
1872
1873
4/4
✓ Branch 0 taken 3273 times.
✓ Branch 1 taken 2 times.
✓ Branch 2 taken 3270 times.
✓ Branch 3 taken 3 times.
3275 if (*key && strspn(*buf, key_val_sep)) {
1874 3270 (*buf)++;
1875 3270 val = av_get_token(buf, pairs_sep);
1876
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3270 times.
3270 if (!val) {
1877 ✗ av_freep(&key);
1878 ✗ return AVERROR(ENOMEM);
1879 }
1880 } else {
1881 5 av_log(ctx, AV_LOG_ERROR, "Missing key or no key/value separator found after key '%s'\n", key);
1882 5 av_free(key);
1883 5 return AVERROR(EINVAL);
1884 }
1885
1886 3270 av_log(ctx, AV_LOG_DEBUG, "Setting entry with key '%s' to value '%s'\n", key, val);
1887
1888 3270 ret = av_opt_set(ctx, key, val, AV_OPT_SEARCH_CHILDREN);
1889
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 3265 times.
3270 if (ret == AVERROR_OPTION_NOT_FOUND)
1890 5 av_log(ctx, AV_LOG_ERROR, "Key '%s' not found.\n", key);
1891
1892 3270 av_free(key);
1893 3270 av_free(val);
1894 3270 return ret;
1895 }
1896
1897 3242 int av_set_options_string(void *ctx, const char *opts,
1898 const char *key_val_sep, const char *pairs_sep)
1899 {
1900 3242 int ret, count = 0;
1901
1902
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 3242 times.
3242 if (!opts)
1903 ✗ return 0;
1904
1905
2/2
✓ Branch 0 taken 3275 times.
✓ Branch 1 taken 3203 times.
6478 while (*opts) {
1906
2/2
✓ Branch 1 taken 39 times.
✓ Branch 2 taken 3236 times.
3275 if ((ret = parse_key_value_pair(ctx, &opts, key_val_sep, pairs_sep)) < 0)
1907 39 return ret;
1908 3236 count++;
1909
1910
2/2
✓ Branch 0 taken 35 times.
✓ Branch 1 taken 3201 times.
3236 if (*opts)
1911 35 opts++;
1912 }
1913
1914 3203 return count;
1915 }
1916
1917 #define WHITESPACES " \n\t\r"
1918
1919 493060 static int is_key_char(char c)
1920 {
1921 635352 return (unsigned)((c | 32) - 'a') < 26 ||
1922
4/4
✓ Branch 0 taken 85253 times.
✓ Branch 1 taken 57039 times.
✓ Branch 2 taken 85166 times.
✓ Branch 3 taken 87 times.
142292 (unsigned)(c - '0') < 10 ||
1923
8/8
✓ Branch 0 taken 142292 times.
✓ Branch 1 taken 350768 times.
✓ Branch 2 taken 56465 times.
✓ Branch 3 taken 28701 times.
✓ Branch 4 taken 56361 times.
✓ Branch 5 taken 104 times.
✓ Branch 6 taken 82 times.
✓ Branch 7 taken 56279 times.
635352 c == '-' || c == '_' || c == '/' || c == '.';
1924 }
1925
1926 /**
1927 * Read a key from a string.
1928 *
1929 * The key consists of is_key_char characters and must be terminated by a
1930 * character from the delim string; spaces are ignored.
1931 *
1932 * @return 0 for success (even with ellipsis), <0 for failure
1933 */
1934 56279 static int get_key(const char **ropts, const char *delim, char **rkey)
1935 {
1936 56279 const char *opts = *ropts;
1937 const char *key_start, *key_end;
1938
1939 56279 key_start = opts += strspn(opts, WHITESPACES);
1940
2/2
✓ Branch 1 taken 436781 times.
✓ Branch 2 taken 56279 times.
493060 while (is_key_char(*opts))
1941 436781 opts++;
1942 56279 key_end = opts;
1943 56279 opts += strspn(opts, WHITESPACES);
1944
4/4
✓ Branch 0 taken 42194 times.
✓ Branch 1 taken 14085 times.
✓ Branch 2 taken 7696 times.
✓ Branch 3 taken 34498 times.
56279 if (!*opts || !strchr(delim, *opts))
1945 21781 return AVERROR(EINVAL);
1946 34498 opts++;
1947
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 34498 times.
34498 if (!(*rkey = av_malloc(key_end - key_start + 1)))
1948 ✗ return AVERROR(ENOMEM);
1949 34498 memcpy(*rkey, key_start, key_end - key_start);
1950 34498 (*rkey)[key_end - key_start] = 0;
1951 34498 *ropts = opts;
1952 34498 return 0;
1953 }
1954
1955 56279 int av_opt_get_key_value(const char **ropts,
1956 const char *key_val_sep, const char *pairs_sep,
1957 unsigned flags,
1958 char **rkey, char **rval)
1959 {
1960 int ret;
1961 56279 char *key = NULL, *val;
1962 56279 const char *opts = *ropts;
1963
1964
2/2
✓ Branch 1 taken 21781 times.
✓ Branch 2 taken 34498 times.
56279 if ((ret = get_key(&opts, key_val_sep, &key)) < 0 &&
1965
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 21780 times.
21781 !(flags & AV_OPT_FLAG_IMPLICIT_KEY))
1966 1 return AVERROR(EINVAL);
1967
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 56278 times.
56278 if (!(val = av_get_token(&opts, pairs_sep))) {
1968 ✗ av_free(key);
1969 ✗ return AVERROR(ENOMEM);
1970 }
1971 56278 *ropts = opts;
1972 56278 *rkey = key;
1973 56278 *rval = val;
1974 56278 return 0;
1975 }
1976
1977 117 int av_opt_set_from_string(void *ctx, const char *opts,
1978 const char *const *shorthand,
1979 const char *key_val_sep, const char *pairs_sep)
1980 {
1981 117 int ret, count = 0;
1982 117 const char *dummy_shorthand = NULL;
1983 const char *key;
1984
1985
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 117 times.
117 if (!opts)
1986 ✗ return 0;
1987
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 117 times.
117 if (!shorthand)
1988 ✗ shorthand = &dummy_shorthand;
1989
1990
2/2
✓ Branch 0 taken 225 times.
✓ Branch 1 taken 113 times.
338 while (*opts) {
1991 char *parsed_key, *value;
1992 225 ret = av_opt_get_key_value(&opts, key_val_sep, pairs_sep,
1993 225 *shorthand ? AV_OPT_FLAG_IMPLICIT_KEY : 0,
1994 &parsed_key, &value);
1995
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 224 times.
225 if (ret < 0) {
1996
1/2
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
1 if (ret == AVERROR(EINVAL))
1997 1 av_log(ctx, AV_LOG_ERROR, "No option name near '%s'\n", opts);
1998 else
1999 ✗ av_log(ctx, AV_LOG_ERROR, "Unable to parse '%s': %s\n", opts,
2000 ✗ av_err2str(ret));
2001 4 return ret;
2002 }
2003
2/2
✓ Branch 0 taken 110 times.
✓ Branch 1 taken 114 times.
224 if (*opts)
2004 110 opts++;
2005
2/2
✓ Branch 0 taken 210 times.
✓ Branch 1 taken 14 times.
224 if (parsed_key) {
2006 210 key = parsed_key;
2007
2/2
✓ Branch 0 taken 108 times.
✓ Branch 1 taken 210 times.
318 while (*shorthand) /* discard all remaining shorthand */
2008 108 shorthand++;
2009 } else {
2010 14 key = *(shorthand++);
2011 }
2012
2013 224 av_log(ctx, AV_LOG_DEBUG, "Setting '%s' to value '%s'\n", key, value);
2014
2/2
✓ Branch 1 taken 3 times.
✓ Branch 2 taken 221 times.
224 if ((ret = av_opt_set(ctx, key, value, 0)) < 0) {
2015
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 1 times.
3 if (ret == AVERROR_OPTION_NOT_FOUND)
2016 2 av_log(ctx, AV_LOG_ERROR, "Option '%s' not found\n", key);
2017 3 av_free(value);
2018 3 av_free(parsed_key);
2019 3 return ret;
2020 }
2021
2022 221 av_free(value);
2023 221 av_free(parsed_key);
2024 221 count++;
2025 }
2026 113 return count;
2027 }
2028
2029 705209 void av_opt_free(void *obj)
2030 {
2031 705209 const AVOption *o = NULL;
2032
2/2
✓ Branch 1 taken 30323436 times.
✓ Branch 2 taken 705209 times.
31028645 while ((o = av_opt_next(obj, o))) {
2033 30323436 void *pitem = (uint8_t *)obj + o->offset;
2034
2035
2/2
✓ Branch 0 taken 126568 times.
✓ Branch 1 taken 30196868 times.
30323436 if (o->type & AV_OPT_TYPE_FLAG_ARRAY)
2036 126568 opt_free_array(o, pitem, opt_array_pcount(pitem));
2037 else
2038 30196868 opt_free_elem(o->type, pitem);
2039 }
2040 705209 }
2041
2042 305103 int av_opt_set_dict2(void *obj, AVDictionary **options, int search_flags)
2043 {
2044 305103 const AVDictionaryEntry *t = NULL;
2045 305103 AVDictionary *tmp = NULL;
2046 int ret;
2047
2048
2/2
✓ Branch 0 taken 73823 times.
✓ Branch 1 taken 231280 times.
305103 if (!options)
2049 73823 return 0;
2050
2051
2/2
✓ Branch 1 taken 209239 times.
✓ Branch 2 taken 231280 times.
440519 while ((t = av_dict_iterate(*options, t))) {
2052 209239 ret = av_opt_set(obj, t->key, t->value, search_flags);
2053
2/2
✓ Branch 0 taken 52397 times.
✓ Branch 1 taken 156842 times.
209239 if (ret == AVERROR_OPTION_NOT_FOUND)
2054 52397 ret = av_dict_set(&tmp, t->key, t->value, AV_DICT_MULTIKEY);
2055
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 209239 times.
209239 if (ret < 0) {
2056 ✗ av_log(obj, AV_LOG_ERROR, "Error setting option %s to value %s.\n", t->key, t->value);
2057 ✗ av_dict_free(&tmp);
2058 ✗ return ret;
2059 }
2060 }
2061 231280 av_dict_free(options);
2062 231280 *options = tmp;
2063 231280 return 0;
2064 }
2065
2066 170254 int av_opt_set_dict(void *obj, AVDictionary **options)
2067 {
2068 170254 return av_opt_set_dict2(obj, options, 0);
2069 }
2070
2071 640357 const AVOption *av_opt_find(void *obj, const char *name, const char *unit,
2072 int opt_flags, int search_flags)
2073 {
2074 640357 return av_opt_find2(obj, name, unit, opt_flags, search_flags, NULL);
2075 }
2076
2077 51919143 const AVOption *av_opt_find2(void *obj, const char *name, const char *unit,
2078 int opt_flags, int search_flags, void **target_obj)
2079 {
2080 const AVClass *c;
2081 51919143 const AVOption *o = NULL;
2082
2083
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 51919143 times.
51919143 if(!obj)
2084 ✗ return NULL;
2085
2086 51919143 c= *(AVClass**)obj;
2087
2088
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 51919143 times.
51919143 if (!c)
2089 ✗ return NULL;
2090
2091
2/2
✓ Branch 0 taken 51420873 times.
✓ Branch 1 taken 498270 times.
51919143 if (search_flags & AV_OPT_SEARCH_CHILDREN) {
2092
2/2
✓ Branch 0 taken 51019582 times.
✓ Branch 1 taken 401291 times.
51420873 if (search_flags & AV_OPT_SEARCH_FAKE_OBJ) {
2093 51019582 void *iter = NULL;
2094 const AVClass *child;
2095
2/2
✓ Branch 1 taken 50701083 times.
✓ Branch 2 taken 51018832 times.
101719915 while (child = av_opt_child_class_iterate(c, &iter))
2096
2/2
✓ Branch 1 taken 750 times.
✓ Branch 2 taken 50700333 times.
50701083 if (o = av_opt_find2(&child, name, unit, opt_flags, search_flags, NULL))
2097 750 return o;
2098 } else {
2099 401291 void *child = NULL;
2100
2/2
✓ Branch 1 taken 190292 times.
✓ Branch 2 taken 328109 times.
518401 while (child = av_opt_child_next(obj, child))
2101
2/2
✓ Branch 1 taken 73182 times.
✓ Branch 2 taken 117110 times.
190292 if (o = av_opt_find2(child, name, unit, opt_flags, search_flags, target_obj))
2102 73182 return o;
2103 }
2104 }
2105
2106
2/2
✓ Branch 1 taken 543482620 times.
✓ Branch 2 taken 51196150 times.
594678770 while (o = av_opt_next(obj, o)) {
2107
6/6
✓ Branch 0 taken 749561 times.
✓ Branch 1 taken 542733059 times.
✓ Branch 2 taken 745949 times.
✓ Branch 3 taken 3612 times.
✓ Branch 4 taken 585308 times.
✓ Branch 5 taken 160641 times.
543482620 if (!strcmp(o->name, name) && (o->flags & opt_flags) == opt_flags &&
2108
4/4
✓ Branch 0 taken 95414 times.
✓ Branch 1 taken 489894 times.
✓ Branch 2 taken 160641 times.
✓ Branch 3 taken 95414 times.
745949 ((!unit && o->type != AV_OPT_TYPE_CONST) ||
2109
4/6
✓ Branch 0 taken 160641 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 160641 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 159167 times.
✓ Branch 5 taken 1474 times.
160641 (unit && o->type == AV_OPT_TYPE_CONST && o->unit && !strcmp(o->unit, unit)))) {
2110
2/2
✓ Branch 0 taken 305067 times.
✓ Branch 1 taken 343994 times.
649061 if (target_obj) {
2111
1/2
✓ Branch 0 taken 305067 times.
✗ Branch 1 not taken.
305067 if (!(search_flags & AV_OPT_SEARCH_FAKE_OBJ))
2112 305067 *target_obj = obj;
2113 else
2114 ✗ *target_obj = NULL;
2115 }
2116 649061 return o;
2117 }
2118 }
2119 51196150 return NULL;
2120 }
2121
2122 518480 void *av_opt_child_next(void *obj, void *prev)
2123 {
2124 518480 const AVClass *c = *(AVClass **)obj;
2125
2/2
✓ Branch 0 taken 382420 times.
✓ Branch 1 taken 136060 times.
518480 if (c->child_next)
2126 382420 return c->child_next(obj, prev);
2127 136060 return NULL;
2128 }
2129
2130 101719915 const AVClass *av_opt_child_class_iterate(const AVClass *parent, void **iter)
2131 {
2132
2/2
✓ Branch 0 taken 51198397 times.
✓ Branch 1 taken 50521518 times.
101719915 if (parent->child_class_iterate)
2133 51198397 return parent->child_class_iterate(iter);
2134 50521518 return NULL;
2135 }
2136
2137 6849155 static int opt_copy_elem(void *logctx, enum AVOptionType type,
2138 void *dst, const void *src)
2139 {
2140
2/2
✓ Branch 0 taken 42781 times.
✓ Branch 1 taken 6806374 times.
6849155 if (type == AV_OPT_TYPE_STRING) {
2141 42781 const char *src_str = *(const char *const *)src;
2142 42781 char **dstp = (char **)dst;
2143
2/2
✓ Branch 0 taken 14 times.
✓ Branch 1 taken 42767 times.
42781 if (*dstp != src_str)
2144 14 av_freep(dstp);
2145
2/2
✓ Branch 0 taken 16 times.
✓ Branch 1 taken 42765 times.
42781 if (src_str) {
2146 16 *dstp = av_strdup(src_str);
2147
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 16 times.
16 if (!*dstp)
2148 ✗ return AVERROR(ENOMEM);
2149 }
2150
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6806368 times.
6806374 } else if (type == AV_OPT_TYPE_BINARY) {
2151 6 const uint8_t *const *src8 = (const uint8_t *const *)src;
2152 6 uint8_t **dst8 = (uint8_t **)dst;
2153 6 int len = *(const int *)(src8 + 1);
2154
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 5 times.
6 if (*dst8 != *src8)
2155 1 av_freep(dst8);
2156 6 *dst8 = av_memdup(*src8, len);
2157
3/4
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 4 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
6 if (len && !*dst8) {
2158 ✗ *(int *)(dst8 + 1) = 0;
2159 ✗ return AVERROR(ENOMEM);
2160 }
2161 6 *(int *)(dst8 + 1) = len;
2162
2/2
✓ Branch 0 taken 2037673 times.
✓ Branch 1 taken 4768695 times.
6806368 } else if (type == AV_OPT_TYPE_CONST) {
2163 // do nothing
2164
2/2
✓ Branch 0 taken 13990 times.
✓ Branch 1 taken 2023683 times.
2037673 } else if (type == AV_OPT_TYPE_DICT) {
2165 13990 const AVDictionary *sdict = *(const AVDictionary * const *)src;
2166 13990 AVDictionary **ddictp = (AVDictionary **)dst;
2167
2/2
✓ Branch 0 taken 7 times.
✓ Branch 1 taken 13983 times.
13990 if (sdict != *ddictp)
2168 7 av_dict_free(ddictp);
2169 13990 *ddictp = NULL;
2170 13990 return av_dict_copy(ddictp, sdict, 0);
2171
2/2
✓ Branch 0 taken 13982 times.
✓ Branch 1 taken 2009701 times.
2023683 } else if (type == AV_OPT_TYPE_CHLAYOUT) {
2172 13982 const AVChannelLayout *slayout = (const AVChannelLayout *)src;
2173 13982 AVChannelLayout *dlayout = (AVChannelLayout *)dst;
2174
1/2
✓ Branch 0 taken 13982 times.
✗ Branch 1 not taken.
13982 if (dlayout != slayout) {
2175
2/2
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 13980 times.
13982 if (dlayout->order == AV_CHANNEL_ORDER_CUSTOM &&
2176
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 1 times.
2 slayout->order == AV_CHANNEL_ORDER_CUSTOM &&
2177
1/2
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
1 dlayout->u.map == slayout->u.map)
2178 1 dlayout->u.map = NULL;
2179 13982 return av_channel_layout_copy(dst, src);
2180 }
2181
1/2
✓ Branch 1 taken 2009701 times.
✗ Branch 2 not taken.
2009701 } else if (opt_is_pod(type)) {
2182 2009701 size_t size = opt_type_desc[type].size;
2183 2009701 memcpy(dst, src, size);
2184 } else {
2185 ✗ av_log(logctx, AV_LOG_ERROR, "Unhandled option type: %d\n", type);
2186 ✗ return AVERROR(EINVAL);
2187 }
2188
2189 6821183 return 0;
2190 }
2191
2192 13992 static int opt_copy_array(void *logctx, const AVOption *o,
2193 void **pdst, const void * const *psrc)
2194 {
2195 13992 unsigned nb_elems = *opt_array_pcount(psrc);
2196 13992 void *dst = NULL;
2197 int ret;
2198
2199
2/2
✓ Branch 0 taken 13990 times.
✓ Branch 1 taken 2 times.
13992 if (*pdst == *psrc) {
2200 13990 *pdst = NULL;
2201 13990 *opt_array_pcount(pdst) = 0;
2202 }
2203
2204 13992 opt_free_array(o, pdst, opt_array_pcount(pdst));
2205
2206 13992 dst = av_calloc(nb_elems, opt_type_desc[TYPE_BASE(o->type)].size);
2207
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 13992 times.
13992 if (!dst)
2208 ✗ return AVERROR(ENOMEM);
2209
2210
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 13992 times.
14002 for (unsigned i = 0; i < nb_elems; i++) {
2211 10 ret = opt_copy_elem(logctx, TYPE_BASE(o->type),
2212 opt_array_pelem(o, dst, i),
2213 10 opt_array_pelem(o, *(void**)psrc, i));
2214
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
10 if (ret < 0) {
2215 ✗ opt_free_array(o, &dst, &nb_elems);
2216 ✗ return ret;
2217 }
2218 }
2219
2220 13992 *pdst = dst;
2221 13992 *opt_array_pcount(pdst) = nb_elems;
2222
2223 13992 return 0;
2224 }
2225
2226 38094 int av_opt_copy(void *dst, const void *src)
2227 {
2228 38094 const AVOption *o = NULL;
2229 const AVClass *c;
2230 38094 int ret = 0;
2231
2232
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 38094 times.
38094 if (!src)
2233 ✗ return AVERROR(EINVAL);
2234
2235 38094 c = *(AVClass **)src;
2236
2/4
✓ Branch 0 taken 38094 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 38094 times.
38094 if (!c || c != *(AVClass **)dst)
2237 ✗ return AVERROR(EINVAL);
2238
2239
2/2
✓ Branch 1 taken 6862913 times.
✓ Branch 2 taken 38094 times.
6901007 while ((o = av_opt_next(src, o))) {
2240 6862913 void *field_dst = (uint8_t *)dst + o->offset;
2241 6862913 void *field_src = (uint8_t *)src + o->offset;
2242
2243 13725826 int err = (o->type & AV_OPT_TYPE_FLAG_ARRAY) ?
2244
2/2
✓ Branch 0 taken 13992 times.
✓ Branch 1 taken 6848921 times.
6862913 opt_copy_array(dst, o, field_dst, field_src) :
2245 6848921 opt_copy_elem (dst, o->type, field_dst, field_src);
2246
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6862913 times.
6862913 if (err < 0)
2247 ✗ ret = err;
2248 }
2249 38094 return ret;
2250 }
2251
2252 20 int av_opt_get_array_size(void *obj, const char *name, int search_flags,
2253 unsigned int *out_val)
2254 {
2255 void *target_obj, *parray;
2256 const AVOption *o;
2257
2258 20 o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
2259
2/4
✓ Branch 0 taken 20 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 20 times.
20 if (!o || !target_obj)
2260 ✗ return AVERROR_OPTION_NOT_FOUND;
2261
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 20 times.
20 if (!(o->type & AV_OPT_TYPE_FLAG_ARRAY))
2262 ✗ return AVERROR(EINVAL);
2263
2264 20 parray = (uint8_t *)target_obj + o->offset;
2265 20 *out_val = *opt_array_pcount(parray);
2266
2267 20 return 0;
2268 }
2269
2270 14 int av_opt_get_array(void *obj, const char *name, int search_flags,
2271 unsigned int start_elem, unsigned int nb_elems,
2272 enum AVOptionType out_type, void *out_val)
2273 {
2274 14 const size_t elem_size_out = opt_type_desc[TYPE_BASE(out_type)].size;
2275
2276 const AVOption *o;
2277 void *target_obj;
2278
2279 const void *parray;
2280 unsigned array_size;
2281
2282 int ret;
2283
2284 14 o = av_opt_find2(obj, name, NULL, 0, search_flags, &target_obj);
2285
2/4
✓ Branch 0 taken 14 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 14 times.
14 if (!o || !target_obj)
2286 ✗ return AVERROR_OPTION_NOT_FOUND;
2287
1/2
✓ Branch 0 taken 14 times.
✗ Branch 1 not taken.
14 if (!(o->type & AV_OPT_TYPE_FLAG_ARRAY) ||
2288
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 14 times.
14 (out_type & AV_OPT_TYPE_FLAG_ARRAY))
2289 ✗ return AVERROR(EINVAL);
2290
2291 14 parray = (uint8_t *)target_obj + o->offset;
2292 14 array_size = *opt_array_pcount(parray);
2293
2294
1/2
✓ Branch 0 taken 14 times.
✗ Branch 1 not taken.
14 if (start_elem >= array_size ||
2295
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 14 times.
14 array_size - start_elem < nb_elems)
2296 ✗ return AVERROR(EINVAL);
2297
2298
2/2
✓ Branch 0 taken 32 times.
✓ Branch 1 taken 14 times.
46 for (unsigned i = 0; i < nb_elems; i++) {
2299 32 const void *src = opt_array_pelem(o, *(void**)parray, start_elem + i);
2300 32 void *dst = (uint8_t*)out_val + i * elem_size_out;
2301
2302
2/2
✓ Branch 0 taken 25 times.
✓ Branch 1 taken 7 times.
32 if (out_type == TYPE_BASE(o->type)) {
2303 25 ret = opt_copy_elem(obj, out_type, dst, src);
2304
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 25 times.
25 if (ret < 0)
2305 ✗ goto fail;
2306
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 2 times.
7 } else if (out_type == AV_OPT_TYPE_STRING) {
2307 5 uint8_t buf[128], *out = buf;
2308
2309 5 ret = opt_get_elem(o, &out, sizeof(buf), src, search_flags);
2310
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 if (ret < 0)
2311 ✗ goto fail;
2312
2313
1/2
✓ Branch 0 taken 5 times.
✗ Branch 1 not taken.
5 if (out == buf) {
2314 5 out = av_strdup(buf);
2315
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 if (!out) {
2316 ✗ ret = AVERROR(ENOMEM);
2317 ✗ goto fail;
2318 }
2319 }
2320
2321 5 *(uint8_t**)dst = out;
2322
2/4
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
2 } else if (out_type == AV_OPT_TYPE_INT64 ||
2323 ✗ out_type == AV_OPT_TYPE_DOUBLE ||
2324 2 out_type == AV_OPT_TYPE_RATIONAL) {
2325 2 double num = 1.0;
2326 2 int den = 1;
2327 2 int64_t intnum = 1;
2328
2329 2 ret = read_number(o, src, &num, &den, &intnum);
2330
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
2 if (ret < 0)
2331 ✗ goto fail;
2332
2333
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
2 switch (out_type) {
2334 ✗ case AV_OPT_TYPE_INT64:
2335 ✗ *(int64_t*)dst = (num == den) ? intnum : num * intnum / den;
2336 2 break;
2337 2 case AV_OPT_TYPE_DOUBLE:
2338 2 *(double*)dst = num * intnum / den;
2339 2 break;
2340 ✗ case AV_OPT_TYPE_RATIONAL:
2341 ✗ *(AVRational*)dst = (num == 1.0 && (int)intnum == intnum) ?
2342 ✗ (AVRational){ intnum, den } :
2343 ✗ double_to_rational(num * intnum / den);
2344 ✗ break;
2345 ✗ default: av_assert0(0);
2346 }
2347 } else
2348 ✗ return AVERROR(ENOSYS);
2349 }
2350
2351 14 return 0;
2352 ✗ fail:
2353 ✗ for (unsigned i = 0; i < nb_elems; i++)
2354 ✗ opt_free_elem(out_type, (uint8_t*)out_val + i * elem_size_out);
2355 ✗ return ret;
2356 }
2357
2358 47 int av_opt_set_array(void *obj, const char *name, int search_flags,
2359 unsigned int start_elem, unsigned int nb_elems,
2360 enum AVOptionType val_type, const void *val)
2361 {
2362 47 const size_t elem_size_val = opt_type_desc[TYPE_BASE(val_type)].size;
2363
2364 const AVOption *o;
2365 const AVOptionArrayDef *arr;
2366 void *target_obj;
2367
2368 void *parray;
2369 void *new_elems;
2370 unsigned *array_size, new_size;
2371 size_t elem_size;
2372
2373 47 int ret = 0;
2374
2375 47 ret = opt_set_init(obj, name, search_flags, 0, &target_obj, &o, &parray);
2376
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 if (ret < 0)
2377 ✗ return ret;
2378
2379
1/2
✓ Branch 0 taken 47 times.
✗ Branch 1 not taken.
47 if (!(o->type & AV_OPT_TYPE_FLAG_ARRAY) ||
2380
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 (val_type & AV_OPT_TYPE_FLAG_ARRAY))
2381 ✗ return AVERROR(EINVAL);
2382
2383 47 arr = o->default_val.arr;
2384 47 array_size = opt_array_pcount(parray);
2385 47 elem_size = opt_type_desc[TYPE_BASE(o->type)].size;
2386
2387
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 if (start_elem > *array_size)
2388 ✗ return AVERROR(EINVAL);
2389
2390 // compute new array size
2391
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 if (!val) {
2392 ✗ if (*array_size - start_elem < nb_elems)
2393 ✗ return AVERROR(EINVAL);
2394
2395 ✗ new_size = *array_size - nb_elems;
2396
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 } else if (search_flags & AV_OPT_ARRAY_REPLACE) {
2397 ✗ if (start_elem >= UINT_MAX - nb_elems)
2398 ✗ return AVERROR(EINVAL);
2399
2400 ✗ new_size = FFMAX(*array_size, start_elem + nb_elems);
2401 } else {
2402
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 if (nb_elems >= UINT_MAX - *array_size)
2403 ✗ return AVERROR(EINVAL);
2404
2405 47 new_size = *array_size + nb_elems;
2406 }
2407
2408
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 if (arr &&
2409 ✗ ((arr->size_max && new_size > arr->size_max) ||
2410 ✗ (arr->size_min && new_size < arr->size_min)))
2411 ✗ return AVERROR(EINVAL);
2412
2413 // desired operation is shrinking the array
2414
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 if (!val) {
2415 ✗ void *array = *(void**)parray;
2416
2417 ✗ for (unsigned i = 0; i < nb_elems; i++) {
2418 ✗ opt_free_elem(o->type,
2419 opt_array_pelem(o, array, start_elem + i));
2420 }
2421
2422 ✗ if (new_size > 0) {
2423 ✗ memmove(opt_array_pelem(o, array, start_elem),
2424 ✗ opt_array_pelem(o, array, start_elem + nb_elems),
2425 ✗ elem_size * (*array_size - start_elem - nb_elems));
2426
2427 ✗ array = av_realloc_array(array, new_size, elem_size);
2428 ✗ if (!array)
2429 ✗ return AVERROR(ENOMEM);
2430
2431 ✗ *(void**)parray = array;
2432 } else
2433 ✗ av_freep(parray);
2434
2435 ✗ *array_size = new_size;
2436
2437 ✗ return 0;
2438 }
2439
2440 // otherwise, desired operation is insert/replace;
2441 // first, store new elements in a separate array to simplify
2442 // rollback on failure
2443 47 new_elems = av_calloc(nb_elems, elem_size);
2444
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 47 times.
47 if (!new_elems)
2445 ✗ return AVERROR(ENOMEM);
2446
2447 // convert/validate each new element
2448
2/2
✓ Branch 0 taken 199 times.
✓ Branch 1 taken 47 times.
246 for (unsigned i = 0; i < nb_elems; i++) {
2449 199 void *dst = opt_array_pelem(o, new_elems, i);
2450 199 const void *src = (uint8_t*)val + i * elem_size_val;
2451
2452 199 double num = 1.0;
2453 199 int den = 1;
2454 199 int64_t intnum = 1;
2455
2456
1/2
✓ Branch 0 taken 199 times.
✗ Branch 1 not taken.
199 if (val_type == TYPE_BASE(o->type)) {
2457 int err;
2458
2459 199 ret = opt_copy_elem(obj, val_type, dst, src);
2460
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 199 times.
199 if (ret < 0)
2461 ✗ goto fail;
2462
2463 // validate the range for numeric options
2464 199 err = read_number(o, dst, &num, &den, &intnum);
2465
2/4
✓ Branch 0 taken 199 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 199 times.
✗ Branch 3 not taken.
199 if (err >= 0 && TYPE_BASE(o->type) != AV_OPT_TYPE_FLAGS &&
2466
3/6
✓ Branch 0 taken 199 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 199 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 199 times.
199 (!den || o->max * den < num * intnum || o->min * den > num * intnum)) {
2467 ✗ num = den ? num * intnum / den : (num && intnum ? INFINITY : NAN);
2468 ✗ av_log(obj, AV_LOG_ERROR, "Cannot set array element %u for "
2469 "parameter '%s': value %f out of range [%g - %g]\n",
2470 ✗ start_elem + i, o->name, num, o->min, o->max);
2471 ✗ ret = AVERROR(ERANGE);
2472 ✗ goto fail;
2473 }
2474 ✗ } else if (val_type == AV_OPT_TYPE_STRING) {
2475 ✗ ret = opt_set_elem(obj, target_obj, o, *(const char **)src, dst);
2476 ✗ if (ret < 0)
2477 ✗ goto fail;
2478 ✗ } else if (val_type == AV_OPT_TYPE_INT ||
2479 ✗ val_type == AV_OPT_TYPE_INT64 ||
2480 ✗ val_type == AV_OPT_TYPE_FLOAT ||
2481 ✗ val_type == AV_OPT_TYPE_DOUBLE ||
2482 val_type == AV_OPT_TYPE_RATIONAL) {
2483
2484 ✗ switch (val_type) {
2485 ✗ case AV_OPT_TYPE_INT: intnum = *(int*)src; break;
2486 ✗ case AV_OPT_TYPE_INT64: intnum = *(int64_t*)src; break;
2487 ✗ case AV_OPT_TYPE_FLOAT: num = *(float*)src; break;
2488 ✗ case AV_OPT_TYPE_DOUBLE: num = *(double*)src; break;
2489 ✗ case AV_OPT_TYPE_RATIONAL: intnum = ((AVRational*)src)->num;
2490 ✗ den = ((AVRational*)src)->den; break;
2491 ✗ default: av_assert0(0);
2492 }
2493
2494 ✗ ret = write_number(obj, o, dst, num, den, intnum, 0);
2495 ✗ if (ret < 0)
2496 ✗ goto fail;
2497 } else {
2498 ✗ ret = AVERROR(ENOSYS);
2499 ✗ goto fail;
2500 }
2501 }
2502
2503 // commit new elements to the array
2504
2/4
✓ Branch 0 taken 47 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 47 times.
✗ Branch 3 not taken.
47 if (start_elem == 0 && nb_elems == new_size) {
2505 // replacing the existing array entirely
2506 47 opt_free_array(o, parray, array_size);
2507 47 *(void**)parray = new_elems;
2508 47 *array_size = nb_elems;
2509
2510 47 new_elems = NULL;
2511 47 nb_elems = 0;
2512 } else {
2513 ✗ void *array = av_realloc_array(*(void**)parray, new_size, elem_size);
2514 ✗ if (!array) {
2515 ✗ ret = AVERROR(ENOMEM);
2516 ✗ goto fail;
2517 }
2518
2519 ✗ if (search_flags & AV_OPT_ARRAY_REPLACE) {
2520 // free the elements being overwritten
2521 ✗ for (unsigned i = start_elem; i < FFMIN(start_elem + nb_elems, *array_size); i++)
2522 ✗ opt_free_elem(o->type, opt_array_pelem(o, array, i));
2523 } else {
2524 // shift existing elements to the end
2525 ✗ memmove(opt_array_pelem(o, array, start_elem + nb_elems),
2526 ✗ opt_array_pelem(o, array, start_elem),
2527 ✗ elem_size * (*array_size - start_elem));
2528 }
2529
2530 ✗ memcpy((uint8_t*)array + elem_size * start_elem, new_elems, elem_size * nb_elems);
2531
2532 ✗ av_freep(&new_elems);
2533 ✗ nb_elems = 0;
2534
2535 ✗ *(void**)parray = array;
2536 ✗ *array_size = new_size;
2537 }
2538
2539 47 fail:
2540 47 opt_free_array(o, &new_elems, &nb_elems);
2541
2542 47 return ret;
2543 }
2544
2545 31 int av_opt_query_ranges(AVOptionRanges **ranges_arg, void *obj, const char *key, int flags)
2546 {
2547 int ret;
2548 31 const AVClass *c = *(AVClass**)obj;
2549 31 int (*callback)(AVOptionRanges **, void *obj, const char *key, int flags) = c->query_ranges;
2550
2551
1/2
✓ Branch 0 taken 31 times.
✗ Branch 1 not taken.
31 if (!callback)
2552 31 callback = av_opt_query_ranges_default;
2553
2554 31 ret = callback(ranges_arg, obj, key, flags);
2555
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 13 times.
31 if (ret >= 0) {
2556
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 if (!(flags & AV_OPT_MULTI_COMPONENT_RANGE))
2557 18 ret = 1;
2558 18 (*ranges_arg)->nb_components = ret;
2559 }
2560 31 return ret;
2561 }
2562
2563 31 int av_opt_query_ranges_default(AVOptionRanges **ranges_arg, void *obj, const char *key, int flags)
2564 {
2565 31 AVOptionRanges *ranges = av_mallocz(sizeof(*ranges));
2566 31 AVOptionRange **range_array = av_mallocz(sizeof(void*));
2567 31 AVOptionRange *range = av_mallocz(sizeof(*range));
2568 31 const AVOption *field = av_opt_find(obj, key, NULL, 0, flags);
2569 int ret;
2570
2571 31 *ranges_arg = NULL;
2572
2573
5/8
✓ Branch 0 taken 31 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 31 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 31 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 3 times.
✓ Branch 7 taken 28 times.
31 if (!ranges || !range || !range_array || !field) {
2574 3 ret = AVERROR(ENOMEM);
2575 3 goto fail;
2576 }
2577
2578 28 ranges->range = range_array;
2579 28 ranges->range[0] = range;
2580 28 ranges->nb_ranges = 1;
2581 28 ranges->nb_components = 1;
2582 28 range->is_range = 1;
2583 28 range->value_min = field->min;
2584 28 range->value_max = field->max;
2585
2586
6/6
✓ Branch 0 taken 13 times.
✓ Branch 1 taken 2 times.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 1 times.
✓ Branch 4 taken 1 times.
✓ Branch 5 taken 10 times.
28 switch (field->type) {
2587 13 case AV_OPT_TYPE_BOOL:
2588 case AV_OPT_TYPE_INT:
2589 case AV_OPT_TYPE_UINT:
2590 case AV_OPT_TYPE_INT64:
2591 case AV_OPT_TYPE_UINT64:
2592 case AV_OPT_TYPE_PIXEL_FMT:
2593 case AV_OPT_TYPE_SAMPLE_FMT:
2594 case AV_OPT_TYPE_FLOAT:
2595 case AV_OPT_TYPE_DOUBLE:
2596 case AV_OPT_TYPE_DURATION:
2597 case AV_OPT_TYPE_COLOR:
2598 13 break;
2599 2 case AV_OPT_TYPE_STRING:
2600 2 range->component_min = 0;
2601 2 range->component_max = 0x10FFFF; // max unicode value
2602 2 range->value_min = -1;
2603 2 range->value_max = INT_MAX;
2604 2 break;
2605 1 case AV_OPT_TYPE_RATIONAL:
2606 1 range->component_min = INT_MIN;
2607 1 range->component_max = INT_MAX;
2608 1 break;
2609 1 case AV_OPT_TYPE_IMAGE_SIZE:
2610 1 range->component_min = 0;
2611 1 range->component_max = INT_MAX/128/8;
2612 1 range->value_min = 0;
2613 1 range->value_max = INT_MAX/8;
2614 1 break;
2615 1 case AV_OPT_TYPE_VIDEO_RATE:
2616 1 range->component_min = 1;
2617 1 range->component_max = INT_MAX;
2618 1 range->value_min = 1;
2619 1 range->value_max = INT_MAX;
2620 1 break;
2621 10 default:
2622 10 ret = AVERROR(ENOSYS);
2623 10 goto fail;
2624 }
2625
2626 18 *ranges_arg = ranges;
2627 18 return 1;
2628 13 fail:
2629 13 av_free(ranges);
2630 13 av_free(range);
2631 13 av_free(range_array);
2632 13 return ret;
2633 }
2634
2635 18 void av_opt_freep_ranges(AVOptionRanges **rangesp)
2636 {
2637 int i;
2638 18 AVOptionRanges *ranges = *rangesp;
2639
2640
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 if (!ranges)
2641 ✗ return;
2642
2643
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 18 times.
36 for (i = 0; i < ranges->nb_ranges * ranges->nb_components; i++) {
2644 18 AVOptionRange *range = ranges->range[i];
2645
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 if (range) {
2646 18 av_freep(&range->str);
2647 18 av_freep(&ranges->range[i]);
2648 }
2649 }
2650 18 av_freep(&ranges->range);
2651 18 av_freep(rangesp);
2652 }
2653
2654 315 int av_opt_is_set_to_default(void *obj, const AVOption *o)
2655 {
2656 int64_t i64;
2657 double d;
2658 AVRational q;
2659 int ret, w, h;
2660 char *str;
2661 void *dst;
2662
2663
2/4
✓ Branch 0 taken 315 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 315 times.
315 if (!o || !obj)
2664 ✗ return AVERROR(EINVAL);
2665
2666 315 dst = ((uint8_t*)obj) + o->offset;
2667
2668
2/2
✓ Branch 0 taken 22 times.
✓ Branch 1 taken 293 times.
315 if (o->type & AV_OPT_TYPE_FLAG_ARRAY) {
2669
2/2
✓ Branch 0 taken 16 times.
✓ Branch 1 taken 6 times.
22 const char *def = o->default_val.arr ? o->default_val.arr->def : NULL;
2670 uint8_t *val;
2671
2672 22 ret = opt_get_array(o, dst, &val);
2673
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 22 times.
22 if (ret < 0)
2674 ✗ return ret;
2675
2676
2/2
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 19 times.
22 if (!!val != !!def)
2677 3 ret = 0;
2678
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 9 times.
19 else if (val)
2679 10 ret = !strcmp(val, def);
2680 else
2681 9 ret = 1;
2682
2683 22 av_freep(&val);
2684
2685 22 return ret;
2686 }
2687
2688
11/13
✗ Branch 0 not taken.
✓ Branch 1 taken 157 times.
✓ Branch 2 taken 15 times.
✓ Branch 3 taken 12 times.
✓ Branch 4 taken 6 times.
✓ Branch 5 taken 6 times.
✓ Branch 6 taken 41 times.
✓ Branch 7 taken 18 times.
✓ Branch 8 taken 18 times.
✓ Branch 9 taken 8 times.
✓ Branch 10 taken 6 times.
✓ Branch 11 taken 6 times.
✗ Branch 12 not taken.
293 switch (o->type) {
2689 ✗ case AV_OPT_TYPE_CONST:
2690 293 return 1;
2691 157 case AV_OPT_TYPE_BOOL:
2692 case AV_OPT_TYPE_FLAGS:
2693 case AV_OPT_TYPE_PIXEL_FMT:
2694 case AV_OPT_TYPE_SAMPLE_FMT:
2695 case AV_OPT_TYPE_INT:
2696 case AV_OPT_TYPE_UINT:
2697 case AV_OPT_TYPE_DURATION:
2698 case AV_OPT_TYPE_INT64:
2699 case AV_OPT_TYPE_UINT64:
2700 157 read_number(o, dst, NULL, NULL, &i64);
2701 157 return o->default_val.i64 == i64;
2702 15 case AV_OPT_TYPE_CHLAYOUT: {
2703 15 AVChannelLayout ch_layout = { 0 };
2704
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 9 times.
15 if (o->default_val.str) {
2705
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
6 if ((ret = av_channel_layout_from_string(&ch_layout, o->default_val.str)) < 0)
2706 ✗ return ret;
2707 }
2708 15 ret = !av_channel_layout_compare((AVChannelLayout *)dst, &ch_layout);
2709 15 av_channel_layout_uninit(&ch_layout);
2710 15 return ret;
2711 }
2712 12 case AV_OPT_TYPE_STRING:
2713 12 str = *(char **)dst;
2714
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 12 times.
12 if (str == o->default_val.str) //2 NULLs
2715 ✗ return 1;
2716
3/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 10 times.
12 if (!str || !o->default_val.str) //1 NULL
2717 2 return 0;
2718 10 return !strcmp(str, o->default_val.str);
2719 6 case AV_OPT_TYPE_DOUBLE:
2720 6 d = *(double *)dst;
2721
3/6
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 5 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
6 return o->default_val.dbl == d || isnan(d) && isnan(o->default_val.dbl);
2722 6 case AV_OPT_TYPE_FLOAT:
2723 6 d = *(float *)dst;
2724
3/6
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 5 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
6 return (float)o->default_val.dbl == d || isnan(d) && isnan(o->default_val.dbl);
2725 41 case AV_OPT_TYPE_RATIONAL: {
2726 41 AVRational v = *(AVRational *) dst;
2727 41 q = av_d2q(o->default_val.dbl, INT_MAX);
2728
3/6
✓ Branch 1 taken 9 times.
✓ Branch 2 taken 32 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 9 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
41 return !av_cmp_q(v, q) || (!q.den && !v.den);
2729 }
2730 18 case AV_OPT_TYPE_BINARY: {
2731 struct {
2732 uint8_t *data;
2733 int size;
2734 18 } tmp = {0};
2735 18 int opt_size = *(int *)((void **)dst + 1);
2736 18 void *opt_ptr = *(void **)dst;
2737
6/6
✓ Branch 0 taken 13 times.
✓ Branch 1 taken 5 times.
✓ Branch 2 taken 7 times.
✓ Branch 3 taken 6 times.
✓ Branch 4 taken 6 times.
✓ Branch 5 taken 1 times.
18 if (!opt_size && (!o->default_val.str || !strlen(o->default_val.str)))
2738 12 return 1;
2739
4/6
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 5 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 5 times.
6 if (!opt_size || !o->default_val.str || !strlen(o->default_val.str ))
2740 1 return 0;
2741
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 if (opt_size != strlen(o->default_val.str) / 2)
2742 ✗ return 0;
2743 5 ret = set_string_binary(NULL, NULL, o->default_val.str, &tmp.data);
2744
1/2
✓ Branch 0 taken 5 times.
✗ Branch 1 not taken.
5 if (!ret)
2745 5 ret = !memcmp(opt_ptr, tmp.data, tmp.size);
2746 5 av_free(tmp.data);
2747 5 return ret;
2748 }
2749 18 case AV_OPT_TYPE_DICT: {
2750 18 AVDictionary *dict1 = NULL;
2751 18 AVDictionary *dict2 = *(AVDictionary **)dst;
2752 18 const AVDictionaryEntry *en1 = NULL;
2753 18 const AVDictionaryEntry *en2 = NULL;
2754 18 ret = av_dict_parse_string(&dict1, o->default_val.str, "=", ":", 0);
2755
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 if (ret < 0) {
2756 ✗ av_dict_free(&dict1);
2757 ✗ return ret;
2758 }
2759 do {
2760 23 en1 = av_dict_iterate(dict1, en1);
2761 23 en2 = av_dict_iterate(dict2, en2);
2762
6/8
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 17 times.
✓ Branch 2 taken 5 times.
✓ Branch 3 taken 1 times.
✓ Branch 4 taken 5 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 5 times.
✗ Branch 7 not taken.
23 } while (en1 && en2 && !strcmp(en1->key, en2->key) && !strcmp(en1->value, en2->value));
2763 18 av_dict_free(&dict1);
2764
4/4
✓ Branch 0 taken 17 times.
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 11 times.
✓ Branch 3 taken 6 times.
18 return (!en1 && !en2);
2765 }
2766 8 case AV_OPT_TYPE_IMAGE_SIZE:
2767
3/4
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 6 times.
8 if (!o->default_val.str || !strcmp(o->default_val.str, "none"))
2768 2 w = h = 0;
2769
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
6 else if ((ret = av_parse_video_size(&w, &h, o->default_val.str)) < 0)
2770 ✗ return ret;
2771
3/4
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 3 times.
✓ Branch 2 taken 5 times.
✗ Branch 3 not taken.
8 return (w == *(int *)dst) && (h == *((int *)dst+1));
2772 6 case AV_OPT_TYPE_VIDEO_RATE:
2773 6 q = (AVRational){0, 0};
2774
1/2
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
6 if (o->default_val.str) {
2775
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
6 if ((ret = av_parse_video_rate(&q, o->default_val.str)) < 0)
2776 ✗ return ret;
2777 }
2778 6 return !av_cmp_q(*(AVRational*)dst, q);
2779 6 case AV_OPT_TYPE_COLOR: {
2780 6 uint8_t color[4] = {0, 0, 0, 0};
2781
1/2
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
6 if (o->default_val.str) {
2782
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
6 if ((ret = av_parse_color(color, o->default_val.str, -1, NULL)) < 0)
2783 ✗ return ret;
2784 }
2785 6 return !memcmp(color, dst, sizeof(color));
2786 }
2787 ✗ default:
2788 ✗ av_log(obj, AV_LOG_WARNING, "Not supported option type: %d, option name: %s\n", o->type, o->name);
2789 ✗ break;
2790 }
2791 ✗ return AVERROR_PATCHWELCOME;
2792 }
2793
2794 62 int av_opt_is_set_to_default_by_name(void *obj, const char *name, int search_flags)
2795 {
2796 const AVOption *o;
2797 void *target;
2798
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 62 times.
62 if (!obj)
2799 ✗ return AVERROR(EINVAL);
2800 62 o = av_opt_find2(obj, name, NULL, 0, search_flags, &target);
2801
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 56 times.
62 if (!o)
2802 6 return AVERROR_OPTION_NOT_FOUND;
2803 56 return av_opt_is_set_to_default(target, o);
2804 }
2805
2806 59 static int opt_serialize(void *obj, int opt_flags, int flags, int *cnt,
2807 AVBPrint *bprint, const char key_val_sep, const char pairs_sep)
2808 {
2809 59 const AVOption *o = NULL;
2810 59 void *child = NULL;
2811 uint8_t *buf;
2812 int ret;
2813 59 const char special_chars[] = {pairs_sep, key_val_sep, '\0'};
2814
2815
2/2
✓ Branch 0 taken 57 times.
✓ Branch 1 taken 2 times.
59 if (flags & AV_OPT_SERIALIZE_SEARCH_CHILDREN)
2816
2/2
✓ Branch 1 taken 22 times.
✓ Branch 2 taken 57 times.
79 while (child = av_opt_child_next(obj, child)) {
2817 22 ret = opt_serialize(child, opt_flags, flags, cnt, bprint,
2818 key_val_sep, pairs_sep);
2819
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 22 times.
22 if (ret < 0)
2820 ✗ return ret;
2821 }
2822
2823
2/2
✓ Branch 1 taken 681 times.
✓ Branch 2 taken 59 times.
740 while (o = av_opt_next(obj, o)) {
2824
2/2
✓ Branch 0 taken 240 times.
✓ Branch 1 taken 441 times.
681 if (o->type == AV_OPT_TYPE_CONST)
2825 240 continue;
2826
2/2
✓ Branch 0 taken 261 times.
✓ Branch 1 taken 180 times.
441 if ((flags & AV_OPT_SERIALIZE_OPT_FLAGS_EXCLUDE)) {
2827
2/2
✓ Branch 0 taken 62 times.
✓ Branch 1 taken 199 times.
261 if ((flags & AV_OPT_SERIALIZE_OPT_FLAGS_EXACT)) {
2828
2/2
✓ Branch 0 taken 27 times.
✓ Branch 1 taken 35 times.
62 if (o->flags == opt_flags)
2829 27 continue;
2830
2/2
✓ Branch 0 taken 31 times.
✓ Branch 1 taken 168 times.
199 } else if ((o->flags & opt_flags) == opt_flags)
2831 31 continue;
2832 } else {
2833
4/4
✓ Branch 0 taken 62 times.
✓ Branch 1 taken 118 times.
✓ Branch 2 taken 35 times.
✓ Branch 3 taken 27 times.
180 if ((flags & AV_OPT_SERIALIZE_OPT_FLAGS_EXACT) && o->flags != opt_flags)
2834 35 continue;
2835
2/2
✓ Branch 0 taken 33 times.
✓ Branch 1 taken 112 times.
145 else if (((o->flags & opt_flags) != opt_flags))
2836 33 continue;
2837 }
2838
4/4
✓ Branch 0 taken 259 times.
✓ Branch 1 taken 56 times.
✓ Branch 3 taken 174 times.
✓ Branch 4 taken 85 times.
315 if (flags & AV_OPT_SERIALIZE_SKIP_DEFAULTS && av_opt_is_set_to_default(obj, o) > 0)
2839 174 continue;
2840
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 141 times.
141 if ((ret = av_opt_get(obj, o->name, 0, &buf)) < 0) {
2841 ✗ av_bprint_finalize(bprint, NULL);
2842 ✗ return ret;
2843 }
2844
1/2
✓ Branch 0 taken 141 times.
✗ Branch 1 not taken.
141 if (buf) {
2845
2/2
✓ Branch 0 taken 104 times.
✓ Branch 1 taken 37 times.
141 if ((*cnt)++)
2846 104 av_bprint_append_data(bprint, &pairs_sep, 1);
2847 141 av_bprint_escape(bprint, o->name, special_chars, AV_ESCAPE_MODE_BACKSLASH, 0);
2848 141 av_bprint_append_data(bprint, &key_val_sep, 1);
2849 141 av_bprint_escape(bprint, buf, special_chars, AV_ESCAPE_MODE_BACKSLASH, 0);
2850 141 av_freep(&buf);
2851 }
2852 }
2853
2854 59 return 0;
2855 }
2856
2857 37 int av_opt_serialize(void *obj, int opt_flags, int flags, char **buffer,
2858 const char key_val_sep, const char pairs_sep)
2859 {
2860 AVBPrint bprint;
2861 37 int ret, cnt = 0;
2862
2863
4/8
✓ Branch 0 taken 37 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 37 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 37 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 37 times.
✗ Branch 7 not taken.
37 if (pairs_sep == '\0' || key_val_sep == '\0' || pairs_sep == key_val_sep ||
2864
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 37 times.
37 pairs_sep == '\\' || key_val_sep == '\\') {
2865 ✗ av_log(obj, AV_LOG_ERROR, "Invalid separator(s) found.");
2866 ✗ return AVERROR(EINVAL);
2867 }
2868
2869
2/4
✓ Branch 0 taken 37 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 37 times.
37 if (!obj || !buffer)
2870 ✗ return AVERROR(EINVAL);
2871
2872 37 *buffer = NULL;
2873 37 av_bprint_init(&bprint, 64, AV_BPRINT_SIZE_UNLIMITED);
2874
2875 37 ret = opt_serialize(obj, opt_flags, flags, &cnt, &bprint,
2876 key_val_sep, pairs_sep);
2877
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 37 times.
37 if (ret < 0)
2878 ✗ return ret;
2879
2880 37 ret = av_bprint_finalize(&bprint, buffer);
2881
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 37 times.
37 if (ret < 0)
2882 ✗ return ret;
2883 37 return 0;
2884 }
2885