Mercurial > libavformat.hg
annotate c93.c @ 3754:8d267b43eaba libavformat
Move malloc() down until after all initializations, so that the resource is
only allocated if initialization worked. This means that on failure, we
don't have to deallocate it.
author | rbultje |
---|---|
date | Sat, 23 Aug 2008 18:46:30 +0000 |
parents | 7a0230981402 |
children | 27537074f2a9 |
rev | line source |
---|---|
1987 | 1 /* |
2 * Interplay C93 demuxer | |
3 * Copyright (c) 2007 Anssi Hannula <anssi.hannula@gmail.com> | |
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 | |
2217 | 19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
1987 | 20 */ |
21 | |
22 #include "avformat.h" | |
23 #include "voc.h" | |
24 | |
25 typedef struct { | |
26 uint16_t index; | |
27 uint8_t length; | |
28 uint8_t frames; | |
29 } C93BlockRecord; | |
30 | |
31 typedef struct { | |
32 voc_dec_context_t voc; | |
33 | |
34 C93BlockRecord block_records[512]; | |
35 int current_block; | |
36 | |
37 uint32_t frame_offsets[32]; | |
38 int current_frame; | |
39 int next_pkt_is_audio; | |
40 | |
41 AVStream *audio; | |
42 } C93DemuxContext; | |
43 | |
2000
ce51095f383b
also remove c93_ prefix for static function in the c93 demuxer
michael
parents:
1987
diff
changeset
|
44 static int probe(AVProbeData *p) |
1987 | 45 { |
46 if (p->buf[0] == 0x01 && p->buf[1] == 0x00 && | |
47 p->buf[4] == 0x01 + p->buf[2] && | |
48 p->buf[8] == p->buf[4] + p->buf[6] && | |
49 p->buf[12] == p->buf[8] + p->buf[10]) | |
50 return AVPROBE_SCORE_MAX; | |
51 | |
52 return 0; | |
53 } | |
54 | |
2000
ce51095f383b
also remove c93_ prefix for static function in the c93 demuxer
michael
parents:
1987
diff
changeset
|
55 static int read_header(AVFormatContext *s, |
1987 | 56 AVFormatParameters *ap) |
57 { | |
58 AVStream *video; | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2274
diff
changeset
|
59 ByteIOContext *pb = s->pb; |
1987 | 60 C93DemuxContext *c93 = s->priv_data; |
61 int i; | |
62 int framecount = 0; | |
63 | |
64 for (i = 0; i < 512; i++) { | |
65 c93->block_records[i].index = get_le16(pb); | |
66 c93->block_records[i].length = get_byte(pb); | |
67 c93->block_records[i].frames = get_byte(pb); | |
68 if (c93->block_records[i].frames > 32) { | |
69 av_log(s, AV_LOG_ERROR, "too many frames in block\n"); | |
70 return AVERROR_INVALIDDATA; | |
71 } | |
72 framecount += c93->block_records[i].frames; | |
73 } | |
74 | |
75 /* Audio streams are added if audio packets are found */ | |
76 s->ctx_flags |= AVFMTCTX_NOHEADER; | |
77 | |
78 video = av_new_stream(s, 0); | |
79 if (!video) | |
2273
7eb456c4ed8a
Replace all occurrences of AVERROR_NOMEM with AVERROR(ENOMEM).
takis
parents:
2217
diff
changeset
|
80 return AVERROR(ENOMEM); |
1987 | 81 |
82 video->codec->codec_type = CODEC_TYPE_VIDEO; | |
83 video->codec->codec_id = CODEC_ID_C93; | |
84 video->codec->width = 320; | |
85 video->codec->height = 192; | |
86 /* 4:3 320x200 with 8 empty lines */ | |
87 video->codec->sample_aspect_ratio = (AVRational) { 5, 6 }; | |
88 video->time_base = (AVRational) { 2, 25 }; | |
89 video->nb_frames = framecount; | |
90 video->duration = framecount; | |
91 video->start_time = 0; | |
92 | |
93 c93->current_block = 0; | |
94 c93->current_frame = 0; | |
95 c93->next_pkt_is_audio = 0; | |
96 return 0; | |
97 } | |
98 | |
99 #define C93_HAS_PALETTE 0x01 | |
100 #define C93_FIRST_FRAME 0x02 | |
101 | |
2000
ce51095f383b
also remove c93_ prefix for static function in the c93 demuxer
michael
parents:
1987
diff
changeset
|
102 static int read_packet(AVFormatContext *s, AVPacket *pkt) |
1987 | 103 { |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2274
diff
changeset
|
104 ByteIOContext *pb = s->pb; |
1987 | 105 C93DemuxContext *c93 = s->priv_data; |
106 C93BlockRecord *br = &c93->block_records[c93->current_block]; | |
107 int datasize; | |
108 int ret, i; | |
109 | |
110 if (c93->next_pkt_is_audio) { | |
111 c93->current_frame++; | |
112 c93->next_pkt_is_audio = 0; | |
113 datasize = get_le16(pb); | |
114 if (datasize > 42) { | |
115 if (!c93->audio) { | |
116 c93->audio = av_new_stream(s, 1); | |
117 if (!c93->audio) | |
2273
7eb456c4ed8a
Replace all occurrences of AVERROR_NOMEM with AVERROR(ENOMEM).
takis
parents:
2217
diff
changeset
|
118 return AVERROR(ENOMEM); |
1987 | 119 c93->audio->codec->codec_type = CODEC_TYPE_AUDIO; |
120 } | |
121 url_fskip(pb, 26); /* VOC header */ | |
122 ret = voc_get_packet(s, pkt, c93->audio, datasize - 26); | |
123 if (ret > 0) { | |
124 pkt->stream_index = 1; | |
125 pkt->flags |= PKT_FLAG_KEY; | |
126 return ret; | |
127 } | |
128 } | |
129 } | |
130 if (c93->current_frame >= br->frames) { | |
131 if (c93->current_block >= 511 || !br[1].length) | |
2274
b21c2af60bc9
Replace all occurrences of AVERROR_IO with AVERROR(EIO).
takis
parents:
2273
diff
changeset
|
132 return AVERROR(EIO); |
1987 | 133 br++; |
134 c93->current_block++; | |
135 c93->current_frame = 0; | |
136 } | |
137 | |
138 if (c93->current_frame == 0) { | |
139 url_fseek(pb, br->index * 2048, SEEK_SET); | |
140 for (i = 0; i < 32; i++) { | |
141 c93->frame_offsets[i] = get_le32(pb); | |
142 } | |
143 } | |
144 | |
145 url_fseek(pb,br->index * 2048 + | |
146 c93->frame_offsets[c93->current_frame], SEEK_SET); | |
147 datasize = get_le16(pb); /* video frame size */ | |
148 | |
149 ret = av_new_packet(pkt, datasize + 768 + 1); | |
150 if (ret < 0) | |
151 return ret; | |
152 pkt->data[0] = 0; | |
153 pkt->size = datasize + 1; | |
154 | |
155 ret = get_buffer(pb, pkt->data + 1, datasize); | |
156 if (ret < datasize) { | |
2274
b21c2af60bc9
Replace all occurrences of AVERROR_IO with AVERROR(EIO).
takis
parents:
2273
diff
changeset
|
157 ret = AVERROR(EIO); |
1987 | 158 goto fail; |
159 } | |
160 | |
161 datasize = get_le16(pb); /* palette size */ | |
162 if (datasize) { | |
163 if (datasize != 768) { | |
164 av_log(s, AV_LOG_ERROR, "invalid palette size %u\n", datasize); | |
165 ret = AVERROR_INVALIDDATA; | |
166 goto fail; | |
167 } | |
168 pkt->data[0] |= C93_HAS_PALETTE; | |
169 ret = get_buffer(pb, pkt->data + pkt->size, datasize); | |
170 if (ret < datasize) { | |
2274
b21c2af60bc9
Replace all occurrences of AVERROR_IO with AVERROR(EIO).
takis
parents:
2273
diff
changeset
|
171 ret = AVERROR(EIO); |
1987 | 172 goto fail; |
173 } | |
174 pkt->size += 768; | |
175 } | |
176 pkt->stream_index = 0; | |
177 c93->next_pkt_is_audio = 1; | |
178 | |
179 /* only the first frame is guaranteed to not reference previous frames */ | |
180 if (c93->current_block == 0 && c93->current_frame == 0) { | |
181 pkt->flags |= PKT_FLAG_KEY; | |
182 pkt->data[0] |= C93_FIRST_FRAME; | |
183 } | |
184 return 0; | |
185 | |
186 fail: | |
187 av_free_packet(pkt); | |
188 return ret; | |
189 } | |
190 | |
191 AVInputFormat c93_demuxer = { | |
192 "c93", | |
3424
7a0230981402
Make long_names in lavf/lavdev optional depending on CONFIG_SMALL.
diego
parents:
2771
diff
changeset
|
193 NULL_IF_CONFIG_SMALL("Interplay C93"), |
1987 | 194 sizeof(C93DemuxContext), |
2000
ce51095f383b
also remove c93_ prefix for static function in the c93 demuxer
michael
parents:
1987
diff
changeset
|
195 probe, |
ce51095f383b
also remove c93_ prefix for static function in the c93 demuxer
michael
parents:
1987
diff
changeset
|
196 read_header, |
ce51095f383b
also remove c93_ prefix for static function in the c93 demuxer
michael
parents:
1987
diff
changeset
|
197 read_packet, |
1987 | 198 }; |