FFmpeg
Loading...
Searching...
No Matches
vqf.c
Go to the documentation of this file.
1/*
2 * VQF demuxer
3 * Copyright (c) 2009 Vitor Sessak
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
22#include "avformat.h"
23#include "avio_internal.h"
24#include "demux.h"
25#include "internal.h"
27#include "libavutil/dict.h"
29#include "libavutil/mem.h"
30#include "metadata.h"
31
37
38static int vqf_probe(const AVProbeData *probe_packet)
39{
40 if (AV_RL32(probe_packet->buf) != MKTAG('T','W','I','N'))
41 return 0;
42
43 if (!memcmp(probe_packet->buf + 4, "97012000", 8))
44 return AVPROBE_SCORE_MAX;
45
46 if (!memcmp(probe_packet->buf + 4, "00052200", 8))
47 return AVPROBE_SCORE_MAX;
48
49 if (AV_RL32(probe_packet->buf + 12) > (1<<27))
51
53}
54
55static int add_metadata(AVFormatContext *s, uint32_t tag,
56 unsigned int tag_len, unsigned int remaining)
57{
58 int len = FFMIN(tag_len, remaining);
59 char *buf, key[5] = {0};
60 int ret;
61
62 if (len == UINT_MAX)
64
65 buf = av_malloc(len+1);
66 if (!buf)
67 return AVERROR(ENOMEM);
68
69 ret = ffio_read_size(s->pb, buf, len);
70 if (ret < 0) {
71 av_free(buf);
72 return ret;
73 }
74 buf[len] = 0;
75 AV_WL32(key, tag);
76 return av_dict_set(&s->metadata, key, buf, AV_DICT_DONT_STRDUP_VAL);
77}
78
80 { "(c) ", "copyright" },
81 { "ARNG", "arranger" },
82 { "AUTH", "author" },
83 { "BAND", "band" },
84 { "CDCT", "conductor" },
85 { "COMT", "comment" },
86 { "FILE", "filename" },
87 { "GENR", "genre" },
88 { "LABL", "publisher" },
89 { "MUSC", "composer" },
90 { "NAME", "title" },
91 { "NOTE", "note" },
92 { "PROD", "producer" },
93 { "PRSN", "personnel" },
94 { "REMX", "remixer" },
95 { "SING", "singer" },
96 { "TRCK", "track" },
97 { "WORD", "words" },
98 { 0 },
99};
100
102{
103 VqfContext *c = s->priv_data;
105 int chunk_tag;
106 int rate_flag = -1;
107 int header_size;
108 int read_bitrate = 0;
109 int size, ret;
110 uint8_t comm_chunk[12];
111
112 if (!st)
113 return AVERROR(ENOMEM);
114
115 avio_skip(s->pb, 12);
116
117 header_size = avio_rb32(s->pb);
118
119 if (header_size < 0)
120 return AVERROR_INVALIDDATA;
121
124 st->start_time = 0;
125
126 do {
127 int len;
128 chunk_tag = avio_rl32(s->pb);
129
130 if (chunk_tag == MKTAG('D','A','T','A'))
131 break;
132
133 len = avio_rb32(s->pb);
134
135 if ((unsigned) len > INT_MAX/2 || header_size < 8) {
136 av_log(s, AV_LOG_ERROR, "Malformed header\n");
137 return -1;
138 }
139
140 header_size -= 8;
141
142 switch(chunk_tag){
143 case MKTAG('C','O','M','M'):
144 if (len < 12)
145 return AVERROR_INVALIDDATA;
146
147 ret = ffio_read_size(s->pb, comm_chunk, 12);
148 if (ret < 0)
149 return ret;
150 st->codecpar->ch_layout.nb_channels = AV_RB32(comm_chunk) + 1;
151 read_bitrate = AV_RB32(comm_chunk + 4);
152 rate_flag = AV_RB32(comm_chunk + 8);
153 avio_skip(s->pb, len-12);
154
155 if (st->codecpar->ch_layout.nb_channels <= 0) {
156 av_log(s, AV_LOG_ERROR, "Invalid number of channels\n");
157 return AVERROR_INVALIDDATA;
158 }
159
160 st->codecpar->bit_rate = (int64_t)read_bitrate * 1000;
161 break;
162 case MKTAG('D','S','I','Z'): // size of compressed data
163 {
164 av_dict_set_int(&s->metadata, "size", avio_rb32(s->pb), 0);
165 }
166 break;
167 case MKTAG('Y','E','A','R'): // recording date
168 case MKTAG('E','N','C','D'): // compression date
169 case MKTAG('E','X','T','R'): // reserved
170 case MKTAG('_','Y','M','H'): // reserved
171 case MKTAG('_','N','T','T'): // reserved
172 case MKTAG('_','I','D','3'): // reserved for ID3 tags
173 avio_skip(s->pb, FFMIN(len, header_size));
174 break;
175 default:
176 ret = add_metadata(s, chunk_tag, len, header_size);
177 if (ret < 0)
178 return ret;
179 break;
180 }
181
182 header_size -= len;
183
184 } while (header_size >= 0 && !avio_feof(s->pb));
185
186 switch (rate_flag) {
187 case -1:
188 av_log(s, AV_LOG_ERROR, "COMM tag not found!\n");
189 return -1;
190 case 44:
191 st->codecpar->sample_rate = 44100;
192 break;
193 case 22:
194 st->codecpar->sample_rate = 22050;
195 break;
196 case 11:
197 st->codecpar->sample_rate = 11025;
198 break;
199 default:
200 if (rate_flag < 8 || rate_flag > 44) {
201 av_log(s, AV_LOG_ERROR, "Invalid rate flag %d\n", rate_flag);
202 return AVERROR_INVALIDDATA;
203 }
204 st->codecpar->sample_rate = rate_flag*1000;
205 break;
206 }
207
208 if (read_bitrate / st->codecpar->ch_layout.nb_channels < 8 ||
209 read_bitrate / st->codecpar->ch_layout.nb_channels > 48) {
210 av_log(s, AV_LOG_ERROR, "Invalid bitrate per channel %d\n",
211 read_bitrate / st->codecpar->ch_layout.nb_channels);
212 return AVERROR_INVALIDDATA;
213 }
214
215 switch (((st->codecpar->sample_rate/1000) << 8) +
216 read_bitrate/st->codecpar->ch_layout.nb_channels) {
217 case (11<<8) + 8 :
218 case (8 <<8) + 8 :
219 case (11<<8) + 10:
220 case (22<<8) + 32:
221 size = 512;
222 break;
223 case (16<<8) + 16:
224 case (22<<8) + 20:
225 case (22<<8) + 24:
226 size = 1024;
227 break;
228 case (44<<8) + 40:
229 case (44<<8) + 48:
230 size = 2048;
231 break;
232 default:
233 av_log(s, AV_LOG_ERROR, "Mode not supported: %d Hz, %"PRId64" kb/s.\n",
235 return -1;
236 }
237 c->frame_bit_len = st->codecpar->bit_rate*size/st->codecpar->sample_rate;
239
240 /* put first 12 bytes of COMM chunk in extradata */
241 if ((ret = ff_alloc_extradata(st->codecpar, 12)) < 0)
242 return ret;
243 memcpy(st->codecpar->extradata, comm_chunk, 12);
244
246
247 return 0;
248}
249
251{
252 VqfContext *c = s->priv_data;
253 int ret;
254 int size = (c->frame_bit_len - c->remaining_bits + 7)>>3;
255
256 if ((ret = av_new_packet(pkt, size + 2)) < 0)
257 return ret;
258
259 pkt->pos = avio_tell(s->pb);
260 pkt->stream_index = 0;
261 pkt->duration = 1;
262
263 pkt->data[0] = 8 - c->remaining_bits; // Number of bits to skip
264 pkt->data[1] = c->last_frame_bits;
265 ret = ffio_read_size(s->pb, pkt->data + 2, size);
266 if (ret < 0)
267 return ret;
268
269 c->last_frame_bits = pkt->data[size+1];
270 c->remaining_bits = (size << 3) - c->frame_bit_len + c->remaining_bits;
271
272 return 0;
273}
274
276 int stream_index, int64_t timestamp, int flags)
277{
278 VqfContext *c = s->priv_data;
279 AVStream *st;
280 int64_t ret;
281 int64_t pos;
282
283 st = s->streams[stream_index];
284 pos = av_rescale_rnd(timestamp * st->codecpar->bit_rate,
285 st->time_base.num,
286 st->time_base.den * (int64_t)c->frame_bit_len,
289 pos *= c->frame_bit_len;
290
293
294 if ((ret = avio_seek(s->pb, ((pos-7) >> 3) + ffformatcontext(s)->data_offset, SEEK_SET)) < 0)
295 return ret;
296
297 c->remaining_bits = -7 - ((pos-7)&7);
298 return 0;
299}
300
302 .p.name = "vqf",
303 .p.long_name = NULL_IF_CONFIG_SMALL("Nippon Telegraph and Telephone Corporation (NTT) TwinVQ"),
304 .p.extensions = "vqf,vql,vqe",
305 .priv_data_size = sizeof(VqfContext),
310};
const FFInputFormat ff_vqf_demuxer
Definition vqf.c:301
void avpriv_set_pts_info(AVStream *st, int pts_wrap_bits, unsigned int pts_num, unsigned int pts_den)
Set the time base and wrapping info for a given stream.
Definition avformat.c:834
Main libavformat public API header.
#define AVPROBE_SCORE_MAX
maximum score
Definition avformat.h:483
#define AVPROBE_SCORE_EXTENSION
score for file extension
Definition avformat.h:481
#define AVSEEK_FLAG_BACKWARD
seek backward
Definition avformat.h:2616
int64_t avio_seek(AVIOContext *s, int64_t offset, int whence)
fseek() equivalent for AVIOContext.
Definition aviobuf.c:236
int avio_feof(AVIOContext *s)
Similar to feof() but also returns nonzero on read errors.
Definition aviobuf.c:349
static av_always_inline int64_t avio_tell(AVIOContext *s)
ftell() equivalent for AVIOContext.
Definition avio.h:494
int64_t avio_skip(AVIOContext *s, int64_t offset)
Skip given number of bytes forward.
Definition aviobuf.c:321
unsigned int avio_rl32(AVIOContext *s)
Definition aviobuf.c:733
unsigned int avio_rb32(AVIOContext *s)
Definition aviobuf.c:764
int ffio_read_size(AVIOContext *s, unsigned char *buf, int size)
Read size bytes from AVIOContext into buf.
Definition aviobuf.c:665
static int read_packet(void *opaque, uint8_t *buf, int buf_size)
#define flags(name, subs,...)
Definition cbs_h264.c:74
#define s(width, name)
Definition cbs_vp9.c:198
static int read_probe(const AVProbeData *p)
Definition cdg.c:30
#define NULL
Definition coverity.c:32
long long int64_t
Definition coverity.c:34
static AVPacket * pkt
Public dictionary API.
const char * key
static int read_header(FFV1Context *f, RangeCoder *c)
Definition ffv1dec.c:578
@ AV_CODEC_ID_TWINVQ
Definition codec_id.h:496
int av_new_packet(AVPacket *pkt, int size)
Allocate the payload of a packet and initialize its fields with default values.
Definition packet.c:98
AVStream * avformat_new_stream(AVFormatContext *s, const struct AVCodec *c)
Add a new stream to a media file.
#define AV_DICT_DONT_STRDUP_VAL
Take ownership of a value that's been allocated with av_malloc() or another memory allocation functio...
Definition dict.h:79
int av_dict_set(AVDictionary **pm, const char *key, const char *value, int flags)
Set the given entry in *pm, overwriting an existing entry.
Definition dict.c:86
int av_dict_set_int(AVDictionary **pm, const char *key, int64_t value, int flags)
Convenience wrapper for av_dict_set() that converts the value to a string and stores it.
Definition dict.c:177
#define AVERROR_INVALIDDATA
Invalid data found when processing input.
Definition error.h:61
#define AVERROR(e)
Definition error.h:45
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition log.h:210
int64_t av_rescale(int64_t a, int64_t b, int64_t c)
Rescale a 64-bit integer with rounding to nearest.
int64_t av_rescale_rnd(int64_t a, int64_t b, int64_t c, enum AVRounding rnd)
Rescale a 64-bit integer with specified rounding.
Definition mathematics.c:58
@ AV_ROUND_DOWN
Round toward -infinity.
@ AV_ROUND_UP
Round toward +infinity.
@ AVMEDIA_TYPE_AUDIO
Definition avutil.h:201
#define AV_WL32(p, v)
#define AV_RL32(p)
#define AV_RB32(p)
static av_always_inline FFStream * ffstream(AVStream *st)
Definition internal.h:365
int ff_alloc_extradata(AVCodecParameters *par, int size)
Allocate extradata with additional AV_INPUT_BUFFER_PADDING_SIZE at end which is always set to 0.
Definition utils.c:237
static av_always_inline FFFormatContext * ffformatcontext(AVFormatContext *s)
Definition internal.h:130
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification.
Definition internal.h:88
static int read_seek(AVFormatContext *ctx, int stream_index, int64_t timestamp, int flags)
Definition libcdio.c:151
#define FFMIN(a, b)
Definition macros.h:49
#define MKTAG(a, b, c, d)
Definition macros.h:55
Memory handling functions.
void ff_metadata_conv_ctx(AVFormatContext *ctx, const AVMetadataConv *d_conv, const AVMetadataConv *s_conv)
Definition metadata.c:59
internal metadata API header see avformat.h or the public API!
uint32_t tag
Definition movenc.c:2087
#define av_malloc(s)
Definition ops_static.c:52
unsigned int pos
Definition spdifenc.c:431
int nb_channels
Number of channels in this layout.
AVChannelLayout ch_layout
The channel layout and number of channels.
Definition codec_par.h:207
int64_t bit_rate
The average bitrate of the encoded data (in bits per second).
Definition codec_par.h:99
enum AVMediaType codec_type
General type of the encoded data.
Definition codec_par.h:53
uint8_t * extradata
Extra binary data needed for initializing the decoder, codec-dependent.
Definition codec_par.h:71
enum AVCodecID codec_id
Specific type of the encoded data (the codec used).
Definition codec_par.h:57
int sample_rate
The number of audio samples per second.
Definition codec_par.h:213
Format I/O context.
Definition avformat.h:1333
This structure stores compressed data.
Definition packet.h:580
This structure contains the data a format has to probe a file.
Definition avformat.h:471
unsigned char * buf
Buffer must have AVPROBE_PADDING_SIZE of extra allocated bytes filled with zero.
Definition avformat.h:473
int num
Numerator.
Definition rational.h:59
int den
Denominator.
Definition rational.h:60
Stream structure.
Definition avformat.h:766
AVCodecParameters * codecpar
Codec parameters associated with this stream.
Definition avformat.h:789
int64_t start_time
Decoding: pts of the first frame of the stream in presentation order, in stream time base.
Definition avformat.h:815
AVRational time_base
This is the fundamental unit of time (in seconds) in terms of which frame timestamps are represented.
Definition avformat.h:805
int64_t cur_dts
Definition internal.h:360
int remaining_bits
Definition vqf.c:35
int frame_bit_len
Definition vqf.c:33
uint8_t last_frame_bits
Definition vqf.c:34
#define av_free(p)
#define av_log(a,...)
int size
int len
static int vqf_read_seek(AVFormatContext *s, int stream_index, int64_t timestamp, int flags)
Definition vqf.c:275
static int vqf_read_packet(AVFormatContext *s, AVPacket *pkt)
Definition vqf.c:250
static const AVMetadataConv vqf_metadata_conv[]
Definition vqf.c:79
static int vqf_probe(const AVProbeData *probe_packet)
Definition vqf.c:38
static int add_metadata(AVFormatContext *s, uint32_t tag, unsigned int tag_len, unsigned int remaining)
Definition vqf.c:55
static int vqf_read_header(AVFormatContext *s)
Definition vqf.c:101
static double c[64]