[FFmpeg-devel] [PATCH 2/5] avformat/matroskadec: Parse dvcC/dvvC block additional mapping
quietvoid
tcchlisop0 at gmail.com
Thu Sep 23 03:46:21 EEST 2021
The parsing was implemented in isom, for the unification of
the mov/mpegts DOVI parsing into one function, in a later patch.
Most of the implementation was done by Plex developers.
Signed-off-by: quietvoid <tcChlisop0 at gmail.com>
---
libavformat/isom.c | 51 +++++++++++++++++++++++++++++++++++++++
libavformat/isom.h | 5 ++++
libavformat/matroskadec.c | 13 ++++++++++
3 files changed, 69 insertions(+)
diff --git a/libavformat/isom.c b/libavformat/isom.c
index 4df5440023..80a8f4d7b0 100644
--- a/libavformat/isom.c
+++ b/libavformat/isom.c
@@ -430,3 +430,54 @@ void ff_mov_write_chan(AVIOContext *pb, int64_t channel_layout)
}
avio_wb32(pb, 0); // mNumberChannelDescriptions
}
+
+int ff_mov_parse_dvcc_dvvc(AVFormatContext *s, AVStream *st, GetBitContext *gb)
+{
+ AVDOVIDecoderConfigurationRecord *dovi;
+ size_t dovi_size;
+ int ret;
+
+ if (gb->size_in_bits < 32)
+ return AVERROR_INVALIDDATA;
+
+ dovi = av_dovi_alloc(&dovi_size);
+ if (!dovi)
+ return AVERROR(ENOMEM);
+
+ dovi->dv_version_major = get_bits(gb, 8);
+ dovi->dv_version_minor = get_bits(gb, 8);
+
+ dovi->dv_profile = get_bits(gb, 7);
+ dovi->dv_level = get_bits(gb, 6);
+ dovi->rpu_present_flag = get_bits1(gb);
+ dovi->el_present_flag = get_bits1(gb);
+ dovi->bl_present_flag = get_bits1(gb);
+
+ // Has enough remaining data
+ if (gb->size_in_bits >= 36) {
+ dovi->dv_bl_signal_compatibility_id = get_bits(gb, 4);
+ } else {
+ // 0 stands for None
+ // Dolby Vision V1.2.93 profiles and levels
+ dovi->dv_bl_signal_compatibility_id = 0;
+ }
+
+ ret = av_stream_add_side_data(st, AV_PKT_DATA_DOVI_CONF,
+ (uint8_t *)dovi, dovi_size);
+ if (ret < 0) {
+ av_free(dovi);
+ return ret;
+ }
+
+ av_log(s, AV_LOG_TRACE, "DOVI, version: %d.%d, profile: %d, level: %d, "
+ "rpu flag: %d, el flag: %d, bl flag: %d, compatibility id: %d\n",
+ dovi->dv_version_major, dovi->dv_version_minor,
+ dovi->dv_profile, dovi->dv_level,
+ dovi->rpu_present_flag,
+ dovi->el_present_flag,
+ dovi->bl_present_flag,
+ dovi->dv_bl_signal_compatibility_id
+ );
+
+ return 0;
+}
diff --git a/libavformat/isom.h b/libavformat/isom.h
index 34a58c79b7..44bd839852 100644
--- a/libavformat/isom.h
+++ b/libavformat/isom.h
@@ -27,6 +27,9 @@
#include <stddef.h>
#include <stdint.h>
+#include "libavcodec/get_bits.h"
+
+#include "libavutil/dovi_meta.h"
#include "libavutil/encryption_info.h"
#include "libavutil/mastering_display_metadata.h"
#include "libavutil/spherical.h"
@@ -390,4 +393,6 @@ static inline enum AVCodecID ff_mov_get_lpcm_codec_id(int bps, int flags)
#define MOV_ISMV_TTML_TAG MKTAG('d', 'f', 'x', 'p')
#define MOV_MP4_TTML_TAG MKTAG('s', 't', 'p', 'p')
+int ff_mov_parse_dvcc_dvvc(AVFormatContext *s, AVStream *st, GetBitContext *gb);
+
#endif /* AVFORMAT_ISOM_H */
diff --git a/libavformat/matroskadec.c b/libavformat/matroskadec.c
index 8ae553953d..4633067d48 100644
--- a/libavformat/matroskadec.c
+++ b/libavformat/matroskadec.c
@@ -2323,6 +2323,14 @@ static int mkv_parse_video_projection(AVStream *st, const MatroskaTrack *track,
return 0;
}
+static int mkv_parse_dvcc_dvvc(AVFormatContext *s, AVStream *st, const MatroskaTrack *track,
+ EbmlBin *bin)
+{
+ GetBitContext gb;
+ init_get_bits8(&gb, bin->data, bin->size);
+ return ff_mov_parse_dvcc_dvvc(s, st, &gb);
+}
+
static int mkv_parse_block_addition_mappings(AVFormatContext *s, AVStream *st, const MatroskaTrack *track)
{
int i, ret;
@@ -2333,6 +2341,11 @@ static int mkv_parse_block_addition_mappings(AVFormatContext *s, AVStream *st, c
MatroskaBlockAdditionMapping *mapping = &mappings[i];
switch (mapping->type) {
+ case MKBETAG('d','v','c','C'):
+ case MKBETAG('d','v','v','C'):
+ if ((ret = mkv_parse_dvcc_dvvc(s, st, track, &mapping->extradata)) < 0)
+ return ret;
+ break;
default:
av_log(s, AV_LOG_DEBUG,
"Unknown block additional mapping type %i, value %i, name \"%s\"\n",
--
2.33.0
More information about the ffmpeg-devel
mailing list