annotate mov.c @ 2660:022174d849d5 libavformat

fix issue 225, instead of stoping when wrong atom size is found, limit atom size to what is left, assuming container atom has correct size.. cricket4.3g2 has incorrect moov atom size which indicates that file size should be 2 bytes bigger than it is and quicktime reads it correctly though.
author bcoudurier
date Mon, 22 Oct 2007 14:36:14 +0000
parents 960795567b33
children 9645f395842d
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1 /*
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
2 * MOV demuxer
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
3 * Copyright (c) 2001 Fabrice Bellard.
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
4 *
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
5 * This file is part of FFmpeg.
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
6 *
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
7 * FFmpeg is free software; you can redistribute it and/or
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
8 * modify it under the terms of the GNU Lesser General Public
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
9 * License as published by the Free Software Foundation; either
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
10 * version 2.1 of the License, or (at your option) any later version.
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
11 *
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
12 * FFmpeg is distributed in the hope that it will be useful,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
15 * Lesser General Public License for more details.
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
16 *
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
17 * You should have received a copy of the GNU Lesser General Public
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
18 * License along with FFmpeg; if not, write to the Free Software
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
20 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
21
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
22 #include <limits.h>
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
23
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
24 //#define DEBUG
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
25
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
26 #include "avformat.h"
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
27 #include "riff.h"
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
28 #include "isom.h"
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
29 #include "dv.h"
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
30
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
31 #ifdef CONFIG_ZLIB
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
32 #include <zlib.h>
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
33 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
34
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
35 /*
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
36 * First version by Francois Revol revol@free.fr
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
37 * Seek function by Gael Chardon gael.dev@4now.net
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
38 *
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
39 * Features and limitations:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
40 * - reads most of the QT files I have (at least the structure),
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
41 * Sample QuickTime files with mp3 audio can be found at: http://www.3ivx.com/showcase.html
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
42 * - the code is quite ugly... maybe I won't do it recursive next time :-)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
43 *
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
44 * Funny I didn't know about http://sourceforge.net/projects/qt-ffmpeg/
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
45 * when coding this :) (it's a writer anyway)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
46 *
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
47 * Reference documents:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
48 * http://www.geocities.com/xhelmboyx/quicktime/formats/qtm-layout.txt
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
49 * Apple:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
50 * http://developer.apple.com/documentation/QuickTime/QTFF/
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
51 * http://developer.apple.com/documentation/QuickTime/QTFF/qtff.pdf
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
52 * QuickTime is a trademark of Apple (AFAIK :))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
53 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
54
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
55 #include "qtpalette.h"
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
56
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
57
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
58 #undef NDEBUG
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
59 #include <assert.h>
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
60
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
61 /* the QuickTime file format is quite convoluted...
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
62 * it has lots of index tables, each indexing something in another one...
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
63 * Here we just use what is needed to read the chunks
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
64 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
65
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
66 typedef struct {
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
67 int first;
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
68 int count;
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
69 int id;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
70 } MOV_stsc_t;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
71
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
72 typedef struct {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
73 uint32_t type;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
74 int64_t offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
75 int64_t size; /* total size (excluding the size and type fields) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
76 } MOV_atom_t;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
77
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
78 typedef struct {
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
79 offset_t offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
80 int64_t size;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
81 } MOV_mdat_t;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
82
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
83 struct MOVParseTableEntry;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
84
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
85 typedef struct MOVStreamContext {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
86 int ffindex; /* the ffmpeg stream id */
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
87 int next_chunk;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
88 unsigned int chunk_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
89 int64_t *chunk_offsets;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
90 unsigned int stts_count;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
91 MOV_stts_t *stts_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
92 unsigned int ctts_count;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
93 MOV_stts_t *ctts_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
94 unsigned int edit_count; /* number of 'edit' (elst atom) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
95 unsigned int sample_to_chunk_sz;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
96 MOV_stsc_t *sample_to_chunk;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
97 int sample_to_ctime_index;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
98 int sample_to_ctime_sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
99 unsigned int sample_size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
100 unsigned int sample_count;
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
101 int *sample_sizes;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
102 unsigned int keyframe_count;
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
103 int *keyframes;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
104 int time_scale;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
105 int time_rate;
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
106 int current_sample;
1940
1a7f66384792 cosmetics, sample_size_v1 -> bytes_per_frame / samples_per_frame
bcoudurier
parents: 1939
diff changeset
107 unsigned int bytes_per_frame;
1a7f66384792 cosmetics, sample_size_v1 -> bytes_per_frame / samples_per_frame
bcoudurier
parents: 1939
diff changeset
108 unsigned int samples_per_frame;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
109 int dv_audio_container;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
110 } MOVStreamContext;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
111
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
112 typedef struct MOVContext {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
113 AVFormatContext *fc;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
114 int time_scale;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
115 int64_t duration; /* duration of the longest track */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
116 int found_moov; /* when both 'moov' and 'mdat' sections has been found */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
117 int found_mdat; /* we suppose we have enough data to read the file */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
118 int64_t mdat_offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
119 int total_streams;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
120 MOVStreamContext *streams[MAX_STREAMS];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
121
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
122 const struct MOVParseTableEntry *parse_table; /* could be eventually used to change the table */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
123 /* NOTE: for recursion save to/ restore from local variable! */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
124
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
125 AVPaletteControl palette_control;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
126 MOV_mdat_t *mdat_list;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
127 int mdat_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
128 DVDemuxContext *dv_demux;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
129 AVFormatContext *dv_fctx;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
130 int isom; /* 1 if file is ISO Media (mp4/3gp) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
131 } MOVContext;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
132
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
133
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
134 /* XXX: it's the first time I make a recursive parser I think... sorry if it's ugly :P */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
135
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
136 /* those functions parse an atom */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
137 /* return code:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
138 1: found what I wanted, exit
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
139 0: continue to parse next atom
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
140 -1: error occured, exit
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
141 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
142 typedef int (*mov_parse_function)(MOVContext *ctx, ByteIOContext *pb, MOV_atom_t atom);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
143
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
144 /* links atom IDs to parse functions */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
145 typedef struct MOVParseTableEntry {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
146 uint32_t type;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
147 mov_parse_function func;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
148 } MOVParseTableEntry;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
149
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
150 static int mov_read_default(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
151 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
152 int64_t total_size = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
153 MOV_atom_t a;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
154 int i;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
155 int err = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
156
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
157 a.offset = atom.offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
158
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
159 if (atom.size < 0)
2026
2e2c2dbb511d use INT64_MAX
bcoudurier
parents: 2023
diff changeset
160 atom.size = INT64_MAX;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
161 while(((total_size + 8) < atom.size) && !url_feof(pb) && !err) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
162 a.size = atom.size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
163 a.type=0L;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
164 if(atom.size >= 8) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
165 a.size = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
166 a.type = get_le32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
167 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
168 total_size += 8;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
169 a.offset += 8;
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
170 dprintf(c->fc, "type: %08x %.4s sz: %"PRIx64" %"PRIx64" %"PRIx64"\n", a.type, (char*)&a.type, a.size, atom.size, total_size);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
171 if (a.size == 1) { /* 64 bit extended size */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
172 a.size = get_be64(pb) - 8;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
173 a.offset += 8;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
174 total_size += 8;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
175 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
176 if (a.size == 0) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
177 a.size = atom.size - total_size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
178 if (a.size <= 8)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
179 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
180 }
1964
4571a481081d move atom size check before parsing function search
bcoudurier
parents: 1963
diff changeset
181 a.size -= 8;
2660
022174d849d5 fix issue 225, instead of stoping when wrong atom size is found,
bcoudurier
parents: 2589
diff changeset
182 if(a.size < 0)
1964
4571a481081d move atom size check before parsing function search
bcoudurier
parents: 1963
diff changeset
183 break;
2660
022174d849d5 fix issue 225, instead of stoping when wrong atom size is found,
bcoudurier
parents: 2589
diff changeset
184 if (a.size > atom.size - total_size)
022174d849d5 fix issue 225, instead of stoping when wrong atom size is found,
bcoudurier
parents: 2589
diff changeset
185 a.size = atom.size - total_size;
1964
4571a481081d move atom size check before parsing function search
bcoudurier
parents: 1963
diff changeset
186
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
187 for (i = 0; c->parse_table[i].type != 0L
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
188 && c->parse_table[i].type != a.type; i++)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
189 /* empty */;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
190
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
191 if (c->parse_table[i].type == 0) { /* skip leaf atoms data */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
192 url_fskip(pb, a.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
193 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
194 offset_t start_pos = url_ftell(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
195 int64_t left;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
196 err = (c->parse_table[i].func)(c, pb, a);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
197 left = a.size - url_ftell(pb) + start_pos;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
198 if (left > 0) /* skip garbage at atom end */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
199 url_fskip(pb, left);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
200 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
201
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
202 a.offset += a.size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
203 total_size += a.size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
204 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
205
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
206 if (!err && total_size < atom.size && atom.size < 0x7ffff) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
207 url_fskip(pb, atom.size - total_size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
208 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
209
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
210 return err;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
211 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
212
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
213 static int mov_read_hdlr(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
214 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
215 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
216 uint32_t type;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
217 uint32_t ctype;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
218
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
219 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
220 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
221
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
222 /* component type */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
223 ctype = get_le32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
224 type = get_le32(pb); /* component subtype */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
225
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
226 dprintf(c->fc, "ctype= %c%c%c%c (0x%08x)\n", *((char *)&ctype), ((char *)&ctype)[1], ((char *)&ctype)[2], ((char *)&ctype)[3], (int) ctype);
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
227 dprintf(c->fc, "stype= %c%c%c%c\n", *((char *)&type), ((char *)&type)[1], ((char *)&type)[2], ((char *)&type)[3]);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
228 if(!ctype)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
229 c->isom = 1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
230 if(type == MKTAG('v', 'i', 'd', 'e'))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
231 st->codec->codec_type = CODEC_TYPE_VIDEO;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
232 else if(type == MKTAG('s', 'o', 'u', 'n'))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
233 st->codec->codec_type = CODEC_TYPE_AUDIO;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
234 else if(type == MKTAG('m', '1', 'a', ' '))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
235 st->codec->codec_id = CODEC_ID_MP2;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
236 else if(type == MKTAG('s', 'u', 'b', 'p')) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
237 st->codec->codec_type = CODEC_TYPE_SUBTITLE;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
238 st->codec->codec_id = CODEC_ID_DVD_SUBTITLE;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
239 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
240 get_be32(pb); /* component manufacture */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
241 get_be32(pb); /* component flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
242 get_be32(pb); /* component flags mask */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
243
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
244 if(atom.size <= 24)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
245 return 0; /* nothing left to read */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
246
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
247 url_fskip(pb, atom.size - (url_ftell(pb) - atom.offset));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
248 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
249 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
250
2029
df8331c95632 cosmetics: mov_mp4 -> mp4
bcoudurier
parents: 2028
diff changeset
251 static int mp4_read_descr_len(ByteIOContext *pb)
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
252 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
253 int len = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
254 int count = 4;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
255 while (count--) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
256 int c = get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
257 len = (len << 7) | (c & 0x7f);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
258 if (!(c & 0x80))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
259 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
260 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
261 return len;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
262 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
263
2029
df8331c95632 cosmetics: mov_mp4 -> mp4
bcoudurier
parents: 2028
diff changeset
264 static int mp4_read_descr(MOVContext *c, ByteIOContext *pb, int *tag)
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
265 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
266 int len;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
267 *tag = get_byte(pb);
2029
df8331c95632 cosmetics: mov_mp4 -> mp4
bcoudurier
parents: 2028
diff changeset
268 len = mp4_read_descr_len(pb);
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
269 dprintf(c->fc, "MPEG4 description: tag=0x%02x len=%d\n", *tag, len);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
270 return len;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
271 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
272
2028
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
273 #define MP4ESDescrTag 0x03
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
274 #define MP4DecConfigDescrTag 0x04
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
275 #define MP4DecSpecificDescrTag 0x05
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
276
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
277 static int mov_read_esds(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
278 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
279 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
280 int tag, len;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
281
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
282 get_be32(pb); /* version + flags */
2029
df8331c95632 cosmetics: mov_mp4 -> mp4
bcoudurier
parents: 2028
diff changeset
283 len = mp4_read_descr(c, pb, &tag);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
284 if (tag == MP4ESDescrTag) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
285 get_be16(pb); /* ID */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
286 get_byte(pb); /* priority */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
287 } else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
288 get_be16(pb); /* ID */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
289
2029
df8331c95632 cosmetics: mov_mp4 -> mp4
bcoudurier
parents: 2028
diff changeset
290 len = mp4_read_descr(c, pb, &tag);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
291 if (tag == MP4DecConfigDescrTag) {
2028
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
292 int object_type_id = get_byte(pb);
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
293 get_byte(pb); /* stream type */
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
294 get_be24(pb); /* buffer size db */
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
295 get_be32(pb); /* max bitrate */
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
296 get_be32(pb); /* avg bitrate */
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
297
2028
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
298 st->codec->codec_id= codec_get_id(ff_mp4_obj_type, object_type_id);
319147157f29 clean and simplify esds reading function
bcoudurier
parents: 2027
diff changeset
299 dprintf(c->fc, "esds object type id %d\n", object_type_id);
2029
df8331c95632 cosmetics: mov_mp4 -> mp4
bcoudurier
parents: 2028
diff changeset
300 len = mp4_read_descr(c, pb, &tag);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
301 if (tag == MP4DecSpecificDescrTag) {
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
302 dprintf(c->fc, "Specific MPEG4 header len=%d\n", len);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
303 st->codec->extradata = av_mallocz(len + FF_INPUT_BUFFER_PADDING_SIZE);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
304 if (st->codec->extradata) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
305 get_buffer(pb, st->codec->extradata, len);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
306 st->codec->extradata_size = len;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
307 /* from mplayer */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
308 if ((*st->codec->extradata >> 3) == 29) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
309 st->codec->codec_id = CODEC_ID_MP3ON4;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
310 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
311 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
312 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
313 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
314 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
315 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
316
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
317 /* this atom contains actual media data */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
318 static int mov_read_mdat(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
319 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
320 if(atom.size == 0) /* wrong one (MP4) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
321 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
322 c->mdat_list = av_realloc(c->mdat_list, (c->mdat_count + 1) * sizeof(*c->mdat_list));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
323 c->mdat_list[c->mdat_count].offset = atom.offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
324 c->mdat_list[c->mdat_count].size = atom.size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
325 c->mdat_count++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
326 c->found_mdat=1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
327 c->mdat_offset = atom.offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
328 if(c->found_moov)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
329 return 1; /* found both, just go */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
330 url_fskip(pb, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
331 return 0; /* now go for moov */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
332 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
333
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
334 static int mov_read_ftyp(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
335 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
336 uint32_t type = get_le32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
337
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
338 if (type != MKTAG('q','t',' ',' '))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
339 c->isom = 1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
340 av_log(c->fc, AV_LOG_DEBUG, "ISO: File Type Major Brand: %.4s\n",(char *)&type);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
341 get_be32(pb); /* minor version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
342 url_fskip(pb, atom.size - 8);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
343 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
344 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
345
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
346 /* this atom should contain all header atoms */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
347 static int mov_read_moov(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
348 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
349 int err;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
350
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
351 err = mov_read_default(c, pb, atom);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
352 /* we parsed the 'moov' atom, we can terminate the parsing as soon as we find the 'mdat' */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
353 /* so we don't parse the whole file if over a network */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
354 c->found_moov=1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
355 if(c->found_mdat)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
356 return 1; /* found both, just go */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
357 return 0; /* now go for mdat */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
358 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
359
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
360
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
361 static int mov_read_mdhd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
362 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
363 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
364 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
365 int version = get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
366 int lang;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
367
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
368 if (version > 1)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
369 return 1; /* unsupported */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
370
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
371 get_byte(pb); get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
372 get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
373
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
374 if (version == 1) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
375 get_be64(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
376 get_be64(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
377 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
378 get_be32(pb); /* creation time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
379 get_be32(pb); /* modification time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
380 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
381
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
382 sc->time_scale = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
383 st->duration = (version == 1) ? get_be64(pb) : get_be32(pb); /* duration */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
384
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
385 lang = get_be16(pb); /* language */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
386 ff_mov_lang_to_iso639(lang, st->language);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
387 get_be16(pb); /* quality */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
388
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
389 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
390 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
391
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
392 static int mov_read_mvhd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
393 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
394 int version = get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
395 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
396
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
397 if (version == 1) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
398 get_be64(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
399 get_be64(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
400 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
401 get_be32(pb); /* creation time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
402 get_be32(pb); /* modification time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
403 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
404 c->time_scale = get_be32(pb); /* time scale */
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
405
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
406 dprintf(c->fc, "time scale = %i\n", c->time_scale);
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
407
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
408 c->duration = (version == 1) ? get_be64(pb) : get_be32(pb); /* duration */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
409 get_be32(pb); /* preferred scale */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
410
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
411 get_be16(pb); /* preferred volume */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
412
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
413 url_fskip(pb, 10); /* reserved */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
414
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
415 url_fskip(pb, 36); /* display matrix */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
416
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
417 get_be32(pb); /* preview time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
418 get_be32(pb); /* preview duration */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
419 get_be32(pb); /* poster time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
420 get_be32(pb); /* selection time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
421 get_be32(pb); /* selection duration */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
422 get_be32(pb); /* current time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
423 get_be32(pb); /* next track ID */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
424
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
425 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
426 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
427
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
428 static int mov_read_smi(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
429 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
430 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
431
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
432 if((uint64_t)atom.size > (1<<30))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
433 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
434
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
435 // currently SVQ3 decoder expect full STSD header - so let's fake it
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
436 // this should be fixed and just SMI header should be passed
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
437 av_free(st->codec->extradata);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
438 st->codec->extradata_size = 0x5a + atom.size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
439 st->codec->extradata = av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
440
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
441 if (st->codec->extradata) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
442 memcpy(st->codec->extradata, "SVQ3", 4); // fake
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
443 get_buffer(pb, st->codec->extradata + 0x5a, atom.size);
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
444 dprintf(c->fc, "Reading SMI %"PRId64" %s\n", atom.size, st->codec->extradata + 0x5a);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
445 } else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
446 url_fskip(pb, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
447
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
448 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
449 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
450
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
451 static int mov_read_enda(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
452 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
453 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
454 int little_endian = get_be16(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
455
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
456 if (little_endian) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
457 switch (st->codec->codec_id) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
458 case CODEC_ID_PCM_S24BE:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
459 st->codec->codec_id = CODEC_ID_PCM_S24LE;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
460 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
461 case CODEC_ID_PCM_S32BE:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
462 st->codec->codec_id = CODEC_ID_PCM_S32LE;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
463 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
464 default:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
465 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
466 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
467 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
468 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
469 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
470
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
471 /* FIXME modify qdm2/svq3/h264 decoders to take full atom as extradata */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
472 static int mov_read_extradata(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
473 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
474 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2589
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
475 uint64_t size= (uint64_t)st->codec->extradata_size + atom.size + 8 + FF_INPUT_BUFFER_PADDING_SIZE;
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
476 uint8_t *buf;
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
477 if(size > INT_MAX || (uint64_t)atom.size > INT_MAX)
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
478 return -1;
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
479 buf= av_realloc(st->codec->extradata, size);
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
480 if(!buf)
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
481 return -1;
2589
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
482 st->codec->extradata= buf;
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
483 buf+= st->codec->extradata_size;
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
484 st->codec->extradata_size= size - FF_INPUT_BUFFER_PADDING_SIZE;
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
485 AV_WB32( buf , atom.size + 8);
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
486 AV_WL32( buf + 4, atom.type);
960795567b33 append extradata atoms when parsing, fix OLOCOONS_O3.mov
bcoudurier
parents: 2547
diff changeset
487 get_buffer(pb, buf + 8, atom.size);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
488 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
489 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
490
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
491 static int mov_read_wave(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
492 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
493 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
494
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
495 if((uint64_t)atom.size > (1<<30))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
496 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
497
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
498 if (st->codec->codec_id == CODEC_ID_QDM2) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
499 // pass all frma atom to codec, needed at least for QDM2
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
500 av_free(st->codec->extradata);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
501 st->codec->extradata_size = atom.size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
502 st->codec->extradata = av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
503
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
504 if (st->codec->extradata) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
505 get_buffer(pb, st->codec->extradata, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
506 } else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
507 url_fskip(pb, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
508 } else if (atom.size > 8) { /* to read frma, esds atoms */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
509 mov_read_default(c, pb, atom);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
510 } else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
511 url_fskip(pb, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
512 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
513 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
514
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
515 static int mov_read_avcC(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
516 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
517 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
518
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
519 if((uint64_t)atom.size > (1<<30))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
520 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
521
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
522 av_free(st->codec->extradata);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
523
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
524 st->codec->extradata_size = atom.size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
525 st->codec->extradata = av_mallocz(st->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
526
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
527 if (st->codec->extradata) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
528 get_buffer(pb, st->codec->extradata, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
529 } else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
530 url_fskip(pb, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
531
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
532 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
533 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
534
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
535 static int mov_read_stco(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
536 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
537 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
538 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
539 unsigned int i, entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
540
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
541 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
542 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
543
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
544 entries = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
545
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
546 if(entries >= UINT_MAX/sizeof(int64_t))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
547 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
548
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
549 sc->chunk_count = entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
550 sc->chunk_offsets = av_malloc(entries * sizeof(int64_t));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
551 if (!sc->chunk_offsets)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
552 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
553 if (atom.type == MKTAG('s', 't', 'c', 'o')) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
554 for(i=0; i<entries; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
555 sc->chunk_offsets[i] = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
556 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
557 } else if (atom.type == MKTAG('c', 'o', '6', '4')) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
558 for(i=0; i<entries; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
559 sc->chunk_offsets[i] = get_be64(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
560 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
561 } else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
562 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
563
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
564 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
565 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
566
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
567 static int mov_read_stsd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
568 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
569 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
570 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
571 int entries, frames_per_sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
572 uint32_t format;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
573 uint8_t codec_name[32];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
574
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
575 /* for palette traversal */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
576 int color_depth;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
577 int color_start;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
578 int color_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
579 int color_end;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
580 int color_index;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
581 int color_dec;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
582 int color_greyscale;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
583 unsigned char *color_table;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
584 int j;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
585 unsigned char r, g, b;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
586
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
587 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
588 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
589
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
590 entries = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
591
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
592 while(entries--) { //Parsing Sample description table
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
593 enum CodecID id;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
594 MOV_atom_t a = { 0, 0, 0 };
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
595 offset_t start_pos = url_ftell(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
596 int size = get_be32(pb); /* size */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
597 format = get_le32(pb); /* data format */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
598
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
599 get_be32(pb); /* reserved */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
600 get_be16(pb); /* reserved */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
601 get_be16(pb); /* index */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
602
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
603 if (st->codec->codec_tag) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
604 /* multiple fourcc, just skip for now */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
605 url_fskip(pb, size - (url_ftell(pb) - start_pos));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
606 continue;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
607 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
608
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
609 st->codec->codec_tag = format;
1847
922180a45610 recommit of the change below after reverting earlier cosmetic-functional mix
michael
parents: 1846
diff changeset
610 id = codec_get_id(codec_movaudio_tags, format);
2298
4f946c9ae9b3 detect MS wav codecs
michael
parents: 2296
diff changeset
611 if (id<=0 && (format&0xFFFF) == 'm' + ('s'<<8))
4f946c9ae9b3 detect MS wav codecs
michael
parents: 2296
diff changeset
612 id = codec_get_id(codec_wav_tags, bswap_32(format)&0xFFFF);
4f946c9ae9b3 detect MS wav codecs
michael
parents: 2296
diff changeset
613
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
614 if (st->codec->codec_type != CODEC_TYPE_VIDEO && id > 0) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
615 st->codec->codec_type = CODEC_TYPE_AUDIO;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
616 } else if (st->codec->codec_type != CODEC_TYPE_AUDIO && /* do not overwrite codec type */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
617 format && format != MKTAG('m', 'p', '4', 's')) { /* skip old asf mpeg4 tag */
1847
922180a45610 recommit of the change below after reverting earlier cosmetic-functional mix
michael
parents: 1846
diff changeset
618 id = codec_get_id(codec_movvideo_tags, format);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
619 if (id <= 0)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
620 id = codec_get_id(codec_bmp_tags, format);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
621 if (id > 0)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
622 st->codec->codec_type = CODEC_TYPE_VIDEO;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
623 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
624
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
625 dprintf(c->fc, "size=%d 4CC= %c%c%c%c codec_type=%d\n",
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
626 size,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
627 (format >> 0) & 0xff, (format >> 8) & 0xff, (format >> 16) & 0xff, (format >> 24) & 0xff,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
628 st->codec->codec_type);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
629
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
630 if(st->codec->codec_type==CODEC_TYPE_VIDEO) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
631 st->codec->codec_id = id;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
632 get_be16(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
633 get_be16(pb); /* revision level */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
634 get_be32(pb); /* vendor */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
635 get_be32(pb); /* temporal quality */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
636 get_be32(pb); /* spacial quality */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
637
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
638 st->codec->width = get_be16(pb); /* width */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
639 st->codec->height = get_be16(pb); /* height */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
640
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
641 get_be32(pb); /* horiz resolution */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
642 get_be32(pb); /* vert resolution */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
643 get_be32(pb); /* data size, always 0 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
644 frames_per_sample = get_be16(pb); /* frames per samples */
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
645
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
646 dprintf(c->fc, "frames/samples = %d\n", frames_per_sample);
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
647
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
648 get_buffer(pb, codec_name, 32); /* codec name, pascal string (FIXME: true for mp4?) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
649 if (codec_name[0] <= 31) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
650 memcpy(st->codec->codec_name, &codec_name[1],codec_name[0]);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
651 st->codec->codec_name[codec_name[0]] = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
652 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
653
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
654 st->codec->bits_per_sample = get_be16(pb); /* depth */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
655 st->codec->color_table_id = get_be16(pb); /* colortable id */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
656
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
657 /* figure out the palette situation */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
658 color_depth = st->codec->bits_per_sample & 0x1F;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
659 color_greyscale = st->codec->bits_per_sample & 0x20;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
660
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
661 /* if the depth is 2, 4, or 8 bpp, file is palettized */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
662 if ((color_depth == 2) || (color_depth == 4) ||
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
663 (color_depth == 8)) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
664
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
665 if (color_greyscale) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
666
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
667 /* compute the greyscale palette */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
668 color_count = 1 << color_depth;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
669 color_index = 255;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
670 color_dec = 256 / (color_count - 1);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
671 for (j = 0; j < color_count; j++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
672 r = g = b = color_index;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
673 c->palette_control.palette[j] =
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
674 (r << 16) | (g << 8) | (b);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
675 color_index -= color_dec;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
676 if (color_index < 0)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
677 color_index = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
678 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
679
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
680 } else if (st->codec->color_table_id & 0x08) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
681
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
682 /* if flag bit 3 is set, use the default palette */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
683 color_count = 1 << color_depth;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
684 if (color_depth == 2)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
685 color_table = ff_qt_default_palette_4;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
686 else if (color_depth == 4)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
687 color_table = ff_qt_default_palette_16;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
688 else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
689 color_table = ff_qt_default_palette_256;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
690
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
691 for (j = 0; j < color_count; j++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
692 r = color_table[j * 4 + 0];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
693 g = color_table[j * 4 + 1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
694 b = color_table[j * 4 + 2];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
695 c->palette_control.palette[j] =
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
696 (r << 16) | (g << 8) | (b);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
697 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
698
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
699 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
700
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
701 /* load the palette from the file */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
702 color_start = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
703 color_count = get_be16(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
704 color_end = get_be16(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
705 for (j = color_start; j <= color_end; j++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
706 /* each R, G, or B component is 16 bits;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
707 * only use the top 8 bits; skip alpha bytes
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
708 * up front */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
709 get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
710 get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
711 r = get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
712 get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
713 g = get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
714 get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
715 b = get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
716 get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
717 c->palette_control.palette[j] =
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
718 (r << 16) | (g << 8) | (b);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
719 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
720 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
721
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
722 st->codec->palctrl = &c->palette_control;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
723 st->codec->palctrl->palette_changed = 1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
724 } else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
725 st->codec->palctrl = NULL;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
726 } else if(st->codec->codec_type==CODEC_TYPE_AUDIO) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
727 int bits_per_sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
728 uint16_t version = get_be16(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
729
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
730 st->codec->codec_id = id;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
731 get_be16(pb); /* revision level */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
732 get_be32(pb); /* vendor */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
733
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
734 st->codec->channels = get_be16(pb); /* channel count */
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
735 dprintf(c->fc, "audio channels %d\n", st->codec->channels);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
736 st->codec->bits_per_sample = get_be16(pb); /* sample size */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
737 /* do we need to force to 16 for AMR ? */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
738
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
739 /* handle specific s8 codec */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
740 get_be16(pb); /* compression id = 0*/
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
741 get_be16(pb); /* packet size = 0 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
742
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
743 st->codec->sample_rate = ((get_be32(pb) >> 16));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
744
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
745 switch (st->codec->codec_id) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
746 case CODEC_ID_PCM_S8:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
747 case CODEC_ID_PCM_U8:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
748 if (st->codec->bits_per_sample == 16)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
749 st->codec->codec_id = CODEC_ID_PCM_S16BE;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
750 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
751 case CODEC_ID_PCM_S16LE:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
752 case CODEC_ID_PCM_S16BE:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
753 if (st->codec->bits_per_sample == 8)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
754 st->codec->codec_id = CODEC_ID_PCM_S8;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
755 else if (st->codec->bits_per_sample == 24)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
756 st->codec->codec_id = CODEC_ID_PCM_S24BE;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
757 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
758 default:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
759 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
760 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
761
2164
3804e39efbfd misc spelling fixes
diego
parents: 2084
diff changeset
762 //Read QT version 1 fields. In version 0 these do not exist.
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
763 dprintf(c->fc, "version =%d, isom =%d\n",version,c->isom);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
764 if(!c->isom) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
765 if(version==1) {
1940
1a7f66384792 cosmetics, sample_size_v1 -> bytes_per_frame / samples_per_frame
bcoudurier
parents: 1939
diff changeset
766 sc->samples_per_frame = get_be32(pb);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
767 get_be32(pb); /* bytes per packet */
1940
1a7f66384792 cosmetics, sample_size_v1 -> bytes_per_frame / samples_per_frame
bcoudurier
parents: 1939
diff changeset
768 sc->bytes_per_frame = get_be32(pb);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
769 get_be32(pb); /* bytes per sample */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
770 } else if(version==2) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
771 get_be32(pb); /* sizeof struct only */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
772 st->codec->sample_rate = av_int2dbl(get_be64(pb)); /* float 64 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
773 st->codec->channels = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
774 get_be32(pb); /* always 0x7F000000 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
775 get_be32(pb); /* bits per channel if sound is uncompressed */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
776 get_be32(pb); /* lcpm format specific flag */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
777 get_be32(pb); /* bytes per audio packet if constant */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
778 get_be32(pb); /* lpcm frames per audio packet if constant */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
779 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
780 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
781
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
782 bits_per_sample = av_get_bits_per_sample(st->codec->codec_id);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
783 if (bits_per_sample) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
784 st->codec->bits_per_sample = bits_per_sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
785 sc->sample_size = (bits_per_sample >> 3) * st->codec->channels;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
786 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
787 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
788 /* other codec type, just skip (rtp, mp4s, tmcd ...) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
789 url_fskip(pb, size - (url_ftell(pb) - start_pos));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
790 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
791 /* this will read extra atoms at the end (wave, alac, damr, avcC, SMI ...) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
792 a.size = size - (url_ftell(pb) - start_pos);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
793 if (a.size > 8)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
794 mov_read_default(c, pb, a);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
795 else if (a.size > 0)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
796 url_fskip(pb, a.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
797 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
798
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
799 if(st->codec->codec_type==CODEC_TYPE_AUDIO && st->codec->sample_rate==0 && sc->time_scale>1) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
800 st->codec->sample_rate= sc->time_scale;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
801 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
802
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
803 /* special codec parameters handling */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
804 switch (st->codec->codec_id) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
805 #ifdef CONFIG_H261_DECODER
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
806 case CODEC_ID_H261:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
807 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
808 #ifdef CONFIG_H263_DECODER
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
809 case CODEC_ID_H263:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
810 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
811 #ifdef CONFIG_MPEG4_DECODER
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
812 case CODEC_ID_MPEG4:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
813 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
814 st->codec->width= 0; /* let decoder init width/height */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
815 st->codec->height= 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
816 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
817 #ifdef CONFIG_LIBFAAD
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
818 case CODEC_ID_AAC:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
819 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
820 #ifdef CONFIG_VORBIS_DECODER
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
821 case CODEC_ID_VORBIS:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
822 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
823 case CODEC_ID_MP3ON4:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
824 st->codec->sample_rate= 0; /* let decoder init parameters properly */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
825 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
826 #ifdef CONFIG_DV_DEMUXER
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
827 case CODEC_ID_DVAUDIO:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
828 c->dv_fctx = av_alloc_format_context();
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
829 c->dv_demux = dv_init_demux(c->dv_fctx);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
830 if (!c->dv_demux) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
831 av_log(c->fc, AV_LOG_ERROR, "dv demux context init error\n");
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
832 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
833 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
834 sc->dv_audio_container = 1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
835 st->codec->codec_id = CODEC_ID_PCM_S16LE;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
836 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
837 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
838 /* no ifdef since parameters are always those */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
839 case CODEC_ID_AMR_WB:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
840 st->codec->sample_rate= 16000;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
841 st->codec->channels= 1; /* really needed */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
842 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
843 case CODEC_ID_AMR_NB:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
844 st->codec->sample_rate= 8000;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
845 st->codec->channels= 1; /* really needed */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
846 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
847 case CODEC_ID_MP2:
1953
edfd6b33d1f6 activate parser on MP3 id, fix [A-Destiny]_Konjiki_no_Gash_Bell_-_65_[71EE362C].mp4
bcoudurier
parents: 1950
diff changeset
848 case CODEC_ID_MP3:
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
849 st->codec->codec_type = CODEC_TYPE_AUDIO; /* force type after stsd for m1a hdlr */
2023
a3e79d6e4e3c add an enum for need_parsing
aurel
parents: 2006
diff changeset
850 st->need_parsing = AVSTREAM_PARSE_FULL;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
851 break;
2299
fe59c768ecf7 set block align to stsd audio v2 bytes per frame for adpcm ms and ima wav, fix surge-2-16-L-ms11.mov and surge-2-16-L-ms02.mov
bcoudurier
parents: 2298
diff changeset
852 case CODEC_ID_ADPCM_MS:
fe59c768ecf7 set block align to stsd audio v2 bytes per frame for adpcm ms and ima wav, fix surge-2-16-L-ms11.mov and surge-2-16-L-ms02.mov
bcoudurier
parents: 2298
diff changeset
853 case CODEC_ID_ADPCM_IMA_WAV:
fe59c768ecf7 set block align to stsd audio v2 bytes per frame for adpcm ms and ima wav, fix surge-2-16-L-ms11.mov and surge-2-16-L-ms02.mov
bcoudurier
parents: 2298
diff changeset
854 st->codec->block_align = sc->bytes_per_frame;
fe59c768ecf7 set block align to stsd audio v2 bytes per frame for adpcm ms and ima wav, fix surge-2-16-L-ms11.mov and surge-2-16-L-ms02.mov
bcoudurier
parents: 2298
diff changeset
855 break;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
856 default:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
857 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
858 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
859
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
860 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
861 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
862
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
863 static int mov_read_stsc(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
864 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
865 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
866 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
867 unsigned int i, entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
868
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
869 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
870 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
871
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
872 entries = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
873
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
874 if(entries >= UINT_MAX / sizeof(MOV_stsc_t))
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
875 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
876
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
877 dprintf(c->fc, "track[%i].stsc.entries = %i\n", c->fc->nb_streams-1, entries);
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
878
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
879 sc->sample_to_chunk_sz = entries;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
880 sc->sample_to_chunk = av_malloc(entries * sizeof(MOV_stsc_t));
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
881 if (!sc->sample_to_chunk)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
882 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
883 for(i=0; i<entries; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
884 sc->sample_to_chunk[i].first = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
885 sc->sample_to_chunk[i].count = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
886 sc->sample_to_chunk[i].id = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
887 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
888 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
889 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
890
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
891 static int mov_read_stss(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
892 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
893 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
894 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
895 unsigned int i, entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
896
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
897 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
898 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
899
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
900 entries = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
901
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
902 if(entries >= UINT_MAX / sizeof(int))
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
903 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
904
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
905 sc->keyframe_count = entries;
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
906
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
907 dprintf(c->fc, "keyframe_count = %d\n", sc->keyframe_count);
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
908
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
909 sc->keyframes = av_malloc(entries * sizeof(int));
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
910 if (!sc->keyframes)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
911 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
912 for(i=0; i<entries; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
913 sc->keyframes[i] = get_be32(pb);
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
914 //dprintf(c->fc, "keyframes[]=%d\n", sc->keyframes[i]);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
915 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
916 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
917 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
918
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
919 static int mov_read_stsz(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
920 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
921 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
922 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
923 unsigned int i, entries, sample_size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
924
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
925 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
926 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
927
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
928 sample_size = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
929 if (!sc->sample_size) /* do not overwrite value computed in stsd */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
930 sc->sample_size = sample_size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
931 entries = get_be32(pb);
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
932 if(entries >= UINT_MAX / sizeof(int))
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
933 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
934
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
935 sc->sample_count = entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
936 if (sample_size)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
937 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
938
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
939 dprintf(c->fc, "sample_size = %d sample_count = %d\n", sc->sample_size, sc->sample_count);
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
940
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
941 sc->sample_sizes = av_malloc(entries * sizeof(int));
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
942 if (!sc->sample_sizes)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
943 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
944 for(i=0; i<entries; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
945 sc->sample_sizes[i] = get_be32(pb);
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
946 dprintf(c->fc, "sample_sizes[]=%d\n", sc->sample_sizes[i]);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
947 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
948 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
949 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
950
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
951 static int mov_read_stts(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
952 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
953 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
954 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
955 unsigned int i, entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
956 int64_t duration=0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
957 int64_t total_sample_count=0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
958
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
959 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
960 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
961 entries = get_be32(pb);
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
962 if(entries >= UINT_MAX / sizeof(MOV_stts_t))
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
963 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
964
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
965 sc->stts_count = entries;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
966 sc->stts_data = av_malloc(entries * sizeof(MOV_stts_t));
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
967
2044
fee0acdb8156 use dprintf with AVFormatContext and simplify
bcoudurier
parents: 2042
diff changeset
968 dprintf(c->fc, "track[%i].stts.entries = %i\n", c->fc->nb_streams-1, entries);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
969
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
970 sc->time_rate=0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
971
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
972 for(i=0; i<entries; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
973 int sample_duration;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
974 int sample_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
975
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
976 sample_count=get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
977 sample_duration = get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
978 sc->stts_data[i].count= sample_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
979 sc->stts_data[i].duration= sample_duration;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
980
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
981 sc->time_rate= ff_gcd(sc->time_rate, sample_duration);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
982
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
983 dprintf(c->fc, "sample_count=%d, sample_duration=%d\n",sample_count,sample_duration);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
984
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
985 duration+=(int64_t)sample_duration*sample_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
986 total_sample_count+=sample_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
987 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
988
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
989 st->nb_frames= total_sample_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
990 if(duration)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
991 st->duration= duration;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
992 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
993 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
994
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
995 static int mov_read_ctts(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
996 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
997 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
998 MOVStreamContext *sc = st->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
999 unsigned int i, entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1000
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1001 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1002 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1003 entries = get_be32(pb);
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
1004 if(entries >= UINT_MAX / sizeof(MOV_stts_t))
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1005 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1006
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1007 sc->ctts_count = entries;
2045
aa5e56700fdf cosmectics, use consistant and homogeneous type names for atoms
bcoudurier
parents: 2044
diff changeset
1008 sc->ctts_data = av_malloc(entries * sizeof(MOV_stts_t));
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1009
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1010 dprintf(c->fc, "track[%i].ctts.entries = %i\n", c->fc->nb_streams-1, entries);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1011
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1012 for(i=0; i<entries; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1013 int count =get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1014 int duration =get_be32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1015
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1016 if (duration < 0) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1017 av_log(c->fc, AV_LOG_ERROR, "negative ctts, ignoring\n");
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1018 sc->ctts_count = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1019 url_fskip(pb, 8 * (entries - i - 1));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1020 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1021 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1022 sc->ctts_data[i].count = count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1023 sc->ctts_data[i].duration= duration;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1024
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1025 sc->time_rate= ff_gcd(sc->time_rate, duration);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1026 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1027 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1028 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1029
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1030 static int mov_read_trak(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1031 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1032 AVStream *st;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1033 MOVStreamContext *sc;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1034
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1035 st = av_new_stream(c->fc, c->fc->nb_streams);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1036 if (!st) return -2;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1037 sc = av_mallocz(sizeof(MOVStreamContext));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1038 if (!sc) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1039 av_free(st);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1040 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1041 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1042
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1043 st->priv_data = sc;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1044 st->codec->codec_type = CODEC_TYPE_DATA;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1045 st->start_time = 0; /* XXX: check */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1046 c->streams[c->fc->nb_streams-1] = sc;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1047
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1048 return mov_read_default(c, pb, atom);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1049 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1050
2296
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1051 static void mov_parse_udta_string(ByteIOContext *pb, char *str, int size)
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1052 {
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1053 uint16_t str_size = get_be16(pb); /* string length */;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1054
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1055 get_be16(pb); /* skip language */
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1056 get_buffer(pb, str, FFMIN(size, str_size));
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1057 }
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1058
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1059 static int mov_read_udta(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1060 {
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1061 uint64_t end = url_ftell(pb) + atom.size;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1062
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1063 while (url_ftell(pb) + 8 < end) {
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1064 uint32_t tag_size = get_be32(pb);
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1065 uint32_t tag = get_le32(pb);
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1066 uint64_t next = url_ftell(pb) + tag_size - 8;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1067
2547
92bf4673d050 stop parsing udta if size is wrong/garbage, fix issue 154, fix RQ004F14.MOV
bcoudurier
parents: 2299
diff changeset
1068 if (next > end) // stop if tag_size is wrong
92bf4673d050 stop parsing udta if size is wrong/garbage, fix issue 154, fix RQ004F14.MOV
bcoudurier
parents: 2299
diff changeset
1069 break;
92bf4673d050 stop parsing udta if size is wrong/garbage, fix issue 154, fix RQ004F14.MOV
bcoudurier
parents: 2299
diff changeset
1070
2296
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1071 switch (tag) {
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1072 case MKTAG(0xa9,'n','a','m'):
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1073 mov_parse_udta_string(pb, c->fc->title, sizeof(c->fc->title));
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1074 break;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1075 case MKTAG(0xa9,'w','r','t'):
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1076 mov_parse_udta_string(pb, c->fc->author, sizeof(c->fc->author));
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1077 break;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1078 case MKTAG(0xa9,'c','p','y'):
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1079 mov_parse_udta_string(pb, c->fc->copyright, sizeof(c->fc->copyright));
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1080 break;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1081 case MKTAG(0xa9,'i','n','f'):
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1082 mov_parse_udta_string(pb, c->fc->comment, sizeof(c->fc->comment));
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1083 break;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1084 default:
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1085 break;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1086 }
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1087
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1088 url_fseek(pb, next, SEEK_SET);
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1089 }
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1090
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1091 return 0;
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1092 }
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1093
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1094 static int mov_read_tkhd(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1095 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1096 AVStream *st = c->fc->streams[c->fc->nb_streams-1];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1097 int version = get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1098
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1099 get_byte(pb); get_byte(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1100 get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1101 /*
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1102 MOV_TRACK_ENABLED 0x0001
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1103 MOV_TRACK_IN_MOVIE 0x0002
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1104 MOV_TRACK_IN_PREVIEW 0x0004
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1105 MOV_TRACK_IN_POSTER 0x0008
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1106 */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1107
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1108 if (version == 1) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1109 get_be64(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1110 get_be64(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1111 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1112 get_be32(pb); /* creation time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1113 get_be32(pb); /* modification time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1114 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1115 st->id = (int)get_be32(pb); /* track id (NOT 0 !)*/
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1116 get_be32(pb); /* reserved */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1117 st->start_time = 0; /* check */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1118 (version == 1) ? get_be64(pb) : get_be32(pb); /* highlevel (considering edits) duration in movie timebase */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1119 get_be32(pb); /* reserved */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1120 get_be32(pb); /* reserved */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1121
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1122 get_be16(pb); /* layer */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1123 get_be16(pb); /* alternate group */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1124 get_be16(pb); /* volume */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1125 get_be16(pb); /* reserved */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1126
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1127 url_fskip(pb, 36); /* display matrix */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1128
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1129 /* those are fixed-point */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1130 get_be32(pb); /* track width */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1131 get_be32(pb); /* track height */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1132
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1133 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1134 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1135
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1136 /* this atom should be null (from specs), but some buggy files put the 'moov' atom inside it... */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1137 /* like the files created with Adobe Premiere 5.0, for samples see */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1138 /* http://graphics.tudelft.nl/~wouter/publications/soundtests/ */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1139 static int mov_read_wide(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1140 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1141 int err;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1142
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1143 if (atom.size < 8)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1144 return 0; /* continue */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1145 if (get_be32(pb) != 0) { /* 0 sized mdat atom... use the 'wide' atom size */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1146 url_fskip(pb, atom.size - 4);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1147 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1148 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1149 atom.type = get_le32(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1150 atom.offset += 8;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1151 atom.size -= 8;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1152 if (atom.type != MKTAG('m', 'd', 'a', 't')) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1153 url_fskip(pb, atom.size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1154 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1155 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1156 err = mov_read_mdat(c, pb, atom);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1157 return err;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1158 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1159
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1160 static int mov_read_cmov(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1161 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1162 #ifdef CONFIG_ZLIB
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1163 ByteIOContext ctx;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1164 uint8_t *cmov_data;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1165 uint8_t *moov_data; /* uncompressed data */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1166 long cmov_len, moov_len;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1167 int ret;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1168
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1169 get_be32(pb); /* dcom atom */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1170 if (get_le32(pb) != MKTAG( 'd', 'c', 'o', 'm' ))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1171 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1172 if (get_le32(pb) != MKTAG( 'z', 'l', 'i', 'b' )) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1173 av_log(NULL, AV_LOG_ERROR, "unknown compression for cmov atom !");
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1174 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1175 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1176 get_be32(pb); /* cmvd atom */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1177 if (get_le32(pb) != MKTAG( 'c', 'm', 'v', 'd' ))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1178 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1179 moov_len = get_be32(pb); /* uncompressed size */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1180 cmov_len = atom.size - 6 * 4;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1181
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1182 cmov_data = av_malloc(cmov_len);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1183 if (!cmov_data)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1184 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1185 moov_data = av_malloc(moov_len);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1186 if (!moov_data) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1187 av_free(cmov_data);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1188 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1189 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1190 get_buffer(pb, cmov_data, cmov_len);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1191 if(uncompress (moov_data, (uLongf *) &moov_len, (const Bytef *)cmov_data, cmov_len) != Z_OK)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1192 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1193 if(init_put_byte(&ctx, moov_data, moov_len, 0, NULL, NULL, NULL, NULL) != 0)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1194 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1195 atom.type = MKTAG( 'm', 'o', 'o', 'v' );
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1196 atom.offset = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1197 atom.size = moov_len;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1198 #ifdef DEBUG
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1199 // { int fd = open("/tmp/uncompheader.mov", O_WRONLY | O_CREAT); write(fd, moov_data, moov_len); close(fd); }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1200 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1201 ret = mov_read_default(c, &ctx, atom);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1202 av_free(moov_data);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1203 av_free(cmov_data);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1204 return ret;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1205 #else
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1206 av_log(c->fc, AV_LOG_ERROR, "this file requires zlib support compiled in\n");
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1207 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1208 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1209 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1210
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1211 /* edit list atom */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1212 static int mov_read_elst(MOVContext *c, ByteIOContext *pb, MOV_atom_t atom)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1213 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1214 int i, edit_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1215
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1216 get_byte(pb); /* version */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1217 get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1218 edit_count= c->streams[c->fc->nb_streams-1]->edit_count = get_be32(pb); /* entries */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1219
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1220 for(i=0; i<edit_count; i++){
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1221 get_be32(pb); /* Track duration */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1222 get_be32(pb); /* Media time */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1223 get_be32(pb); /* Media rate */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1224 }
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1225 dprintf(c->fc, "track[%i].edit_count = %i\n", c->fc->nb_streams-1, c->streams[c->fc->nb_streams-1]->edit_count);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1226 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1227 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1228
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1229 static const MOVParseTableEntry mov_default_parse_table[] = {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1230 /* mp4 atoms */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1231 { MKTAG( 'c', 'o', '6', '4' ), mov_read_stco },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1232 { MKTAG( 'c', 't', 't', 's' ), mov_read_ctts }, /* composition time to sample */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1233 { MKTAG( 'e', 'd', 't', 's' ), mov_read_default },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1234 { MKTAG( 'e', 'l', 's', 't' ), mov_read_elst },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1235 { MKTAG( 'e', 'n', 'd', 'a' ), mov_read_enda },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1236 { MKTAG( 'f', 'i', 'e', 'l' ), mov_read_extradata },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1237 { MKTAG( 'f', 't', 'y', 'p' ), mov_read_ftyp },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1238 { MKTAG( 'h', 'd', 'l', 'r' ), mov_read_hdlr },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1239 { MKTAG( 'j', 'p', '2', 'h' ), mov_read_extradata },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1240 { MKTAG( 'm', 'd', 'a', 't' ), mov_read_mdat },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1241 { MKTAG( 'm', 'd', 'h', 'd' ), mov_read_mdhd },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1242 { MKTAG( 'm', 'd', 'i', 'a' ), mov_read_default },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1243 { MKTAG( 'm', 'i', 'n', 'f' ), mov_read_default },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1244 { MKTAG( 'm', 'o', 'o', 'v' ), mov_read_moov },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1245 { MKTAG( 'm', 'v', 'h', 'd' ), mov_read_mvhd },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1246 { MKTAG( 'S', 'M', 'I', ' ' ), mov_read_smi }, /* Sorenson extension ??? */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1247 { MKTAG( 'a', 'l', 'a', 'c' ), mov_read_extradata }, /* alac specific atom */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1248 { MKTAG( 'a', 'v', 'c', 'C' ), mov_read_avcC },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1249 { MKTAG( 's', 't', 'b', 'l' ), mov_read_default },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1250 { MKTAG( 's', 't', 'c', 'o' ), mov_read_stco },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1251 { MKTAG( 's', 't', 's', 'c' ), mov_read_stsc },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1252 { MKTAG( 's', 't', 's', 'd' ), mov_read_stsd }, /* sample description */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1253 { MKTAG( 's', 't', 's', 's' ), mov_read_stss }, /* sync sample */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1254 { MKTAG( 's', 't', 's', 'z' ), mov_read_stsz }, /* sample size */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1255 { MKTAG( 's', 't', 't', 's' ), mov_read_stts },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1256 { MKTAG( 't', 'k', 'h', 'd' ), mov_read_tkhd }, /* track header */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1257 { MKTAG( 't', 'r', 'a', 'k' ), mov_read_trak },
2296
0cfc556604e3 fill title, author, copyright and comment fields by parsing udta atom
benoit
parents: 2164
diff changeset
1258 { MKTAG( 'u', 'd', 't', 'a' ), mov_read_udta },
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1259 { MKTAG( 'w', 'a', 'v', 'e' ), mov_read_wave },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1260 { MKTAG( 'e', 's', 'd', 's' ), mov_read_esds },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1261 { MKTAG( 'w', 'i', 'd', 'e' ), mov_read_wide }, /* place holder */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1262 { MKTAG( 'c', 'm', 'o', 'v' ), mov_read_cmov },
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1263 { 0L, NULL }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1264 };
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1265
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1266 /* XXX: is it sufficient ? */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1267 static int mov_probe(AVProbeData *p)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1268 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1269 unsigned int offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1270 uint32_t tag;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1271 int score = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1272
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1273 /* check file header */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1274 offset = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1275 for(;;) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1276 /* ignore invalid offset */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1277 if ((offset + 8) > (unsigned int)p->buf_size)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1278 return score;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1279 tag = AV_RL32(p->buf + offset + 4);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1280 switch(tag) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1281 /* check for obvious tags */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1282 case MKTAG( 'j', 'P', ' ', ' ' ): /* jpeg 2000 signature */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1283 case MKTAG( 'm', 'o', 'o', 'v' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1284 case MKTAG( 'm', 'd', 'a', 't' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1285 case MKTAG( 'p', 'n', 'o', 't' ): /* detect movs with preview pics like ew.mov and april.mov */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1286 case MKTAG( 'u', 'd', 't', 'a' ): /* Packet Video PVAuthor adds this and a lot of more junk */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1287 return AVPROBE_SCORE_MAX;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1288 /* those are more common words, so rate then a bit less */
2039
5dd45d0a5340 add 'wide' reversed tag in probe, detect broken xdcam files xdcam_hd_1080i60.mov
bcoudurier
parents: 2030
diff changeset
1289 case MKTAG( 'e', 'd', 'i', 'w' ): /* xdcam files have reverted first tags */
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1290 case MKTAG( 'w', 'i', 'd', 'e' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1291 case MKTAG( 'f', 'r', 'e', 'e' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1292 case MKTAG( 'j', 'u', 'n', 'k' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1293 case MKTAG( 'p', 'i', 'c', 't' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1294 return AVPROBE_SCORE_MAX - 5;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1295 case MKTAG( 'f', 't', 'y', 'p' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1296 case MKTAG( 's', 'k', 'i', 'p' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1297 case MKTAG( 'u', 'u', 'i', 'd' ):
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1298 offset = AV_RB32(p->buf+offset) + offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1299 /* if we only find those cause probedata is too small at least rate them */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1300 score = AVPROBE_SCORE_MAX - 50;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1301 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1302 default:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1303 /* unrecognized tag */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1304 return score;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1305 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1306 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1307 return score;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1308 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1309
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1310 static void mov_build_index(MOVContext *mov, AVStream *st)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1311 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1312 MOVStreamContext *sc = st->priv_data;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1313 offset_t current_offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1314 int64_t current_dts = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1315 unsigned int stts_index = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1316 unsigned int stsc_index = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1317 unsigned int stss_index = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1318 unsigned int i, j, k;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1319
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1320 if (sc->sample_sizes || st->codec->codec_type == CODEC_TYPE_VIDEO || sc->dv_audio_container) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1321 unsigned int current_sample = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1322 unsigned int stts_sample = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1323 unsigned int keyframe, sample_size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1324 unsigned int distance = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1325
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1326 st->nb_frames = sc->sample_count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1327 for (i = 0; i < sc->chunk_count; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1328 current_offset = sc->chunk_offsets[i];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1329 if (stsc_index + 1 < sc->sample_to_chunk_sz && i + 1 == sc->sample_to_chunk[stsc_index + 1].first)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1330 stsc_index++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1331 for (j = 0; j < sc->sample_to_chunk[stsc_index].count; j++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1332 if (current_sample >= sc->sample_count) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1333 av_log(mov->fc, AV_LOG_ERROR, "wrong sample count\n");
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1334 goto out;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1335 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1336 keyframe = !sc->keyframe_count || current_sample + 1 == sc->keyframes[stss_index];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1337 if (keyframe) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1338 distance = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1339 if (stss_index + 1 < sc->keyframe_count)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1340 stss_index++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1341 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1342 sample_size = sc->sample_size > 0 ? sc->sample_size : sc->sample_sizes[current_sample];
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1343 dprintf(mov->fc, "AVIndex stream %d, sample %d, offset %"PRIx64", dts %"PRId64", size %d, distance %d, keyframe %d\n",
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1344 st->index, current_sample, current_offset, current_dts, sample_size, distance, keyframe);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1345 av_add_index_entry(st, current_offset, current_dts, sample_size, distance, keyframe ? AVINDEX_KEYFRAME : 0);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1346 current_offset += sample_size;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1347 assert(sc->stts_data[stts_index].duration % sc->time_rate == 0);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1348 current_dts += sc->stts_data[stts_index].duration / sc->time_rate;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1349 distance++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1350 stts_sample++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1351 current_sample++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1352 if (stts_index + 1 < sc->stts_count && stts_sample == sc->stts_data[stts_index].count) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1353 stts_sample = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1354 stts_index++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1355 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1356 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1357 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1358 } else { /* read whole chunk */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1359 unsigned int chunk_samples, chunk_size, chunk_duration;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1360
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1361 for (i = 0; i < sc->chunk_count; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1362 current_offset = sc->chunk_offsets[i];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1363 if (stsc_index + 1 < sc->sample_to_chunk_sz && i + 1 == sc->sample_to_chunk[stsc_index + 1].first)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1364 stsc_index++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1365 chunk_samples = sc->sample_to_chunk[stsc_index].count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1366 /* get chunk size */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1367 if (sc->sample_size > 1 || st->codec->codec_id == CODEC_ID_PCM_U8 || st->codec->codec_id == CODEC_ID_PCM_S8)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1368 chunk_size = chunk_samples * sc->sample_size;
1940
1a7f66384792 cosmetics, sample_size_v1 -> bytes_per_frame / samples_per_frame
bcoudurier
parents: 1939
diff changeset
1369 else if (sc->samples_per_frame > 0 && (chunk_samples * sc->bytes_per_frame % sc->samples_per_frame == 0))
1a7f66384792 cosmetics, sample_size_v1 -> bytes_per_frame / samples_per_frame
bcoudurier
parents: 1939
diff changeset
1370 chunk_size = chunk_samples * sc->bytes_per_frame / sc->samples_per_frame;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1371 else { /* workaround to find nearest next chunk offset */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1372 chunk_size = INT_MAX;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1373 for (j = 0; j < mov->total_streams; j++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1374 MOVStreamContext *msc = mov->streams[j];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1375
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1376 for (k = msc->next_chunk; k < msc->chunk_count; k++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1377 if (msc->chunk_offsets[k] > current_offset && msc->chunk_offsets[k] - current_offset < chunk_size) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1378 chunk_size = msc->chunk_offsets[k] - current_offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1379 msc->next_chunk = k;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1380 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1381 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1382 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1383 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1384 /* check for last chunk */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1385 if (chunk_size == INT_MAX)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1386 for (j = 0; j < mov->mdat_count; j++) {
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1387 dprintf(mov->fc, "mdat %d, offset %"PRIx64", size %"PRId64", current offset %"PRIx64"\n",
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1388 j, mov->mdat_list[j].offset, mov->mdat_list[j].size, current_offset);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1389 if (mov->mdat_list[j].offset <= current_offset && mov->mdat_list[j].offset + mov->mdat_list[j].size > current_offset)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1390 chunk_size = mov->mdat_list[j].offset + mov->mdat_list[j].size - current_offset;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1391 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1392 assert(chunk_size != INT_MAX);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1393 for (j = 0; j < mov->total_streams; j++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1394 mov->streams[j]->next_chunk = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1395 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1396 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1397 av_add_index_entry(st, current_offset, current_dts, chunk_size, 0, AVINDEX_KEYFRAME);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1398 /* get chunk duration */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1399 chunk_duration = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1400 while (chunk_samples > 0) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1401 if (chunk_samples < sc->stts_data[stts_index].count) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1402 chunk_duration += sc->stts_data[stts_index].duration * chunk_samples;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1403 sc->stts_data[stts_index].count -= chunk_samples;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1404 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1405 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1406 chunk_duration += sc->stts_data[stts_index].duration * chunk_samples;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1407 chunk_samples -= sc->stts_data[stts_index].count;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1408 if (stts_index + 1 < sc->stts_count) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1409 stts_index++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1410 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1411 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1412 }
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1413 dprintf(mov->fc, "AVIndex stream %d, chunk %d, offset %"PRIx64", dts %"PRId64", size %d, duration %d\n",
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1414 st->index, i, current_offset, current_dts, chunk_size, chunk_duration);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1415 assert(chunk_duration % sc->time_rate == 0);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1416 current_dts += chunk_duration / sc->time_rate;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1417 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1418 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1419 out:
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1420 /* adjust sample count to avindex entries */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1421 sc->sample_count = st->nb_index_entries;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1422 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1423
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1424 static int mov_read_header(AVFormatContext *s, AVFormatParameters *ap)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1425 {
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
1426 MOVContext *mov = s->priv_data;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1427 ByteIOContext *pb = &s->pb;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1428 int i, err;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1429 MOV_atom_t atom = { 0, 0, 0 };
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1430
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1431 mov->fc = s;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1432 mov->parse_table = mov_default_parse_table;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1433
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1434 if(!url_is_streamed(pb)) /* .mov and .mp4 aren't streamable anyway (only progressive download if moov is before mdat) */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1435 atom.size = url_fsize(pb);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1436 else
2026
2e2c2dbb511d use INT64_MAX
bcoudurier
parents: 2023
diff changeset
1437 atom.size = INT64_MAX;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1438
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1439 /* check MOV header */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1440 err = mov_read_default(mov, pb, atom);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1441 if (err<0 || (!mov->found_moov && !mov->found_mdat)) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1442 av_log(s, AV_LOG_ERROR, "mov: header not found !!! (err:%d, moov:%d, mdat:%d) pos:%"PRId64"\n",
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1443 err, mov->found_moov, mov->found_mdat, url_ftell(pb));
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1444 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1445 }
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1446 dprintf(mov->fc, "on_parse_exit_offset=%d\n", (int) url_ftell(pb));
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1447
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1448 /* some cleanup : make sure we are on the mdat atom */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1449 if(!url_is_streamed(pb) && (url_ftell(pb) != mov->mdat_offset))
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1450 url_fseek(pb, mov->mdat_offset, SEEK_SET);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1451
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1452 mov->total_streams = s->nb_streams;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1453
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1454 for(i=0; i<mov->total_streams; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1455 MOVStreamContext *sc = mov->streams[i];
1938
1e93a2174dc6 set audio frame size based on stts
bcoudurier
parents: 1907
diff changeset
1456 AVStream *st = s->streams[i];
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1457 /* sanity checks */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1458 if(!sc->stts_count || !sc->chunk_count || !sc->sample_to_chunk_sz ||
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1459 (!sc->sample_size && !sc->sample_count)){
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1460 av_log(s, AV_LOG_ERROR, "missing mandatory atoms, broken header\n");
1963
81268e2bd9aa unset sample count to disable track when is broken
bcoudurier
parents: 1962
diff changeset
1461 sc->sample_count = 0; //ignore track
1950
4ef37f929c21 dont fail immediately when a somehow broken track is detected, some tracks might be good, fix mi2_vorbis51.mp4
bcoudurier
parents: 1948
diff changeset
1462 continue;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1463 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1464 if(!sc->time_rate)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1465 sc->time_rate=1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1466 if(!sc->time_scale)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1467 sc->time_scale= mov->time_scale;
1939
f846a0c202b5 cosmetics
bcoudurier
parents: 1938
diff changeset
1468 av_set_pts_info(st, 64, sc->time_rate, sc->time_scale);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1469
1938
1e93a2174dc6 set audio frame size based on stts
bcoudurier
parents: 1907
diff changeset
1470 if (st->codec->codec_type == CODEC_TYPE_AUDIO && sc->stts_count == 1)
1e93a2174dc6 set audio frame size based on stts
bcoudurier
parents: 1907
diff changeset
1471 st->codec->frame_size = sc->stts_data[0].duration;
1e93a2174dc6 set audio frame size based on stts
bcoudurier
parents: 1907
diff changeset
1472
1939
f846a0c202b5 cosmetics
bcoudurier
parents: 1938
diff changeset
1473 if(st->duration != AV_NOPTS_VALUE){
f846a0c202b5 cosmetics
bcoudurier
parents: 1938
diff changeset
1474 assert(st->duration % sc->time_rate == 0);
f846a0c202b5 cosmetics
bcoudurier
parents: 1938
diff changeset
1475 st->duration /= sc->time_rate;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1476 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1477 sc->ffindex = i;
1939
f846a0c202b5 cosmetics
bcoudurier
parents: 1938
diff changeset
1478 mov_build_index(mov, st);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1479 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1480
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1481 for(i=0; i<mov->total_streams; i++) {
2164
3804e39efbfd misc spelling fixes
diego
parents: 2084
diff changeset
1482 /* Do not need those anymore. */
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1483 av_freep(&mov->streams[i]->chunk_offsets);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1484 av_freep(&mov->streams[i]->sample_to_chunk);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1485 av_freep(&mov->streams[i]->sample_sizes);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1486 av_freep(&mov->streams[i]->keyframes);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1487 av_freep(&mov->streams[i]->stts_data);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1488 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1489 av_freep(&mov->mdat_list);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1490 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1491 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1492
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1493 static int mov_read_packet(AVFormatContext *s, AVPacket *pkt)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1494 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1495 MOVContext *mov = s->priv_data;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1496 MOVStreamContext *sc = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1497 AVIndexEntry *sample = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1498 int64_t best_dts = INT64_MAX;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1499 int i;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1500
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1501 for (i = 0; i < mov->total_streams; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1502 MOVStreamContext *msc = mov->streams[i];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1503
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1504 if (s->streams[i]->discard != AVDISCARD_ALL && msc->current_sample < msc->sample_count) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1505 AVIndexEntry *current_sample = &s->streams[i]->index_entries[msc->current_sample];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1506 int64_t dts = av_rescale(current_sample->timestamp * (int64_t)msc->time_rate, AV_TIME_BASE, msc->time_scale);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1507
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
1508 dprintf(s, "stream %d, sample %d, dts %"PRId64"\n", i, msc->current_sample, dts);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1509 if (dts < best_dts) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1510 sample = current_sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1511 best_dts = dts;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1512 sc = msc;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1513 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1514 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1515 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1516 if (!sample)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1517 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1518 /* must be done just before reading, to avoid infinite loop on sample */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1519 sc->current_sample++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1520 if (sample->pos >= url_fsize(&s->pb)) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1521 av_log(mov->fc, AV_LOG_ERROR, "stream %d, offset 0x%"PRIx64": partial file\n", sc->ffindex, sample->pos);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1522 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1523 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1524 #ifdef CONFIG_DV_DEMUXER
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1525 if (sc->dv_audio_container) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1526 dv_get_packet(mov->dv_demux, pkt);
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1527 dprintf(s, "dv audio pkt size %d\n", pkt->size);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1528 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1529 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1530 url_fseek(&s->pb, sample->pos, SEEK_SET);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1531 av_get_packet(&s->pb, pkt, sample->size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1532 #ifdef CONFIG_DV_DEMUXER
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1533 if (mov->dv_demux) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1534 void *pkt_destruct_func = pkt->destruct;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1535 dv_produce_packet(mov->dv_demux, pkt, pkt->data, pkt->size);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1536 pkt->destruct = pkt_destruct_func;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1537 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1538 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1539 #endif
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1540 pkt->stream_index = sc->ffindex;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1541 pkt->dts = sample->timestamp;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1542 if (sc->ctts_data) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1543 assert(sc->ctts_data[sc->sample_to_ctime_index].duration % sc->time_rate == 0);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1544 pkt->pts = pkt->dts + sc->ctts_data[sc->sample_to_ctime_index].duration / sc->time_rate;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1545 /* update ctts context */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1546 sc->sample_to_ctime_sample++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1547 if (sc->sample_to_ctime_index < sc->ctts_count && sc->ctts_data[sc->sample_to_ctime_index].count == sc->sample_to_ctime_sample) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1548 sc->sample_to_ctime_index++;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1549 sc->sample_to_ctime_sample = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1550 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1551 } else {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1552 pkt->pts = pkt->dts;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1553 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1554 pkt->flags |= sample->flags & AVINDEX_KEYFRAME ? PKT_FLAG_KEY : 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1555 pkt->pos = sample->pos;
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1556 dprintf(s, "stream %d, pts %"PRId64", dts %"PRId64", pos 0x%"PRIx64", duration %d\n", pkt->stream_index, pkt->pts, pkt->dts, pkt->pos, pkt->duration);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1557 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1558 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1559
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1560 static int mov_seek_stream(AVStream *st, int64_t timestamp, int flags)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1561 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1562 MOVStreamContext *sc = st->priv_data;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1563 int sample, time_sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1564 int i;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1565
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1566 sample = av_index_search_timestamp(st, timestamp, flags);
1907
b33db97089ba Give context to dprintf
mbardiaux
parents: 1848
diff changeset
1567 dprintf(st->codec, "stream %d, timestamp %"PRId64", sample %d\n", st->index, timestamp, sample);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1568 if (sample < 0) /* not sure what to do */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1569 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1570 sc->current_sample = sample;
2030
4464239eddbb long -> int
bcoudurier
parents: 2029
diff changeset
1571 dprintf(st->codec, "stream %d, found sample %d\n", st->index, sc->current_sample);
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1572 /* adjust ctts index */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1573 if (sc->ctts_data) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1574 time_sample = 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1575 for (i = 0; i < sc->ctts_count; i++) {
2083
2c3887f02739 fix ctts index computation when seeking, check must be done against next ctts sample, thanks to Uoti
bcoudurier
parents: 2046
diff changeset
1576 int next = time_sample + sc->ctts_data[i].count;
2c3887f02739 fix ctts index computation when seeking, check must be done against next ctts sample, thanks to Uoti
bcoudurier
parents: 2046
diff changeset
1577 if (next > sc->current_sample) {
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1578 sc->sample_to_ctime_index = i;
2083
2c3887f02739 fix ctts index computation when seeking, check must be done against next ctts sample, thanks to Uoti
bcoudurier
parents: 2046
diff changeset
1579 sc->sample_to_ctime_sample = sc->current_sample - time_sample;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1580 break;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1581 }
2083
2c3887f02739 fix ctts index computation when seeking, check must be done against next ctts sample, thanks to Uoti
bcoudurier
parents: 2046
diff changeset
1582 time_sample = next;
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1583 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1584 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1585 return sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1586 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1587
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1588 static int mov_read_seek(AVFormatContext *s, int stream_index, int64_t sample_time, int flags)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1589 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1590 AVStream *st;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1591 int64_t seek_timestamp, timestamp;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1592 int sample;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1593 int i;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1594
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1595 if (stream_index >= s->nb_streams)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1596 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1597
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1598 st = s->streams[stream_index];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1599 sample = mov_seek_stream(st, sample_time, flags);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1600 if (sample < 0)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1601 return -1;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1602
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1603 /* adjust seek timestamp to found sample timestamp */
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1604 seek_timestamp = st->index_entries[sample].timestamp;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1605
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1606 for (i = 0; i < s->nb_streams; i++) {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1607 st = s->streams[i];
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1608 if (stream_index == i || st->discard == AVDISCARD_ALL)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1609 continue;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1610
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1611 timestamp = av_rescale_q(seek_timestamp, s->streams[stream_index]->time_base, st->time_base);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1612 mov_seek_stream(st, timestamp, flags);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1613 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1614 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1615 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1616
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1617 static int mov_read_close(AVFormatContext *s)
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1618 {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1619 int i;
2006
2f0154760e5f Get rid of unnecessary pointer casts.
diego
parents: 2001
diff changeset
1620 MOVContext *mov = s->priv_data;
2084
f5671ebda7cd simplify, no need for a function
bcoudurier
parents: 2083
diff changeset
1621 for(i=0; i<mov->total_streams; i++) {
f5671ebda7cd simplify, no need for a function
bcoudurier
parents: 2083
diff changeset
1622 av_freep(&mov->streams[i]->ctts_data);
f5671ebda7cd simplify, no need for a function
bcoudurier
parents: 2083
diff changeset
1623 av_freep(&mov->streams[i]);
f5671ebda7cd simplify, no need for a function
bcoudurier
parents: 2083
diff changeset
1624 }
1845
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1625 if(mov->dv_demux){
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1626 for(i=0; i<mov->dv_fctx->nb_streams; i++){
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1627 av_freep(&mov->dv_fctx->streams[i]->codec);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1628 av_freep(&mov->dv_fctx->streams[i]);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1629 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1630 av_freep(&mov->dv_fctx);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1631 av_freep(&mov->dv_demux);
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1632 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1633 return 0;
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1634 }
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1635
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1636 AVInputFormat mov_demuxer = {
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1637 "mov,mp4,m4a,3gp,3g2,mj2",
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1638 "QuickTime/MPEG4/Motion JPEG 2000 format",
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1639 sizeof(MOVContext),
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1640 mov_probe,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1641 mov_read_header,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1642 mov_read_packet,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1643 mov_read_close,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1644 mov_read_seek,
4c4825b91451 functional part of the commit below
michael
parents:
diff changeset
1645 };