Statistics
| Branch: | Revision:

ffmpeg / libavformat / mov.c @ ed70a509

History | View | Annotate | Download (76.2 KB)

1
/*
2
 * MOV decoder.
3
 * Copyright (c) 2001 Fabrice Bellard.
4
 *
5
 * This library is free software; you can redistribute it and/or
6
 * modify it under the terms of the GNU Lesser General Public
7
 * License as published by the Free Software Foundation; either
8
 * version 2 of the License, or (at your option) any later version.
9
 *
10
 * This library is distributed in the hope that it will be useful,
11
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13
 * Lesser General Public License for more details.
14
 *
15
 * You should have received a copy of the GNU Lesser General Public
16
 * License along with this library; if not, write to the Free Software
17
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
 */
19

    
20
#include <limits.h>
21

    
22
//#define DEBUG
23

    
24
#include "avformat.h"
25
#include "avi.h"
26
#include "mov.h"
27

    
28
#ifdef CONFIG_ZLIB
29
#include <zlib.h>
30
#endif
31

    
32
/*
33
 * First version by Francois Revol revol@free.fr
34
 * Seek function by Gael Chardon gael.dev@4now.net
35
 *
36
 * Features and limitations:
37
 * - reads most of the QT files I have (at least the structure),
38
 *   the exceptions are .mov with zlib compressed headers ('cmov' section). It shouldn't be hard to implement.
39
 *   FIXED, Francois Revol, 07/17/2002
40
 * - ffmpeg has nearly none of the usual QuickTime codecs,
41
 *   although I succesfully dumped raw and mp3 audio tracks off .mov files.
42
 *   Sample QuickTime files with mp3 audio can be found at: http://www.3ivx.com/showcase.html
43
 * - .mp4 parsing is still hazardous, although the format really is QuickTime with some minor changes
44
 *   (to make .mov parser crash maybe ?), despite what they say in the MPEG FAQ at
45
 *   http://mpeg.telecomitalialab.com/faq.htm
46
 * - the code is quite ugly... maybe I won't do it recursive next time :-)
47
 * - seek is not supported with files that contain edit list
48
 *
49
 * Funny I didn't know about http://sourceforge.net/projects/qt-ffmpeg/
50
 * when coding this :) (it's a writer anyway)
51
 *
52
 * Reference documents:
53
 * http://www.geocities.com/xhelmboyx/quicktime/formats/qtm-layout.txt
54
 * Apple:
55
 *  http://developer.apple.com/documentation/QuickTime/QTFF/
56
 *  http://developer.apple.com/documentation/QuickTime/QTFF/qtff.pdf
57
 * QuickTime is a trademark of Apple (AFAIK :))
58
 */
59

    
60
#include "qtpalette.h"
61

    
62

    
63
#undef NDEBUG
64
#include <assert.h>
65

    
66
/* Allows seeking */
67
#define MOV_SEEK
68

    
69
/* some streams in QT (and in MP4 mostly) aren't either video nor audio */
70
/* so we first list them as this, then clean up the list of streams we give back, */
71
/* getting rid of these */
72
#define CODEC_TYPE_MOV_OTHER    (enum CodecType) 2
73

    
74
/* http://gpac.sourceforge.net/tutorial/mediatypes.htm */
75
const CodecTag ff_mov_obj_type[] = {
76
    { CODEC_ID_MPEG4     ,  32 },
77
    { CODEC_ID_H264      ,  33 },
78
    { CODEC_ID_AAC       ,  64 },
79
    { CODEC_ID_MPEG2VIDEO,  96 }, /* MPEG2 Simple */
80
    { CODEC_ID_MPEG2VIDEO,  97 }, /* MPEG2 Main */
81
    { CODEC_ID_MPEG2VIDEO,  98 }, /* MPEG2 SNR */
82
    { CODEC_ID_MPEG2VIDEO,  99 }, /* MPEG2 Spatial */
83
    { CODEC_ID_MPEG2VIDEO, 100 }, /* MPEG2 High */
84
    { CODEC_ID_MPEG2VIDEO, 101 }, /* MPEG2 422 */
85
    { CODEC_ID_AAC       , 102 }, /* MPEG2 AAC Main */
86
    { CODEC_ID_AAC       , 103 }, /* MPEG2 AAC Low */
87
    { CODEC_ID_AAC       , 104 }, /* MPEG2 AAC SSR */
88
    { CODEC_ID_MP3       , 105 },
89
    { CODEC_ID_MPEG1VIDEO, 106 },
90
    { CODEC_ID_MP2       , 107 },
91
    { CODEC_ID_MJPEG     , 108 },
92
    { CODEC_ID_PCM_S16LE , 224 },
93
    { CODEC_ID_VORBIS    , 221 },
94
    { CODEC_ID_AC3       , 226 },
95
    { CODEC_ID_PCM_ALAW  , 227 },
96
    { CODEC_ID_PCM_MULAW , 228 },
97
    { CODEC_ID_PCM_S16BE , 230 },
98
    { CODEC_ID_H263      , 242 },
99
    { CODEC_ID_H261      , 243 },
100
    { 0, 0 },
101
};
102

    
103
static const CodecTag mov_video_tags[] = {
104
/*  { CODEC_ID_, MKTAG('c', 'v', 'i', 'd') }, *//* Cinepak */
105
/*  { CODEC_ID_H263, MKTAG('r', 'a', 'w', ' ') }, *//* Uncompressed RGB */
106
/*  { CODEC_ID_H263, MKTAG('Y', 'u', 'v', '2') }, *//* Uncompressed YUV422 */
107
/*    { CODEC_ID_RAWVIDEO, MKTAG('A', 'V', 'U', 'I') }, *//* YUV with alpha-channel (AVID Uncompressed) */
108
/* Graphics */
109
/* Animation */
110
/* Apple video */
111
/* Kodak Photo CD */
112
    { CODEC_ID_MJPEG, MKTAG('j', 'p', 'e', 'g') }, /* PhotoJPEG */
113
    { CODEC_ID_MPEG1VIDEO, MKTAG('m', 'p', 'e', 'g') }, /* MPEG */
114
    { CODEC_ID_MJPEG, MKTAG('m', 'j', 'p', 'a') }, /* Motion-JPEG (format A) */
115
    { CODEC_ID_MJPEGB, MKTAG('m', 'j', 'p', 'b') }, /* Motion-JPEG (format B) */
116
    { CODEC_ID_MJPEG, MKTAG('A', 'V', 'D', 'J') }, /* MJPEG with alpha-channel (AVID JFIF meridien compressed) */
117
/*    { CODEC_ID_MJPEG, MKTAG('A', 'V', 'R', 'n') }, *//* MJPEG with alpha-channel (AVID ABVB/Truevision NuVista) */
118
/*    { CODEC_ID_GIF, MKTAG('g', 'i', 'f', ' ') }, *//* embedded gif files as frames (usually one "click to play movie" frame) */
119
/* Sorenson video */
120
    { CODEC_ID_SVQ1, MKTAG('S', 'V', 'Q', '1') }, /* Sorenson Video v1 */
121
    { CODEC_ID_SVQ1, MKTAG('s', 'v', 'q', '1') }, /* Sorenson Video v1 */
122
    { CODEC_ID_SVQ1, MKTAG('s', 'v', 'q', 'i') }, /* Sorenson Video v1 (from QT specs)*/
123
    { CODEC_ID_SVQ3, MKTAG('S', 'V', 'Q', '3') }, /* Sorenson Video v3 */
124
    { CODEC_ID_MPEG4, MKTAG('m', 'p', '4', 'v') },
125
    { CODEC_ID_MPEG4, MKTAG('D', 'I', 'V', 'X') }, /* OpenDiVX *//* sample files at http://heroinewarrior.com/xmovie.php3 use this tag */
126
    { CODEC_ID_MPEG4, MKTAG('X', 'V', 'I', 'D') },
127
    { CODEC_ID_MPEG4, MKTAG('3', 'I', 'V', '2') }, /* experimental: 3IVX files before ivx D4 4.5.1 */
128
/*    { CODEC_ID_, MKTAG('I', 'V', '5', '0') }, *//* Indeo 5.0 */
129
    { CODEC_ID_H263, MKTAG('h', '2', '6', '3') }, /* H263 */
130
    { CODEC_ID_H263, MKTAG('s', '2', '6', '3') }, /* H263 ?? works */
131
    { CODEC_ID_DVVIDEO, MKTAG('d', 'v', 'c', ' ') }, /* DV NTSC */
132
    { CODEC_ID_DVVIDEO, MKTAG('d', 'v', 'c', 'p') }, /* DV PAL */
133
/*    { CODEC_ID_DVVIDEO, MKTAG('A', 'V', 'd', 'v') }, *//* AVID dv */
134
    { CODEC_ID_VP3, MKTAG('V', 'P', '3', '1') }, /* On2 VP3 */
135
    { CODEC_ID_RPZA, MKTAG('r', 'p', 'z', 'a') }, /* Apple Video (RPZA) */
136
    { CODEC_ID_CINEPAK, MKTAG('c', 'v', 'i', 'd') }, /* Cinepak */
137
    { CODEC_ID_8BPS, MKTAG('8', 'B', 'P', 'S') }, /* Planar RGB (8BPS) */
138
    { CODEC_ID_SMC, MKTAG('s', 'm', 'c', ' ') }, /* Apple Graphics (SMC) */
139
    { CODEC_ID_QTRLE, MKTAG('r', 'l', 'e', ' ') }, /* Apple Animation (RLE) */
140
    { CODEC_ID_QDRAW, MKTAG('q', 'd', 'r', 'w') }, /* QuickDraw */
141
    { CODEC_ID_H264, MKTAG('a', 'v', 'c', '1') }, /* AVC-1/H.264 */
142
    { CODEC_ID_MPEG2VIDEO, MKTAG('h', 'd', 'v', '2') }, /* MPEG2 produced by Sony HD camera */
143
    { CODEC_ID_MPEG2VIDEO, MKTAG('h', 'd', 'v', '3') }, /* HDV produced by FCP */
144
    { CODEC_ID_MPEG2VIDEO, MKTAG('m', 'x', '5', 'n') }, /* MPEG2 IMX NTSC 525/60 50mb/s produced by FCP */
145
    { CODEC_ID_MPEG2VIDEO, MKTAG('m', 'x', '5', 'p') }, /* MPEG2 IMX PAL 625/50 50mb/s produced by FCP */
146
    { CODEC_ID_MPEG2VIDEO, MKTAG('m', 'x', '3', 'n') }, /* MPEG2 IMX NTSC 525/60 30mb/s produced by FCP */
147
    { CODEC_ID_MPEG2VIDEO, MKTAG('m', 'x', '3', 'p') }, /* MPEG2 IMX PAL 625/50 30mb/s produced by FCP */
148
    { CODEC_ID_DVVIDEO, MKTAG('d', 'v', 'p', 'p') }, /* DVCPRO PAL produced by FCP */
149
    //{ CODEC_ID_DVVIDEO, MKTAG('d', 'v', 'h', '5') }, /* DVCPRO HD 50i produced by FCP */
150
    //{ CODEC_ID_DVVIDEO, MKTAG('d', 'v', 'h', '6') }, /* DVCPRO HD 60i produced by FCP */
151
    { CODEC_ID_DVVIDEO, MKTAG('d', 'v', '5', 'p') }, /* DVCPRO50 PAL produced by FCP */
152
    { CODEC_ID_DVVIDEO, MKTAG('d', 'v', '5', 'n') }, /* DVCPRO50 NTSC produced by FCP */
153
    { CODEC_ID_DVVIDEO, MKTAG('A', 'V', 'd', 'v') }, /* AVID DV */
154
    //{ CODEC_ID_JPEG2000, MKTAG('m', 'j', 'p', '2') }, /* JPEG 2000 produced by FCP */
155
    { CODEC_ID_RAWVIDEO, MKTAG('2', 'v', 'u', 'y') }, /* UNCOMPRESSED 8BIT 4:2:2 */
156
    { CODEC_ID_NONE, 0 },
157
};
158

    
159
static const CodecTag mov_audio_tags[] = {
160
    { CODEC_ID_PCM_S32BE, MKTAG('i', 'n', '3', '2') },
161
    { CODEC_ID_PCM_S24BE, MKTAG('i', 'n', '2', '4') },
162
/*    { CODEC_ID_PCM_S16BE, MKTAG('N', 'O', 'N', 'E') }, *//* uncompressed */
163
    { CODEC_ID_PCM_S16BE, MKTAG('t', 'w', 'o', 's') }, /* 16 bits */
164
    /* { CODEC_ID_PCM_S8, MKTAG('t', 'w', 'o', 's') },*/ /* 8 bits */
165
    { CODEC_ID_PCM_U8, MKTAG('r', 'a', 'w', ' ') }, /* 8 bits unsigned */
166
    { CODEC_ID_PCM_S16LE, MKTAG('s', 'o', 'w', 't') }, /*  */
167
    { CODEC_ID_PCM_MULAW, MKTAG('u', 'l', 'a', 'w') }, /*  */
168
    { CODEC_ID_PCM_ALAW, MKTAG('a', 'l', 'a', 'w') }, /*  */
169
    { CODEC_ID_ADPCM_IMA_QT, MKTAG('i', 'm', 'a', '4') }, /* IMA-4 ADPCM */
170
    { CODEC_ID_MACE3, MKTAG('M', 'A', 'C', '3') }, /* Macintosh Audio Compression and Expansion 3:1 */
171
    { CODEC_ID_MACE6, MKTAG('M', 'A', 'C', '6') }, /* Macintosh Audio Compression and Expansion 6:1 */
172

    
173
    { CODEC_ID_MP2, MKTAG('.', 'm', 'p', '3') }, /* MPEG layer 3 */ /* sample files at http://www.3ivx.com/showcase.html use this tag */
174
    { CODEC_ID_MP2, 0x6D730055 }, /* MPEG layer 3 */
175
    { CODEC_ID_MP2, 0x5500736D }, /* MPEG layer 3 *//* XXX: check endianness */
176
/*    { CODEC_ID_OGG_VORBIS, MKTAG('O', 'g', 'g', 'S') }, *//* sample files at http://heroinewarrior.com/xmovie.php3 use this tag */
177
/* MP4 tags */
178
    { CODEC_ID_AAC, MKTAG('m', 'p', '4', 'a') }, /* MPEG-4 AAC */
179
    /* The standard for mpeg4 audio is still not normalised AFAIK anyway */
180
    { CODEC_ID_AMR_NB, MKTAG('s', 'a', 'm', 'r') }, /* AMR-NB 3gp */
181
    { CODEC_ID_AMR_WB, MKTAG('s', 'a', 'w', 'b') }, /* AMR-WB 3gp */
182
    { CODEC_ID_AC3, MKTAG('m', 's', 0x20, 0x00) }, /* Dolby AC-3 */
183
    { CODEC_ID_ALAC,MKTAG('a', 'l', 'a', 'c') }, /* Apple Lossless */
184
    { CODEC_ID_QDM2,MKTAG('Q', 'D', 'M', '2') }, /* QDM2 */
185
    { CODEC_ID_NONE, 0 },
186
};
187

    
188
/* map numeric codes from mdhd atom to ISO 639 */
189
/* cf. QTFileFormat.pdf p253, qtff.pdf p205 */
190
/* http://developer.apple.com/documentation/mac/Text/Text-368.html */
191
/* deprecated by putting the code as 3*5bit ascii */
192
static const char *mov_mdhd_language_map[] = {
193
/* 0-9 */
194
"eng", "fra", "ger", "ita", "dut", "sve", "spa", "dan", "por", "nor",
195
"heb", "jpn", "ara", "fin", "gre", "ice", "mlt", "tur", "hr "/*scr*/, "chi"/*ace?*/,
196
"urd", "hin", "tha", "kor", "lit", "pol", "hun", "est", "lav",  NULL,
197
"fo ",  NULL, "rus", "chi",  NULL, "iri", "alb", "ron", "ces", "slk",
198
"slv", "yid", "sr ", "mac", "bul", "ukr", "bel", "uzb", "kaz", "aze",
199
/*?*/
200
"aze", "arm", "geo", "mol", "kir", "tgk", "tuk", "mon",  NULL, "pus",
201
"kur", "kas", "snd", "tib", "nep", "san", "mar", "ben", "asm", "guj",
202
"pa ", "ori", "mal", "kan", "tam", "tel",  NULL, "bur", "khm", "lao",
203
/*                   roman? arabic? */
204
"vie", "ind", "tgl", "may", "may", "amh", "tir", "orm", "som", "swa",
205
/*==rundi?*/
206
 NULL, "run",  NULL, "mlg", "epo",  NULL,  NULL,  NULL,  NULL,  NULL,
207
/* 100 */
208
 NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,
209
 NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,
210
 NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL,  NULL, "wel", "baq",
211
"cat", "lat", "que", "grn", "aym", "tat", "uig", "dzo", "jav"
212
};
213

    
214
/* the QuickTime file format is quite convoluted...
215
 * it has lots of index tables, each indexing something in another one...
216
 * Here we just use what is needed to read the chunks
217
 */
