comparison libvorbis.c @ 5875:5a61e8e2f65c libavcodec

Remove libvorbis Vorbis decoding support. Our native decoder is complete and has no known bugs, any remaining issues will hopefully be uncovered now.
author diego
date Sun, 04 Nov 2007 12:55:32 +0000
parents bc4791868c52
children 48759bfbd073
comparison
equal deleted inserted replaced
5874:ce9415dd447a 5875:5a61e8e2f65c
216 oggvorbis_encode_init, 216 oggvorbis_encode_init,
217 oggvorbis_encode_frame, 217 oggvorbis_encode_frame,
218 oggvorbis_encode_close, 218 oggvorbis_encode_close,
219 .capabilities= CODEC_CAP_DELAY, 219 .capabilities= CODEC_CAP_DELAY,
220 } ; 220 } ;
221
222 static int oggvorbis_decode_init(AVCodecContext *avccontext) {
223 OggVorbisContext *context = avccontext->priv_data ;
224 uint8_t *p= avccontext->extradata;
225 int i, hsizes[3];
226 unsigned char *headers[3], *extradata = avccontext->extradata;
227
228 vorbis_info_init(&context->vi) ;
229 vorbis_comment_init(&context->vc) ;
230
231 if(! avccontext->extradata_size || ! p) {
232 av_log(avccontext, AV_LOG_ERROR, "vorbis extradata absent\n");
233 return -1;
234 }
235
236 if(p[0] == 0 && p[1] == 30) {
237 for(i = 0; i < 3; i++){
238 hsizes[i] = bytestream_get_be16(&p);
239 headers[i] = p;
240 p += hsizes[i];
241 }
242 } else if(*p == 2) {
243 unsigned int offset = 1;
244 p++;
245 for(i=0; i<2; i++) {
246 hsizes[i] = 0;
247 while((*p == 0xFF) && (offset < avccontext->extradata_size)) {
248 hsizes[i] += 0xFF;
249 offset++;
250 p++;
251 }
252 if(offset >= avccontext->extradata_size - 1) {
253 av_log(avccontext, AV_LOG_ERROR,
254 "vorbis header sizes damaged\n");
255 return -1;
256 }
257 hsizes[i] += *p;
258 offset++;
259 p++;
260 }
261 hsizes[2] = avccontext->extradata_size - hsizes[0]-hsizes[1]-offset;
262 #if 0
263 av_log(avccontext, AV_LOG_DEBUG,
264 "vorbis header sizes: %d, %d, %d, / extradata_len is %d \n",
265 hsizes[0], hsizes[1], hsizes[2], avccontext->extradata_size);
266 #endif
267 headers[0] = extradata + offset;
268 headers[1] = extradata + offset + hsizes[0];
269 headers[2] = extradata + offset + hsizes[0] + hsizes[1];
270 } else {
271 av_log(avccontext, AV_LOG_ERROR,
272 "vorbis initial header len is wrong: %d\n", *p);
273 return -1;
274 }
275
276 for(i=0; i<3; i++){
277 context->op.b_o_s= i==0;
278 context->op.bytes = hsizes[i];
279 context->op.packet = headers[i];
280 if(vorbis_synthesis_headerin(&context->vi, &context->vc, &context->op)<0){
281 av_log(avccontext, AV_LOG_ERROR, "%d. vorbis header damaged\n", i+1);
282 return -1;
283 }
284 }
285
286 avccontext->channels = context->vi.channels;
287 avccontext->sample_rate = context->vi.rate;
288 avccontext->time_base= (AVRational){1, avccontext->sample_rate};
289
290 vorbis_synthesis_init(&context->vd, &context->vi);
291 vorbis_block_init(&context->vd, &context->vb);
292
293 return 0 ;
294 }
295
296
297 static inline int conv(int samples, float **pcm, char *buf, int channels) {
298 int i, j;
299 ogg_int16_t *ptr, *data = (ogg_int16_t*)buf ;
300 float *mono ;
301
302 for(i = 0 ; i < channels ; i++){
303 ptr = &data[i];
304 mono = pcm[i] ;
305
306 for(j = 0 ; j < samples ; j++) {
307 *ptr = av_clip_int16(mono[j] * 32767.f);
308 ptr += channels;
309 }
310 }
311
312 return 0 ;
313 }
314
315
316 static int oggvorbis_decode_frame(AVCodecContext *avccontext,
317 void *data, int *data_size,
318 uint8_t *buf, int buf_size)
319 {
320 OggVorbisContext *context = avccontext->priv_data ;
321 float **pcm ;
322 ogg_packet *op= &context->op;
323 int samples, total_samples, total_bytes;
324
325 if(!buf_size){
326 //FIXME flush
327 return 0;
328 }
329
330 op->packet = buf;
331 op->bytes = buf_size;
332
333 // av_log(avccontext, AV_LOG_DEBUG, "%d %d %d %"PRId64" %"PRId64" %d %d\n", op->bytes, op->b_o_s, op->e_o_s, op->granulepos, op->packetno, buf_size, context->vi.rate);
334
335 /* for(i=0; i<op->bytes; i++)
336 av_log(avccontext, AV_LOG_DEBUG, "%02X ", op->packet[i]);
337 av_log(avccontext, AV_LOG_DEBUG, "\n");*/
338
339 if(vorbis_synthesis(&context->vb, op) == 0)
340 vorbis_synthesis_blockin(&context->vd, &context->vb) ;
341
342 total_samples = 0 ;
343 total_bytes = 0 ;
344
345 while((samples = vorbis_synthesis_pcmout(&context->vd, &pcm)) > 0) {
346 conv(samples, pcm, (char*)data + total_bytes, context->vi.channels) ;
347 total_bytes += samples * 2 * context->vi.channels ;
348 total_samples += samples ;
349 vorbis_synthesis_read(&context->vd, samples) ;
350 }
351
352 *data_size = total_bytes ;
353 return buf_size ;
354 }
355
356
357 static int oggvorbis_decode_close(AVCodecContext *avccontext) {
358 OggVorbisContext *context = avccontext->priv_data ;
359
360 vorbis_info_clear(&context->vi) ;
361 vorbis_comment_clear(&context->vc) ;
362
363 return 0 ;
364 }
365
366
367 AVCodec libvorbis_decoder = {
368 "libvorbis",
369 CODEC_TYPE_AUDIO,
370 CODEC_ID_VORBIS,
371 sizeof(OggVorbisContext),
372 oggvorbis_decode_init,
373 NULL,
374 oggvorbis_decode_close,
375 oggvorbis_decode_frame,
376 .capabilities= CODEC_CAP_DELAY,
377 } ;