00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "voc.h"
00023
00024
00025 static int voc_probe(AVProbeData *p)
00026 {
00027 int version, check;
00028
00029 if (memcmp(p->buf, voc_magic, sizeof(voc_magic) - 1))
00030 return 0;
00031 version = AV_RL16(p->buf + 22);
00032 check = AV_RL16(p->buf + 24);
00033 if (~version + 0x1234 != check)
00034 return 10;
00035
00036 return AVPROBE_SCORE_MAX;
00037 }
00038
00039 static int voc_read_header(AVFormatContext *s, AVFormatParameters *ap)
00040 {
00041 voc_dec_context_t *voc = s->priv_data;
00042 ByteIOContext *pb = s->pb;
00043 int header_size;
00044 AVStream *st;
00045
00046 url_fskip(pb, 20);
00047 header_size = get_le16(pb) - 22;
00048 if (header_size != 4) {
00049 av_log(s, AV_LOG_ERROR, "unknown header size: %d\n", header_size);
00050 return AVERROR(ENOSYS);
00051 }
00052 url_fskip(pb, header_size);
00053 st = av_new_stream(s, 0);
00054 if (!st)
00055 return AVERROR(ENOMEM);
00056 st->codec->codec_type = CODEC_TYPE_AUDIO;
00057
00058 voc->remaining_size = 0;
00059 return 0;
00060 }
00061
00062 int
00063 voc_get_packet(AVFormatContext *s, AVPacket *pkt, AVStream *st, int max_size)
00064 {
00065 voc_dec_context_t *voc = s->priv_data;
00066 AVCodecContext *dec = st->codec;
00067 ByteIOContext *pb = s->pb;
00068 voc_type_t type;
00069 int size;
00070 int sample_rate = 0;
00071 int channels = 1;
00072
00073 while (!voc->remaining_size) {
00074 type = get_byte(pb);
00075 if (type == VOC_TYPE_EOF)
00076 return AVERROR(EIO);
00077 voc->remaining_size = get_le24(pb);
00078 max_size -= 4;
00079
00080 switch (type) {
00081 case VOC_TYPE_VOICE_DATA:
00082 dec->sample_rate = 1000000 / (256 - get_byte(pb));
00083 if (sample_rate)
00084 dec->sample_rate = sample_rate;
00085 dec->channels = channels;
00086 dec->codec_id = codec_get_id(voc_codec_tags, get_byte(pb));
00087 dec->bits_per_sample = av_get_bits_per_sample(dec->codec_id);
00088 voc->remaining_size -= 2;
00089 max_size -= 2;
00090 channels = 1;
00091 break;
00092
00093 case VOC_TYPE_VOICE_DATA_CONT:
00094 break;
00095
00096 case VOC_TYPE_EXTENDED:
00097 sample_rate = get_le16(pb);
00098 get_byte(pb);
00099 channels = get_byte(pb) + 1;
00100 sample_rate = 256000000 / (channels * (65536 - sample_rate));
00101 voc->remaining_size = 0;
00102 max_size -= 4;
00103 break;
00104
00105 case VOC_TYPE_NEW_VOICE_DATA:
00106 dec->sample_rate = get_le32(pb);
00107 dec->bits_per_sample = get_byte(pb);
00108 dec->channels = get_byte(pb);
00109 dec->codec_id = codec_get_id(voc_codec_tags, get_le16(pb));
00110 url_fskip(pb, 4);
00111 voc->remaining_size -= 12;
00112 max_size -= 12;
00113 break;
00114
00115 default:
00116 url_fskip(pb, voc->remaining_size);
00117 max_size -= voc->remaining_size;
00118 voc->remaining_size = 0;
00119 break;
00120 }
00121 }
00122
00123 dec->bit_rate = dec->sample_rate * dec->bits_per_sample;
00124
00125 if (max_size <= 0)
00126 max_size = 2048;
00127 size = FFMIN(voc->remaining_size, max_size);
00128 voc->remaining_size -= size;
00129 return av_get_packet(pb, pkt, size);
00130 }
00131
00132 static int voc_read_packet(AVFormatContext *s, AVPacket *pkt)
00133 {
00134 return voc_get_packet(s, pkt, s->streams[0], 0);
00135 }
00136
00137 AVInputFormat voc_demuxer = {
00138 "voc",
00139 "Creative Voice File format",
00140 sizeof(voc_dec_context_t),
00141 voc_probe,
00142 voc_read_header,
00143 voc_read_packet,
00144 .codec_tag=(const AVCodecTag*[]){voc_codec_tags, 0},
00145 };