218

    
219
typedef struct MOV_sample_to_chunk_tbl {
220
    long first;
221
    long count;
222
    long id;
223
} MOV_sample_to_chunk_tbl;
224

    
225
typedef struct {
226
    uint32_t type;
227
    int64_t offset;
228
    int64_t size; /* total size (excluding the size and type fields) */
229
} MOV_atom_t;
230

    
231
typedef struct {
232
    int seed;
233
    int flags;
234
    int size;
235
    void* clrs;
236
} MOV_ctab_t;
237

    
238
typedef struct {
239
    uint8_t  version;
240
    uint32_t flags; // 24bit
241

    
242
    /* 0x03 ESDescrTag */
243
    uint16_t es_id;
244
#define MP4ODescrTag                    0x01
245
#define MP4IODescrTag                   0x02
246
#define MP4ESDescrTag                   0x03
247
#define MP4DecConfigDescrTag            0x04
248
#define MP4DecSpecificDescrTag          0x05
249
#define MP4SLConfigDescrTag             0x06
250
#define MP4ContentIdDescrTag            0x07
251
#define MP4SupplContentIdDescrTag       0x08
252
#define MP4IPIPtrDescrTag               0x09
253
#define MP4IPMPPtrDescrTag              0x0A
254
#define MP4IPMPDescrTag                 0x0B
255
#define MP4RegistrationDescrTag         0x0D
256
#define MP4ESIDIncDescrTag              0x0E
257
#define MP4ESIDRefDescrTag              0x0F
258
#define MP4FileIODescrTag               0x10
259
#define MP4FileODescrTag                0x11
260
#define MP4ExtProfileLevelDescrTag      0x13
261
#define MP4ExtDescrTagsStart            0x80
262
#define MP4ExtDescrTagsEnd              0xFE
263
    uint8_t  stream_priority;
264

    
265
    /* 0x04 DecConfigDescrTag */
266
    uint8_t  object_type_id;
267
    uint8_t  stream_type;
268
    /* XXX: really streamType is
269
     * only 6bit, followed by:
270
     * 1bit  upStream
271
     * 1bit  reserved
272
     */
273
    uint32_t buffer_size_db; // 24
274
    uint32_t max_bitrate;
275
    uint32_t avg_bitrate;
276

    
277
    /* 0x05 DecSpecificDescrTag */
278
    uint8_t  decoder_cfg_len;
279
    uint8_t *decoder_cfg;
280

    
281
    /* 0x06 SLConfigDescrTag */
282
    uint8_t  sl_config_len;
283
    uint8_t *sl_config;
284
} MOV_esds_t;
285

    
286
struct MOVParseTableEntry;
287

    
288
typedef struct MOVStreamContext {
289
    int ffindex; /* the ffmpeg stream id */
290
    int is_ff_stream; /* Is this stream presented to ffmpeg ? i.e. is this an audio or video stream ? */
291
    long next_chunk;
292
    long chunk_count;
293
    int64_t *chunk_offsets;
294
    int stts_count;
295
    Time2Sample *stts_data;
296
    int ctts_count;
297
    Time2Sample *ctts_data;
298
    int edit_count;             /* number of 'edit' (elst atom) */
299
    long sample_to_chunk_sz;
300
    MOV_sample_to_chunk_tbl *sample_to_chunk;
301
    long sample_to_chunk_index;
302
    int sample_to_time_index;
303
    long sample_to_time_sample;
304
    uint64_t sample_to_time_time;
305
    int sample_to_ctime_index;
306
    int sample_to_ctime_sample;
307
    long sample_size;
308
    long sample_count;
309
    long *sample_sizes;
310
    long keyframe_count;
311
    long *keyframes;
312
    int time_scale;
313
    int time_rate;
314
    long current_sample;
315
    long left_in_chunk; /* how many samples before next chunk */
316
    MOV_esds_t esds;
317
} MOVStreamContext;
318

    
319
typedef struct MOVContext {
320
    int mp4; /* set to 1 as soon as we are sure that the file is an .mp4 file (even some header parsing depends on this) */
321
    AVFormatContext *fc;
322
    int time_scale;
323
    int64_t duration; /* duration of the longest track */
324
    int found_moov; /* when both 'moov' and 'mdat' sections has been found */
325
    int found_mdat; /* we suppose we have enough data to read the file */
326
    int64_t mdat_size;
327
    int64_t mdat_offset;
328
    int ni;                                         ///< non interleaved mode
329
    int total_streams;
330
    /* some streams listed here aren't presented to the ffmpeg API, since they aren't either video nor audio
331
     * but we need the info to be able to skip data from those streams in the 'mdat' section
332
     */
333
    MOVStreamContext *streams[MAX_STREAMS];
334

    
335
    int64_t next_chunk_offset;
336
    MOVStreamContext *partial; /* != 0 : there is still to read in the current chunk */
337
    int ctab_size;
338
    MOV_ctab_t **ctab;           /* color tables */
339
    const struct MOVParseTableEntry *parse_table; /* could be eventually used to change the table */
340
    /* NOTE: for recursion save to/ restore from local variable! */
341

    
342
    AVPaletteControl palette_control;
343
} MOVContext;
344

    
345

    
346
/* XXX: it's the first time I make a recursive parser I think... sorry if it's ugly :P */
347

    
348
/* those functions parse an atom */
349
/* return code:
350
 1: found what I wanted, exit
351
 0: continue to parse next atom
352
 -1: error occured, exit
353
 */
