summaryrefslogtreecommitdiff
path: root/libavformat/matroskadec.c
diff options
context:
space:
mode:
authorAndreas Rheinhardt <andreas.rheinhardt@gmail.com>2019-05-17 00:30:06 +0200
committerJames Almer <jamrial@gmail.com>2019-07-16 16:16:58 -0300
commitc1abd95ad0964ff7295fa38af564f2dea1a3b314 (patch)
tree7f4a342710b37579ef094cbd13345bb4a1f01209 /libavformat/matroskadec.c
parenta3db9f62a42a8e5365de67722ecfac7065a70699 (diff)
avformat/matroskadec: Link to parents in syntax tables
By linking to the syntax of the parent (i.e. the containing master element) one can check whether an element is actually part of a higher level in the EBML hierarchy. Knowing this is important for unknown-length levels, because they end when an element that doesn't belong to this, but to a higher hierarchy level is encountered. Sometimes there are different syntaxes dealing with the same elements. In this case it is important to use a parent that contains all the elements at the parent level; whether this is the syntax actually used to enter the child's level is irrelevant. This affects the list of level 1 elements (which has been used as parent for matroska_cluster, too) and it affects recursive elements (currently only the SimpleTag), where the non-recursive parent has to be choosen. This is in preparation for a patch that redoes level handling. Finally, the segment id has been added to ebml_syntax. This will enable handling of unknown-length EBML headers. Signed-off-by: Andreas Rheinhardt <andreas.rheinhardt@gmail.com>
Diffstat (limited to 'libavformat/matroskadec.c')
-rw-r--r--libavformat/matroskadec.c89
1 files changed, 50 insertions, 39 deletions
diff --git a/libavformat/matroskadec.c b/libavformat/matroskadec.c
index 6825002523..e8ebdea661 100644
--- a/libavformat/matroskadec.c
+++ b/libavformat/matroskadec.c
@@ -378,6 +378,15 @@ typedef struct MatroskaDemuxContext {
int bandwidth;
} MatroskaDemuxContext;
+#define CHILD_OF(parent) { .def = { .n = parent } }
+
+static const EbmlSyntax ebml_syntax[], matroska_segment[], matroska_track_video_color[], matroska_track_video[],
+ matroska_track[], matroska_track_encoding[], matroska_track_encodings[],
+ matroska_track_combine_planes[], matroska_track_operation[], matroska_tracks[],
+ matroska_attachments[], matroska_chapter_entry[], matroska_chapter[], matroska_chapters[],
+ matroska_index_entry[], matroska_index[], matroska_tag[], matroska_tags[], matroska_seekhead[],
+ matroska_blockadditions[], matroska_blockgroup[], matroska_cluster_parsing[];
+
static const EbmlSyntax ebml_header[] = {
{ EBML_ID_EBMLREADVERSION, EBML_UINT, 0, offsetof(Ebml, version), { .u = EBML_VERSION } },
{ EBML_ID_EBMLMAXSIZELENGTH, EBML_UINT, 0, offsetof(Ebml, max_size), { .u = 8 } },
@@ -386,11 +395,12 @@ static const EbmlSyntax ebml_header[] = {
{ EBML_ID_DOCTYPEREADVERSION, EBML_UINT, 0, offsetof(Ebml, doctype_version), { .u = 1 } },
{ EBML_ID_EBMLVERSION, EBML_NONE },
{ EBML_ID_DOCTYPEVERSION, EBML_NONE },
- { 0 }
+ CHILD_OF(ebml_syntax)
};
static const EbmlSyntax ebml_syntax[] = {
- { EBML_ID_HEADER, EBML_NEST, 0, 0, { .n = ebml_header } },
+ { EBML_ID_HEADER, EBML_NEST, 0, 0, { .n = ebml_header } },
+ { MATROSKA_ID_SEGMENT, EBML_STOP },
{ 0 }
};
@@ -402,7 +412,7 @@ static const EbmlSyntax matroska_info[] = {
{ MATROSKA_ID_MUXINGAPP, EBML_UTF8, 0, offsetof(MatroskaDemuxContext, muxingapp) },
{ MATROSKA_ID_DATEUTC, EBML_BIN, 0, offsetof(MatroskaDemuxContext, date_utc) },
{ MATROSKA_ID_SEGMENTUID, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_mastering_meta[] = {
@@ -416,7 +426,7 @@ static const EbmlSyntax matroska_mastering_meta[] = {
{ MATROSKA_ID_VIDEOCOLOR_WHITEY, EBML_FLOAT, 0, offsetof(MatroskaMasteringMeta, white_y), { .f=-1 } },
{ MATROSKA_ID_VIDEOCOLOR_LUMINANCEMIN, EBML_FLOAT, 0, offsetof(MatroskaMasteringMeta, min_luminance), { .f=-1 } },
{ MATROSKA_ID_VIDEOCOLOR_LUMINANCEMAX, EBML_FLOAT, 0, offsetof(MatroskaMasteringMeta, max_luminance), { .f=-1 } },
- { 0 }
+ CHILD_OF(matroska_track_video_color)
};
static const EbmlSyntax matroska_track_video_color[] = {
@@ -434,7 +444,7 @@ static const EbmlSyntax matroska_track_video_color[] = {
{ MATROSKA_ID_VIDEOCOLORMAXCLL, EBML_UINT, 0, offsetof(MatroskaTrackVideoColor, max_cll), { .u=0 } },
{ MATROSKA_ID_VIDEOCOLORMAXFALL, EBML_UINT, 0, offsetof(MatroskaTrackVideoColor, max_fall), { .u=0 } },
{ MATROSKA_ID_VIDEOCOLORMASTERINGMETA, EBML_NEST, 0, offsetof(MatroskaTrackVideoColor, mastering_meta), { .n = matroska_mastering_meta } },
- { 0 }
+ CHILD_OF(matroska_track_video)
};
static const EbmlSyntax matroska_track_video_projection[] = {
@@ -443,7 +453,7 @@ static const EbmlSyntax matroska_track_video_projection[] = {
{ MATROSKA_ID_VIDEOPROJECTIONPOSEYAW, EBML_FLOAT, 0, offsetof(MatroskaTrackVideoProjection, yaw), { .f=0.0 } },
{ MATROSKA_ID_VIDEOPROJECTIONPOSEPITCH, EBML_FLOAT, 0, offsetof(MatroskaTrackVideoProjection, pitch), { .f=0.0 } },
{ MATROSKA_ID_VIDEOPROJECTIONPOSEROLL, EBML_FLOAT, 0, offsetof(MatroskaTrackVideoProjection, roll), { .f=0.0 } },
- { 0 }
+ CHILD_OF(matroska_track_video)
};
static const EbmlSyntax matroska_track_video[] = {
@@ -465,7 +475,7 @@ static const EbmlSyntax matroska_track_video[] = {
{ MATROSKA_ID_VIDEOFIELDORDER, EBML_UINT, 0, offsetof(MatroskaTrackVideo, field_order), { .u = MATROSKA_VIDEO_FIELDORDER_UNDETERMINED } },
{ MATROSKA_ID_VIDEOSTEREOMODE, EBML_UINT, 0, offsetof(MatroskaTrackVideo, stereo_mode), { .u = MATROSKA_VIDEO_STEREOMODE_TYPE_NB } },
{ MATROSKA_ID_VIDEOASPECTRATIO, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_track)
};
static const EbmlSyntax matroska_track_audio[] = {
@@ -473,13 +483,13 @@ static const EbmlSyntax matroska_track_audio[] = {
{ MATROSKA_ID_AUDIOOUTSAMPLINGFREQ, EBML_FLOAT, 0, offsetof(MatroskaTrackAudio, out_samplerate) },
{ MATROSKA_ID_AUDIOBITDEPTH, EBML_UINT, 0, offsetof(MatroskaTrackAudio, bitdepth) },
{ MATROSKA_ID_AUDIOCHANNELS, EBML_UINT, 0, offsetof(MatroskaTrackAudio, channels), { .u = 1 } },
- { 0 }
+ CHILD_OF(matroska_track)
};
static const EbmlSyntax matroska_track_encoding_compression[] = {
{ MATROSKA_ID_ENCODINGCOMPALGO, EBML_UINT, 0, offsetof(MatroskaTrackCompression, algo), { .u = 0 } },
{ MATROSKA_ID_ENCODINGCOMPSETTINGS, EBML_BIN, 0, offsetof(MatroskaTrackCompression, settings) },
- { 0 }
+ CHILD_OF(matroska_track_encoding)
};
static const EbmlSyntax matroska_track_encoding_encryption[] = {
@@ -490,7 +500,7 @@ static const EbmlSyntax matroska_track_encoding_encryption[] = {
{ MATROSKA_ID_ENCODINGSIGHASHALGO, EBML_NONE },
{ MATROSKA_ID_ENCODINGSIGKEYID, EBML_NONE },
{ MATROSKA_ID_ENCODINGSIGNATURE, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_track_encoding)
};
static const EbmlSyntax matroska_track_encoding[] = {
{ MATROSKA_ID_ENCODINGSCOPE, EBML_UINT, 0, offsetof(MatroskaTrackEncoding, scope), { .u = 1 } },
@@ -498,28 +508,28 @@ static const EbmlSyntax matroska_track_encoding[] = {
{ MATROSKA_ID_ENCODINGCOMPRESSION, EBML_NEST, 0, offsetof(MatroskaTrackEncoding, compression), { .n = matroska_track_encoding_compression } },
{ MATROSKA_ID_ENCODINGENCRYPTION, EBML_NEST, 0, offsetof(MatroskaTrackEncoding, encryption), { .n = matroska_track_encoding_encryption } },
{ MATROSKA_ID_ENCODINGORDER, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_track_encodings)
};
static const EbmlSyntax matroska_track_encodings[] = {
{ MATROSKA_ID_TRACKCONTENTENCODING, EBML_NEST, sizeof(MatroskaTrackEncoding), offsetof(MatroskaTrack, encodings), { .n = matroska_track_encoding } },
- { 0 }
+ CHILD_OF(matroska_track)
};
static const EbmlSyntax matroska_track_plane[] = {
{ MATROSKA_ID_TRACKPLANEUID, EBML_UINT, 0, offsetof(MatroskaTrackPlane,uid) },
{ MATROSKA_ID_TRACKPLANETYPE, EBML_UINT, 0, offsetof(MatroskaTrackPlane,type) },
- { 0 }
+ CHILD_OF(matroska_track_combine_planes)
};
static const EbmlSyntax matroska_track_combine_planes[] = {
{ MATROSKA_ID_TRACKPLANE, EBML_NEST, sizeof(MatroskaTrackPlane), offsetof(MatroskaTrackOperation,combine_planes), {.n = matroska_track_plane} },
- { 0 }
+ CHILD_OF(matroska_track_operation)
};
static const EbmlSyntax matroska_track_operation[] = {
{ MATROSKA_ID_TRACKCOMBINEPLANES, EBML_NEST, 0, 0, {.n = matroska_track_combine_planes} },
- { 0 }
+ CHILD_OF(matroska_track)
};
static const EbmlSyntax matroska_track[] = {
@@ -549,12 +559,12 @@ static const EbmlSyntax matroska_track[] = {
{ MATROSKA_ID_CODECDOWNLOADURL, EBML_NONE },
{ MATROSKA_ID_TRACKMINCACHE, EBML_NONE },
{ MATROSKA_ID_TRACKMAXCACHE, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_tracks)
};
static const EbmlSyntax matroska_tracks[] = {
{ MATROSKA_ID_TRACKENTRY, EBML_NEST, sizeof(MatroskaTrack), offsetof(MatroskaDemuxContext, tracks), { .n = matroska_track } },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_attachment[] = {
@@ -563,19 +573,19 @@ static const EbmlSyntax matroska_attachment[] = {
{ MATROSKA_ID_FILEMIMETYPE, EBML_STR, 0, offsetof(MatroskaAttachment, mime) },
{ MATROSKA_ID_FILEDATA, EBML_BIN, 0, offsetof(MatroskaAttachment, bin) },
{ MATROSKA_ID_FILEDESC, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_attachments)
};
static const EbmlSyntax matroska_attachments[] = {
{ MATROSKA_ID_ATTACHEDFILE, EBML_NEST, sizeof(MatroskaAttachment), offsetof(MatroskaDemuxContext, attachments), { .n = matroska_attachment } },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_chapter_display[] = {
{ MATROSKA_ID_CHAPSTRING, EBML_UTF8, 0, offsetof(MatroskaChapter, title) },
{ MATROSKA_ID_CHAPLANG, EBML_NONE },
{ MATROSKA_ID_CHAPCOUNTRY, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_chapter_entry)
};
static const EbmlSyntax matroska_chapter_entry[] = {
@@ -587,7 +597,7 @@ static const EbmlSyntax matroska_chapter_entry[] = {
{ MATROSKA_ID_CHAPTERFLAGENABLED, EBML_NONE },
{ MATROSKA_ID_CHAPTERPHYSEQUIV, EBML_NONE },
{ MATROSKA_ID_CHAPTERATOM, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_chapter)
};
static const EbmlSyntax matroska_chapter[] = {
@@ -596,12 +606,12 @@ static const EbmlSyntax matroska_chapter[] = {
{ MATROSKA_ID_EDITIONFLAGHIDDEN, EBML_NONE },
{ MATROSKA_ID_EDITIONFLAGDEFAULT, EBML_NONE },
{ MATROSKA_ID_EDITIONFLAGORDERED, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_chapters)
};
static const EbmlSyntax matroska_chapters[] = {
{ MATROSKA_ID_EDITIONENTRY, EBML_NEST, 0, 0, { .n = matroska_chapter } },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_index_pos[] = {
@@ -610,18 +620,18 @@ static const EbmlSyntax matroska_index_pos[] = {
{ MATROSKA_ID_CUERELATIVEPOSITION,EBML_NONE },
{ MATROSKA_ID_CUEDURATION, EBML_NONE },
{ MATROSKA_ID_CUEBLOCKNUMBER, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_index_entry)
};
static const EbmlSyntax matroska_index_entry[] = {
{ MATROSKA_ID_CUETIME, EBML_UINT, 0, offsetof(MatroskaIndex, time) },
{ MATROSKA_ID_CUETRACKPOSITION, EBML_NEST, sizeof(MatroskaIndexPos), offsetof(MatroskaIndex, pos), { .n = matroska_index_pos } },
- { 0 }
+ CHILD_OF(matroska_index)
};
static const EbmlSyntax matroska_index[] = {
{ MATROSKA_ID_POINTENTRY, EBML_NEST, sizeof(MatroskaIndex), offsetof(MatroskaDemuxContext, index), { .n = matroska_index_entry } },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_simpletag[] = {
@@ -631,7 +641,7 @@ static const EbmlSyntax matroska_simpletag[] = {
{ MATROSKA_ID_TAGDEFAULT, EBML_UINT, 0, offsetof(MatroskaTag, def) },
{ MATROSKA_ID_TAGDEFAULT_BUG, EBML_UINT, 0, offsetof(MatroskaTag, def) },
{ MATROSKA_ID_SIMPLETAG, EBML_NEST, sizeof(MatroskaTag), offsetof(MatroskaTag, sub), { .n = matroska_simpletag } },
- { 0 }
+ CHILD_OF(matroska_tag)
};
static const EbmlSyntax matroska_tagtargets[] = {
@@ -640,29 +650,29 @@ static const EbmlSyntax matroska_tagtargets[] = {
{ MATROSKA_ID_TAGTARGETS_TRACKUID, EBML_UINT, 0, offsetof(MatroskaTagTarget, trackuid) },
{ MATROSKA_ID_TAGTARGETS_CHAPTERUID, EBML_UINT, 0, offsetof(MatroskaTagTarget, chapteruid) },
{ MATROSKA_ID_TAGTARGETS_ATTACHUID, EBML_UINT, 0, offsetof(MatroskaTagTarget, attachuid) },
- { 0 }
+ CHILD_OF(matroska_tag)
};
static const EbmlSyntax matroska_tag[] = {
{ MATROSKA_ID_SIMPLETAG, EBML_NEST, sizeof(MatroskaTag), offsetof(MatroskaTags, tag), { .n = matroska_simpletag } },
{ MATROSKA_ID_TAGTARGETS, EBML_NEST, 0, offsetof(MatroskaTags, target), { .n = matroska_tagtargets } },
- { 0 }
+ CHILD_OF(matroska_tags)
};
static const EbmlSyntax matroska_tags[] = {
{ MATROSKA_ID_TAG, EBML_NEST, sizeof(MatroskaTags), offsetof(MatroskaDemuxContext, tags), { .n = matroska_tag } },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_seekhead_entry[] = {
{ MATROSKA_ID_SEEKID, EBML_UINT, 0, offsetof(MatroskaSeekhead, id) },
{ MATROSKA_ID_SEEKPOSITION, EBML_UINT, 0, offsetof(MatroskaSeekhead, pos), { .u = -1 } },
- { 0 }
+ CHILD_OF(matroska_seekhead)
};
static const EbmlSyntax matroska_seekhead[] = {
{ MATROSKA_ID_SEEKENTRY, EBML_NEST, sizeof(MatroskaSeekhead), offsetof(MatroskaDemuxContext, seekhead), { .n = matroska_seekhead_entry } },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_segment[] = {
@@ -674,7 +684,7 @@ static const EbmlSyntax matroska_segment[] = {
{ MATROSKA_ID_TAGS, EBML_LEVEL1, 0, 0, { .n = matroska_tags } },
{ MATROSKA_ID_SEEKHEAD, EBML_LEVEL1, 0, 0, { .n = matroska_seekhead } },
{ MATROSKA_ID_CLUSTER, EBML_STOP },
- { 0 }
+ { 0 } /* We don't want to go back to level 0, so don't add the parent. */
};
static const EbmlSyntax matroska_segments[] = {
@@ -685,12 +695,12 @@ static const EbmlSyntax matroska_segments[] = {
static const EbmlSyntax matroska_blockmore[] = {
{ MATROSKA_ID_BLOCKADDID, EBML_UINT, 0, offsetof(MatroskaBlock,additional_id) },
{ MATROSKA_ID_BLOCKADDITIONAL, EBML_BIN, 0, offsetof(MatroskaBlock,additional) },
- { 0 }
+ CHILD_OF(matroska_blockadditions)
};
static const EbmlSyntax matroska_blockadditions[] = {
{ MATROSKA_ID_BLOCKMORE, EBML_NEST, 0, 0, {.n = matroska_blockmore} },
- { 0 }
+ CHILD_OF(matroska_blockgroup)
};
static const EbmlSyntax matroska_blockgroup[] = {
@@ -701,7 +711,7 @@ static const EbmlSyntax matroska_blockgroup[] = {
{ MATROSKA_ID_BLOCKREFERENCE, EBML_SINT, 0, offsetof(MatroskaBlock, reference), { .i = INT64_MIN } },
{ MATROSKA_ID_CODECSTATE, EBML_NONE },
{ 1, EBML_UINT, 0, offsetof(MatroskaBlock, non_simple), { .u = 1 } },
- { 0 }
+ CHILD_OF(matroska_cluster_parsing)
};
static const EbmlSyntax matroska_cluster_parsing[] = {
@@ -715,7 +725,7 @@ static const EbmlSyntax matroska_cluster_parsing[] = {
{ MATROSKA_ID_TAGS, EBML_NONE },
{ MATROSKA_ID_SEEKHEAD, EBML_NONE },
{ MATROSKA_ID_CLUSTER, EBML_STOP },
- { 0 }
+ { 0 } /* We don't want to go back to level 0, so don't add the parent. */
};
static const EbmlSyntax matroska_cluster[] = {
@@ -724,7 +734,7 @@ static const EbmlSyntax matroska_cluster[] = {
{ MATROSKA_ID_SIMPLEBLOCK, EBML_STOP },
{ MATROSKA_ID_CLUSTERPOSITION, EBML_NONE },
{ MATROSKA_ID_CLUSTERPREVSIZE, EBML_NONE },
- { 0 }
+ CHILD_OF(matroska_segment)
};
static const EbmlSyntax matroska_clusters[] = {
@@ -733,8 +743,9 @@ static const EbmlSyntax matroska_clusters[] = {
{ MATROSKA_ID_CUES, EBML_NONE },
{ MATROSKA_ID_TAGS, EBML_NONE },
{ MATROSKA_ID_SEEKHEAD, EBML_NONE },
- { 0 }
+ { 0 } /* We don't want to go back to level 0, so don't add the parent. */
};
+#undef CHILD_OF
static const char *const matroska_doctypes[] = { "matroska", "webm" };