2 * Sega FILM Format (CPK) Demuxer
3 * Copyright (c) 2003 The FFmpeg Project
5 * This file is part of FFmpeg.
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.
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.
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
24 * Sega FILM (.cpk) file demuxer
25 * by Mike Melanson (melanson@pcisys.net)
26 * For more information regarding the Sega FILM file format, visit:
27 * http://www.pcisys.net/~melanson/codecs/
30 #include "libavutil/intreadwrite.h"
33 #include "avio_internal.h"
35 #define FILM_TAG MKBETAG('F', 'I', 'L', 'M')
36 #define FDSC_TAG MKBETAG('F', 'D', 'S', 'C')
37 #define STAB_TAG MKBETAG('S', 'T', 'A', 'B')
38 #define CVID_TAG MKBETAG('c', 'v', 'i', 'd')
39 #define RAW_TAG MKBETAG('r', 'a', 'w', ' ')
43 int64_t sample_offset
;
44 unsigned int sample_size
;
49 typedef struct FilmDemuxContext
{
50 int video_stream_index
;
51 int audio_stream_index
;
53 enum AVCodecID audio_type
;
54 unsigned int audio_samplerate
;
55 unsigned int audio_bits
;
56 unsigned int audio_channels
;
58 enum AVCodecID video_type
;
59 unsigned int sample_count
;
60 film_sample
*sample_table
;
61 unsigned int current_sample
;
63 unsigned int base_clock
;
67 static int film_probe(AVProbeData
*p
)
69 if (AV_RB32(&p
->buf
[0]) != FILM_TAG
)
72 if (AV_RB32(&p
->buf
[16]) != FDSC_TAG
)
75 return AVPROBE_SCORE_MAX
;
78 static int film_read_close(AVFormatContext
*s
)
80 FilmDemuxContext
*film
= s
->priv_data
;
82 av_freep(&film
->sample_table
);
87 static int film_read_header(AVFormatContext
*s
)
89 FilmDemuxContext
*film
= s
->priv_data
;
90 AVIOContext
*pb
= s
->pb
;
92 unsigned char scratch
[256];
94 unsigned int data_offset
;
95 unsigned int audio_frame_counter
;
97 film
->sample_table
= NULL
;
99 /* load the main FILM header */
100 if (avio_read(pb
, scratch
, 16) != 16)
102 data_offset
= AV_RB32(&scratch
[4]);
103 film
->version
= AV_RB32(&scratch
[8]);
105 /* load the FDSC chunk */
106 if (film
->version
== 0) {
107 /* special case for Lemmings .film files; 20-byte header */
108 if (avio_read(pb
, scratch
, 20) != 20)
110 /* make some assumptions about the audio parameters */
111 film
->audio_type
= AV_CODEC_ID_PCM_S8
;
112 film
->audio_samplerate
= 22050;
113 film
->audio_channels
= 1;
114 film
->audio_bits
= 8;
116 /* normal Saturn .cpk files; 32-byte header */
117 if (avio_read(pb
, scratch
, 32) != 32)
119 film
->audio_samplerate
= AV_RB16(&scratch
[24]);
120 film
->audio_channels
= scratch
[21];
121 film
->audio_bits
= scratch
[22];
122 if (scratch
[23] == 2 && film
->audio_channels
> 0)
123 film
->audio_type
= AV_CODEC_ID_ADPCM_ADX
;
124 else if (film
->audio_channels
> 0) {
125 if (film
->audio_bits
== 8)
126 film
->audio_type
= AV_CODEC_ID_PCM_S8_PLANAR
;
127 else if (film
->audio_bits
== 16)
128 film
->audio_type
= AV_CODEC_ID_PCM_S16BE_PLANAR
;
130 film
->audio_type
= AV_CODEC_ID_NONE
;
132 film
->audio_type
= AV_CODEC_ID_NONE
;
135 if (AV_RB32(&scratch
[0]) != FDSC_TAG
)
136 return AVERROR_INVALIDDATA
;
138 if (AV_RB32(&scratch
[8]) == CVID_TAG
) {
139 film
->video_type
= AV_CODEC_ID_CINEPAK
;
140 } else if (AV_RB32(&scratch
[8]) == RAW_TAG
) {
141 film
->video_type
= AV_CODEC_ID_RAWVIDEO
;
143 film
->video_type
= AV_CODEC_ID_NONE
;
146 /* initialize the decoder streams */
147 if (film
->video_type
) {
148 st
= avformat_new_stream(s
, NULL
);
150 return AVERROR(ENOMEM
);
151 film
->video_stream_index
= st
->index
;
152 st
->codec
->codec_type
= AVMEDIA_TYPE_VIDEO
;
153 st
->codec
->codec_id
= film
->video_type
;
154 st
->codec
->codec_tag
= 0; /* no fourcc */
155 st
->codec
->width
= AV_RB32(&scratch
[16]);
156 st
->codec
->height
= AV_RB32(&scratch
[12]);
158 if (film
->video_type
== AV_CODEC_ID_RAWVIDEO
) {
159 if (scratch
[20] == 24) {
160 st
->codec
->pix_fmt
= AV_PIX_FMT_RGB24
;
162 av_log(s
, AV_LOG_ERROR
, "raw video is using unhandled %dbpp\n", scratch
[20]);
168 if (film
->audio_type
) {
169 st
= avformat_new_stream(s
, NULL
);
171 return AVERROR(ENOMEM
);
172 film
->audio_stream_index
= st
->index
;
173 st
->codec
->codec_type
= AVMEDIA_TYPE_AUDIO
;
174 st
->codec
->codec_id
= film
->audio_type
;
175 st
->codec
->codec_tag
= 1;
176 st
->codec
->channels
= film
->audio_channels
;
177 st
->codec
->sample_rate
= film
->audio_samplerate
;
179 if (film
->audio_type
== AV_CODEC_ID_ADPCM_ADX
) {
180 st
->codec
->bits_per_coded_sample
= 18 * 8 / 32;
181 st
->codec
->block_align
= st
->codec
->channels
* 18;
182 st
->need_parsing
= AVSTREAM_PARSE_FULL
;
184 st
->codec
->bits_per_coded_sample
= film
->audio_bits
;
185 st
->codec
->block_align
= st
->codec
->channels
*
186 st
->codec
->bits_per_coded_sample
/ 8;
189 st
->codec
->bit_rate
= st
->codec
->channels
* st
->codec
->sample_rate
*
190 st
->codec
->bits_per_coded_sample
;
193 /* load the sample table */
194 if (avio_read(pb
, scratch
, 16) != 16)
196 if (AV_RB32(&scratch
[0]) != STAB_TAG
)
197 return AVERROR_INVALIDDATA
;
198 film
->base_clock
= AV_RB32(&scratch
[8]);
199 film
->sample_count
= AV_RB32(&scratch
[12]);
200 if(film
->sample_count
>= UINT_MAX
/ sizeof(film_sample
))
202 film
->sample_table
= av_malloc(film
->sample_count
* sizeof(film_sample
));
203 if (!film
->sample_table
)
204 return AVERROR(ENOMEM
);
206 for (i
= 0; i
< s
->nb_streams
; i
++) {
208 if (st
->codec
->codec_type
== AVMEDIA_TYPE_VIDEO
)
209 avpriv_set_pts_info(st
, 33, 1, film
->base_clock
);
211 avpriv_set_pts_info(st
, 64, 1, film
->audio_samplerate
);
214 audio_frame_counter
= 0;
215 for (i
= 0; i
< film
->sample_count
; i
++) {
216 /* load the next sample record and transfer it to an internal struct */
217 if (avio_read(pb
, scratch
, 16) != 16) {
221 film
->sample_table
[i
].sample_offset
=
222 data_offset
+ AV_RB32(&scratch
[0]);
223 film
->sample_table
[i
].sample_size
= AV_RB32(&scratch
[4]);
224 if (film
->sample_table
[i
].sample_size
> INT_MAX
/ 4) {
225 ret
= AVERROR_INVALIDDATA
;
228 if (AV_RB32(&scratch
[8]) == 0xFFFFFFFF) {
229 film
->sample_table
[i
].stream
= film
->audio_stream_index
;
230 film
->sample_table
[i
].pts
= audio_frame_counter
;
232 if (film
->audio_type
== AV_CODEC_ID_ADPCM_ADX
)
233 audio_frame_counter
+= (film
->sample_table
[i
].sample_size
* 32 /
234 (18 * film
->audio_channels
));
235 else if (film
->audio_type
!= AV_CODEC_ID_NONE
)
236 audio_frame_counter
+= (film
->sample_table
[i
].sample_size
/
237 (film
->audio_channels
* film
->audio_bits
/ 8));
239 film
->sample_table
[i
].stream
= film
->video_stream_index
;
240 film
->sample_table
[i
].pts
= AV_RB32(&scratch
[8]) & 0x7FFFFFFF;
241 film
->sample_table
[i
].keyframe
= (scratch
[8] & 0x80) ? 0 : 1;
245 film
->current_sample
= 0;
253 static int film_read_packet(AVFormatContext
*s
,
256 FilmDemuxContext
*film
= s
->priv_data
;
257 AVIOContext
*pb
= s
->pb
;
261 if (film
->current_sample
>= film
->sample_count
)
264 sample
= &film
->sample_table
[film
->current_sample
];
266 /* position the stream (will probably be there anyway) */
267 avio_seek(pb
, sample
->sample_offset
, SEEK_SET
);
270 ret
= av_get_packet(pb
, pkt
, sample
->sample_size
);
271 if (ret
!= sample
->sample_size
)
274 pkt
->stream_index
= sample
->stream
;
275 pkt
->pts
= sample
->pts
;
277 film
->current_sample
++;
282 AVInputFormat ff_segafilm_demuxer
= {
284 .long_name
= NULL_IF_CONFIG_SMALL("Sega FILM / CPK"),
285 .priv_data_size
= sizeof(FilmDemuxContext
),
286 .read_probe
= film_probe
,
287 .read_header
= film_read_header
,
288 .read_packet
= film_read_packet
,
289 .read_close
= film_read_close
,