Mercurial > libavformat.hg
annotate siff.c @ 5953:c3ebc8d7af38 libavformat
Remove useless assert(), since this can (in theora) be used for any Xiph
codec, so there's no reason to (invalidly) limit it to only Theora.
Also fixes issue 1880 (compilation error on -DDEBUG).
author | rbultje |
---|---|
date | Thu, 15 Apr 2010 13:30:12 +0000 |
parents | 11bb10c37225 |
children |
rev | line source |
---|---|
2659 | 1 /* |
2 * Beam Software SIFF demuxer | |
4251
77e0c7511d41
cosmetics: Remove pointless period after copyright statement non-sentences.
diego
parents:
4201
diff
changeset
|
3 * Copyright (c) 2007 Konstantin Shishkov |
2659 | 4 * |
5 * This file is part of FFmpeg. | |
6 * | |
7 * FFmpeg is free software; you can redistribute it and/or | |
8 * modify it under the terms of the GNU Lesser General Public | |
9 * License as published by the Free Software Foundation; either | |
10 * version 2.1 of the License, or (at your option) any later version. | |
11 * | |
12 * FFmpeg is distributed in the hope that it will be useful, | |
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
15 * Lesser General Public License for more details. | |
16 * | |
17 * You should have received a copy of the GNU Lesser General Public | |
18 * License along with FFmpeg; if not, write to the Free Software | |
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | |
20 */ | |
21 | |
4201
7d2f3f1b68d8
Fix build: Add intreadwrite.h and bswap.h #includes where necessary.
diego
parents:
3908
diff
changeset
|
22 #include "libavutil/intreadwrite.h" |
2659 | 23 #include "avformat.h" |
24 | |
25 enum SIFFTags{ | |
26 TAG_SIFF = MKTAG('S', 'I', 'F', 'F'), | |
27 TAG_BODY = MKTAG('B', 'O', 'D', 'Y'), | |
28 TAG_VBHD = MKTAG('V', 'B', 'H', 'D'), | |
29 TAG_SHDR = MKTAG('S', 'H', 'D', 'R'), | |
30 TAG_VBV1 = MKTAG('V', 'B', 'V', '1'), | |
31 TAG_SOUN = MKTAG('S', 'O', 'U', 'N'), | |
32 }; | |
33 | |
34 enum VBFlags{ | |
35 VB_HAS_GMC = 0x01, | |
36 VB_HAS_AUDIO = 0x04, | |
37 VB_HAS_VIDEO = 0x08, | |
38 VB_HAS_PALETTE = 0x10, | |
39 VB_HAS_LENGTH = 0x20 | |
40 }; | |
41 | |
42 typedef struct SIFFContext{ | |
43 int frames; | |
44 int cur_frame; | |
45 int rate; | |
46 int bits; | |
47 int block_align; | |
48 | |
49 int has_video; | |
50 int has_audio; | |
51 | |
52 int curstrm; | |
53 int pktsize; | |
54 int gmcsize; | |
55 int sndsize; | |
56 | |
57 int flags; | |
58 uint8_t gmc[4]; | |
59 }SIFFContext; | |
60 | |
61 static int siff_probe(AVProbeData *p) | |
62 { | |
5217
0d44bd284a96
Improve SIFF probe by also checking the first tag is one of the expected.
reimar
parents:
4251
diff
changeset
|
63 uint32_t tag = AV_RL32(p->buf + 8); |
2659 | 64 /* check file header */ |
5217
0d44bd284a96
Improve SIFF probe by also checking the first tag is one of the expected.
reimar
parents:
4251
diff
changeset
|
65 if (AV_RL32(p->buf) != TAG_SIFF || |
0d44bd284a96
Improve SIFF probe by also checking the first tag is one of the expected.
reimar
parents:
4251
diff
changeset
|
66 (tag != TAG_VBV1 && tag != TAG_SOUN)) |
2659 | 67 return 0; |
5217
0d44bd284a96
Improve SIFF probe by also checking the first tag is one of the expected.
reimar
parents:
4251
diff
changeset
|
68 return AVPROBE_SCORE_MAX; |
2659 | 69 } |
70 | |
71 static int create_audio_stream(AVFormatContext *s, SIFFContext *c) | |
72 { | |
73 AVStream *ast; | |
74 ast = av_new_stream(s, 0); | |
75 if (!ast) | |
76 return -1; | |
5910
536e5527c1e0
Define AVMediaType enum, and use it instead of enum CodecType, which
stefano
parents:
5217
diff
changeset
|
77 ast->codec->codec_type = AVMEDIA_TYPE_AUDIO; |
2659 | 78 ast->codec->codec_id = CODEC_ID_PCM_U8; |
79 ast->codec->channels = 1; | |
3908
1d3d17de20ba
Bump Major version, this commit is almost just renaming bits_per_sample to
michael
parents:
3424
diff
changeset
|
80 ast->codec->bits_per_coded_sample = c->bits; |
2659 | 81 ast->codec->sample_rate = c->rate; |
82 ast->codec->frame_size = c->block_align; | |
83 av_set_pts_info(ast, 16, 1, c->rate); | |
84 return 0; | |
85 } | |
86 | |
87 static int siff_parse_vbv1(AVFormatContext *s, SIFFContext *c, ByteIOContext *pb) | |
88 { | |
89 AVStream *st; | |
90 int width, height; | |
91 | |
92 if (get_le32(pb) != TAG_VBHD){ | |
93 av_log(s, AV_LOG_ERROR, "Header chunk is missing\n"); | |
94 return -1; | |
95 } | |
96 if(get_be32(pb) != 32){ | |
97 av_log(s, AV_LOG_ERROR, "Header chunk size is incorrect\n"); | |
98 return -1; | |
99 } | |
100 if(get_le16(pb) != 1){ | |
101 av_log(s, AV_LOG_ERROR, "Incorrect header version\n"); | |
102 return -1; | |
103 } | |
104 width = get_le16(pb); | |
105 height = get_le16(pb); | |
106 url_fskip(pb, 4); | |
107 c->frames = get_le16(pb); | |
108 if(!c->frames){ | |
109 av_log(s, AV_LOG_ERROR, "File contains no frames ???\n"); | |
110 return -1; | |
111 } | |
112 c->bits = get_le16(pb); | |
113 c->rate = get_le16(pb); | |
114 c->block_align = c->rate * (c->bits >> 3); | |
115 | |
116 url_fskip(pb, 16); //zeroes | |
117 | |
118 st = av_new_stream(s, 0); | |
119 if (!st) | |
120 return -1; | |
5910
536e5527c1e0
Define AVMediaType enum, and use it instead of enum CodecType, which
stefano
parents:
5217
diff
changeset
|
121 st->codec->codec_type = AVMEDIA_TYPE_VIDEO; |
2659 | 122 st->codec->codec_id = CODEC_ID_VB; |
123 st->codec->codec_tag = MKTAG('V', 'B', 'V', '1'); | |
124 st->codec->width = width; | |
125 st->codec->height = height; | |
126 st->codec->pix_fmt = PIX_FMT_PAL8; | |
127 av_set_pts_info(st, 16, 1, 12); | |
128 | |
129 c->cur_frame = 0; | |
130 c->has_video = 1; | |
131 c->has_audio = !!c->rate; | |
132 c->curstrm = -1; | |
133 if (c->has_audio && create_audio_stream(s, c) < 0) | |
134 return -1; | |
135 return 0; | |
136 } | |
137 | |
138 static int siff_parse_soun(AVFormatContext *s, SIFFContext *c, ByteIOContext *pb) | |
139 { | |
140 if (get_le32(pb) != TAG_SHDR){ | |
141 av_log(s, AV_LOG_ERROR, "Header chunk is missing\n"); | |
142 return -1; | |
143 } | |
144 if(get_be32(pb) != 8){ | |
145 av_log(s, AV_LOG_ERROR, "Header chunk size is incorrect\n"); | |
146 return -1; | |
147 } | |
148 url_fskip(pb, 4); //unknown value | |
149 c->rate = get_le16(pb); | |
150 c->bits = get_le16(pb); | |
151 c->block_align = c->rate * (c->bits >> 3); | |
152 return create_audio_stream(s, c); | |
153 } | |
154 | |
155 static int siff_read_header(AVFormatContext *s, AVFormatParameters *ap) | |
156 { | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
157 ByteIOContext *pb = s->pb; |
2659 | 158 SIFFContext *c = s->priv_data; |
159 uint32_t tag; | |
160 | |
161 if (get_le32(pb) != TAG_SIFF) | |
162 return -1; | |
163 url_fskip(pb, 4); //ignore size | |
164 tag = get_le32(pb); | |
165 | |
166 if (tag != TAG_VBV1 && tag != TAG_SOUN){ | |
167 av_log(s, AV_LOG_ERROR, "Not a VBV file\n"); | |
168 return -1; | |
169 } | |
170 | |
171 if (tag == TAG_VBV1 && siff_parse_vbv1(s, c, pb) < 0) | |
172 return -1; | |
173 if (tag == TAG_SOUN && siff_parse_soun(s, c, pb) < 0) | |
174 return -1; | |
175 if (get_le32(pb) != MKTAG('B', 'O', 'D', 'Y')){ | |
176 av_log(s, AV_LOG_ERROR, "'BODY' chunk is missing\n"); | |
177 return -1; | |
178 } | |
179 url_fskip(pb, 4); //ignore size | |
180 | |
181 return 0; | |
182 } | |
183 | |
184 static int siff_read_packet(AVFormatContext *s, AVPacket *pkt) | |
185 { | |
186 SIFFContext *c = s->priv_data; | |
2690
0a8f2dc62d01
Remove unused variables, fixes the following warnings:
diego
parents:
2659
diff
changeset
|
187 int size; |
2659 | 188 |
189 if (c->has_video){ | |
190 if (c->cur_frame >= c->frames) | |
191 return AVERROR(EIO); | |
192 if (c->curstrm == -1){ | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
193 c->pktsize = get_le32(s->pb) - 4; |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
194 c->flags = get_le16(s->pb); |
2659 | 195 c->gmcsize = (c->flags & VB_HAS_GMC) ? 4 : 0; |
196 if (c->gmcsize) | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
197 get_buffer(s->pb, c->gmc, c->gmcsize); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
198 c->sndsize = (c->flags & VB_HAS_AUDIO) ? get_le32(s->pb): 0; |
2659 | 199 c->curstrm = !!(c->flags & VB_HAS_AUDIO); |
200 } | |
201 | |
202 if (!c->curstrm){ | |
203 size = c->pktsize - c->sndsize; | |
204 if (av_new_packet(pkt, size) < 0) | |
205 return AVERROR(ENOMEM); | |
206 AV_WL16(pkt->data, c->flags); | |
207 if (c->gmcsize) | |
208 memcpy(pkt->data + 2, c->gmc, c->gmcsize); | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
209 get_buffer(s->pb, pkt->data + 2 + c->gmcsize, size - c->gmcsize - 2); |
2659 | 210 pkt->stream_index = 0; |
211 c->curstrm = -1; | |
212 }else{ | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
213 if (av_get_packet(s->pb, pkt, c->sndsize - 4) < 0) |
2659 | 214 return AVERROR(EIO); |
215 pkt->stream_index = 1; | |
216 c->curstrm = 0; | |
217 } | |
218 if(!c->cur_frame || c->curstrm) | |
5913
11bb10c37225
Replace all occurences of PKT_FLAG_KEY with AV_PKT_FLAG_KEY.
cehoyos
parents:
5910
diff
changeset
|
219 pkt->flags |= AV_PKT_FLAG_KEY; |
2659 | 220 if (c->curstrm == -1) |
221 c->cur_frame++; | |
222 }else{ | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2690
diff
changeset
|
223 size = av_get_packet(s->pb, pkt, c->block_align); |
2659 | 224 if(size <= 0) |
225 return AVERROR(EIO); | |
226 } | |
227 return pkt->size; | |
228 } | |
229 | |
230 AVInputFormat siff_demuxer = { | |
231 "siff", | |
3424
7a0230981402
Make long_names in lavf/lavdev optional depending on CONFIG_SMALL.
diego
parents:
3399
diff
changeset
|
232 NULL_IF_CONFIG_SMALL("Beam Software SIFF"), |
2659 | 233 sizeof(SIFFContext), |
234 siff_probe, | |
235 siff_read_header, | |
236 siff_read_packet, | |
237 .extensions = "vb,son" | |
238 }; |