Sorry, please disregard this patch. I just realized that my test changes are not in it.
Kenny > On Aug 10, 2020, at 7:36 PM, Kenny McClive <kenny.mccl...@me.com> wrote: > > Previously, the only way to input the master display and content light > metadata required for HDR10 was through x265-params. Obviously, that only > worked with x265. If you wanted to use a different encoder like nvenc, you > were out of luck. The options specified are written to the container (mov or > matroska) only. Additional work would be required to write it to frames. The > default values for the master display options may seem unorthodox, but it > allows you to differentiate between 0 (which some movies use) and > unspecified. The same was not done for content light metadata because 0 seems > to mean unspecified in other systems such as x265. > > Signed-off-by: Kenny McClive <kenny.mccl...@me.com> > --- > libavcodec/avcodec.h | 84 +++++++++++++++++++++++ > libavcodec/codec_par.h | 7 ++ > libavcodec/options_table.h | 12 ++++ > libavcodec/utils.c | 133 +++++++++++++++++++++++++++++++++++++ > libavformat/matroskaenc.c | 62 +++++++++++------ > libavformat/movenc.c | 29 ++++++-- > 6 files changed, 298 insertions(+), 29 deletions(-) > > diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h > index c91b2fd169..24f97345b7 100644 > --- a/libavcodec/avcodec.h > +++ b/libavcodec/avcodec.h > @@ -2352,6 +2352,90 @@ typedef struct AVCodecContext { > * - encoding: set by user > */ > int export_side_data; > + > + /** > + * CIE 1931 x chromaticity coord of red color primary for mastering > display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_red_x; > + > + /** > + * CIE 1931 y chromaticity coord of red color primary for mastering > display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_red_y; > + > + /** > + * CIE 1931 x chromaticity coord of green color primary for mastering > display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_green_x; > + > + /** > + * CIE 1931 y chromaticity coord of green color primary for mastering > display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_green_y; > + > + /** > + * CIE 1931 x chromaticity coord of blue color primary for mastering > display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_blue_x; > + > + /** > + * CIE 1931 y chromaticity coord of blue color primary for mastering > display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_blue_y; > + > + /** > + * CIE 1931 x chromaticity coord of white point for mastering display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_white_x; > + > + /** > + * CIE 1931 y chromaticity coord of white point for mastering display. > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_white_y; > + > + /** > + * Min luminance of mastering display (cd/m^2). > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_min_luminance; > + > + /** > + * Max luminance of mastering display (cd/m^2). > + * - encoding: Set by user > + * - decoding: unused > + */ > + AVRational master_display_max_luminance; > + > + /** > + * Max content light level (cd/m^2). > + * - encoding: Set by user > + * - decoding: unused > + */ > + unsigned max_cll; > + > + /** > + * Max average light level per frame (cd/m^2). > + * - encoding: Set by user > + * - decoding: unused > + */ > + unsigned max_fall; > } AVCodecContext; > > #if FF_API_CODEC_GET_SET > diff --git a/libavcodec/codec_par.h b/libavcodec/codec_par.h > index 948758e237..fe1fe3861b 100644 > --- a/libavcodec/codec_par.h > +++ b/libavcodec/codec_par.h > @@ -24,6 +24,7 @@ > #include <stdint.h> > > #include "libavutil/avutil.h" > +#include "libavutil/mastering_display_metadata.h" > #include "libavutil/rational.h" > #include "libavutil/pixfmt.h" > > @@ -149,6 +150,12 @@ typedef struct AVCodecParameters { > enum AVColorSpace color_space; > enum AVChromaLocation chroma_location; > > + /** > + * Video only. HDR metadata. > + */ > + AVMasteringDisplayMetadata master_display_metadata; > + AVContentLightMetadata content_light_metadata; > + > /** > * Video only. Number of delayed frames. > */ > diff --git a/libavcodec/options_table.h b/libavcodec/options_table.h > index 1d0db1b5a4..680d05469a 100644 > --- a/libavcodec/options_table.h > +++ b/libavcodec/options_table.h > @@ -412,6 +412,18 @@ static const AVOption avcodec_options[] = { > {"bottomleft", "Bottom-left", 0, AV_OPT_TYPE_CONST, {.i64 = > AVCHROMA_LOC_BOTTOMLEFT }, INT_MIN, INT_MAX, V|E|D, > "chroma_sample_location_type"}, > {"bottom", "Bottom", 0, AV_OPT_TYPE_CONST, {.i64 = > AVCHROMA_LOC_BOTTOM }, INT_MIN, INT_MAX, V|E|D, > "chroma_sample_location_type"}, > {"unspecified", "Unspecified", 0, AV_OPT_TYPE_CONST, {.i64 = > AVCHROMA_LOC_UNSPECIFIED }, INT_MIN, INT_MAX, V|E|D, > "chroma_sample_location_type"}, > +{"master_display_red_x", "mastering display x chromaticity coord for red > color primary", OFFSET(master_display_red_x), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_red_y", "mastering display y chromaticity coord for red > color primary", OFFSET(master_display_red_y), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_green_x", "mastering display x chromaticity coord for green > color primary", OFFSET(master_display_green_x), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_green_y", "mastering display y chromaticity coord for green > color primary", OFFSET(master_display_green_y), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_blue_x", "mastering display x chromaticity coord for blue > color primary", OFFSET(master_display_blue_x), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_blue_y", "mastering display y chromaticity coord for blue > color primary", OFFSET(master_display_blue_y), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_white_x", "mastering display x chromaticity coord for white > point", OFFSET(master_display_white_x), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_white_y", "mastering display y chromaticity coord for white > point", OFFSET(master_display_white_y), AV_OPT_TYPE_RATIONAL, {.dbl = > INT_MAX}, 0, INT_MAX, V|E}, > +{"master_display_min_lum", "mastering display min luminance", > OFFSET(master_display_min_luminance), AV_OPT_TYPE_RATIONAL, {.dbl = INT_MAX}, > 0, INT_MAX, V|E}, > +{"master_display_max_lum", "mastering display max luminance", > OFFSET(master_display_max_luminance), AV_OPT_TYPE_RATIONAL, {.dbl = INT_MAX}, > 0, INT_MAX, V|E}, > +{"max_cll", "max content light level", OFFSET(max_cll), AV_OPT_TYPE_INT64, > {.i64 = DEFAULT }, 0, INT_MAX, V|E}, > +{"max_fall", "max frame average light level", OFFSET(max_fall), > AV_OPT_TYPE_INT64, {.i64 = DEFAULT }, 0, INT_MAX, V|E}, > {"log_level_offset", "set the log level offset", OFFSET(log_level_offset), > AV_OPT_TYPE_INT, {.i64 = 0 }, INT_MIN, INT_MAX }, > {"slices", "set the number of slices, used in parallelized encoding", > OFFSET(slices), AV_OPT_TYPE_INT, {.i64 = 0 }, 0, INT_MAX, V|E}, > {"thread_type", "select multithreading type", OFFSET(thread_type), > AV_OPT_TYPE_FLAGS, {.i64 = FF_THREAD_SLICE|FF_THREAD_FRAME }, 0, INT_MAX, > V|A|E|D, "thread_type"}, > diff --git a/libavcodec/utils.c b/libavcodec/utils.c > index 5a2a90b030..b31041a755 100644 > --- a/libavcodec/utils.c > +++ b/libavcodec/utils.c > @@ -35,6 +35,7 @@ > #include "libavutil/frame.h" > #include "libavutil/hwcontext.h" > #include "libavutil/internal.h" > +#include "libavutil/mastering_display_metadata.h" > #include "libavutil/mathematics.h" > #include "libavutil/mem_internal.h" > #include "libavutil/pixdesc.h" > @@ -67,6 +68,7 @@ > const char av_codec_ffversion[] = "FFmpeg version " FFMPEG_VERSION; > > static AVMutex codec_mutex = AV_MUTEX_INITIALIZER; > +static int unspecified_coord = INT_MAX; > > void av_fast_padded_malloc(void *ptr, unsigned int *size, size_t min_size) > { > @@ -2031,6 +2033,34 @@ AVCPBProperties *ff_add_cpb_side_data(AVCodecContext > *avctx) > return props; > } > > +static void master_display_metadata_reset(AVMasteringDisplayMetadata > *metadata) > +{ > + if (!metadata) > + return; > + > + metadata->display_primaries[0][0] = (AVRational){ 0, 1 }; > + metadata->display_primaries[0][1] = (AVRational){ 0, 1 }; > + metadata->display_primaries[1][0] = (AVRational){ 0, 1 }; > + metadata->display_primaries[1][1] = (AVRational){ 0, 1 }; > + metadata->display_primaries[2][0] = (AVRational){ 0, 1 }; > + metadata->display_primaries[2][1] = (AVRational){ 0, 1 }; > + metadata->white_point[0] = (AVRational){ 0, 1 }; > + metadata->white_point[1] = (AVRational){ 0, 1 }; > + metadata->has_primaries = 0; > + metadata->min_luminance = (AVRational){ 0, 1 }; > + metadata->max_luminance = (AVRational){ 0, 1 }; > + metadata->has_luminance = 0; > +} > + > +static void content_light_metadata_reset(AVContentLightMetadata *metadata) > +{ > + if (!metadata) > + return; > + > + metadata->MaxCLL = 0; > + metadata->MaxFALL = 0; > +} > + > static void codec_parameters_reset(AVCodecParameters *par) > { > av_freep(&par->extradata); > @@ -2049,6 +2079,9 @@ static void codec_parameters_reset(AVCodecParameters > *par) > par->sample_aspect_ratio = (AVRational){ 0, 1 }; > par->profile = FF_PROFILE_UNKNOWN; > par->level = FF_LEVEL_UNKNOWN; > + > + master_display_metadata_reset(&par->master_display_metadata); > + content_light_metadata_reset(&par->content_light_metadata); > } > > AVCodecParameters *avcodec_parameters_alloc(void) > @@ -2090,6 +2123,53 @@ int avcodec_parameters_copy(AVCodecParameters *dst, > const AVCodecParameters *src > return 0; > } > > +static void > mastering_display_metadata_from_context(AVMasteringDisplayMetadata *metadata, > + const AVCodecContext > *codec) > +{ > + if (!metadata || !codec) > + return; > + > + master_display_metadata_reset(metadata); > + > + if (codec->master_display_red_x.num != unspecified_coord && > + codec->master_display_red_y.num != unspecified_coord && > + codec->master_display_green_x.num != unspecified_coord && > + codec->master_display_green_y.num != unspecified_coord && > + codec->master_display_blue_x.num != unspecified_coord && > + codec->master_display_blue_y.num != unspecified_coord && > + codec->master_display_white_x.num != unspecified_coord && > + codec->master_display_white_y.num != unspecified_coord) > + { > + metadata->display_primaries[0][0] = codec->master_display_red_x; > + metadata->display_primaries[0][1] = codec->master_display_red_y; > + metadata->display_primaries[1][0] = codec->master_display_green_x; > + metadata->display_primaries[1][1] = codec->master_display_green_y; > + metadata->display_primaries[2][0] = codec->master_display_blue_x; > + metadata->display_primaries[2][1] = codec->master_display_blue_y; > + metadata->white_point[0] = codec->master_display_white_x; > + metadata->white_point[1] = codec->master_display_white_y; > + metadata->has_primaries = 1; > + } > + > + if (codec->master_display_min_luminance.den > 0 && > + codec->master_display_max_luminance.den > 0) > + { > + metadata->min_luminance = codec->master_display_min_luminance; > + metadata->max_luminance = codec->master_display_max_luminance; > + metadata->has_luminance = 1; > + } > +} > + > +static void content_light_metadata_from_context(AVContentLightMetadata > *metadata, > + const AVCodecContext *codec) > +{ > + if (!metadata || !codec) > + return; > + > + metadata->MaxCLL = codec->max_cll; > + metadata->MaxFALL = codec->max_fall; > +} > + > int avcodec_parameters_from_context(AVCodecParameters *par, > const AVCodecContext *codec) > { > @@ -2118,6 +2198,9 @@ int avcodec_parameters_from_context(AVCodecParameters > *par, > par->chroma_location = codec->chroma_sample_location; > par->sample_aspect_ratio = codec->sample_aspect_ratio; > par->video_delay = codec->has_b_frames; > + > + > mastering_display_metadata_from_context(&par->master_display_metadata, codec); > + content_light_metadata_from_context(&par->content_light_metadata, > codec); > break; > case AVMEDIA_TYPE_AUDIO: > par->format = codec->sample_fmt; > @@ -2147,6 +2230,53 @@ int avcodec_parameters_from_context(AVCodecParameters > *par, > return 0; > } > > +static void mastering_display_metadata_to_context(AVCodecContext *codec, > + const > AVMasteringDisplayMetadata *metadata) > +{ > + if (!codec || !metadata) > + return; > + > + if (metadata->has_primaries) > + { > + codec->master_display_red_x = metadata->display_primaries[0][0]; > + codec->master_display_red_y = metadata->display_primaries[0][1]; > + codec->master_display_green_x = metadata->display_primaries[1][0]; > + codec->master_display_green_y = metadata->display_primaries[1][1]; > + codec->master_display_blue_x = metadata->display_primaries[2][0]; > + codec->master_display_blue_y = metadata->display_primaries[2][1]; > + codec->master_display_white_x = metadata->white_point[0]; > + codec->master_display_white_y = metadata->white_point[1]; > + } else { > + codec->master_display_red_x = (AVRational){ unspecified_coord, 1 }; > + codec->master_display_red_y = (AVRational){ unspecified_coord, 1 }; > + codec->master_display_green_x = (AVRational){ unspecified_coord, 1 }; > + codec->master_display_green_y = (AVRational){ unspecified_coord, 1 }; > + codec->master_display_blue_x = (AVRational){ unspecified_coord, 1 }; > + codec->master_display_blue_y = (AVRational){ unspecified_coord, 1 }; > + codec->master_display_white_x = (AVRational){ unspecified_coord, 1 }; > + codec->master_display_white_y = (AVRational){ unspecified_coord, 1 }; > + } > + > + if (metadata->has_luminance) > + { > + codec->master_display_min_luminance = metadata->min_luminance; > + codec->master_display_max_luminance = metadata->max_luminance; > + } else { > + codec->master_display_min_luminance = (AVRational){ > unspecified_coord, 1 }; > + codec->master_display_max_luminance = (AVRational){ > unspecified_coord, 1 }; > + } > +} > + > +static void content_light_metadata_to_context(AVCodecContext *codec, > + const AVContentLightMetadata > *metadata) > +{ > + if (!codec || !metadata) > + return; > + > + codec->max_cll = metadata->MaxCLL; > + codec->max_fall = metadata->MaxFALL; > +} > + > int avcodec_parameters_to_context(AVCodecContext *codec, > const AVCodecParameters *par) > { > @@ -2173,6 +2303,9 @@ int avcodec_parameters_to_context(AVCodecContext *codec, > codec->chroma_sample_location = par->chroma_location; > codec->sample_aspect_ratio = par->sample_aspect_ratio; > codec->has_b_frames = par->video_delay; > + > + mastering_display_metadata_to_context(codec, > &par->master_display_metadata); > + content_light_metadata_to_context(codec, > &par->content_light_metadata); > break; > case AVMEDIA_TYPE_AUDIO: > codec->sample_fmt = par->format; > diff --git a/libavformat/matroskaenc.c b/libavformat/matroskaenc.c > index 233c472b8f..dfe9d45f6f 100644 > --- a/libavformat/matroskaenc.c > +++ b/libavformat/matroskaenc.c > @@ -869,43 +869,61 @@ static void mkv_write_video_color(AVIOContext *pb, > const AVStream *st, > put_ebml_uint(dyn_cp, MATROSKA_ID_VIDEOCOLORCHROMASITINGVERT, (ypos > >> 7) + 1); > } > > - side_data = av_stream_get_side_data(st, AV_PKT_DATA_CONTENT_LIGHT_LEVEL, > - NULL); > - if (side_data) { > - const AVContentLightMetadata *metadata = side_data; > - put_ebml_uint(dyn_cp, MATROSKA_ID_VIDEOCOLORMAXCLL, > metadata->MaxCLL); > - put_ebml_uint(dyn_cp, MATROSKA_ID_VIDEOCOLORMAXFALL, > metadata->MaxFALL); > + const AVContentLightMetadata *content_light_metadata = > &par->content_light_metadata; > + > + if (content_light_metadata->MaxCLL <= 0 || > content_light_metadata->MaxFALL <= 0) { > + side_data = av_stream_get_side_data(st, > AV_PKT_DATA_CONTENT_LIGHT_LEVEL, > + NULL); > + if (side_data) { > + content_light_metadata = side_data; > + } else { > + content_light_metadata = NULL; > + } > + } > + > + if (content_light_metadata) { > + put_ebml_uint(dyn_cp, MATROSKA_ID_VIDEOCOLORMAXCLL, > content_light_metadata->MaxCLL); > + put_ebml_uint(dyn_cp, MATROSKA_ID_VIDEOCOLORMAXFALL, > content_light_metadata->MaxFALL); > } > > - side_data = av_stream_get_side_data(st, > AV_PKT_DATA_MASTERING_DISPLAY_METADATA, > - NULL); > - if (side_data) { > + const AVMasteringDisplayMetadata *master_display_metadata = > &par->master_display_metadata; > + > + if (!master_display_metadata->has_primaries || > !master_display_metadata->has_luminance) { > + side_data = av_stream_get_side_data(st, > AV_PKT_DATA_MASTERING_DISPLAY_METADATA, > + NULL); > + if (side_data) { > + master_display_metadata = side_data; > + } else { > + master_display_metadata = NULL; > + } > + } > + > + if (master_display_metadata) { > ebml_master meta_element = start_ebml_master( > dyn_cp, MATROSKA_ID_VIDEOCOLORMASTERINGMETA, 10 * (2 + 1 + 8)); > - const AVMasteringDisplayMetadata *metadata = side_data; > - if (metadata->has_primaries) { > + if (master_display_metadata->has_primaries) { > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_RX, > - av_q2d(metadata->display_primaries[0][0])); > + > av_q2d(master_display_metadata->display_primaries[0][0])); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_RY, > - av_q2d(metadata->display_primaries[0][1])); > + > av_q2d(master_display_metadata->display_primaries[0][1])); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_GX, > - av_q2d(metadata->display_primaries[1][0])); > + > av_q2d(master_display_metadata->display_primaries[1][0])); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_GY, > - av_q2d(metadata->display_primaries[1][1])); > + > av_q2d(master_display_metadata->display_primaries[1][1])); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_BX, > - av_q2d(metadata->display_primaries[2][0])); > + > av_q2d(master_display_metadata->display_primaries[2][0])); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_BY, > - av_q2d(metadata->display_primaries[2][1])); > + > av_q2d(master_display_metadata->display_primaries[2][1])); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_WHITEX, > - av_q2d(metadata->white_point[0])); > + av_q2d(master_display_metadata->white_point[0])); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_WHITEY, > - av_q2d(metadata->white_point[1])); > + av_q2d(master_display_metadata->white_point[1])); > } > - if (metadata->has_luminance) { > + if (master_display_metadata->has_luminance) { > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_LUMINANCEMAX, > - av_q2d(metadata->max_luminance)); > + av_q2d(master_display_metadata->max_luminance)); > put_ebml_float(dyn_cp, MATROSKA_ID_VIDEOCOLOR_LUMINANCEMIN, > - av_q2d(metadata->min_luminance)); > + av_q2d(master_display_metadata->min_luminance)); > } > end_ebml_master(dyn_cp, meta_element); > } > diff --git a/libavformat/movenc.c b/libavformat/movenc.c > index 7db2e28840..074c463cee 100644 > --- a/libavformat/movenc.c > +++ b/libavformat/movenc.c > @@ -1947,14 +1947,21 @@ static int mov_write_colr_tag(AVIOContext *pb, > MOVTrack *track, int prefer_icc) > static int mov_write_clli_tag(AVIOContext *pb, MOVTrack *track) > { > const uint8_t *side_data; > - const AVContentLightMetadata *content_light_metadata; > + const AVContentLightMetadata *content_light_metadata = > &track->par->content_light_metadata; > > - side_data = av_stream_get_side_data(track->st, > AV_PKT_DATA_CONTENT_LIGHT_LEVEL, NULL); > - if (!side_data) { > + if (content_light_metadata->MaxCLL <= 0 || > content_light_metadata->MaxFALL <= 0) { > + side_data = av_stream_get_side_data(track->st, > AV_PKT_DATA_CONTENT_LIGHT_LEVEL, NULL); > + if (side_data) { > + content_light_metadata = (const > AVContentLightMetadata*)side_data; > + } else { > + content_light_metadata = NULL; > + } > + } > + > + if (!content_light_metadata) { > av_log(NULL, AV_LOG_VERBOSE, "Not writing 'clli' atom. No content > light level info.\n"); > return 0; > } > - content_light_metadata = (const AVContentLightMetadata*)side_data; > > avio_wb32(pb, 12); // size > ffio_wfourcc(pb, "clli"); > @@ -1973,10 +1980,18 @@ static int mov_write_mdcv_tag(AVIOContext *pb, > MOVTrack *track) > const int chroma_den = 50000; > const int luma_den = 10000; > const uint8_t *side_data; > - const AVMasteringDisplayMetadata *metadata; > + const AVMasteringDisplayMetadata *metadata = > &track->par->master_display_metadata; > > - side_data = av_stream_get_side_data(track->st, > AV_PKT_DATA_MASTERING_DISPLAY_METADATA, NULL); > - metadata = (const AVMasteringDisplayMetadata*)side_data; > + if (!metadata->has_primaries || !metadata->has_luminance) { > + side_data = av_stream_get_side_data(track->st, > AV_PKT_DATA_MASTERING_DISPLAY_METADATA, NULL); > + > + if (side_data) { > + metadata = (const AVMasteringDisplayMetadata*)side_data; > + } else { > + metadata = NULL; > + } > + } > + > if (!metadata || !metadata->has_primaries || !metadata->has_luminance) { > av_log(NULL, AV_LOG_VERBOSE, "Not writing 'mdcv' atom. Missing > mastering metadata.\n"); > return 0; > -- > 2.28.0 > > > _______________________________________________ > ffmpeg-devel mailing list > ffmpeg-devel@ffmpeg.org > https://ffmpeg.org/mailman/listinfo/ffmpeg-devel > > To unsubscribe, visit link above, or email > ffmpeg-devel-requ...@ffmpeg.org with subject "unsubscribe". _______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org https://ffmpeg.org/mailman/listinfo/ffmpeg-devel To unsubscribe, visit link above, or email ffmpeg-devel-requ...@ffmpeg.org with subject "unsubscribe".