]> git.sesse.net Git - ffmpeg/blob - libavformat/mov.c
avformat/mov: set AVFMT_SEEK_TO_PTS flag
[ffmpeg] / libavformat / mov.c
1 /*
2  * MOV demuxer
3  * Copyright (c) 2001 Fabrice Bellard
4  * Copyright (c) 2009 Baptiste Coudurier <baptiste dot coudurier at gmail dot com>
5  *
6  * first version by Francois Revol <revol@free.fr>
7  * seek function by Gael Chardon <gael.dev@4now.net>
8  *
9  * This file is part of FFmpeg.
10  *
11  * FFmpeg is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU Lesser General Public
13  * License as published by the Free Software Foundation; either
14  * version 2.1 of the License, or (at your option) any later version.
15  *
16  * FFmpeg is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
19  * Lesser General Public License for more details.
20  *
21  * You should have received a copy of the GNU Lesser General Public
22  * License along with FFmpeg; if not, write to the Free Software
23  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
24  */
25
26 #include <inttypes.h>
27 #include <limits.h>
28 #include <stdint.h>
29
30 #include "libavutil/attributes.h"
31 #include "libavutil/channel_layout.h"
32 #include "libavutil/internal.h"
33 #include "libavutil/intreadwrite.h"
34 #include "libavutil/intfloat.h"
35 #include "libavutil/mathematics.h"
36 #include "libavutil/time_internal.h"
37 #include "libavutil/avassert.h"
38 #include "libavutil/avstring.h"
39 #include "libavutil/dict.h"
40 #include "libavutil/display.h"
41 #include "libavutil/opt.h"
42 #include "libavutil/aes.h"
43 #include "libavutil/aes_ctr.h"
44 #include "libavutil/pixdesc.h"
45 #include "libavutil/sha.h"
46 #include "libavutil/spherical.h"
47 #include "libavutil/stereo3d.h"
48 #include "libavutil/timecode.h"
49 #include "libavcodec/ac3tab.h"
50 #include "libavcodec/flac.h"
51 #include "libavcodec/mpegaudiodecheader.h"
52 #include "avformat.h"
53 #include "internal.h"
54 #include "avio_internal.h"
55 #include "riff.h"
56 #include "isom.h"
57 #include "libavcodec/get_bits.h"
58 #include "id3v1.h"
59 #include "mov_chan.h"
60 #include "replaygain.h"
61
62 #if CONFIG_ZLIB
63 #include <zlib.h>
64 #endif
65
66 #include "qtpalette.h"
67
68 /* those functions parse an atom */
69 /* links atom IDs to parse functions */
70 typedef struct MOVParseTableEntry {
71     uint32_t type;
72     int (*parse)(MOVContext *ctx, AVIOContext *pb, MOVAtom atom);
73 } MOVParseTableEntry;
74
75 static int mov_read_default(MOVContext *c, AVIOContext *pb, MOVAtom atom);
76 static int mov_read_mfra(MOVContext *c, AVIOContext *f);
77 static int64_t add_ctts_entry(MOVStts** ctts_data, unsigned int* ctts_count, unsigned int* allocated_size,
78                               int count, int duration);
79
80 static int mov_metadata_track_or_disc_number(MOVContext *c, AVIOContext *pb,
81                                              unsigned len, const char *key)
82 {
83     char buf[16];
84
85     short current, total = 0;
86     avio_rb16(pb); // unknown
87     current = avio_rb16(pb);
88     if (len >= 6)
89         total = avio_rb16(pb);
90     if (!total)
91         snprintf(buf, sizeof(buf), "%d", current);
92     else
93         snprintf(buf, sizeof(buf), "%d/%d", current, total);
94     c->fc->event_flags |= AVFMT_EVENT_FLAG_METADATA_UPDATED;
95     av_dict_set(&c->fc->metadata, key, buf, 0);
96
97     return 0;
98 }
99
100 static int mov_metadata_int8_bypass_padding(MOVContext *c, AVIOContext *pb,
101                                             unsigned len, const char *key)
102 {
103     /* bypass padding bytes */
104     avio_r8(pb);
105     avio_r8(pb);
106     avio_r8(pb);
107
108     c->fc->event_flags |= AVFMT_EVENT_FLAG_METADATA_UPDATED;
109     av_dict_set_int(&c->fc->metadata, key, avio_r8(pb), 0);
110
111     return 0;
112 }
113
114 static int mov_metadata_int8_no_padding(MOVContext *c, AVIOContext *pb,
115                                         unsigned len, const char *key)
116 {
117     c->fc->event_flags |= AVFMT_EVENT_FLAG_METADATA_UPDATED;
118     av_dict_set_int(&c->fc->metadata, key, avio_r8(pb), 0);
119
120     return 0;
121 }
122
123 static int mov_metadata_gnre(MOVContext *c, AVIOContext *pb,
124                              unsigned len, const char *key)
125 {
126     short genre;
127
128     avio_r8(pb); // unknown
129
130     genre = avio_r8(pb);
131     if (genre < 1 || genre > ID3v1_GENRE_MAX)
132         return 0;
133     c->fc->event_flags |= AVFMT_EVENT_FLAG_METADATA_UPDATED;
134     av_dict_set(&c->fc->metadata, key, ff_id3v1_genre_str[genre-1], 0);
135
136     return 0;
137 }
138
139 static const uint32_t mac_to_unicode[128] = {
140     0x00C4,0x00C5,0x00C7,0x00C9,0x00D1,0x00D6,0x00DC,0x00E1,
141     0x00E0,0x00E2,0x00E4,0x00E3,0x00E5,0x00E7,0x00E9,0x00E8,
142     0x00EA,0x00EB,0x00ED,0x00EC,0x00EE,0x00EF,0x00F1,0x00F3,
143     0x00F2,0x00F4,0x00F6,0x00F5,0x00FA,0x00F9,0x00FB,0x00FC,
144     0x2020,0x00B0,0x00A2,0x00A3,0x00A7,0x2022,0x00B6,0x00DF,
145     0x00AE,0x00A9,0x2122,0x00B4,0x00A8,0x2260,0x00C6,0x00D8,
146     0x221E,0x00B1,0x2264,0x2265,0x00A5,0x00B5,0x2202,0x2211,
147     0x220F,0x03C0,0x222B,0x00AA,0x00BA,0x03A9,0x00E6,0x00F8,
148     0x00BF,0x00A1,0x00AC,0x221A,0x0192,0x2248,0x2206,0x00AB,
149     0x00BB,0x2026,0x00A0,0x00C0,0x00C3,0x00D5,0x0152,0x0153,
150     0x2013,0x2014,0x201C,0x201D,0x2018,0x2019,0x00F7,0x25CA,
151     0x00FF,0x0178,0x2044,0x20AC,0x2039,0x203A,0xFB01,0xFB02,
152     0x2021,0x00B7,0x201A,0x201E,0x2030,0x00C2,0x00CA,0x00C1,
153     0x00CB,0x00C8,0x00CD,0x00CE,0x00CF,0x00CC,0x00D3,0x00D4,
154     0xF8FF,0x00D2,0x00DA,0x00DB,0x00D9,0x0131,0x02C6,0x02DC,
155     0x00AF,0x02D8,0x02D9,0x02DA,0x00B8,0x02DD,0x02DB,0x02C7,
156 };
157
158 static int mov_read_mac_string(MOVContext *c, AVIOContext *pb, int len,
159                                char *dst, int dstlen)
160 {
161     char *p = dst;
162     char *end = dst+dstlen-1;
163     int i;
164
165     for (i = 0; i < len; i++) {
166         uint8_t t, c = avio_r8(pb);
167
168         if (p >= end)
169             continue;
170
171         if (c < 0x80)
172             *p++ = c;
173         else if (p < end)
174             PUT_UTF8(mac_to_unicode[c-0x80], t, if (p < end) *p++ = t;);
175     }
176     *p = 0;
177     return p - dst;
178 }
179
180 static int mov_read_covr(MOVContext *c, AVIOContext *pb, int type, int len)
181 {
182     AVPacket pkt;
183     AVStream *st;
184     MOVStreamContext *sc;
185     enum AVCodecID id;
186     int ret;
187
188     switch (type) {
189     case 0xd:  id = AV_CODEC_ID_MJPEG; break;
190     case 0xe:  id = AV_CODEC_ID_PNG;   break;
191     case 0x1b: id = AV_CODEC_ID_BMP;   break;
192     default:
193         av_log(c->fc, AV_LOG_WARNING, "Unknown cover type: 0x%x.\n", type);
194         avio_skip(pb, len);
195         return 0;
196     }
197
198     st = avformat_new_stream(c->fc, NULL);
199     if (!st)
200         return AVERROR(ENOMEM);
201     sc = av_mallocz(sizeof(*sc));
202     if (!sc)
203         return AVERROR(ENOMEM);
204     st->priv_data = sc;
205
206     ret = av_get_packet(pb, &pkt, len);
207     if (ret < 0)
208         return ret;
209
210     if (pkt.size >= 8 && id != AV_CODEC_ID_BMP) {
211         if (AV_RB64(pkt.data) == 0x89504e470d0a1a0a) {
212             id = AV_CODEC_ID_PNG;
213         } else {
214             id = AV_CODEC_ID_MJPEG;
215         }
216     }
217
218     st->disposition              |= AV_DISPOSITION_ATTACHED_PIC;
219
220     st->attached_pic              = pkt;
221     st->attached_pic.stream_index = st->index;
222     st->attached_pic.flags       |= AV_PKT_FLAG_KEY;
223
224     st->codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
225     st->codecpar->codec_id   = id;
226
227     return 0;
228 }
229
230 // 3GPP TS 26.244
231 static int mov_metadata_loci(MOVContext *c, AVIOContext *pb, unsigned len)
232 {
233     char language[4] = { 0 };
234     char buf[200], place[100];
235     uint16_t langcode = 0;
236     double longitude, latitude, altitude;
237     const char *key = "location";
238
239     if (len < 4 + 2 + 1 + 1 + 4 + 4 + 4) {
240         av_log(c->fc, AV_LOG_ERROR, "loci too short\n");
241         return AVERROR_INVALIDDATA;
242     }
243
244     avio_skip(pb, 4); // version+flags
245     langcode = avio_rb16(pb);
246     ff_mov_lang_to_iso639(langcode, language);
247     len -= 6;
248
249     len -= avio_get_str(pb, len, place, sizeof(place));
250     if (len < 1) {
251         av_log(c->fc, AV_LOG_ERROR, "place name too long\n");
252         return AVERROR_INVALIDDATA;
253     }
254     avio_skip(pb, 1); // role
255     len -= 1;
256
257     if (len < 12) {
258         av_log(c->fc, AV_LOG_ERROR,
259                "loci too short (%u bytes left, need at least %d)\n", len, 12);
260         return AVERROR_INVALIDDATA;
261     }
262     longitude = ((int32_t) avio_rb32(pb)) / (float) (1 << 16);
263     latitude  = ((int32_t) avio_rb32(pb)) / (float) (1 << 16);
264     altitude  = ((int32_t) avio_rb32(pb)) / (float) (1 << 16);
265
266     // Try to output in the same format as the ?xyz field
267     snprintf(buf, sizeof(buf), "%+08.4f%+09.4f",  latitude, longitude);
268     if (altitude)
269         av_strlcatf(buf, sizeof(buf), "%+f", altitude);
270     av_strlcatf(buf, sizeof(buf), "/%s", place);
271
272     if (*language && strcmp(language, "und")) {
273         char key2[16];
274         snprintf(key2, sizeof(key2), "%s-%s", key, language);
275         av_dict_set(&c->fc->metadata, key2, buf, 0);
276     }
277     c->fc->event_flags |= AVFMT_EVENT_FLAG_METADATA_UPDATED;
278     return av_dict_set(&c->fc->metadata, key, buf, 0);
279 }
280
281 static int mov_metadata_hmmt(MOVContext *c, AVIOContext *pb, unsigned len)
282 {
283     int i, n_hmmt;
284
285     if (len < 2)
286         return 0;
287     if (c->ignore_chapters)
288         return 0;
289
290     n_hmmt = avio_rb32(pb);
291     for (i = 0; i < n_hmmt && !pb->eof_reached; i++) {
292         int moment_time = avio_rb32(pb);
293         avpriv_new_chapter(c->fc, i, av_make_q(1, 1000), moment_time, AV_NOPTS_VALUE, NULL);
294     }
295     return 0;
296 }
297
298 static int mov_read_udta_string(MOVContext *c, AVIOContext *pb, MOVAtom atom)
299 {
300     char tmp_key[5];
301     char key2[32], language[4] = {0};
302     char *str = NULL;
303     const char *key = NULL;
304     uint16_t langcode = 0;
305     uint32_t data_type = 0, str_size, str_size_alloc;
306     int (*parse)(MOVContext*, AVIOContext*, unsigned, const char*) = NULL;
307     int raw = 0;
308     int num = 0;
309
310     switch (atom.type) {
311     case MKTAG( '@','P','R','M'): key = "premiere_version"; raw = 1; break;
312     case MKTAG( '@','P','R','Q'): key = "quicktime_version"; raw = 1; break;
313     case MKTAG( 'X','M','P','_'):
314         if (c->export_xmp) { key = "xmp"; raw = 1; } break;
315     case MKTAG( 'a','A','R','T'): key = "album_artist";    break;
316     case MKTAG( 'a','k','I','D'): key = "account_type";
317         parse = mov_metadata_int8_no_padding; break;
318     case MKTAG( 'a','p','I','D'): key = "account_id"; break;
319     case MKTAG( 'c','a','t','g'): key = "category"; break;
320     case MKTAG( 'c','p','i','l'): key = "compilation";
321         parse = mov_metadata_int8_no_padding; break;
322     case MKTAG( 'c','p','r','t'): key = "copyright"; break;
323     case MKTAG( 'd','e','s','c'): key = "description"; break;
324     case MKTAG( 'd','i','s','k'): key = "disc";
325         parse = mov_metadata_track_or_disc_number; break;
326     case MKTAG( 'e','g','i','d'): key = "episode_uid";
327         parse = mov_metadata_int8_no_padding; break;
328     case MKTAG( 'F','I','R','M'): key = "firmware"; raw = 1; break;
329     case MKTAG( 'g','n','r','e'): key = "genre";
330         parse = mov_metadata_gnre; break;
331     case MKTAG( 'h','d','v','d'): key = "hd_video";
332         parse = mov_metadata_int8_no_padding; break;
333     case MKTAG( 'H','M','M','T'):
334         return mov_metadata_hmmt(c, pb, atom.size);
335     case MKTAG( 'k','e','y','w'): key = "keywords";  break;
336     case MKTAG( 'l','d','e','s'): key = "synopsis";  break;
337     case MKTAG( 'l','o','c','i'):
338         return mov_metadata_loci(c, pb, atom.size);
339     case MKTAG( 'm','a','n','u'): key = "make"; break;
340     case MKTAG( 'm','o','d','l'): key = "model"; break;
341     case MKTAG( 'p','c','s','t'): key = "podcast";
342         parse = mov_metadata_int8_no_padding; break;
343     case MKTAG( 'p','g','a','p'): key = "gapless_playback";
344         parse = mov_metadata_int8_no_padding; break;
345     case MKTAG( 'p','u','r','d'): key = "purchase_date"; break;
346     case MKTAG( 'r','t','n','g'): key = "rating";
347         parse = mov_metadata_int8_no_padding; break;
348     case MKTAG( 's','o','a','a'): key = "sort_album_artist"; break;
349     case MKTAG( 's','o','a','l'): key = "sort_album";   break;
350     case MKTAG( 's','o','a','r'): key = "sort_artist";  break;
351     case MKTAG( 's','o','c','o'): key = "sort_composer"; break;
352     case MKTAG( 's','o','n','m'): key = "sort_name";    break;
353     case MKTAG( 's','o','s','n'): key = "sort_show";    break;
354     case MKTAG( 's','t','i','k'): key = "media_type";
355         parse = mov_metadata_int8_no_padding; break;
356     case MKTAG( 't','r','k','n'): key = "track";
357         parse = mov_metadata_track_or_disc_number; break;
358     case MKTAG( 't','v','e','n'): key = "episode_id"; break;
359     case MKTAG( 't','v','e','s'): key = "episode_sort";
360         parse = mov_metadata_int8_bypass_padding; break;
361     case MKTAG( 't','v','n','n'): key = "network";   break;
362     case MKTAG( 't','v','s','h'): key = "show";      break;
363     case MKTAG( 't','v','s','n'): key = "season_number";
364         parse = mov_metadata_int8_bypass_padding; break;
365     case MKTAG(0xa9,'A','R','T'): key = "artist";    break;
366     case MKTAG(0xa9,'P','R','D'): key = "producer";  break;
367     case MKTAG(0xa9,'a','l','b'): key = "album";     break;
368     case MKTAG(0xa9,'a','u','t'): key = "artist";    break;
369     case MKTAG(0xa9,'c','h','p'): key = "chapter";   break;
370     case MKTAG(0xa9,'c','m','t'): key = "comment";   break;
371     case MKTAG(0xa9,'c','o','m'): key = "composer";  break;
372     case MKTAG(0xa9,'c','p','y'): key = "copyright"; break;
373     case MKTAG(0xa9,'d','a','y'): key = "date";      break;
374     case MKTAG(0xa9,'d','i','r'): key = "director";  break;
375     case MKTAG(0xa9,'d','i','s'): key = "disclaimer"; break;
376     case MKTAG(0xa9,'e','d','1'): key = "edit_date"; break;
377     case MKTAG(0xa9,'e','n','c'): key = "encoder";   break;
378     case MKTAG(0xa9,'f','m','t'): key = "original_format"; break;
379     case MKTAG(0xa9,'g','e','n'): key = "genre";     break;
380     case MKTAG(0xa9,'g','r','p'): key = "grouping";  break;
381     case MKTAG(0xa9,'h','s','t'): key = "host_computer"; break;
382     case MKTAG(0xa9,'i','n','f'): key = "comment";   break;
383     case MKTAG(0xa9,'l','y','r'): key = "lyrics";    break;
384     case MKTAG(0xa9,'m','a','k'): key = "make";      break;
385     case MKTAG(0xa9,'m','o','d'): key = "model";     break;
386     case MKTAG(0xa9,'n','a','m'): key = "title";     break;
387     case MKTAG(0xa9,'o','p','e'): key = "original_artist"; break;
388     case MKTAG(0xa9,'p','r','d'): key = "producer";  break;
389     case MKTAG(0xa9,'p','r','f'): key = "performers"; break;
390     case MKTAG(0xa9,'r','e','q'): key = "playback_requirements"; break;
391     case MKTAG(0xa9,'s','r','c'): key = "original_source"; break;
392     case MKTAG(0xa9,'s','t','3'): key = "subtitle";  break;
393     case MKTAG(0xa9,'s','w','r'): key = "encoder";   break;
394     case MKTAG(0xa9,'t','o','o'): key = "encoder";   break;
395     case MKTAG(0xa9,'t','r','k'): key = "track";     break;
396     case MKTAG(0xa9,'u','r','l'): key = "URL";       break;
397     case MKTAG(0xa9,'w','r','n'): key = "warning";   break;
398     case MKTAG(0xa9,'w','r','t'): key = "composer";  break;
399     case MKTAG(0xa9,'x','y','z'): key = "location";  break;
400     }
401 retry:
402     if (c->itunes_metadata && atom.size > 8) {
403         int data_size = avio_rb32(pb);
404         int tag = avio_rl32(pb);
405         if (tag == MKTAG('d','a','t','a') && data_size <= atom.size) {
406             data_type = avio_rb32(pb); // type
407             avio_rb32(pb); // unknown
408             str_size = data_size - 16;
409             atom.size -= 16;
410
411             if (atom.type == MKTAG('c', 'o', 'v', 'r')) {
412                 int ret = mov_read_covr(c, pb, data_type, str_size);
413                 if (ret < 0) {
414                     av_log(c->fc, AV_LOG_ERROR, "Error parsing cover art.\n");
415                     return ret;
416                 }
417                 atom.size -= str_size;
418                 if (atom.size > 8)
419                     goto retry;
420                 return ret;
421             } else if (!key && c->found_hdlr_mdta && c->meta_keys) {
422                 uint32_t index = AV_RB32(&atom.type);
423                 if (index < c->meta_keys_count && index > 0) {
424                     key = c->meta_keys[index];
425                 } else {
426                     av_log(c->fc, AV_LOG_WARNING,
427                            "The index of 'data' is out of range: %"PRId32" < 1 or >= %d.\n",
428                            index, c->meta_keys_count);
429                 }
430             }
431         } else return 0;
432     } else if (atom.size > 4 && key && !c->itunes_metadata && !raw) {
433         str_size = avio_rb16(pb); // string length
434         if (str_size > atom.size) {
435             raw = 1;
436             avio_seek(pb, -2, SEEK_CUR);
437             av_log(c->fc, AV_LOG_WARNING, "UDTA parsing failed retrying raw\n");
438             goto retry;
439         }
440         langcode = avio_rb16(pb);
441         ff_mov_lang_to_iso639(langcode, language);
442         atom.size -= 4;
443     } else
444         str_size = atom.size;
445
446     if (c->export_all && !key) {
447         snprintf(tmp_key, 5, "%.4s", (char*)&atom.type);
448         key = tmp_key;
449     }
450
451     if (!key)
452         return 0;
453     if (atom.size < 0 || str_size >= INT_MAX/2)
454         return AVERROR_INVALIDDATA;
455
456     // Allocates enough space if data_type is a int32 or float32 number, otherwise
457     // worst-case requirement for output string in case of utf8 coded input
458     num = (data_type >= 21 && data_type <= 23);
459     str_size_alloc = (num ? 512 : (raw ? str_size : str_size * 2)) + 1;
460     str = av_mallocz(str_size_alloc);
461     if (!str)
462         return AVERROR(ENOMEM);
463
464     if (parse)
465         parse(c, pb, str_size, key);
466     else {
467         if (!raw && (data_type == 3 || (data_type == 0 && (langcode < 0x400 || langcode == 0x7fff)))) { // MAC Encoded
468             mov_read_mac_string(c, pb, str_size, str, str_size_alloc);
469         } else if (data_type == 21) { // BE signed integer, variable size
470             int val = 0;
471             if (str_size == 1)
472                 val = (int8_t)avio_r8(pb);
473             else if (str_size == 2)
474                 val = (int16_t)avio_rb16(pb);
475             else if (str_size == 3)
476                 val = ((int32_t)(avio_rb24(pb)<<8))>>8;
477             else if (str_size == 4)
478                 val = (int32_t)avio_rb32(pb);
479             if (snprintf(str, str_size_alloc, "%d", val) >= str_size_alloc) {
480                 av_log(c->fc, AV_LOG_ERROR,
481                        "Failed to store the number (%d) in string.\n", val);
482                 av_free(str);
483                 return AVERROR_INVALIDDATA;
484             }
485         } else if (data_type == 22) { // BE unsigned integer, variable size
486             unsigned int val = 0;
487             if (str_size == 1)
488                 val = avio_r8(pb);
489             else if (str_size == 2)
490                 val = avio_rb16(pb);
491             else if (str_size == 3)
492                 val = avio_rb24(pb);
493             else if (str_size == 4)
494                 val = avio_rb32(pb);
495             if (snprintf(str, str_size_alloc, "%u", val) >= str_size_alloc) {
496                 av_log(c->fc, AV_LOG_ERROR,
497                        "Failed to store the number (%u) in string.\n", val);
498                 av_free(str);
499                 return AVERROR_INVALIDDATA;
500             }
501         } else if (data_type == 23 && str_size >= 4) {  // BE float32
502             float val = av_int2float(avio_rb32(pb));
503             if (snprintf(str, str_size_alloc, "%f", val) >= str_size_alloc) {
504                 av_log(c->fc, AV_LOG_ERROR,
505                        "Failed to store the float32 number (%f) in string.\n", val);
506                 av_free(str);
507                 return AVERROR_INVALIDDATA;
508             }
509         } else {
510             int ret = ffio_read_size(pb, str, str_size);
511             if (ret < 0) {
512                 av_free(str);
513                 return ret;
514             }
515             str[str_size] = 0;
516         }
517         c->fc->event_flags |= AVFMT_EVENT_FLAG_METADATA_UPDATED;
518         av_dict_set(&c->fc->metadata, key, str, 0);
519         if (*language && strcmp(language, "und")) {
520             snprintf(key2, sizeof(key2), "%s-%s", key, language);
521             av_dict_set(&c->fc->metadata, key2, str, 0);
522         }
523         if (!strcmp(key, "encoder")) {
524             int major, minor, micro;
525             if (sscanf(str, "HandBrake %d.%d.%d", &major, &minor, &micro) == 3) {
526                 c->handbrake_version = 1000000*major + 1000*minor + micro;
527             }
528         }
529     }
530
531     av_freep(&str);
532     return 0;
533 }
534
535 static int mov_read_chpl(MOVContext *c, AVIOContext *pb, MOVAtom atom)
536 {
537     int64_t start;
538     int i, nb_chapters, str_len, version;
539     char str[256+1];
540     int ret;
541
542     if (c->ignore_chapters)
543         return 0;
544
545     if ((atom.size -= 5) < 0)
546         return 0;
547
548     version = avio_r8(pb);
549     avio_rb24(pb);
550     if (version)
551         avio_rb32(pb); // ???
552     nb_chapters = avio_r8(pb);
553
554     for (i = 0; i < nb_chapters; i++) {
555         if (atom.size < 9)
556             return 0;
557
558         start = avio_rb64(pb);
559         str_len = avio_r8(pb);
560
561         if ((atom.size -= 9+str_len) < 0)
562             return 0;
563
564         ret = ffio_read_size(pb, str, str_len);
565         if (ret < 0)
566             return ret;
567         str[str_len] = 0;
568         avpriv_new_chapter(c->fc, i, (AVRational){1,10000000}, start, AV_NOPTS_VALUE, str);
569     }
570     return 0;
571 }
572
573 #define MIN_DATA_ENTRY_BOX_SIZE 12
574 static int mov_read_dref(MOVContext *c, AVIOContext *pb, MOVAtom atom)
575 {
576     AVStream *st;
577     MOVStreamContext *sc;
578     int entries, i, j;
579
580     if (c->fc->nb_streams < 1)
581         return 0;
582     st = c->fc->streams[c->fc->nb_streams-1];
583     sc = st->priv_data;
584
585     avio_rb32(pb); // version + flags
586     entries = avio_rb32(pb);
587     if (!entries ||
588         entries >  (atom.size - 1) / MIN_DATA_ENTRY_BOX_SIZE + 1 ||
589         entries >= UINT_MAX / sizeof(*sc->drefs))
590         return AVERROR_INVALIDDATA;
591     sc->drefs_count = 0;
592     av_free(sc->drefs);
593     sc->drefs_count = 0;
594     sc->drefs = av_mallocz(entries * sizeof(*sc->drefs));
595     if (!sc->drefs)
596         return AVERROR(ENOMEM);
597     sc->drefs_count = entries;
598
599     for (i = 0; i < entries; i++) {
600         MOVDref *dref = &sc->drefs[i];
601         uint32_t size = avio_rb32(pb);
602         int64_t next = avio_tell(pb) + size - 4;
603
604         if (size < 12)
605             return AVERROR_INVALIDDATA;
606
607         dref->type = avio_rl32(pb);
608         avio_rb32(pb); // version + flags
609
610         if (dref->type == MKTAG('a','l','i','s') && size > 150) {
611             /* macintosh alias record */
612             uint16_t volume_len, len;
613             int16_t type;
614             int ret;
615
616             avio_skip(pb, 10);
617
618             volume_len = avio_r8(pb);
619             volume_len = FFMIN(volume_len, 27);
620             ret = ffio_read_size(pb, dref->volume, 27);
621             if (ret < 0)
622                 return ret;
623             dref->volume[volume_len] = 0;
624             av_log(c->fc, AV_LOG_DEBUG, "volume %s, len %d\n", dref->volume, volume_len);
625
626             avio_skip(pb, 12);
627
628             len = avio_r8(pb);
629             len = FFMIN(len, 63);
630             ret = ffio_read_size(pb, dref->filename, 63);
631             if (ret < 0)
632                 return ret;
633             dref->filename[len] = 0;
634             av_log(c->fc, AV_LOG_DEBUG, "filename %s, len %d\n", dref->filename, len);
635
636             avio_skip(pb, 16);
637
638             /* read next level up_from_alias/down_to_target */
639             dref->nlvl_from = avio_rb16(pb);
640             dref->nlvl_to   = avio_rb16(pb);
641             av_log(c->fc, AV_LOG_DEBUG, "nlvl from %d, nlvl to %d\n",
642                    dref->nlvl_from, dref->nlvl_to);
643
644             avio_skip(pb, 16);
645
646             for (type = 0; type != -1 && avio_tell(pb) < next; ) {
647                 if(avio_feof(pb))
648                     return AVERROR_EOF;
649                 type = avio_rb16(pb);
650                 len = avio_rb16(pb);
651                 av_log(c->fc, AV_LOG_DEBUG, "type %d, len %d\n", type, len);
652                 if (len&1)
653                     len += 1;
654                 if (type == 2) { // absolute path
655                     av_free(dref->path);
656                     dref->path = av_mallocz(len+1);
657                     if (!dref->path)
658                         return AVERROR(ENOMEM);
659
660                     ret = ffio_read_size(pb, dref->path, len);
661                     if (ret < 0) {
662                         av_freep(&dref->path);
663                         return ret;
664                     }
665                     if (len > volume_len && !strncmp(dref->path, dref->volume, volume_len)) {
666                         len -= volume_len;
667                         memmove(dref->path, dref->path+volume_len, len);
668                         dref->path[len] = 0;
669                     }
670                     // trim string of any ending zeros
671                     for (j = len - 1; j >= 0; j--) {
672                         if (dref->path[j] == 0)
673                             len--;
674                         else
675                             break;
676                     }
677                     for (j = 0; j < len; j++)
678                         if (dref->path[j] == ':' || dref->path[j] == 0)
679                             dref->path[j] = '/';
680                     av_log(c->fc, AV_LOG_DEBUG, "path %s\n", dref->path);
681                 } else if (type == 0) { // directory name
682                     av_free(dref->dir);
683                     dref->dir = av_malloc(len+1);
684                     if (!dref->dir)
685                         return AVERROR(ENOMEM);
686
687                     ret = ffio_read_size(pb, dref->dir, len);
688                     if (ret < 0) {
689                         av_freep(&dref->dir);
690                         return ret;
691                     }
692                     dref->dir[len] = 0;
693                     for (j = 0; j < len; j++)
694                         if (dref->dir[j] == ':')
695                             dref->dir[j] = '/';
696                     av_log(c->fc, AV_LOG_DEBUG, "dir %s\n", dref->dir);
697                 } else
698                     avio_skip(pb, len);
699             }
700         } else {
701             av_log(c->fc, AV_LOG_DEBUG, "Unknown dref type 0x%08"PRIx32" size %"PRIu32"\n",
702                    dref->type, size);
703             entries--;
704             i--;
705         }
706         avio_seek(pb, next, SEEK_SET);
707     }
708     return 0;
709 }
710
711 static int mov_read_hdlr(MOVContext *c, AVIOContext *pb, MOVAtom atom)
712 {
713     AVStream *st;
714     uint32_t type;
715     uint32_t ctype;
716     int64_t title_size;
717     char *title_str;
718     int ret;
719
720     avio_r8(pb); /* version */
721     avio_rb24(pb); /* flags */
722
723     /* component type */
724     ctype = avio_rl32(pb);
725     type = avio_rl32(pb); /* component subtype */
726
727     av_log(c->fc, AV_LOG_TRACE, "ctype=%s\n", av_fourcc2str(ctype));
728     av_log(c->fc, AV_LOG_TRACE, "stype=%s\n", av_fourcc2str(type));
729
730     if (c->trak_index < 0) {  // meta not inside a trak
731         if (type == MKTAG('m','d','t','a')) {
732             c->found_hdlr_mdta = 1;
733         }
734         return 0;
735     }
736
737     st = c->fc->streams[c->fc->nb_streams-1];
738
739     if     (type == MKTAG('v','i','d','e'))
740         st->codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
741     else if (type == MKTAG('s','o','u','n'))
742         st->codecpar->codec_type = AVMEDIA_TYPE_AUDIO;
743     else if (type == MKTAG('m','1','a',' '))
744         st->codecpar->codec_id = AV_CODEC_ID_MP2;
745     else if ((type == MKTAG('s','u','b','p')) || (type == MKTAG('c','l','c','p')))
746         st->codecpar->codec_type = AVMEDIA_TYPE_SUBTITLE;
747
748     avio_rb32(pb); /* component  manufacture */
749     avio_rb32(pb); /* component flags */
750     avio_rb32(pb); /* component flags mask */
751
752     title_size = atom.size - 24;
753     if (title_size > 0) {
754         if (title_size > FFMIN(INT_MAX, SIZE_MAX-1))
755             return AVERROR_INVALIDDATA;
756         title_str = av_malloc(title_size + 1); /* Add null terminator */
757         if (!title_str)
758             return AVERROR(ENOMEM);
759
760         ret = ffio_read_size(pb, title_str, title_size);
761         if (ret < 0) {
762             av_freep(&title_str);
763             return ret;
764         }
765         title_str[title_size] = 0;
766         if (title_str[0]) {
767             int off = (!c->isom && title_str[0] == title_size - 1);
768             // flag added so as to not set stream handler name if already set from mdia->hdlr
769             av_dict_set(&st->metadata, "handler_name", title_str + off, AV_DICT_DONT_OVERWRITE);
770         }
771         av_freep(&title_str);
772     }
773
774     return 0;
775 }
776
777 static int mov_read_esds(MOVContext *c, AVIOContext *pb, MOVAtom atom)
778 {
779     return ff_mov_read_esds(c->fc, pb);
780 }
781
782 static int mov_read_dac3(MOVContext *c, AVIOContext *pb, MOVAtom atom)
783 {
784     AVStream *st;
785     enum AVAudioServiceType *ast;
786     int ac3info, acmod, lfeon, bsmod;
787
788     if (c->fc->nb_streams < 1)
789         return 0;
790     st = c->fc->streams[c->fc->nb_streams-1];
791
792     ast = (enum AVAudioServiceType*)av_stream_new_side_data(st, AV_PKT_DATA_AUDIO_SERVICE_TYPE,
793                                                             sizeof(*ast));
794     if (!ast)
795         return AVERROR(ENOMEM);
796
797     ac3info = avio_rb24(pb);
798     bsmod = (ac3info >> 14) & 0x7;
799     acmod = (ac3info >> 11) & 0x7;
800     lfeon = (ac3info >> 10) & 0x1;
801     st->codecpar->channels = ((int[]){2,1,2,3,3,4,4,5})[acmod] + lfeon;
802     st->codecpar->channel_layout = avpriv_ac3_channel_layout_tab[acmod];
803     if (lfeon)
804         st->codecpar->channel_layout |= AV_CH_LOW_FREQUENCY;
805     *ast = bsmod;
806     if (st->codecpar->channels > 1 && bsmod == 0x7)
807         *ast = AV_AUDIO_SERVICE_TYPE_KARAOKE;
808
809 #if FF_API_LAVF_AVCTX
810     FF_DISABLE_DEPRECATION_WARNINGS
811     st->codec->audio_service_type = *ast;
812     FF_ENABLE_DEPRECATION_WARNINGS
813 #endif
814
815     return 0;
816 }
817
818 static int mov_read_dec3(MOVContext *c, AVIOContext *pb, MOVAtom atom)
819 {
820     AVStream *st;
821     enum AVAudioServiceType *ast;
822     int eac3info, acmod, lfeon, bsmod;
823
824     if (c->fc->nb_streams < 1)
825         return 0;
826     st = c->fc->streams[c->fc->nb_streams-1];
827
828     ast = (enum AVAudioServiceType*)av_stream_new_side_data(st, AV_PKT_DATA_AUDIO_SERVICE_TYPE,
829                                                             sizeof(*ast));
830     if (!ast)
831         return AVERROR(ENOMEM);
832
833     /* No need to parse fields for additional independent substreams and its
834      * associated dependent substreams since libavcodec's E-AC-3 decoder
835      * does not support them yet. */
836     avio_rb16(pb); /* data_rate and num_ind_sub */
837     eac3info = avio_rb24(pb);
838     bsmod = (eac3info >> 12) & 0x1f;
839     acmod = (eac3info >>  9) & 0x7;
840     lfeon = (eac3info >>  8) & 0x1;
841     st->codecpar->channel_layout = avpriv_ac3_channel_layout_tab[acmod];
842     if (lfeon)
843         st->codecpar->channel_layout |= AV_CH_LOW_FREQUENCY;
844     st->codecpar->channels = av_get_channel_layout_nb_channels(st->codecpar->channel_layout);
845     *ast = bsmod;
846     if (st->codecpar->channels > 1 && bsmod == 0x7)
847         *ast = AV_AUDIO_SERVICE_TYPE_KARAOKE;
848
849 #if FF_API_LAVF_AVCTX
850     FF_DISABLE_DEPRECATION_WARNINGS
851     st->codec->audio_service_type = *ast;
852     FF_ENABLE_DEPRECATION_WARNINGS
853 #endif
854
855     return 0;
856 }
857
858 static int mov_read_ddts(MOVContext *c, AVIOContext *pb, MOVAtom atom)
859 {
860     const uint32_t ddts_size = 20;
861     AVStream *st = NULL;
862     uint8_t *buf = NULL;
863     uint32_t frame_duration_code = 0;
864     uint32_t channel_layout_code = 0;
865     GetBitContext gb;
866
867     buf = av_malloc(ddts_size + AV_INPUT_BUFFER_PADDING_SIZE);
868     if (!buf) {
869         return AVERROR(ENOMEM);
870     }
871     if (avio_read(pb, buf, ddts_size) < ddts_size) {
872         av_free(buf);
873         return AVERROR_INVALIDDATA;
874     }
875
876     init_get_bits(&gb, buf, 8*ddts_size);
877
878     if (c->fc->nb_streams < 1) {
879         av_free(buf);
880         return 0;
881     }
882     st = c->fc->streams[c->fc->nb_streams-1];
883
884     st->codecpar->sample_rate = get_bits_long(&gb, 32);
885     if (st->codecpar->sample_rate <= 0) {
886         av_log(c->fc, AV_LOG_ERROR, "Invalid sample rate %d\n", st->codecpar->sample_rate);
887         av_free(buf);
888         return AVERROR_INVALIDDATA;
889     }
890     skip_bits_long(&gb, 32); /* max bitrate */
891     st->codecpar->bit_rate = get_bits_long(&gb, 32);
892     st->codecpar->bits_per_coded_sample = get_bits(&gb, 8);
893     frame_duration_code = get_bits(&gb, 2);
894     skip_bits(&gb, 30); /* various fields */
895     channel_layout_code = get_bits(&gb, 16);
896
897     st->codecpar->frame_size =
898             (frame_duration_code == 0) ? 512 :
899             (frame_duration_code == 1) ? 1024 :
900             (frame_duration_code == 2) ? 2048 :
901             (frame_duration_code == 3) ? 4096 : 0;
902
903     if (channel_layout_code > 0xff) {
904         av_log(c->fc, AV_LOG_WARNING, "Unsupported DTS audio channel layout");
905     }
906     st->codecpar->channel_layout =
907             ((channel_layout_code & 0x1) ? AV_CH_FRONT_CENTER : 0) |
908             ((channel_layout_code & 0x2) ? AV_CH_FRONT_LEFT : 0) |
909             ((channel_layout_code & 0x2) ? AV_CH_FRONT_RIGHT : 0) |
910             ((channel_layout_code & 0x4) ? AV_CH_SIDE_LEFT : 0) |
911             ((channel_layout_code & 0x4) ? AV_CH_SIDE_RIGHT : 0) |
912             ((channel_layout_code & 0x8) ? AV_CH_LOW_FREQUENCY : 0);
913
914     st->codecpar->channels = av_get_channel_layout_nb_channels(st->codecpar->channel_layout);
915     av_free(buf);
916
917     return 0;
918 }
919
920 static int mov_read_chan(MOVContext *c, AVIOContext *pb, MOVAtom atom)
921 {
922     AVStream *st;
923
924     if (c->fc->nb_streams < 1)
925         return 0;
926     st = c->fc->streams[c->fc->nb_streams-1];
927
928     if (atom.size < 16)
929         return 0;
930
931     /* skip version and flags */
932     avio_skip(pb, 4);
933
934     ff_mov_read_chan(c->fc, pb, st, atom.size - 4);
935
936     return 0;
937 }
938
939 static int mov_read_wfex(MOVContext *c, AVIOContext *pb, MOVAtom atom)
940 {
941     AVStream *st;
942     int ret;
943
944     if (c->fc->nb_streams < 1)
945         return 0;
946     st = c->fc->streams[c->fc->nb_streams-1];
947
948     if ((ret = ff_get_wav_header(c->fc, pb, st->codecpar, atom.size, 0)) < 0)
949         av_log(c->fc, AV_LOG_WARNING, "get_wav_header failed\n");
950
951     return ret;
952 }
953
954 static int mov_read_pasp(MOVContext *c, AVIOContext *pb, MOVAtom atom)
955 {
956     const int num = avio_rb32(pb);
957     const int den = avio_rb32(pb);
958     AVStream *st;
959
960     if (c->fc->nb_streams < 1)
961         return 0;
962     st = c->fc->streams[c->fc->nb_streams-1];
963
964     if ((st->sample_aspect_ratio.den != 1 || st->sample_aspect_ratio.num) && // default
965         (den != st->sample_aspect_ratio.den || num != st->sample_aspect_ratio.num)) {
966         av_log(c->fc, AV_LOG_WARNING,
967                "sample aspect ratio already set to %d:%d, ignoring 'pasp' atom (%d:%d)\n",
968                st->sample_aspect_ratio.num, st->sample_aspect_ratio.den,
969                num, den);
970     } else if (den != 0) {
971         av_reduce(&st->sample_aspect_ratio.num, &st->sample_aspect_ratio.den,
972                   num, den, 32767);
973     }
974     return 0;
975 }
976
977 /* this atom contains actual media data */
978 static int mov_read_mdat(MOVContext *c, AVIOContext *pb, MOVAtom atom)
979 {
980     if (atom.size == 0) /* wrong one (MP4) */
981         return 0;
982     c->found_mdat=1;
983     return 0; /* now go for moov */
984 }
985
986 #define DRM_BLOB_SIZE 56
987
988 static int mov_read_adrm(MOVContext *c, AVIOContext *pb, MOVAtom atom)
989 {
990     uint8_t intermediate_key[20];
991     uint8_t intermediate_iv[20];
992     uint8_t input[64];
993     uint8_t output[64];
994     uint8_t file_checksum[20];
995     uint8_t calculated_checksum[20];
996     struct AVSHA *sha;
997     int i;
998     int ret = 0;
999     uint8_t *activation_bytes = c->activation_bytes;
1000     uint8_t *fixed_key = c->audible_fixed_key;
1001
1002     c->aax_mode = 1;
1003
1004     sha = av_sha_alloc();
1005     if (!sha)
1006         return AVERROR(ENOMEM);
1007     c->aes_decrypt = av_aes_alloc();
1008     if (!c->aes_decrypt) {
1009         ret = AVERROR(ENOMEM);
1010         goto fail;
1011     }
1012
1013     /* drm blob processing */
1014     avio_read(pb, output, 8); // go to offset 8, absolute position 0x251
1015     avio_read(pb, input, DRM_BLOB_SIZE);
1016     avio_read(pb, output, 4); // go to offset 4, absolute position 0x28d
1017     avio_read(pb, file_checksum, 20);
1018
1019     av_log(c->fc, AV_LOG_INFO, "[aax] file checksum == "); // required by external tools
1020     for (i = 0; i < 20; i++)
1021         av_log(c->fc, AV_LOG_INFO, "%02x", file_checksum[i]);
1022     av_log(c->fc, AV_LOG_INFO, "\n");
1023
1024     /* verify activation data */
1025     if (!activation_bytes) {
1026         av_log(c->fc, AV_LOG_WARNING, "[aax] activation_bytes option is missing!\n");
1027         ret = 0;  /* allow ffprobe to continue working on .aax files */
1028         goto fail;
1029     }
1030     if (c->activation_bytes_size != 4) {
1031         av_log(c->fc, AV_LOG_FATAL, "[aax] activation_bytes value needs to be 4 bytes!\n");
1032         ret = AVERROR(EINVAL);
1033         goto fail;
1034     }
1035
1036     /* verify fixed key */
1037     if (c->audible_fixed_key_size != 16) {
1038         av_log(c->fc, AV_LOG_FATAL, "[aax] audible_fixed_key value needs to be 16 bytes!\n");
1039         ret = AVERROR(EINVAL);
1040         goto fail;
1041     }
1042
1043     /* AAX (and AAX+) key derivation */
1044     av_sha_init(sha, 160);
1045     av_sha_update(sha, fixed_key, 16);
1046     av_sha_update(sha, activation_bytes, 4);
1047     av_sha_final(sha, intermediate_key);
1048     av_sha_init(sha, 160);
1049     av_sha_update(sha, fixed_key, 16);
1050     av_sha_update(sha, intermediate_key, 20);
1051     av_sha_update(sha, activation_bytes, 4);
1052     av_sha_final(sha, intermediate_iv);
1053     av_sha_init(sha, 160);
1054     av_sha_update(sha, intermediate_key, 16);
1055     av_sha_update(sha, intermediate_iv, 16);
1056     av_sha_final(sha, calculated_checksum);
1057     if (memcmp(calculated_checksum, file_checksum, 20)) { // critical error
1058         av_log(c->fc, AV_LOG_ERROR, "[aax] mismatch in checksums!\n");
1059         ret = AVERROR_INVALIDDATA;
1060         goto fail;
1061     }
1062     av_aes_init(c->aes_decrypt, intermediate_key, 128, 1);
1063     av_aes_crypt(c->aes_decrypt, output, input, DRM_BLOB_SIZE >> 4, intermediate_iv, 1);
1064     for (i = 0; i < 4; i++) {
1065         // file data (in output) is stored in big-endian mode
1066         if (activation_bytes[i] != output[3 - i]) { // critical error
1067             av_log(c->fc, AV_LOG_ERROR, "[aax] error in drm blob decryption!\n");
1068             ret = AVERROR_INVALIDDATA;
1069             goto fail;
1070         }
1071     }
1072     memcpy(c->file_key, output + 8, 16);
1073     memcpy(input, output + 26, 16);
1074     av_sha_init(sha, 160);
1075     av_sha_update(sha, input, 16);
1076     av_sha_update(sha, c->file_key, 16);
1077     av_sha_update(sha, fixed_key, 16);
1078     av_sha_final(sha, c->file_iv);
1079
1080 fail:
1081     av_free(sha);
1082
1083     return ret;
1084 }
1085
1086 // Audible AAX (and AAX+) bytestream decryption
1087 static int aax_filter(uint8_t *input, int size, MOVContext *c)
1088 {
1089     int blocks = 0;
1090     unsigned char iv[16];
1091
1092     memcpy(iv, c->file_iv, 16); // iv is overwritten
1093     blocks = size >> 4; // trailing bytes are not encrypted!
1094     av_aes_init(c->aes_decrypt, c->file_key, 128, 1);
1095     av_aes_crypt(c->aes_decrypt, input, input, blocks, iv, 1);
1096
1097     return 0;
1098 }
1099
1100 /* read major brand, minor version and compatible brands and store them as metadata */
1101 static int mov_read_ftyp(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1102 {
1103     uint32_t minor_ver;
1104     int comp_brand_size;
1105     char* comp_brands_str;
1106     uint8_t type[5] = {0};
1107     int ret = ffio_read_size(pb, type, 4);
1108     if (ret < 0)
1109         return ret;
1110
1111     if (strcmp(type, "qt  "))
1112         c->isom = 1;
1113     av_log(c->fc, AV_LOG_DEBUG, "ISO: File Type Major Brand: %.4s\n",(char *)&type);
1114     av_dict_set(&c->fc->metadata, "major_brand", type, 0);
1115     minor_ver = avio_rb32(pb); /* minor version */
1116     av_dict_set_int(&c->fc->metadata, "minor_version", minor_ver, 0);
1117
1118     comp_brand_size = atom.size - 8;
1119     if (comp_brand_size < 0)
1120         return AVERROR_INVALIDDATA;
1121     comp_brands_str = av_malloc(comp_brand_size + 1); /* Add null terminator */
1122     if (!comp_brands_str)
1123         return AVERROR(ENOMEM);
1124
1125     ret = ffio_read_size(pb, comp_brands_str, comp_brand_size);
1126     if (ret < 0) {
1127         av_freep(&comp_brands_str);
1128         return ret;
1129     }
1130     comp_brands_str[comp_brand_size] = 0;
1131     av_dict_set(&c->fc->metadata, "compatible_brands", comp_brands_str, 0);
1132     av_freep(&comp_brands_str);
1133
1134     return 0;
1135 }
1136
1137 /* this atom should contain all header atoms */
1138 static int mov_read_moov(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1139 {
1140     int ret;
1141
1142     if (c->found_moov) {
1143         av_log(c->fc, AV_LOG_WARNING, "Found duplicated MOOV Atom. Skipped it\n");
1144         avio_skip(pb, atom.size);
1145         return 0;
1146     }
1147
1148     if ((ret = mov_read_default(c, pb, atom)) < 0)
1149         return ret;
1150     /* we parsed the 'moov' atom, we can terminate the parsing as soon as we find the 'mdat' */
1151     /* so we don't parse the whole file if over a network */
1152     c->found_moov=1;
1153     return 0; /* now go for mdat */
1154 }
1155
1156 static MOVFragmentStreamInfo * get_frag_stream_info(
1157     MOVFragmentIndex *frag_index,
1158     int index,
1159     int id)
1160 {
1161     int i;
1162     MOVFragmentIndexItem * item;
1163
1164     if (index < 0 || index >= frag_index->nb_items)
1165         return NULL;
1166     item = &frag_index->item[index];
1167     for (i = 0; i < item->nb_stream_info; i++)
1168         if (item->stream_info[i].id == id)
1169             return &item->stream_info[i];
1170
1171     // This shouldn't happen
1172     return NULL;
1173 }
1174
1175 static void set_frag_stream(MOVFragmentIndex *frag_index, int id)
1176 {
1177     int i;
1178     MOVFragmentIndexItem * item;
1179
1180     if (frag_index->current < 0 ||
1181         frag_index->current >= frag_index->nb_items)
1182         return;
1183
1184     item = &frag_index->item[frag_index->current];
1185     for (i = 0; i < item->nb_stream_info; i++)
1186         if (item->stream_info[i].id == id) {
1187             item->current = i;
1188             return;
1189         }
1190
1191     // id not found.  This shouldn't happen.
1192     item->current = -1;
1193 }
1194
1195 static MOVFragmentStreamInfo * get_current_frag_stream_info(
1196     MOVFragmentIndex *frag_index)
1197 {
1198     MOVFragmentIndexItem *item;
1199     if (frag_index->current < 0 ||
1200         frag_index->current >= frag_index->nb_items)
1201         return NULL;
1202
1203     item = &frag_index->item[frag_index->current];
1204     if (item->current >= 0 && item->current < item->nb_stream_info)
1205         return &item->stream_info[item->current];
1206
1207     // This shouldn't happen
1208     return NULL;
1209 }
1210
1211 static int search_frag_moof_offset(MOVFragmentIndex *frag_index, int64_t offset)
1212 {
1213     int a, b, m;
1214     int64_t moof_offset;
1215
1216     // Optimize for appending new entries
1217     if (!frag_index->nb_items ||
1218         frag_index->item[frag_index->nb_items - 1].moof_offset < offset)
1219         return frag_index->nb_items;
1220
1221     a = -1;
1222     b = frag_index->nb_items;
1223
1224     while (b - a > 1) {
1225         m = (a + b) >> 1;
1226         moof_offset = frag_index->item[m].moof_offset;
1227         if (moof_offset >= offset)
1228             b = m;
1229         if (moof_offset <= offset)
1230             a = m;
1231     }
1232     return b;
1233 }
1234
1235 static int64_t get_stream_info_time(MOVFragmentStreamInfo * frag_stream_info)
1236 {
1237     av_assert0(frag_stream_info);
1238     if (frag_stream_info->sidx_pts != AV_NOPTS_VALUE)
1239         return frag_stream_info->sidx_pts;
1240     if (frag_stream_info->first_tfra_pts != AV_NOPTS_VALUE)
1241         return frag_stream_info->first_tfra_pts;
1242     return frag_stream_info->tfdt_dts;
1243 }
1244
1245 static int64_t get_frag_time(MOVFragmentIndex *frag_index,
1246                              int index, int track_id)
1247 {
1248     MOVFragmentStreamInfo * frag_stream_info;
1249     int64_t timestamp;
1250     int i;
1251
1252     if (track_id >= 0) {
1253         frag_stream_info = get_frag_stream_info(frag_index, index, track_id);
1254         return frag_stream_info->sidx_pts;
1255     }
1256
1257     for (i = 0; i < frag_index->item[index].nb_stream_info; i++) {
1258         frag_stream_info = &frag_index->item[index].stream_info[i];
1259         timestamp = get_stream_info_time(frag_stream_info);
1260         if (timestamp != AV_NOPTS_VALUE)
1261             return timestamp;
1262     }
1263     return AV_NOPTS_VALUE;
1264 }
1265
1266 static int search_frag_timestamp(MOVFragmentIndex *frag_index,
1267                                  AVStream *st, int64_t timestamp)
1268 {
1269     int a, b, m, m0;
1270     int64_t frag_time;
1271     int id = -1;
1272
1273     if (st) {
1274         // If the stream is referenced by any sidx, limit the search
1275         // to fragments that referenced this stream in the sidx
1276         MOVStreamContext *sc = st->priv_data;
1277         if (sc->has_sidx)
1278             id = st->id;
1279     }
1280
1281     a = -1;
1282     b = frag_index->nb_items;
1283
1284     while (b - a > 1) {
1285         m0 = m = (a + b) >> 1;
1286
1287         while (m < b &&
1288                (frag_time = get_frag_time(frag_index, m, id)) == AV_NOPTS_VALUE)
1289             m++;
1290
1291         if (m < b && frag_time <= timestamp)
1292             a = m;
1293         else
1294             b = m0;
1295     }
1296
1297     return a;
1298 }
1299
1300 static int update_frag_index(MOVContext *c, int64_t offset)
1301 {
1302     int index, i;
1303     MOVFragmentIndexItem * item;
1304     MOVFragmentStreamInfo * frag_stream_info;
1305
1306     // If moof_offset already exists in frag_index, return index to it
1307     index = search_frag_moof_offset(&c->frag_index, offset);
1308     if (index < c->frag_index.nb_items &&
1309         c->frag_index.item[index].moof_offset == offset)
1310         return index;
1311
1312     // offset is not yet in frag index.
1313     // Insert new item at index (sorted by moof offset)
1314     item = av_fast_realloc(c->frag_index.item,
1315                            &c->frag_index.allocated_size,
1316                            (c->frag_index.nb_items + 1) *
1317                            sizeof(*c->frag_index.item));
1318     if(!item)
1319         return -1;
1320     c->frag_index.item = item;
1321
1322     frag_stream_info = av_realloc_array(NULL, c->fc->nb_streams,
1323                                         sizeof(*item->stream_info));
1324     if (!frag_stream_info)
1325         return -1;
1326
1327     for (i = 0; i < c->fc->nb_streams; i++) {
1328         // Avoid building frag index if streams lack track id.
1329         if (c->fc->streams[i]->id < 0)
1330             return AVERROR_INVALIDDATA;
1331
1332         frag_stream_info[i].id = c->fc->streams[i]->id;
1333         frag_stream_info[i].sidx_pts = AV_NOPTS_VALUE;
1334         frag_stream_info[i].tfdt_dts = AV_NOPTS_VALUE;
1335         frag_stream_info[i].first_tfra_pts = AV_NOPTS_VALUE;
1336         frag_stream_info[i].index_entry = -1;
1337         frag_stream_info[i].encryption_index = NULL;
1338     }
1339
1340     if (index < c->frag_index.nb_items)
1341         memmove(c->frag_index.item + index + 1, c->frag_index.item + index,
1342                 (c->frag_index.nb_items - index) * sizeof(*c->frag_index.item));
1343
1344     item = &c->frag_index.item[index];
1345     item->headers_read = 0;
1346     item->current = 0;
1347     item->nb_stream_info = c->fc->nb_streams;
1348     item->moof_offset = offset;
1349     item->stream_info = frag_stream_info;
1350     c->frag_index.nb_items++;
1351
1352     return index;
1353 }
1354
1355 static void fix_frag_index_entries(MOVFragmentIndex *frag_index, int index,
1356                                    int id, int entries)
1357 {
1358     int i;
1359     MOVFragmentStreamInfo * frag_stream_info;
1360
1361     if (index < 0)
1362         return;
1363     for (i = index; i < frag_index->nb_items; i++) {
1364         frag_stream_info = get_frag_stream_info(frag_index, i, id);
1365         if (frag_stream_info && frag_stream_info->index_entry >= 0)
1366             frag_stream_info->index_entry += entries;
1367     }
1368 }
1369
1370 static int mov_read_moof(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1371 {
1372     // Set by mov_read_tfhd(). mov_read_trun() will reject files missing tfhd.
1373     c->fragment.found_tfhd = 0;
1374
1375     if (!c->has_looked_for_mfra && c->use_mfra_for > 0) {
1376         c->has_looked_for_mfra = 1;
1377         if (pb->seekable & AVIO_SEEKABLE_NORMAL) {
1378             int ret;
1379             av_log(c->fc, AV_LOG_VERBOSE, "stream has moof boxes, will look "
1380                     "for a mfra\n");
1381             if ((ret = mov_read_mfra(c, pb)) < 0) {
1382                 av_log(c->fc, AV_LOG_VERBOSE, "found a moof box but failed to "
1383                         "read the mfra (may be a live ismv)\n");
1384             }
1385         } else {
1386             av_log(c->fc, AV_LOG_VERBOSE, "found a moof box but stream is not "
1387                     "seekable, can not look for mfra\n");
1388         }
1389     }
1390     c->fragment.moof_offset = c->fragment.implicit_offset = avio_tell(pb) - 8;
1391     av_log(c->fc, AV_LOG_TRACE, "moof offset %"PRIx64"\n", c->fragment.moof_offset);
1392     c->frag_index.current = update_frag_index(c, c->fragment.moof_offset);
1393     return mov_read_default(c, pb, atom);
1394 }
1395
1396 static void mov_metadata_creation_time(AVDictionary **metadata, int64_t time)
1397 {
1398     if (time) {
1399         if(time >= 2082844800)
1400             time -= 2082844800;  /* seconds between 1904-01-01 and Epoch */
1401
1402         if ((int64_t)(time * 1000000ULL) / 1000000 != time) {
1403             av_log(NULL, AV_LOG_DEBUG, "creation_time is not representable\n");
1404             return;
1405         }
1406
1407         avpriv_dict_set_timestamp(metadata, "creation_time", time * 1000000);
1408     }
1409 }
1410
1411 static int mov_read_mdhd(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1412 {
1413     AVStream *st;
1414     MOVStreamContext *sc;
1415     int version;
1416     char language[4] = {0};
1417     unsigned lang;
1418     int64_t creation_time;
1419
1420     if (c->fc->nb_streams < 1)
1421         return 0;
1422     st = c->fc->streams[c->fc->nb_streams-1];
1423     sc = st->priv_data;
1424
1425     if (sc->time_scale) {
1426         av_log(c->fc, AV_LOG_ERROR, "Multiple mdhd?\n");
1427         return AVERROR_INVALIDDATA;
1428     }
1429
1430     version = avio_r8(pb);
1431     if (version > 1) {
1432         avpriv_request_sample(c->fc, "Version %d", version);
1433         return AVERROR_PATCHWELCOME;
1434     }
1435     avio_rb24(pb); /* flags */
1436     if (version == 1) {
1437         creation_time = avio_rb64(pb);
1438         avio_rb64(pb);
1439     } else {
1440         creation_time = avio_rb32(pb);
1441         avio_rb32(pb); /* modification time */
1442     }
1443     mov_metadata_creation_time(&st->metadata, creation_time);
1444
1445     sc->time_scale = avio_rb32(pb);
1446     if (sc->time_scale <= 0) {
1447         av_log(c->fc, AV_LOG_ERROR, "Invalid mdhd time scale %d, defaulting to 1\n", sc->time_scale);
1448         sc->time_scale = 1;
1449     }
1450     st->duration = (version == 1) ? avio_rb64(pb) : avio_rb32(pb); /* duration */
1451
1452     lang = avio_rb16(pb); /* language */
1453     if (ff_mov_lang_to_iso639(lang, language))
1454         av_dict_set(&st->metadata, "language", language, 0);
1455     avio_rb16(pb); /* quality */
1456
1457     return 0;
1458 }
1459
1460 static int mov_read_mvhd(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1461 {
1462     int i;
1463     int64_t creation_time;
1464     int version = avio_r8(pb); /* version */
1465     avio_rb24(pb); /* flags */
1466
1467     if (version == 1) {
1468         creation_time = avio_rb64(pb);
1469         avio_rb64(pb);
1470     } else {
1471         creation_time = avio_rb32(pb);
1472         avio_rb32(pb); /* modification time */
1473     }
1474     mov_metadata_creation_time(&c->fc->metadata, creation_time);
1475     c->time_scale = avio_rb32(pb); /* time scale */
1476     if (c->time_scale <= 0) {
1477         av_log(c->fc, AV_LOG_ERROR, "Invalid mvhd time scale %d, defaulting to 1\n", c->time_scale);
1478         c->time_scale = 1;
1479     }
1480     av_log(c->fc, AV_LOG_TRACE, "time scale = %i\n", c->time_scale);
1481
1482     c->duration = (version == 1) ? avio_rb64(pb) : avio_rb32(pb); /* duration */
1483     // set the AVCodecContext duration because the duration of individual tracks
1484     // may be inaccurate
1485     if (c->time_scale > 0 && !c->trex_data)
1486         c->fc->duration = av_rescale(c->duration, AV_TIME_BASE, c->time_scale);
1487     avio_rb32(pb); /* preferred scale */
1488
1489     avio_rb16(pb); /* preferred volume */
1490
1491     avio_skip(pb, 10); /* reserved */
1492
1493     /* movie display matrix, store it in main context and use it later on */
1494     for (i = 0; i < 3; i++) {
1495         c->movie_display_matrix[i][0] = avio_rb32(pb); // 16.16 fixed point
1496         c->movie_display_matrix[i][1] = avio_rb32(pb); // 16.16 fixed point
1497         c->movie_display_matrix[i][2] = avio_rb32(pb); //  2.30 fixed point
1498     }
1499
1500     avio_rb32(pb); /* preview time */
1501     avio_rb32(pb); /* preview duration */
1502     avio_rb32(pb); /* poster time */
1503     avio_rb32(pb); /* selection time */
1504     avio_rb32(pb); /* selection duration */
1505     avio_rb32(pb); /* current time */
1506     avio_rb32(pb); /* next track ID */
1507
1508     return 0;
1509 }
1510
1511 static int mov_read_enda(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1512 {
1513     AVStream *st;
1514     int little_endian;
1515
1516     if (c->fc->nb_streams < 1)
1517         return 0;
1518     st = c->fc->streams[c->fc->nb_streams-1];
1519
1520     little_endian = avio_rb16(pb) & 0xFF;
1521     av_log(c->fc, AV_LOG_TRACE, "enda %d\n", little_endian);
1522     if (little_endian == 1) {
1523         switch (st->codecpar->codec_id) {
1524         case AV_CODEC_ID_PCM_S24BE:
1525             st->codecpar->codec_id = AV_CODEC_ID_PCM_S24LE;
1526             break;
1527         case AV_CODEC_ID_PCM_S32BE:
1528             st->codecpar->codec_id = AV_CODEC_ID_PCM_S32LE;
1529             break;
1530         case AV_CODEC_ID_PCM_F32BE:
1531             st->codecpar->codec_id = AV_CODEC_ID_PCM_F32LE;
1532             break;
1533         case AV_CODEC_ID_PCM_F64BE:
1534             st->codecpar->codec_id = AV_CODEC_ID_PCM_F64LE;
1535             break;
1536         default:
1537             break;
1538         }
1539     }
1540     return 0;
1541 }
1542
1543 static int mov_read_colr(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1544 {
1545     AVStream *st;
1546     char color_parameter_type[5] = { 0 };
1547     uint16_t color_primaries, color_trc, color_matrix;
1548     int ret;
1549
1550     if (c->fc->nb_streams < 1)
1551         return 0;
1552     st = c->fc->streams[c->fc->nb_streams - 1];
1553
1554     ret = ffio_read_size(pb, color_parameter_type, 4);
1555     if (ret < 0)
1556         return ret;
1557     if (strncmp(color_parameter_type, "nclx", 4) &&
1558         strncmp(color_parameter_type, "nclc", 4)) {
1559         av_log(c->fc, AV_LOG_WARNING, "unsupported color_parameter_type %s\n",
1560                color_parameter_type);
1561         return 0;
1562     }
1563
1564     color_primaries = avio_rb16(pb);
1565     color_trc = avio_rb16(pb);
1566     color_matrix = avio_rb16(pb);
1567
1568     av_log(c->fc, AV_LOG_TRACE,
1569            "%s: pri %d trc %d matrix %d",
1570            color_parameter_type, color_primaries, color_trc, color_matrix);
1571
1572     if (!strncmp(color_parameter_type, "nclx", 4)) {
1573         uint8_t color_range = avio_r8(pb) >> 7;
1574         av_log(c->fc, AV_LOG_TRACE, " full %"PRIu8"", color_range);
1575         if (color_range)
1576             st->codecpar->color_range = AVCOL_RANGE_JPEG;
1577         else
1578             st->codecpar->color_range = AVCOL_RANGE_MPEG;
1579     }
1580
1581     if (!av_color_primaries_name(color_primaries))
1582         color_primaries = AVCOL_PRI_UNSPECIFIED;
1583     if (!av_color_transfer_name(color_trc))
1584         color_trc = AVCOL_TRC_UNSPECIFIED;
1585     if (!av_color_space_name(color_matrix))
1586         color_matrix = AVCOL_SPC_UNSPECIFIED;
1587
1588     st->codecpar->color_primaries = color_primaries;
1589     st->codecpar->color_trc       = color_trc;
1590     st->codecpar->color_space     = color_matrix;
1591     av_log(c->fc, AV_LOG_TRACE, "\n");
1592
1593     return 0;
1594 }
1595
1596 static int mov_read_fiel(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1597 {
1598     AVStream *st;
1599     unsigned mov_field_order;
1600     enum AVFieldOrder decoded_field_order = AV_FIELD_UNKNOWN;
1601
1602     if (c->fc->nb_streams < 1) // will happen with jp2 files
1603         return 0;
1604     st = c->fc->streams[c->fc->nb_streams-1];
1605     if (atom.size < 2)
1606         return AVERROR_INVALIDDATA;
1607     mov_field_order = avio_rb16(pb);
1608     if ((mov_field_order & 0xFF00) == 0x0100)
1609         decoded_field_order = AV_FIELD_PROGRESSIVE;
1610     else if ((mov_field_order & 0xFF00) == 0x0200) {
1611         switch (mov_field_order & 0xFF) {
1612         case 0x01: decoded_field_order = AV_FIELD_TT;
1613                    break;
1614         case 0x06: decoded_field_order = AV_FIELD_BB;
1615                    break;
1616         case 0x09: decoded_field_order = AV_FIELD_TB;
1617                    break;
1618         case 0x0E: decoded_field_order = AV_FIELD_BT;
1619                    break;
1620         }
1621     }
1622     if (decoded_field_order == AV_FIELD_UNKNOWN && mov_field_order) {
1623         av_log(NULL, AV_LOG_ERROR, "Unknown MOV field order 0x%04x\n", mov_field_order);
1624     }
1625     st->codecpar->field_order = decoded_field_order;
1626
1627     return 0;
1628 }
1629
1630 static int mov_realloc_extradata(AVCodecParameters *par, MOVAtom atom)
1631 {
1632     int err = 0;
1633     uint64_t size = (uint64_t)par->extradata_size + atom.size + 8 + AV_INPUT_BUFFER_PADDING_SIZE;
1634     if (size > INT_MAX || (uint64_t)atom.size > INT_MAX)
1635         return AVERROR_INVALIDDATA;
1636     if ((err = av_reallocp(&par->extradata, size)) < 0) {
1637         par->extradata_size = 0;
1638         return err;
1639     }
1640     par->extradata_size = size - AV_INPUT_BUFFER_PADDING_SIZE;
1641     return 0;
1642 }
1643
1644 /* Read a whole atom into the extradata return the size of the atom read, possibly truncated if != atom.size */
1645 static int64_t mov_read_atom_into_extradata(MOVContext *c, AVIOContext *pb, MOVAtom atom,
1646                                         AVCodecParameters *par, uint8_t *buf)
1647 {
1648     int64_t result = atom.size;
1649     int err;
1650
1651     AV_WB32(buf    , atom.size + 8);
1652     AV_WL32(buf + 4, atom.type);
1653     err = ffio_read_size(pb, buf + 8, atom.size);
1654     if (err < 0) {
1655         par->extradata_size -= atom.size;
1656         return err;
1657     } else if (err < atom.size) {
1658         av_log(c->fc, AV_LOG_WARNING, "truncated extradata\n");
1659         par->extradata_size -= atom.size - err;
1660         result = err;
1661     }
1662     memset(buf + 8 + err, 0, AV_INPUT_BUFFER_PADDING_SIZE);
1663     return result;
1664 }
1665
1666 /* FIXME modify QDM2/SVQ3/H.264 decoders to take full atom as extradata */
1667 static int mov_read_extradata(MOVContext *c, AVIOContext *pb, MOVAtom atom,
1668                               enum AVCodecID codec_id)
1669 {
1670     AVStream *st;
1671     uint64_t original_size;
1672     int err;
1673
1674     if (c->fc->nb_streams < 1) // will happen with jp2 files
1675         return 0;
1676     st = c->fc->streams[c->fc->nb_streams-1];
1677
1678     if (st->codecpar->codec_id != codec_id)
1679         return 0; /* unexpected codec_id - don't mess with extradata */
1680
1681     original_size = st->codecpar->extradata_size;
1682     err = mov_realloc_extradata(st->codecpar, atom);
1683     if (err)
1684         return err;
1685
1686     err =  mov_read_atom_into_extradata(c, pb, atom, st->codecpar,  st->codecpar->extradata + original_size);
1687     if (err < 0)
1688         return err;
1689     return 0; // Note: this is the original behavior to ignore truncation.
1690 }
1691
1692 /* wrapper functions for reading ALAC/AVS/MJPEG/MJPEG2000 extradata atoms only for those codecs */
1693 static int mov_read_alac(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1694 {
1695     return mov_read_extradata(c, pb, atom, AV_CODEC_ID_ALAC);
1696 }
1697
1698 static int mov_read_avss(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1699 {
1700     return mov_read_extradata(c, pb, atom, AV_CODEC_ID_AVS);
1701 }
1702
1703 static int mov_read_jp2h(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1704 {
1705     return mov_read_extradata(c, pb, atom, AV_CODEC_ID_JPEG2000);
1706 }
1707
1708 static int mov_read_dpxe(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1709 {
1710     return mov_read_extradata(c, pb, atom, AV_CODEC_ID_R10K);
1711 }
1712
1713 static int mov_read_avid(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1714 {
1715     int ret = mov_read_extradata(c, pb, atom, AV_CODEC_ID_AVUI);
1716     if(ret == 0)
1717         ret = mov_read_extradata(c, pb, atom, AV_CODEC_ID_DNXHD);
1718     return ret;
1719 }
1720
1721 static int mov_read_targa_y216(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1722 {
1723     int ret = mov_read_extradata(c, pb, atom, AV_CODEC_ID_TARGA_Y216);
1724
1725     if (!ret && c->fc->nb_streams >= 1) {
1726         AVCodecParameters *par = c->fc->streams[c->fc->nb_streams-1]->codecpar;
1727         if (par->extradata_size >= 40) {
1728             par->height = AV_RB16(&par->extradata[36]);
1729             par->width  = AV_RB16(&par->extradata[38]);
1730         }
1731     }
1732     return ret;
1733 }
1734
1735 static int mov_read_ares(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1736 {
1737     if (c->fc->nb_streams >= 1) {
1738         AVCodecParameters *par = c->fc->streams[c->fc->nb_streams-1]->codecpar;
1739         if (par->codec_tag == MKTAG('A', 'V', 'i', 'n') &&
1740             par->codec_id == AV_CODEC_ID_H264 &&
1741             atom.size > 11) {
1742             int cid;
1743             avio_skip(pb, 10);
1744             cid = avio_rb16(pb);
1745             /* For AVID AVCI50, force width of 1440 to be able to select the correct SPS and PPS */
1746             if (cid == 0xd4d || cid == 0xd4e)
1747                 par->width = 1440;
1748             return 0;
1749         } else if ((par->codec_tag == MKTAG('A', 'V', 'd', '1') ||
1750                     par->codec_tag == MKTAG('A', 'V', 'j', '2') ||
1751                     par->codec_tag == MKTAG('A', 'V', 'd', 'n')) &&
1752                    atom.size >= 24) {
1753             int num, den;
1754             avio_skip(pb, 12);
1755             num = avio_rb32(pb);
1756             den = avio_rb32(pb);
1757             if (num <= 0 || den <= 0)
1758                 return 0;
1759             switch (avio_rb32(pb)) {
1760             case 2:
1761                 if (den >= INT_MAX / 2)
1762                     return 0;
1763                 den *= 2;
1764             case 1:
1765                 c->fc->streams[c->fc->nb_streams-1]->display_aspect_ratio.num = num;
1766                 c->fc->streams[c->fc->nb_streams-1]->display_aspect_ratio.den = den;
1767             default:
1768                 return 0;
1769             }
1770         }
1771     }
1772
1773     return mov_read_avid(c, pb, atom);
1774 }
1775
1776 static int mov_read_aclr(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1777 {
1778     int ret = 0;
1779     int length = 0;
1780     uint64_t original_size;
1781     if (c->fc->nb_streams >= 1) {
1782         AVCodecParameters *par = c->fc->streams[c->fc->nb_streams-1]->codecpar;
1783         if (par->codec_id == AV_CODEC_ID_H264)
1784             return 0;
1785         if (atom.size == 16) {
1786             original_size = par->extradata_size;
1787             ret = mov_realloc_extradata(par, atom);
1788             if (!ret) {
1789                 length =  mov_read_atom_into_extradata(c, pb, atom, par, par->extradata + original_size);
1790                 if (length == atom.size) {
1791                     const uint8_t range_value = par->extradata[original_size + 19];
1792                     switch (range_value) {
1793                     case 1:
1794                         par->color_range = AVCOL_RANGE_MPEG;
1795                         break;
1796                     case 2:
1797                         par->color_range = AVCOL_RANGE_JPEG;
1798                         break;
1799                     default:
1800                         av_log(c, AV_LOG_WARNING, "ignored unknown aclr value (%d)\n", range_value);
1801                         break;
1802                     }
1803                     ff_dlog(c, "color_range: %d\n", par->color_range);
1804                 } else {
1805                   /* For some reason the whole atom was not added to the extradata */
1806                   av_log(c, AV_LOG_ERROR, "aclr not decoded - incomplete atom\n");
1807                 }
1808             } else {
1809                 av_log(c, AV_LOG_ERROR, "aclr not decoded - unable to add atom to extradata\n");
1810             }
1811         } else {
1812             av_log(c, AV_LOG_WARNING, "aclr not decoded - unexpected size %"PRId64"\n", atom.size);
1813         }
1814     }
1815
1816     return ret;
1817 }
1818
1819 static int mov_read_svq3(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1820 {
1821     return mov_read_extradata(c, pb, atom, AV_CODEC_ID_SVQ3);
1822 }
1823
1824 static int mov_read_wave(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1825 {
1826     AVStream *st;
1827     int ret;
1828
1829     if (c->fc->nb_streams < 1)
1830         return 0;
1831     st = c->fc->streams[c->fc->nb_streams-1];
1832
1833     if ((uint64_t)atom.size > (1<<30))
1834         return AVERROR_INVALIDDATA;
1835
1836     if (st->codecpar->codec_id == AV_CODEC_ID_QDM2 ||
1837         st->codecpar->codec_id == AV_CODEC_ID_QDMC ||
1838         st->codecpar->codec_id == AV_CODEC_ID_SPEEX) {
1839         // pass all frma atom to codec, needed at least for QDMC and QDM2
1840         av_freep(&st->codecpar->extradata);
1841         ret = ff_get_extradata(c->fc, st->codecpar, pb, atom.size);
1842         if (ret < 0)
1843             return ret;
1844     } else if (atom.size > 8) { /* to read frma, esds atoms */
1845         if (st->codecpar->codec_id == AV_CODEC_ID_ALAC && atom.size >= 24) {
1846             uint64_t buffer;
1847             ret = ffio_ensure_seekback(pb, 8);
1848             if (ret < 0)
1849                 return ret;
1850             buffer = avio_rb64(pb);
1851             atom.size -= 8;
1852             if (  (buffer & 0xFFFFFFFF) == MKBETAG('f','r','m','a')
1853                 && buffer >> 32 <= atom.size
1854                 && buffer >> 32 >= 8) {
1855                 avio_skip(pb, -8);
1856                 atom.size += 8;
1857             } else if (!st->codecpar->extradata_size) {
1858 #define ALAC_EXTRADATA_SIZE 36
1859                 st->codecpar->extradata = av_mallocz(ALAC_EXTRADATA_SIZE + AV_INPUT_BUFFER_PADDING_SIZE);
1860                 if (!st->codecpar->extradata)
1861                     return AVERROR(ENOMEM);
1862                 st->codecpar->extradata_size = ALAC_EXTRADATA_SIZE;
1863                 AV_WB32(st->codecpar->extradata    , ALAC_EXTRADATA_SIZE);
1864                 AV_WB32(st->codecpar->extradata + 4, MKTAG('a','l','a','c'));
1865                 AV_WB64(st->codecpar->extradata + 12, buffer);
1866                 avio_read(pb, st->codecpar->extradata + 20, 16);
1867                 avio_skip(pb, atom.size - 24);
1868                 return 0;
1869             }
1870         }
1871         if ((ret = mov_read_default(c, pb, atom)) < 0)
1872             return ret;
1873     } else
1874         avio_skip(pb, atom.size);
1875     return 0;
1876 }
1877
1878 /**
1879  * This function reads atom content and puts data in extradata without tag
1880  * nor size unlike mov_read_extradata.
1881  */
1882 static int mov_read_glbl(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1883 {
1884     AVStream *st;
1885     int ret;
1886
1887     if (c->fc->nb_streams < 1)
1888         return 0;
1889     st = c->fc->streams[c->fc->nb_streams-1];
1890
1891     if ((uint64_t)atom.size > (1<<30))
1892         return AVERROR_INVALIDDATA;
1893
1894     if (atom.size >= 10) {
1895         // Broken files created by legacy versions of libavformat will
1896         // wrap a whole fiel atom inside of a glbl atom.
1897         unsigned size = avio_rb32(pb);
1898         unsigned type = avio_rl32(pb);
1899         avio_seek(pb, -8, SEEK_CUR);
1900         if (type == MKTAG('f','i','e','l') && size == atom.size)
1901             return mov_read_default(c, pb, atom);
1902     }
1903     if (st->codecpar->extradata_size > 1 && st->codecpar->extradata) {
1904         av_log(c, AV_LOG_WARNING, "ignoring multiple glbl\n");
1905         return 0;
1906     }
1907     av_freep(&st->codecpar->extradata);
1908     ret = ff_get_extradata(c->fc, st->codecpar, pb, atom.size);
1909     if (ret < 0)
1910         return ret;
1911     if (atom.type == MKTAG('h','v','c','C') && st->codecpar->codec_tag == MKTAG('d','v','h','1'))
1912         /* HEVC-based Dolby Vision derived from hvc1.
1913            Happens to match with an identifier
1914            previously utilized for DV. Thus, if we have
1915            the hvcC extradata box available as specified,
1916            set codec to HEVC */
1917         st->codecpar->codec_id = AV_CODEC_ID_HEVC;
1918
1919     return 0;
1920 }
1921
1922 static int mov_read_dvc1(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1923 {
1924     AVStream *st;
1925     uint8_t profile_level;
1926     int ret;
1927
1928     if (c->fc->nb_streams < 1)
1929         return 0;
1930     st = c->fc->streams[c->fc->nb_streams-1];
1931
1932     if (atom.size >= (1<<28) || atom.size < 7)
1933         return AVERROR_INVALIDDATA;
1934
1935     profile_level = avio_r8(pb);
1936     if ((profile_level & 0xf0) != 0xc0)
1937         return 0;
1938
1939     avio_seek(pb, 6, SEEK_CUR);
1940     av_freep(&st->codecpar->extradata);
1941     ret = ff_get_extradata(c->fc, st->codecpar, pb, atom.size - 7);
1942     if (ret < 0)
1943         return ret;
1944
1945     return 0;
1946 }
1947
1948 /**
1949  * An strf atom is a BITMAPINFOHEADER struct. This struct is 40 bytes itself,
1950  * but can have extradata appended at the end after the 40 bytes belonging
1951  * to the struct.
1952  */
1953 static int mov_read_strf(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1954 {
1955     AVStream *st;
1956     int ret;
1957
1958     if (c->fc->nb_streams < 1)
1959         return 0;
1960     if (atom.size <= 40)
1961         return 0;
1962     st = c->fc->streams[c->fc->nb_streams-1];
1963
1964     if ((uint64_t)atom.size > (1<<30))
1965         return AVERROR_INVALIDDATA;
1966
1967     avio_skip(pb, 40);
1968     av_freep(&st->codecpar->extradata);
1969     ret = ff_get_extradata(c->fc, st->codecpar, pb, atom.size - 40);
1970     if (ret < 0)
1971         return ret;
1972
1973     return 0;
1974 }
1975
1976 static int mov_read_stco(MOVContext *c, AVIOContext *pb, MOVAtom atom)
1977 {
1978     AVStream *st;
1979     MOVStreamContext *sc;
1980     unsigned int i, entries;
1981
1982     if (c->fc->nb_streams < 1)
1983         return 0;
1984     st = c->fc->streams[c->fc->nb_streams-1];
1985     sc = st->priv_data;
1986
1987     avio_r8(pb); /* version */
1988     avio_rb24(pb); /* flags */
1989
1990     entries = avio_rb32(pb);
1991
1992     if (!entries)
1993         return 0;
1994
1995     if (sc->chunk_offsets)
1996         av_log(c->fc, AV_LOG_WARNING, "Duplicated STCO atom\n");
1997     av_free(sc->chunk_offsets);
1998     sc->chunk_count = 0;
1999     sc->chunk_offsets = av_malloc_array(entries, sizeof(*sc->chunk_offsets));
2000     if (!sc->chunk_offsets)
2001         return AVERROR(ENOMEM);
2002     sc->chunk_count = entries;
2003
2004     if      (atom.type == MKTAG('s','t','c','o'))
2005         for (i = 0; i < entries && !pb->eof_reached; i++)
2006             sc->chunk_offsets[i] = avio_rb32(pb);
2007     else if (atom.type == MKTAG('c','o','6','4'))
2008         for (i = 0; i < entries && !pb->eof_reached; i++)
2009             sc->chunk_offsets[i] = avio_rb64(pb);
2010     else
2011         return AVERROR_INVALIDDATA;
2012
2013     sc->chunk_count = i;
2014
2015     if (pb->eof_reached) {
2016         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted STCO atom\n");
2017         return AVERROR_EOF;
2018     }
2019
2020     return 0;
2021 }
2022
2023 static int mov_codec_id(AVStream *st, uint32_t format)
2024 {
2025     int id = ff_codec_get_id(ff_codec_movaudio_tags, format);
2026
2027     if (id <= 0 &&
2028         ((format & 0xFFFF) == 'm' + ('s' << 8) ||
2029          (format & 0xFFFF) == 'T' + ('S' << 8)))
2030         id = ff_codec_get_id(ff_codec_wav_tags, av_bswap32(format) & 0xFFFF);
2031
2032     if (st->codecpar->codec_type != AVMEDIA_TYPE_VIDEO && id > 0) {
2033         st->codecpar->codec_type = AVMEDIA_TYPE_AUDIO;
2034     } else if (st->codecpar->codec_type != AVMEDIA_TYPE_AUDIO &&
2035                /* skip old ASF MPEG-4 tag */
2036                format && format != MKTAG('m','p','4','s')) {
2037         id = ff_codec_get_id(ff_codec_movvideo_tags, format);
2038         if (id <= 0)
2039             id = ff_codec_get_id(ff_codec_bmp_tags, format);
2040         if (id > 0)
2041             st->codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
2042         else if (st->codecpar->codec_type == AVMEDIA_TYPE_DATA ||
2043                     (st->codecpar->codec_type == AVMEDIA_TYPE_SUBTITLE &&
2044                     st->codecpar->codec_id == AV_CODEC_ID_NONE)) {
2045             id = ff_codec_get_id(ff_codec_movsubtitle_tags, format);
2046             if (id > 0)
2047                 st->codecpar->codec_type = AVMEDIA_TYPE_SUBTITLE;
2048             else
2049                 id = ff_codec_get_id(ff_codec_movdata_tags, format);
2050         }
2051     }
2052
2053     st->codecpar->codec_tag = format;
2054
2055     return id;
2056 }
2057
2058 static void mov_parse_stsd_video(MOVContext *c, AVIOContext *pb,
2059                                  AVStream *st, MOVStreamContext *sc)
2060 {
2061     uint8_t codec_name[32] = { 0 };
2062     int64_t stsd_start;
2063     unsigned int len;
2064
2065     /* The first 16 bytes of the video sample description are already
2066      * read in ff_mov_read_stsd_entries() */
2067     stsd_start = avio_tell(pb) - 16;
2068
2069     avio_rb16(pb); /* version */
2070     avio_rb16(pb); /* revision level */
2071     avio_rb32(pb); /* vendor */
2072     avio_rb32(pb); /* temporal quality */
2073     avio_rb32(pb); /* spatial quality */
2074
2075     st->codecpar->width  = avio_rb16(pb); /* width */
2076     st->codecpar->height = avio_rb16(pb); /* height */
2077
2078     avio_rb32(pb); /* horiz resolution */
2079     avio_rb32(pb); /* vert resolution */
2080     avio_rb32(pb); /* data size, always 0 */
2081     avio_rb16(pb); /* frames per samples */
2082
2083     len = avio_r8(pb); /* codec name, pascal string */
2084     if (len > 31)
2085         len = 31;
2086     mov_read_mac_string(c, pb, len, codec_name, sizeof(codec_name));
2087     if (len < 31)
2088         avio_skip(pb, 31 - len);
2089
2090     if (codec_name[0])
2091         av_dict_set(&st->metadata, "encoder", codec_name, 0);
2092
2093     /* codec_tag YV12 triggers an UV swap in rawdec.c */
2094     if (!strncmp(codec_name, "Planar Y'CbCr 8-bit 4:2:0", 25)) {
2095         st->codecpar->codec_tag = MKTAG('I', '4', '2', '0');
2096         st->codecpar->width &= ~1;
2097         st->codecpar->height &= ~1;
2098     }
2099     /* Flash Media Server uses tag H.263 with Sorenson Spark */
2100     if (st->codecpar->codec_tag == MKTAG('H','2','6','3') &&
2101         !strncmp(codec_name, "Sorenson H263", 13))
2102         st->codecpar->codec_id = AV_CODEC_ID_FLV1;
2103
2104     st->codecpar->bits_per_coded_sample = avio_rb16(pb); /* depth */
2105
2106     avio_seek(pb, stsd_start, SEEK_SET);
2107
2108     if (ff_get_qtpalette(st->codecpar->codec_id, pb, sc->palette)) {
2109         st->codecpar->bits_per_coded_sample &= 0x1F;
2110         sc->has_palette = 1;
2111     }
2112 }
2113
2114 static void mov_parse_stsd_audio(MOVContext *c, AVIOContext *pb,
2115                                  AVStream *st, MOVStreamContext *sc)
2116 {
2117     int bits_per_sample, flags;
2118     uint16_t version = avio_rb16(pb);
2119     AVDictionaryEntry *compatible_brands = av_dict_get(c->fc->metadata, "compatible_brands", NULL, AV_DICT_MATCH_CASE);
2120
2121     avio_rb16(pb); /* revision level */
2122     avio_rb32(pb); /* vendor */
2123
2124     st->codecpar->channels              = avio_rb16(pb); /* channel count */
2125     st->codecpar->bits_per_coded_sample = avio_rb16(pb); /* sample size */
2126     av_log(c->fc, AV_LOG_TRACE, "audio channels %d\n", st->codecpar->channels);
2127
2128     sc->audio_cid = avio_rb16(pb);
2129     avio_rb16(pb); /* packet size = 0 */
2130
2131     st->codecpar->sample_rate = ((avio_rb32(pb) >> 16));
2132
2133     // Read QT version 1 fields. In version 0 these do not exist.
2134     av_log(c->fc, AV_LOG_TRACE, "version =%d, isom =%d\n", version, c->isom);
2135     if (!c->isom ||
2136         (compatible_brands && strstr(compatible_brands->value, "qt  ")) ||
2137         (sc->stsd_version == 0 && version > 0)) {
2138         if (version == 1) {
2139             sc->samples_per_frame = avio_rb32(pb);
2140             avio_rb32(pb); /* bytes per packet */
2141             sc->bytes_per_frame = avio_rb32(pb);
2142             avio_rb32(pb); /* bytes per sample */
2143         } else if (version == 2) {
2144             avio_rb32(pb); /* sizeof struct only */
2145             st->codecpar->sample_rate = av_int2double(avio_rb64(pb));
2146             st->codecpar->channels    = avio_rb32(pb);
2147             avio_rb32(pb); /* always 0x7F000000 */
2148             st->codecpar->bits_per_coded_sample = avio_rb32(pb);
2149
2150             flags = avio_rb32(pb); /* lpcm format specific flag */
2151             sc->bytes_per_frame   = avio_rb32(pb);
2152             sc->samples_per_frame = avio_rb32(pb);
2153             if (st->codecpar->codec_tag == MKTAG('l','p','c','m'))
2154                 st->codecpar->codec_id =
2155                     ff_mov_get_lpcm_codec_id(st->codecpar->bits_per_coded_sample,
2156                                              flags);
2157         }
2158         if (version == 0 || (version == 1 && sc->audio_cid != -2)) {
2159             /* can't correctly handle variable sized packet as audio unit */
2160             switch (st->codecpar->codec_id) {
2161             case AV_CODEC_ID_MP2:
2162             case AV_CODEC_ID_MP3:
2163                 st->need_parsing = AVSTREAM_PARSE_FULL;
2164                 break;
2165             }
2166         }
2167     }
2168
2169     if (sc->format == 0) {
2170         if (st->codecpar->bits_per_coded_sample == 8)
2171             st->codecpar->codec_id = mov_codec_id(st, MKTAG('r','a','w',' '));
2172         else if (st->codecpar->bits_per_coded_sample == 16)
2173             st->codecpar->codec_id = mov_codec_id(st, MKTAG('t','w','o','s'));
2174     }
2175
2176     switch (st->codecpar->codec_id) {
2177     case AV_CODEC_ID_PCM_S8:
2178     case AV_CODEC_ID_PCM_U8:
2179         if (st->codecpar->bits_per_coded_sample == 16)
2180             st->codecpar->codec_id = AV_CODEC_ID_PCM_S16BE;
2181         break;
2182     case AV_CODEC_ID_PCM_S16LE:
2183     case AV_CODEC_ID_PCM_S16BE:
2184         if (st->codecpar->bits_per_coded_sample == 8)
2185             st->codecpar->codec_id = AV_CODEC_ID_PCM_S8;
2186         else if (st->codecpar->bits_per_coded_sample == 24)
2187             st->codecpar->codec_id =
2188                 st->codecpar->codec_id == AV_CODEC_ID_PCM_S16BE ?
2189                 AV_CODEC_ID_PCM_S24BE : AV_CODEC_ID_PCM_S24LE;
2190         else if (st->codecpar->bits_per_coded_sample == 32)
2191              st->codecpar->codec_id =
2192                 st->codecpar->codec_id == AV_CODEC_ID_PCM_S16BE ?
2193                 AV_CODEC_ID_PCM_S32BE : AV_CODEC_ID_PCM_S32LE;
2194         break;
2195     /* set values for old format before stsd version 1 appeared */
2196     case AV_CODEC_ID_MACE3:
2197         sc->samples_per_frame = 6;
2198         sc->bytes_per_frame   = 2 * st->codecpar->channels;
2199         break;
2200     case AV_CODEC_ID_MACE6:
2201         sc->samples_per_frame = 6;
2202         sc->bytes_per_frame   = 1 * st->codecpar->channels;
2203         break;
2204     case AV_CODEC_ID_ADPCM_IMA_QT:
2205         sc->samples_per_frame = 64;
2206         sc->bytes_per_frame   = 34 * st->codecpar->channels;
2207         break;
2208     case AV_CODEC_ID_GSM:
2209         sc->samples_per_frame = 160;
2210         sc->bytes_per_frame   = 33;
2211         break;
2212     default:
2213         break;
2214     }
2215
2216     bits_per_sample = av_get_bits_per_sample(st->codecpar->codec_id);
2217     if (bits_per_sample) {
2218         st->codecpar->bits_per_coded_sample = bits_per_sample;
2219         sc->sample_size = (bits_per_sample >> 3) * st->codecpar->channels;
2220     }
2221 }
2222
2223 static void mov_parse_stsd_subtitle(MOVContext *c, AVIOContext *pb,
2224                                     AVStream *st, MOVStreamContext *sc,
2225                                     int64_t size)
2226 {
2227     // ttxt stsd contains display flags, justification, background
2228     // color, fonts, and default styles, so fake an atom to read it
2229     MOVAtom fake_atom = { .size = size };
2230     // mp4s contains a regular esds atom
2231     if (st->codecpar->codec_tag != AV_RL32("mp4s"))
2232         mov_read_glbl(c, pb, fake_atom);
2233     st->codecpar->width  = sc->width;
2234     st->codecpar->height = sc->height;
2235 }
2236
2237 static uint32_t yuv_to_rgba(uint32_t ycbcr)
2238 {
2239     uint8_t r, g, b;
2240     int y, cb, cr;
2241
2242     y  = (ycbcr >> 16) & 0xFF;
2243     cr = (ycbcr >> 8)  & 0xFF;
2244     cb =  ycbcr        & 0xFF;
2245
2246     b = av_clip_uint8((1164 * (y - 16)                     + 2018 * (cb - 128)) / 1000);
2247     g = av_clip_uint8((1164 * (y - 16) -  813 * (cr - 128) -  391 * (cb - 128)) / 1000);
2248     r = av_clip_uint8((1164 * (y - 16) + 1596 * (cr - 128)                    ) / 1000);
2249
2250     return (r << 16) | (g << 8) | b;
2251 }
2252
2253 static int mov_rewrite_dvd_sub_extradata(AVStream *st)
2254 {
2255     char buf[256] = {0};
2256     uint8_t *src = st->codecpar->extradata;
2257     int i;
2258
2259     if (st->codecpar->extradata_size != 64)
2260         return 0;
2261
2262     if (st->codecpar->width > 0 &&  st->codecpar->height > 0)
2263         snprintf(buf, sizeof(buf), "size: %dx%d\n",
2264                  st->codecpar->width, st->codecpar->height);
2265     av_strlcat(buf, "palette: ", sizeof(buf));
2266
2267     for (i = 0; i < 16; i++) {
2268         uint32_t yuv = AV_RB32(src + i * 4);
2269         uint32_t rgba = yuv_to_rgba(yuv);
2270
2271         av_strlcatf(buf, sizeof(buf), "%06"PRIx32"%s", rgba, i != 15 ? ", " : "");
2272     }
2273
2274     if (av_strlcat(buf, "\n", sizeof(buf)) >= sizeof(buf))
2275         return 0;
2276
2277     av_freep(&st->codecpar->extradata);
2278     st->codecpar->extradata_size = 0;
2279     st->codecpar->extradata = av_mallocz(strlen(buf) + AV_INPUT_BUFFER_PADDING_SIZE);
2280     if (!st->codecpar->extradata)
2281         return AVERROR(ENOMEM);
2282     st->codecpar->extradata_size = strlen(buf);
2283     memcpy(st->codecpar->extradata, buf, st->codecpar->extradata_size);
2284
2285     return 0;
2286 }
2287
2288 static int mov_parse_stsd_data(MOVContext *c, AVIOContext *pb,
2289                                 AVStream *st, MOVStreamContext *sc,
2290                                 int64_t size)
2291 {
2292     int ret;
2293
2294     if (st->codecpar->codec_tag == MKTAG('t','m','c','d')) {
2295         if ((int)size != size)
2296             return AVERROR(ENOMEM);
2297
2298         ret = ff_get_extradata(c->fc, st->codecpar, pb, size);
2299         if (ret < 0)
2300             return ret;
2301         if (size > 16) {
2302             MOVStreamContext *tmcd_ctx = st->priv_data;
2303             int val;
2304             val = AV_RB32(st->codecpar->extradata + 4);
2305             tmcd_ctx->tmcd_flags = val;
2306             st->avg_frame_rate.num = st->codecpar->extradata[16]; /* number of frame */
2307             st->avg_frame_rate.den = 1;
2308 #if FF_API_LAVF_AVCTX
2309 FF_DISABLE_DEPRECATION_WARNINGS
2310             st->codec->time_base = av_inv_q(st->avg_frame_rate);
2311 FF_ENABLE_DEPRECATION_WARNINGS
2312 #endif
2313             /* adjust for per frame dur in counter mode */
2314             if (tmcd_ctx->tmcd_flags & 0x0008) {
2315                 int timescale = AV_RB32(st->codecpar->extradata + 8);
2316                 int framedur = AV_RB32(st->codecpar->extradata + 12);
2317                 st->avg_frame_rate.num *= timescale;
2318                 st->avg_frame_rate.den *= framedur;
2319 #if FF_API_LAVF_AVCTX
2320 FF_DISABLE_DEPRECATION_WARNINGS
2321                 st->codec->time_base.den *= timescale;
2322                 st->codec->time_base.num *= framedur;
2323 FF_ENABLE_DEPRECATION_WARNINGS
2324 #endif
2325             }
2326             if (size > 30) {
2327                 uint32_t len = AV_RB32(st->codecpar->extradata + 18); /* name atom length */
2328                 uint32_t format = AV_RB32(st->codecpar->extradata + 22);
2329                 if (format == AV_RB32("name") && (int64_t)size >= (int64_t)len + 18) {
2330                     uint16_t str_size = AV_RB16(st->codecpar->extradata + 26); /* string length */
2331                     if (str_size > 0 && size >= (int)str_size + 26) {
2332                         char *reel_name = av_malloc(str_size + 1);
2333                         if (!reel_name)
2334                             return AVERROR(ENOMEM);
2335                         memcpy(reel_name, st->codecpar->extradata + 30, str_size);
2336                         reel_name[str_size] = 0; /* Add null terminator */
2337                         /* don't add reel_name if emtpy string */
2338                         if (*reel_name == 0) {
2339                             av_free(reel_name);
2340                         } else {
2341                             av_dict_set(&st->metadata, "reel_name", reel_name,  AV_DICT_DONT_STRDUP_VAL);
2342                         }
2343                     }
2344                 }
2345             }
2346         }
2347     } else {
2348         /* other codec type, just skip (rtp, mp4s ...) */
2349         avio_skip(pb, size);
2350     }
2351     return 0;
2352 }
2353
2354 static int mov_finalize_stsd_codec(MOVContext *c, AVIOContext *pb,
2355                                    AVStream *st, MOVStreamContext *sc)
2356 {
2357     if (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO &&
2358         !st->codecpar->sample_rate && sc->time_scale > 1)
2359         st->codecpar->sample_rate = sc->time_scale;
2360
2361     /* special codec parameters handling */
2362     switch (st->codecpar->codec_id) {
2363 #if CONFIG_DV_DEMUXER
2364     case AV_CODEC_ID_DVAUDIO:
2365         c->dv_fctx = avformat_alloc_context();
2366         if (!c->dv_fctx) {
2367             av_log(c->fc, AV_LOG_ERROR, "dv demux context alloc error\n");
2368             return AVERROR(ENOMEM);
2369         }
2370         c->dv_demux = avpriv_dv_init_demux(c->dv_fctx);
2371         if (!c->dv_demux) {
2372             av_log(c->fc, AV_LOG_ERROR, "dv demux context init error\n");
2373             return AVERROR(ENOMEM);
2374         }
2375         sc->dv_audio_container = 1;
2376         st->codecpar->codec_id    = AV_CODEC_ID_PCM_S16LE;
2377         break;
2378 #endif
2379     /* no ifdef since parameters are always those */
2380     case AV_CODEC_ID_QCELP:
2381         st->codecpar->channels = 1;
2382         // force sample rate for qcelp when not stored in mov
2383         if (st->codecpar->codec_tag != MKTAG('Q','c','l','p'))
2384             st->codecpar->sample_rate = 8000;
2385         // FIXME: Why is the following needed for some files?
2386         sc->samples_per_frame = 160;
2387         if (!sc->bytes_per_frame)
2388             sc->bytes_per_frame = 35;
2389         break;
2390     case AV_CODEC_ID_AMR_NB:
2391         st->codecpar->channels    = 1;
2392         /* force sample rate for amr, stsd in 3gp does not store sample rate */
2393         st->codecpar->sample_rate = 8000;
2394         break;
2395     case AV_CODEC_ID_AMR_WB:
2396         st->codecpar->channels    = 1;
2397         st->codecpar->sample_rate = 16000;
2398         break;
2399     case AV_CODEC_ID_MP2:
2400     case AV_CODEC_ID_MP3:
2401         /* force type after stsd for m1a hdlr */
2402         st->codecpar->codec_type = AVMEDIA_TYPE_AUDIO;
2403         break;
2404     case AV_CODEC_ID_GSM:
2405     case AV_CODEC_ID_ADPCM_MS:
2406     case AV_CODEC_ID_ADPCM_IMA_WAV:
2407     case AV_CODEC_ID_ILBC:
2408     case AV_CODEC_ID_MACE3:
2409     case AV_CODEC_ID_MACE6:
2410     case AV_CODEC_ID_QDM2:
2411         st->codecpar->block_align = sc->bytes_per_frame;
2412         break;
2413     case AV_CODEC_ID_ALAC:
2414         if (st->codecpar->extradata_size == 36) {
2415             st->codecpar->channels    = AV_RB8 (st->codecpar->extradata + 21);
2416             st->codecpar->sample_rate = AV_RB32(st->codecpar->extradata + 32);
2417         }
2418         break;
2419     case AV_CODEC_ID_AC3:
2420     case AV_CODEC_ID_EAC3:
2421     case AV_CODEC_ID_MPEG1VIDEO:
2422     case AV_CODEC_ID_VC1:
2423     case AV_CODEC_ID_VP8:
2424     case AV_CODEC_ID_VP9:
2425         st->need_parsing = AVSTREAM_PARSE_FULL;
2426         break;
2427     default:
2428         break;
2429     }
2430     return 0;
2431 }
2432
2433 static int mov_skip_multiple_stsd(MOVContext *c, AVIOContext *pb,
2434                                   int codec_tag, int format,
2435                                   int64_t size)
2436 {
2437     int video_codec_id = ff_codec_get_id(ff_codec_movvideo_tags, format);
2438
2439     if (codec_tag &&
2440          (codec_tag != format &&
2441           // AVID 1:1 samples with differing data format and codec tag exist
2442           (codec_tag != AV_RL32("AV1x") || format != AV_RL32("AVup")) &&
2443           // prores is allowed to have differing data format and codec tag
2444           codec_tag != AV_RL32("apcn") && codec_tag != AV_RL32("apch") &&
2445           // so is dv (sigh)
2446           codec_tag != AV_RL32("dvpp") && codec_tag != AV_RL32("dvcp") &&
2447           (c->fc->video_codec_id ? video_codec_id != c->fc->video_codec_id
2448                                  : codec_tag != MKTAG('j','p','e','g')))) {
2449         /* Multiple fourcc, we skip JPEG. This is not correct, we should
2450          * export it as a separate AVStream but this needs a few changes
2451          * in the MOV demuxer, patch welcome. */
2452
2453         av_log(c->fc, AV_LOG_WARNING, "multiple fourcc not supported\n");
2454         avio_skip(pb, size);
2455         return 1;
2456     }
2457
2458     return 0;
2459 }
2460
2461 int ff_mov_read_stsd_entries(MOVContext *c, AVIOContext *pb, int entries)
2462 {
2463     AVStream *st;
2464     MOVStreamContext *sc;
2465     int pseudo_stream_id;
2466
2467     av_assert0 (c->fc->nb_streams >= 1);
2468     st = c->fc->streams[c->fc->nb_streams-1];
2469     sc = st->priv_data;
2470
2471     for (pseudo_stream_id = 0;
2472          pseudo_stream_id < entries && !pb->eof_reached;
2473          pseudo_stream_id++) {
2474         //Parsing Sample description table
2475         enum AVCodecID id;
2476         int ret, dref_id = 1;
2477         MOVAtom a = { AV_RL32("stsd") };
2478         int64_t start_pos = avio_tell(pb);
2479         int64_t size    = avio_rb32(pb); /* size */
2480         uint32_t format = avio_rl32(pb); /* data format */
2481
2482         if (size >= 16) {
2483             avio_rb32(pb); /* reserved */
2484             avio_rb16(pb); /* reserved */
2485             dref_id = avio_rb16(pb);
2486         } else if (size <= 7) {
2487             av_log(c->fc, AV_LOG_ERROR,
2488                    "invalid size %"PRId64" in stsd\n", size);
2489             return AVERROR_INVALIDDATA;
2490         }
2491
2492         if (mov_skip_multiple_stsd(c, pb, st->codecpar->codec_tag, format,
2493                                    size - (avio_tell(pb) - start_pos))) {
2494             sc->stsd_count++;
2495             continue;
2496         }
2497
2498         sc->pseudo_stream_id = st->codecpar->codec_tag ? -1 : pseudo_stream_id;
2499         sc->dref_id= dref_id;
2500         sc->format = format;
2501
2502         id = mov_codec_id(st, format);
2503
2504         av_log(c->fc, AV_LOG_TRACE,
2505                "size=%"PRId64" 4CC=%s codec_type=%d\n", size,
2506                av_fourcc2str(format), st->codecpar->codec_type);
2507
2508         st->codecpar->codec_id = id;
2509         if (st->codecpar->codec_type==AVMEDIA_TYPE_VIDEO) {
2510             mov_parse_stsd_video(c, pb, st, sc);
2511         } else if (st->codecpar->codec_type==AVMEDIA_TYPE_AUDIO) {
2512             mov_parse_stsd_audio(c, pb, st, sc);
2513             if (st->codecpar->sample_rate < 0) {
2514                 av_log(c->fc, AV_LOG_ERROR, "Invalid sample rate %d\n", st->codecpar->sample_rate);
2515                 return AVERROR_INVALIDDATA;
2516             }
2517         } else if (st->codecpar->codec_type==AVMEDIA_TYPE_SUBTITLE){
2518             mov_parse_stsd_subtitle(c, pb, st, sc,
2519                                     size - (avio_tell(pb) - start_pos));
2520         } else {
2521             ret = mov_parse_stsd_data(c, pb, st, sc,
2522                                       size - (avio_tell(pb) - start_pos));
2523             if (ret < 0)
2524                 return ret;
2525         }
2526         /* this will read extra atoms at the end (wave, alac, damr, avcC, hvcC, SMI ...) */
2527         a.size = size - (avio_tell(pb) - start_pos);
2528         if (a.size > 8) {
2529             if ((ret = mov_read_default(c, pb, a)) < 0)
2530                 return ret;
2531         } else if (a.size > 0)
2532             avio_skip(pb, a.size);
2533
2534         if (sc->extradata && st->codecpar->extradata) {
2535             int extra_size = st->codecpar->extradata_size;
2536
2537             /* Move the current stream extradata to the stream context one. */
2538             sc->extradata_size[pseudo_stream_id] = extra_size;
2539             sc->extradata[pseudo_stream_id] = av_malloc(extra_size + AV_INPUT_BUFFER_PADDING_SIZE);
2540             if (!sc->extradata[pseudo_stream_id])
2541                 return AVERROR(ENOMEM);
2542             memcpy(sc->extradata[pseudo_stream_id], st->codecpar->extradata, extra_size);
2543             av_freep(&st->codecpar->extradata);
2544             st->codecpar->extradata_size = 0;
2545         }
2546         sc->stsd_count++;
2547     }
2548
2549     if (pb->eof_reached) {
2550         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted STSD atom\n");
2551         return AVERROR_EOF;
2552     }
2553
2554     return 0;
2555 }
2556
2557 static int mov_read_stsd(MOVContext *c, AVIOContext *pb, MOVAtom atom)
2558 {
2559     AVStream *st;
2560     MOVStreamContext *sc;
2561     int ret, entries;
2562
2563     if (c->fc->nb_streams < 1)
2564         return 0;
2565     st = c->fc->streams[c->fc->nb_streams - 1];
2566     sc = st->priv_data;
2567
2568     sc->stsd_version = avio_r8(pb);
2569     avio_rb24(pb); /* flags */
2570     entries = avio_rb32(pb);
2571
2572     /* Each entry contains a size (4 bytes) and format (4 bytes). */
2573     if (entries <= 0 || entries > atom.size / 8) {
2574         av_log(c->fc, AV_LOG_ERROR, "invalid STSD entries %d\n", entries);
2575         return AVERROR_INVALIDDATA;
2576     }
2577
2578     if (sc->extradata) {
2579         av_log(c->fc, AV_LOG_ERROR,
2580                "Duplicate stsd found in this track.\n");
2581         return AVERROR_INVALIDDATA;
2582     }
2583
2584     /* Prepare space for hosting multiple extradata. */
2585     sc->extradata = av_mallocz_array(entries, sizeof(*sc->extradata));
2586     if (!sc->extradata)
2587         return AVERROR(ENOMEM);
2588
2589     sc->extradata_size = av_mallocz_array(entries, sizeof(*sc->extradata_size));
2590     if (!sc->extradata_size) {
2591         ret = AVERROR(ENOMEM);
2592         goto fail;
2593     }
2594
2595     ret = ff_mov_read_stsd_entries(c, pb, entries);
2596     if (ret < 0)
2597         goto fail;
2598
2599     /* Restore back the primary extradata. */
2600     av_freep(&st->codecpar->extradata);
2601     st->codecpar->extradata_size = sc->extradata_size[0];
2602     if (sc->extradata_size[0]) {
2603         st->codecpar->extradata = av_mallocz(sc->extradata_size[0] + AV_INPUT_BUFFER_PADDING_SIZE);
2604         if (!st->codecpar->extradata)
2605             return AVERROR(ENOMEM);
2606         memcpy(st->codecpar->extradata, sc->extradata[0], sc->extradata_size[0]);
2607     }
2608
2609     return mov_finalize_stsd_codec(c, pb, st, sc);
2610 fail:
2611     if (sc->extradata) {
2612         int j;
2613         for (j = 0; j < sc->stsd_count; j++)
2614             av_freep(&sc->extradata[j]);
2615     }
2616
2617     av_freep(&sc->extradata);
2618     av_freep(&sc->extradata_size);
2619     return ret;
2620 }
2621
2622 static int mov_read_stsc(MOVContext *c, AVIOContext *pb, MOVAtom atom)
2623 {
2624     AVStream *st;
2625     MOVStreamContext *sc;
2626     unsigned int i, entries;
2627
2628     if (c->fc->nb_streams < 1)
2629         return 0;
2630     st = c->fc->streams[c->fc->nb_streams-1];
2631     sc = st->priv_data;
2632
2633     avio_r8(pb); /* version */
2634     avio_rb24(pb); /* flags */
2635
2636     entries = avio_rb32(pb);
2637     if ((uint64_t)entries * 12 + 4 > atom.size)
2638         return AVERROR_INVALIDDATA;
2639
2640     av_log(c->fc, AV_LOG_TRACE, "track[%u].stsc.entries = %u\n", c->fc->nb_streams - 1, entries);
2641
2642     if (!entries)
2643         return 0;
2644     if (sc->stsc_data)
2645         av_log(c->fc, AV_LOG_WARNING, "Duplicated STSC atom\n");
2646     av_free(sc->stsc_data);
2647     sc->stsc_count = 0;
2648     sc->stsc_data = av_malloc_array(entries, sizeof(*sc->stsc_data));
2649     if (!sc->stsc_data)
2650         return AVERROR(ENOMEM);
2651
2652     for (i = 0; i < entries && !pb->eof_reached; i++) {
2653         sc->stsc_data[i].first = avio_rb32(pb);
2654         sc->stsc_data[i].count = avio_rb32(pb);
2655         sc->stsc_data[i].id = avio_rb32(pb);
2656     }
2657
2658     sc->stsc_count = i;
2659     for (i = sc->stsc_count - 1; i < UINT_MAX; i--) {
2660         int64_t first_min = i + 1;
2661         if ((i+1 < sc->stsc_count && sc->stsc_data[i].first >= sc->stsc_data[i+1].first) ||
2662             (i > 0 && sc->stsc_data[i].first <= sc->stsc_data[i-1].first) ||
2663             sc->stsc_data[i].first < first_min ||
2664             sc->stsc_data[i].count < 1 ||
2665             sc->stsc_data[i].id < 1) {
2666             av_log(c->fc, AV_LOG_WARNING, "STSC entry %d is invalid (first=%d count=%d id=%d)\n", i, sc->stsc_data[i].first, sc->stsc_data[i].count, sc->stsc_data[i].id);
2667             if (i+1 >= sc->stsc_count) {
2668                 sc->stsc_data[i].first = FFMAX(sc->stsc_data[i].first, first_min);
2669                 if (i > 0 && sc->stsc_data[i].first <= sc->stsc_data[i-1].first)
2670                     sc->stsc_data[i].first = FFMIN(sc->stsc_data[i-1].first + 1LL, INT_MAX);
2671                 sc->stsc_data[i].count = FFMAX(sc->stsc_data[i].count, 1);
2672                 sc->stsc_data[i].id    = FFMAX(sc->stsc_data[i].id, 1);
2673                 continue;
2674             }
2675             av_assert0(sc->stsc_data[i+1].first >= 2);
2676             // We replace this entry by the next valid
2677             sc->stsc_data[i].first = sc->stsc_data[i+1].first - 1;
2678             sc->stsc_data[i].count = sc->stsc_data[i+1].count;
2679             sc->stsc_data[i].id    = sc->stsc_data[i+1].id;
2680         }
2681     }
2682
2683     if (pb->eof_reached) {
2684         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted STSC atom\n");
2685         return AVERROR_EOF;
2686     }
2687
2688     return 0;
2689 }
2690
2691 static inline int mov_stsc_index_valid(unsigned int index, unsigned int count)
2692 {
2693     return index < count - 1;
2694 }
2695
2696 /* Compute the samples value for the stsc entry at the given index. */
2697 static inline int64_t mov_get_stsc_samples(MOVStreamContext *sc, unsigned int index)
2698 {
2699     int chunk_count;
2700
2701     if (mov_stsc_index_valid(index, sc->stsc_count))
2702         chunk_count = sc->stsc_data[index + 1].first - sc->stsc_data[index].first;
2703     else {
2704         // Validation for stsc / stco  happens earlier in mov_read_stsc + mov_read_trak.
2705         av_assert0(sc->stsc_data[index].first <= sc->chunk_count);
2706         chunk_count = sc->chunk_count - (sc->stsc_data[index].first - 1);
2707     }
2708
2709     return sc->stsc_data[index].count * (int64_t)chunk_count;
2710 }
2711
2712 static int mov_read_stps(MOVContext *c, AVIOContext *pb, MOVAtom atom)
2713 {
2714     AVStream *st;
2715     MOVStreamContext *sc;
2716     unsigned i, entries;
2717
2718     if (c->fc->nb_streams < 1)
2719         return 0;
2720     st = c->fc->streams[c->fc->nb_streams-1];
2721     sc = st->priv_data;
2722
2723     avio_rb32(pb); // version + flags
2724
2725     entries = avio_rb32(pb);
2726     if (sc->stps_data)
2727         av_log(c->fc, AV_LOG_WARNING, "Duplicated STPS atom\n");
2728     av_free(sc->stps_data);
2729     sc->stps_count = 0;
2730     sc->stps_data = av_malloc_array(entries, sizeof(*sc->stps_data));
2731     if (!sc->stps_data)
2732         return AVERROR(ENOMEM);
2733
2734     for (i = 0; i < entries && !pb->eof_reached; i++) {
2735         sc->stps_data[i] = avio_rb32(pb);
2736     }
2737
2738     sc->stps_count = i;
2739
2740     if (pb->eof_reached) {
2741         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted STPS atom\n");
2742         return AVERROR_EOF;
2743     }
2744
2745     return 0;
2746 }
2747
2748 static int mov_read_stss(MOVContext *c, AVIOContext *pb, MOVAtom atom)
2749 {
2750     AVStream *st;
2751     MOVStreamContext *sc;
2752     unsigned int i, entries;
2753
2754     if (c->fc->nb_streams < 1)
2755         return 0;
2756     st = c->fc->streams[c->fc->nb_streams-1];
2757     sc = st->priv_data;
2758
2759     avio_r8(pb); /* version */
2760     avio_rb24(pb); /* flags */
2761
2762     entries = avio_rb32(pb);
2763
2764     av_log(c->fc, AV_LOG_TRACE, "keyframe_count = %u\n", entries);
2765
2766     if (!entries)
2767     {
2768         sc->keyframe_absent = 1;
2769         if (!st->need_parsing && st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO)
2770             st->need_parsing = AVSTREAM_PARSE_HEADERS;
2771         return 0;
2772     }
2773     if (sc->keyframes)
2774         av_log(c->fc, AV_LOG_WARNING, "Duplicated STSS atom\n");
2775     if (entries >= UINT_MAX / sizeof(int))
2776         return AVERROR_INVALIDDATA;
2777     av_freep(&sc->keyframes);
2778     sc->keyframe_count = 0;
2779     sc->keyframes = av_malloc_array(entries, sizeof(*sc->keyframes));
2780     if (!sc->keyframes)
2781         return AVERROR(ENOMEM);
2782
2783     for (i = 0; i < entries && !pb->eof_reached; i++) {
2784         sc->keyframes[i] = avio_rb32(pb);
2785     }
2786
2787     sc->keyframe_count = i;
2788
2789     if (pb->eof_reached) {
2790         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted STSS atom\n");
2791         return AVERROR_EOF;
2792     }
2793
2794     return 0;
2795 }
2796
2797 static int mov_read_stsz(MOVContext *c, AVIOContext *pb, MOVAtom atom)
2798 {
2799     AVStream *st;
2800     MOVStreamContext *sc;
2801     unsigned int i, entries, sample_size, field_size, num_bytes;
2802     GetBitContext gb;
2803     unsigned char* buf;
2804     int ret;
2805
2806     if (c->fc->nb_streams < 1)
2807         return 0;
2808     st = c->fc->streams[c->fc->nb_streams-1];
2809     sc = st->priv_data;
2810
2811     avio_r8(pb); /* version */
2812     avio_rb24(pb); /* flags */
2813
2814     if (atom.type == MKTAG('s','t','s','z')) {
2815         sample_size = avio_rb32(pb);
2816         if (!sc->sample_size) /* do not overwrite value computed in stsd */
2817             sc->sample_size = sample_size;
2818         sc->stsz_sample_size = sample_size;
2819         field_size = 32;
2820     } else {
2821         sample_size = 0;
2822         avio_rb24(pb); /* reserved */
2823         field_size = avio_r8(pb);
2824     }
2825     entries = avio_rb32(pb);
2826
2827     av_log(c->fc, AV_LOG_TRACE, "sample_size = %u sample_count = %u\n", sc->sample_size, entries);
2828
2829     sc->sample_count = entries;
2830     if (sample_size)
2831         return 0;
2832
2833     if (field_size != 4 && field_size != 8 && field_size != 16 && field_size != 32) {
2834         av_log(c->fc, AV_LOG_ERROR, "Invalid sample field size %u\n", field_size);
2835         return AVERROR_INVALIDDATA;
2836     }
2837
2838     if (!entries)
2839         return 0;
2840     if (entries >= (UINT_MAX - 4) / field_size)
2841         return AVERROR_INVALIDDATA;
2842     if (sc->sample_sizes)
2843         av_log(c->fc, AV_LOG_WARNING, "Duplicated STSZ atom\n");
2844     av_free(sc->sample_sizes);
2845     sc->sample_count = 0;
2846     sc->sample_sizes = av_malloc_array(entries, sizeof(*sc->sample_sizes));
2847     if (!sc->sample_sizes)
2848         return AVERROR(ENOMEM);
2849
2850     num_bytes = (entries*field_size+4)>>3;
2851
2852     buf = av_malloc(num_bytes+AV_INPUT_BUFFER_PADDING_SIZE);
2853     if (!buf) {
2854         av_freep(&sc->sample_sizes);
2855         return AVERROR(ENOMEM);
2856     }
2857
2858     ret = ffio_read_size(pb, buf, num_bytes);
2859     if (ret < 0) {
2860         av_freep(&sc->sample_sizes);
2861         av_free(buf);
2862         av_log(c->fc, AV_LOG_WARNING, "STSZ atom truncated\n");
2863         return 0;
2864     }
2865
2866     init_get_bits(&gb, buf, 8*num_bytes);
2867
2868     for (i = 0; i < entries && !pb->eof_reached; i++) {
2869         sc->sample_sizes[i] = get_bits_long(&gb, field_size);
2870         sc->data_size += sc->sample_sizes[i];
2871     }
2872
2873     sc->sample_count = i;
2874
2875     av_free(buf);
2876
2877     if (pb->eof_reached) {
2878         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted STSZ atom\n");
2879         return AVERROR_EOF;
2880     }
2881
2882     return 0;
2883 }
2884
2885 static int mov_read_stts(MOVContext *c, AVIOContext *pb, MOVAtom atom)
2886 {
2887     AVStream *st;
2888     MOVStreamContext *sc;
2889     unsigned int i, entries, alloc_size = 0;
2890     int64_t duration=0;
2891     int64_t total_sample_count=0;
2892
2893     if (c->fc->nb_streams < 1)
2894         return 0;
2895     st = c->fc->streams[c->fc->nb_streams-1];
2896     sc = st->priv_data;
2897
2898     avio_r8(pb); /* version */
2899     avio_rb24(pb); /* flags */
2900     entries = avio_rb32(pb);
2901
2902     av_log(c->fc, AV_LOG_TRACE, "track[%u].stts.entries = %u\n",
2903             c->fc->nb_streams-1, entries);
2904
2905     if (sc->stts_data)
2906         av_log(c->fc, AV_LOG_WARNING, "Duplicated STTS atom\n");
2907     av_freep(&sc->stts_data);
2908     sc->stts_count = 0;
2909     if (entries >= INT_MAX / sizeof(*sc->stts_data))
2910         return AVERROR(ENOMEM);
2911
2912     for (i = 0; i < entries && !pb->eof_reached; i++) {
2913         int sample_duration;
2914         unsigned int sample_count;
2915         unsigned int min_entries = FFMIN(FFMAX(i + 1, 1024 * 1024), entries);
2916         MOVStts *stts_data = av_fast_realloc(sc->stts_data, &alloc_size,
2917                                              min_entries * sizeof(*sc->stts_data));
2918         if (!stts_data) {
2919             av_freep(&sc->stts_data);
2920             sc->stts_count = 0;
2921             return AVERROR(ENOMEM);
2922         }
2923         sc->stts_count = min_entries;
2924         sc->stts_data = stts_data;
2925
2926         sample_count=avio_rb32(pb);
2927         sample_duration = avio_rb32(pb);
2928
2929         sc->stts_data[i].count= sample_count;
2930         sc->stts_data[i].duration= sample_duration;
2931
2932         av_log(c->fc, AV_LOG_TRACE, "sample_count=%d, sample_duration=%d\n",
2933                 sample_count, sample_duration);
2934
2935         duration+=(int64_t)sample_duration*(uint64_t)sample_count;
2936         total_sample_count+=sample_count;
2937     }
2938
2939     sc->stts_count = i;
2940
2941     if (duration > 0 &&
2942         duration <= INT64_MAX - sc->duration_for_fps &&
2943         total_sample_count <= INT_MAX - sc->nb_frames_for_fps
2944     ) {
2945         sc->duration_for_fps  += duration;
2946         sc->nb_frames_for_fps += total_sample_count;
2947     }
2948
2949     if (pb->eof_reached) {
2950         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted STTS atom\n");
2951         return AVERROR_EOF;
2952     }
2953
2954     st->nb_frames= total_sample_count;
2955     if (duration)
2956         st->duration= FFMIN(st->duration, duration);
2957     sc->track_end = duration;
2958     return 0;
2959 }
2960
2961 static void mov_update_dts_shift(MOVStreamContext *sc, int duration)
2962 {
2963     if (duration < 0) {
2964         if (duration == INT_MIN) {
2965             av_log(NULL, AV_LOG_WARNING, "mov_update_dts_shift(): dts_shift set to %d\n", INT_MAX);
2966             duration++;
2967         }
2968         sc->dts_shift = FFMAX(sc->dts_shift, -duration);
2969     }
2970 }
2971
2972 static int mov_read_ctts(MOVContext *c, AVIOContext *pb, MOVAtom atom)
2973 {
2974     AVStream *st;
2975     MOVStreamContext *sc;
2976     unsigned int i, entries, ctts_count = 0;
2977
2978     if (c->fc->nb_streams < 1)
2979         return 0;
2980     st = c->fc->streams[c->fc->nb_streams-1];
2981     sc = st->priv_data;
2982
2983     avio_r8(pb); /* version */
2984     avio_rb24(pb); /* flags */
2985     entries = avio_rb32(pb);
2986
2987     av_log(c->fc, AV_LOG_TRACE, "track[%u].ctts.entries = %u\n", c->fc->nb_streams - 1, entries);
2988
2989     if (!entries)
2990         return 0;
2991     if (entries >= UINT_MAX / sizeof(*sc->ctts_data))
2992         return AVERROR_INVALIDDATA;
2993     av_freep(&sc->ctts_data);
2994     sc->ctts_data = av_fast_realloc(NULL, &sc->ctts_allocated_size, entries * sizeof(*sc->ctts_data));
2995     if (!sc->ctts_data)
2996         return AVERROR(ENOMEM);
2997
2998     for (i = 0; i < entries && !pb->eof_reached; i++) {
2999         int count    =avio_rb32(pb);
3000         int duration =avio_rb32(pb);
3001
3002         if (count <= 0) {
3003             av_log(c->fc, AV_LOG_TRACE,
3004                    "ignoring CTTS entry with count=%d duration=%d\n",
3005                    count, duration);
3006             continue;
3007         }
3008
3009         add_ctts_entry(&sc->ctts_data, &ctts_count, &sc->ctts_allocated_size,
3010                        count, duration);
3011
3012         av_log(c->fc, AV_LOG_TRACE, "count=%d, duration=%d\n",
3013                 count, duration);
3014
3015         if (FFNABS(duration) < -(1<<28) && i+2<entries) {
3016             av_log(c->fc, AV_LOG_WARNING, "CTTS invalid\n");
3017             av_freep(&sc->ctts_data);
3018             sc->ctts_count = 0;
3019             return 0;
3020         }
3021
3022         if (i+2<entries)
3023             mov_update_dts_shift(sc, duration);
3024     }
3025
3026     sc->ctts_count = ctts_count;
3027
3028     if (pb->eof_reached) {
3029         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted CTTS atom\n");
3030         return AVERROR_EOF;
3031     }
3032
3033     av_log(c->fc, AV_LOG_TRACE, "dts shift %d\n", sc->dts_shift);
3034
3035     return 0;
3036 }
3037
3038 static int mov_read_sbgp(MOVContext *c, AVIOContext *pb, MOVAtom atom)
3039 {
3040     AVStream *st;
3041     MOVStreamContext *sc;
3042     unsigned int i, entries;
3043     uint8_t version;
3044     uint32_t grouping_type;
3045
3046     if (c->fc->nb_streams < 1)
3047         return 0;
3048     st = c->fc->streams[c->fc->nb_streams-1];
3049     sc = st->priv_data;
3050
3051     version = avio_r8(pb); /* version */
3052     avio_rb24(pb); /* flags */
3053     grouping_type = avio_rl32(pb);
3054     if (grouping_type != MKTAG( 'r','a','p',' '))
3055         return 0; /* only support 'rap ' grouping */
3056     if (version == 1)
3057         avio_rb32(pb); /* grouping_type_parameter */
3058
3059     entries = avio_rb32(pb);
3060     if (!entries)
3061         return 0;
3062     if (sc->rap_group)
3063         av_log(c->fc, AV_LOG_WARNING, "Duplicated SBGP atom\n");
3064     av_free(sc->rap_group);
3065     sc->rap_group_count = 0;
3066     sc->rap_group = av_malloc_array(entries, sizeof(*sc->rap_group));
3067     if (!sc->rap_group)
3068         return AVERROR(ENOMEM);
3069
3070     for (i = 0; i < entries && !pb->eof_reached; i++) {
3071         sc->rap_group[i].count = avio_rb32(pb); /* sample_count */
3072         sc->rap_group[i].index = avio_rb32(pb); /* group_description_index */
3073     }
3074
3075     sc->rap_group_count = i;
3076
3077     if (pb->eof_reached) {
3078         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted SBGP atom\n");
3079         return AVERROR_EOF;
3080     }
3081
3082     return 0;
3083 }
3084
3085 /**
3086  * Get ith edit list entry (media time, duration).
3087  */
3088 static int get_edit_list_entry(MOVContext *mov,
3089                                const MOVStreamContext *msc,
3090                                unsigned int edit_list_index,
3091                                int64_t *edit_list_media_time,
3092                                int64_t *edit_list_duration,
3093                                int64_t global_timescale)
3094 {
3095     if (edit_list_index == msc->elst_count) {
3096         return 0;
3097     }
3098     *edit_list_media_time = msc->elst_data[edit_list_index].time;
3099     *edit_list_duration = msc->elst_data[edit_list_index].duration;
3100
3101     /* duration is in global timescale units;convert to msc timescale */
3102     if (global_timescale == 0) {
3103       avpriv_request_sample(mov->fc, "Support for mvhd.timescale = 0 with editlists");
3104       return 0;
3105     }
3106     *edit_list_duration = av_rescale(*edit_list_duration, msc->time_scale,
3107                                      global_timescale);
3108     return 1;
3109 }
3110
3111 /**
3112  * Find the closest previous frame to the timestamp_pts, in e_old index
3113  * entries. Searching for just any frame / just key frames can be controlled by
3114  * last argument 'flag'.
3115  * Note that if ctts_data is not NULL, we will always search for a key frame
3116  * irrespective of the value of 'flag'. If we don't find any keyframe, we will
3117  * return the first frame of the video.
3118  *
3119  * Here the timestamp_pts is considered to be a presentation timestamp and
3120  * the timestamp of index entries are considered to be decoding timestamps.
3121  *
3122  * Returns 0 if successful in finding a frame, else returns -1.
3123  * Places the found index corresponding output arg.
3124  *
3125  * If ctts_old is not NULL, then refines the searched entry by searching
3126  * backwards from the found timestamp, to find the frame with correct PTS.
3127  *
3128  * Places the found ctts_index and ctts_sample in corresponding output args.
3129  */
3130 static int find_prev_closest_index(AVStream *st,
3131                                    AVIndexEntry *e_old,
3132                                    int nb_old,
3133                                    MOVStts* ctts_data,
3134                                    int64_t ctts_count,
3135                                    int64_t timestamp_pts,
3136                                    int flag,
3137                                    int64_t* index,
3138                                    int64_t* ctts_index,
3139                                    int64_t* ctts_sample)
3140 {
3141     MOVStreamContext *msc = st->priv_data;
3142     AVIndexEntry *e_keep = st->index_entries;
3143     int nb_keep = st->nb_index_entries;
3144     int64_t i = 0;
3145     int64_t index_ctts_count;
3146
3147     av_assert0(index);
3148
3149     // If dts_shift > 0, then all the index timestamps will have to be offset by
3150     // at least dts_shift amount to obtain PTS.
3151     // Hence we decrement the searched timestamp_pts by dts_shift to find the closest index element.
3152     if (msc->dts_shift > 0) {
3153         timestamp_pts -= msc->dts_shift;
3154     }
3155
3156     st->index_entries = e_old;
3157     st->nb_index_entries = nb_old;
3158     *index = av_index_search_timestamp(st, timestamp_pts, flag | AVSEEK_FLAG_BACKWARD);
3159
3160     // Keep going backwards in the index entries until the timestamp is the same.
3161     if (*index >= 0) {
3162         for (i = *index; i > 0 && e_old[i].timestamp == e_old[i - 1].timestamp;
3163              i--) {
3164             if ((flag & AVSEEK_FLAG_ANY) ||
3165                 (e_old[i - 1].flags & AVINDEX_KEYFRAME)) {
3166                 *index = i - 1;
3167             }
3168         }
3169     }
3170
3171     // If we have CTTS then refine the search, by searching backwards over PTS
3172     // computed by adding corresponding CTTS durations to index timestamps.
3173     if (ctts_data && *index >= 0) {
3174         av_assert0(ctts_index);
3175         av_assert0(ctts_sample);
3176         // Find out the ctts_index for the found frame.
3177         *ctts_index = 0;
3178         *ctts_sample = 0;
3179         for (index_ctts_count = 0; index_ctts_count < *index; index_ctts_count++) {
3180             if (*ctts_index < ctts_count) {
3181                 (*ctts_sample)++;
3182                 if (ctts_data[*ctts_index].count == *ctts_sample) {
3183                     (*ctts_index)++;
3184                     *ctts_sample = 0;
3185                 }
3186             }
3187         }
3188
3189         while (*index >= 0 && (*ctts_index) >= 0 && (*ctts_index) < ctts_count) {
3190             // Find a "key frame" with PTS <= timestamp_pts (So that we can decode B-frames correctly).
3191             // No need to add dts_shift to the timestamp here becase timestamp_pts has already been
3192             // compensated by dts_shift above.
3193             if ((e_old[*index].timestamp + ctts_data[*ctts_index].duration) <= timestamp_pts &&
3194                 (e_old[*index].flags & AVINDEX_KEYFRAME)) {
3195                 break;
3196             }
3197
3198             (*index)--;
3199             if (*ctts_sample == 0) {
3200                 (*ctts_index)--;
3201                 if (*ctts_index >= 0)
3202                   *ctts_sample = ctts_data[*ctts_index].count - 1;
3203             } else {
3204                 (*ctts_sample)--;
3205             }
3206         }
3207     }
3208
3209     /* restore AVStream state*/
3210     st->index_entries = e_keep;
3211     st->nb_index_entries = nb_keep;
3212     return *index >= 0 ? 0 : -1;
3213 }
3214
3215 /**
3216  * Add index entry with the given values, to the end of st->index_entries.
3217  * Returns the new size st->index_entries if successful, else returns -1.
3218  *
3219  * This function is similar to ff_add_index_entry in libavformat/utils.c
3220  * except that here we are always unconditionally adding an index entry to
3221  * the end, instead of searching the entries list and skipping the add if
3222  * there is an existing entry with the same timestamp.
3223  * This is needed because the mov_fix_index calls this func with the same
3224  * unincremented timestamp for successive discarded frames.
3225  */
3226 static int64_t add_index_entry(AVStream *st, int64_t pos, int64_t timestamp,
3227                                int size, int distance, int flags)
3228 {
3229     AVIndexEntry *entries, *ie;
3230     int64_t index = -1;
3231     const size_t min_size_needed = (st->nb_index_entries + 1) * sizeof(AVIndexEntry);
3232
3233     // Double the allocation each time, to lower memory fragmentation.
3234     // Another difference from ff_add_index_entry function.
3235     const size_t requested_size =
3236         min_size_needed > st->index_entries_allocated_size ?
3237         FFMAX(min_size_needed, 2 * st->index_entries_allocated_size) :
3238         min_size_needed;
3239
3240     if((unsigned)st->nb_index_entries + 1 >= UINT_MAX / sizeof(AVIndexEntry))
3241         return -1;
3242
3243     entries = av_fast_realloc(st->index_entries,
3244                               &st->index_entries_allocated_size,
3245                               requested_size);
3246     if(!entries)
3247         return -1;
3248
3249     st->index_entries= entries;
3250
3251     index= st->nb_index_entries++;
3252     ie= &entries[index];
3253
3254     ie->pos = pos;
3255     ie->timestamp = timestamp;
3256     ie->min_distance= distance;
3257     ie->size= size;
3258     ie->flags = flags;
3259     return index;
3260 }
3261
3262 /**
3263  * Rewrite timestamps of index entries in the range [end_index - frame_duration_buffer_size, end_index)
3264  * by subtracting end_ts successively by the amounts given in frame_duration_buffer.
3265  */
3266 static void fix_index_entry_timestamps(AVStream* st, int end_index, int64_t end_ts,
3267                                        int64_t* frame_duration_buffer,
3268                                        int frame_duration_buffer_size) {
3269     int i = 0;
3270     av_assert0(end_index >= 0 && end_index <= st->nb_index_entries);
3271     for (i = 0; i < frame_duration_buffer_size; i++) {
3272         end_ts -= frame_duration_buffer[frame_duration_buffer_size - 1 - i];
3273         st->index_entries[end_index - 1 - i].timestamp = end_ts;
3274     }
3275 }
3276
3277 /**
3278  * Append a new ctts entry to ctts_data.
3279  * Returns the new ctts_count if successful, else returns -1.
3280  */
3281 static int64_t add_ctts_entry(MOVStts** ctts_data, unsigned int* ctts_count, unsigned int* allocated_size,
3282                               int count, int duration)
3283 {
3284     MOVStts *ctts_buf_new;
3285     const size_t min_size_needed = (*ctts_count + 1) * sizeof(MOVStts);
3286     const size_t requested_size =
3287         min_size_needed > *allocated_size ?
3288         FFMAX(min_size_needed, 2 * (*allocated_size)) :
3289         min_size_needed;
3290
3291     if((unsigned)(*ctts_count) >= UINT_MAX / sizeof(MOVStts) - 1)
3292         return -1;
3293
3294     ctts_buf_new = av_fast_realloc(*ctts_data, allocated_size, requested_size);
3295
3296     if(!ctts_buf_new)
3297         return -1;
3298
3299     *ctts_data = ctts_buf_new;
3300
3301     ctts_buf_new[*ctts_count].count = count;
3302     ctts_buf_new[*ctts_count].duration = duration;
3303
3304     *ctts_count = (*ctts_count) + 1;
3305     return *ctts_count;
3306 }
3307
3308 #define MAX_REORDER_DELAY 16
3309 static void mov_estimate_video_delay(MOVContext *c, AVStream* st) {
3310     MOVStreamContext *msc = st->priv_data;
3311     int ind;
3312     int ctts_ind = 0;
3313     int ctts_sample = 0;
3314     int64_t pts_buf[MAX_REORDER_DELAY + 1]; // Circular buffer to sort pts.
3315     int buf_start = 0;
3316     int j, r, num_swaps;
3317
3318     for (j = 0; j < MAX_REORDER_DELAY + 1; j++)
3319         pts_buf[j] = INT64_MIN;
3320
3321     if (st->codecpar->video_delay <= 0 && msc->ctts_data &&
3322         st->codecpar->codec_id == AV_CODEC_ID_H264) {
3323         st->codecpar->video_delay = 0;
3324         for(ind = 0; ind < st->nb_index_entries && ctts_ind < msc->ctts_count; ++ind) {
3325             // Point j to the last elem of the buffer and insert the current pts there.
3326             j = buf_start;
3327             buf_start = (buf_start + 1);
3328             if (buf_start == MAX_REORDER_DELAY + 1)
3329                 buf_start = 0;
3330
3331             pts_buf[j] = st->index_entries[ind].timestamp + msc->ctts_data[ctts_ind].duration;
3332
3333             // The timestamps that are already in the sorted buffer, and are greater than the
3334             // current pts, are exactly the timestamps that need to be buffered to output PTS
3335             // in correct sorted order.
3336             // Hence the video delay (which is the buffer size used to sort DTS and output PTS),
3337             // can be computed as the maximum no. of swaps any particular timestamp needs to
3338             // go through, to keep this buffer in sorted order.
3339             num_swaps = 0;
3340             while (j != buf_start) {
3341                 r = j - 1;
3342                 if (r < 0) r = MAX_REORDER_DELAY;
3343                 if (pts_buf[j] < pts_buf[r]) {
3344                     FFSWAP(int64_t, pts_buf[j], pts_buf[r]);
3345                     ++num_swaps;
3346                 } else {
3347                     break;
3348                 }
3349                 j = r;
3350             }
3351             st->codecpar->video_delay = FFMAX(st->codecpar->video_delay, num_swaps);
3352
3353             ctts_sample++;
3354             if (ctts_sample == msc->ctts_data[ctts_ind].count) {
3355                 ctts_ind++;
3356                 ctts_sample = 0;
3357             }
3358         }
3359         av_log(c->fc, AV_LOG_DEBUG, "Setting codecpar->delay to %d for stream st: %d\n",
3360                st->codecpar->video_delay, st->index);
3361     }
3362 }
3363
3364 static void mov_current_sample_inc(MOVStreamContext *sc)
3365 {
3366     sc->current_sample++;
3367     sc->current_index++;
3368     if (sc->index_ranges &&
3369         sc->current_index >= sc->current_index_range->end &&
3370         sc->current_index_range->end) {
3371         sc->current_index_range++;
3372         sc->current_index = sc->current_index_range->start;
3373     }
3374 }
3375
3376 static void mov_current_sample_dec(MOVStreamContext *sc)
3377 {
3378     sc->current_sample--;
3379     sc->current_index--;
3380     if (sc->index_ranges &&
3381         sc->current_index < sc->current_index_range->start &&
3382         sc->current_index_range > sc->index_ranges) {
3383         sc->current_index_range--;
3384         sc->current_index = sc->current_index_range->end - 1;
3385     }
3386 }
3387
3388 static void mov_current_sample_set(MOVStreamContext *sc, int current_sample)
3389 {
3390     int64_t range_size;
3391
3392     sc->current_sample = current_sample;
3393     sc->current_index = current_sample;
3394     if (!sc->index_ranges) {
3395         return;
3396     }
3397
3398     for (sc->current_index_range = sc->index_ranges;
3399         sc->current_index_range->end;
3400         sc->current_index_range++) {
3401         range_size = sc->current_index_range->end - sc->current_index_range->start;
3402         if (range_size > current_sample) {
3403             sc->current_index = sc->current_index_range->start + current_sample;
3404             break;
3405         }
3406         current_sample -= range_size;
3407     }
3408 }
3409
3410 /**
3411  * Fix st->index_entries, so that it contains only the entries (and the entries
3412  * which are needed to decode them) that fall in the edit list time ranges.
3413  * Also fixes the timestamps of the index entries to match the timeline
3414  * specified the edit lists.
3415  */
3416 static void mov_fix_index(MOVContext *mov, AVStream *st)
3417 {
3418     MOVStreamContext *msc = st->priv_data;
3419     AVIndexEntry *e_old = st->index_entries;
3420     int nb_old = st->nb_index_entries;
3421     const AVIndexEntry *e_old_end = e_old + nb_old;
3422     const AVIndexEntry *current = NULL;
3423     MOVStts *ctts_data_old = msc->ctts_data;
3424     int64_t ctts_index_old = 0;
3425     int64_t ctts_sample_old = 0;
3426     int64_t ctts_count_old = msc->ctts_count;
3427     int64_t edit_list_media_time = 0;
3428     int64_t edit_list_duration = 0;
3429     int64_t frame_duration = 0;
3430     int64_t edit_list_dts_counter = 0;
3431     int64_t edit_list_dts_entry_end = 0;
3432     int64_t edit_list_start_ctts_sample = 0;
3433     int64_t curr_cts;
3434     int64_t curr_ctts = 0;
3435     int64_t empty_edits_sum_duration = 0;
3436     int64_t edit_list_index = 0;
3437     int64_t index;
3438     int flags;
3439     int64_t start_dts = 0;
3440     int64_t edit_list_start_encountered = 0;
3441     int64_t search_timestamp = 0;
3442     int64_t* frame_duration_buffer = NULL;
3443     int num_discarded_begin = 0;
3444     int first_non_zero_audio_edit = -1;
3445     int packet_skip_samples = 0;
3446     MOVIndexRange *current_index_range;
3447     int i;
3448     int found_keyframe_after_edit = 0;
3449     int found_non_empty_edit = 0;
3450
3451     if (!msc->elst_data || msc->elst_count <= 0 || nb_old <= 0) {
3452         return;
3453     }
3454
3455     // allocate the index ranges array
3456     msc->index_ranges = av_malloc((msc->elst_count + 1) * sizeof(msc->index_ranges[0]));
3457     if (!msc->index_ranges) {
3458         av_log(mov->fc, AV_LOG_ERROR, "Cannot allocate index ranges buffer\n");
3459         return;
3460     }
3461     msc->current_index_range = msc->index_ranges;
3462     current_index_range = msc->index_ranges - 1;
3463
3464     // Clean AVStream from traces of old index
3465     st->index_entries = NULL;
3466     st->index_entries_allocated_size = 0;
3467     st->nb_index_entries = 0;
3468
3469     // Clean ctts fields of MOVStreamContext
3470     msc->ctts_data = NULL;
3471     msc->ctts_count = 0;
3472     msc->ctts_index = 0;
3473     msc->ctts_sample = 0;
3474     msc->ctts_allocated_size = 0;
3475
3476     // Reinitialize min_corrected_pts so that it can be computed again.
3477     msc->min_corrected_pts = -1;
3478
3479     // If the dts_shift is positive (in case of negative ctts values in mov),
3480     // then negate the DTS by dts_shift
3481     if (msc->dts_shift > 0) {
3482         edit_list_dts_entry_end -= msc->dts_shift;
3483         av_log(mov->fc, AV_LOG_DEBUG, "Shifting DTS by %d because of negative CTTS.\n", msc->dts_shift);
3484     }
3485
3486     start_dts = edit_list_dts_entry_end;
3487
3488     while (get_edit_list_entry(mov, msc, edit_list_index, &edit_list_media_time,
3489                                &edit_list_duration, mov->time_scale)) {
3490         av_log(mov->fc, AV_LOG_DEBUG, "Processing st: %d, edit list %"PRId64" - media time: %"PRId64", duration: %"PRId64"\n",
3491                st->index, edit_list_index, edit_list_media_time, edit_list_duration);
3492         edit_list_index++;
3493         edit_list_dts_counter = edit_list_dts_entry_end;
3494         edit_list_dts_entry_end += edit_list_duration;
3495         num_discarded_begin = 0;
3496         if (!found_non_empty_edit && edit_list_media_time == -1) {
3497             empty_edits_sum_duration += edit_list_duration;
3498             continue;
3499         }
3500         found_non_empty_edit = 1;
3501
3502         // If we encounter a non-negative edit list reset the skip_samples/start_pad fields and set them
3503         // according to the edit list below.
3504         if (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO) {
3505             if (first_non_zero_audio_edit < 0) {
3506                 first_non_zero_audio_edit = 1;
3507             } else {
3508                 first_non_zero_audio_edit = 0;
3509             }
3510
3511             if (first_non_zero_audio_edit > 0)
3512                 st->skip_samples = msc->start_pad = 0;
3513         }
3514
3515         // While reordering frame index according to edit list we must handle properly
3516         // the scenario when edit list entry starts from none key frame.
3517         // We find closest previous key frame and preserve it and consequent frames in index.
3518         // All frames which are outside edit list entry time boundaries will be dropped after decoding.
3519         search_timestamp = edit_list_media_time;
3520         if (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO) {
3521             // Audio decoders like AAC need need a decoder delay samples previous to the current sample,
3522             // to correctly decode this frame. Hence for audio we seek to a frame 1 sec. before the
3523             // edit_list_media_time to cover the decoder delay.
3524             search_timestamp = FFMAX(search_timestamp - msc->time_scale, e_old[0].timestamp);
3525         }
3526
3527         if (find_prev_closest_index(st, e_old, nb_old, ctts_data_old, ctts_count_old, search_timestamp, 0,
3528                                     &index, &ctts_index_old, &ctts_sample_old) < 0) {
3529             av_log(mov->fc, AV_LOG_WARNING,
3530                    "st: %d edit list: %"PRId64" Missing key frame while searching for timestamp: %"PRId64"\n",
3531                    st->index, edit_list_index, search_timestamp);
3532             if (find_prev_closest_index(st, e_old, nb_old, ctts_data_old, ctts_count_old, search_timestamp, AVSEEK_FLAG_ANY,
3533                                         &index, &ctts_index_old, &ctts_sample_old) < 0) {
3534                 av_log(mov->fc, AV_LOG_WARNING,
3535                        "st: %d edit list %"PRId64" Cannot find an index entry before timestamp: %"PRId64".\n",
3536                        st->index, edit_list_index, search_timestamp);
3537                 index = 0;
3538                 ctts_index_old = 0;
3539                 ctts_sample_old = 0;
3540             }
3541         }
3542         current = e_old + index;
3543         edit_list_start_ctts_sample = ctts_sample_old;
3544
3545         // Iterate over index and arrange it according to edit list
3546         edit_list_start_encountered = 0;
3547         found_keyframe_after_edit = 0;
3548         for (; current < e_old_end; current++, index++) {
3549             // check  if frame outside edit list mark it for discard
3550             frame_duration = (current + 1 <  e_old_end) ?
3551                              ((current + 1)->timestamp - current->timestamp) : edit_list_duration;
3552
3553             flags = current->flags;
3554
3555             // frames (pts) before or after edit list
3556             curr_cts = current->timestamp + msc->dts_shift;
3557             curr_ctts = 0;
3558
3559             if (ctts_data_old && ctts_index_old < ctts_count_old) {
3560                 curr_ctts = ctts_data_old[ctts_index_old].duration;
3561                 av_log(mov->fc, AV_LOG_DEBUG, "stts: %"PRId64" ctts: %"PRId64", ctts_index: %"PRId64", ctts_count: %"PRId64"\n",
3562                        curr_cts, curr_ctts, ctts_index_old, ctts_count_old);
3563                 curr_cts += curr_ctts;
3564                 ctts_sample_old++;
3565                 if (ctts_sample_old == ctts_data_old[ctts_index_old].count) {
3566                     if (add_ctts_entry(&msc->ctts_data, &msc->ctts_count,
3567                                        &msc->ctts_allocated_size,
3568                                        ctts_data_old[ctts_index_old].count - edit_list_start_ctts_sample,
3569                                        ctts_data_old[ctts_index_old].duration) == -1) {
3570                         av_log(mov->fc, AV_LOG_ERROR, "Cannot add CTTS entry %"PRId64" - {%"PRId64", %d}\n",
3571                                ctts_index_old,
3572                                ctts_data_old[ctts_index_old].count - edit_list_start_ctts_sample,
3573                                ctts_data_old[ctts_index_old].duration);
3574                         break;
3575                     }
3576                     ctts_index_old++;
3577                     ctts_sample_old = 0;
3578                     edit_list_start_ctts_sample = 0;
3579                 }
3580             }
3581
3582             if (curr_cts < edit_list_media_time || curr_cts >= (edit_list_duration + edit_list_media_time)) {
3583                 if (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO && st->codecpar->codec_id != AV_CODEC_ID_VORBIS &&
3584                     curr_cts < edit_list_media_time && curr_cts + frame_duration > edit_list_media_time &&
3585                     first_non_zero_audio_edit > 0) {
3586                     packet_skip_samples = edit_list_media_time - curr_cts;
3587                     st->skip_samples += packet_skip_samples;
3588
3589                     // Shift the index entry timestamp by packet_skip_samples to be correct.
3590                     edit_list_dts_counter -= packet_skip_samples;
3591                     if (edit_list_start_encountered == 0)  {
3592                         edit_list_start_encountered = 1;
3593                         // Make timestamps strictly monotonically increasing for audio, by rewriting timestamps for
3594                         // discarded packets.
3595                         if (frame_duration_buffer) {
3596                             fix_index_entry_timestamps(st, st->nb_index_entries, edit_list_dts_counter,
3597                                                        frame_duration_buffer, num_discarded_begin);
3598                             av_freep(&frame_duration_buffer);
3599                         }
3600                     }
3601
3602                     av_log(mov->fc, AV_LOG_DEBUG, "skip %d audio samples from curr_cts: %"PRId64"\n", packet_skip_samples, curr_cts);
3603                 } else {
3604                     flags |= AVINDEX_DISCARD_FRAME;
3605                     av_log(mov->fc, AV_LOG_DEBUG, "drop a frame at curr_cts: %"PRId64" @ %"PRId64"\n", curr_cts, index);
3606
3607                     if (edit_list_start_encountered == 0) {
3608                         num_discarded_begin++;
3609                         frame_duration_buffer = av_realloc(frame_duration_buffer,
3610                                                            num_discarded_begin * sizeof(int64_t));
3611                         if (!frame_duration_buffer) {
3612                             av_log(mov->fc, AV_LOG_ERROR, "Cannot reallocate frame duration buffer\n");
3613                             break;
3614                         }
3615                         frame_duration_buffer[num_discarded_begin - 1] = frame_duration;
3616
3617                         // Increment skip_samples for the first non-zero audio edit list
3618                         if (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO &&
3619                             first_non_zero_audio_edit > 0 && st->codecpar->codec_id != AV_CODEC_ID_VORBIS) {
3620                             st->skip_samples += frame_duration;
3621                         }
3622                     }
3623                 }
3624             } else {
3625                 if (msc->min_corrected_pts < 0) {
3626                     msc->min_corrected_pts = edit_list_dts_counter + curr_ctts + msc->dts_shift;
3627                 } else {
3628                     msc->min_corrected_pts = FFMIN(msc->min_corrected_pts, edit_list_dts_counter + curr_ctts + msc->dts_shift);
3629                 }
3630                 if (edit_list_start_encountered == 0) {
3631                     edit_list_start_encountered = 1;
3632                     // Make timestamps strictly monotonically increasing by rewriting timestamps for
3633                     // discarded packets.
3634                     if (frame_duration_buffer) {
3635                         fix_index_entry_timestamps(st, st->nb_index_entries, edit_list_dts_counter,
3636                                                    frame_duration_buffer, num_discarded_begin);
3637                         av_freep(&frame_duration_buffer);
3638                     }
3639                 }
3640             }
3641
3642             if (add_index_entry(st, current->pos, edit_list_dts_counter, current->size,
3643                                 current->min_distance, flags) == -1) {
3644                 av_log(mov->fc, AV_LOG_ERROR, "Cannot add index entry\n");
3645                 break;
3646             }
3647
3648             // Update the index ranges array
3649             if (current_index_range < msc->index_ranges || index != current_index_range->end) {
3650                 current_index_range++;
3651                 current_index_range->start = index;
3652             }
3653             current_index_range->end = index + 1;
3654
3655             // Only start incrementing DTS in frame_duration amounts, when we encounter a frame in edit list.
3656             if (edit_list_start_encountered > 0) {
3657                 edit_list_dts_counter = edit_list_dts_counter + frame_duration;
3658             }
3659
3660             // Break when found first key frame after edit entry completion
3661             if ((curr_cts + frame_duration >= (edit_list_duration + edit_list_media_time)) &&
3662                 ((flags & AVINDEX_KEYFRAME) || ((st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO)))) {
3663                 if (ctts_data_old) {
3664                     // If we have CTTS and this is the first keyframe after edit elist,
3665                     // wait for one more, because there might be trailing B-frames after this I-frame
3666                     // that do belong to the edit.
3667                     if (st->codecpar->codec_type != AVMEDIA_TYPE_AUDIO && found_keyframe_after_edit == 0) {
3668                         found_keyframe_after_edit = 1;
3669                         continue;
3670                     }
3671                     if (ctts_sample_old != 0) {
3672                         if (add_ctts_entry(&msc->ctts_data, &msc->ctts_count,
3673                                            &msc->ctts_allocated_size,
3674                                            ctts_sample_old - edit_list_start_ctts_sample,
3675                                            ctts_data_old[ctts_index_old].duration) == -1) {
3676                             av_log(mov->fc, AV_LOG_ERROR, "Cannot add CTTS entry %"PRId64" - {%"PRId64", %d}\n",
3677                                    ctts_index_old, ctts_sample_old - edit_list_start_ctts_sample,
3678                                    ctts_data_old[ctts_index_old].duration);
3679                             break;
3680                         }
3681                     }
3682                 }
3683                 break;
3684             }
3685         }
3686     }
3687     // If there are empty edits, then msc->min_corrected_pts might be positive
3688     // intentionally. So we subtract the sum duration of emtpy edits here.
3689     msc->min_corrected_pts -= empty_edits_sum_duration;
3690
3691     // If the minimum pts turns out to be greater than zero after fixing the index, then we subtract the
3692     // dts by that amount to make the first pts zero.
3693     if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {
3694         if (msc->min_corrected_pts > 0) {
3695             av_log(mov->fc, AV_LOG_DEBUG, "Offset DTS by %"PRId64" to make first pts zero.\n", msc->min_corrected_pts);
3696             for (i = 0; i < st->nb_index_entries; ++i) {
3697                 st->index_entries[i].timestamp -= msc->min_corrected_pts;
3698             }
3699         }
3700     }
3701     // Start time should be equal to zero or the duration of any empty edits.
3702     st->start_time = empty_edits_sum_duration;
3703
3704     // Update av stream length, if it ends up shorter than the track's media duration
3705     st->duration = FFMIN(st->duration, edit_list_dts_entry_end - start_dts);
3706     msc->start_pad = st->skip_samples;
3707
3708     // Free the old index and the old CTTS structures
3709     av_free(e_old);
3710     av_free(ctts_data_old);
3711     av_freep(&frame_duration_buffer);
3712
3713     // Null terminate the index ranges array
3714     current_index_range++;
3715     current_index_range->start = 0;
3716     current_index_range->end = 0;
3717     msc->current_index = msc->index_ranges[0].start;
3718 }
3719
3720 static void mov_build_index(MOVContext *mov, AVStream *st)
3721 {
3722     MOVStreamContext *sc = st->priv_data;
3723     int64_t current_offset;
3724     int64_t current_dts = 0;
3725     unsigned int stts_index = 0;
3726     unsigned int stsc_index = 0;
3727     unsigned int stss_index = 0;
3728     unsigned int stps_index = 0;
3729     unsigned int i, j;
3730     uint64_t stream_size = 0;
3731     MOVStts *ctts_data_old = sc->ctts_data;
3732     unsigned int ctts_count_old = sc->ctts_count;
3733
3734     if (sc->elst_count) {
3735         int i, edit_start_index = 0, multiple_edits = 0;
3736         int64_t empty_duration = 0; // empty duration of the first edit list entry
3737         int64_t start_time = 0; // start time of the media
3738
3739         for (i = 0; i < sc->elst_count; i++) {
3740             const MOVElst *e = &sc->elst_data[i];
3741             if (i == 0 && e->time == -1) {
3742                 /* if empty, the first entry is the start time of the stream
3743                  * relative to the presentation itself */
3744                 empty_duration = e->duration;
3745                 edit_start_index = 1;
3746             } else if (i == edit_start_index && e->time >= 0) {
3747                 start_time = e->time;
3748             } else {
3749                 multiple_edits = 1;
3750             }
3751         }
3752
3753         if (multiple_edits && !mov->advanced_editlist)
3754             av_log(mov->fc, AV_LOG_WARNING, "multiple edit list entries, "
3755                    "Use -advanced_editlist to correctly decode otherwise "
3756                    "a/v desync might occur\n");
3757
3758         /* adjust first dts according to edit list */
3759         if ((empty_duration || start_time) && mov->time_scale > 0) {
3760             if (empty_duration)
3761                 empty_duration = av_rescale(empty_duration, sc->time_scale, mov->time_scale);
3762             sc->time_offset = start_time - empty_duration;
3763             sc->min_corrected_pts = start_time;
3764             if (!mov->advanced_editlist)
3765                 current_dts = -sc->time_offset;
3766         }
3767
3768         if (!multiple_edits && !mov->advanced_editlist &&
3769             st->codecpar->codec_id == AV_CODEC_ID_AAC && start_time > 0)
3770             sc->start_pad = start_time;
3771     }
3772
3773     /* only use old uncompressed audio chunk demuxing when stts specifies it */
3774     if (!(st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO &&
3775           sc->stts_count == 1 && sc->stts_data[0].duration == 1)) {
3776         unsigned int current_sample = 0;
3777         unsigned int stts_sample = 0;
3778         unsigned int sample_size;
3779         unsigned int distance = 0;
3780         unsigned int rap_group_index = 0;
3781         unsigned int rap_group_sample = 0;
3782         int64_t last_dts = 0;
3783         int64_t dts_correction = 0;
3784         int rap_group_present = sc->rap_group_count && sc->rap_group;
3785         int key_off = (sc->keyframe_count && sc->keyframes[0] > 0) || (sc->stps_count && sc->stps_data[0] > 0);
3786
3787         current_dts -= sc->dts_shift;
3788         last_dts     = current_dts;
3789
3790         if (!sc->sample_count || st->nb_index_entries)
3791             return;
3792         if (sc->sample_count >= UINT_MAX / sizeof(*st->index_entries) - st->nb_index_entries)
3793             return;
3794         if (av_reallocp_array(&st->index_entries,
3795                               st->nb_index_entries + sc->sample_count,
3796                               sizeof(*st->index_entries)) < 0) {
3797             st->nb_index_entries = 0;
3798             return;
3799         }
3800         st->index_entries_allocated_size = (st->nb_index_entries + sc->sample_count) * sizeof(*st->index_entries);
3801
3802         if (ctts_data_old) {
3803             // Expand ctts entries such that we have a 1-1 mapping with samples
3804             if (sc->sample_count >= UINT_MAX / sizeof(*sc->ctts_data))
3805                 return;
3806             sc->ctts_count = 0;
3807             sc->ctts_allocated_size = 0;
3808             sc->ctts_data = av_fast_realloc(NULL, &sc->ctts_allocated_size,
3809                                     sc->sample_count * sizeof(*sc->ctts_data));
3810             if (!sc->ctts_data) {
3811                 av_free(ctts_data_old);
3812                 return;
3813             }
3814
3815             memset((uint8_t*)(sc->ctts_data), 0, sc->ctts_allocated_size);
3816
3817             for (i = 0; i < ctts_count_old &&
3818                         sc->ctts_count < sc->sample_count; i++)
3819                 for (j = 0; j < ctts_data_old[i].count &&
3820                             sc->ctts_count < sc->sample_count; j++)
3821                     add_ctts_entry(&sc->ctts_data, &sc->ctts_count,
3822                                    &sc->ctts_allocated_size, 1,
3823                                    ctts_data_old[i].duration);
3824             av_free(ctts_data_old);
3825         }
3826
3827         for (i = 0; i < sc->chunk_count; i++) {
3828             int64_t next_offset = i+1 < sc->chunk_count ? sc->chunk_offsets[i+1] : INT64_MAX;
3829             current_offset = sc->chunk_offsets[i];
3830             while (mov_stsc_index_valid(stsc_index, sc->stsc_count) &&
3831                 i + 1 == sc->stsc_data[stsc_index + 1].first)
3832                 stsc_index++;
3833
3834             if (next_offset > current_offset && sc->sample_size>0 && sc->sample_size < sc->stsz_sample_size &&
3835                 sc->stsc_data[stsc_index].count * (int64_t)sc->stsz_sample_size > next_offset - current_offset) {
3836                 av_log(mov->fc, AV_LOG_WARNING, "STSZ sample size %d invalid (too large), ignoring\n", sc->stsz_sample_size);
3837                 sc->stsz_sample_size = sc->sample_size;
3838             }
3839             if (sc->stsz_sample_size>0 && sc->stsz_sample_size < sc->sample_size) {
3840                 av_log(mov->fc, AV_LOG_WARNING, "STSZ sample size %d invalid (too small), ignoring\n", sc->stsz_sample_size);
3841                 sc->stsz_sample_size = sc->sample_size;
3842             }
3843
3844             for (j = 0; j < sc->stsc_data[stsc_index].count; j++) {
3845                 int keyframe = 0;
3846                 if (current_sample >= sc->sample_count) {
3847                     av_log(mov->fc, AV_LOG_ERROR, "wrong sample count\n");
3848                     return;
3849                 }
3850
3851                 if (!sc->keyframe_absent && (!sc->keyframe_count || current_sample+key_off == sc->keyframes[stss_index])) {
3852                     keyframe = 1;
3853                     if (stss_index + 1 < sc->keyframe_count)
3854                         stss_index++;
3855                 } else if (sc->stps_count && current_sample+key_off == sc->stps_data[stps_index]) {
3856                     keyframe = 1;
3857                     if (stps_index + 1 < sc->stps_count)
3858                         stps_index++;
3859                 }
3860                 if (rap_group_present && rap_group_index < sc->rap_group_count) {
3861                     if (sc->rap_group[rap_group_index].index > 0)
3862                         keyframe = 1;
3863                     if (++rap_group_sample == sc->rap_group[rap_group_index].count) {
3864                         rap_group_sample = 0;
3865                         rap_group_index++;
3866                     }
3867                 }
3868                 if (sc->keyframe_absent
3869                     && !sc->stps_count
3870                     && !rap_group_present
3871                     && (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO || (i==0 && j==0)))
3872                      keyframe = 1;
3873                 if (keyframe)
3874                     distance = 0;
3875                 sample_size = sc->stsz_sample_size > 0 ? sc->stsz_sample_size : sc->sample_sizes[current_sample];
3876                 if (sc->pseudo_stream_id == -1 ||
3877                    sc->stsc_data[stsc_index].id - 1 == sc->pseudo_stream_id) {
3878                     AVIndexEntry *e;
3879                     if (sample_size > 0x3FFFFFFF) {
3880                         av_log(mov->fc, AV_LOG_ERROR, "Sample size %u is too large\n", sample_size);
3881                         return;
3882                     }
3883                     e = &st->index_entries[st->nb_index_entries++];
3884                     e->pos = current_offset;
3885                     e->timestamp = current_dts;
3886                     e->size = sample_size;
3887                     e->min_distance = distance;
3888                     e->flags = keyframe ? AVINDEX_KEYFRAME : 0;
3889                     av_log(mov->fc, AV_LOG_TRACE, "AVIndex stream %d, sample %u, offset %"PRIx64", dts %"PRId64", "
3890                             "size %u, distance %u, keyframe %d\n", st->index, current_sample,
3891                             current_offset, current_dts, sample_size, distance, keyframe);
3892                     if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO && st->nb_index_entries < 100)
3893                         ff_rfps_add_frame(mov->fc, st, current_dts);
3894                 }
3895
3896                 current_offset += sample_size;
3897                 stream_size += sample_size;
3898
3899                 /* A negative sample duration is invalid based on the spec,
3900                  * but some samples need it to correct the DTS. */
3901                 if (sc->stts_data[stts_index].duration < 0) {
3902                     av_log(mov->fc, AV_LOG_WARNING,
3903                            "Invalid SampleDelta %d in STTS, at %d st:%d\n",
3904                            sc->stts_data[stts_index].duration, stts_index,
3905                            st->index);
3906                     dts_correction += sc->stts_data[stts_index].duration - 1;
3907                     sc->stts_data[stts_index].duration = 1;
3908                 }
3909                 current_dts += sc->stts_data[stts_index].duration;
3910                 if (!dts_correction || current_dts + dts_correction > last_dts) {
3911                     current_dts += dts_correction;
3912                     dts_correction = 0;
3913                 } else {
3914                     /* Avoid creating non-monotonous DTS */
3915                     dts_correction += current_dts - last_dts - 1;
3916                     current_dts = last_dts + 1;
3917                 }
3918                 last_dts = current_dts;
3919                 distance++;
3920                 stts_sample++;
3921                 current_sample++;
3922                 if (stts_index + 1 < sc->stts_count && stts_sample == sc->stts_data[stts_index].count) {
3923                     stts_sample = 0;
3924                     stts_index++;
3925                 }
3926             }
3927         }
3928         if (st->duration > 0)
3929             st->codecpar->bit_rate = stream_size*8*sc->time_scale/st->duration;
3930     } else {
3931         unsigned chunk_samples, total = 0;
3932
3933         if (!sc->chunk_count)
3934             return;
3935
3936         // compute total chunk count
3937         for (i = 0; i < sc->stsc_count; i++) {
3938             unsigned count, chunk_count;
3939
3940             chunk_samples = sc->stsc_data[i].count;
3941             if (i != sc->stsc_count - 1 &&
3942                 sc->samples_per_frame && chunk_samples % sc->samples_per_frame) {
3943                 av_log(mov->fc, AV_LOG_ERROR, "error unaligned chunk\n");
3944                 return;
3945             }
3946
3947             if (sc->samples_per_frame >= 160) { // gsm
3948                 count = chunk_samples / sc->samples_per_frame;
3949             } else if (sc->samples_per_frame > 1) {
3950                 unsigned samples = (1024/sc->samples_per_frame)*sc->samples_per_frame;
3951                 count = (chunk_samples+samples-1) / samples;
3952             } else {
3953                 count = (chunk_samples+1023) / 1024;
3954             }
3955
3956             if (mov_stsc_index_valid(i, sc->stsc_count))
3957                 chunk_count = sc->stsc_data[i+1].first - sc->stsc_data[i].first;
3958             else
3959                 chunk_count = sc->chunk_count - (sc->stsc_data[i].first - 1);
3960             total += chunk_count * count;
3961         }
3962
3963         av_log(mov->fc, AV_LOG_TRACE, "chunk count %u\n", total);
3964         if (total >= UINT_MAX / sizeof(*st->index_entries) - st->nb_index_entries)
3965             return;
3966         if (av_reallocp_array(&st->index_entries,
3967                               st->nb_index_entries + total,
3968                               sizeof(*st->index_entries)) < 0) {
3969             st->nb_index_entries = 0;
3970             return;
3971         }
3972         st->index_entries_allocated_size = (st->nb_index_entries + total) * sizeof(*st->index_entries);
3973
3974         // populate index
3975         for (i = 0; i < sc->chunk_count; i++) {
3976             current_offset = sc->chunk_offsets[i];
3977             if (mov_stsc_index_valid(stsc_index, sc->stsc_count) &&
3978                 i + 1 == sc->stsc_data[stsc_index + 1].first)
3979                 stsc_index++;
3980             chunk_samples = sc->stsc_data[stsc_index].count;
3981
3982             while (chunk_samples > 0) {
3983                 AVIndexEntry *e;
3984                 unsigned size, samples;
3985
3986                 if (sc->samples_per_frame > 1 && !sc->bytes_per_frame) {
3987                     avpriv_request_sample(mov->fc,
3988                            "Zero bytes per frame, but %d samples per frame",
3989                            sc->samples_per_frame);
3990                     return;
3991                 }
3992
3993                 if (sc->samples_per_frame >= 160) { // gsm
3994                     samples = sc->samples_per_frame;
3995                     size = sc->bytes_per_frame;
3996                 } else {
3997                     if (sc->samples_per_frame > 1) {
3998                         samples = FFMIN((1024 / sc->samples_per_frame)*
3999                                         sc->samples_per_frame, chunk_samples);
4000                         size = (samples / sc->samples_per_frame) * sc->bytes_per_frame;
4001                     } else {
4002                         samples = FFMIN(1024, chunk_samples);
4003                         size = samples * sc->sample_size;
4004                     }
4005                 }
4006
4007                 if (st->nb_index_entries >= total) {
4008                     av_log(mov->fc, AV_LOG_ERROR, "wrong chunk count %u\n", total);
4009                     return;
4010                 }
4011                 if (size > 0x3FFFFFFF) {
4012                     av_log(mov->fc, AV_LOG_ERROR, "Sample size %u is too large\n", size);
4013                     return;
4014                 }
4015                 e = &st->index_entries[st->nb_index_entries++];
4016                 e->pos = current_offset;
4017                 e->timestamp = current_dts;
4018                 e->size = size;
4019                 e->min_distance = 0;
4020                 e->flags = AVINDEX_KEYFRAME;
4021                 av_log(mov->fc, AV_LOG_TRACE, "AVIndex stream %d, chunk %u, offset %"PRIx64", dts %"PRId64", "
4022                        "size %u, duration %u\n", st->index, i, current_offset, current_dts,
4023                        size, samples);
4024
4025                 current_offset += size;
4026                 current_dts += samples;
4027                 chunk_samples -= samples;
4028             }
4029         }
4030     }
4031
4032     if (!mov->ignore_editlist && mov->advanced_editlist) {
4033         // Fix index according to edit lists.
4034         mov_fix_index(mov, st);
4035     }
4036
4037     // Update start time of the stream.
4038     if (st->start_time == AV_NOPTS_VALUE && st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO && st->nb_index_entries > 0) {
4039         st->start_time = st->index_entries[0].timestamp + sc->dts_shift;
4040         if (sc->ctts_data) {
4041             st->start_time += sc->ctts_data[0].duration;
4042         }
4043     }
4044
4045     mov_estimate_video_delay(mov, st);
4046 }
4047
4048 static int test_same_origin(const char *src, const char *ref) {
4049     char src_proto[64];
4050     char ref_proto[64];
4051     char src_auth[256];
4052     char ref_auth[256];
4053     char src_host[256];
4054     char ref_host[256];
4055     int src_port=-1;
4056     int ref_port=-1;
4057
4058     av_url_split(src_proto, sizeof(src_proto), src_auth, sizeof(src_auth), src_host, sizeof(src_host), &src_port, NULL, 0, src);
4059     av_url_split(ref_proto, sizeof(ref_proto), ref_auth, sizeof(ref_auth), ref_host, sizeof(ref_host), &ref_port, NULL, 0, ref);
4060
4061     if (strlen(src) == 0) {
4062         return -1;
4063     } else if (strlen(src_auth) + 1 >= sizeof(src_auth) ||
4064         strlen(ref_auth) + 1 >= sizeof(ref_auth) ||
4065         strlen(src_host) + 1 >= sizeof(src_host) ||
4066         strlen(ref_host) + 1 >= sizeof(ref_host)) {
4067         return 0;
4068     } else if (strcmp(src_proto, ref_proto) ||
4069                strcmp(src_auth, ref_auth) ||
4070                strcmp(src_host, ref_host) ||
4071                src_port != ref_port) {
4072         return 0;
4073     } else
4074         return 1;
4075 }
4076
4077 static int mov_open_dref(MOVContext *c, AVIOContext **pb, const char *src, MOVDref *ref)
4078 {
4079     /* try relative path, we do not try the absolute because it can leak information about our
4080        system to an attacker */
4081     if (ref->nlvl_to > 0 && ref->nlvl_from > 0) {
4082         char filename[1025];
4083         const char *src_path;
4084         int i, l;
4085
4086         /* find a source dir */
4087         src_path = strrchr(src, '/');
4088         if (src_path)
4089             src_path++;
4090         else
4091             src_path = src;
4092
4093         /* find a next level down to target */
4094         for (i = 0, l = strlen(ref->path) - 1; l >= 0; l--)
4095             if (ref->path[l] == '/') {
4096                 if (i == ref->nlvl_to - 1)
4097                     break;
4098                 else
4099                     i++;
4100             }
4101
4102         /* compose filename if next level down to target was found */
4103         if (i == ref->nlvl_to - 1 && src_path - src  < sizeof(filename)) {
4104             memcpy(filename, src, src_path - src);
4105             filename[src_path - src] = 0;
4106
4107             for (i = 1; i < ref->nlvl_from; i++)
4108                 av_strlcat(filename, "../", sizeof(filename));
4109
4110             av_strlcat(filename, ref->path + l + 1, sizeof(filename));
4111             if (!c->use_absolute_path) {
4112                 int same_origin = test_same_origin(src, filename);
4113
4114                 if (!same_origin) {
4115                     av_log(c->fc, AV_LOG_ERROR,
4116                         "Reference with mismatching origin, %s not tried for security reasons, "
4117                         "set demuxer option use_absolute_path to allow it anyway\n",
4118                         ref->path);
4119                     return AVERROR(ENOENT);
4120                 }
4121
4122                 if(strstr(ref->path + l + 1, "..") ||
4123                    strstr(ref->path + l + 1, ":") ||
4124                    (ref->nlvl_from > 1 && same_origin < 0) ||
4125                    (filename[0] == '/' && src_path == src))
4126                     return AVERROR(ENOENT);
4127             }
4128
4129             if (strlen(filename) + 1 == sizeof(filename))
4130                 return AVERROR(ENOENT);
4131             if (!c->fc->io_open(c->fc, pb, filename, AVIO_FLAG_READ, NULL))
4132                 return 0;
4133         }
4134     } else if (c->use_absolute_path) {
4135         av_log(c->fc, AV_LOG_WARNING, "Using absolute path on user request, "
4136                "this is a possible security issue\n");
4137         if (!c->fc->io_open(c->fc, pb, ref->path, AVIO_FLAG_READ, NULL))
4138             return 0;
4139     } else {
4140         av_log(c->fc, AV_LOG_ERROR,
4141                "Absolute path %s not tried for security reasons, "
4142                "set demuxer option use_absolute_path to allow absolute paths\n",
4143                ref->path);
4144     }
4145
4146     return AVERROR(ENOENT);
4147 }
4148
4149 static void fix_timescale(MOVContext *c, MOVStreamContext *sc)
4150 {
4151     if (sc->time_scale <= 0) {
4152         av_log(c->fc, AV_LOG_WARNING, "stream %d, timescale not set\n", sc->ffindex);
4153         sc->time_scale = c->time_scale;
4154         if (sc->time_scale <= 0)
4155             sc->time_scale = 1;
4156     }
4157 }
4158
4159 static int mov_read_trak(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4160 {
4161     AVStream *st;
4162     MOVStreamContext *sc;
4163     int ret;
4164
4165     st = avformat_new_stream(c->fc, NULL);
4166     if (!st) return AVERROR(ENOMEM);
4167     st->id = -1;
4168     sc = av_mallocz(sizeof(MOVStreamContext));
4169     if (!sc) return AVERROR(ENOMEM);
4170
4171     st->priv_data = sc;
4172     st->codecpar->codec_type = AVMEDIA_TYPE_DATA;
4173     sc->ffindex = st->index;
4174     c->trak_index = st->index;
4175
4176     if ((ret = mov_read_default(c, pb, atom)) < 0)
4177         return ret;
4178
4179     c->trak_index = -1;
4180
4181     // Here stsc refers to a chunk not described in stco. This is technically invalid,
4182     // but we can overlook it (clearing stsc) whenever stts_count == 0 (indicating no samples).
4183     if (!sc->chunk_count && !sc->stts_count && sc->stsc_count) {
4184         sc->stsc_count = 0;
4185         av_freep(&sc->stsc_data);
4186     }
4187
4188     /* sanity checks */
4189     if ((sc->chunk_count && (!sc->stts_count || !sc->stsc_count ||
4190                             (!sc->sample_size && !sc->sample_count))) ||
4191         (!sc->chunk_count && sc->sample_count)) {
4192         av_log(c->fc, AV_LOG_ERROR, "stream %d, missing mandatory atoms, broken header\n",
4193                st->index);
4194         return 0;
4195     }
4196     if (sc->stsc_count && sc->stsc_data[ sc->stsc_count - 1 ].first > sc->chunk_count) {
4197         av_log(c->fc, AV_LOG_ERROR, "stream %d, contradictionary STSC and STCO\n",
4198                st->index);
4199         return AVERROR_INVALIDDATA;
4200     }
4201
4202     fix_timescale(c, sc);
4203
4204     avpriv_set_pts_info(st, 64, 1, sc->time_scale);
4205
4206     mov_build_index(c, st);
4207
4208     if (sc->dref_id-1 < sc->drefs_count && sc->drefs[sc->dref_id-1].path) {
4209         MOVDref *dref = &sc->drefs[sc->dref_id - 1];
4210         if (c->enable_drefs) {
4211             if (mov_open_dref(c, &sc->pb, c->fc->url, dref) < 0)
4212                 av_log(c->fc, AV_LOG_ERROR,
4213                        "stream %d, error opening alias: path='%s', dir='%s', "
4214                        "filename='%s', volume='%s', nlvl_from=%d, nlvl_to=%d\n",
4215                        st->index, dref->path, dref->dir, dref->filename,
4216                        dref->volume, dref->nlvl_from, dref->nlvl_to);
4217         } else {
4218             av_log(c->fc, AV_LOG_WARNING,
4219                    "Skipped opening external track: "
4220                    "stream %d, alias: path='%s', dir='%s', "
4221                    "filename='%s', volume='%s', nlvl_from=%d, nlvl_to=%d."
4222                    "Set enable_drefs to allow this.\n",
4223                    st->index, dref->path, dref->dir, dref->filename,
4224                    dref->volume, dref->nlvl_from, dref->nlvl_to);
4225         }
4226     } else {
4227         sc->pb = c->fc->pb;
4228         sc->pb_is_copied = 1;
4229     }
4230
4231     if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {
4232         if (!st->sample_aspect_ratio.num && st->codecpar->width && st->codecpar->height &&
4233             sc->height && sc->width &&
4234             (st->codecpar->width != sc->width || st->codecpar->height != sc->height)) {
4235             st->sample_aspect_ratio = av_d2q(((double)st->codecpar->height * sc->width) /
4236                                              ((double)st->codecpar->width * sc->height), INT_MAX);
4237         }
4238
4239 #if FF_API_R_FRAME_RATE
4240         if (sc->stts_count == 1 || (sc->stts_count == 2 && sc->stts_data[1].count == 1))
4241             av_reduce(&st->r_frame_rate.num, &st->r_frame_rate.den,
4242                       sc->time_scale, sc->stts_data[0].duration, INT_MAX);
4243 #endif
4244     }
4245
4246     // done for ai5q, ai52, ai55, ai1q, ai12 and ai15.
4247     if (!st->codecpar->extradata_size && st->codecpar->codec_id == AV_CODEC_ID_H264 &&
4248         TAG_IS_AVCI(st->codecpar->codec_tag)) {
4249         ret = ff_generate_avci_extradata(st);
4250         if (ret < 0)
4251             return ret;
4252     }
4253
4254     switch (st->codecpar->codec_id) {
4255 #if CONFIG_H261_DECODER
4256     case AV_CODEC_ID_H261:
4257 #endif
4258 #if CONFIG_H263_DECODER
4259     case AV_CODEC_ID_H263:
4260 #endif
4261 #if CONFIG_MPEG4_DECODER
4262     case AV_CODEC_ID_MPEG4:
4263 #endif
4264         st->codecpar->width = 0; /* let decoder init width/height */
4265         st->codecpar->height= 0;
4266         break;
4267     }
4268
4269     // If the duration of the mp3 packets is not constant, then they could need a parser
4270     if (st->codecpar->codec_id == AV_CODEC_ID_MP3
4271         && sc->stts_count > 3
4272         && sc->stts_count*10 > st->nb_frames
4273         && sc->time_scale == st->codecpar->sample_rate) {
4274             st->need_parsing = AVSTREAM_PARSE_FULL;
4275     }
4276     /* Do not need those anymore. */
4277     av_freep(&sc->chunk_offsets);
4278     av_freep(&sc->sample_sizes);
4279     av_freep(&sc->keyframes);
4280     av_freep(&sc->stts_data);
4281     av_freep(&sc->stps_data);
4282     av_freep(&sc->elst_data);
4283     av_freep(&sc->rap_group);
4284
4285     return 0;
4286 }
4287
4288 static int mov_read_ilst(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4289 {
4290     int ret;
4291     c->itunes_metadata = 1;
4292     ret = mov_read_default(c, pb, atom);
4293     c->itunes_metadata = 0;
4294     return ret;
4295 }
4296
4297 static int mov_read_keys(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4298 {
4299     uint32_t count;
4300     uint32_t i;
4301
4302     if (atom.size < 8)
4303         return 0;
4304
4305     avio_skip(pb, 4);
4306     count = avio_rb32(pb);
4307     if (count > UINT_MAX / sizeof(*c->meta_keys) - 1) {
4308         av_log(c->fc, AV_LOG_ERROR,
4309                "The 'keys' atom with the invalid key count: %"PRIu32"\n", count);
4310         return AVERROR_INVALIDDATA;
4311     }
4312
4313     c->meta_keys_count = count + 1;
4314     c->meta_keys = av_mallocz(c->meta_keys_count * sizeof(*c->meta_keys));
4315     if (!c->meta_keys)
4316         return AVERROR(ENOMEM);
4317
4318     for (i = 1; i <= count; ++i) {
4319         uint32_t key_size = avio_rb32(pb);
4320         uint32_t type = avio_rl32(pb);
4321         if (key_size < 8) {
4322             av_log(c->fc, AV_LOG_ERROR,
4323                    "The key# %"PRIu32" in meta has invalid size:"
4324                    "%"PRIu32"\n", i, key_size);
4325             return AVERROR_INVALIDDATA;
4326         }
4327         key_size -= 8;
4328         if (type != MKTAG('m','d','t','a')) {
4329             avio_skip(pb, key_size);
4330         }
4331         c->meta_keys[i] = av_mallocz(key_size + 1);
4332         if (!c->meta_keys[i])
4333             return AVERROR(ENOMEM);
4334         avio_read(pb, c->meta_keys[i], key_size);
4335     }
4336
4337     return 0;
4338 }
4339
4340 static int mov_read_custom(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4341 {
4342     int64_t end = avio_tell(pb) + atom.size;
4343     uint8_t *key = NULL, *val = NULL, *mean = NULL;
4344     int i;
4345     int ret = 0;
4346     AVStream *st;
4347     MOVStreamContext *sc;
4348
4349     if (c->fc->nb_streams < 1)
4350         return 0;
4351     st = c->fc->streams[c->fc->nb_streams-1];
4352     sc = st->priv_data;
4353
4354     for (i = 0; i < 3; i++) {
4355         uint8_t **p;
4356         uint32_t len, tag;
4357
4358         if (end - avio_tell(pb) <= 12)
4359             break;
4360
4361         len = avio_rb32(pb);
4362         tag = avio_rl32(pb);
4363         avio_skip(pb, 4); // flags
4364
4365         if (len < 12 || len - 12 > end - avio_tell(pb))
4366             break;
4367         len -= 12;
4368
4369         if (tag == MKTAG('m', 'e', 'a', 'n'))
4370             p = &mean;
4371         else if (tag == MKTAG('n', 'a', 'm', 'e'))
4372             p = &key;
4373         else if (tag == MKTAG('d', 'a', 't', 'a') && len > 4) {
4374             avio_skip(pb, 4);
4375             len -= 4;
4376             p = &val;
4377         } else
4378             break;
4379
4380         *p = av_malloc(len + 1);
4381         if (!*p) {
4382             ret = AVERROR(ENOMEM);
4383             break;
4384         }
4385         ret = ffio_read_size(pb, *p, len);
4386         if (ret < 0) {
4387             av_freep(p);
4388             break;
4389         }
4390         (*p)[len] = 0;
4391     }
4392
4393     if (mean && key && val) {
4394         if (strcmp(key, "iTunSMPB") == 0) {
4395             int priming, remainder, samples;
4396             if(sscanf(val, "%*X %X %X %X", &priming, &remainder, &samples) == 3){
4397                 if(priming>0 && priming<16384)
4398                     sc->start_pad = priming;
4399             }
4400         }
4401         if (strcmp(key, "cdec") != 0) {
4402             av_dict_set(&c->fc->metadata, key, val,
4403                         AV_DICT_DONT_STRDUP_KEY | AV_DICT_DONT_STRDUP_VAL);
4404             key = val = NULL;
4405         }
4406     } else {
4407         av_log(c->fc, AV_LOG_VERBOSE,
4408                "Unhandled or malformed custom metadata of size %"PRId64"\n", atom.size);
4409     }
4410
4411     avio_seek(pb, end, SEEK_SET);
4412     av_freep(&key);
4413     av_freep(&val);
4414     av_freep(&mean);
4415     return ret;
4416 }
4417
4418 static int mov_read_meta(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4419 {
4420     while (atom.size > 8) {
4421         uint32_t tag = avio_rl32(pb);
4422         atom.size -= 4;
4423         if (tag == MKTAG('h','d','l','r')) {
4424             avio_seek(pb, -8, SEEK_CUR);
4425             atom.size += 8;
4426             return mov_read_default(c, pb, atom);
4427         }
4428     }
4429     return 0;
4430 }
4431
4432 // return 1 when matrix is identity, 0 otherwise
4433 #define IS_MATRIX_IDENT(matrix)            \
4434     ( (matrix)[0][0] == (1 << 16) &&       \
4435       (matrix)[1][1] == (1 << 16) &&       \
4436       (matrix)[2][2] == (1 << 30) &&       \
4437      !(matrix)[0][1] && !(matrix)[0][2] && \
4438      !(matrix)[1][0] && !(matrix)[1][2] && \
4439      !(matrix)[2][0] && !(matrix)[2][1])
4440
4441 static int mov_read_tkhd(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4442 {
4443     int i, j, e;
4444     int width;
4445     int height;
4446     int display_matrix[3][3];
4447     int res_display_matrix[3][3] = { { 0 } };
4448     AVStream *st;
4449     MOVStreamContext *sc;
4450     int version;
4451     int flags;
4452
4453     if (c->fc->nb_streams < 1)
4454         return 0;
4455     st = c->fc->streams[c->fc->nb_streams-1];
4456     sc = st->priv_data;
4457
4458     // Each stream (trak) should have exactly 1 tkhd. This catches bad files and
4459     // avoids corrupting AVStreams mapped to an earlier tkhd.
4460     if (st->id != -1)
4461         return AVERROR_INVALIDDATA;
4462
4463     version = avio_r8(pb);
4464     flags = avio_rb24(pb);
4465     st->disposition |= (flags & MOV_TKHD_FLAG_ENABLED) ? AV_DISPOSITION_DEFAULT : 0;
4466
4467     if (version == 1) {
4468         avio_rb64(pb);
4469         avio_rb64(pb);
4470     } else {
4471         avio_rb32(pb); /* creation time */
4472         avio_rb32(pb); /* modification time */
4473     }
4474     st->id = (int)avio_rb32(pb); /* track id (NOT 0 !)*/
4475     avio_rb32(pb); /* reserved */
4476
4477     /* highlevel (considering edits) duration in movie timebase */
4478     (version == 1) ? avio_rb64(pb) : avio_rb32(pb);
4479     avio_rb32(pb); /* reserved */
4480     avio_rb32(pb); /* reserved */
4481
4482     avio_rb16(pb); /* layer */
4483     avio_rb16(pb); /* alternate group */
4484     avio_rb16(pb); /* volume */
4485     avio_rb16(pb); /* reserved */
4486
4487     //read in the display matrix (outlined in ISO 14496-12, Section 6.2.2)
4488     // they're kept in fixed point format through all calculations
4489     // save u,v,z to store the whole matrix in the AV_PKT_DATA_DISPLAYMATRIX
4490     // side data, but the scale factor is not needed to calculate aspect ratio
4491     for (i = 0; i < 3; i++) {
4492         display_matrix[i][0] = avio_rb32(pb);   // 16.16 fixed point
4493         display_matrix[i][1] = avio_rb32(pb);   // 16.16 fixed point
4494         display_matrix[i][2] = avio_rb32(pb);   //  2.30 fixed point
4495     }
4496
4497     width = avio_rb32(pb);       // 16.16 fixed point track width
4498     height = avio_rb32(pb);      // 16.16 fixed point track height
4499     sc->width = width >> 16;
4500     sc->height = height >> 16;
4501
4502     // apply the moov display matrix (after the tkhd one)
4503     for (i = 0; i < 3; i++) {
4504         const int sh[3] = { 16, 16, 30 };
4505         for (j = 0; j < 3; j++) {
4506             for (e = 0; e < 3; e++) {
4507                 res_display_matrix[i][j] +=
4508                     ((int64_t) display_matrix[i][e] *
4509                      c->movie_display_matrix[e][j]) >> sh[e];
4510             }
4511         }
4512     }
4513
4514     // save the matrix when it is not the default identity
4515     if (!IS_MATRIX_IDENT(res_display_matrix)) {
4516         double rotate;
4517
4518         av_freep(&sc->display_matrix);
4519         sc->display_matrix = av_malloc(sizeof(int32_t) * 9);
4520         if (!sc->display_matrix)
4521             return AVERROR(ENOMEM);
4522
4523         for (i = 0; i < 3; i++)
4524             for (j = 0; j < 3; j++)
4525                 sc->display_matrix[i * 3 + j] = res_display_matrix[i][j];
4526
4527 #if FF_API_OLD_ROTATE_API
4528         rotate = av_display_rotation_get(sc->display_matrix);
4529         if (!isnan(rotate)) {
4530             char rotate_buf[64];
4531             rotate = -rotate;
4532             if (rotate < 0) // for backward compatibility
4533                 rotate += 360;
4534             snprintf(rotate_buf, sizeof(rotate_buf), "%g", rotate);
4535             av_dict_set(&st->metadata, "rotate", rotate_buf, 0);
4536         }
4537 #endif
4538     }
4539
4540     // transform the display width/height according to the matrix
4541     // to keep the same scale, use [width height 1<<16]
4542     if (width && height && sc->display_matrix) {
4543         double disp_transform[2];
4544
4545         for (i = 0; i < 2; i++)
4546             disp_transform[i] = hypot(sc->display_matrix[0 + i],
4547                                       sc->display_matrix[3 + i]);
4548
4549         if (disp_transform[0] > 0       && disp_transform[1] > 0 &&
4550             disp_transform[0] < (1<<24) && disp_transform[1] < (1<<24) &&
4551             fabs((disp_transform[0] / disp_transform[1]) - 1.0) > 0.01)
4552             st->sample_aspect_ratio = av_d2q(
4553                 disp_transform[0] / disp_transform[1],
4554                 INT_MAX);
4555     }
4556     return 0;
4557 }
4558
4559 static int mov_read_tfhd(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4560 {
4561     MOVFragment *frag = &c->fragment;
4562     MOVTrackExt *trex = NULL;
4563     int flags, track_id, i;
4564
4565     c->fragment.found_tfhd = 1;
4566
4567     avio_r8(pb); /* version */
4568     flags = avio_rb24(pb);
4569
4570     track_id = avio_rb32(pb);
4571     if (!track_id)
4572         return AVERROR_INVALIDDATA;
4573     for (i = 0; i < c->trex_count; i++)
4574         if (c->trex_data[i].track_id == track_id) {
4575             trex = &c->trex_data[i];
4576             break;
4577         }
4578     if (!trex) {
4579         av_log(c->fc, AV_LOG_WARNING, "could not find corresponding trex (id %u)\n", track_id);
4580         return 0;
4581     }
4582     frag->track_id = track_id;
4583     set_frag_stream(&c->frag_index, track_id);
4584
4585     frag->base_data_offset = flags & MOV_TFHD_BASE_DATA_OFFSET ?
4586                              avio_rb64(pb) : flags & MOV_TFHD_DEFAULT_BASE_IS_MOOF ?
4587                              frag->moof_offset : frag->implicit_offset;
4588     frag->stsd_id  = flags & MOV_TFHD_STSD_ID ? avio_rb32(pb) : trex->stsd_id;
4589
4590     frag->duration = flags & MOV_TFHD_DEFAULT_DURATION ?
4591                      avio_rb32(pb) : trex->duration;
4592     frag->size     = flags & MOV_TFHD_DEFAULT_SIZE ?
4593                      avio_rb32(pb) : trex->size;
4594     frag->flags    = flags & MOV_TFHD_DEFAULT_FLAGS ?
4595                      avio_rb32(pb) : trex->flags;
4596     av_log(c->fc, AV_LOG_TRACE, "frag flags 0x%x\n", frag->flags);
4597
4598     return 0;
4599 }
4600
4601 static int mov_read_chap(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4602 {
4603     unsigned i, num;
4604     void *new_tracks;
4605
4606     num = atom.size / 4;
4607     if (!(new_tracks = av_malloc_array(num, sizeof(int))))
4608         return AVERROR(ENOMEM);
4609
4610     av_free(c->chapter_tracks);
4611     c->chapter_tracks = new_tracks;
4612     c->nb_chapter_tracks = num;
4613
4614     for (i = 0; i < num && !pb->eof_reached; i++)
4615         c->chapter_tracks[i] = avio_rb32(pb);
4616
4617     return 0;
4618 }
4619
4620 static int mov_read_trex(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4621 {
4622     MOVTrackExt *trex;
4623     int err;
4624
4625     if ((uint64_t)c->trex_count+1 >= UINT_MAX / sizeof(*c->trex_data))
4626         return AVERROR_INVALIDDATA;
4627     if ((err = av_reallocp_array(&c->trex_data, c->trex_count + 1,
4628                                  sizeof(*c->trex_data))) < 0) {
4629         c->trex_count = 0;
4630         return err;
4631     }
4632
4633     c->fc->duration = AV_NOPTS_VALUE; // the duration from mvhd is not representing the whole file when fragments are used.
4634
4635     trex = &c->trex_data[c->trex_count++];
4636     avio_r8(pb); /* version */
4637     avio_rb24(pb); /* flags */
4638     trex->track_id = avio_rb32(pb);
4639     trex->stsd_id  = avio_rb32(pb);
4640     trex->duration = avio_rb32(pb);
4641     trex->size     = avio_rb32(pb);
4642     trex->flags    = avio_rb32(pb);
4643     return 0;
4644 }
4645
4646 static int mov_read_tfdt(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4647 {
4648     MOVFragment *frag = &c->fragment;
4649     AVStream *st = NULL;
4650     MOVStreamContext *sc;
4651     int version, i;
4652     MOVFragmentStreamInfo * frag_stream_info;
4653     int64_t base_media_decode_time;
4654
4655     for (i = 0; i < c->fc->nb_streams; i++) {
4656         if (c->fc->streams[i]->id == frag->track_id) {
4657             st = c->fc->streams[i];
4658             break;
4659         }
4660     }
4661     if (!st) {
4662         av_log(c->fc, AV_LOG_WARNING, "could not find corresponding track id %u\n", frag->track_id);
4663         return 0;
4664     }
4665     sc = st->priv_data;
4666     if (sc->pseudo_stream_id + 1 != frag->stsd_id && sc->pseudo_stream_id != -1)
4667         return 0;
4668     version = avio_r8(pb);
4669     avio_rb24(pb); /* flags */
4670     if (version) {
4671         base_media_decode_time = avio_rb64(pb);
4672     } else {
4673         base_media_decode_time = avio_rb32(pb);
4674     }
4675
4676     frag_stream_info = get_current_frag_stream_info(&c->frag_index);
4677     if (frag_stream_info)
4678         frag_stream_info->tfdt_dts = base_media_decode_time;
4679     sc->track_end = base_media_decode_time;
4680
4681     return 0;
4682 }
4683
4684 static int mov_read_trun(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4685 {
4686     MOVFragment *frag = &c->fragment;
4687     AVStream *st = NULL;
4688     MOVStreamContext *sc;
4689     MOVStts *ctts_data;
4690     uint64_t offset;
4691     int64_t dts, pts = AV_NOPTS_VALUE;
4692     int data_offset = 0;
4693     unsigned entries, first_sample_flags = frag->flags;
4694     int flags, distance, i;
4695     int64_t prev_dts = AV_NOPTS_VALUE;
4696     int next_frag_index = -1, index_entry_pos;
4697     size_t requested_size;
4698     size_t old_ctts_allocated_size;
4699     AVIndexEntry *new_entries;
4700     MOVFragmentStreamInfo * frag_stream_info;
4701
4702     if (!frag->found_tfhd) {
4703         av_log(c->fc, AV_LOG_ERROR, "trun track id unknown, no tfhd was found\n");
4704         return AVERROR_INVALIDDATA;
4705     }
4706
4707     for (i = 0; i < c->fc->nb_streams; i++) {
4708         if (c->fc->streams[i]->id == frag->track_id) {
4709             st = c->fc->streams[i];
4710             break;
4711         }
4712     }
4713     if (!st) {
4714         av_log(c->fc, AV_LOG_WARNING, "could not find corresponding track id %u\n", frag->track_id);
4715         return 0;
4716     }
4717     sc = st->priv_data;
4718     if (sc->pseudo_stream_id+1 != frag->stsd_id && sc->pseudo_stream_id != -1)
4719         return 0;
4720
4721     // Find the next frag_index index that has a valid index_entry for
4722     // the current track_id.
4723     //
4724     // A valid index_entry means the trun for the fragment was read
4725     // and it's samples are in index_entries at the given position.
4726     // New index entries will be inserted before the index_entry found.
4727     index_entry_pos = st->nb_index_entries;
4728     for (i = c->frag_index.current + 1; i < c->frag_index.nb_items; i++) {
4729         frag_stream_info = get_frag_stream_info(&c->frag_index, i, frag->track_id);
4730         if (frag_stream_info && frag_stream_info->index_entry >= 0) {
4731             next_frag_index = i;
4732             index_entry_pos = frag_stream_info->index_entry;
4733             break;
4734         }
4735     }
4736     av_assert0(index_entry_pos <= st->nb_index_entries);
4737
4738     avio_r8(pb); /* version */
4739     flags = avio_rb24(pb);
4740     entries = avio_rb32(pb);
4741     av_log(c->fc, AV_LOG_TRACE, "flags 0x%x entries %u\n", flags, entries);
4742
4743     if ((uint64_t)entries+sc->ctts_count >= UINT_MAX/sizeof(*sc->ctts_data))
4744         return AVERROR_INVALIDDATA;
4745     if (flags & MOV_TRUN_DATA_OFFSET)        data_offset        = avio_rb32(pb);
4746     if (flags & MOV_TRUN_FIRST_SAMPLE_FLAGS) first_sample_flags = avio_rb32(pb);
4747
4748     frag_stream_info = get_current_frag_stream_info(&c->frag_index);
4749     if (frag_stream_info)
4750     {
4751         if (frag_stream_info->first_tfra_pts != AV_NOPTS_VALUE &&
4752             c->use_mfra_for == FF_MOV_FLAG_MFRA_PTS) {
4753             pts = frag_stream_info->first_tfra_pts;
4754             av_log(c->fc, AV_LOG_DEBUG, "found mfra time %"PRId64
4755                     ", using it for pts\n", pts);
4756         } else if (frag_stream_info->sidx_pts != AV_NOPTS_VALUE) {
4757             // FIXME: sidx earliest_presentation_time is *PTS*, s.b.
4758             // pts = frag_stream_info->sidx_pts;
4759             dts = frag_stream_info->sidx_pts - sc->time_offset;
4760             av_log(c->fc, AV_LOG_DEBUG, "found sidx time %"PRId64
4761                     ", using it for pts\n", pts);
4762         } else if (frag_stream_info->tfdt_dts != AV_NOPTS_VALUE) {
4763             dts = frag_stream_info->tfdt_dts - sc->time_offset;
4764             av_log(c->fc, AV_LOG_DEBUG, "found tfdt time %"PRId64
4765                     ", using it for dts\n", dts);
4766         } else {
4767             dts = sc->track_end - sc->time_offset;
4768             av_log(c->fc, AV_LOG_DEBUG, "found track end time %"PRId64
4769                     ", using it for dts\n", dts);
4770         }
4771     } else {
4772         dts = sc->track_end - sc->time_offset;
4773         av_log(c->fc, AV_LOG_DEBUG, "found track end time %"PRId64
4774                 ", using it for dts\n", dts);
4775     }
4776     offset   = frag->base_data_offset + data_offset;
4777     distance = 0;
4778     av_log(c->fc, AV_LOG_TRACE, "first sample flags 0x%x\n", first_sample_flags);
4779
4780     // realloc space for new index entries
4781     if((uint64_t)st->nb_index_entries + entries >= UINT_MAX / sizeof(AVIndexEntry)) {
4782         entries = UINT_MAX / sizeof(AVIndexEntry) - st->nb_index_entries;
4783         av_log(c->fc, AV_LOG_ERROR, "Failed to add index entry\n");
4784     }
4785     if (entries <= 0)
4786         return -1;
4787
4788     requested_size = (st->nb_index_entries + entries) * sizeof(AVIndexEntry);
4789     new_entries = av_fast_realloc(st->index_entries,
4790                                   &st->index_entries_allocated_size,
4791                                   requested_size);
4792     if(!new_entries)
4793         return AVERROR(ENOMEM);
4794     st->index_entries= new_entries;
4795
4796     requested_size = (st->nb_index_entries + entries) * sizeof(*sc->ctts_data);
4797     old_ctts_allocated_size = sc->ctts_allocated_size;
4798     ctts_data = av_fast_realloc(sc->ctts_data, &sc->ctts_allocated_size,
4799                                 requested_size);
4800     if (!ctts_data)
4801         return AVERROR(ENOMEM);
4802     sc->ctts_data = ctts_data;
4803
4804     // In case there were samples without ctts entries, ensure they get
4805     // zero valued entries. This ensures clips which mix boxes with and
4806     // without ctts entries don't pickup uninitialized data.
4807     memset((uint8_t*)(sc->ctts_data) + old_ctts_allocated_size, 0,
4808            sc->ctts_allocated_size - old_ctts_allocated_size);
4809
4810     if (index_entry_pos < st->nb_index_entries) {
4811         // Make hole in index_entries and ctts_data for new samples
4812         memmove(st->index_entries + index_entry_pos + entries,
4813                 st->index_entries + index_entry_pos,
4814                 sizeof(*st->index_entries) *
4815                 (st->nb_index_entries - index_entry_pos));
4816         memmove(sc->ctts_data + index_entry_pos + entries,
4817                 sc->ctts_data + index_entry_pos,
4818                 sizeof(*sc->ctts_data) * (sc->ctts_count - index_entry_pos));
4819         if (index_entry_pos < sc->current_sample) {
4820             sc->current_sample += entries;
4821         }
4822     }
4823
4824     st->nb_index_entries += entries;
4825     sc->ctts_count = st->nb_index_entries;
4826
4827     // Record the index_entry position in frag_index of this fragment
4828     if (frag_stream_info)
4829         frag_stream_info->index_entry = index_entry_pos;
4830
4831     if (index_entry_pos > 0)
4832         prev_dts = st->index_entries[index_entry_pos-1].timestamp;
4833
4834     for (i = 0; i < entries && !pb->eof_reached; i++) {
4835         unsigned sample_size = frag->size;
4836         int sample_flags = i ? frag->flags : first_sample_flags;
4837         unsigned sample_duration = frag->duration;
4838         unsigned ctts_duration = 0;
4839         int keyframe = 0;
4840         int index_entry_flags = 0;
4841
4842         if (flags & MOV_TRUN_SAMPLE_DURATION) sample_duration = avio_rb32(pb);
4843         if (flags & MOV_TRUN_SAMPLE_SIZE)     sample_size     = avio_rb32(pb);
4844         if (flags & MOV_TRUN_SAMPLE_FLAGS)    sample_flags    = avio_rb32(pb);
4845         if (flags & MOV_TRUN_SAMPLE_CTS)      ctts_duration   = avio_rb32(pb);
4846
4847         mov_update_dts_shift(sc, ctts_duration);
4848         if (pts != AV_NOPTS_VALUE) {
4849             dts = pts - sc->dts_shift;
4850             if (flags & MOV_TRUN_SAMPLE_CTS) {
4851                 dts -= ctts_duration;
4852             } else {
4853                 dts -= sc->time_offset;
4854             }
4855             av_log(c->fc, AV_LOG_DEBUG,
4856                    "pts %"PRId64" calculated dts %"PRId64
4857                    " sc->dts_shift %d ctts.duration %d"
4858                    " sc->time_offset %"PRId64
4859                    " flags & MOV_TRUN_SAMPLE_CTS %d\n",
4860                    pts, dts,
4861                    sc->dts_shift, ctts_duration,
4862                    sc->time_offset, flags & MOV_TRUN_SAMPLE_CTS);
4863             pts = AV_NOPTS_VALUE;
4864         }
4865
4866         if (st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO)
4867             keyframe = 1;
4868         else
4869             keyframe =
4870                 !(sample_flags & (MOV_FRAG_SAMPLE_FLAG_IS_NON_SYNC |
4871                                   MOV_FRAG_SAMPLE_FLAG_DEPENDS_YES));
4872         if (keyframe) {
4873             distance = 0;
4874             index_entry_flags |= AVINDEX_KEYFRAME;
4875         }
4876         // Fragments can overlap in time.  Discard overlapping frames after
4877         // decoding.
4878         if (prev_dts >= dts)
4879             index_entry_flags |= AVINDEX_DISCARD_FRAME;
4880
4881         st->index_entries[index_entry_pos].pos = offset;
4882         st->index_entries[index_entry_pos].timestamp = dts;
4883         st->index_entries[index_entry_pos].size= sample_size;
4884         st->index_entries[index_entry_pos].min_distance= distance;
4885         st->index_entries[index_entry_pos].flags = index_entry_flags;
4886
4887         sc->ctts_data[index_entry_pos].count = 1;
4888         sc->ctts_data[index_entry_pos].duration = ctts_duration;
4889         index_entry_pos++;
4890
4891         av_log(c->fc, AV_LOG_TRACE, "AVIndex stream %d, sample %d, offset %"PRIx64", dts %"PRId64", "
4892                 "size %u, distance %d, keyframe %d\n", st->index,
4893                 index_entry_pos, offset, dts, sample_size, distance, keyframe);
4894         distance++;
4895         dts += sample_duration;
4896         offset += sample_size;
4897         sc->data_size += sample_size;
4898
4899         if (sample_duration <= INT64_MAX - sc->duration_for_fps &&
4900             1 <= INT_MAX - sc->nb_frames_for_fps
4901         ) {
4902             sc->duration_for_fps += sample_duration;
4903             sc->nb_frames_for_fps ++;
4904         }
4905     }
4906     if (i < entries) {
4907         // EOF found before reading all entries.  Fix the hole this would
4908         // leave in index_entries and ctts_data
4909         int gap = entries - i;
4910         memmove(st->index_entries + index_entry_pos,
4911                 st->index_entries + index_entry_pos + gap,
4912                 sizeof(*st->index_entries) *
4913                 (st->nb_index_entries - (index_entry_pos + gap)));
4914         memmove(sc->ctts_data + index_entry_pos,
4915                 sc->ctts_data + index_entry_pos + gap,
4916                 sizeof(*sc->ctts_data) *
4917                 (sc->ctts_count - (index_entry_pos + gap)));
4918
4919         st->nb_index_entries -= gap;
4920         sc->ctts_count -= gap;
4921         if (index_entry_pos < sc->current_sample) {
4922             sc->current_sample -= gap;
4923         }
4924         entries = i;
4925     }
4926
4927     // The end of this new fragment may overlap in time with the start
4928     // of the next fragment in index_entries. Mark the samples in the next
4929     // fragment that overlap with AVINDEX_DISCARD_FRAME
4930     prev_dts = AV_NOPTS_VALUE;
4931     if (index_entry_pos > 0)
4932         prev_dts = st->index_entries[index_entry_pos-1].timestamp;
4933     for (i = index_entry_pos; i < st->nb_index_entries; i++) {
4934         if (prev_dts < st->index_entries[i].timestamp)
4935             break;
4936         st->index_entries[i].flags |= AVINDEX_DISCARD_FRAME;
4937     }
4938
4939     // If a hole was created to insert the new index_entries into,
4940     // the index_entry recorded for all subsequent moof must
4941     // be incremented by the number of entries inserted.
4942     fix_frag_index_entries(&c->frag_index, next_frag_index,
4943                            frag->track_id, entries);
4944
4945     if (pb->eof_reached) {
4946         av_log(c->fc, AV_LOG_WARNING, "reached eof, corrupted TRUN atom\n");
4947         return AVERROR_EOF;
4948     }
4949
4950     frag->implicit_offset = offset;
4951
4952     sc->track_end = dts + sc->time_offset;
4953     if (st->duration < sc->track_end)
4954         st->duration = sc->track_end;
4955
4956     return 0;
4957 }
4958
4959 static int mov_read_sidx(MOVContext *c, AVIOContext *pb, MOVAtom atom)
4960 {
4961     int64_t offset = avio_tell(pb) + atom.size, pts, timestamp;
4962     uint8_t version;
4963     unsigned i, j, track_id, item_count;
4964     AVStream *st = NULL;
4965     AVStream *ref_st = NULL;
4966     MOVStreamContext *sc, *ref_sc = NULL;
4967     AVRational timescale;
4968
4969     version = avio_r8(pb);
4970     if (version > 1) {
4971         avpriv_request_sample(c->fc, "sidx version %u", version);
4972         return 0;
4973     }
4974
4975     avio_rb24(pb); // flags
4976
4977     track_id = avio_rb32(pb); // Reference ID
4978     for (i = 0; i < c->fc->nb_streams; i++) {
4979         if (c->fc->streams[i]->id == track_id) {
4980             st = c->fc->streams[i];
4981             break;
4982         }
4983     }
4984     if (!st) {
4985         av_log(c->fc, AV_LOG_WARNING, "could not find corresponding track id %d\n", track_id);
4986         return 0;
4987     }
4988
4989     sc = st->priv_data;
4990
4991     timescale = av_make_q(1, avio_rb32(pb));
4992
4993     if (timescale.den <= 0) {
4994         av_log(c->fc, AV_LOG_ERROR, "Invalid sidx timescale 1/%d\n", timescale.den);
4995         return AVERROR_INVALIDDATA;
4996     }
4997
4998     if (version == 0) {
4999         pts = avio_rb32(pb);
5000         offset += avio_rb32(pb);
5001     } else {
5002         pts = avio_rb64(pb);
5003         offset += avio_rb64(pb);
5004     }
5005
5006     avio_rb16(pb); // reserved
5007
5008     item_count = avio_rb16(pb);
5009
5010     for (i = 0; i < item_count; i++) {
5011         int index;
5012         MOVFragmentStreamInfo * frag_stream_info;
5013         uint32_t size = avio_rb32(pb);
5014         uint32_t duration = avio_rb32(pb);
5015         if (size & 0x80000000) {
5016             avpriv_request_sample(c->fc, "sidx reference_type 1");
5017             return AVERROR_PATCHWELCOME;
5018         }
5019         avio_rb32(pb); // sap_flags
5020         timestamp = av_rescale_q(pts, st->time_base, timescale);
5021
5022         index = update_frag_index(c, offset);
5023         frag_stream_info = get_frag_stream_info(&c->frag_index, index, track_id);
5024         if (frag_stream_info)
5025             frag_stream_info->sidx_pts = timestamp;
5026
5027         offset += size;
5028         pts += duration;
5029     }
5030
5031     st->duration = sc->track_end = pts;
5032
5033     sc->has_sidx = 1;
5034
5035     if (offset == avio_size(pb)) {
5036         // Find first entry in fragment index that came from an sidx.
5037         // This will pretty much always be the first entry.
5038         for (i = 0; i < c->frag_index.nb_items; i++) {
5039             MOVFragmentIndexItem * item = &c->frag_index.item[i];
5040             for (j = 0; ref_st == NULL && j < item->nb_stream_info; j++) {
5041                 MOVFragmentStreamInfo * si;
5042                 si = &item->stream_info[j];
5043                 if (si->sidx_pts != AV_NOPTS_VALUE) {
5044                     ref_st = c->fc->streams[j];
5045                     ref_sc = ref_st->priv_data;
5046                     break;
5047                 }
5048             }
5049         }
5050         if (ref_st) for (i = 0; i < c->fc->nb_streams; i++) {
5051             st = c->fc->streams[i];
5052             sc = st->priv_data;
5053             if (!sc->has_sidx) {
5054                 st->duration = sc->track_end = av_rescale(ref_st->duration, sc->time_scale, ref_sc->time_scale);
5055             }
5056         }
5057
5058         c->frag_index.complete = 1;
5059     }
5060
5061     return 0;
5062 }
5063
5064 /* this atom should be null (from specs), but some buggy files put the 'moov' atom inside it... */
5065 /* like the files created with Adobe Premiere 5.0, for samples see */
5066 /* http://graphics.tudelft.nl/~wouter/publications/soundtests/ */
5067 static int mov_read_wide(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5068 {
5069     int err;
5070
5071     if (atom.size < 8)
5072         return 0; /* continue */
5073     if (avio_rb32(pb) != 0) { /* 0 sized mdat atom... use the 'wide' atom size */
5074         avio_skip(pb, atom.size - 4);
5075         return 0;
5076     }
5077     atom.type = avio_rl32(pb);
5078     atom.size -= 8;
5079     if (atom.type != MKTAG('m','d','a','t')) {
5080         avio_skip(pb, atom.size);
5081         return 0;
5082     }
5083     err = mov_read_mdat(c, pb, atom);
5084     return err;
5085 }
5086
5087 static int mov_read_cmov(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5088 {
5089 #if CONFIG_ZLIB
5090     AVIOContext ctx;
5091     uint8_t *cmov_data;
5092     uint8_t *moov_data; /* uncompressed data */
5093     long cmov_len, moov_len;
5094     int ret = -1;
5095
5096     avio_rb32(pb); /* dcom atom */
5097     if (avio_rl32(pb) != MKTAG('d','c','o','m'))
5098         return AVERROR_INVALIDDATA;
5099     if (avio_rl32(pb) != MKTAG('z','l','i','b')) {
5100         av_log(c->fc, AV_LOG_ERROR, "unknown compression for cmov atom !\n");
5101         return AVERROR_INVALIDDATA;
5102     }
5103     avio_rb32(pb); /* cmvd atom */
5104     if (avio_rl32(pb) != MKTAG('c','m','v','d'))
5105         return AVERROR_INVALIDDATA;
5106     moov_len = avio_rb32(pb); /* uncompressed size */
5107     cmov_len = atom.size - 6 * 4;
5108
5109     cmov_data = av_malloc(cmov_len);
5110     if (!cmov_data)
5111         return AVERROR(ENOMEM);
5112     moov_data = av_malloc(moov_len);
5113     if (!moov_data) {
5114         av_free(cmov_data);
5115         return AVERROR(ENOMEM);
5116     }
5117     ret = ffio_read_size(pb, cmov_data, cmov_len);
5118     if (ret < 0)
5119         goto free_and_return;
5120
5121     ret = AVERROR_INVALIDDATA;
5122     if (uncompress (moov_data, (uLongf *) &moov_len, (const Bytef *)cmov_data, cmov_len) != Z_OK)
5123         goto free_and_return;
5124     if (ffio_init_context(&ctx, moov_data, moov_len, 0, NULL, NULL, NULL, NULL) != 0)
5125         goto free_and_return;
5126     ctx.seekable = AVIO_SEEKABLE_NORMAL;
5127     atom.type = MKTAG('m','o','o','v');
5128     atom.size = moov_len;
5129     ret = mov_read_default(c, &ctx, atom);
5130 free_and_return:
5131     av_free(moov_data);
5132     av_free(cmov_data);
5133     return ret;
5134 #else
5135     av_log(c->fc, AV_LOG_ERROR, "this file requires zlib support compiled in\n");
5136     return AVERROR(ENOSYS);
5137 #endif
5138 }
5139
5140 /* edit list atom */
5141 static int mov_read_elst(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5142 {
5143     MOVStreamContext *sc;
5144     int i, edit_count, version;
5145     int64_t elst_entry_size;
5146
5147     if (c->fc->nb_streams < 1 || c->ignore_editlist)
5148         return 0;
5149     sc = c->fc->streams[c->fc->nb_streams-1]->priv_data;
5150
5151     version = avio_r8(pb); /* version */
5152     avio_rb24(pb); /* flags */
5153     edit_count = avio_rb32(pb); /* entries */
5154     atom.size -= 8;
5155
5156     elst_entry_size = version == 1 ? 20 : 12;
5157     if (atom.size != edit_count * elst_entry_size) {
5158         if (c->fc->strict_std_compliance >= FF_COMPLIANCE_STRICT) {
5159             av_log(c->fc, AV_LOG_ERROR, "Invalid edit list entry_count: %d for elst atom of size: %"PRId64" bytes.\n",
5160                    edit_count, atom.size + 8);
5161             return AVERROR_INVALIDDATA;
5162         } else {
5163             edit_count = atom.size / elst_entry_size;
5164             if (edit_count * elst_entry_size != atom.size) {
5165                 av_log(c->fc, AV_LOG_WARNING, "ELST atom of %"PRId64" bytes, bigger than %d entries.", atom.size, edit_count);
5166             }
5167         }
5168     }
5169
5170     if (!edit_count)
5171         return 0;
5172     if (sc->elst_data)
5173         av_log(c->fc, AV_LOG_WARNING, "Duplicated ELST atom\n");
5174     av_free(sc->elst_data);
5175     sc->elst_count = 0;
5176     sc->elst_data = av_malloc_array(edit_count, sizeof(*sc->elst_data));
5177     if (!sc->elst_data)
5178         return AVERROR(ENOMEM);
5179
5180     av_log(c->fc, AV_LOG_TRACE, "track[%u].edit_count = %i\n", c->fc->nb_streams - 1, edit_count);
5181     for (i = 0; i < edit_count && atom.size > 0 && !pb->eof_reached; i++) {
5182         MOVElst *e = &sc->elst_data[i];
5183
5184         if (version == 1) {
5185             e->duration = avio_rb64(pb);
5186             e->time     = avio_rb64(pb);
5187             atom.size -= 16;
5188         } else {
5189             e->duration = avio_rb32(pb); /* segment duration */
5190             e->time     = (int32_t)avio_rb32(pb); /* media time */
5191             atom.size -= 8;
5192         }
5193         e->rate = avio_rb32(pb) / 65536.0;
5194         atom.size -= 4;
5195         av_log(c->fc, AV_LOG_TRACE, "duration=%"PRId64" time=%"PRId64" rate=%f\n",
5196                e->duration, e->time, e->rate);
5197
5198         if (e->time < 0 && e->time != -1 &&
5199             c->fc->strict_std_compliance >= FF_COMPLIANCE_STRICT) {
5200             av_log(c->fc, AV_LOG_ERROR, "Track %d, edit %d: Invalid edit list media time=%"PRId64"\n",
5201                    c->fc->nb_streams-1, i, e->time);
5202             return AVERROR_INVALIDDATA;
5203         }
5204     }
5205     sc->elst_count = i;
5206
5207     return 0;
5208 }
5209
5210 static int mov_read_tmcd(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5211 {
5212     MOVStreamContext *sc;
5213
5214     if (c->fc->nb_streams < 1)
5215         return AVERROR_INVALIDDATA;
5216     sc = c->fc->streams[c->fc->nb_streams - 1]->priv_data;
5217     sc->timecode_track = avio_rb32(pb);
5218     return 0;
5219 }
5220
5221 static int mov_read_av1c(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5222 {
5223     AVStream *st;
5224     int ret;
5225
5226     if (c->fc->nb_streams < 1)
5227         return 0;
5228     st = c->fc->streams[c->fc->nb_streams - 1];
5229
5230     if (atom.size < 4) {
5231         av_log(c->fc, AV_LOG_ERROR, "Empty AV1 Codec Configuration Box\n");
5232         return AVERROR_INVALIDDATA;
5233     }
5234
5235     /* For now, propagate only the OBUs, if any. Once libavcodec is
5236        updated to handle isobmff style extradata this can be removed. */
5237     avio_skip(pb, 4);
5238
5239     if (atom.size == 4)
5240         return 0;
5241
5242     ret = ff_get_extradata(c->fc, st->codecpar, pb, atom.size - 4);
5243     if (ret < 0)
5244         return ret;
5245
5246     return 0;
5247 }
5248
5249 static int mov_read_vpcc(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5250 {
5251     AVStream *st;
5252     int version, color_range, color_primaries, color_trc, color_space;
5253
5254     if (c->fc->nb_streams < 1)
5255         return 0;
5256     st = c->fc->streams[c->fc->nb_streams - 1];
5257
5258     if (atom.size < 5) {
5259         av_log(c->fc, AV_LOG_ERROR, "Empty VP Codec Configuration box\n");
5260         return AVERROR_INVALIDDATA;
5261     }
5262
5263     version = avio_r8(pb);
5264     if (version != 1) {
5265         av_log(c->fc, AV_LOG_WARNING, "Unsupported VP Codec Configuration box version %d\n", version);
5266         return 0;
5267     }
5268     avio_skip(pb, 3); /* flags */
5269
5270     avio_skip(pb, 2); /* profile + level */
5271     color_range     = avio_r8(pb); /* bitDepth, chromaSubsampling, videoFullRangeFlag */
5272     color_primaries = avio_r8(pb);
5273     color_trc       = avio_r8(pb);
5274     color_space     = avio_r8(pb);
5275     if (avio_rb16(pb)) /* codecIntializationDataSize */
5276         return AVERROR_INVALIDDATA;
5277
5278     if (!av_color_primaries_name(color_primaries))
5279         color_primaries = AVCOL_PRI_UNSPECIFIED;
5280     if (!av_color_transfer_name(color_trc))
5281         color_trc = AVCOL_TRC_UNSPECIFIED;
5282     if (!av_color_space_name(color_space))
5283         color_space = AVCOL_SPC_UNSPECIFIED;
5284
5285     st->codecpar->color_range     = (color_range & 1) ? AVCOL_RANGE_JPEG : AVCOL_RANGE_MPEG;
5286     st->codecpar->color_primaries = color_primaries;
5287     st->codecpar->color_trc       = color_trc;
5288     st->codecpar->color_space     = color_space;
5289
5290     return 0;
5291 }
5292
5293 static int mov_read_smdm(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5294 {
5295     MOVStreamContext *sc;
5296     int i, version;
5297
5298     if (c->fc->nb_streams < 1)
5299         return AVERROR_INVALIDDATA;
5300
5301     sc = c->fc->streams[c->fc->nb_streams - 1]->priv_data;
5302
5303     if (atom.size < 5) {
5304         av_log(c->fc, AV_LOG_ERROR, "Empty Mastering Display Metadata box\n");
5305         return AVERROR_INVALIDDATA;
5306     }
5307
5308     version = avio_r8(pb);
5309     if (version) {
5310         av_log(c->fc, AV_LOG_WARNING, "Unsupported Mastering Display Metadata box version %d\n", version);
5311         return 0;
5312     }
5313     avio_skip(pb, 3); /* flags */
5314
5315     sc->mastering = av_mastering_display_metadata_alloc();
5316     if (!sc->mastering)
5317         return AVERROR(ENOMEM);
5318
5319     for (i = 0; i < 3; i++) {
5320         sc->mastering->display_primaries[i][0] = av_make_q(avio_rb16(pb), 1 << 16);
5321         sc->mastering->display_primaries[i][1] = av_make_q(avio_rb16(pb), 1 << 16);
5322     }
5323     sc->mastering->white_point[0] = av_make_q(avio_rb16(pb), 1 << 16);
5324     sc->mastering->white_point[1] = av_make_q(avio_rb16(pb), 1 << 16);
5325
5326     sc->mastering->max_luminance = av_make_q(avio_rb32(pb), 1 << 8);
5327     sc->mastering->min_luminance = av_make_q(avio_rb32(pb), 1 << 14);
5328
5329     sc->mastering->has_primaries = 1;
5330     sc->mastering->has_luminance = 1;
5331
5332     return 0;
5333 }
5334
5335 static int mov_read_mdcv(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5336 {
5337     MOVStreamContext *sc;
5338     const int mapping[3] = {1, 2, 0};
5339     const int chroma_den = 50000;
5340     const int luma_den = 10000;
5341     int i;
5342
5343     if (c->fc->nb_streams < 1)
5344         return AVERROR_INVALIDDATA;
5345
5346     sc = c->fc->streams[c->fc->nb_streams - 1]->priv_data;
5347
5348     if (atom.size < 24) {
5349         av_log(c->fc, AV_LOG_ERROR, "Invalid Mastering Display Color Volume box\n");
5350         return AVERROR_INVALIDDATA;
5351     }
5352
5353     sc->mastering = av_mastering_display_metadata_alloc();
5354     if (!sc->mastering)
5355         return AVERROR(ENOMEM);
5356
5357     for (i = 0; i < 3; i++) {
5358         const int j = mapping[i];
5359         sc->mastering->display_primaries[j][0] = av_make_q(avio_rb16(pb), chroma_den);
5360         sc->mastering->display_primaries[j][1] = av_make_q(avio_rb16(pb), chroma_den);
5361     }
5362     sc->mastering->white_point[0] = av_make_q(avio_rb16(pb), chroma_den);
5363     sc->mastering->white_point[1] = av_make_q(avio_rb16(pb), chroma_den);
5364
5365     sc->mastering->max_luminance = av_make_q(avio_rb32(pb), luma_den);
5366     sc->mastering->min_luminance = av_make_q(avio_rb32(pb), luma_den);
5367
5368     sc->mastering->has_luminance = 1;
5369     sc->mastering->has_primaries = 1;
5370
5371     return 0;
5372 }
5373
5374 static int mov_read_coll(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5375 {
5376     MOVStreamContext *sc;
5377     int version;
5378
5379     if (c->fc->nb_streams < 1)
5380         return AVERROR_INVALIDDATA;
5381
5382     sc = c->fc->streams[c->fc->nb_streams - 1]->priv_data;
5383
5384     if (atom.size < 5) {
5385         av_log(c->fc, AV_LOG_ERROR, "Empty Content Light Level box\n");
5386         return AVERROR_INVALIDDATA;
5387     }
5388
5389     version = avio_r8(pb);
5390     if (version) {
5391         av_log(c->fc, AV_LOG_WARNING, "Unsupported Content Light Level box version %d\n", version);
5392         return 0;
5393     }
5394     avio_skip(pb, 3); /* flags */
5395
5396     sc->coll = av_content_light_metadata_alloc(&sc->coll_size);
5397     if (!sc->coll)
5398         return AVERROR(ENOMEM);
5399
5400     sc->coll->MaxCLL  = avio_rb16(pb);
5401     sc->coll->MaxFALL = avio_rb16(pb);
5402
5403     return 0;
5404 }
5405
5406 static int mov_read_clli(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5407 {
5408     MOVStreamContext *sc;
5409
5410     if (c->fc->nb_streams < 1)
5411         return AVERROR_INVALIDDATA;
5412
5413     sc = c->fc->streams[c->fc->nb_streams - 1]->priv_data;
5414
5415     if (atom.size < 4) {
5416         av_log(c->fc, AV_LOG_ERROR, "Empty Content Light Level Info box\n");
5417         return AVERROR_INVALIDDATA;
5418     }
5419
5420     sc->coll = av_content_light_metadata_alloc(&sc->coll_size);
5421     if (!sc->coll)
5422         return AVERROR(ENOMEM);
5423
5424     sc->coll->MaxCLL  = avio_rb16(pb);
5425     sc->coll->MaxFALL = avio_rb16(pb);
5426
5427     return 0;
5428 }
5429
5430 static int mov_read_st3d(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5431 {
5432     AVStream *st;
5433     MOVStreamContext *sc;
5434     enum AVStereo3DType type;
5435     int mode;
5436
5437     if (c->fc->nb_streams < 1)
5438         return 0;
5439
5440     st = c->fc->streams[c->fc->nb_streams - 1];
5441     sc = st->priv_data;
5442
5443     if (atom.size < 5) {
5444         av_log(c->fc, AV_LOG_ERROR, "Empty stereoscopic video box\n");
5445         return AVERROR_INVALIDDATA;
5446     }
5447     avio_skip(pb, 4); /* version + flags */
5448
5449     mode = avio_r8(pb);
5450     switch (mode) {
5451     case 0:
5452         type = AV_STEREO3D_2D;
5453         break;
5454     case 1:
5455         type = AV_STEREO3D_TOPBOTTOM;
5456         break;
5457     case 2:
5458         type = AV_STEREO3D_SIDEBYSIDE;
5459         break;
5460     default:
5461         av_log(c->fc, AV_LOG_WARNING, "Unknown st3d mode value %d\n", mode);
5462         return 0;
5463     }
5464
5465     sc->stereo3d = av_stereo3d_alloc();
5466     if (!sc->stereo3d)
5467         return AVERROR(ENOMEM);
5468
5469     sc->stereo3d->type = type;
5470     return 0;
5471 }
5472
5473 static int mov_read_sv3d(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5474 {
5475     AVStream *st;
5476     MOVStreamContext *sc;
5477     int size, version, layout;
5478     int32_t yaw, pitch, roll;
5479     uint32_t l = 0, t = 0, r = 0, b = 0;
5480     uint32_t tag, padding = 0;
5481     enum AVSphericalProjection projection;
5482
5483     if (c->fc->nb_streams < 1)
5484         return 0;
5485
5486     st = c->fc->streams[c->fc->nb_streams - 1];
5487     sc = st->priv_data;
5488
5489     if (atom.size < 8) {
5490         av_log(c->fc, AV_LOG_ERROR, "Empty spherical video box\n");
5491         return AVERROR_INVALIDDATA;
5492     }
5493
5494     size = avio_rb32(pb);
5495     if (size <= 12 || size > atom.size)
5496         return AVERROR_INVALIDDATA;
5497
5498     tag = avio_rl32(pb);
5499     if (tag != MKTAG('s','v','h','d')) {
5500         av_log(c->fc, AV_LOG_ERROR, "Missing spherical video header\n");
5501         return 0;
5502     }
5503     version = avio_r8(pb);
5504     if (version != 0) {
5505         av_log(c->fc, AV_LOG_WARNING, "Unknown spherical version %d\n",
5506                version);
5507         return 0;
5508     }
5509     avio_skip(pb, 3); /* flags */
5510     avio_skip(pb, size - 12); /* metadata_source */
5511
5512     size = avio_rb32(pb);
5513     if (size > atom.size)
5514         return AVERROR_INVALIDDATA;
5515
5516     tag = avio_rl32(pb);
5517     if (tag != MKTAG('p','r','o','j')) {
5518         av_log(c->fc, AV_LOG_ERROR, "Missing projection box\n");
5519         return 0;
5520     }
5521
5522     size = avio_rb32(pb);
5523     if (size > atom.size)
5524         return AVERROR_INVALIDDATA;
5525
5526     tag = avio_rl32(pb);
5527     if (tag != MKTAG('p','r','h','d')) {
5528         av_log(c->fc, AV_LOG_ERROR, "Missing projection header box\n");
5529         return 0;
5530     }
5531     version = avio_r8(pb);
5532     if (version != 0) {
5533         av_log(c->fc, AV_LOG_WARNING, "Unknown spherical version %d\n",
5534                version);
5535         return 0;
5536     }
5537     avio_skip(pb, 3); /* flags */
5538
5539     /* 16.16 fixed point */
5540     yaw   = avio_rb32(pb);
5541     pitch = avio_rb32(pb);
5542     roll  = avio_rb32(pb);
5543
5544     size = avio_rb32(pb);
5545     if (size > atom.size)
5546         return AVERROR_INVALIDDATA;
5547
5548     tag = avio_rl32(pb);
5549     version = avio_r8(pb);
5550     if (version != 0) {
5551         av_log(c->fc, AV_LOG_WARNING, "Unknown spherical version %d\n",
5552                version);
5553         return 0;
5554     }
5555     avio_skip(pb, 3); /* flags */
5556     switch (tag) {
5557     case MKTAG('c','b','m','p'):
5558         layout = avio_rb32(pb);
5559         if (layout) {
5560             av_log(c->fc, AV_LOG_WARNING,
5561                    "Unsupported cubemap layout %d\n", layout);
5562             return 0;
5563         }
5564         projection = AV_SPHERICAL_CUBEMAP;
5565         padding = avio_rb32(pb);
5566         break;
5567     case MKTAG('e','q','u','i'):
5568         t = avio_rb32(pb);
5569         b = avio_rb32(pb);
5570         l = avio_rb32(pb);
5571         r = avio_rb32(pb);
5572
5573         if (b >= UINT_MAX - t || r >= UINT_MAX - l) {
5574             av_log(c->fc, AV_LOG_ERROR,
5575                    "Invalid bounding rectangle coordinates "
5576                    "%"PRIu32",%"PRIu32",%"PRIu32",%"PRIu32"\n", l, t, r, b);
5577             return AVERROR_INVALIDDATA;
5578         }
5579
5580         if (l || t || r || b)
5581             projection = AV_SPHERICAL_EQUIRECTANGULAR_TILE;
5582         else
5583             projection = AV_SPHERICAL_EQUIRECTANGULAR;
5584         break;
5585     default:
5586         av_log(c->fc, AV_LOG_ERROR, "Unknown projection type: %s\n", av_fourcc2str(tag));
5587         return 0;
5588     }
5589
5590     sc->spherical = av_spherical_alloc(&sc->spherical_size);
5591     if (!sc->spherical)
5592         return AVERROR(ENOMEM);
5593
5594     sc->spherical->projection = projection;
5595
5596     sc->spherical->yaw   = yaw;
5597     sc->spherical->pitch = pitch;
5598     sc->spherical->roll  = roll;
5599
5600     sc->spherical->padding = padding;
5601
5602     sc->spherical->bound_left   = l;
5603     sc->spherical->bound_top    = t;
5604     sc->spherical->bound_right  = r;
5605     sc->spherical->bound_bottom = b;
5606
5607     return 0;
5608 }
5609
5610 static int mov_parse_uuid_spherical(MOVStreamContext *sc, AVIOContext *pb, size_t len)
5611 {
5612     int ret = 0;
5613     uint8_t *buffer = av_malloc(len + 1);
5614     const char *val;
5615
5616     if (!buffer)
5617         return AVERROR(ENOMEM);
5618     buffer[len] = '\0';
5619
5620     ret = ffio_read_size(pb, buffer, len);
5621     if (ret < 0)
5622         goto out;
5623
5624     /* Check for mandatory keys and values, try to support XML as best-effort */
5625     if (!sc->spherical &&
5626         av_stristr(buffer, "<GSpherical:StitchingSoftware>") &&
5627         (val = av_stristr(buffer, "<GSpherical:Spherical>")) &&
5628         av_stristr(val, "true") &&
5629         (val = av_stristr(buffer, "<GSpherical:Stitched>")) &&
5630         av_stristr(val, "true") &&
5631         (val = av_stristr(buffer, "<GSpherical:ProjectionType>")) &&
5632         av_stristr(val, "equirectangular")) {
5633         sc->spherical = av_spherical_alloc(&sc->spherical_size);
5634         if (!sc->spherical)
5635             goto out;
5636
5637         sc->spherical->projection = AV_SPHERICAL_EQUIRECTANGULAR;
5638
5639         if (av_stristr(buffer, "<GSpherical:StereoMode>") && !sc->stereo3d) {
5640             enum AVStereo3DType mode;
5641
5642             if (av_stristr(buffer, "left-right"))
5643                 mode = AV_STEREO3D_SIDEBYSIDE;
5644             else if (av_stristr(buffer, "top-bottom"))
5645                 mode = AV_STEREO3D_TOPBOTTOM;
5646             else
5647                 mode = AV_STEREO3D_2D;
5648
5649             sc->stereo3d = av_stereo3d_alloc();
5650             if (!sc->stereo3d)
5651                 goto out;
5652
5653             sc->stereo3d->type = mode;
5654         }
5655
5656         /* orientation */
5657         val = av_stristr(buffer, "<GSpherical:InitialViewHeadingDegrees>");
5658         if (val)
5659             sc->spherical->yaw = strtol(val, NULL, 10) * (1 << 16);
5660         val = av_stristr(buffer, "<GSpherical:InitialViewPitchDegrees>");
5661         if (val)
5662             sc->spherical->pitch = strtol(val, NULL, 10) * (1 << 16);
5663         val = av_stristr(buffer, "<GSpherical:InitialViewRollDegrees>");
5664         if (val)
5665             sc->spherical->roll = strtol(val, NULL, 10) * (1 << 16);
5666     }
5667
5668 out:
5669     av_free(buffer);
5670     return ret;
5671 }
5672
5673 static int mov_read_uuid(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5674 {
5675     AVStream *st;
5676     MOVStreamContext *sc;
5677     int64_t ret;
5678     uint8_t uuid[16];
5679     static const uint8_t uuid_isml_manifest[] = {
5680         0xa5, 0xd4, 0x0b, 0x30, 0xe8, 0x14, 0x11, 0xdd,
5681         0xba, 0x2f, 0x08, 0x00, 0x20, 0x0c, 0x9a, 0x66
5682     };
5683     static const uint8_t uuid_xmp[] = {
5684         0xbe, 0x7a, 0xcf, 0xcb, 0x97, 0xa9, 0x42, 0xe8,
5685         0x9c, 0x71, 0x99, 0x94, 0x91, 0xe3, 0xaf, 0xac
5686     };
5687     static const uint8_t uuid_spherical[] = {
5688         0xff, 0xcc, 0x82, 0x63, 0xf8, 0x55, 0x4a, 0x93,
5689         0x88, 0x14, 0x58, 0x7a, 0x02, 0x52, 0x1f, 0xdd,
5690     };
5691
5692     if (atom.size < sizeof(uuid) || atom.size >= FFMIN(INT_MAX, SIZE_MAX))
5693         return AVERROR_INVALIDDATA;
5694
5695     if (c->fc->nb_streams < 1)
5696         return 0;
5697     st = c->fc->streams[c->fc->nb_streams - 1];
5698     sc = st->priv_data;
5699
5700     ret = avio_read(pb, uuid, sizeof(uuid));
5701     if (ret < 0) {
5702         return ret;
5703     } else if (ret != sizeof(uuid)) {
5704         return AVERROR_INVALIDDATA;
5705     }
5706     if (!memcmp(uuid, uuid_isml_manifest, sizeof(uuid))) {
5707         uint8_t *buffer, *ptr;
5708         char *endptr;
5709         size_t len = atom.size - sizeof(uuid);
5710
5711         if (len < 4) {
5712             return AVERROR_INVALIDDATA;
5713         }
5714         ret = avio_skip(pb, 4); // zeroes
5715         len -= 4;
5716
5717         buffer = av_mallocz(len + 1);
5718         if (!buffer) {
5719             return AVERROR(ENOMEM);
5720         }
5721         ret = avio_read(pb, buffer, len);
5722         if (ret < 0) {
5723             av_free(buffer);
5724             return ret;
5725         } else if (ret != len) {
5726             av_free(buffer);
5727             return AVERROR_INVALIDDATA;
5728         }
5729
5730         ptr = buffer;
5731         while ((ptr = av_stristr(ptr, "systemBitrate=\""))) {
5732             ptr += sizeof("systemBitrate=\"") - 1;
5733             c->bitrates_count++;
5734             c->bitrates = av_realloc_f(c->bitrates, c->bitrates_count, sizeof(*c->bitrates));
5735             if (!c->bitrates) {
5736                 c->bitrates_count = 0;
5737                 av_free(buffer);
5738                 return AVERROR(ENOMEM);
5739             }
5740             errno = 0;
5741             ret = strtol(ptr, &endptr, 10);
5742             if (ret < 0 || errno || *endptr != '"') {
5743                 c->bitrates[c->bitrates_count - 1] = 0;
5744             } else {
5745                 c->bitrates[c->bitrates_count - 1] = ret;
5746             }
5747         }
5748
5749         av_free(buffer);
5750     } else if (!memcmp(uuid, uuid_xmp, sizeof(uuid))) {
5751         uint8_t *buffer;
5752         size_t len = atom.size - sizeof(uuid);
5753         if (c->export_xmp) {
5754             buffer = av_mallocz(len + 1);
5755             if (!buffer) {
5756                 return AVERROR(ENOMEM);
5757             }
5758             ret = avio_read(pb, buffer, len);
5759             if (ret < 0) {
5760                 av_free(buffer);
5761                 return ret;
5762             } else if (ret != len) {
5763                 av_free(buffer);
5764                 return AVERROR_INVALIDDATA;
5765             }
5766             buffer[len] = '\0';
5767             av_dict_set(&c->fc->metadata, "xmp", buffer, 0);
5768             av_free(buffer);
5769         } else {
5770             // skip all uuid atom, which makes it fast for long uuid-xmp file
5771             ret = avio_skip(pb, len);
5772             if (ret < 0)
5773                 return ret;
5774         }
5775     } else if (!memcmp(uuid, uuid_spherical, sizeof(uuid))) {
5776         size_t len = atom.size - sizeof(uuid);
5777         ret = mov_parse_uuid_spherical(sc, pb, len);
5778         if (ret < 0)
5779             return ret;
5780         if (!sc->spherical)
5781             av_log(c->fc, AV_LOG_WARNING, "Invalid spherical metadata found\n");
5782     }
5783
5784     return 0;
5785 }
5786
5787 static int mov_read_free(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5788 {
5789     int ret;
5790     uint8_t content[16];
5791
5792     if (atom.size < 8)
5793         return 0;
5794
5795     ret = avio_read(pb, content, FFMIN(sizeof(content), atom.size));
5796     if (ret < 0)
5797         return ret;
5798
5799     if (   !c->found_moov
5800         && !c->found_mdat
5801         && !memcmp(content, "Anevia\x1A\x1A", 8)
5802         && c->use_mfra_for == FF_MOV_FLAG_MFRA_AUTO) {
5803         c->use_mfra_for = FF_MOV_FLAG_MFRA_PTS;
5804     }
5805
5806     return 0;
5807 }
5808
5809 static int mov_read_frma(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5810 {
5811     uint32_t format = avio_rl32(pb);
5812     MOVStreamContext *sc;
5813     enum AVCodecID id;
5814     AVStream *st;
5815
5816     if (c->fc->nb_streams < 1)
5817         return 0;
5818     st = c->fc->streams[c->fc->nb_streams - 1];
5819     sc = st->priv_data;
5820
5821     switch (sc->format)
5822     {
5823     case MKTAG('e','n','c','v'):        // encrypted video
5824     case MKTAG('e','n','c','a'):        // encrypted audio
5825         id = mov_codec_id(st, format);
5826         if (st->codecpar->codec_id != AV_CODEC_ID_NONE &&
5827             st->codecpar->codec_id != id) {
5828             av_log(c->fc, AV_LOG_WARNING,
5829                    "ignoring 'frma' atom of '%.4s', stream has codec id %d\n",
5830                    (char*)&format, st->codecpar->codec_id);
5831             break;
5832         }
5833
5834         st->codecpar->codec_id = id;
5835         sc->format = format;
5836         break;
5837
5838     default:
5839         if (format != sc->format) {
5840             av_log(c->fc, AV_LOG_WARNING,
5841                    "ignoring 'frma' atom of '%.4s', stream format is '%.4s'\n",
5842                    (char*)&format, (char*)&sc->format);
5843         }
5844         break;
5845     }
5846
5847     return 0;
5848 }
5849
5850 /**
5851  * Gets the current encryption info and associated current stream context.  If
5852  * we are parsing a track fragment, this will return the specific encryption
5853  * info for this fragment; otherwise this will return the global encryption
5854  * info for the current stream.
5855  */
5856 static int get_current_encryption_info(MOVContext *c, MOVEncryptionIndex **encryption_index, MOVStreamContext **sc)
5857 {
5858     MOVFragmentStreamInfo *frag_stream_info;
5859     AVStream *st;
5860     int i;
5861
5862     frag_stream_info = get_current_frag_stream_info(&c->frag_index);
5863     if (frag_stream_info) {
5864         for (i = 0; i < c->fc->nb_streams; i++) {
5865             if (c->fc->streams[i]->id == frag_stream_info->id) {
5866               st = c->fc->streams[i];
5867               break;
5868             }
5869         }
5870         if (i == c->fc->nb_streams)
5871             return 0;
5872         *sc = st->priv_data;
5873
5874         if (!frag_stream_info->encryption_index) {
5875             // If this stream isn't encrypted, don't create the index.
5876             if (!(*sc)->cenc.default_encrypted_sample)
5877                 return 0;
5878             frag_stream_info->encryption_index = av_mallocz(sizeof(*frag_stream_info->encryption_index));
5879             if (!frag_stream_info->encryption_index)
5880                 return AVERROR(ENOMEM);
5881         }
5882         *encryption_index = frag_stream_info->encryption_index;
5883         return 1;
5884     } else {
5885         // No current track fragment, using stream level encryption info.
5886
5887         if (c->fc->nb_streams < 1)
5888             return 0;
5889         st = c->fc->streams[c->fc->nb_streams - 1];
5890         *sc = st->priv_data;
5891
5892         if (!(*sc)->cenc.encryption_index) {
5893             // If this stream isn't encrypted, don't create the index.
5894             if (!(*sc)->cenc.default_encrypted_sample)
5895                 return 0;
5896             (*sc)->cenc.encryption_index = av_mallocz(sizeof(*frag_stream_info->encryption_index));
5897             if (!(*sc)->cenc.encryption_index)
5898                 return AVERROR(ENOMEM);
5899         }
5900
5901         *encryption_index = (*sc)->cenc.encryption_index;
5902         return 1;
5903     }
5904 }
5905
5906 static int mov_read_sample_encryption_info(MOVContext *c, AVIOContext *pb, MOVStreamContext *sc, AVEncryptionInfo **sample, int use_subsamples)
5907 {
5908     int i;
5909     unsigned int subsample_count;
5910     AVSubsampleEncryptionInfo *subsamples;
5911
5912     if (!sc->cenc.default_encrypted_sample) {
5913         av_log(c->fc, AV_LOG_ERROR, "Missing schm or tenc\n");
5914         return AVERROR_INVALIDDATA;
5915     }
5916
5917     *sample = av_encryption_info_clone(sc->cenc.default_encrypted_sample);
5918     if (!*sample)
5919         return AVERROR(ENOMEM);
5920
5921     if (sc->cenc.per_sample_iv_size != 0) {
5922         if (avio_read(pb, (*sample)->iv, sc->cenc.per_sample_iv_size) != sc->cenc.per_sample_iv_size) {
5923             av_log(c->fc, AV_LOG_ERROR, "failed to read the initialization vector\n");
5924             av_encryption_info_free(*sample);
5925             *sample = NULL;
5926             return AVERROR_INVALIDDATA;
5927         }
5928     }
5929
5930     if (use_subsamples) {
5931         subsample_count = avio_rb16(pb);
5932         av_free((*sample)->subsamples);
5933         (*sample)->subsamples = av_mallocz_array(subsample_count, sizeof(*subsamples));
5934         if (!(*sample)->subsamples) {
5935             av_encryption_info_free(*sample);
5936             *sample = NULL;
5937             return AVERROR(ENOMEM);
5938         }
5939
5940         for (i = 0; i < subsample_count && !pb->eof_reached; i++) {
5941             (*sample)->subsamples[i].bytes_of_clear_data = avio_rb16(pb);
5942             (*sample)->subsamples[i].bytes_of_protected_data = avio_rb32(pb);
5943         }
5944
5945         if (pb->eof_reached) {
5946             av_log(c->fc, AV_LOG_ERROR, "hit EOF while reading sub-sample encryption info\n");
5947             av_encryption_info_free(*sample);
5948             *sample = NULL;
5949             return AVERROR_INVALIDDATA;
5950         }
5951         (*sample)->subsample_count = subsample_count;
5952     }
5953
5954     return 0;
5955 }
5956
5957 static int mov_read_senc(MOVContext *c, AVIOContext *pb, MOVAtom atom)
5958 {
5959     AVEncryptionInfo **encrypted_samples;
5960     MOVEncryptionIndex *encryption_index;
5961     MOVStreamContext *sc;
5962     int use_subsamples, ret;
5963     unsigned int sample_count, i, alloc_size = 0;
5964
5965     ret = get_current_encryption_info(c, &encryption_index, &sc);
5966     if (ret != 1)
5967         return ret;
5968
5969     if (encryption_index->nb_encrypted_samples) {
5970         // This can happen if we have both saio/saiz and senc atoms.
5971         av_log(c->fc, AV_LOG_DEBUG, "Ignoring duplicate encryption info in senc\n");
5972         return 0;
5973     }
5974
5975     avio_r8(pb); /* version */
5976     use_subsamples = avio_rb24(pb) & 0x02; /* flags */
5977
5978     sample_count = avio_rb32(pb);
5979     if (sample_count >= INT_MAX / sizeof(*encrypted_samples))
5980         return AVERROR(ENOMEM);
5981
5982     for (i = 0; i < sample_count; i++) {
5983         unsigned int min_samples = FFMIN(FFMAX(i + 1, 1024 * 1024), sample_count);
5984         encrypted_samples = av_fast_realloc(encryption_index->encrypted_samples, &alloc_size,
5985                                             min_samples * sizeof(*encrypted_samples));
5986         if (encrypted_samples) {
5987             encryption_index->encrypted_samples = encrypted_samples;
5988
5989             ret = mov_read_sample_encryption_info(
5990                 c, pb, sc, &encryption_index->encrypted_samples[i], use_subsamples);
5991         } else {
5992             ret = AVERROR(ENOMEM);
5993         }
5994         if (pb->eof_reached) {
5995             av_log(c->fc, AV_LOG_ERROR, "Hit EOF while reading senc\n");
5996             ret = AVERROR_INVALIDDATA;
5997         }
5998
5999         if (ret < 0) {
6000             for (; i > 0; i--)
6001                 av_encryption_info_free(encryption_index->encrypted_samples[i - 1]);
6002             av_freep(&encryption_index->encrypted_samples);
6003             return ret;
6004         }
6005     }
6006     encryption_index->nb_encrypted_samples = sample_count;
6007
6008     return 0;
6009 }
6010
6011 static int mov_parse_auxiliary_info(MOVContext *c, MOVStreamContext *sc, AVIOContext *pb, MOVEncryptionIndex *encryption_index)
6012 {
6013     AVEncryptionInfo **sample, **encrypted_samples;
6014     int64_t prev_pos;
6015     size_t sample_count, sample_info_size, i;
6016     int ret = 0;
6017     unsigned int alloc_size = 0;
6018
6019     if (encryption_index->nb_encrypted_samples)
6020         return 0;
6021     sample_count = encryption_index->auxiliary_info_sample_count;
6022     if (encryption_index->auxiliary_offsets_count != 1) {
6023         av_log(c->fc, AV_LOG_ERROR, "Multiple auxiliary info chunks are not supported\n");
6024         return AVERROR_PATCHWELCOME;
6025     }
6026     if (sample_count >= INT_MAX / sizeof(*encrypted_samples))
6027         return AVERROR(ENOMEM);
6028
6029     prev_pos = avio_tell(pb);
6030     if (!(pb->seekable & AVIO_SEEKABLE_NORMAL) ||
6031         avio_seek(pb, encryption_index->auxiliary_offsets[0], SEEK_SET) != encryption_index->auxiliary_offsets[0]) {
6032         av_log(c->fc, AV_LOG_INFO, "Failed to seek for auxiliary info, will only parse senc atoms for encryption info\n");
6033         goto finish;
6034     }
6035
6036     for (i = 0; i < sample_count && !pb->eof_reached; i++) {
6037         unsigned int min_samples = FFMIN(FFMAX(i + 1, 1024 * 1024), sample_count);
6038         encrypted_samples = av_fast_realloc(encryption_index->encrypted_samples, &alloc_size,
6039                                             min_samples * sizeof(*encrypted_samples));
6040         if (!encrypted_samples) {
6041             ret = AVERROR(ENOMEM);
6042             goto finish;
6043         }
6044         encryption_index->encrypted_samples = encrypted_samples;
6045
6046         sample = &encryption_index->encrypted_samples[i];
6047         sample_info_size = encryption_index->auxiliary_info_default_size
6048                                ? encryption_index->auxiliary_info_default_size
6049                                : encryption_index->auxiliary_info_sizes[i];
6050
6051         ret = mov_read_sample_encryption_info(c, pb, sc, sample, sample_info_size > sc->cenc.per_sample_iv_size);
6052         if (ret < 0)
6053             goto finish;
6054     }
6055     if (pb->eof_reached) {
6056         av_log(c->fc, AV_LOG_ERROR, "Hit EOF while reading auxiliary info\n");
6057         ret = AVERROR_INVALIDDATA;
6058     } else {
6059         encryption_index->nb_encrypted_samples = sample_count;
6060     }
6061
6062 finish:
6063     avio_seek(pb, prev_pos, SEEK_SET);
6064     if (ret < 0) {
6065         for (; i > 0; i--) {
6066             av_encryption_info_free(encryption_index->encrypted_samples[i - 1]);
6067         }
6068         av_freep(&encryption_index->encrypted_samples);
6069     }
6070     return ret;
6071 }
6072
6073 /**
6074  * Tries to read the given number of bytes from the stream and puts it in a
6075  * newly allocated buffer.  This reads in small chunks to avoid allocating large
6076  * memory if the file contains an invalid/malicious size value.
6077  */
6078 static int mov_try_read_block(AVIOContext *pb, size_t size, uint8_t **data)
6079 {
6080     const unsigned int block_size = 1024 * 1024;
6081     uint8_t *buffer = NULL;
6082     unsigned int alloc_size = 0, offset = 0;
6083     while (offset < size) {
6084         unsigned int new_size =
6085             alloc_size >= INT_MAX - block_size ? INT_MAX : alloc_size + block_size;
6086         uint8_t *new_buffer = av_fast_realloc(buffer, &alloc_size, new_size);
6087         unsigned int to_read = FFMIN(size, alloc_size) - offset;
6088         if (!new_buffer) {
6089             av_free(buffer);
6090             return AVERROR(ENOMEM);
6091         }
6092         buffer = new_buffer;
6093
6094         if (avio_read(pb, buffer + offset, to_read) != to_read) {
6095             av_free(buffer);
6096             return AVERROR_INVALIDDATA;
6097         }
6098         offset += to_read;
6099     }
6100
6101     *data = buffer;
6102     return 0;
6103 }
6104
6105 static int mov_read_saiz(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6106 {
6107     MOVEncryptionIndex *encryption_index;
6108     MOVStreamContext *sc;
6109     int ret;
6110     unsigned int sample_count, aux_info_type, aux_info_param;
6111
6112     ret = get_current_encryption_info(c, &encryption_index, &sc);
6113     if (ret != 1)
6114         return ret;
6115
6116     if (encryption_index->nb_encrypted_samples) {
6117         // This can happen if we have both saio/saiz and senc atoms.
6118         av_log(c->fc, AV_LOG_DEBUG, "Ignoring duplicate encryption info in saiz\n");
6119         return 0;
6120     }
6121
6122     if (encryption_index->auxiliary_info_sample_count) {
6123         av_log(c->fc, AV_LOG_ERROR, "Duplicate saiz atom\n");
6124         return AVERROR_INVALIDDATA;
6125     }
6126
6127     avio_r8(pb); /* version */
6128     if (avio_rb24(pb) & 0x01) {  /* flags */
6129         aux_info_type = avio_rb32(pb);
6130         aux_info_param = avio_rb32(pb);
6131         if (sc->cenc.default_encrypted_sample) {
6132             if (aux_info_type != sc->cenc.default_encrypted_sample->scheme) {
6133                 av_log(c->fc, AV_LOG_DEBUG, "Ignoring saiz box with non-zero aux_info_type\n");
6134                 return 0;
6135             }
6136             if (aux_info_param != 0) {
6137                 av_log(c->fc, AV_LOG_DEBUG, "Ignoring saiz box with non-zero aux_info_type_parameter\n");
6138                 return 0;
6139             }
6140         } else {
6141             // Didn't see 'schm' or 'tenc', so this isn't encrypted.
6142             if ((aux_info_type == MKBETAG('c','e','n','c') ||
6143                  aux_info_type == MKBETAG('c','e','n','s') ||
6144                  aux_info_type == MKBETAG('c','b','c','1') ||
6145                  aux_info_type == MKBETAG('c','b','c','s')) &&
6146                 aux_info_param == 0) {
6147                 av_log(c->fc, AV_LOG_ERROR, "Saw encrypted saiz without schm/tenc\n");
6148                 return AVERROR_INVALIDDATA;
6149             } else {
6150                 return 0;
6151             }
6152         }
6153     } else if (!sc->cenc.default_encrypted_sample) {
6154         // Didn't see 'schm' or 'tenc', so this isn't encrypted.
6155         return 0;
6156     }
6157
6158     encryption_index->auxiliary_info_default_size = avio_r8(pb);
6159     sample_count = avio_rb32(pb);
6160     encryption_index->auxiliary_info_sample_count = sample_count;
6161
6162     if (encryption_index->auxiliary_info_default_size == 0) {
6163         ret = mov_try_read_block(pb, sample_count, &encryption_index->auxiliary_info_sizes);
6164         if (ret < 0) {
6165             av_log(c->fc, AV_LOG_ERROR, "Failed to read the auxiliary info\n");
6166             return ret;
6167         }
6168     }
6169
6170     if (encryption_index->auxiliary_offsets_count) {
6171         return mov_parse_auxiliary_info(c, sc, pb, encryption_index);
6172     }
6173
6174     return 0;
6175 }
6176
6177 static int mov_read_saio(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6178 {
6179     uint64_t *auxiliary_offsets;
6180     MOVEncryptionIndex *encryption_index;
6181     MOVStreamContext *sc;
6182     int i, ret;
6183     unsigned int version, entry_count, aux_info_type, aux_info_param;
6184     unsigned int alloc_size = 0;
6185
6186     ret = get_current_encryption_info(c, &encryption_index, &sc);
6187     if (ret != 1)
6188         return ret;
6189
6190     if (encryption_index->nb_encrypted_samples) {
6191         // This can happen if we have both saio/saiz and senc atoms.
6192         av_log(c->fc, AV_LOG_DEBUG, "Ignoring duplicate encryption info in saio\n");
6193         return 0;
6194     }
6195
6196     if (encryption_index->auxiliary_offsets_count) {
6197         av_log(c->fc, AV_LOG_ERROR, "Duplicate saio atom\n");
6198         return AVERROR_INVALIDDATA;
6199     }
6200
6201     version = avio_r8(pb); /* version */
6202     if (avio_rb24(pb) & 0x01) {  /* flags */
6203         aux_info_type = avio_rb32(pb);
6204         aux_info_param = avio_rb32(pb);
6205         if (sc->cenc.default_encrypted_sample) {
6206             if (aux_info_type != sc->cenc.default_encrypted_sample->scheme) {
6207                 av_log(c->fc, AV_LOG_DEBUG, "Ignoring saio box with non-zero aux_info_type\n");
6208                 return 0;
6209             }
6210             if (aux_info_param != 0) {
6211                 av_log(c->fc, AV_LOG_DEBUG, "Ignoring saio box with non-zero aux_info_type_parameter\n");
6212                 return 0;
6213             }
6214         } else {
6215             // Didn't see 'schm' or 'tenc', so this isn't encrypted.
6216             if ((aux_info_type == MKBETAG('c','e','n','c') ||
6217                  aux_info_type == MKBETAG('c','e','n','s') ||
6218                  aux_info_type == MKBETAG('c','b','c','1') ||
6219                  aux_info_type == MKBETAG('c','b','c','s')) &&
6220                 aux_info_param == 0) {
6221                 av_log(c->fc, AV_LOG_ERROR, "Saw encrypted saio without schm/tenc\n");
6222                 return AVERROR_INVALIDDATA;
6223             } else {
6224                 return 0;
6225             }
6226         }
6227     } else if (!sc->cenc.default_encrypted_sample) {
6228         // Didn't see 'schm' or 'tenc', so this isn't encrypted.
6229         return 0;
6230     }
6231
6232     entry_count = avio_rb32(pb);
6233     if (entry_count >= INT_MAX / sizeof(*auxiliary_offsets))
6234         return AVERROR(ENOMEM);
6235
6236     for (i = 0; i < entry_count && !pb->eof_reached; i++) {
6237         unsigned int min_offsets = FFMIN(FFMAX(i + 1, 1024), entry_count);
6238         auxiliary_offsets = av_fast_realloc(
6239             encryption_index->auxiliary_offsets, &alloc_size,
6240             min_offsets * sizeof(*auxiliary_offsets));
6241         if (!auxiliary_offsets) {
6242             av_freep(&encryption_index->auxiliary_offsets);
6243             return AVERROR(ENOMEM);
6244         }
6245         encryption_index->auxiliary_offsets = auxiliary_offsets;
6246
6247         if (version == 0) {
6248             encryption_index->auxiliary_offsets[i] = avio_rb32(pb);
6249         } else {
6250             encryption_index->auxiliary_offsets[i] = avio_rb64(pb);
6251         }
6252         if (c->frag_index.current >= 0) {
6253             encryption_index->auxiliary_offsets[i] += c->fragment.base_data_offset;
6254         }
6255     }
6256
6257     if (pb->eof_reached) {
6258         av_log(c->fc, AV_LOG_ERROR, "Hit EOF while reading saio\n");
6259         av_freep(&encryption_index->auxiliary_offsets);
6260         return AVERROR_INVALIDDATA;
6261     }
6262
6263     encryption_index->auxiliary_offsets_count = entry_count;
6264
6265     if (encryption_index->auxiliary_info_sample_count) {
6266         return mov_parse_auxiliary_info(c, sc, pb, encryption_index);
6267     }
6268
6269     return 0;
6270 }
6271
6272 static int mov_read_pssh(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6273 {
6274     AVEncryptionInitInfo *info, *old_init_info;
6275     uint8_t **key_ids;
6276     AVStream *st;
6277     uint8_t *side_data, *extra_data, *old_side_data;
6278     size_t side_data_size;
6279     int ret = 0, old_side_data_size;
6280     unsigned int version, kid_count, extra_data_size, alloc_size = 0;
6281
6282     if (c->fc->nb_streams < 1)
6283         return 0;
6284     st = c->fc->streams[c->fc->nb_streams-1];
6285
6286     version = avio_r8(pb); /* version */
6287     avio_rb24(pb);  /* flags */
6288
6289     info = av_encryption_init_info_alloc(/* system_id_size */ 16, /* num_key_ids */ 0,
6290                                          /* key_id_size */ 16, /* data_size */ 0);
6291     if (!info)
6292         return AVERROR(ENOMEM);
6293
6294     if (avio_read(pb, info->system_id, 16) != 16) {
6295         av_log(c->fc, AV_LOG_ERROR, "Failed to read the system id\n");
6296         ret = AVERROR_INVALIDDATA;
6297         goto finish;
6298     }
6299
6300     if (version > 0) {
6301         kid_count = avio_rb32(pb);
6302         if (kid_count >= INT_MAX / sizeof(*key_ids))
6303             return AVERROR(ENOMEM);
6304
6305         for (unsigned int i = 0; i < kid_count && !pb->eof_reached; i++) {
6306             unsigned int min_kid_count = FFMIN(FFMAX(i + 1, 1024), kid_count);
6307             key_ids = av_fast_realloc(info->key_ids, &alloc_size,
6308                                       min_kid_count * sizeof(*key_ids));
6309             if (!key_ids) {
6310                 ret = AVERROR(ENOMEM);
6311                 goto finish;
6312             }
6313             info->key_ids = key_ids;
6314
6315             info->key_ids[i] = av_mallocz(16);
6316             if (!info->key_ids[i]) {
6317                 ret = AVERROR(ENOMEM);
6318                 goto finish;
6319             }
6320             info->num_key_ids = i + 1;
6321
6322             if (avio_read(pb, info->key_ids[i], 16) != 16) {
6323                 av_log(c->fc, AV_LOG_ERROR, "Failed to read the key id\n");
6324                 ret = AVERROR_INVALIDDATA;
6325                 goto finish;
6326             }
6327         }
6328
6329         if (pb->eof_reached) {
6330             av_log(c->fc, AV_LOG_ERROR, "Hit EOF while reading pssh\n");
6331             ret = AVERROR_INVALIDDATA;
6332             goto finish;
6333         }
6334     }
6335
6336     extra_data_size = avio_rb32(pb);
6337     ret = mov_try_read_block(pb, extra_data_size, &extra_data);
6338     if (ret < 0)
6339         goto finish;
6340
6341     av_freep(&info->data);  // malloc(0) may still allocate something.
6342     info->data = extra_data;
6343     info->data_size = extra_data_size;
6344
6345     // If there is existing initialization data, append to the list.
6346     old_side_data = av_stream_get_side_data(st, AV_PKT_DATA_ENCRYPTION_INIT_INFO, &old_side_data_size);
6347     if (old_side_data) {
6348         old_init_info = av_encryption_init_info_get_side_data(old_side_data, old_side_data_size);
6349         if (old_init_info) {
6350             // Append to the end of the list.
6351             for (AVEncryptionInitInfo *cur = old_init_info;; cur = cur->next) {
6352                 if (!cur->next) {
6353                     cur->next = info;
6354                     break;
6355                 }
6356             }
6357             info = old_init_info;
6358         } else {
6359             // Assume existing side-data will be valid, so the only error we could get is OOM.
6360             ret = AVERROR(ENOMEM);
6361             goto finish;
6362         }
6363     }
6364
6365     side_data = av_encryption_init_info_add_side_data(info, &side_data_size);
6366     if (!side_data) {
6367         ret = AVERROR(ENOMEM);
6368         goto finish;
6369     }
6370     ret = av_stream_add_side_data(st, AV_PKT_DATA_ENCRYPTION_INIT_INFO,
6371                                   side_data, side_data_size);
6372     if (ret < 0)
6373         av_free(side_data);
6374
6375 finish:
6376     av_encryption_init_info_free(info);
6377     return ret;
6378 }
6379
6380 static int mov_read_schm(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6381 {
6382     AVStream *st;
6383     MOVStreamContext *sc;
6384
6385     if (c->fc->nb_streams < 1)
6386         return 0;
6387     st = c->fc->streams[c->fc->nb_streams-1];
6388     sc = st->priv_data;
6389
6390     if (sc->pseudo_stream_id != 0) {
6391         av_log(c->fc, AV_LOG_ERROR, "schm boxes are only supported in first sample descriptor\n");
6392         return AVERROR_PATCHWELCOME;
6393     }
6394
6395     if (atom.size < 8)
6396         return AVERROR_INVALIDDATA;
6397
6398     avio_rb32(pb); /* version and flags */
6399
6400     if (!sc->cenc.default_encrypted_sample) {
6401         sc->cenc.default_encrypted_sample = av_encryption_info_alloc(0, 16, 16);
6402         if (!sc->cenc.default_encrypted_sample) {
6403             return AVERROR(ENOMEM);
6404         }
6405     }
6406
6407     sc->cenc.default_encrypted_sample->scheme = avio_rb32(pb);
6408     return 0;
6409 }
6410
6411 static int mov_read_tenc(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6412 {
6413     AVStream *st;
6414     MOVStreamContext *sc;
6415     unsigned int version, pattern, is_protected, iv_size;
6416
6417     if (c->fc->nb_streams < 1)
6418         return 0;
6419     st = c->fc->streams[c->fc->nb_streams-1];
6420     sc = st->priv_data;
6421
6422     if (sc->pseudo_stream_id != 0) {
6423         av_log(c->fc, AV_LOG_ERROR, "tenc atom are only supported in first sample descriptor\n");
6424         return AVERROR_PATCHWELCOME;
6425     }
6426
6427     if (!sc->cenc.default_encrypted_sample) {
6428         sc->cenc.default_encrypted_sample = av_encryption_info_alloc(0, 16, 16);
6429         if (!sc->cenc.default_encrypted_sample) {
6430             return AVERROR(ENOMEM);
6431         }
6432     }
6433
6434     if (atom.size < 20)
6435         return AVERROR_INVALIDDATA;
6436
6437     version = avio_r8(pb); /* version */
6438     avio_rb24(pb); /* flags */
6439
6440     avio_r8(pb); /* reserved */
6441     pattern = avio_r8(pb);
6442
6443     if (version > 0) {
6444         sc->cenc.default_encrypted_sample->crypt_byte_block = pattern >> 4;
6445         sc->cenc.default_encrypted_sample->skip_byte_block = pattern & 0xf;
6446     }
6447
6448     is_protected = avio_r8(pb);
6449     if (is_protected && !sc->cenc.encryption_index) {
6450         // The whole stream should be by-default encrypted.
6451         sc->cenc.encryption_index = av_mallocz(sizeof(MOVEncryptionIndex));
6452         if (!sc->cenc.encryption_index)
6453             return AVERROR(ENOMEM);
6454     }
6455     sc->cenc.per_sample_iv_size = avio_r8(pb);
6456     if (sc->cenc.per_sample_iv_size != 0 && sc->cenc.per_sample_iv_size != 8 &&
6457         sc->cenc.per_sample_iv_size != 16) {
6458         av_log(c->fc, AV_LOG_ERROR, "invalid per-sample IV size value\n");
6459         return AVERROR_INVALIDDATA;
6460     }
6461     if (avio_read(pb, sc->cenc.default_encrypted_sample->key_id, 16) != 16) {
6462         av_log(c->fc, AV_LOG_ERROR, "failed to read the default key ID\n");
6463         return AVERROR_INVALIDDATA;
6464     }
6465
6466     if (is_protected && !sc->cenc.per_sample_iv_size) {
6467         iv_size = avio_r8(pb);
6468         if (iv_size != 8 && iv_size != 16) {
6469             av_log(c->fc, AV_LOG_ERROR, "invalid default_constant_IV_size in tenc atom\n");
6470             return AVERROR_INVALIDDATA;
6471         }
6472
6473         if (avio_read(pb, sc->cenc.default_encrypted_sample->iv, iv_size) != iv_size) {
6474             av_log(c->fc, AV_LOG_ERROR, "failed to read the default IV\n");
6475             return AVERROR_INVALIDDATA;
6476         }
6477     }
6478
6479     return 0;
6480 }
6481
6482 static int mov_read_dfla(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6483 {
6484     AVStream *st;
6485     int last, type, size, ret;
6486     uint8_t buf[4];
6487
6488     if (c->fc->nb_streams < 1)
6489         return 0;
6490     st = c->fc->streams[c->fc->nb_streams-1];
6491
6492     if ((uint64_t)atom.size > (1<<30) || atom.size < 42)
6493         return AVERROR_INVALIDDATA;
6494
6495     /* Check FlacSpecificBox version. */
6496     if (avio_r8(pb) != 0)
6497         return AVERROR_INVALIDDATA;
6498
6499     avio_rb24(pb); /* Flags */
6500
6501     avio_read(pb, buf, sizeof(buf));
6502     flac_parse_block_header(buf, &last, &type, &size);
6503
6504     if (type != FLAC_METADATA_TYPE_STREAMINFO || size != FLAC_STREAMINFO_SIZE) {
6505         av_log(c->fc, AV_LOG_ERROR, "STREAMINFO must be first FLACMetadataBlock\n");
6506         return AVERROR_INVALIDDATA;
6507     }
6508
6509     ret = ff_get_extradata(c->fc, st->codecpar, pb, size);
6510     if (ret < 0)
6511         return ret;
6512
6513     if (!last)
6514         av_log(c->fc, AV_LOG_WARNING, "non-STREAMINFO FLACMetadataBlock(s) ignored\n");
6515
6516     return 0;
6517 }
6518
6519 static int cenc_decrypt(MOVContext *c, MOVStreamContext *sc, AVEncryptionInfo *sample, uint8_t *input, int size)
6520 {
6521     int i, ret;
6522
6523     if (sample->scheme != MKBETAG('c','e','n','c') || sample->crypt_byte_block != 0 || sample->skip_byte_block != 0) {
6524         av_log(c->fc, AV_LOG_ERROR, "Only the 'cenc' encryption scheme is supported\n");
6525         return AVERROR_PATCHWELCOME;
6526     }
6527
6528     if (!sc->cenc.aes_ctr) {
6529         /* initialize the cipher */
6530         sc->cenc.aes_ctr = av_aes_ctr_alloc();
6531         if (!sc->cenc.aes_ctr) {
6532             return AVERROR(ENOMEM);
6533         }
6534
6535         ret = av_aes_ctr_init(sc->cenc.aes_ctr, c->decryption_key);
6536         if (ret < 0) {
6537             return ret;
6538         }
6539     }
6540
6541     av_aes_ctr_set_full_iv(sc->cenc.aes_ctr, sample->iv);
6542
6543     if (!sample->subsample_count)
6544     {
6545         /* decrypt the whole packet */
6546         av_aes_ctr_crypt(sc->cenc.aes_ctr, input, input, size);
6547         return 0;
6548     }
6549
6550     for (i = 0; i < sample->subsample_count; i++)
6551     {
6552         if (sample->subsamples[i].bytes_of_clear_data + sample->subsamples[i].bytes_of_protected_data > size) {
6553             av_log(c->fc, AV_LOG_ERROR, "subsample size exceeds the packet size left\n");
6554             return AVERROR_INVALIDDATA;
6555         }
6556
6557         /* skip the clear bytes */
6558         input += sample->subsamples[i].bytes_of_clear_data;
6559         size -= sample->subsamples[i].bytes_of_clear_data;
6560
6561         /* decrypt the encrypted bytes */
6562         av_aes_ctr_crypt(sc->cenc.aes_ctr, input, input, sample->subsamples[i].bytes_of_protected_data);
6563         input += sample->subsamples[i].bytes_of_protected_data;
6564         size -= sample->subsamples[i].bytes_of_protected_data;
6565     }
6566
6567     if (size > 0) {
6568         av_log(c->fc, AV_LOG_ERROR, "leftover packet bytes after subsample processing\n");
6569         return AVERROR_INVALIDDATA;
6570     }
6571
6572     return 0;
6573 }
6574
6575 static int cenc_filter(MOVContext *mov, AVStream* st, MOVStreamContext *sc, AVPacket *pkt, int current_index)
6576 {
6577     MOVFragmentStreamInfo *frag_stream_info;
6578     MOVEncryptionIndex *encryption_index;
6579     AVEncryptionInfo *encrypted_sample;
6580     int encrypted_index, ret;
6581
6582     frag_stream_info = get_frag_stream_info(&mov->frag_index, mov->frag_index.current, st->id);
6583     encrypted_index = current_index;
6584     encryption_index = NULL;
6585     if (frag_stream_info) {
6586         // Note this only supports encryption info in the first sample descriptor.
6587         if (mov->fragment.stsd_id == 1) {
6588             if (frag_stream_info->encryption_index) {
6589                 encrypted_index = current_index - frag_stream_info->index_entry;
6590                 encryption_index = frag_stream_info->encryption_index;
6591             } else {
6592                 encryption_index = sc->cenc.encryption_index;
6593             }
6594         }
6595     } else {
6596         encryption_index = sc->cenc.encryption_index;
6597     }
6598
6599     if (encryption_index) {
6600         if (encryption_index->auxiliary_info_sample_count &&
6601             !encryption_index->nb_encrypted_samples) {
6602             av_log(mov->fc, AV_LOG_ERROR, "saiz atom found without saio\n");
6603             return AVERROR_INVALIDDATA;
6604         }
6605         if (encryption_index->auxiliary_offsets_count &&
6606             !encryption_index->nb_encrypted_samples) {
6607             av_log(mov->fc, AV_LOG_ERROR, "saio atom found without saiz\n");
6608             return AVERROR_INVALIDDATA;
6609         }
6610
6611         if (!encryption_index->nb_encrypted_samples) {
6612             // Full-sample encryption with default settings.
6613             encrypted_sample = sc->cenc.default_encrypted_sample;
6614         } else if (encrypted_index >= 0 && encrypted_index < encryption_index->nb_encrypted_samples) {
6615             // Per-sample setting override.
6616             encrypted_sample = encryption_index->encrypted_samples[encrypted_index];
6617         } else {
6618             av_log(mov->fc, AV_LOG_ERROR, "Incorrect number of samples in encryption info\n");
6619             return AVERROR_INVALIDDATA;
6620         }
6621
6622         if (mov->decryption_key) {
6623             return cenc_decrypt(mov, sc, encrypted_sample, pkt->data, pkt->size);
6624         } else {
6625             size_t size;
6626             uint8_t *side_data = av_encryption_info_add_side_data(encrypted_sample, &size);
6627             if (!side_data)
6628                 return AVERROR(ENOMEM);
6629             ret = av_packet_add_side_data(pkt, AV_PKT_DATA_ENCRYPTION_INFO, side_data, size);
6630             if (ret < 0)
6631                 av_free(side_data);
6632             return ret;
6633         }
6634     }
6635
6636     return 0;
6637 }
6638
6639 static int mov_read_dops(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6640 {
6641     const int OPUS_SEEK_PREROLL_MS = 80;
6642     AVStream *st;
6643     size_t size;
6644     uint16_t pre_skip;
6645
6646     if (c->fc->nb_streams < 1)
6647         return 0;
6648     st = c->fc->streams[c->fc->nb_streams-1];
6649
6650     if ((uint64_t)atom.size > (1<<30) || atom.size < 11)
6651         return AVERROR_INVALIDDATA;
6652
6653     /* Check OpusSpecificBox version. */
6654     if (avio_r8(pb) != 0) {
6655         av_log(c->fc, AV_LOG_ERROR, "unsupported OpusSpecificBox version\n");
6656         return AVERROR_INVALIDDATA;
6657     }
6658
6659     /* OpusSpecificBox size plus magic for Ogg OpusHead header. */
6660     size = atom.size + 8;
6661
6662     if (ff_alloc_extradata(st->codecpar, size))
6663         return AVERROR(ENOMEM);
6664
6665     AV_WL32(st->codecpar->extradata, MKTAG('O','p','u','s'));
6666     AV_WL32(st->codecpar->extradata + 4, MKTAG('H','e','a','d'));
6667     AV_WB8(st->codecpar->extradata + 8, 1); /* OpusHead version */
6668     avio_read(pb, st->codecpar->extradata + 9, size - 9);
6669
6670     /* OpusSpecificBox is stored in big-endian, but OpusHead is
6671        little-endian; aside from the preceeding magic and version they're
6672        otherwise currently identical.  Data after output gain at offset 16
6673        doesn't need to be bytewapped. */
6674     pre_skip = AV_RB16(st->codecpar->extradata + 10);
6675     AV_WL16(st->codecpar->extradata + 10, pre_skip);
6676     AV_WL32(st->codecpar->extradata + 12, AV_RB32(st->codecpar->extradata + 12));
6677     AV_WL16(st->codecpar->extradata + 16, AV_RB16(st->codecpar->extradata + 16));
6678
6679     st->codecpar->initial_padding = pre_skip;
6680     st->codecpar->seek_preroll = av_rescale_q(OPUS_SEEK_PREROLL_MS,
6681                                               (AVRational){1, 1000},
6682                                               (AVRational){1, 48000});
6683
6684     return 0;
6685 }
6686
6687 static const MOVParseTableEntry mov_default_parse_table[] = {
6688 { MKTAG('A','C','L','R'), mov_read_aclr },
6689 { MKTAG('A','P','R','G'), mov_read_avid },
6690 { MKTAG('A','A','L','P'), mov_read_avid },
6691 { MKTAG('A','R','E','S'), mov_read_ares },
6692 { MKTAG('a','v','s','s'), mov_read_avss },
6693 { MKTAG('a','v','1','C'), mov_read_av1c },
6694 { MKTAG('c','h','p','l'), mov_read_chpl },
6695 { MKTAG('c','o','6','4'), mov_read_stco },
6696 { MKTAG('c','o','l','r'), mov_read_colr },
6697 { MKTAG('c','t','t','s'), mov_read_ctts }, /* composition time to sample */
6698 { MKTAG('d','i','n','f'), mov_read_default },
6699 { MKTAG('D','p','x','E'), mov_read_dpxe },
6700 { MKTAG('d','r','e','f'), mov_read_dref },
6701 { MKTAG('e','d','t','s'), mov_read_default },
6702 { MKTAG('e','l','s','t'), mov_read_elst },
6703 { MKTAG('e','n','d','a'), mov_read_enda },
6704 { MKTAG('f','i','e','l'), mov_read_fiel },
6705 { MKTAG('a','d','r','m'), mov_read_adrm },
6706 { MKTAG('f','t','y','p'), mov_read_ftyp },
6707 { MKTAG('g','l','b','l'), mov_read_glbl },
6708 { MKTAG('h','d','l','r'), mov_read_hdlr },
6709 { MKTAG('i','l','s','t'), mov_read_ilst },
6710 { MKTAG('j','p','2','h'), mov_read_jp2h },
6711 { MKTAG('m','d','a','t'), mov_read_mdat },
6712 { MKTAG('m','d','h','d'), mov_read_mdhd },
6713 { MKTAG('m','d','i','a'), mov_read_default },
6714 { MKTAG('m','e','t','a'), mov_read_meta },
6715 { MKTAG('m','i','n','f'), mov_read_default },
6716 { MKTAG('m','o','o','f'), mov_read_moof },
6717 { MKTAG('m','o','o','v'), mov_read_moov },
6718 { MKTAG('m','v','e','x'), mov_read_default },
6719 { MKTAG('m','v','h','d'), mov_read_mvhd },
6720 { MKTAG('S','M','I',' '), mov_read_svq3 },
6721 { MKTAG('a','l','a','c'), mov_read_alac }, /* alac specific atom */
6722 { MKTAG('a','v','c','C'), mov_read_glbl },
6723 { MKTAG('p','a','s','p'), mov_read_pasp },
6724 { MKTAG('s','i','d','x'), mov_read_sidx },
6725 { MKTAG('s','t','b','l'), mov_read_default },
6726 { MKTAG('s','t','c','o'), mov_read_stco },
6727 { MKTAG('s','t','p','s'), mov_read_stps },
6728 { MKTAG('s','t','r','f'), mov_read_strf },
6729 { MKTAG('s','t','s','c'), mov_read_stsc },
6730 { MKTAG('s','t','s','d'), mov_read_stsd }, /* sample description */
6731 { MKTAG('s','t','s','s'), mov_read_stss }, /* sync sample */
6732 { MKTAG('s','t','s','z'), mov_read_stsz }, /* sample size */
6733 { MKTAG('s','t','t','s'), mov_read_stts },
6734 { MKTAG('s','t','z','2'), mov_read_stsz }, /* compact sample size */
6735 { MKTAG('t','k','h','d'), mov_read_tkhd }, /* track header */
6736 { MKTAG('t','f','d','t'), mov_read_tfdt },
6737 { MKTAG('t','f','h','d'), mov_read_tfhd }, /* track fragment header */
6738 { MKTAG('t','r','a','k'), mov_read_trak },
6739 { MKTAG('t','r','a','f'), mov_read_default },
6740 { MKTAG('t','r','e','f'), mov_read_default },
6741 { MKTAG('t','m','c','d'), mov_read_tmcd },
6742 { MKTAG('c','h','a','p'), mov_read_chap },
6743 { MKTAG('t','r','e','x'), mov_read_trex },
6744 { MKTAG('t','r','u','n'), mov_read_trun },
6745 { MKTAG('u','d','t','a'), mov_read_default },
6746 { MKTAG('w','a','v','e'), mov_read_wave },
6747 { MKTAG('e','s','d','s'), mov_read_esds },
6748 { MKTAG('d','a','c','3'), mov_read_dac3 }, /* AC-3 info */
6749 { MKTAG('d','e','c','3'), mov_read_dec3 }, /* EAC-3 info */
6750 { MKTAG('d','d','t','s'), mov_read_ddts }, /* DTS audio descriptor */
6751 { MKTAG('w','i','d','e'), mov_read_wide }, /* place holder */
6752 { MKTAG('w','f','e','x'), mov_read_wfex },
6753 { MKTAG('c','m','o','v'), mov_read_cmov },
6754 { MKTAG('c','h','a','n'), mov_read_chan }, /* channel layout */
6755 { MKTAG('d','v','c','1'), mov_read_dvc1 },
6756 { MKTAG('s','b','g','p'), mov_read_sbgp },
6757 { MKTAG('h','v','c','C'), mov_read_glbl },
6758 { MKTAG('u','u','i','d'), mov_read_uuid },
6759 { MKTAG('C','i','n', 0x8e), mov_read_targa_y216 },
6760 { MKTAG('f','r','e','e'), mov_read_free },
6761 { MKTAG('-','-','-','-'), mov_read_custom },
6762 { MKTAG('s','i','n','f'), mov_read_default },
6763 { MKTAG('f','r','m','a'), mov_read_frma },
6764 { MKTAG('s','e','n','c'), mov_read_senc },
6765 { MKTAG('s','a','i','z'), mov_read_saiz },
6766 { MKTAG('s','a','i','o'), mov_read_saio },
6767 { MKTAG('p','s','s','h'), mov_read_pssh },
6768 { MKTAG('s','c','h','m'), mov_read_schm },
6769 { MKTAG('s','c','h','i'), mov_read_default },
6770 { MKTAG('t','e','n','c'), mov_read_tenc },
6771 { MKTAG('d','f','L','a'), mov_read_dfla },
6772 { MKTAG('s','t','3','d'), mov_read_st3d }, /* stereoscopic 3D video box */
6773 { MKTAG('s','v','3','d'), mov_read_sv3d }, /* spherical video box */
6774 { MKTAG('d','O','p','s'), mov_read_dops },
6775 { MKTAG('S','m','D','m'), mov_read_smdm },
6776 { MKTAG('C','o','L','L'), mov_read_coll },
6777 { MKTAG('v','p','c','C'), mov_read_vpcc },
6778 { MKTAG('m','d','c','v'), mov_read_mdcv },
6779 { MKTAG('c','l','l','i'), mov_read_clli },
6780 { 0, NULL }
6781 };
6782
6783 static int mov_read_default(MOVContext *c, AVIOContext *pb, MOVAtom atom)
6784 {
6785     int64_t total_size = 0;
6786     MOVAtom a;
6787     int i;
6788
6789     if (c->atom_depth > 10) {
6790         av_log(c->fc, AV_LOG_ERROR, "Atoms too deeply nested\n");
6791         return AVERROR_INVALIDDATA;
6792     }
6793     c->atom_depth ++;
6794
6795     if (atom.size < 0)
6796         atom.size = INT64_MAX;
6797     while (total_size <= atom.size - 8 && !avio_feof(pb)) {
6798         int (*parse)(MOVContext*, AVIOContext*, MOVAtom) = NULL;
6799         a.size = atom.size;
6800         a.type=0;
6801         if (atom.size >= 8) {
6802             a.size = avio_rb32(pb);
6803             a.type = avio_rl32(pb);
6804             if (a.type == MKTAG('f','r','e','e') &&
6805                 a.size >= 8 &&
6806                 c->fc->strict_std_compliance < FF_COMPLIANCE_STRICT &&
6807                 c->moov_retry) {
6808                 uint8_t buf[8];
6809                 uint32_t *type = (uint32_t *)buf + 1;
6810                 if (avio_read(pb, buf, 8) != 8)
6811                     return AVERROR_INVALIDDATA;
6812                 avio_seek(pb, -8, SEEK_CUR);
6813                 if (*type == MKTAG('m','v','h','d') ||
6814                     *type == MKTAG('c','m','o','v')) {
6815                     av_log(c->fc, AV_LOG_ERROR, "Detected moov in a free atom.\n");
6816                     a.type = MKTAG('m','o','o','v');
6817                 }
6818             }
6819             if (atom.type != MKTAG('r','o','o','t') &&
6820                 atom.type != MKTAG('m','o','o','v'))
6821             {
6822                 if (a.type == MKTAG('t','r','a','k') || a.type == MKTAG('m','d','a','t'))
6823                 {
6824                     av_log(c->fc, AV_LOG_ERROR, "Broken file, trak/mdat not at top-level\n");
6825                     avio_skip(pb, -8);
6826                     c->atom_depth --;
6827                     return 0;
6828                 }
6829             }
6830             total_size += 8;
6831             if (a.size == 1 && total_size + 8 <= atom.size) { /* 64 bit extended size */
6832                 a.size = avio_rb64(pb) - 8;
6833                 total_size += 8;
6834             }
6835         }
6836         av_log(c->fc, AV_LOG_TRACE, "type:'%s' parent:'%s' sz: %"PRId64" %"PRId64" %"PRId64"\n",
6837                av_fourcc2str(a.type), av_fourcc2str(atom.type), a.size, total_size, atom.size);
6838         if (a.size == 0) {
6839             a.size = atom.size - total_size + 8;
6840         }
6841         a.size -= 8;
6842         if (a.size < 0)
6843             break;
6844         a.size = FFMIN(a.size, atom.size - total_size);
6845
6846         for (i = 0; mov_default_parse_table[i].type; i++)
6847             if (mov_default_parse_table[i].type == a.type) {
6848                 parse = mov_default_parse_table[i].parse;
6849                 break;
6850             }
6851
6852         // container is user data
6853         if (!parse && (atom.type == MKTAG('u','d','t','a') ||
6854                        atom.type == MKTAG('i','l','s','t')))
6855             parse = mov_read_udta_string;
6856
6857         // Supports parsing the QuickTime Metadata Keys.
6858         // https://developer.apple.com/library/mac/documentation/QuickTime/QTFF/Metadata/Metadata.html
6859         if (!parse && c->found_hdlr_mdta &&
6860             atom.type == MKTAG('m','e','t','a') &&
6861             a.type == MKTAG('k','e','y','s')) {
6862             parse = mov_read_keys;
6863         }
6864
6865         if (!parse) { /* skip leaf atoms data */
6866             avio_skip(pb, a.size);
6867         } else {
6868             int64_t start_pos = avio_tell(pb);
6869             int64_t left;
6870             int err = parse(c, pb, a);
6871             if (err < 0) {
6872                 c->atom_depth --;
6873                 return err;
6874             }
6875             if (c->found_moov && c->found_mdat &&
6876                 ((!(pb->seekable & AVIO_SEEKABLE_NORMAL) || c->fc->flags & AVFMT_FLAG_IGNIDX || c->frag_index.complete) ||
6877                  start_pos + a.size == avio_size(pb))) {
6878                 if (!(pb->seekable & AVIO_SEEKABLE_NORMAL) || c->fc->flags & AVFMT_FLAG_IGNIDX || c->frag_index.complete)
6879                     c->next_root_atom = start_pos + a.size;
6880                 c->atom_depth --;
6881                 return 0;
6882             }
6883             left = a.size - avio_tell(pb) + start_pos;
6884             if (left > 0) /* skip garbage at atom end */
6885                 avio_skip(pb, left);
6886             else if (left < 0) {
6887                 av_log(c->fc, AV_LOG_WARNING,
6888                        "overread end of atom '%.4s' by %"PRId64" bytes\n",
6889                        (char*)&a.type, -left);
6890                 avio_seek(pb, left, SEEK_CUR);
6891             }
6892         }
6893
6894         total_size += a.size;
6895     }
6896
6897     if (total_size < atom.size && atom.size < 0x7ffff)
6898         avio_skip(pb, atom.size - total_size);
6899
6900     c->atom_depth --;
6901     return 0;
6902 }
6903
6904 static int mov_probe(const AVProbeData *p)
6905 {
6906     int64_t offset;
6907     uint32_t tag;
6908     int score = 0;
6909     int moov_offset = -1;
6910
6911     /* check file header */
6912     offset = 0;
6913     for (;;) {
6914         /* ignore invalid offset */
6915         if ((offset + 8) > (unsigned int)p->buf_size)
6916             break;
6917         tag = AV_RL32(p->buf + offset + 4);
6918         switch(tag) {
6919         /* check for obvious tags */
6920         case MKTAG('m','o','o','v'):
6921             moov_offset = offset + 4;
6922         case MKTAG('m','d','a','t'):
6923         case MKTAG('p','n','o','t'): /* detect movs with preview pics like ew.mov and april.mov */
6924         case MKTAG('u','d','t','a'): /* Packet Video PVAuthor adds this and a lot of more junk */
6925         case MKTAG('f','t','y','p'):
6926             if (AV_RB32(p->buf+offset) < 8 &&
6927                 (AV_RB32(p->buf+offset) != 1 ||
6928                  offset + 12 > (unsigned int)p->buf_size ||
6929                  AV_RB64(p->buf+offset + 8) == 0)) {
6930                 score = FFMAX(score, AVPROBE_SCORE_EXTENSION);
6931             } else if (tag == MKTAG('f','t','y','p') &&
6932                        (   AV_RL32(p->buf + offset + 8) == MKTAG('j','p','2',' ')
6933                         || AV_RL32(p->buf + offset + 8) == MKTAG('j','p','x',' ')
6934                     )) {
6935                 score = FFMAX(score, 5);
6936             } else {
6937                 score = AVPROBE_SCORE_MAX;
6938             }
6939             offset = FFMAX(4, AV_RB32(p->buf+offset)) + offset;
6940             break;
6941         /* those are more common words, so rate then a bit less */
6942         case MKTAG('e','d','i','w'): /* xdcam files have reverted first tags */
6943         case MKTAG('w','i','d','e'):
6944         case MKTAG('f','r','e','e'):
6945         case MKTAG('j','u','n','k'):
6946         case MKTAG('p','i','c','t'):
6947             score  = FFMAX(score, AVPROBE_SCORE_MAX - 5);
6948             offset = FFMAX(4, AV_RB32(p->buf+offset)) + offset;
6949             break;
6950         case MKTAG(0x82,0x82,0x7f,0x7d):
6951         case MKTAG('s','k','i','p'):
6952         case MKTAG('u','u','i','d'):
6953         case MKTAG('p','r','f','l'):
6954             /* if we only find those cause probedata is too small at least rate them */
6955             score  = FFMAX(score, AVPROBE_SCORE_EXTENSION);
6956             offset = FFMAX(4, AV_RB32(p->buf+offset)) + offset;
6957             break;
6958         default:
6959             offset = FFMAX(4, AV_RB32(p->buf+offset)) + offset;
6960         }
6961     }
6962     if(score > AVPROBE_SCORE_MAX - 50 && moov_offset != -1) {
6963         /* moov atom in the header - we should make sure that this is not a
6964          * MOV-packed MPEG-PS */
6965         offset = moov_offset;
6966
6967         while(offset < (p->buf_size - 16)){ /* Sufficient space */
6968                /* We found an actual hdlr atom */
6969             if(AV_RL32(p->buf + offset     ) == MKTAG('h','d','l','r') &&
6970                AV_RL32(p->buf + offset +  8) == MKTAG('m','h','l','r') &&
6971                AV_RL32(p->buf + offset + 12) == MKTAG('M','P','E','G')){
6972                 av_log(NULL, AV_LOG_WARNING, "Found media data tag MPEG indicating this is a MOV-packed MPEG-PS.\n");
6973                 /* We found a media handler reference atom describing an
6974                  * MPEG-PS-in-MOV, return a
6975                  * low score to force expanding the probe window until
6976                  * mpegps_probe finds what it needs */
6977                 return 5;
6978             }else
6979                 /* Keep looking */
6980                 offset+=2;
6981         }
6982     }
6983
6984     return score;
6985 }
6986
6987 // must be done after parsing all trak because there's no order requirement
6988 static void mov_read_chapters(AVFormatContext *s)
6989 {
6990     MOVContext *mov = s->priv_data;
6991     AVStream *st;
6992     MOVStreamContext *sc;
6993     int64_t cur_pos;
6994     int i, j;
6995     int chapter_track;
6996
6997     for (j = 0; j < mov->nb_chapter_tracks; j++) {
6998         chapter_track = mov->chapter_tracks[j];
6999         st = NULL;
7000         for (i = 0; i < s->nb_streams; i++)
7001             if (s->streams[i]->id == chapter_track) {
7002                 st = s->streams[i];
7003                 break;
7004             }
7005         if (!st) {
7006             av_log(s, AV_LOG_ERROR, "Referenced QT chapter track not found\n");
7007             continue;
7008         }
7009
7010         sc = st->priv_data;
7011         cur_pos = avio_tell(sc->pb);
7012
7013         if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {
7014             st->disposition |= AV_DISPOSITION_ATTACHED_PIC | AV_DISPOSITION_TIMED_THUMBNAILS;
7015             if (st->nb_index_entries) {
7016                 // Retrieve the first frame, if possible
7017                 AVPacket pkt;
7018                 AVIndexEntry *sample = &st->index_entries[0];
7019                 if (avio_seek(sc->pb, sample->pos, SEEK_SET) != sample->pos) {
7020                     av_log(s, AV_LOG_ERROR, "Failed to retrieve first frame\n");
7021                     goto finish;
7022                 }
7023
7024                 if (av_get_packet(sc->pb, &pkt, sample->size) < 0)
7025                     goto finish;
7026
7027                 st->attached_pic              = pkt;
7028                 st->attached_pic.stream_index = st->index;
7029                 st->attached_pic.flags       |= AV_PKT_FLAG_KEY;
7030             }
7031         } else {
7032             st->codecpar->codec_type = AVMEDIA_TYPE_DATA;
7033             st->codecpar->codec_id = AV_CODEC_ID_BIN_DATA;
7034             st->discard = AVDISCARD_ALL;
7035             for (i = 0; i < st->nb_index_entries; i++) {
7036                 AVIndexEntry *sample = &st->index_entries[i];
7037                 int64_t end = i+1 < st->nb_index_entries ? st->index_entries[i+1].timestamp : st->duration;
7038                 uint8_t *title;
7039                 uint16_t ch;
7040                 int len, title_len;
7041
7042                 if (end < sample->timestamp) {
7043                     av_log(s, AV_LOG_WARNING, "ignoring stream duration which is shorter than chapters\n");
7044                     end = AV_NOPTS_VALUE;
7045                 }
7046
7047                 if (avio_seek(sc->pb, sample->pos, SEEK_SET) != sample->pos) {
7048                     av_log(s, AV_LOG_ERROR, "Chapter %d not found in file\n", i);
7049                     goto finish;
7050                 }
7051
7052                 // the first two bytes are the length of the title
7053                 len = avio_rb16(sc->pb);
7054                 if (len > sample->size-2)
7055                     continue;
7056                 title_len = 2*len + 1;
7057                 if (!(title = av_mallocz(title_len)))
7058                     goto finish;
7059
7060                 // The samples could theoretically be in any encoding if there's an encd
7061                 // atom following, but in practice are only utf-8 or utf-16, distinguished
7062                 // instead by the presence of a BOM
7063                 if (!len) {
7064                     title[0] = 0;
7065                 } else {
7066                     ch = avio_rb16(sc->pb);
7067                     if (ch == 0xfeff)
7068                         avio_get_str16be(sc->pb, len, title, title_len);
7069                     else if (ch == 0xfffe)
7070                         avio_get_str16le(sc->pb, len, title, title_len);
7071                     else {
7072                         AV_WB16(title, ch);
7073                         if (len == 1 || len == 2)
7074                             title[len] = 0;
7075                         else
7076                             avio_get_str(sc->pb, INT_MAX, title + 2, len - 1);
7077                     }
7078                 }
7079
7080                 avpriv_new_chapter(s, i, st->time_base, sample->timestamp, end, title);
7081                 av_freep(&title);
7082             }
7083         }
7084 finish:
7085         avio_seek(sc->pb, cur_pos, SEEK_SET);
7086     }
7087 }
7088
7089 static int parse_timecode_in_framenum_format(AVFormatContext *s, AVStream *st,
7090                                              uint32_t value, int flags)
7091 {
7092     AVTimecode tc;
7093     char buf[AV_TIMECODE_STR_SIZE];
7094     AVRational rate = st->avg_frame_rate;
7095     int ret = av_timecode_init(&tc, rate, flags, 0, s);
7096     if (ret < 0)
7097         return ret;
7098     av_dict_set(&st->metadata, "timecode",
7099                 av_timecode_make_string(&tc, buf, value), 0);
7100     return 0;
7101 }
7102
7103 static int mov_read_rtmd_track(AVFormatContext *s, AVStream *st)
7104 {
7105     MOVStreamContext *sc = st->priv_data;
7106     char buf[AV_TIMECODE_STR_SIZE];
7107     int64_t cur_pos = avio_tell(sc->pb);
7108     int hh, mm, ss, ff, drop;
7109
7110     if (!st->nb_index_entries)
7111         return -1;
7112
7113     avio_seek(sc->pb, st->index_entries->pos, SEEK_SET);
7114     avio_skip(s->pb, 13);
7115     hh = avio_r8(s->pb);
7116     mm = avio_r8(s->pb);
7117     ss = avio_r8(s->pb);
7118     drop = avio_r8(s->pb);
7119     ff = avio_r8(s->pb);
7120     snprintf(buf, AV_TIMECODE_STR_SIZE, "%02d:%02d:%02d%c%02d",
7121              hh, mm, ss, drop ? ';' : ':', ff);
7122     av_dict_set(&st->metadata, "timecode", buf, 0);
7123
7124     avio_seek(sc->pb, cur_pos, SEEK_SET);
7125     return 0;
7126 }
7127
7128 static int mov_read_timecode_track(AVFormatContext *s, AVStream *st)
7129 {
7130     MOVStreamContext *sc = st->priv_data;
7131     int flags = 0;
7132     int64_t cur_pos = avio_tell(sc->pb);
7133     uint32_t value;
7134
7135     if (!st->nb_index_entries)
7136         return -1;
7137
7138     avio_seek(sc->pb, st->index_entries->pos, SEEK_SET);
7139     value = avio_rb32(s->pb);
7140
7141     if (sc->tmcd_flags & 0x0001) flags |= AV_TIMECODE_FLAG_DROPFRAME;
7142     if (sc->tmcd_flags & 0x0002) flags |= AV_TIMECODE_FLAG_24HOURSMAX;
7143     if (sc->tmcd_flags & 0x0004) flags |= AV_TIMECODE_FLAG_ALLOWNEGATIVE;
7144
7145     /* Assume Counter flag is set to 1 in tmcd track (even though it is likely
7146      * not the case) and thus assume "frame number format" instead of QT one.
7147      * No sample with tmcd track can be found with a QT timecode at the moment,
7148      * despite what the tmcd track "suggests" (Counter flag set to 0 means QT
7149      * format). */
7150     parse_timecode_in_framenum_format(s, st, value, flags);
7151
7152     avio_seek(sc->pb, cur_pos, SEEK_SET);
7153     return 0;
7154 }
7155
7156 static void mov_free_encryption_index(MOVEncryptionIndex **index) {
7157     int i;
7158     if (!index || !*index) return;
7159     for (i = 0; i < (*index)->nb_encrypted_samples; i++) {
7160         av_encryption_info_free((*index)->encrypted_samples[i]);
7161     }
7162     av_freep(&(*index)->encrypted_samples);
7163     av_freep(&(*index)->auxiliary_info_sizes);
7164     av_freep(&(*index)->auxiliary_offsets);
7165     av_freep(index);
7166 }
7167
7168 static int mov_read_close(AVFormatContext *s)
7169 {
7170     MOVContext *mov = s->priv_data;
7171     int i, j;
7172
7173     for (i = 0; i < s->nb_streams; i++) {
7174         AVStream *st = s->streams[i];
7175         MOVStreamContext *sc = st->priv_data;
7176
7177         if (!sc)
7178             continue;
7179
7180         av_freep(&sc->ctts_data);
7181         for (j = 0; j < sc->drefs_count; j++) {
7182             av_freep(&sc->drefs[j].path);
7183             av_freep(&sc->drefs[j].dir);
7184         }
7185         av_freep(&sc->drefs);
7186
7187         sc->drefs_count = 0;
7188
7189         if (!sc->pb_is_copied)
7190             ff_format_io_close(s, &sc->pb);
7191
7192         sc->pb = NULL;
7193         av_freep(&sc->chunk_offsets);
7194         av_freep(&sc->stsc_data);
7195         av_freep(&sc->sample_sizes);
7196         av_freep(&sc->keyframes);
7197         av_freep(&sc->stts_data);
7198         av_freep(&sc->stps_data);
7199         av_freep(&sc->elst_data);
7200         av_freep(&sc->rap_group);
7201         av_freep(&sc->display_matrix);
7202         av_freep(&sc->index_ranges);
7203
7204         if (sc->extradata)
7205             for (j = 0; j < sc->stsd_count; j++)
7206                 av_free(sc->extradata[j]);
7207         av_freep(&sc->extradata);
7208         av_freep(&sc->extradata_size);
7209
7210         mov_free_encryption_index(&sc->cenc.encryption_index);
7211         av_encryption_info_free(sc->cenc.default_encrypted_sample);
7212         av_aes_ctr_free(sc->cenc.aes_ctr);
7213
7214         av_freep(&sc->stereo3d);
7215         av_freep(&sc->spherical);
7216         av_freep(&sc->mastering);
7217         av_freep(&sc->coll);
7218     }
7219
7220     if (mov->dv_demux) {
7221         avformat_free_context(mov->dv_fctx);
7222         mov->dv_fctx = NULL;
7223     }
7224
7225     if (mov->meta_keys) {
7226         for (i = 1; i < mov->meta_keys_count; i++) {
7227             av_freep(&mov->meta_keys[i]);
7228         }
7229         av_freep(&mov->meta_keys);
7230     }
7231
7232     av_freep(&mov->trex_data);
7233     av_freep(&mov->bitrates);
7234
7235     for (i = 0; i < mov->frag_index.nb_items; i++) {
7236         MOVFragmentStreamInfo *frag = mov->frag_index.item[i].stream_info;
7237         for (j = 0; j < mov->frag_index.item[i].nb_stream_info; j++) {
7238             mov_free_encryption_index(&frag[j].encryption_index);
7239         }
7240         av_freep(&mov->frag_index.item[i].stream_info);
7241     }
7242     av_freep(&mov->frag_index.item);
7243
7244     av_freep(&mov->aes_decrypt);
7245     av_freep(&mov->chapter_tracks);
7246
7247     return 0;
7248 }
7249
7250 static int tmcd_is_referenced(AVFormatContext *s, int tmcd_id)
7251 {
7252     int i;
7253
7254     for (i = 0; i < s->nb_streams; i++) {
7255         AVStream *st = s->streams[i];
7256         MOVStreamContext *sc = st->priv_data;
7257
7258         if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO &&
7259             sc->timecode_track == tmcd_id)
7260             return 1;
7261     }
7262     return 0;
7263 }
7264
7265 /* look for a tmcd track not referenced by any video track, and export it globally */
7266 static void export_orphan_timecode(AVFormatContext *s)
7267 {
7268     int i;
7269
7270     for (i = 0; i < s->nb_streams; i++) {
7271         AVStream *st = s->streams[i];
7272
7273         if (st->codecpar->codec_tag  == MKTAG('t','m','c','d') &&
7274             !tmcd_is_referenced(s, i + 1)) {
7275             AVDictionaryEntry *tcr = av_dict_get(st->metadata, "timecode", NULL, 0);
7276             if (tcr) {
7277                 av_dict_set(&s->metadata, "timecode", tcr->value, 0);
7278                 break;
7279             }
7280         }
7281     }
7282 }
7283
7284 static int read_tfra(MOVContext *mov, AVIOContext *f)
7285 {
7286     int version, fieldlength, i, j;
7287     int64_t pos = avio_tell(f);
7288     uint32_t size = avio_rb32(f);
7289     unsigned track_id, item_count;
7290
7291     if (avio_rb32(f) != MKBETAG('t', 'f', 'r', 'a')) {
7292         return 1;
7293     }
7294     av_log(mov->fc, AV_LOG_VERBOSE, "found tfra\n");
7295
7296     version = avio_r8(f);
7297     avio_rb24(f);
7298     track_id = avio_rb32(f);
7299     fieldlength = avio_rb32(f);
7300     item_count = avio_rb32(f);
7301     for (i = 0; i < item_count; i++) {
7302         int64_t time, offset;
7303         int index;
7304         MOVFragmentStreamInfo * frag_stream_info;
7305
7306         if (avio_feof(f)) {
7307             return AVERROR_INVALIDDATA;
7308         }
7309
7310         if (version == 1) {
7311             time   = avio_rb64(f);
7312             offset = avio_rb64(f);
7313         } else {
7314             time   = avio_rb32(f);
7315             offset = avio_rb32(f);
7316         }
7317
7318         // The first sample of each stream in a fragment is always a random
7319         // access sample.  So it's entry in the tfra can be used as the
7320         // initial PTS of the fragment.
7321         index = update_frag_index(mov, offset);
7322         frag_stream_info = get_frag_stream_info(&mov->frag_index, index, track_id);
7323         if (frag_stream_info &&
7324             frag_stream_info->first_tfra_pts == AV_NOPTS_VALUE)
7325             frag_stream_info->first_tfra_pts = time;
7326
7327         for (j = 0; j < ((fieldlength >> 4) & 3) + 1; j++)
7328             avio_r8(f);
7329         for (j = 0; j < ((fieldlength >> 2) & 3) + 1; j++)
7330             avio_r8(f);
7331         for (j = 0; j < ((fieldlength >> 0) & 3) + 1; j++)
7332             avio_r8(f);
7333     }
7334
7335     avio_seek(f, pos + size, SEEK_SET);
7336     return 0;
7337 }
7338
7339 static int mov_read_mfra(MOVContext *c, AVIOContext *f)
7340 {
7341     int64_t stream_size = avio_size(f);
7342     int64_t original_pos = avio_tell(f);
7343     int64_t seek_ret;
7344     int32_t mfra_size;
7345     int ret = -1;
7346     if ((seek_ret = avio_seek(f, stream_size - 4, SEEK_SET)) < 0) {
7347         ret = seek_ret;
7348         goto fail;
7349     }
7350     mfra_size = avio_rb32(f);
7351     if (mfra_size < 0 || mfra_size > stream_size) {
7352         av_log(c->fc, AV_LOG_DEBUG, "doesn't look like mfra (unreasonable size)\n");
7353         goto fail;
7354     }
7355     if ((seek_ret = avio_seek(f, -mfra_size, SEEK_CUR)) < 0) {
7356         ret = seek_ret;
7357         goto fail;
7358     }
7359     if (avio_rb32(f) != mfra_size) {
7360         av_log(c->fc, AV_LOG_DEBUG, "doesn't look like mfra (size mismatch)\n");
7361         goto fail;
7362     }
7363     if (avio_rb32(f) != MKBETAG('m', 'f', 'r', 'a')) {
7364         av_log(c->fc, AV_LOG_DEBUG, "doesn't look like mfra (tag mismatch)\n");
7365         goto fail;
7366     }
7367     av_log(c->fc, AV_LOG_VERBOSE, "stream has mfra\n");
7368     do {
7369         ret = read_tfra(c, f);
7370         if (ret < 0)
7371             goto fail;
7372     } while (!ret);
7373     ret = 0;
7374 fail:
7375     seek_ret = avio_seek(f, original_pos, SEEK_SET);
7376     if (seek_ret < 0) {
7377         av_log(c->fc, AV_LOG_ERROR,
7378                "failed to seek back after looking for mfra\n");
7379         ret = seek_ret;
7380     }
7381     return ret;
7382 }
7383
7384 static int mov_read_header(AVFormatContext *s)
7385 {
7386     MOVContext *mov = s->priv_data;
7387     AVIOContext *pb = s->pb;
7388     int j, err;
7389     MOVAtom atom = { AV_RL32("root") };
7390     int i;
7391
7392     if (mov->decryption_key_len != 0 && mov->decryption_key_len != AES_CTR_KEY_SIZE) {
7393         av_log(s, AV_LOG_ERROR, "Invalid decryption key len %d expected %d\n",
7394             mov->decryption_key_len, AES_CTR_KEY_SIZE);
7395         return AVERROR(EINVAL);
7396     }
7397
7398     mov->fc = s;
7399     mov->trak_index = -1;
7400     /* .mov and .mp4 aren't streamable anyway (only progressive download if moov is before mdat) */
7401     if (pb->seekable & AVIO_SEEKABLE_NORMAL)
7402         atom.size = avio_size(pb);
7403     else
7404         atom.size = INT64_MAX;
7405
7406     /* check MOV header */
7407     do {
7408         if (mov->moov_retry)
7409             avio_seek(pb, 0, SEEK_SET);
7410         if ((err = mov_read_default(mov, pb, atom)) < 0) {
7411             av_log(s, AV_LOG_ERROR, "error reading header\n");
7412             mov_read_close(s);
7413             return err;
7414         }
7415     } while ((pb->seekable & AVIO_SEEKABLE_NORMAL) && !mov->found_moov && !mov->moov_retry++);
7416     if (!mov->found_moov) {
7417         av_log(s, AV_LOG_ERROR, "moov atom not found\n");
7418         mov_read_close(s);
7419         return AVERROR_INVALIDDATA;
7420     }
7421     av_log(mov->fc, AV_LOG_TRACE, "on_parse_exit_offset=%"PRId64"\n", avio_tell(pb));
7422
7423     if (pb->seekable & AVIO_SEEKABLE_NORMAL) {
7424         if (mov->nb_chapter_tracks > 0 && !mov->ignore_chapters)
7425             mov_read_chapters(s);
7426         for (i = 0; i < s->nb_streams; i++)
7427             if (s->streams[i]->codecpar->codec_tag == AV_RL32("tmcd")) {
7428                 mov_read_timecode_track(s, s->streams[i]);
7429             } else if (s->streams[i]->codecpar->codec_tag == AV_RL32("rtmd")) {
7430                 mov_read_rtmd_track(s, s->streams[i]);
7431             }
7432     }
7433
7434     /* copy timecode metadata from tmcd tracks to the related video streams */
7435     for (i = 0; i < s->nb_streams; i++) {
7436         AVStream *st = s->streams[i];
7437         MOVStreamContext *sc = st->priv_data;
7438         if (sc->timecode_track > 0) {
7439             AVDictionaryEntry *tcr;
7440             int tmcd_st_id = -1;
7441
7442             for (j = 0; j < s->nb_streams; j++)
7443                 if (s->streams[j]->id == sc->timecode_track)
7444                     tmcd_st_id = j;
7445
7446             if (tmcd_st_id < 0 || tmcd_st_id == i)
7447                 continue;
7448             tcr = av_dict_get(s->streams[tmcd_st_id]->metadata, "timecode", NULL, 0);
7449             if (tcr)
7450                 av_dict_set(&st->metadata, "timecode", tcr->value, 0);
7451         }
7452     }
7453     export_orphan_timecode(s);
7454
7455     for (i = 0; i < s->nb_streams; i++) {
7456         AVStream *st = s->streams[i];
7457         MOVStreamContext *sc = st->priv_data;
7458         fix_timescale(mov, sc);
7459         if(st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO && st->codecpar->codec_id == AV_CODEC_ID_AAC) {
7460             st->skip_samples = sc->start_pad;
7461         }
7462         if (st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO && sc->nb_frames_for_fps > 0 && sc->duration_for_fps > 0)
7463             av_reduce(&st->avg_frame_rate.num, &st->avg_frame_rate.den,
7464                       sc->time_scale*(int64_t)sc->nb_frames_for_fps, sc->duration_for_fps, INT_MAX);
7465         if (st->codecpar->codec_type == AVMEDIA_TYPE_SUBTITLE) {
7466             if (st->codecpar->width <= 0 || st->codecpar->height <= 0) {
7467                 st->codecpar->width  = sc->width;
7468                 st->codecpar->height = sc->height;
7469             }
7470             if (st->codecpar->codec_id == AV_CODEC_ID_DVD_SUBTITLE) {
7471                 if ((err = mov_rewrite_dvd_sub_extradata(st)) < 0)
7472                     return err;
7473             }
7474         }
7475         if (mov->handbrake_version &&
7476             mov->handbrake_version <= 1000000*0 + 1000*10 + 2 &&  // 0.10.2
7477             st->codecpar->codec_id == AV_CODEC_ID_MP3
7478         ) {
7479             av_log(s, AV_LOG_VERBOSE, "Forcing full parsing for mp3 stream\n");
7480             st->need_parsing = AVSTREAM_PARSE_FULL;
7481         }
7482     }
7483
7484     if (mov->trex_data) {
7485         for (i = 0; i < s->nb_streams; i++) {
7486             AVStream *st = s->streams[i];
7487             MOVStreamContext *sc = st->priv_data;
7488             if (st->duration > 0) {
7489                 if (sc->data_size > INT64_MAX / sc->time_scale / 8) {
7490                     av_log(s, AV_LOG_ERROR, "Overflow during bit rate calculation %"PRId64" * 8 * %d\n",
7491                            sc->data_size, sc->time_scale);
7492                     mov_read_close(s);
7493                     return AVERROR_INVALIDDATA;
7494                 }
7495                 st->codecpar->bit_rate = sc->data_size * 8 * sc->time_scale / st->duration;
7496             }
7497         }
7498     }
7499
7500     if (mov->use_mfra_for > 0) {
7501         for (i = 0; i < s->nb_streams; i++) {
7502             AVStream *st = s->streams[i];
7503             MOVStreamContext *sc = st->priv_data;
7504             if (sc->duration_for_fps > 0) {
7505                 if (sc->data_size > INT64_MAX / sc->time_scale / 8) {
7506                     av_log(s, AV_LOG_ERROR, "Overflow during bit rate calculation %"PRId64" * 8 * %d\n",
7507                            sc->data_size, sc->time_scale);
7508                     mov_read_close(s);
7509                     return AVERROR_INVALIDDATA;
7510                 }
7511                 st->codecpar->bit_rate = sc->data_size * 8 * sc->time_scale /
7512                     sc->duration_for_fps;
7513             }
7514         }
7515     }
7516
7517     for (i = 0; i < mov->bitrates_count && i < s->nb_streams; i++) {
7518         if (mov->bitrates[i]) {
7519             s->streams[i]->codecpar->bit_rate = mov->bitrates[i];
7520         }
7521     }
7522
7523     ff_rfps_calculate(s);
7524
7525     for (i = 0; i < s->nb_streams; i++) {
7526         AVStream *st = s->streams[i];
7527         MOVStreamContext *sc = st->priv_data;
7528
7529         switch (st->codecpar->codec_type) {
7530         case AVMEDIA_TYPE_AUDIO:
7531             err = ff_replaygain_export(st, s->metadata);
7532             if (err < 0) {
7533                 mov_read_close(s);
7534                 return err;
7535             }
7536             break;
7537         case AVMEDIA_TYPE_VIDEO:
7538             if (sc->display_matrix) {
7539                 err = av_stream_add_side_data(st, AV_PKT_DATA_DISPLAYMATRIX, (uint8_t*)sc->display_matrix,
7540                                               sizeof(int32_t) * 9);
7541                 if (err < 0)
7542                     return err;
7543
7544                 sc->display_matrix = NULL;
7545             }
7546             if (sc->stereo3d) {
7547                 err = av_stream_add_side_data(st, AV_PKT_DATA_STEREO3D,
7548                                               (uint8_t *)sc->stereo3d,
7549                                               sizeof(*sc->stereo3d));
7550                 if (err < 0)
7551                     return err;
7552
7553                 sc->stereo3d = NULL;
7554             }
7555             if (sc->spherical) {
7556                 err = av_stream_add_side_data(st, AV_PKT_DATA_SPHERICAL,
7557                                               (uint8_t *)sc->spherical,
7558                                               sc->spherical_size);
7559                 if (err < 0)
7560                     return err;
7561
7562                 sc->spherical = NULL;
7563             }
7564             if (sc->mastering) {
7565                 err = av_stream_add_side_data(st, AV_PKT_DATA_MASTERING_DISPLAY_METADATA,
7566                                               (uint8_t *)sc->mastering,
7567                                               sizeof(*sc->mastering));
7568                 if (err < 0)
7569                     return err;
7570
7571                 sc->mastering = NULL;
7572             }
7573             if (sc->coll) {
7574                 err = av_stream_add_side_data(st, AV_PKT_DATA_CONTENT_LIGHT_LEVEL,
7575                                               (uint8_t *)sc->coll,
7576                                               sc->coll_size);
7577                 if (err < 0)
7578                     return err;
7579
7580                 sc->coll = NULL;
7581             }
7582             break;
7583         }
7584     }
7585     ff_configure_buffers_for_index(s, AV_TIME_BASE);
7586
7587     for (i = 0; i < mov->frag_index.nb_items; i++)
7588         if (mov->frag_index.item[i].moof_offset <= mov->fragment.moof_offset)
7589             mov->frag_index.item[i].headers_read = 1;
7590
7591     return 0;
7592 }
7593
7594 static AVIndexEntry *mov_find_next_sample(AVFormatContext *s, AVStream **st)
7595 {
7596     AVIndexEntry *sample = NULL;
7597     int64_t best_dts = INT64_MAX;
7598     int i;
7599     for (i = 0; i < s->nb_streams; i++) {
7600         AVStream *avst = s->streams[i];
7601         MOVStreamContext *msc = avst->priv_data;
7602         if (msc->pb && msc->current_sample < avst->nb_index_entries) {
7603             AVIndexEntry *current_sample = &avst->index_entries[msc->current_sample];
7604             int64_t dts = av_rescale(current_sample->timestamp, AV_TIME_BASE, msc->time_scale);
7605             av_log(s, AV_LOG_TRACE, "stream %d, sample %d, dts %"PRId64"\n", i, msc->current_sample, dts);
7606             if (!sample || (!(s->pb->seekable & AVIO_SEEKABLE_NORMAL) && current_sample->pos < sample->pos) ||
7607                 ((s->pb->seekable & AVIO_SEEKABLE_NORMAL) &&
7608                  ((msc->pb != s->pb && dts < best_dts) || (msc->pb == s->pb &&
7609                  ((FFABS(best_dts - dts) <= AV_TIME_BASE && current_sample->pos < sample->pos) ||
7610                   (FFABS(best_dts - dts) > AV_TIME_BASE && dts < best_dts)))))) {
7611                 sample = current_sample;
7612                 best_dts = dts;
7613                 *st = avst;
7614             }
7615         }
7616     }
7617     return sample;
7618 }
7619
7620 static int should_retry(AVIOContext *pb, int error_code) {
7621     if (error_code == AVERROR_EOF || avio_feof(pb))
7622         return 0;
7623
7624     return 1;
7625 }
7626
7627 static int mov_switch_root(AVFormatContext *s, int64_t target, int index)
7628 {
7629     int ret;
7630     MOVContext *mov = s->priv_data;
7631
7632     if (index >= 0 && index < mov->frag_index.nb_items)
7633         target = mov->frag_index.item[index].moof_offset;
7634     if (avio_seek(s->pb, target, SEEK_SET) != target) {
7635         av_log(mov->fc, AV_LOG_ERROR, "root atom offset 0x%"PRIx64": partial file\n", target);
7636         return AVERROR_INVALIDDATA;
7637     }
7638
7639     mov->next_root_atom = 0;
7640     if (index < 0 || index >= mov->frag_index.nb_items)
7641         index = search_frag_moof_offset(&mov->frag_index, target);
7642     if (index < mov->frag_index.nb_items) {
7643         if (index + 1 < mov->frag_index.nb_items)
7644             mov->next_root_atom = mov->frag_index.item[index + 1].moof_offset;
7645         if (mov->frag_index.item[index].headers_read)
7646             return 0;
7647         mov->frag_index.item[index].headers_read = 1;
7648     }
7649
7650     mov->found_mdat = 0;
7651
7652     ret = mov_read_default(mov, s->pb, (MOVAtom){ AV_RL32("root"), INT64_MAX });
7653     if (ret < 0)
7654         return ret;
7655     if (avio_feof(s->pb))
7656         return AVERROR_EOF;
7657     av_log(s, AV_LOG_TRACE, "read fragments, offset 0x%"PRIx64"\n", avio_tell(s->pb));
7658
7659     return 1;
7660 }
7661
7662 static int mov_change_extradata(MOVStreamContext *sc, AVPacket *pkt)
7663 {
7664     uint8_t *side, *extradata;
7665     int extradata_size;
7666
7667     /* Save the current index. */
7668     sc->last_stsd_index = sc->stsc_data[sc->stsc_index].id - 1;
7669
7670     /* Notify the decoder that extradata changed. */
7671     extradata_size = sc->extradata_size[sc->last_stsd_index];
7672     extradata = sc->extradata[sc->last_stsd_index];
7673     if (extradata_size > 0 && extradata) {
7674         side = av_packet_new_side_data(pkt,
7675                                        AV_PKT_DATA_NEW_EXTRADATA,
7676                                        extradata_size);
7677         if (!side)
7678             return AVERROR(ENOMEM);
7679         memcpy(side, extradata, extradata_size);
7680     }
7681
7682     return 0;
7683 }
7684
7685 static int mov_read_packet(AVFormatContext *s, AVPacket *pkt)
7686 {
7687     MOVContext *mov = s->priv_data;
7688     MOVStreamContext *sc;
7689     AVIndexEntry *sample;
7690     AVStream *st = NULL;
7691     int64_t current_index;
7692     int ret;
7693     mov->fc = s;
7694  retry:
7695     sample = mov_find_next_sample(s, &st);
7696     if (!sample || (mov->next_root_atom && sample->pos > mov->next_root_atom)) {
7697         if (!mov->next_root_atom)
7698             return AVERROR_EOF;
7699         if ((ret = mov_switch_root(s, mov->next_root_atom, -1)) < 0)
7700             return ret;
7701         goto retry;
7702     }
7703     sc = st->priv_data;
7704     /* must be done just before reading, to avoid infinite loop on sample */
7705     current_index = sc->current_index;
7706     mov_current_sample_inc(sc);
7707
7708     if (mov->next_root_atom) {
7709         sample->pos = FFMIN(sample->pos, mov->next_root_atom);
7710         sample->size = FFMIN(sample->size, (mov->next_root_atom - sample->pos));
7711     }
7712
7713     if (st->discard != AVDISCARD_ALL) {
7714         int64_t ret64 = avio_seek(sc->pb, sample->pos, SEEK_SET);
7715         if (ret64 != sample->pos) {
7716             av_log(mov->fc, AV_LOG_ERROR, "stream %d, offset 0x%"PRIx64": partial file\n",
7717                    sc->ffindex, sample->pos);
7718             if (should_retry(sc->pb, ret64)) {
7719                 mov_current_sample_dec(sc);
7720             }
7721             return AVERROR_INVALIDDATA;
7722         }
7723
7724         if( st->discard == AVDISCARD_NONKEY && 0==(sample->flags & AVINDEX_KEYFRAME) ) {
7725             av_log(mov->fc, AV_LOG_DEBUG, "Nonkey frame from stream %d discarded due to AVDISCARD_NONKEY\n", sc->ffindex);
7726             goto retry;
7727         }
7728
7729         ret = av_get_packet(sc->pb, pkt, sample->size);
7730         if (ret < 0) {
7731             if (should_retry(sc->pb, ret)) {
7732                 mov_current_sample_dec(sc);
7733             }
7734             return ret;
7735         }
7736         if (sc->has_palette) {
7737             uint8_t *pal;
7738
7739             pal = av_packet_new_side_data(pkt, AV_PKT_DATA_PALETTE, AVPALETTE_SIZE);
7740             if (!pal) {
7741                 av_log(mov->fc, AV_LOG_ERROR, "Cannot append palette to packet\n");
7742             } else {
7743                 memcpy(pal, sc->palette, AVPALETTE_SIZE);
7744                 sc->has_palette = 0;
7745             }
7746         }
7747 #if CONFIG_DV_DEMUXER
7748         if (mov->dv_demux && sc->dv_audio_container) {
7749             avpriv_dv_produce_packet(mov->dv_demux, pkt, pkt->data, pkt->size, pkt->pos);
7750             av_freep(&pkt->data);
7751             pkt->size = 0;
7752             ret = avpriv_dv_get_packet(mov->dv_demux, pkt);
7753             if (ret < 0)
7754                 return ret;
7755         }
7756 #endif
7757         if (st->codecpar->codec_id == AV_CODEC_ID_MP3 && !st->need_parsing && pkt->size > 4) {
7758             if (ff_mpa_check_header(AV_RB32(pkt->data)) < 0)
7759                 st->need_parsing = AVSTREAM_PARSE_FULL;
7760         }
7761     }
7762
7763     pkt->stream_index = sc->ffindex;
7764     pkt->dts = sample->timestamp;
7765     if (sample->flags & AVINDEX_DISCARD_FRAME) {
7766         pkt->flags |= AV_PKT_FLAG_DISCARD;
7767     }
7768     if (sc->ctts_data && sc->ctts_index < sc->ctts_count) {
7769         pkt->pts = pkt->dts + sc->dts_shift + sc->ctts_data[sc->ctts_index].duration;
7770         /* update ctts context */
7771         sc->ctts_sample++;
7772         if (sc->ctts_index < sc->ctts_count &&
7773             sc->ctts_data[sc->ctts_index].count == sc->ctts_sample) {
7774             sc->ctts_index++;
7775             sc->ctts_sample = 0;
7776         }
7777     } else {
7778         int64_t next_dts = (sc->current_sample < st->nb_index_entries) ?
7779             st->index_entries[sc->current_sample].timestamp : st->duration;
7780
7781         if (next_dts >= pkt->dts)
7782             pkt->duration = next_dts - pkt->dts;
7783         pkt->pts = pkt->dts;
7784     }
7785     if (st->discard == AVDISCARD_ALL)
7786         goto retry;
7787     pkt->flags |= sample->flags & AVINDEX_KEYFRAME ? AV_PKT_FLAG_KEY : 0;
7788     pkt->pos = sample->pos;
7789
7790     /* Multiple stsd handling. */
7791     if (sc->stsc_data) {
7792         /* Keep track of the stsc index for the given sample, then check
7793         * if the stsd index is different from the last used one. */
7794         sc->stsc_sample++;
7795         if (mov_stsc_index_valid(sc->stsc_index, sc->stsc_count) &&
7796             mov_get_stsc_samples(sc, sc->stsc_index) == sc->stsc_sample) {
7797             sc->stsc_index++;
7798             sc->stsc_sample = 0;
7799         /* Do not check indexes after a switch. */
7800         } else if (sc->stsc_data[sc->stsc_index].id > 0 &&
7801                    sc->stsc_data[sc->stsc_index].id - 1 < sc->stsd_count &&
7802                    sc->stsc_data[sc->stsc_index].id - 1 != sc->last_stsd_index) {
7803             ret = mov_change_extradata(sc, pkt);
7804             if (ret < 0)
7805                 return ret;
7806         }
7807     }
7808
7809     if (mov->aax_mode)
7810         aax_filter(pkt->data, pkt->size, mov);
7811
7812     ret = cenc_filter(mov, st, sc, pkt, current_index);
7813     if (ret < 0)
7814         return ret;
7815
7816     return 0;
7817 }
7818
7819 static int mov_seek_fragment(AVFormatContext *s, AVStream *st, int64_t timestamp)
7820 {
7821     MOVContext *mov = s->priv_data;
7822     int index;
7823
7824     if (!mov->frag_index.complete)
7825         return 0;
7826
7827     index = search_frag_timestamp(&mov->frag_index, st, timestamp);
7828     if (index < 0)
7829         index = 0;
7830     if (!mov->frag_index.item[index].headers_read)
7831         return mov_switch_root(s, -1, index);
7832     if (index + 1 < mov->frag_index.nb_items)
7833         mov->next_root_atom = mov->frag_index.item[index + 1].moof_offset;
7834
7835     return 0;
7836 }
7837
7838 static int mov_seek_stream(AVFormatContext *s, AVStream *st, int64_t timestamp, int flags)
7839 {
7840     MOVStreamContext *sc = st->priv_data;
7841     int sample, time_sample, ret;
7842     unsigned int i;
7843
7844     // Here we consider timestamp to be PTS, hence try to offset it so that we
7845     // can search over the DTS timeline.
7846     timestamp -= (sc->min_corrected_pts + sc->dts_shift);
7847
7848     ret = mov_seek_fragment(s, st, timestamp);
7849     if (ret < 0)
7850         return ret;
7851
7852     sample = av_index_search_timestamp(st, timestamp, flags);
7853     av_log(s, AV_LOG_TRACE, "stream %d, timestamp %"PRId64", sample %d\n", st->index, timestamp, sample);
7854     if (sample < 0 && st->nb_index_entries && timestamp < st->index_entries[0].timestamp)
7855         sample = 0;
7856     if (sample < 0) /* not sure what to do */
7857         return AVERROR_INVALIDDATA;
7858     mov_current_sample_set(sc, sample);
7859     av_log(s, AV_LOG_TRACE, "stream %d, found sample %d\n", st->index, sc->current_sample);
7860     /* adjust ctts index */
7861     if (sc->ctts_data) {
7862         time_sample = 0;
7863         for (i = 0; i < sc->ctts_count; i++) {
7864             int next = time_sample + sc->ctts_data[i].count;
7865             if (next > sc->current_sample) {
7866                 sc->ctts_index = i;
7867                 sc->ctts_sample = sc->current_sample - time_sample;
7868                 break;
7869             }
7870             time_sample = next;
7871         }
7872     }
7873
7874     /* adjust stsd index */
7875     if (sc->chunk_count) {
7876     time_sample = 0;
7877     for (i = 0; i < sc->stsc_count; i++) {
7878         int64_t next = time_sample + mov_get_stsc_samples(sc, i);
7879         if (next > sc->current_sample) {
7880             sc->stsc_index = i;
7881             sc->stsc_sample = sc->current_sample - time_sample;
7882             break;
7883         }
7884         av_assert0(next == (int)next);
7885         time_sample = next;
7886     }
7887     }
7888
7889     return sample;
7890 }
7891
7892 static int mov_read_seek(AVFormatContext *s, int stream_index, int64_t sample_time, int flags)
7893 {
7894     MOVContext *mc = s->priv_data;
7895     AVStream *st;
7896     int sample;
7897     int i;
7898
7899     if (stream_index >= s->nb_streams)
7900         return AVERROR_INVALIDDATA;
7901
7902     st = s->streams[stream_index];
7903     sample = mov_seek_stream(s, st, sample_time, flags);
7904     if (sample < 0)
7905         return sample;
7906
7907     if (mc->seek_individually) {
7908         /* adjust seek timestamp to found sample timestamp */
7909         int64_t seek_timestamp = st->index_entries[sample].timestamp;
7910
7911         for (i = 0; i < s->nb_streams; i++) {
7912             int64_t timestamp;
7913             MOVStreamContext *sc = s->streams[i]->priv_data;
7914             st = s->streams[i];
7915             st->skip_samples = (sample_time <= 0) ? sc->start_pad : 0;
7916
7917             if (stream_index == i)
7918                 continue;
7919
7920             timestamp = av_rescale_q(seek_timestamp, s->streams[stream_index]->time_base, st->time_base);
7921             mov_seek_stream(s, st, timestamp, flags);
7922         }
7923     } else {
7924         for (i = 0; i < s->nb_streams; i++) {
7925             MOVStreamContext *sc;
7926             st = s->streams[i];
7927             sc = st->priv_data;
7928             mov_current_sample_set(sc, 0);
7929         }
7930         while (1) {
7931             MOVStreamContext *sc;
7932             AVIndexEntry *entry = mov_find_next_sample(s, &st);
7933             if (!entry)
7934                 return AVERROR_INVALIDDATA;
7935             sc = st->priv_data;
7936             if (sc->ffindex == stream_index && sc->current_sample == sample)
7937                 break;
7938             mov_current_sample_inc(sc);
7939         }
7940     }
7941     return 0;
7942 }
7943
7944 #define OFFSET(x) offsetof(MOVContext, x)
7945 #define FLAGS AV_OPT_FLAG_VIDEO_PARAM | AV_OPT_FLAG_DECODING_PARAM
7946 static const AVOption mov_options[] = {
7947     {"use_absolute_path",
7948         "allow using absolute path when opening alias, this is a possible security issue",
7949         OFFSET(use_absolute_path), AV_OPT_TYPE_BOOL, {.i64 = 0},
7950         0, 1, FLAGS},
7951     {"seek_streams_individually",
7952         "Seek each stream individually to the to the closest point",
7953         OFFSET(seek_individually), AV_OPT_TYPE_BOOL, { .i64 = 1 },
7954         0, 1, FLAGS},
7955     {"ignore_editlist", "Ignore the edit list atom.", OFFSET(ignore_editlist), AV_OPT_TYPE_BOOL, {.i64 = 0},
7956         0, 1, FLAGS},
7957     {"advanced_editlist",
7958         "Modify the AVIndex according to the editlists. Use this option to decode in the order specified by the edits.",
7959         OFFSET(advanced_editlist), AV_OPT_TYPE_BOOL, {.i64 = 1},
7960         0, 1, FLAGS},
7961     {"ignore_chapters", "", OFFSET(ignore_chapters), AV_OPT_TYPE_BOOL, {.i64 = 0},
7962         0, 1, FLAGS},
7963     {"use_mfra_for",
7964         "use mfra for fragment timestamps",
7965         OFFSET(use_mfra_for), AV_OPT_TYPE_INT, {.i64 = FF_MOV_FLAG_MFRA_AUTO},
7966         -1, FF_MOV_FLAG_MFRA_PTS, FLAGS,
7967         "use_mfra_for"},
7968     {"auto", "auto", 0, AV_OPT_TYPE_CONST, {.i64 = FF_MOV_FLAG_MFRA_AUTO}, 0, 0,
7969         FLAGS, "use_mfra_for" },
7970     {"dts", "dts", 0, AV_OPT_TYPE_CONST, {.i64 = FF_MOV_FLAG_MFRA_DTS}, 0, 0,
7971         FLAGS, "use_mfra_for" },
7972     {"pts", "pts", 0, AV_OPT_TYPE_CONST, {.i64 = FF_MOV_FLAG_MFRA_PTS}, 0, 0,
7973         FLAGS, "use_mfra_for" },
7974     { "export_all", "Export unrecognized metadata entries", OFFSET(export_all),
7975         AV_OPT_TYPE_BOOL, { .i64 = 0 }, 0, 1, .flags = FLAGS },
7976     { "export_xmp", "Export full XMP metadata", OFFSET(export_xmp),
7977         AV_OPT_TYPE_BOOL, { .i64 = 0 }, 0, 1, .flags = FLAGS },
7978     { "activation_bytes", "Secret bytes for Audible AAX files", OFFSET(activation_bytes),
7979         AV_OPT_TYPE_BINARY, .flags = AV_OPT_FLAG_DECODING_PARAM },
7980     { "audible_fixed_key", // extracted from libAAX_SDK.so and AAXSDKWin.dll files!
7981         "Fixed key used for handling Audible AAX files", OFFSET(audible_fixed_key),
7982         AV_OPT_TYPE_BINARY, {.str="77214d4b196a87cd520045fd20a51d67"},
7983         .flags = AV_OPT_FLAG_DECODING_PARAM },
7984     { "decryption_key", "The media decryption key (hex)", OFFSET(decryption_key), AV_OPT_TYPE_BINARY, .flags = AV_OPT_FLAG_DECODING_PARAM },
7985     { "enable_drefs", "Enable external track support.", OFFSET(enable_drefs), AV_OPT_TYPE_BOOL,
7986         {.i64 = 0}, 0, 1, FLAGS },
7987
7988     { NULL },
7989 };
7990
7991 static const AVClass mov_class = {
7992     .class_name = "mov,mp4,m4a,3gp,3g2,mj2",
7993     .item_name  = av_default_item_name,
7994     .option     = mov_options,
7995     .version    = LIBAVUTIL_VERSION_INT,
7996 };
7997
7998 AVInputFormat ff_mov_demuxer = {
7999     .name           = "mov,mp4,m4a,3gp,3g2,mj2",
8000     .long_name      = NULL_IF_CONFIG_SMALL("QuickTime / MOV"),
8001     .priv_class     = &mov_class,
8002     .priv_data_size = sizeof(MOVContext),
8003     .extensions     = "mov,mp4,m4a,3gp,3g2,mj2",
8004     .read_probe     = mov_probe,
8005     .read_header    = mov_read_header,
8006     .read_packet    = mov_read_packet,
8007     .read_close     = mov_read_close,
8008     .read_seek      = mov_read_seek,
8009     .flags          = AVFMT_NO_BYTE_SEEK | AVFMT_SEEK_TO_PTS,
8010 };