]> git.sesse.net Git - vlc/blob - modules/codec/a52.c
Added support for eac3 in a52 packetizer.
[vlc] / modules / codec / a52.c
1 /*****************************************************************************
2  * a52.c: parse A/52 audio sync info and packetize the stream
3  *****************************************************************************
4  * Copyright (C) 2001-2002 the VideoLAN team
5  * $Id$
6  *
7  * Authors: Stéphane Borel <stef@via.ecp.fr>
8  *          Christophe Massiot <massiot@via.ecp.fr>
9  *          Gildas Bazin <gbazin@videolan.org>
10  *
11  * This program is free software; you can redistribute it and/or modify
12  * it under the terms of the GNU General Public License as published by
13  * the Free Software Foundation; either version 2 of the License, or
14  * (at your option) any later version.
15  *
16  * This program is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  * GNU General Public License for more details.
20  *
21  * You should have received a copy of the GNU General Public License
22  * along with this program; if not, write to the Free Software
23  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
24  *****************************************************************************/
25
26 /*****************************************************************************
27  * Preamble
28  *****************************************************************************/
29 #ifdef HAVE_CONFIG_H
30 # include "config.h"
31 #endif
32
33 #include <vlc_common.h>
34 #include <vlc_plugin.h>
35 #include <vlc_codec.h>
36 #include <vlc_aout.h>
37 #include <vlc_input.h>
38 #include <vlc_block_helper.h>
39 #include <vlc_bits.h>
40
41 /*****************************************************************************
42  * Module descriptor
43  *****************************************************************************/
44 static int  OpenDecoder   ( vlc_object_t * );
45 static int  OpenPacketizer( vlc_object_t * );
46 static void CloseCommon   ( vlc_object_t * );
47
48 vlc_module_begin();
49     set_description( N_("A/52 parser") );
50     set_capability( "decoder", 100 );
51     set_callbacks( OpenDecoder, CloseCommon );
52     set_category( CAT_INPUT );
53     set_subcategory( SUBCAT_INPUT_ACODEC );
54
55     add_submodule();
56     set_description( N_("A/52 audio packetizer") );
57     set_capability( "packetizer", 10 );
58     set_callbacks( OpenPacketizer, CloseCommon );
59 vlc_module_end();
60
61 /*****************************************************************************
62  * decoder_sys_t : decoder descriptor
63  *****************************************************************************/
64
65 #define A52_HEADER_SIZE 7
66
67 struct decoder_sys_t
68 {
69     /* Module mode */
70     bool b_packetizer;
71
72     /*
73      * Input properties
74      */
75     int i_state;
76
77     block_bytestream_t bytestream;
78
79     /*
80      * Common properties
81      */
82     audio_date_t   end_date;
83
84     mtime_t i_pts;
85     int i_frame_size, i_bit_rate;
86     unsigned int i_rate, i_channels, i_channels_conf;
87
88     int i_input_rate;
89 };
90
91 enum {
92
93     STATE_NOSYNC,
94     STATE_SYNC,
95     STATE_HEADER,
96     STATE_NEXT_SYNC,
97     STATE_GET_DATA,
98     STATE_SEND_DATA
99 };
100
101 /****************************************************************************
102  * Local prototypes
103  ****************************************************************************/
104 static void *DecodeBlock  ( decoder_t *, block_t ** );
105
106 static int  SyncInfo      ( const uint8_t *, unsigned int *, unsigned int *,
107                             unsigned int *, int * );
108
109 static uint8_t       *GetOutBuffer ( decoder_t *, void ** );
110 static aout_buffer_t *GetAoutBuffer( decoder_t * );
111 static block_t       *GetSoutBuffer( decoder_t * );
112
113 /*****************************************************************************
114  * OpenCommon: probe the decoder/packetizer and return score
115  *****************************************************************************/
116 static int OpenCommon( vlc_object_t *p_this, bool b_packetizer )
117 {
118     decoder_t *p_dec = (decoder_t*)p_this;
119     decoder_sys_t *p_sys;
120     vlc_fourcc_t i_codec;
121
122     switch( p_dec->fmt_in.i_codec )
123     {
124     case VLC_FOURCC('a','5','2',' '):
125     case VLC_FOURCC('a','5','2','b'):
126         i_codec = VLC_FOURCC('a','5','2',' ');
127         break;
128     case VLC_FOURCC('e','a','c','3'):
129         /* XXX ugly hack, a52 does not support eac3 so no eac3 pass-through
130          * support */
131         if( !b_packetizer )
132             return VLC_EGENERIC;
133         i_codec = VLC_FOURCC('e','a','c','3');
134         break;
135     default:
136         return VLC_EGENERIC;
137     }
138
139     /* Allocate the memory needed to store the decoder's structure */
140     if( ( p_dec->p_sys = p_sys =
141           (decoder_sys_t *)malloc(sizeof(decoder_sys_t)) ) == NULL )
142         return VLC_ENOMEM;
143
144     /* Misc init */
145     p_sys->b_packetizer = b_packetizer;
146     p_sys->i_state = STATE_NOSYNC;
147     aout_DateSet( &p_sys->end_date, 0 );
148
149     p_sys->bytestream = block_BytestreamInit();
150     p_sys->i_input_rate = INPUT_RATE_DEFAULT;
151
152     /* Set output properties */
153     p_dec->fmt_out.i_cat = AUDIO_ES;
154     p_dec->fmt_out.i_codec = i_codec;
155     p_dec->fmt_out.audio.i_rate = 0; /* So end_date gets initialized */
156
157     /* Set callback */
158     if( b_packetizer )
159         p_dec->pf_packetize    = (block_t *(*)(decoder_t *, block_t **))
160             DecodeBlock;
161     else
162         p_dec->pf_decode_audio = (aout_buffer_t *(*)(decoder_t *, block_t **))
163             DecodeBlock;
164     return VLC_SUCCESS;
165 }
166
167 static int OpenDecoder( vlc_object_t *p_this )
168 {
169     return OpenCommon( p_this, false );
170 }
171
172 static int OpenPacketizer( vlc_object_t *p_this )
173 {
174     return OpenCommon( p_this, true );
175 }
176
177 /****************************************************************************
178  * DecodeBlock: the whole thing
179  ****************************************************************************
180  * This function is called just after the thread is launched.
181  ****************************************************************************/
182 static void *DecodeBlock( decoder_t *p_dec, block_t **pp_block )
183 {
184     decoder_sys_t *p_sys = p_dec->p_sys;
185     uint8_t p_header[A52_HEADER_SIZE];
186     uint8_t *p_buf;
187     void *p_out_buffer;
188
189     if( !pp_block || !*pp_block ) return NULL;
190
191     if( (*pp_block)->i_flags&(BLOCK_FLAG_DISCONTINUITY|BLOCK_FLAG_CORRUPTED) )
192     {
193         if( (*pp_block)->i_flags&BLOCK_FLAG_CORRUPTED )
194         {
195             p_sys->i_state = STATE_NOSYNC;
196             block_BytestreamFlush( &p_sys->bytestream );
197         }
198 //        aout_DateSet( &p_sys->end_date, 0 );
199         block_Release( *pp_block );
200         return NULL;
201     }
202
203     if( !aout_DateGet( &p_sys->end_date ) && !(*pp_block)->i_pts )
204     {
205         /* We've just started the stream, wait for the first PTS. */
206         block_Release( *pp_block );
207         return NULL;
208     }
209
210     if( (*pp_block)->i_rate > 0 )
211         p_sys->i_input_rate = (*pp_block)->i_rate;
212
213     block_BytestreamPush( &p_sys->bytestream, *pp_block );
214
215     while( 1 )
216     {
217         switch( p_sys->i_state )
218         {
219         case STATE_NOSYNC:
220             while( block_PeekBytes( &p_sys->bytestream, p_header, 2 )
221                    == VLC_SUCCESS )
222             {
223                 if( p_header[0] == 0x0b && p_header[1] == 0x77 )
224                 {
225                     p_sys->i_state = STATE_SYNC;
226                     break;
227                 }
228                 block_SkipByte( &p_sys->bytestream );
229             }
230             if( p_sys->i_state != STATE_SYNC )
231             {
232                 block_BytestreamFlush( &p_sys->bytestream );
233
234                 /* Need more data */
235                 return NULL;
236             }
237
238         case STATE_SYNC:
239             /* New frame, set the Presentation Time Stamp */
240             p_sys->i_pts = p_sys->bytestream.p_block->i_pts;
241             if( p_sys->i_pts != 0 &&
242                 p_sys->i_pts != aout_DateGet( &p_sys->end_date ) )
243             {
244                 aout_DateSet( &p_sys->end_date, p_sys->i_pts );
245             }
246             p_sys->i_state = STATE_HEADER;
247
248         case STATE_HEADER:
249             /* Get A/52 frame header (A52_HEADER_SIZE bytes) */
250             if( block_PeekBytes( &p_sys->bytestream, p_header,
251                                  A52_HEADER_SIZE ) != VLC_SUCCESS )
252             {
253                 /* Need more data */
254                 return NULL;
255             }
256
257             /* Check if frame is valid and get frame info */
258             p_sys->i_frame_size = SyncInfo( p_header,
259                                             &p_sys->i_channels,
260                                             &p_sys->i_channels_conf,
261                                             &p_sys->i_rate,
262                                             &p_sys->i_bit_rate );
263             if( !p_sys->i_frame_size )
264             {
265                 msg_Dbg( p_dec, "emulated sync word" );
266                 block_SkipByte( &p_sys->bytestream );
267                 p_sys->i_state = STATE_NOSYNC;
268                 break;
269             }
270             p_sys->i_state = STATE_NEXT_SYNC;
271
272         case STATE_NEXT_SYNC:
273             /* TODO: If pp_block == NULL, flush the buffer without checking the
274              * next sync word */
275
276             /* Check if next expected frame contains the sync word */
277             if( block_PeekOffsetBytes( &p_sys->bytestream,
278                                        p_sys->i_frame_size, p_header, 2 )
279                 != VLC_SUCCESS )
280             {
281                 /* Need more data */
282                 return NULL;
283             }
284
285             if( p_sys->b_packetizer &&
286                 p_header[0] == 0 && p_header[1] == 0 )
287             {
288                 /* A52 wav files and audio CD's use stuffing */
289                 p_sys->i_state = STATE_GET_DATA;
290                 break;
291             }
292
293             if( p_header[0] != 0x0b || p_header[1] != 0x77 )
294             {
295                 msg_Dbg( p_dec, "emulated sync word "
296                          "(no sync on following frame)" );
297                 p_sys->i_state = STATE_NOSYNC;
298                 block_SkipByte( &p_sys->bytestream );
299                 break;
300             }
301             p_sys->i_state = STATE_SEND_DATA;
302             break;
303
304         case STATE_GET_DATA:
305             /* Make sure we have enough data.
306              * (Not useful if we went through NEXT_SYNC) */
307             if( block_WaitBytes( &p_sys->bytestream,
308                                  p_sys->i_frame_size ) != VLC_SUCCESS )
309             {
310                 /* Need more data */
311                 return NULL;
312             }
313             p_sys->i_state = STATE_SEND_DATA;
314
315         case STATE_SEND_DATA:
316             if( !(p_buf = GetOutBuffer( p_dec, &p_out_buffer )) )
317             {
318                 //p_dec->b_error = true;
319                 return NULL;
320             }
321
322             /* Copy the whole frame into the buffer. When we reach this point
323              * we already know we have enough data available. */
324             block_GetBytes( &p_sys->bytestream, p_buf, p_sys->i_frame_size );
325
326             /* Make sure we don't reuse the same pts twice */
327             if( p_sys->i_pts == p_sys->bytestream.p_block->i_pts )
328                 p_sys->i_pts = p_sys->bytestream.p_block->i_pts = 0;
329
330             /* So p_block doesn't get re-added several times */
331             *pp_block = block_BytestreamPop( &p_sys->bytestream );
332
333             p_sys->i_state = STATE_NOSYNC;
334
335             return p_out_buffer;
336         }
337     }
338
339     return NULL;
340 }
341
342 /*****************************************************************************
343  * CloseCommon: clean up the decoder
344  *****************************************************************************/
345 static void CloseCommon( vlc_object_t *p_this )
346 {
347     decoder_t *p_dec = (decoder_t*)p_this;
348     decoder_sys_t *p_sys = p_dec->p_sys;
349
350     block_BytestreamRelease( &p_sys->bytestream );
351
352     free( p_sys );
353 }
354
355 /*****************************************************************************
356  * GetOutBuffer:
357  *****************************************************************************/
358 static uint8_t *GetOutBuffer( decoder_t *p_dec, void **pp_out_buffer )
359 {
360     decoder_sys_t *p_sys = p_dec->p_sys;
361     uint8_t *p_buf;
362
363     if( p_dec->fmt_out.audio.i_rate != p_sys->i_rate )
364     {
365         msg_Info( p_dec, "A/52 channels:%d samplerate:%d bitrate:%d",
366                   p_sys->i_channels, p_sys->i_rate, p_sys->i_bit_rate );
367
368         aout_DateInit( &p_sys->end_date, p_sys->i_rate );
369         aout_DateSet( &p_sys->end_date, p_sys->i_pts );
370     }
371
372     p_dec->fmt_out.audio.i_rate     = p_sys->i_rate;
373     p_dec->fmt_out.audio.i_channels = p_sys->i_channels;
374     p_dec->fmt_out.audio.i_bytes_per_frame = p_sys->i_frame_size;
375     p_dec->fmt_out.audio.i_frame_length = A52_FRAME_NB;
376
377     p_dec->fmt_out.audio.i_original_channels = p_sys->i_channels_conf;
378     p_dec->fmt_out.audio.i_physical_channels =
379         p_sys->i_channels_conf & AOUT_CHAN_PHYSMASK;
380
381     p_dec->fmt_out.i_bitrate = p_sys->i_bit_rate;
382
383     if( p_sys->b_packetizer )
384     {
385         block_t *p_sout_buffer = GetSoutBuffer( p_dec );
386         p_buf = p_sout_buffer ? p_sout_buffer->p_buffer : NULL;
387         *pp_out_buffer = p_sout_buffer;
388     }
389     else
390     {
391         aout_buffer_t *p_aout_buffer = GetAoutBuffer( p_dec );
392         p_buf = p_aout_buffer ? p_aout_buffer->p_buffer : NULL;
393         *pp_out_buffer = p_aout_buffer;
394     }
395
396     return p_buf;
397 }
398
399 /*****************************************************************************
400  * GetAoutBuffer:
401  *****************************************************************************/
402 static aout_buffer_t *GetAoutBuffer( decoder_t *p_dec )
403 {
404     decoder_sys_t *p_sys = p_dec->p_sys;
405     aout_buffer_t *p_buf;
406
407     p_buf = p_dec->pf_aout_buffer_new( p_dec, A52_FRAME_NB  );
408     if( p_buf == NULL ) return NULL;
409
410     p_buf->start_date = aout_DateGet( &p_sys->end_date );
411     p_buf->end_date = aout_DateIncrement( &p_sys->end_date,
412                                           A52_FRAME_NB * p_sys->i_input_rate / INPUT_RATE_DEFAULT );
413
414     return p_buf;
415 }
416
417 /*****************************************************************************
418  * GetSoutBuffer:
419  *****************************************************************************/
420 static block_t *GetSoutBuffer( decoder_t *p_dec )
421 {
422     decoder_sys_t *p_sys = p_dec->p_sys;
423     block_t *p_block;
424
425     p_block = block_New( p_dec, p_sys->i_frame_size );
426     if( p_block == NULL ) return NULL;
427
428     p_block->i_pts = p_block->i_dts = aout_DateGet( &p_sys->end_date );
429
430     p_block->i_length =
431         aout_DateIncrement( &p_sys->end_date,
432                             A52_FRAME_NB * p_sys->i_input_rate / INPUT_RATE_DEFAULT ) -
433             p_block->i_pts;
434
435     return p_block;
436 }
437
438 /* Tables */
439 static const struct
440 {
441     unsigned int i_count;
442     unsigned int i_configuration;
443 } p_acmod[8] = {
444     { 2, AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_DUALMONO },   /* Dual-channel 1+1 */
445     { 1, AOUT_CHAN_CENTER },                                        /* Mono 1/0 */
446     { 2, AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT },                        /* Stereo 2/0 */
447     { 3, AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER },     /* 3F 3/0 */
448     { 3, AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_REARCENTER }, /* 2F1R 2/1 */
449     { 4, AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER |
450          AOUT_CHAN_REARCENTER },                                    /* 3F1R 3/1 */
451     { 5, AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT |
452          AOUT_CHAN_REARLEFT | AOUT_CHAN_REARRIGHT },                /* 2F2R 2/2 */
453     { 6, AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER |
454          AOUT_CHAN_REARLEFT | AOUT_CHAN_REARRIGHT },                /* 3F2R 3/2 */
455 };
456
457 /**
458  * It parse AC3 sync info.
459  *
460  * This code is borrowed from liba52 by Aaron Holtzman & Michel Lespinasse,
461  * since we don't want to oblige S/PDIF people to use liba52 just to get
462  * their SyncInfo...
463  */
464 static int SyncInfoAC3( const uint8_t *p_buf,
465                         unsigned int *pi_channels,
466                         unsigned int *pi_channels_conf,
467                         unsigned int *pi_sample_rate, int *pi_bit_rate )
468 {
469     static const uint8_t halfrate[12] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3 };
470     static const int rate[] = { 32,  40,  48,  56,  64,  80,  96, 112,
471                                 128, 160, 192, 224, 256, 320, 384, 448,
472                                 512, 576, 640 };
473     static const uint8_t lfeon[8] = { 0x10, 0x10, 0x04, 0x04,
474                                       0x04, 0x01, 0x04, 0x01 };
475     int frmsizecod;
476     int bitrate;
477     int half;
478     int acmod;
479
480     /* */
481     half = halfrate[p_buf[5] >> 3];
482
483     /* acmod, dsurmod and lfeon */
484     acmod = p_buf[6] >> 5;
485     if ( (p_buf[6] & 0xf8) == 0x50 )
486     {
487         /* Dolby surround = stereo + Dolby */
488         *pi_channels = 2;
489         *pi_channels_conf = AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT
490                             | AOUT_CHAN_DOLBYSTEREO;
491     }
492     else
493     {
494         *pi_channels      = p_acmod[acmod].i_count;
495         *pi_channels_conf = p_acmod[acmod].i_configuration;
496     }
497
498     if ( p_buf[6] & lfeon[acmod] )
499     {
500         (*pi_channels)++;
501         *pi_channels_conf |= AOUT_CHAN_LFE;
502     }
503
504     frmsizecod = p_buf[4] & 63;
505     if (frmsizecod >= 38)
506         return 0;
507     bitrate = rate [frmsizecod >> 1];
508     *pi_bit_rate = (bitrate * 1000) >> half;
509
510     switch (p_buf[4] & 0xc0) {
511     case 0:
512         *pi_sample_rate = 48000 >> half;
513         return 4 * bitrate;
514     case 0x40:
515         *pi_sample_rate = 44100 >> half;
516         return 2 * (320 * bitrate / 147 + (frmsizecod & 1));
517     case 0x80:
518         *pi_sample_rate = 32000 >> half;
519         return 6 * bitrate;
520     default:
521         return 0;
522     }
523 }
524
525 /**
526  * It parse E-AC3 sync info
527  */
528 static int SyncInfoEAC3( const uint8_t *p_buf,
529                          unsigned int *pi_channels,
530                          unsigned int *pi_channels_conf,
531                          unsigned int *pi_sample_rate, int *pi_bit_rate )
532 {
533     static const int pi_samplerate[3] = { 48000, 44100, 32000 };
534     bs_t s;
535     int i_frame_size;
536     int i_fscod, i_fscod2;
537     int i_numblkscod;
538     int i_acmod, i_lfeon;
539     int i_bytes;
540
541
542     bs_init( &s, (void*)p_buf, A52_HEADER_SIZE );
543     bs_skip( &s, 16 +   /* start code */
544                  2 +    /* stream type */
545                  3 );   /* substream id */
546     i_frame_size = bs_read( &s, 11 );
547     if( i_frame_size < 2 )
548         return 0;
549     i_bytes = 2 * ( i_frame_size + 1 );
550
551     i_fscod = bs_read( &s, 2 );
552     if( i_fscod == 0x03 )
553     {
554         i_fscod2 = bs_read( &s, 2 );
555         if( i_fscod2 == 0X03 )
556             return 0;
557         *pi_sample_rate = pi_samplerate[i_fscod2] / 2;
558         i_numblkscod = 6;
559     }
560     else
561     {
562         static const int pi_blocks[4] = { 1, 2, 3, 6 };
563
564         *pi_sample_rate = pi_samplerate[i_fscod];
565         i_numblkscod = pi_blocks[bs_read( &s, 2 )];
566     }
567
568     i_acmod = bs_read( &s, 3 );
569     i_lfeon = bs_read1( &s );
570
571     *pi_channels      = p_acmod[i_acmod].i_count + i_lfeon;
572     *pi_channels_conf = p_acmod[i_acmod].i_configuration | ( i_lfeon ? AOUT_CHAN_LFE : 0);
573     *pi_bit_rate = 8 * i_bytes * (*pi_sample_rate) / (i_numblkscod * 256);
574
575     return i_bytes;
576 }
577
578 static int SyncInfo( const uint8_t *p_buf,
579                      unsigned int *pi_channels,
580                      unsigned int *pi_channels_conf,
581                      unsigned int *pi_sample_rate, int *pi_bit_rate )
582 {
583     int bsid;
584
585     /* Check synword */
586     if( p_buf[0] != 0x0b || p_buf[1] != 0x77 )
587         return 0;
588
589     /* Check bsid */
590     bsid = p_buf[5] >> 3;
591     if( bsid > 16 )
592         return 0;
593
594     if( bsid <= 10 )
595         return SyncInfoAC3( p_buf, pi_channels, pi_channels_conf,
596                             pi_sample_rate, pi_bit_rate );
597     else
598         return SyncInfoEAC3( p_buf, pi_channels, pi_channels_conf,
599                              pi_sample_rate, pi_bit_rate );
600 }
601