354
typedef int (*mov_parse_function)(MOVContext *ctx, ByteIOContext *pb, MOV_atom_t atom);
355

    
356
/* links atom IDs to parse functions */
357
typedef struct MOVParseTableEntry {
358
    uint32_t type;
359
    mov_parse_function func;
360
} MOVParseTableEntry;
361

    
362
static int ff_mov_lang_to_iso639(int code, char *to)
363
{
364
    int i;
365
    /* is it the mangled iso code? */
366
    /* see http://www.geocities.com/xhelmboyx/quicktime/formats/mp4-layout.txt */
367
    if (code > 138) {
368
        for (i = 2; i >= 0; i--) {
369
            to[i] = 0x60 + (code & 0x1f);
370
            code >>= 5;
371
        }
372
        return 1;
373
    }
374
    /* old fashion apple lang code */
375
    if (code >= (sizeof(mov_mdhd_language_map)/sizeof(char *)))
376
        return 0;
377
    if (!mov_mdhd_language_map[code])
378
        return 0;
379
    strncpy(to, mov_mdhd_language_map[code], 4);
380
    return 1;
381
}
382

    
383
int ff_mov_iso639_to_lang(const char *lang, int mp4)
384
{
385
    int i, code = 0;
386

    
387
    /* old way, only for QT? */
388
    for (i = 0; !mp4 && (i < (sizeof(mov_mdhd_language_map)/sizeof(char *))); i++) {
389
        if (mov_mdhd_language_map[i] && !strcmp(lang, mov_mdhd_language_map[i]))
390
            return i;
391
    }
392
    /* XXX:can we do that in mov too? */
393
    if (!mp4)
394
        return 0;
395
    /* handle undefined as such */
396
    if (lang[0] == '\0')
397
        lang = "und";
398
    /* 5bit ascii */
399
    for (i = 0; i < 3; i++) {
400
        unsigned char c = (unsigned char)lang[i];
401
        if (c < 0x60)
402
            return 0;
403
        if (c > 0x60 + 0x1f)
404
            return 0;
405
        code <<= 5;
406
        code |= (c - 0x60);
407
    }
408
    return code;
409
}
410

    
411
static int mov_read_leaf(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
412
{
413
    if (atom.size>1)
414
        url_fskip(pb, atom.size);
415
/*        url_seek(pb, atom_offset+atom.size, SEEK_SET); */
416
    return 0;
417
}
418

    
419
static int mov_read_default(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
420
{
421
    int64_t total_size = 0;
422
    MOV_atom_t a;
423
    int i;
424
    int err = 0;
425

    
426
    a.offset = atom.offset;
427

    
428
    if (atom.size < 0)
429
        atom.size = 0x7fffffffffffffffLL;
430
    while(((total_size + 8) < atom.size) && !url_feof(pb) && !err) {
431
        a.size = atom.size;
432
        a.type=0L;
433
        if(atom.size >= 8) {
434
            a.size = get_be32(pb);
435
            a.type = get_le32(pb);
436
        }
437
        total_size += 8;
438
        a.offset += 8;
439
        dprintf("type: %08x  %.4s  sz: %"PRIx64"  %"PRIx64"   %"PRIx64"\n", a.type, (char*)&a.type, a.size, atom.size, total_size);
440
        if (a.size == 1) { /* 64 bit extended size */
441
            a.size = get_be64(pb) - 8;
442
            a.offset += 8;
443
            total_size += 8;
444
        }
445
        if (a.size == 0) {
446
            a.size = atom.size - total_size;
447
            if (a.size <= 8)
448
                break;
449
        }
450
        for (i = 0; c->parse_table[i].type != 0L
451
             && c->parse_table[i].type != a.type; i++)
452
            /* empty */;
453

    
454
        a.size -= 8;
455

    
456
        if(a.size < 0)
457
            break;
458

    
459
        if (c->parse_table[i].type == 0) { /* skip leaf atoms data */
460
            url_fskip(pb, a.size);
461
        } else {
462
            offset_t start_pos = url_ftell(pb);
463
            int64_t left;
464
            err = (c->parse_table[i].func)(c, pb, a);
465
            left = a.size - url_ftell(pb) + start_pos;
466
            if (left > 0) /* skip garbage at atom end */
467
                url_fskip(pb, left);
468
        }
469

    
470
        a.offset += a.size;
471
        total_size += a.size;
472
    }
473

    
474
    if (!err && total_size < atom.size && atom.size < 0x7ffff) {
475
        url_fskip(pb, atom.size - total_size);
476
    }
477

    
478
    return err;
479
}
480

    
481
static int mov_read_ctab(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
482
{
483
#if 1
484
    url_fskip(pb, atom.size); // for now
485
#else
486
    VERY VERY BROKEN, NEVER execute this, needs rewrite
487
    unsigned int len;
488
    MOV_ctab_t *t;
489
    c->ctab = av_realloc(c->ctab, ++c->ctab_size);
490
    t = c->ctab[c->ctab_size];
491
    t->seed = get_be32(pb);
492
    t->flags = get_be16(pb);
493
    t->size = get_be16(pb) + 1;
494
    len = 2 * t->size * 4;
495
    if (len > 0) {
496
        t->clrs = av_malloc(len); // 16bit A R G B
497
        if (t->clrs)
498
            get_buffer(pb, t->clrs, len);
499
    }
500
#endif
501

    
502
    return 0;
503
}
504

    
505
static int mov_read_hdlr(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
506
{
507
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
508
    int len = 0;
509
    uint32_t type;
510
    uint32_t ctype;
511

    
512
    get_byte(pb); /* version */
513
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
514

    
515
    /* component type */
516
    ctype = get_le32(pb);
517
    type = get_le32(pb); /* component subtype */
518

    
519
    dprintf("ctype= %c%c%c%c (0x%08lx)\n", *((char *)&ctype), ((char *)&ctype)[1], ((char *)&ctype)[2], ((char *)&ctype)[3], (long) ctype);
520
    dprintf("stype= %c%c%c%c\n", *((char *)&type), ((char *)&type)[1], ((char *)&type)[2], ((char *)&type)[3]);
521
    if(ctype == MKTAG('m', 'h', 'l', 'r')) /* MOV */
522
        c->mp4 = 0;
523
    else if(ctype == 0)
524
        c->mp4 = 1;
525
    if(type == MKTAG('v', 'i', 'd', 'e'))
526
        st->codec->codec_type = CODEC_TYPE_VIDEO;
527
    else if(type == MKTAG('s', 'o', 'u', 'n'))
528
        st->codec->codec_type = CODEC_TYPE_AUDIO;
529
    get_be32(pb); /* component  manufacture */
530
    get_be32(pb); /* component flags */
531
    get_be32(pb); /* component flags mask */
532

    
533
    if(atom.size <= 24)
534
        return 0; /* nothing left to read */
535
    /* XXX: MP4 uses a C string, not a pascal one */
536
    /* component name */
537

    
538
    if(c->mp4) {
539
        /* .mp4: C string */
540
        while(get_byte(pb) && (++len < (atom.size - 24)));
541
    } else {
542
        /* .mov: PASCAL string */
543
        len = get_byte(pb);
544
        url_fskip(pb, len);
545
    }
546

    
547
    url_fskip(pb, atom.size - (url_ftell(pb) - atom.offset));
548
    return 0;
549
}
550

    
551
static int mov_mp4_read_descr_len(ByteIOContext *pb)
552
{
553
    int len = 0;
554
    int count = 4;
555
    while (count--) {
556
        int c = get_byte(pb);
557
        len = (len << 7) | (c & 0x7f);
558
        if (!(c & 0x80))
559
            break;
560
    }
561
    return len;
562
}
563

    
564
static int mov_mp4_read_descr(ByteIOContext *pb, int *tag)
565
{
566
    int len;
567
    *tag = get_byte(pb);
568
    len = mov_mp4_read_descr_len(pb);
569
    dprintf("MPEG4 description: tag=0x%02x len=%d\n", *tag, len);
570
    return len;
571
}
572

    
573
static int mov_read_esds(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
574
{
575
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
576
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
577
    int tag, len;
578

    
579
    /* Well, broken but suffisant for some MP4 streams */
580
    get_be32(pb); /* version + flags */
581
    len = mov_mp4_read_descr(pb, &tag);
582
    if (tag == MP4ESDescrTag) {
583
        get_be16(pb); /* ID */
584
        get_byte(pb); /* priority */
585
    } else
586
        get_be16(pb); /* ID */
587

    
588
    len = mov_mp4_read_descr(pb, &tag);
589
    if (tag == MP4DecConfigDescrTag) {
590
        sc->esds.object_type_id = get_byte(pb);
591
        sc->esds.stream_type = get_byte(pb);
592
        sc->esds.buffer_size_db = get_be24(pb);
593
        sc->esds.max_bitrate = get_be32(pb);
594
        sc->esds.avg_bitrate = get_be32(pb);
595

    
596
        st->codec->codec_id= codec_get_id(ff_mov_obj_type, sc->esds.object_type_id);
597
        len = mov_mp4_read_descr(pb, &tag);
598
        if (tag == MP4DecSpecificDescrTag) {
599
            dprintf("Specific MPEG4 header len=%d\n", len);
600
            st->codec->extradata = (uint8_t*) av_mallocz(len + FF_INPUT_BUFFER_PADDING_SIZE);
601
            if (st->codec->extradata) {
602
                get_buffer(pb, st->codec->extradata, len);
603
                st->codec->extradata_size = len;
604
                /* from mplayer */
605
                if ((*(uint8_t *)st->codec->extradata >> 3) == 29) {
606
                    st->codec->codec_id = CODEC_ID_MP3ON4;
607
                }
608
            }
609
        }
610
    }
611
    return 0;
612
}
613

    
614
/* this atom contains actual media data */
615
static int mov_read_mdat(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
616
{
617
    if(atom.size == 0) /* wrong one (MP4) */
618
        return 0;
619
    c->found_mdat=1;
620
    c->mdat_offset = atom.offset;
621
    c->mdat_size = atom.size;
622
    if(c->found_moov)
623
        return 1; /* found both, just go */
624
    url_fskip(pb, atom.size);
625
    return 0; /* now go for moov */
626
}
627

    
628
static int mov_read_ftyp(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
629
{
630
    uint32_t type = get_le32(pb);
631

    
632
    /* from mplayer */
633
    switch (type) {
634
    case MKTAG('i', 's', 'o', 'm'):
635
    case MKTAG('m', 'p', '4', '1'):
636
    case MKTAG('m', 'p', '4', '2'):
637
    case MKTAG('3', 'g', 'p', '1'):
638
    case MKTAG('3', 'g', 'p', '2'):
639
    case MKTAG('3', 'g', '2', 'a'):
640
    case MKTAG('3', 'g', 'p', '3'):
641
    case MKTAG('3', 'g', 'p', '4'):
642
    case MKTAG('3', 'g', 'p', '5'):
643
    case MKTAG('m', 'm', 'p', '4'): /* Mobile MP4 */
644
    case MKTAG('M', '4', 'A', ' '): /* Apple iTunes AAC-LC Audio */
645
    case MKTAG('M', '4', 'P', ' '): /* Apple iTunes AAC-LC Protected Audio */
646
    case MKTAG('m', 'j', 'p', '2'): /* Motion Jpeg 2000 */
647
        c->mp4 = 1;
648
    case MKTAG('q', 't', ' ', ' '):
649
    default:
650
        av_log(c->fc, AV_LOG_DEBUG, "ISO: File Type Major Brand: %.4s\n",(char *)&type);
651
    }
652
    get_be32(pb); /* minor version */
653
    url_fskip(pb, atom.size - 8);
654
    return 0;
655
}
656

    
657
/* this atom should contain all header atoms */
658
static int mov_read_moov(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
659
{
660
    int err;
661

    
662
    err = mov_read_default(c, pb, atom);
663
    /* we parsed the 'moov' atom, we can terminate the parsing as soon as we find the 'mdat' */
664
    /* so we don't parse the whole file if over a network */
665
    c->found_moov=1;
666
    if(c->found_mdat)
667
        return 1; /* found both, just go */
668
    return 0; /* now go for mdat */
669
}
670

    
671

    
672
static int mov_read_mdhd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
673
{
674
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
675
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
676
    int version = get_byte(pb);
677
    int lang;
678

    
679
    if (version > 1)
680
        return 1; /* unsupported */
681

    
682
    get_byte(pb); get_byte(pb);
683
    get_byte(pb); /* flags */
684

    
685
    if (version == 1) {
686
        get_be64(pb);
687
        get_be64(pb);
688
    } else {
689
        get_be32(pb); /* creation time */
690
        get_be32(pb); /* modification time */
691
    }
692

    
693
    sc->time_scale = get_be32(pb);
694
    st->duration = (version == 1) ? get_be64(pb) : get_be32(pb); /* duration */
695

    
696
    lang = get_be16(pb); /* language */
697
    ff_mov_lang_to_iso639(lang, st->language);
698
    get_be16(pb); /* quality */
699

    
700
    return 0;
701
}
702

    
703
static int mov_read_mvhd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
704
{
705
    int version = get_byte(pb); /* version */
706
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
707

    
708
    if (version == 1) {
709
        get_be64(pb);
710
        get_be64(pb);
711
    } else {
712
        get_be32(pb); /* creation time */
713
        get_be32(pb); /* modification time */
714
    }
715
    c->time_scale = get_be32(pb); /* time scale */
716
#ifdef DEBUG
717
    av_log(NULL, AV_LOG_DEBUG, "time scale = %i\n", c->time_scale);
718
#endif
719
    c->duration = (version == 1) ? get_be64(pb) : get_be32(pb); /* duration */
720
    get_be32(pb); /* preferred scale */
721

    
722
    get_be16(pb); /* preferred volume */
723

    
724
    url_fskip(pb, 10); /* reserved */
725

    
726
    url_fskip(pb, 36); /* display matrix */
727

    
728
    get_be32(pb); /* preview time */
729
    get_be32(pb); /* preview duration */
730
    get_be32(pb); /* poster time */
731
    get_be32(pb); /* selection time */
732
    get_be32(pb); /* selection duration */
733
    get_be32(pb); /* current time */
734
    get_be32(pb); /* next track ID */
735

    
736
    return 0;
737
}
738

    
739
static int mov_read_smi(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
740
{
741
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
742

    
743
    if((uint64_t)atom.size > (1<<30))
744
        return -1;
745

    
746
    // currently SVQ3 decoder expect full STSD header - so let's fake it
747
    // this should be fixed and just SMI header should be passed
748
    av_free(st->codec->extradata);
749
    st->codec->extradata_size = 0x5a + atom.size;
750
    st->codec->extradata = (uint8_t*) av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
751

    
752
    if (st->codec->extradata) {
753
        strcpy(st->codec->extradata, "SVQ3"); // fake
754
        get_buffer(pb, st->codec->extradata + 0x5a, atom.size);
755
        dprintf("Reading SMI %"PRId64"  %s\n", atom.size, (char*)st->codec->extradata + 0x5a);
756
    } else
757
        url_fskip(pb, atom.size);
758

    
759
    return 0;
760
}
761

    
762
static int mov_read_enda(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
763
{
764
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
765
    int little_endian = get_be16(pb);
766

    
767
    if (little_endian) {
768
        switch (st->codec->codec_id) {
769
        case CODEC_ID_PCM_S24BE:
770
            st->codec->codec_id = CODEC_ID_PCM_S24LE;
771
            break;
772
        case CODEC_ID_PCM_S32BE:
773
            st->codec->codec_id = CODEC_ID_PCM_S32LE;
774
            break;
775
        default:
776
            break;
777
        }
778
    }
779
    return 0;
780
}
781

    
782
static int mov_read_alac(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
783
{
784
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
785

    
786
    // currently ALAC decoder expect full atom header - so let's fake it
787
    // this should be fixed and just ALAC header should be passed
788

    
789
    av_free(st->codec->extradata);
790
    st->codec->extradata_size = 36;
791
    st->codec->extradata = (uint8_t*) av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
792

    
793
    if (st->codec->extradata) {
794
        strcpy(st->codec->extradata + 4, "alac"); // fake
795
        get_buffer(pb, st->codec->extradata + 8, 36 - 8);
796
        dprintf("Reading alac %d  %s\n", st->codec->extradata_size, (char*)st->codec->extradata);
797
    } else
798
        url_fskip(pb, atom.size);
799
    return 0;
800
}
801

    
802
static int mov_read_wave(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
803
{
804
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
805

    
806
    if((uint64_t)atom.size > (1<<30))
807
        return -1;
808

    
809
    if (st->codec->codec_id == CODEC_ID_QDM2) {
810
        // pass all frma atom to codec, needed at least for QDM2
811
        av_free(st->codec->extradata);
812
        st->codec->extradata_size = atom.size;
813
        st->codec->extradata = (uint8_t*) av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
814

    
815
        if (st->codec->extradata) {
816
            get_buffer(pb, st->codec->extradata, atom.size);
817
        } else
818
            url_fskip(pb, atom.size);
819
    } else if (atom.size > 8) { /* to read frma, esds atoms */
820
        mov_read_default(c, pb, atom);
821
    } else
822
        url_fskip(pb, atom.size);
823
    return 0;
824
}
825

    
826
static int mov_read_jp2h(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
827
{
828
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
829

    
830
    if((uint64_t)atom.size > (1<<30))
831
        return -1;
832

    
833
    av_free(st->codec->extradata);
834

    
835
    st->codec->extradata_size = atom.size + 8;
836
    st->codec->extradata = (uint8_t*) av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
837

    
838
    /* pass all jp2h atom to codec */
839
    if (st->codec->extradata) {
840
        strcpy(st->codec->extradata + 4, "jp2h");
841
        get_buffer(pb, st->codec->extradata + 8, atom.size);
842
    } else
843
        url_fskip(pb, atom.size);
844
    return 0;
845
}
846

    
847
static int mov_read_avcC(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
848
{
849
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
850

    
851
    if((uint64_t)atom.size > (1<<30))
852
        return -1;
853

    
854
    av_free(st->codec->extradata);
855

    
856
    st->codec->extradata_size = atom.size;
857
    st->codec->extradata = (uint8_t*) av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
858

    
859
    if (st->codec->extradata) {
860
        get_buffer(pb, st->codec->extradata, atom.size);
861
    } else
862
        url_fskip(pb, atom.size);
863

    
864
    return 0;
865
}
866

    
867
static int mov_read_stco(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
868
{
869
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
870
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
871
    unsigned int i, entries;
872

    
873
    get_byte(pb); /* version */
874
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
875

    
876
    entries = get_be32(pb);
877

    
878
    if(entries >= UINT_MAX/sizeof(int64_t))
879
        return -1;
880

    
881
    sc->chunk_count = entries;
882
    sc->chunk_offsets = (int64_t*) av_malloc(entries * sizeof(int64_t));
883
    if (!sc->chunk_offsets)
884
        return -1;
885
    if (atom.type == MKTAG('s', 't', 'c', 'o')) {
886
        for(i=0; i<entries; i++) {
887
            sc->chunk_offsets[i] = get_be32(pb);
888
        }
889
    } else if (atom.type == MKTAG('c', 'o', '6', '4')) {
890
        for(i=0; i<entries; i++) {
891
            sc->chunk_offsets[i] = get_be64(pb);
892
        }
893
    } else
894
        return -1;
895

    
896
    for(i=0; i<c->fc->nb_streams; i++){
897
        MOVStreamContext *sc2 = (MOVStreamContext *)c->fc->streams[i]->priv_data;
898
        if(sc2 && sc2->chunk_offsets){
899
            int64_t first= sc2->chunk_offsets[0];
900
            int64_t last= sc2->chunk_offsets[sc2->chunk_count-1];
901
            if(first >= sc->chunk_offsets[entries-1] || last <= sc->chunk_offsets[0])
902
                c->ni=1;
903
        }
904
    }
905
    return 0;
906
}
907

    
908
static int mov_read_stsd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
909
{
910
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
911
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
912
    int entries, frames_per_sample;
913
    uint32_t format;
914
    uint8_t codec_name[32];
915

    
916
    /* for palette traversal */
917
    int color_depth;
918
    int color_start;
919
    int color_count;
920
    int color_end;
921
    int color_index;
922
    int color_dec;
923
    int color_greyscale;
924
    unsigned char *color_table;
925
    int j;
926
    unsigned char r, g, b;
927

    
928
    get_byte(pb); /* version */
929
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
930

    
931
    entries = get_be32(pb);
932

    
933
    while(entries--) { //Parsing Sample description table
934
        enum CodecID id;
935
        MOV_atom_t a = { 0, 0, 0 };
936
        offset_t start_pos = url_ftell(pb);
937
        int size = get_be32(pb); /* size */
938
        format = get_le32(pb); /* data format */
939

    
940
        get_be32(pb); /* reserved */
941
        get_be16(pb); /* reserved */
942
        get_be16(pb); /* index */
943

    
944
        st->codec->codec_tag = format;
945
        id = codec_get_id(mov_audio_tags, format);
946
        if (id > 0) {
947
            st->codec->codec_type = CODEC_TYPE_AUDIO;
948
        } else if (format && format != MKTAG('m', 'p', '4', 's')) { /* skip old asf mpeg4 tag */
949
            id = codec_get_id(mov_video_tags, format);
950
            if (id <= 0)
951
                id = codec_get_id(codec_bmp_tags, format);
952
            if (id > 0)
953
                st->codec->codec_type = CODEC_TYPE_VIDEO;
954
        }
955

    
956
        dprintf("size=%d 4CC= %c%c%c%c codec_type=%d\n",
957
                size,
958
                (format >> 0) & 0xff, (format >> 8) & 0xff, (format >> 16) & 0xff, (format >> 24) & 0xff,
959
                st->codec->codec_type);
960

    
961
        if(st->codec->codec_type==CODEC_TYPE_VIDEO) {
962
            st->codec->codec_id = id;
963
            get_be16(pb); /* version */
964
            get_be16(pb); /* revision level */
965
            get_be32(pb); /* vendor */
966
            get_be32(pb); /* temporal quality */
967
            get_be32(pb); /* spacial quality */
968

    
969
            st->codec->width = get_be16(pb); /* width */
970
            st->codec->height = get_be16(pb); /* height */
971

    
972
            get_be32(pb); /* horiz resolution */
973
            get_be32(pb); /* vert resolution */
974
            get_be32(pb); /* data size, always 0 */
975
            frames_per_sample = get_be16(pb); /* frames per samples */
976
#ifdef DEBUG
977
            av_log(NULL, AV_LOG_DEBUG, "frames/samples = %d\n", frames_per_sample);
978
#endif
979
            get_buffer(pb, codec_name, 32); /* codec name, pascal string (FIXME: true for mp4?) */
980
            if (codec_name[0] <= 31) {
981
                memcpy(st->codec->codec_name, &codec_name[1],codec_name[0]);
982
                st->codec->codec_name[codec_name[0]] = 0;
983
            }
984

    
985
            st->codec->bits_per_sample = get_be16(pb); /* depth */
986
            st->codec->color_table_id = get_be16(pb); /* colortable id */
987

    
988
/*          These are set in mov_read_stts and might already be set!
989
            st->codec->time_base.den      = 25;
990
            st->codec->time_base.num = 1;
991
*/
992

    
993
            /* figure out the palette situation */
994
            color_depth = st->codec->bits_per_sample & 0x1F;
995
            color_greyscale = st->codec->bits_per_sample & 0x20;
996

    
997
            /* if the depth is 2, 4, or 8 bpp, file is palettized */
998
            if ((color_depth == 2) || (color_depth == 4) ||
999
                (color_depth == 8)) {
1000

    
1001
                if (color_greyscale) {
1002

    
1003
                    /* compute the greyscale palette */
1004
                    color_count = 1 << color_depth;
1005
                    color_index = 255;
1006
                    color_dec = 256 / (color_count - 1);
1007
                    for (j = 0; j < color_count; j++) {
1008
                        r = g = b = color_index;
1009
                        c->palette_control.palette[j] =
1010
                            (r << 16) | (g << 8) | (b);
1011
                        color_index -= color_dec;
1012
                        if (color_index < 0)
1013
                            color_index = 0;
1014
                    }
1015

    
1016
                } else if (st->codec->color_table_id & 0x08) {
1017

    
1018
                    /* if flag bit 3 is set, use the default palette */
1019
                    color_count = 1 << color_depth;
1020
                    if (color_depth == 2)
1021
                        color_table = ff_qt_default_palette_4;
1022
                    else if (color_depth == 4)
1023
                        color_table = ff_qt_default_palette_16;
1024
                    else
1025
                        color_table = ff_qt_default_palette_256;
1026

    
1027
                    for (j = 0; j < color_count; j++) {
1028
                        r = color_table[j * 4 + 0];
1029
                        g = color_table[j * 4 + 1];
1030
                        b = color_table[j * 4 + 2];
1031
                        c->palette_control.palette[j] =
1032
                            (r << 16) | (g << 8) | (b);
1033
                    }
1034

    
1035
                } else {
1036

    
1037
                    /* load the palette from the file */
1038
                    color_start = get_be32(pb);
1039
                    color_count = get_be16(pb);
1040
                    color_end = get_be16(pb);
1041
                    for (j = color_start; j <= color_end; j++) {
1042
                        /* each R, G, or B component is 16 bits;
1043
                         * only use the top 8 bits; skip alpha bytes
1044
                         * up front */
1045
                        get_byte(pb);
1046
                        get_byte(pb);
1047
                        r = get_byte(pb);
1048
                        get_byte(pb);
1049
                        g = get_byte(pb);
1050
                        get_byte(pb);
1051
                        b = get_byte(pb);
1052
                        get_byte(pb);
1053
                        c->palette_control.palette[j] =
1054
                            (r << 16) | (g << 8) | (b);
1055
                    }
1056
                }
1057

    
1058
                st->codec->palctrl = &c->palette_control;
1059
                st->codec->palctrl->palette_changed = 1;
1060
            } else
1061
                st->codec->palctrl = NULL;
1062
        } else if(st->codec->codec_type==CODEC_TYPE_AUDIO) {
1063
            uint16_t version = get_be16(pb);
1064

    
1065
            st->codec->codec_id = id;
1066
            get_be16(pb); /* revision level */
1067
            get_be32(pb); /* vendor */
1068

    
1069
            st->codec->channels = get_be16(pb);             /* channel count */
1070
            st->codec->bits_per_sample = get_be16(pb);      /* sample size */
1071
            /* do we need to force to 16 for AMR ? */
1072

    
1073
            /* handle specific s8 codec */
1074
            get_be16(pb); /* compression id = 0*/
1075
            get_be16(pb); /* packet size = 0 */
1076

    
1077
            st->codec->sample_rate = ((get_be32(pb) >> 16));
1078

    
1079
            switch (st->codec->codec_id) {
1080
            case CODEC_ID_PCM_S16LE:
1081
            case CODEC_ID_PCM_S16BE:
1082
                if (st->codec->bits_per_sample == 8)
1083
                    st->codec->codec_id = CODEC_ID_PCM_S8;
1084
                st->codec->bit_rate = st->codec->sample_rate * 8;
1085
                break;
1086
            case CODEC_ID_PCM_U8:
1087
                if (st->codec->bits_per_sample == 16)
1088
                    st->codec->codec_id = CODEC_ID_PCM_S16BE;
1089
                st->codec->bit_rate = st->codec->sample_rate * 8;
1090
                break;
1091
            case CODEC_ID_AMR_WB:
1092
                st->codec->sample_rate = 16000; /* should really we ? */
1093
                st->codec->channels=1; /* really needed */
1094
                break;
1095
            case CODEC_ID_AMR_NB:
1096
                st->codec->sample_rate = 8000; /* should really we ? */
1097
                st->codec->channels=1; /* really needed */
1098
                break;
1099
            default:
1100
                break;
1101
            }
1102

    
1103
            //Read QT version 1 fields. In version 0 theese dont exist
1104
            dprintf("version =%d mp4=%d\n",version,c->mp4);
1105
            if(version==1) {
1106
                get_be32(pb); /* samples per packet */
1107
                get_be32(pb); /* bytes per packet */
1108
                get_be32(pb); /* bytes per frame */
1109
                get_be32(pb); /* bytes per sample */
1110
            } else if(version==2) {
1111
                get_be32(pb); /* sizeof struct only */
1112
                st->codec->sample_rate = av_int2dbl(get_be64(pb)); /* float 64 */
1113
                st->codec->channels = get_be32(pb);
1114
                get_be32(pb); /* always 0x7F000000 */
1115
                get_be32(pb); /* bits per channel if sound is uncompressed */
1116
                get_be32(pb); /* lcpm format specific flag */
1117
                get_be32(pb); /* bytes per audio packet if constant */
1118
                get_be32(pb); /* lpcm frames per audio packet if constant */
1119
            }
1120
        } else {
1121
            /* other codec type, just skip (rtp, mp4s, tmcd ...) */
1122
            url_fskip(pb, size - (url_ftell(pb) - start_pos));
1123
        }
1124
        /* this will read extra atoms at the end (wave, alac, damr, avcC, SMI ...) */
1125
        a.size = size - (url_ftell(pb) - start_pos);
1126
        if (a.size > 8)
1127
            mov_read_default(c, pb, a);
1128
        else if (a.size > 0)
1129
            url_fskip(pb, a.size);
1130
    }
1131

    
1132
    if(st->codec->codec_type==CODEC_TYPE_AUDIO && st->codec->sample_rate==0 && sc->time_scale>1) {
1133
        st->codec->sample_rate= sc->time_scale;
1134
    }
1135

    
1136
    switch (st->codec->codec_id) {
1137
#ifdef CONFIG_FAAD
1138
    case CODEC_ID_AAC:
1139
#endif
1140
#ifdef CONFIG_VORBIS_DECODER
1141
    case CODEC_ID_VORBIS:
1142
#endif
1143
    case CODEC_ID_MP3ON4:
1144
        st->codec->sample_rate= 0; /* let decoder init parameters properly */
1145
        break;
1146
    default:
1147
        break;
1148
    }
1149

    
1150
    return 0;
1151
}
1152

    
1153
static int mov_read_stsc(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1154
{
1155
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
1156
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
1157
    unsigned int i, entries;
1158

    
1159
    get_byte(pb); /* version */
1160
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
1161

    
1162
    entries = get_be32(pb);
1163

    
1164
    if(entries >= UINT_MAX / sizeof(MOV_sample_to_chunk_tbl))
1165
        return -1;
1166

    
1167
#ifdef DEBUG
1168
av_log(NULL, AV_LOG_DEBUG, "track[%i].stsc.entries = %i\n", c->fc->nb_streams-1, entries);
1169
#endif
1170
    sc->sample_to_chunk_sz = entries;
1171
    sc->sample_to_chunk = (MOV_sample_to_chunk_tbl*) av_malloc(entries * sizeof(MOV_sample_to_chunk_tbl));
1172
    if (!sc->sample_to_chunk)
1173
        return -1;
1174
    for(i=0; i<entries; i++) {
1175
        sc->sample_to_chunk[i].first = get_be32(pb);
1176
        sc->sample_to_chunk[i].count = get_be32(pb);
1177
        sc->sample_to_chunk[i].id = get_be32(pb);
1178
    }
1179
    return 0;
1180
}
1181

    
1182
static int mov_read_stss(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1183
{
1184
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
1185
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
1186
    unsigned int i, entries;
1187

    
1188
    get_byte(pb); /* version */
1189
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
1190

    
1191
    entries = get_be32(pb);
1192

    
1193
    if(entries >= UINT_MAX / sizeof(long))
1194
        return -1;
1195

    
1196
    sc->keyframe_count = entries;
1197
#ifdef DEBUG
1198
    av_log(NULL, AV_LOG_DEBUG, "keyframe_count = %ld\n", sc->keyframe_count);
1199
#endif
1200
    sc->keyframes = (long*) av_malloc(entries * sizeof(long));
1201
    if (!sc->keyframes)
1202
        return -1;
1203
    for(i=0; i<entries; i++) {
1204
        sc->keyframes[i] = get_be32(pb);
1205
#ifdef DEBUG
1206
/*        av_log(NULL, AV_LOG_DEBUG, "keyframes[]=%ld\n", sc->keyframes[i]); */
1207
#endif
1208
    }
1209
    return 0;
1210
}
1211

    
1212
static int mov_read_stsz(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1213
{
1214
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
1215
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
1216
    unsigned int i, entries;
1217

    
1218
    get_byte(pb); /* version */
1219
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
1220

    
1221
    sc->sample_size = get_be32(pb);
1222
    entries = get_be32(pb);
1223
    if(entries >= UINT_MAX / sizeof(long))
1224
        return -1;
1225

    
1226
    sc->sample_count = entries;
1227
#ifdef DEBUG
1228
    av_log(NULL, AV_LOG_DEBUG, "sample_size = %ld sample_count = %ld\n", sc->sample_size, sc->sample_count);
1229
#endif
1230
    if(sc->sample_size) {
1231
        /* override sample size for uncompressed sound */
1232
        switch (st->codec->codec_id) {
1233
        case CODEC_ID_PCM_S32BE:
1234
        case CODEC_ID_PCM_S32LE:
1235
            sc->sample_size = 4 * st->codec->channels;
1236
            break;
1237
        case CODEC_ID_PCM_S24BE:
1238
        case CODEC_ID_PCM_S24LE:
1239
            sc->sample_size = 3 * st->codec->channels;
1240
            break;
1241
        case CODEC_ID_PCM_S16BE:
1242
        case CODEC_ID_PCM_S16LE:
1243
            sc->sample_size = 2 * st->codec->channels;
1244
            break;
1245
        case CODEC_ID_PCM_MULAW:
1246
        case CODEC_ID_PCM_ALAW:
1247
        case CODEC_ID_PCM_S8:
1248
        case CODEC_ID_PCM_U8:
1249
            sc->sample_size = 1 * st->codec->channels;
1250
            break;
1251
        default:
1252
            break;
1253
        }
1254
        assert(sc->sample_size);
1255
        return 0; /* there isn't any table following */
1256
    }
1257
    sc->sample_sizes = (long*) av_malloc(entries * sizeof(long));
1258
    if (!sc->sample_sizes)
1259
        return -1;
1260
    for(i=0; i<entries; i++) {
1261
        sc->sample_sizes[i] = get_be32(pb);
1262
#ifdef DEBUG
1263
        av_log(NULL, AV_LOG_DEBUG, "sample_sizes[]=%ld\n", sc->sample_sizes[i]);
1264
#endif
1265
    }
1266
    return 0;
1267
}
1268

    
1269
static int mov_read_stts(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1270
{
1271
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
1272
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
1273
    unsigned int i, entries;
1274
    int64_t duration=0;
1275
    int64_t total_sample_count=0;
1276

    
1277
    get_byte(pb); /* version */
1278
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
1279
    entries = get_be32(pb);
1280
    if(entries >= UINT_MAX / sizeof(Time2Sample))
1281
        return -1;
1282

    
1283
    sc->stts_count = entries;
1284
    sc->stts_data = av_malloc(entries * sizeof(Time2Sample));
1285

    
1286
#ifdef DEBUG
1287
av_log(NULL, AV_LOG_DEBUG, "track[%i].stts.entries = %i\n", c->fc->nb_streams-1, entries);
1288
#endif
1289

    
1290
    sc->time_rate=0;
1291

    
1292
    for(i=0; i<entries; i++) {
1293
        int sample_duration;
1294
        int sample_count;
1295

    
1296
        sample_count=get_be32(pb);
1297
        sample_duration = get_be32(pb);
1298
        sc->stts_data[i].count= sample_count;
1299
        sc->stts_data[i].duration= sample_duration;
1300

    
1301
        sc->time_rate= ff_gcd(sc->time_rate, sample_duration);
1302

    
1303
        dprintf("sample_count=%d, sample_duration=%d\n",sample_count,sample_duration);
1304

    
1305
        duration+=(int64_t)sample_duration*sample_count;
1306
        total_sample_count+=sample_count;
1307
    }
1308

    
1309
    st->nb_frames= total_sample_count;
1310
    if(duration)
1311
        st->duration= duration;
1312
    return 0;
1313
}
1314

    
1315
static int mov_read_ctts(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1316
{
1317
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
1318
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
1319
    unsigned int i, entries;
1320

    
1321
    get_byte(pb); /* version */
1322
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
1323
    entries = get_be32(pb);
1324
    if(entries >= UINT_MAX / sizeof(Time2Sample))
1325
        return -1;
1326

    
1327
    sc->ctts_count = entries;
1328
    sc->ctts_data = av_malloc(entries * sizeof(Time2Sample));
1329

    
1330
    dprintf("track[%i].ctts.entries = %i\n", c->fc->nb_streams-1, entries);
1331

    
1332
    for(i=0; i<entries; i++) {
1333
        int count    =get_be32(pb);
1334
        int duration =get_be32(pb);
1335

    
1336
        if (duration < 0) {
1337
            av_log(c->fc, AV_LOG_ERROR, "negative ctts, ignoring\n");
1338
            sc->ctts_count = 0;
1339
            url_fskip(pb, 8 * (entries - i - 1));
1340
            break;
1341
        }
1342
        sc->ctts_data[i].count   = count;
1343
        sc->ctts_data[i].duration= duration;
1344

    
1345
        sc->time_rate= ff_gcd(sc->time_rate, duration);
1346
    }
1347
    return 0;
1348
}
1349

    
1350
static int mov_read_trak(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1351
{
1352
    AVStream *st;
1353
    MOVStreamContext *sc;
1354

    
1355
    st = av_new_stream(c->fc, c->fc->nb_streams);
1356
    if (!st) return -2;
1357
    sc = (MOVStreamContext*) av_mallocz(sizeof(MOVStreamContext));
1358
    if (!sc) {
1359
        av_free(st);
1360
        return -1;
1361
    }
1362

    
1363
    sc->sample_to_chunk_index = -1;
1364
    st->priv_data = sc;
1365
    st->codec->codec_type = CODEC_TYPE_MOV_OTHER;
1366
    st->start_time = 0; /* XXX: check */
1367
    c->streams[c->fc->nb_streams-1] = sc;
1368

    
1369
    return mov_read_default(c, pb, atom);
1370
}
1371

    
1372
static int mov_read_tkhd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1373
{
1374
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
1375
    int version = get_byte(pb);
1376

    
1377
    get_byte(pb); get_byte(pb);
1378
    get_byte(pb); /* flags */
1379
    /*
1380
    MOV_TRACK_ENABLED 0x0001
1381
    MOV_TRACK_IN_MOVIE 0x0002
1382
    MOV_TRACK_IN_PREVIEW 0x0004
1383
    MOV_TRACK_IN_POSTER 0x0008
1384
    */
1385

    
1386
    if (version == 1) {
1387
        get_be64(pb);
1388
        get_be64(pb);
1389
    } else {
1390
        get_be32(pb); /* creation time */
1391
        get_be32(pb); /* modification time */
1392
    }
1393
    st->id = (int)get_be32(pb); /* track id (NOT 0 !)*/
1394
    get_be32(pb); /* reserved */
1395
    st->start_time = 0; /* check */
1396
    (version == 1) ? get_be64(pb) : get_be32(pb); /* highlevel (considering edits) duration in movie timebase */
1397
    get_be32(pb); /* reserved */
1398
    get_be32(pb); /* reserved */
1399

    
1400
    get_be16(pb); /* layer */
1401
    get_be16(pb); /* alternate group */
1402
    get_be16(pb); /* volume */
1403
    get_be16(pb); /* reserved */
1404

    
1405
    url_fskip(pb, 36); /* display matrix */
1406

    
1407
    /* those are fixed-point */
1408
    /*st->codec->width =*/ get_be32(pb) >> 16; /* track width */
1409
    /*st->codec->height =*/ get_be32(pb) >> 16; /* track height */
1410

    
1411
    return 0;
1412
}
1413

    
1414
/* this atom should be null (from specs), but some buggy files put the 'moov' atom inside it... */
1415
/* like the files created with Adobe Premiere 5.0, for samples see */
1416
/* http://graphics.tudelft.nl/~wouter/publications/soundtests/ */
1417
static int mov_read_wide(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1418
{
1419
    int err;
1420

    
1421
    if (atom.size < 8)
1422
        return 0; /* continue */
1423
    if (get_be32(pb) != 0) { /* 0 sized mdat atom... use the 'wide' atom size */
1424
        url_fskip(pb, atom.size - 4);
1425
        return 0;
1426
    }
1427
    atom.type = get_le32(pb);
1428
    atom.offset += 8;
1429
    atom.size -= 8;
1430
    if (atom.type != MKTAG('m', 'd', 'a', 't')) {
1431
        url_fskip(pb, atom.size);
1432
        return 0;
1433
    }
1434
    err = mov_read_mdat(c, pb, atom);
1435
    return err;
1436
}
1437

    
1438

    
1439
#ifdef CONFIG_ZLIB
1440
static int null_read_packet(void *opaque, uint8_t *buf, int buf_size)
1441
{
1442
    return -1;
1443
}
1444

    
1445
static int mov_read_cmov(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1446
{
1447
    ByteIOContext ctx;
1448
    uint8_t *cmov_data;
1449
    uint8_t *moov_data; /* uncompressed data */
1450
    long cmov_len, moov_len;
1451
    int ret;
1452

    
1453
    get_be32(pb); /* dcom atom */
1454
    if (get_le32(pb) != MKTAG( 'd', 'c', 'o', 'm' ))
1455
        return -1;
1456
    if (get_le32(pb) != MKTAG( 'z', 'l', 'i', 'b' )) {
1457
        av_log(NULL, AV_LOG_ERROR, "unknown compression for cmov atom !");
1458
        return -1;
1459
    }
1460
    get_be32(pb); /* cmvd atom */
1461
    if (get_le32(pb) != MKTAG( 'c', 'm', 'v', 'd' ))
1462
        return -1;
1463
    moov_len = get_be32(pb); /* uncompressed size */
1464
    cmov_len = atom.size - 6 * 4;
1465

    
1466
    cmov_data = (uint8_t *) av_malloc(cmov_len);
1467
    if (!cmov_data)
1468
        return -1;
1469
    moov_data = (uint8_t *) av_malloc(moov_len);
1470
    if (!moov_data) {
1471
        av_free(cmov_data);
1472
        return -1;
1473
    }
1474
    get_buffer(pb, cmov_data, cmov_len);
1475
    if(uncompress (moov_data, (uLongf *) &moov_len, (const Bytef *)cmov_data, cmov_len) != Z_OK)
1476
        return -1;
1477
    if(init_put_byte(&ctx, moov_data, moov_len, 0, NULL, null_read_packet, NULL, NULL) != 0)
1478
        return -1;
1479
    ctx.buf_end = ctx.buffer + moov_len;
1480
    atom.type = MKTAG( 'm', 'o', 'o', 'v' );
1481
    atom.offset = 0;
1482
    atom.size = moov_len;
1483
#ifdef DEBUG
1484
//    { int fd = open("/tmp/uncompheader.mov", O_WRONLY | O_CREAT); write(fd, moov_data, moov_len); close(fd); }
1485
#endif
1486
    ret = mov_read_default(c, &ctx, atom);
1487
    av_free(moov_data);
1488
    av_free(cmov_data);
1489

    
1490
    return ret;
1491
}
1492
#endif
1493

    
1494
/* edit list atom */
1495
static int mov_read_elst(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
1496
{
1497
    int i, edit_count;
1498

    
1499
    get_byte(pb); /* version */
1500
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
1501
    edit_count= c->streams[c->fc->nb_streams-1]->edit_count = get_be32(pb);     /* entries */
1502

    
1503
    for(i=0; i<edit_count; i++){
1504
        get_be32(pb); /* Track duration */
1505
        get_be32(pb); /* Media time */
1506
        get_be32(pb); /* Media rate */
1507
    }
1508
    dprintf("track[%i].edit_count = %i\n", c->fc->nb_streams-1, c->streams[c->fc->nb_streams-1]->edit_count);
1509
    return 0;
1510
}
1511

    
1512
static const MOVParseTableEntry mov_default_parse_table[] = {
1513
/* mp4 atoms */
1514
{ MKTAG( 'c', 'o', '6', '4' ), mov_read_stco },
1515
{ MKTAG( 'c', 'p', 'r', 't' ), mov_read_default },
1516
{ MKTAG( 'c', 'r', 'h', 'd' ), mov_read_default },
1517
{ MKTAG( 'c', 't', 't', 's' ), mov_read_ctts }, /* composition time to sample */
1518
{ MKTAG( 'd', 'i', 'n', 'f' ), mov_read_default }, /* data information */
1519
{ MKTAG( 'd', 'p', 'n', 'd' ), mov_read_leaf },
1520
{ MKTAG( 'd', 'r', 'e', 'f' ), mov_read_leaf },
1521
{ MKTAG( 'e', 'd', 't', 's' ), mov_read_default },
1522
{ MKTAG( 'e', 'l', 's', 't' ), mov_read_elst },
1523
{ MKTAG( 'e', 'n', 'd', 'a' ), mov_read_enda },
1524
{ MKTAG( 'f', 'r', 'e', 'e' ), mov_read_leaf },
1525
{ MKTAG( 'f', 't', 'y', 'p' ), mov_read_ftyp },
1526
{ MKTAG( 'h', 'd', 'l', 'r' ), mov_read_hdlr },
1527
{ MKTAG( 'h', 'i', 'n', 't' ), mov_read_leaf },
1528
{ MKTAG( 'h', 'm', 'h', 'd' ), mov_read_leaf },
1529
{ MKTAG( 'i', 'o', 'd', 's' ), mov_read_leaf },
1530
{ MKTAG( 'j', 'p', '2', 'h' ), mov_read_jp2h },
1531
{ MKTAG( 'm', 'd', 'a', 't' ), mov_read_mdat },
1532
{ MKTAG( 'm', 'd', 'h', 'd' ), mov_read_mdhd },
1533
{ MKTAG( 'm', 'd', 'i', 'a' ), mov_read_default },
1534
{ MKTAG( 'm', 'i', 'n', 'f' ), mov_read_default },
1535
{ MKTAG( 'm', 'o', 'o', 'v' ), mov_read_moov },
1536
{ MKTAG( 'm', 'p', '4', 'a' ), mov_read_default },
1537
{ MKTAG( 'm', 'p', '4', 's' ), mov_read_default },
1538
{ MKTAG( 'm', 'p', '4', 'v' ), mov_read_default },
1539
{ MKTAG( 'm', 'p', 'o', 'd' ), mov_read_leaf },
1540
{ MKTAG( 'm', 'v', 'h', 'd' ), mov_read_mvhd },
1541
{ MKTAG( 'n', 'm', 'h', 'd' ), mov_read_leaf },
1542
{ MKTAG( 'o', 'd', 'h', 'd' ), mov_read_default },
1543
{ MKTAG( 's', 'd', 'h', 'd' ), mov_read_default },
1544
{ MKTAG( 's', 'k', 'i', 'p' ), mov_read_leaf },
1545
{ MKTAG( 's', 'm', 'h', 'd' ), mov_read_leaf }, /* sound media info header */
1546
{ MKTAG( 'S', 'M', 'I', ' ' ), mov_read_smi }, /* Sorenson extension ??? */
1547
{ MKTAG( 'a', 'l', 'a', 'c' ), mov_read_alac }, /* alac specific atom */
1548
{ MKTAG( 'a', 'v', 'c', 'C' ), mov_read_avcC },
1549
{ MKTAG( 's', 't', 'b', 'l' ), mov_read_default },
1550
{ MKTAG( 's', 't', 'c', 'o' ), mov_read_stco },
1551
{ MKTAG( 's', 't', 'd', 'p' ), mov_read_default },
1552
{ MKTAG( 's', 't', 's', 'c' ), mov_read_stsc },
1553
{ MKTAG( 's', 't', 's', 'd' ), mov_read_stsd }, /* sample description */
1554
{ MKTAG( 's', 't', 's', 'h' ), mov_read_default },
1555
{ MKTAG( 's', 't', 's', 's' ), mov_read_stss }, /* sync sample */
1556
{ MKTAG( 's', 't', 's', 'z' ), mov_read_stsz }, /* sample size */
1557
{ MKTAG( 's', 't', 't', 's' ), mov_read_stts },
1558
{ MKTAG( 't', 'k', 'h', 'd' ), mov_read_tkhd }, /* track header */
1559
{ MKTAG( 't', 'r', 'a', 'k' ), mov_read_trak },
1560
{ MKTAG( 't', 'r', 'e', 'f' ), mov_read_default }, /* not really */
1561
{ MKTAG( 'u', 'd', 't', 'a' ), mov_read_leaf },
1562
{ MKTAG( 'u', 'r', 'l', ' ' ), mov_read_leaf },
1563
{ MKTAG( 'u', 'r', 'n', ' ' ), mov_read_leaf },
1564
{ MKTAG( 'u', 'u', 'i', 'd' ), mov_read_leaf },
1565
{ MKTAG( 'v', 'm', 'h', 'd' ), mov_read_leaf }, /* video media info header */
1566
{ MKTAG( 'w', 'a', 'v', 'e' ), mov_read_wave },
1567
/* extra mp4 */
1568
{ MKTAG( 'M', 'D', 'E', 'S' ), mov_read_leaf },
1569
/* QT atoms */
1570
{ MKTAG( 'c', 'h', 'a', 'p' ), mov_read_leaf },
1571
{ MKTAG( 'c', 'l', 'i', 'p' ), mov_read_default },
1572
{ MKTAG( 'c', 'r', 'g', 'n' ), mov_read_leaf },
1573
{ MKTAG( 'c', 't', 'a', 'b' ), mov_read_ctab },
1574
{ MKTAG( 'e', 's', 'd', 's' ), mov_read_esds },
1575
{ MKTAG( 'k', 'm', 'a', 't' ), mov_read_leaf },
1576
{ MKTAG( 'm', 'a', 't', 't' ), mov_read_default },
1577
{ MKTAG( 'r', 'd', 'r', 'f' ), mov_read_leaf },
1578
{ MKTAG( 'r', 'm', 'd', 'a' ), mov_read_default },
1579
{ MKTAG( 'r', 'm', 'd', 'r' ), mov_read_leaf },
1580
{ MKTAG( 'r', 'm', 'r', 'a' ), mov_read_default },
1581
{ MKTAG( 's', 'c', 'p', 't' ), mov_read_leaf },
1582
{ MKTAG( 's', 's', 'r', 'c' ), mov_read_leaf },
1583
{ MKTAG( 's', 'y', 'n', 'c' ), mov_read_leaf },
1584
{ MKTAG( 't', 'c', 'm', 'd' ), mov_read_leaf },
1585
{ MKTAG( 'w', 'i', 'd', 'e' ), mov_read_wide }, /* place holder */
1586
//{ MKTAG( 'r', 'm', 'q', 'u' ), mov_read_leaf },
1587
#ifdef CONFIG_ZLIB
1588
{ MKTAG( 'c', 'm', 'o', 'v' ), mov_read_cmov },
1589
#else
1590
{ MKTAG( 'c', 'm', 'o', 'v' ), mov_read_leaf },
1591
#endif
1592
{ 0L, mov_read_leaf }
1593
};
1594

    
1595
static void mov_free_stream_context(MOVStreamContext *sc)
1596
{
1597
    if(sc) {
1598
        av_freep(&sc->chunk_offsets);
1599
        av_freep(&sc->sample_to_chunk);
1600
        av_freep(&sc->sample_sizes);
1601
        av_freep(&sc->keyframes);
1602
        av_freep(&sc->stts_data);
1603
        av_freep(&sc->ctts_data);
1604
        av_freep(&sc);
1605
    }
1606
}
1607

    
1608
static inline uint32_t mov_to_tag(uint8_t *buf)
1609
{
1610
    return MKTAG(buf[0], buf[1], buf[2], buf[3]);
1611
}
1612

    
1613
static inline uint32_t to_be32(uint8_t *buf)
1614
{
1615
    return (buf[0] << 24) | (buf[1] << 16) | (buf[2] << 8) | buf[3];
1616
}
1617

    
1618
/* XXX: is it sufficient ? */
1619
static int mov_probe(AVProbeData *p)
1620
{
1621
    unsigned int offset;
1622
    uint32_t tag;
1623
    int score = 0;
1624

    
1625
    /* check file header */
1626
    if (p->buf_size <= 12)
1627
        return 0;
1628
    offset = 0;
1629
    for(;;) {
1630
        /* ignore invalid offset */
1631
        if ((offset + 8) > (unsigned int)p->buf_size)
1632
            return score;
1633
        tag = mov_to_tag(p->buf + offset + 4);
1634
        switch(tag) {
1635
        /* check for obvious tags */
1636
        case MKTAG( 'j', 'P', ' ', ' ' ): /* jpeg 2000 signature */
1637
        case MKTAG( 'm', 'o', 'o', 'v' ):
1638
        case MKTAG( 'm', 'd', 'a', 't' ):
1639
        case MKTAG( 'p', 'n', 'o', 't' ): /* detect movs with preview pics like ew.mov and april.mov */
1640
        case MKTAG( 'u', 'd', 't', 'a' ): /* Packet Video PVAuthor adds this and a lot of more junk */
1641
            return AVPROBE_SCORE_MAX;
1642
        /* those are more common words, so rate then a bit less */
1643
        case MKTAG( 'w', 'i', 'd', 'e' ):
1644
        case MKTAG( 'f', 'r', 'e', 'e' ):
1645
        case MKTAG( 'j', 'u', 'n', 'k' ):
1646
        case MKTAG( 'p', 'i', 'c', 't' ):
1647
            return AVPROBE_SCORE_MAX - 5;
1648
        case MKTAG( 'f', 't', 'y', 'p' ):
1649
        case MKTAG( 's', 'k', 'i', 'p' ):
1650
        case MKTAG( 'u', 'u', 'i', 'd' ):
1651
            offset = to_be32(p->buf+offset) + offset;
1652
            /* if we only find those cause probedata is too small at least rate them */
1653
            score = AVPROBE_SCORE_MAX - 50;
1654
            break;
1655
        default:
1656
            /* unrecognized tag */
1657
            return score;
1658
        }
1659
    }
1660
    return score;
1661
}
1662

    
1663
static int mov_read_header(AVFormatContext *s, AVFormatParameters *ap)
1664
{
1665
    MOVContext *mov = (MOVContext *) s->priv_data;
1666
    ByteIOContext *pb = &s->pb;
1667
    int i, j, nb, err;
1668
    MOV_atom_t atom = { 0, 0, 0 };
1669

    
1670
    mov->fc = s;
1671
    mov->parse_table = mov_default_parse_table;
1672

    
1673
    if(!url_is_streamed(pb)) /* .mov and .mp4 aren't streamable anyway (only progressive download if moov is before mdat) */
1674
        atom.size = url_fsize(pb);
1675
    else
1676
        atom.size = 0x7FFFFFFFFFFFFFFFLL;
1677

    
1678
    /* check MOV header */
1679
    err = mov_read_default(mov, pb, atom);
1680
    if (err<0 || (!mov->found_moov && !mov->found_mdat)) {
1681
        av_log(s, AV_LOG_ERROR, "mov: header not found !!! (err:%d, moov:%d, mdat:%d) pos:%"PRId64"\n",
1682
                err, mov->found_moov, mov->found_mdat, url_ftell(pb));
1683
        return -1;
1684
    }
1685
    dprintf("on_parse_exit_offset=%d\n", (int) url_ftell(pb));
1686

    
1687
    /* some cleanup : make sure we are on the mdat atom */
1688
    if(!url_is_streamed(pb) && (url_ftell(pb) != mov->mdat_offset))
1689
        url_fseek(pb, mov->mdat_offset, SEEK_SET);
1690

    
1691
    mov->next_chunk_offset = mov->mdat_offset; /* initialise reading */
1692
    mov->total_streams = nb = s->nb_streams;
1693

    
1694
#if 1
1695
    for(i=0; i<s->nb_streams;) {
1696
        if(s->streams[i]->codec->codec_type == CODEC_TYPE_MOV_OTHER) {/* not audio, not video, delete */
1697
            av_free(s->streams[i]);
1698
            for(j=i+1; j<s->nb_streams; j++)
1699
                s->streams[j-1] = s->streams[j];
1700
            s->nb_streams--;
1701
        } else
1702
            i++;
1703
    }
1704
    for(i=0; i<s->nb_streams;i++) {
1705
        MOVStreamContext *sc = (MOVStreamContext *)s->streams[i]->priv_data;
1706

    
1707
        if(!sc->time_rate)
1708
            sc->time_rate=1;
1709
        if(!sc->time_scale)
1710
            sc->time_scale= mov->time_scale;
1711
        av_set_pts_info(s->streams[i], 64, sc->time_rate, sc->time_scale);
1712

    
1713
        if(s->streams[i]->duration != AV_NOPTS_VALUE){
1714
            assert(s->streams[i]->duration % sc->time_rate == 0);
1715
            s->streams[i]->duration /= sc->time_rate;
1716
        }
1717

    
1718
        sc->ffindex = i;
1719
        sc->is_ff_stream = 1;
1720
    }
1721
#endif
1722
    return 0;
1723
}
1724

    
1725
/* Yes, this is ugly... I didn't write the specs of QT :p */
1726
/* XXX:remove useless commented code sometime */
1727
static int mov_read_packet(AVFormatContext *s, AVPacket *pkt)
1728
{
1729
    MOVContext *mov = (MOVContext *) s->priv_data;
1730
    MOVStreamContext *sc;
1731
    AVStream *st;
1732
    int64_t offset = INT64_MAX;
1733
    int64_t best_dts = INT64_MAX;
1734
    int i, a, b, m;
1735
    int next_sample= -99;
1736
    int size;
1737
    int idx;
1738
    size = 0x0FFFFFFF;
1739

    
1740
    if (mov->partial) {
1741
        sc = mov->partial;
1742
        idx = sc->sample_to_chunk_index;
1743

    
1744
        if (idx < 0) return 0;
1745
        dprintf("sc[ffid %d]->sample_size = %ld\n", sc->ffindex, sc->sample_size);
1746
        //size = sc->sample_sizes[sc->current_sample];
1747
        // that ain't working...
1748
        //size = (sc->sample_size)?sc->sample_size:sc->sample_sizes[sc->current_sample];
1749
        size = (sc->sample_size > 1)?sc->sample_size:sc->sample_sizes[sc->current_sample];
1750

    
1751
        next_sample= sc->current_sample+1;
1752

    
1753
        sc->left_in_chunk--;
1754

    
1755
        if (sc->left_in_chunk <= 0)
1756
            mov->partial = 0;
1757
        offset = mov->next_chunk_offset;
1758
        /* extract the sample */
1759

    
1760
        goto readchunk;
1761
    }
1762

    
1763
again:
1764
    sc = 0;
1765
    if(offset == INT64_MAX)
1766
        best_dts= INT64_MAX;
1767
    for(i=0; i<mov->total_streams; i++) {
1768
        MOVStreamContext *msc = mov->streams[i];
1769

    
1770
        if ((msc->next_chunk < msc->chunk_count) && msc->next_chunk >= 0){
1771
            if (msc->sample_to_time_index < msc->stts_count && mov->ni) {
1772
                int64_t dts;
1773
                int index= msc->sample_to_time_index;
1774
                int sample= msc->sample_to_time_sample;
1775
                int time= msc->sample_to_time_time;
1776
                int duration = msc->stts_data[index].duration;
1777
                int count = msc->stts_data[index].count;
1778
                if (sample + count <= msc->current_sample) {
1779
                    sample += count;
1780
                    time   += count*duration;
1781
                    index ++;
1782
                    duration = msc->stts_data[index].duration;
1783
                }
1784
                dts = time + (msc->current_sample - sample) * (int64_t)duration;
1785
                dts = av_rescale(dts, AV_TIME_BASE, msc->time_scale);
1786
                dprintf("stream: %d dts: %"PRId64" best_dts: %"PRId64" offset: %"PRId64"\n", i, dts, best_dts, offset);
1787
                if(dts < best_dts){
1788
                    best_dts= dts;
1789
                    sc = msc;
1790
                    offset = msc->chunk_offsets[msc->next_chunk];
1791
                }
1792
            }else{
1793
                if ((msc->chunk_offsets[msc->next_chunk] < offset)) {
1794
                    sc = msc;
1795
                    offset = msc->chunk_offsets[msc->next_chunk];
1796
                }
1797
            }
1798
        }
1799
    }
1800
    if (!sc || offset==INT64_MAX)
1801
        return -1;
1802

    
1803
    sc->next_chunk++;
1804

    
1805
    if(mov->next_chunk_offset < offset) { /* some meta data */
1806
        url_fskip(&s->pb, (offset - mov->next_chunk_offset));
1807
        mov->next_chunk_offset = offset;
1808
    }
1809

    
1810
    if(!sc->is_ff_stream || (s->streams[sc->ffindex]->discard >= AVDISCARD_ALL)) {
1811
        url_fskip(&s->pb, (offset - mov->next_chunk_offset));
1812
        mov->next_chunk_offset = offset;
1813
        offset = INT64_MAX;
1814
        goto again;
1815
    }
1816

    
1817
    idx = sc->sample_to_chunk_index;
1818
    if (idx + 1 < sc->sample_to_chunk_sz && sc->next_chunk >= sc->sample_to_chunk[idx + 1].first)
1819
        idx++;
1820
    sc->sample_to_chunk_index = idx;
1821
    /* split chunks into samples */
1822
    if (sc->sample_size == 0 || sc->sample_size > 100) {
1823
        if (idx >= 0 && sc->sample_to_chunk[idx].count != 1) {
1824
            mov->partial = sc;
1825
            /* we'll have to get those samples before next chunk */
1826
            sc->left_in_chunk = sc->sample_to_chunk[idx].count - 1;
1827
        }
1828
        size = (sc->sample_size > 1)?sc->sample_size:sc->sample_sizes[sc->current_sample];
1829
        next_sample= sc->current_sample+1;
1830
    }else{
1831
        int adjusted= 0;
1832
        /* get the chunk size... */
1833
        for(i=0; i<mov->total_streams; i++) {
1834
            MOVStreamContext *msc = mov->streams[i];
1835
            if ((msc->next_chunk < msc->chunk_count)
1836
                && msc->chunk_offsets[msc->next_chunk] - offset < size
1837
                && msc->chunk_offsets[msc->next_chunk] > offset)
1838
                size = msc->chunk_offsets[msc->next_chunk] - offset;
1839
        }
1840
        //Make sure that size is according to sample_size (Needed by .mov files
1841
        //created on a Minolta Dimage Xi where audio chunks contains waste data in the end)
1842
        //needed for 'raw '
1843
        //sample_size is already adjusted in read_stsz
1844
        adjusted= sc->sample_to_chunk[idx].count * sc->sample_size;
1845
        if (adjusted < size) {
1846
            dprintf("adjusted %d, size %d, sample count %ld\n", adjusted, size, sc->sample_to_chunk[idx].count);
1847
            size = adjusted;
1848
        }
1849
        if(idx < sc->sample_to_chunk_sz){
1850
            next_sample= sc->current_sample + sc->sample_to_chunk[idx].count;
1851
        }else
1852
            next_sample= sc->current_sample;
1853
    }
1854

    
1855
readchunk:
1856
    dprintf("chunk: %"PRId64" -> %"PRId64" (%i)\n", offset, offset + size, size);
1857
    if(size == 0x0FFFFFFF)
1858
        size = mov->mdat_size + mov->mdat_offset - offset;
1859
    if(size < 0)
1860
        return -1;
1861
    if(size == 0)
1862
        return -1;
1863
    url_fseek(&s->pb, offset, SEEK_SET);
1864

    
1865
    av_get_packet(&s->pb, pkt, size);
1866
    pkt->stream_index = sc->ffindex;
1867

    
1868
    // If the keyframes table exists, mark any samples that are in the table as key frames.
1869
    // If no table exists, treat very sample as a key frame.
1870
    if (sc->keyframes) {
1871
        a = 0;
1872
        b = sc->keyframe_count - 1;
1873

    
1874
        while (a < b) {
1875
            m = (a + b + 1) >> 1;
1876
            if (sc->keyframes[m] > sc->current_sample) {
1877
                b = m - 1;
1878
            } else {
1879
                a = m;
1880
            }
1881
        }
1882

    
1883
        if (sc->keyframes[a] == sc->current_sample)
1884
            pkt->flags |= PKT_FLAG_KEY;
1885
    }
1886
    else
1887
        pkt->flags |= PKT_FLAG_KEY;
1888

    
1889
    mov->next_chunk_offset = offset + size;
1890

    
1891
    /* find the corresponding dts */
1892
    if (sc && sc->sample_to_time_index < sc->stts_count && pkt) {
1893
      unsigned int count;
1894
      uint64_t dts, pts;
1895
      unsigned int duration = sc->stts_data[sc->sample_to_time_index].duration;
1896
      count = sc->stts_data[sc->sample_to_time_index].count;
1897
      if ((sc->sample_to_time_sample + count) <= sc->current_sample) {
1898
        sc->sample_to_time_sample += count;
1899
        sc->sample_to_time_time   += count*duration;
1900
        sc->sample_to_time_index ++;
1901
        duration = sc->stts_data[sc->sample_to_time_index].duration;
1902
      }
1903
      dts = sc->sample_to_time_time + (sc->current_sample - sc->sample_to_time_sample) * (int64_t)duration;
1904
        /* find the corresponding pts */
1905
        if (sc->sample_to_ctime_index < sc->ctts_count) {
1906
            int duration = sc->ctts_data[sc->sample_to_ctime_index].duration;
1907
            int count = sc->ctts_data[sc->sample_to_ctime_index].count;
1908

    
1909
            if ((sc->sample_to_ctime_sample + count) <= sc->current_sample) {
1910
                sc->sample_to_ctime_sample += count;
1911
                sc->sample_to_ctime_index ++;
1912
                duration = sc->ctts_data[sc->sample_to_ctime_index].duration;
1913
            }
1914
            pts = dts + duration;
1915
        }else
1916
            pts = dts;
1917

    
1918
        st= s->streams[ sc->ffindex ];
1919
        assert(pts % st->time_base.num == 0);
1920
        assert(dts % st->time_base.num == 0);
1921

    
1922
        pkt->pts = pts / st->time_base.num;
1923
        pkt->dts = dts / st->time_base.num;
1924
        dprintf("stream #%d smp #%ld dts = %"PRId64" pts = %"PRId64" (smp:%ld time:%"PRId64" idx:%d ent:%d count:%d dur:%d)\n"
1925
                , pkt->stream_index, sc->current_sample-1, pkt->dts, pkt->pts
1926
                , sc->sample_to_time_sample
1927
                , sc->sample_to_time_time
1928
                , sc->sample_to_time_index
1929
                , sc->stts_count
1930
                , count
1931
                , duration);
1932
    }
1933

    
1934
    assert(next_sample>=0);
1935
    sc->current_sample= next_sample;
1936

    
1937
    return 0;
1938
}
1939

    
1940
#if defined(MOV_SEEK)
1941
/**
1942
 * Seek method based on the one described in the Appendix C of QTFileFormat.pdf
1943
 */
1944
static int mov_read_seek(AVFormatContext *s, int stream_index, int64_t sample_time, int flags)
1945
{
1946
    MOVContext* mov = (MOVContext *) s->priv_data;
1947
    MOVStreamContext* sc;
1948
    int32_t i, a, b, m;
1949
    int64_t start_time;
1950
    int32_t seek_sample, sample;
1951
    int32_t duration;
1952
    int32_t count;
1953
    int32_t chunk;
1954
    int32_t left_in_chunk;
1955
    int64_t chunk_file_offset;
1956
    int64_t sample_file_offset;
1957
    int32_t first_chunk_sample;
1958
    int32_t sample_to_chunk_idx;
1959
    int sample_to_time_index;
1960
    long sample_to_time_sample = 0;
1961
    uint64_t sample_to_time_time = 0;
1962
    int mov_idx;
1963

    
1964
    // Find the corresponding mov stream
1965
    for (mov_idx = 0; mov_idx < mov->total_streams; mov_idx++)
1966
        if (mov->streams[mov_idx]->ffindex == stream_index)
1967
            break;
1968
    if (mov_idx == mov->total_streams) {
1969
        av_log(s, AV_LOG_ERROR, "mov: requested stream was not found in mov streams (idx=%i)\n", stream_index);
1970
        return -1;
1971
    }
1972
    sc = mov->streams[mov_idx];
1973

    
1974
    sample_time *= s->streams[stream_index]->time_base.num;
1975

    
1976
    // Step 1. Find the edit that contains the requested time (elst)
1977
    if (sc->edit_count && 0) {
1978
        // FIXME should handle edit list
1979
        av_log(s, AV_LOG_ERROR, "mov: does not handle seeking in files that contain edit list (c:%d)\n", sc->edit_count);
1980
        return -1;
1981
    }
1982

    
1983
    // Step 2. Find the corresponding sample using the Time-to-sample atom (stts) */
1984
    dprintf("Searching for time %li in stream #%i (time_scale=%i)\n", (long)sample_time, mov_idx, sc->time_scale);
1985
    start_time = 0; // FIXME use elst atom
1986
    sample = 1; // sample are 0 based in table
1987

    
1988
    for (i = 0; i < sc->stts_count; i++) {
1989
        count = sc->stts_data[i].count;
1990
        duration = sc->stts_data[i].duration;
1991
        if ((start_time + count*duration) > sample_time) {
1992
            sample_to_time_time = start_time;
1993
            sample_to_time_index = i;
1994
            sample_to_time_sample = sample;
1995
            sample += (sample_time - start_time) / duration;
1996
            break;
1997
        }
1998
        sample += count;
1999
        start_time += count * duration;
2000
    }
2001
    sample_to_time_time = start_time;
2002
    sample_to_time_index = i;
2003
    /* NOTE: despite what qt doc say, the dt value (Display Time in qt vocabulary) computed with the stts atom
2004
       is a decoding time stamp (dts) not a presentation time stamp. And as usual dts != pts for stream with b frames */
2005

    
2006
    dprintf("Found time %li at sample #%u\n", (long)sample_time, sample);
2007
    if (sample > sc->sample_count) {
2008
        av_log(s, AV_LOG_ERROR, "mov: sample pos is too high, unable to seek (req. sample=%i, sample count=%ld)\n", sample, sc->sample_count);
2009
        return -1;
2010
    }
2011

    
2012
    // Step 3. Find the prior sync. sample using the Sync sample atom (stss)
2013
    if (sc->keyframes) {
2014
        a = 0;
2015
        b = sc->keyframe_count - 1;
2016
        while (a < b) {
2017
            m = (a + b + 1) >> 1;
2018
            if (sc->keyframes[m] > sample) {
2019
                b = m - 1;
2020
            } else {
2021
                a = m;
2022
            }
2023
        }
2024
        // for low latency prob: always use the previous keyframe, just uncomment the next line
2025
        // if (a) a--;
2026
        seek_sample = sc->keyframes[a];
2027
    }
2028
    else
2029
        seek_sample = sample; // else all samples are key frames
2030
    dprintf("Found nearest keyframe at sample #%i \n", seek_sample);
2031

    
2032
    // Step 4. Find the chunk of the sample using the Sample-to-chunk-atom (stsc)
2033
    for (first_chunk_sample = 1, i = 0; i < (sc->sample_to_chunk_sz - 1); i++) {
2034
        b = (sc->sample_to_chunk[i + 1].first - sc->sample_to_chunk[i].first) * sc->sample_to_chunk[i].count;
2035
        if (seek_sample >= first_chunk_sample && seek_sample < (first_chunk_sample + b))
2036
            break;
2037
        first_chunk_sample += b;
2038
    }
2039
    chunk = sc->sample_to_chunk[i].first + (seek_sample - first_chunk_sample) / sc->sample_to_chunk[i].count;
2040
    left_in_chunk = sc->sample_to_chunk[i].count - (seek_sample - first_chunk_sample) % sc->sample_to_chunk[i].count;
2041
    first_chunk_sample += ((seek_sample - first_chunk_sample) / sc->sample_to_chunk[i].count) * sc->sample_to_chunk[i].count;
2042
    sample_to_chunk_idx = i;
2043
    dprintf("Sample was found in chunk #%i at sample offset %i (idx %i)\n", chunk, seek_sample - first_chunk_sample, sample_to_chunk_idx);
2044

    
2045
    // Step 5. Find the offset of the chunk using the chunk offset atom
2046
    if (!sc->chunk_offsets) {
2047
        av_log(s, AV_LOG_ERROR, "mov: no chunk offset atom, unable to seek\n");
2048
        return -1;
2049
    }
2050
    if (chunk > sc->chunk_count) {
2051
        av_log(s, AV_LOG_ERROR, "mov: chunk offset atom too short, unable to seek (req. chunk=%i, chunk count=%li)\n", chunk, sc->chunk_count);
2052
        return -1;
2053
    }
2054
    chunk_file_offset = sc->chunk_offsets[chunk - 1];
2055
    dprintf("Chunk file offset is #%"PRIu64"\n", chunk_file_offset);
2056

    
2057
    // Step 6. Find the byte offset within the chunk using the sample size atom
2058
    sample_file_offset = chunk_file_offset;
2059
    if (sc->sample_size)
2060
        sample_file_offset += (seek_sample - first_chunk_sample) * sc->sample_size;
2061
    else {
2062
        for (i = 0; i < (seek_sample - first_chunk_sample); i++) {
2063
        sample_file_offset += sc->sample_sizes[first_chunk_sample + i - 1];
2064
        }
2065
    }
2066
    dprintf("Sample file offset is #%"PRIu64"\n", sample_file_offset);
2067

    
2068
    // Step 6. Update the parser
2069
    mov->partial = sc;
2070
    mov->next_chunk_offset = sample_file_offset;
2071
    // Update current stream state
2072
    sc->current_sample = seek_sample - 1;  // zero based
2073
    sc->left_in_chunk = left_in_chunk;
2074
    sc->next_chunk = chunk; // +1 -1 (zero based)
2075
    sc->sample_to_chunk_index = sample_to_chunk_idx;
2076

    
2077
    // Update other streams
2078
    for (i = 0; i<mov->total_streams; i++) {
2079
        MOVStreamContext *msc;
2080
        if (i == mov_idx) continue;
2081
        // Find the nearest 'next' chunk
2082
        msc = mov->streams[i];
2083
        a = 0;
2084
        b = msc->chunk_count - 1;
2085
        while (a < b) {
2086
            m = (a + b + 1) >> 1;
2087
            if (msc->chunk_offsets[m] > chunk_file_offset) {
2088
                b = m - 1;
2089
            } else {
2090
                a = m;
2091
            }
2092
        }
2093
        msc->next_chunk = a;
2094
        if (msc->chunk_offsets[a] < chunk_file_offset && a < (msc->chunk_count-1))
2095
            msc->next_chunk ++;
2096
        dprintf("Nearest next chunk for stream #%i is #%li @%"PRId64"\n", i, msc->next_chunk+1, msc->chunk_offsets[msc->next_chunk]);
2097

    
2098
        // Compute sample count and index in the sample_to_chunk table (what a pity)
2099
        msc->sample_to_chunk_index = 0;
2100
        msc->current_sample = 0;
2101
        for(;  msc->sample_to_chunk_index < (msc->sample_to_chunk_sz - 1)
2102
            && msc->sample_to_chunk[msc->sample_to_chunk_index + 1].first <= (1 + msc->next_chunk); msc->sample_to_chunk_index++) {
2103
            msc->current_sample += (msc->sample_to_chunk[msc->sample_to_chunk_index + 1].first - msc->sample_to_chunk[msc->sample_to_chunk_index].first) \
2104
            * msc->sample_to_chunk[msc->sample_to_chunk_index].count;
2105
        }
2106
        msc->current_sample += (msc->next_chunk - (msc->sample_to_chunk[msc->sample_to_chunk_index].first - 1)) * sc->sample_to_chunk[msc->sample_to_chunk_index].count;
2107
        msc->left_in_chunk = msc->sample_to_chunk[msc->sample_to_chunk_index].count - 1;
2108
        // Find corresponding position in stts (used later to compute dts)
2109
        sample = 0;
2110
        start_time = 0;
2111
        for (msc->sample_to_time_index = 0; msc->sample_to_time_index < msc->stts_count; msc->sample_to_time_index++) {
2112
            count = msc->stts_data[msc->sample_to_time_index].count;
2113
            duration = msc->stts_data[msc->sample_to_time_index].duration;
2114
            if ((sample + count - 1) > msc->current_sample) {
2115
                msc->sample_to_time_time = start_time;
2116
                msc->sample_to_time_sample = sample;
2117
                break;
2118
            }
2119
            sample += count;
2120
            start_time += count * duration;
2121
        }
2122
        sample = 0;
2123
        for (msc->sample_to_ctime_index = 0; msc->sample_to_ctime_index < msc->ctts_count; msc->sample_to_ctime_index++) {
2124
            count = msc->ctts_data[msc->sample_to_ctime_index].count;
2125
            duration = msc->ctts_data[msc->sample_to_ctime_index].duration;
2126
            if ((sample + count - 1) > msc->current_sample) {
2127
                msc->sample_to_ctime_sample = sample;
2128
                break;
2129
            }
2130
            sample += count;
2131
        }
2132
        dprintf("Next Sample for stream #%i is #%li @%li\n", i, msc->current_sample + 1, msc->sample_to_chunk_index + 1);
2133
    }
2134
    return 0;
2135
}
2136
#endif
2137

    
2138
static int mov_read_close(AVFormatContext *s)
2139
{
2140
    int i;
2141
    MOVContext *mov = (MOVContext *) s->priv_data;
2142
    for(i=0; i<mov->total_streams; i++)
2143
        mov_free_stream_context(mov->streams[i]);
2144
    /* free color tabs */
2145
    for(i=0; i<mov->ctab_size; i++)
2146
        av_freep(&mov->ctab[i]);
2147
    av_freep(&mov->ctab);
2148
    return 0;
2149
}
2150

    
2151
static AVInputFormat mov_iformat = {
2152
    "mov,mp4,m4a,3gp,3g2,mj2",
2153
    "QuickTime/MPEG4/Motion JPEG 2000 format",
2154
    sizeof(MOVContext),
2155
    mov_probe,
2156
    mov_read_header,
2157
    mov_read_packet,
2158
    mov_read_close,
2159
#if defined(MOV_SEEK)
2160
    mov_read_seek,
2161
#endif
2162
};
2163

    
2164
int mov_init(void)
2165
{
2166
    av_register_input_format(&mov_iformat);
2167
    return 0;
2168
}