2 * Filter layer - format negotiation
3 * Copyright (c) 2007 Bobby Bingham
5 * This file is part of FFmpeg.
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.
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.
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
34 * Add all refs from a to ret and destroy a.
36 #define MERGE_REF(ret, a, fmts, type, fail_statement) \
41 if (!(tmp = av_realloc_array(ret->refs, ret->refcount + a->refcount, \
46 for (i = 0; i < a->refcount; i ++) { \
47 ret->refs[ret->refcount] = a->refs[i]; \
48 *ret->refs[ret->refcount++] = ret; \
57 * Add all formats common to a and b to a, add b's refs to a and destroy b.
58 * If check is set, nothing is modified and it is only checked whether
59 * the formats are compatible.
60 * If empty_allowed is set and one of a,b->nb is zero, the lists are
61 * merged; otherwise, 0 (for nonmergeability) is returned.
63 #define MERGE_FORMATS(a, b, fmts, nb, type, check, empty_allowed) \
65 int i, j, k = 0, skip = 0; \
67 if (empty_allowed) { \
68 if (!a->nb || !b->nb) { \
72 FFSWAP(type *, a, b); \
77 for (i = 0; i < a->nb; i++) \
78 for (j = 0; j < b->nb; j++) \
79 if (a->fmts[i] == b->fmts[j]) { \
82 a->fmts[k++] = a->fmts[i]; \
85/* Check that there was at least one common format. \
86 * Notice that both a and b are unchanged if not. */ \
93 MERGE_REF(a, b, fmts, type, return AVERROR(ENOMEM);); \
100 int alpha1=0, alpha2=0;
101 int chroma1=0, chroma2=0;
108 /* Do not lose chroma or alpha in merging.
109 It happens if both lists have formats with chroma (resp. alpha), but
110 the only formats in common do not have it (e.g. YUV+gray vs.
111 RGB+gray): in that case, the merging would select the gray format,
112 possibly causing a lossy conversion elsewhere in the graph.
113 To avoid that, pretend that there are no common formats to force the
114 insertion of a conversion filter. */
116 for (
i = 0;
i <
a->nb_formats;
i++) {
118 for (j = 0; j <
b->nb_formats; j++) {
122 if (
a->formats[
i] ==
b->formats[j]) {
129 // If chroma or alpha can be lost through merging then do not merge
130 if (alpha2 > alpha1 || chroma2 > chroma1)
140 * Check the formats lists for compatibility for merging without actually
143 * @return 1 if they are compatible, 0 if not.
152 * Merge the formats lists if they are compatible and update all the
153 * references of a and b to point to the combined list and free the old
154 * lists as needed. The combined list usually contains the intersection of
155 * the lists of a and b.
157 * Both a and b must have owners (i.e. refcount > 0) for these functions.
159 * @return 1 if merging succeeded, 0 if a and b are incompatible
160 * and negative AVERROR code on failure.
161 * a and b are unmodified if 0 is returned.
169 * See can_merge_pix_fmts().
178 * See merge_pix_fmts().
189 if (
a ==
b)
return 1;
196 * See can_merge_pix_fmts().
204 * See merge_pix_fmts().
212 * See merge_pix_fmts().
218 unsigned a_all =
a->all_layouts +
a->all_counts;
219 unsigned b_all =
b->all_layouts +
b->all_counts;
220 int ret_max, ret_nb = 0,
i, j,
round;
224 if (
a ==
b)
return 1;
226 /* Put the most generic set in a, to avoid doing everything twice */
229 FFSWAP(
unsigned, a_all, b_all);
232 if (a_all == 1 && !b_all) {
233 /* keep only known layouts in b; works also for b_all = 1 */
234 for (
i = j = 0;
i <
b->nb_channel_layouts;
i++)
235 if (
KNOWN(&
b->channel_layouts[
i]) &&
i != j++) {
240 /* Not optimal: the unknown layouts of b may become known after
244 b->nb_channel_layouts = j;
250 ret_max =
a->nb_channel_layouts +
b->nb_channel_layouts;
254 /* a[known] intersect b[known] */
255 for (
i = 0;
i <
a->nb_channel_layouts;
i++) {
256 if (!
KNOWN(&
a->channel_layouts[
i]))
258 for (j = 0; j <
b->nb_channel_layouts; j++) {
269 /* 1st round: a[known] intersect b[generic]
270 2nd round: a[generic] intersect b[known] */
272 for (
i = 0;
i <
a->nb_channel_layouts;
i++) {
277 for (j = 0; j <
b->nb_channel_layouts; j++)
284 /* 1st round: swap to prepare 2nd round; 2nd round: put it back */
287 /* a[generic] intersect b[generic] */
288 for (
i = 0;
i <
a->nb_channel_layouts;
i++) {
289 if (
KNOWN(&
a->channel_layouts[
i]))
291 for (j = 0; j <
b->nb_channel_layouts; j++)
304 if (
a->refcount >
b->refcount)
311 b->nb_channel_layouts = ret_nb;
350#define PRINT_NAME(type, type_name) \
351static void print_##type_name(AVBPrint *bp, const void *fmtsp) \
353 const AVFilterFormats *fmts = fmtsp; \
354 for (int i = 0; i < fmts->nb_formats; i++) { \
355 const char *name = av_##type_name(fmts->formats[i]); \
356 av_bprint_chars(bp, ' ', i ? 1 : 0); \
357 av_bprint_append_data(bp, name, name ? strlen(name) : 0); \
370 for (
int i = 0;
i <
layouts->nb_channel_layouts;
i++) {
379 for (
int i = 0;
i <
rates->nb_formats;
i++)
383#define CONVERSION_FILTER_SWSCALE \
384 .conversion_filter = "scale", \
385 .conversion_opts_offset = offsetof(AVFilterGraph, scale_sws_opts),
387#define CONVERSION_FILTER_ARESAMPLE \
388 .conversion_filter = "aresample", \
389 .conversion_opts_offset = offsetof(AVFilterGraph, aresample_swr_opts),
393 .name =
"Pixel formats",
397 .print_list = print_get_pix_fmt_name,
401 .name =
"Color spaces",
405 .print_list = print_color_space_name,
409 .name =
"Color ranges",
413 .print_list = print_color_range_name,
417 .name =
"Alpha modes",
421 .print_list = print_alpha_mode_name,
422 .conversion_filter =
"premultiply_dynamic",
428 .name =
"Channel layouts",
436 .name =
"Sample rates",
444 .name =
"Sample formats",
448 .print_list = print_get_sample_fmt_name,
465 switch (link->
type) {
468 default:
return NULL;
481#define MAKE_FORMAT_LIST(type, field, count_field) \
485 for (count = 0; fmts[count] != -1; count++) \
487 formats = av_mallocz(sizeof(*formats)); \
490 formats->count_field = count; \
492 formats->field = av_malloc_array(count, sizeof(*formats->field)); \
493 if (!formats->field) { \
494 av_freep(&formats); \
499#define MAKE_FORMAT_LIST_TYPE(name, type) \
500 AVFilterFormats *ff_make_ ## name ## _list(const type* fmts) \
502 MAKE_FORMAT_LIST(AVFilterFormats, formats, nb_formats); \
504 formats->formats[count] = (int)fmts[count]; \
517 for (count = 0; fmts[count].nb_channels; count++)
530 for (
int i = 0;
i < count;
i++) {
540 for (
int i = 0;
i < count;
i++)
548#define ADD_FORMAT(f, fmt, unref_fn, type, list, nb) \
552 if (!(*f) && !(*f = av_mallocz(sizeof(**f)))) { \
553 return AVERROR(ENOMEM); \
556 fmts = av_realloc_array((*f)->list, (*f)->nb + 1, \
557 sizeof(*(*f)->list)); \
560 return AVERROR(ENOMEM); \
564 ASSIGN_FMT(f, fmt, list, nb); \
567#define ASSIGN_FMT(f, fmt, list, nb) \
569 (*f)->list[(*f)->nb++] = fmt; \
579#define ASSIGN_FMT(f, fmt, list, nb) \
582 memset((*f)->list + (*f)->nb, 0, sizeof(*(*f)->list)); \
583 ret = av_channel_layout_copy(&(*f)->list[(*f)->nb], fmt); \
599 int fmts[2] = { fmt, -1 };
623 unsigned nb_formats, fmt,
flags;
628 for (fmt = 0;; fmt++) {
635 (
desc->log2_chroma_w ||
desc->log2_chroma_h))
637 if ((
flags & (want | rej)) != want)
640 formats->formats[nb_formats] = fmt;
650 formats->nb_formats = nb_formats;
736#define FORMATS_REF(f, ref, unref_fn) \
740 return AVERROR(ENOMEM); \
742 tmp = av_realloc_array(f->refs, f->refcount + 1, sizeof(*f->refs)); \
745 return AVERROR(ENOMEM); \
748 f->refs[f->refcount++] = ref; \
762#define FIND_REF_INDEX(ref, idx) \
765 for (i = 0; i < (*ref)->refcount; i ++) \
766 if((*ref)->refs[i] == ref) { \
772#define FORMATS_UNREF(ref, list) \
779 FIND_REF_INDEX(ref, idx); \
782 memmove((*ref)->refs + idx, (*ref)->refs + idx + 1, \
783 sizeof(*(*ref)->refs) * ((*ref)->refcount - idx - 1)); \
784 --(*ref)->refcount; \
786 if (!(*ref)->refcount) { \
787 FREE_LIST(ref, list); \
788 av_free((*ref)->list); \
789 av_free((*ref)->refs); \
795 #define FREE_LIST(ref, list) do { } while(0)
802#define FREE_LIST(ref, list) \
804 for (int i = 0; i < (*ref)->nb_channel_layouts; i++) \
805 av_channel_layout_uninit(&(*ref)->list[i]); \
813#define FORMATS_CHANGEREF(oldref, newref) \
817 FIND_REF_INDEX(oldref, idx); \
820 (*oldref)->refs[idx] = newref; \
837#define SET_COMMON_FORMATS(ctx, fmts, media_type, ref_fn, unref_fn) \
841 return AVERROR(ENOMEM); \
843 for (i = 0; i < ctx->nb_inputs; i++) { \
844 AVFilterLink *const link = ctx->inputs[i]; \
845 if (link && !link->outcfg.fmts && \
846 (media_type == AVMEDIA_TYPE_UNKNOWN || link->type == media_type)) { \
847 int ret = ref_fn(fmts, &ctx->inputs[i]->outcfg.fmts); \
853 for (i = 0; i < ctx->nb_outputs; i++) { \
854 AVFilterLink *const link = ctx->outputs[i]; \
855 if (link && !link->incfg.fmts && \
856 (media_type == AVMEDIA_TYPE_UNKNOWN || link->type == media_type)) { \
857 int ret = ref_fn(fmts, &ctx->outputs[i]->incfg.fmts); \
864 if (!fmts->refcount) \
895 const int *samplerates)
913 const int *color_spaces)
931 const int *color_ranges)
949 const int *alpha_modes)
960 * A helper for query_formats() which sets all links to the same list of
961 * formats. If there are no links hooked to this filter, the list of formats is
985#define SET_COMMON_FORMATS2(ctx, cfg_in, cfg_out, fmts, media_type, \
988 return AVERROR(ENOMEM); \
990 for (unsigned i = 0; i < ctx->nb_inputs; i++) { \
991 const AVFilterLink *const link = ctx->inputs[i]; \
992 if (!cfg_in[i]->fmts && \
993 (media_type == AVMEDIA_TYPE_UNKNOWN || \
994 link->type == media_type)) { \
995 int ret = ref_fn(fmts, &cfg_in[i]->fmts); \
1001 for (unsigned i = 0; i < ctx->nb_outputs; i++) { \
1002 const AVFilterLink *const link = ctx->outputs[i]; \
1003 if (!cfg_out[i]->fmts && \
1004 (media_type == AVMEDIA_TYPE_UNKNOWN || \
1005 link->type == media_type)) { \
1006 int ret = ref_fn(fmts, &cfg_out[i]->fmts); \
1013 if (!fmts->refcount) \
1054 const int *samplerates)
1078 const int *color_spaces)
1102 const int *color_ranges)
1126 const int *alpha_modes)
1178 switch (
f->formats_state) {
1203 ctx->nb_outputs ?
ctx->outputs[0]->type :
1257 return check_list(log,
"pixel format", fmts);
1262 return check_list(log,
"sample format", fmts);
static const char *const format[]
static AVFormatContext * ctx
simple assert() macros that are a bit more flexible than ISO C assert().
#define av_assert2(cond)
assert() equivalent, that does lie in speed critical code.
#define av_assert1(cond)
assert() equivalent, that does not lie in speed critical code.
#define av_assert0(cond)
assert() equivalent, that is always enabled.
Main libavfilter public API header.
void av_bprintf(AVBPrint *buf, const char *fmt,...)
#define flags(name, subs,...)
#define i(width, name, range_min, range_max)
Public libavutil channel layout APIs header.
common internal and external API header
static const uint16_t channel_layouts[7]
int av_channel_layout_describe_bprint(const AVChannelLayout *channel_layout, AVBPrint *bp)
bprint variant of av_channel_layout_describe().
int av_channel_layout_compare(const AVChannelLayout *chl, const AVChannelLayout *chl1)
Check whether two channel layouts are semantically the same, i.e.
void av_channel_layout_uninit(AVChannelLayout *channel_layout)
Free any allocated data in the channel layout and reset the channel count to 0.
int av_channel_layout_check(const AVChannelLayout *channel_layout)
Check whether a channel layout is valid, i.e.
int av_channel_layout_copy(AVChannelLayout *dst, const AVChannelLayout *src)
Make a copy of a channel layout.
void av_bprint_chars(AVBPrint *buf, char c, unsigned n)
Append char c n times to a print buffer.
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
@ AVMEDIA_TYPE_UNKNOWN
Usually treated as AVMEDIA_TYPE_DATA.
int av_sample_fmt_is_planar(enum AVSampleFormat sample_fmt)
Check if the sample format is planar.
int av_get_bytes_per_sample(enum AVSampleFormat sample_fmt)
Return number of bytes per sample.
const char * av_get_sample_fmt_name(enum AVSampleFormat sample_fmt)
Return the name of sample_fmt, or NULL if sample_fmt is not recognized.
AVSampleFormat
Audio sample formats.
@ FF_FILTER_FORMATS_QUERY_FUNC
formats.query active.
@ FF_FILTER_FORMATS_SINGLE_PIXFMT
formats.pix_fmt active
@ FF_FILTER_FORMATS_SAMPLEFMTS_LIST
formats.samples_list active.
@ FF_FILTER_FORMATS_SINGLE_SAMPLEFMT
formats.sample_fmt active.
@ FF_FILTER_FORMATS_PASSTHROUGH
The default value meaning that this filter supports all formats and (for audio) sample rates and chan...
@ FF_FILTER_FORMATS_PIXFMT_LIST
formats.pixels_list active.
@ FF_FILTER_FORMATS_QUERY_FUNC2
formats.query_func2 active.
static const FFFilter * fffilter(const AVFilter *f)
Macro definitions for various function/variable attributes.
static av_always_inline av_const double round(double x)
#define FFSWAP(type, a, b)
void * av_calloc(size_t nmemb, size_t size)
Memory handling functions.
#define check(x, y, S, v)
enum MovChannelLayoutTag * layouts
const AVPixFmtDescriptor * av_pix_fmt_desc_get(enum AVPixelFormat pix_fmt)
#define AV_PIX_FMT_FLAG_ALPHA
The pixel format has an alpha channel.
#define AV_PIX_FMT_FLAG_HWACCEL
Pixel format is an HW accelerated format.
#define AV_PIX_FMT_FLAG_PLANAR
At least one pixel component is not in the first data plane.
AVColorRange
Visual content value range.
@ AVCOL_RANGE_NB
Not part of ABI.
AVAlphaMode
Correlation between the alpha channel and color values.
@ AVALPHA_MODE_NB
Not part of ABI.
AVPixelFormat
Pixel format.
AVColorSpace
YUV colorspace type.
@ AVCOL_SPC_NB
Not part of ABI.
@ AVCOL_SPC_RESERVED
reserved for future use by ITU-T and ISO/IEC just like 15-255 are
#define FF_ARRAY_ELEMS(a)
An AVChannelLayout holds information about the channel layout of audio data.
int nb_channels
Number of channels in this layout.
A list of supported channel layouts.
char all_layouts
accept any known channel layout
char all_counts
accept any channel layout or count
AVChannelLayout * channel_layouts
list of channel layouts
int nb_channel_layouts
number of channel layouts
A link between two filters.
enum AVMediaType type
filter media type
Callbacks and properties to describe the steps of a format negotiation.
Descriptor that unambiguously describes how the bits of a pixel are stored in the up to 4 data planes...
uint64_t flags
Combination of AV_PIX_FMT_FLAG_... flags.
uint8_t nb_components
The number of components each pixel has, (1-4)
#define av_malloc_array(a, b)
static int ref[MAX_W *MAX_W]