* aout_internal.h : internal defines for audio output
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: aout_internal.h,v 1.22 2002/09/27 23:38:04 massiot Exp $
+ * $Id: aout_internal.h,v 1.23 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
/* From common.c : */
VLC_EXPORT( int, aout_FormatNbChannels, ( audio_sample_format_t * p_format ) );
void aout_FormatPrepare( audio_sample_format_t * p_format );
+VLC_EXPORT( void, aout_FormatPrint, ( aout_instance_t * p_aout, const char * psz_text, audio_sample_format_t * p_format ) );
+VLC_EXPORT( void, aout_FormatsPrint, ( aout_instance_t * p_aout, const char * psz_text, audio_sample_format_t * p_format1, audio_sample_format_t * p_format2 ) );
void aout_FifoInit( aout_instance_t *, aout_fifo_t *, u32 );
mtime_t aout_FifoNextStart( aout_instance_t *, aout_fifo_t * );
void aout_FifoPush( aout_instance_t *, aout_fifo_t *, aout_buffer_t * );
* audio_output.h : audio output interface
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: audio_output.h,v 1.68 2002/09/30 21:32:31 massiot Exp $
+ * $Id: audio_output.h,v 1.69 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
VLC_EXPORT( int, aout_VolumeUp, ( aout_instance_t *, int, audio_volume_t * ) );
VLC_EXPORT( int, aout_VolumeDown, ( aout_instance_t *, int, audio_volume_t * ) );
VLC_EXPORT( int, aout_Restart, ( aout_instance_t * p_aout ) );
+VLC_EXPORT( void, aout_FindAndRestart, ( vlc_object_t * p_this ) );
* This header provides portable declarations for mutexes & conditions
*****************************************************************************
* Copyright (C) 1999, 2002 VideoLAN
- * $Id: vlc_threads.h,v 1.14 2002/10/08 22:48:25 massiot Exp $
+ * $Id: vlc_threads.h,v 1.15 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Jean-Marc Dressler <polux@via.ecp.fr>
* Samuel Hocevar <sam@via.ecp.fr>
# define VLC_THREAD_PRIORITY_INPUT 37
# define VLC_THREAD_PRIORITY_AUDIO 38
# define VLC_THREAD_PRIORITY_VIDEO 31
-# define VLC_THREAD_PRIORITY_OUTPUT 38
+# define VLC_THREAD_PRIORITY_OUTPUT 31
#elif defined(WIN32)
# define VLC_THREAD_PRIORITY_LOW 0
* (http://liba52.sf.net/).
*****************************************************************************
* Copyright (C) 2001, 2002 VideoLAN
- * $Id: a52tofloat32.c,v 1.3 2002/09/30 21:32:32 massiot Exp $
+ * $Id: a52tofloat32.c,v 1.4 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Gildas Bazin <gbazin@netcourrier.com>
* Christophe Massiot <massiot@via.ecp.fr>
{
msg_Err( p_filter,
"liba52 couldn't do the requested downmix 0x%x->0x%x",
- p_sys->i_flags, i_flags );
+ p_sys->i_flags & A52_CHANNEL_MASK,
+ i_flags & A52_CHANNEL_MASK );
memset( p_out_buf->p_buffer, 0, i_bytes_per_block * 6 );
return;
}
* alsa.c : alsa plugin for vlc
*****************************************************************************
* Copyright (C) 2000-2001 VideoLAN
- * $Id: alsa.c,v 1.13 2002/10/05 03:44:50 bozo Exp $
+ * $Id: alsa.c,v 1.14 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Henri Fallon <henri@videolan.org> - Original Author
* Jeffrey Baker <jwbaker@acm.org> - Port to ALSA 1.0 API
struct aout_sys_t
{
snd_pcm_t * p_snd_pcm;
- snd_pcm_sframes_t i_buffer_size;
int i_period_time;
- volatile vlc_bool_t b_can_sleek;
-
#ifdef DEBUG
snd_output_t * p_snd_stderr;
#endif
#define ALSA_DEFAULT_BUFFER_SIZE ( ALSA_DEFAULT_PERIOD_SIZE << 4 )
#define ALSA_SPDIF_PERIOD_SIZE A52_FRAME_NB
#define ALSA_SPDIF_BUFFER_SIZE ( ALSA_SPDIF_PERIOD_SIZE << 4 )
+/* Why << 4 ? --Meuuh */
/*****************************************************************************
* Local prototypes
*****************************************************************************/
vlc_module_begin();
add_category_hint( N_("ALSA"), NULL );
- add_string( "alsa-device", NULL, NULL, N_("device name"), NULL );
+ add_string( "alsa-device", "default", aout_FindAndRestart,
+ N_("device name"), NULL );
set_description( _("ALSA audio module") );
set_capability( "audio output", 50 );
set_callbacks( Open, Close );
{
aout_instance_t * p_aout = (aout_instance_t *)p_this;
struct aout_sys_t * p_sys;
+ char * psz_device;
+ int i_buffer_size;
- int i_snd_rc = -1;
-
- char * psz_device = NULL;
- char psz_alsadev[128];
- char * psz_userdev;
+ snd_pcm_hw_params_t *p_hw;
+ snd_pcm_sw_params_t *p_sw;
- int i_format_tries[2];
- int i_tries_count, i;
+ int i_snd_rc = -1;
int i_format;
- int i_channels;
- snd_pcm_hw_params_t *p_hw;
- snd_pcm_sw_params_t *p_sw;
/* Allocate structures */
p_aout->output.p_sys = p_sys = malloc( sizeof( aout_sys_t ) );
return -1;
}
- p_aout->output.pf_play = Play;
+ /* Get device name */
+ if( (psz_device = config_GetPsz( p_aout, "dspdev" )) == NULL )
+ {
+ msg_Err( p_aout, "no audio device given (maybe \"default\" ?)" );
+ free( p_sys );
+ return VLC_EGENERIC;
+ }
#ifdef DEBUG
snd_output_stdio_attach( &p_sys->p_snd_stderr, stderr, 0 );
#endif
- i_tries_count = 0;
- i_format_tries[i_tries_count++] = p_aout->output.output.i_format;
- if( i_format_tries[0] == VLC_FOURCC('s','p','d','i') )
+ /* Open the device */
+ if ( AOUT_FMT_NON_LINEAR( &p_aout->output.output )
+ && !strcmp( "default", psz_device ) )
{
- /* Try S/PDIF, and then FLOAT32 */
- i_format_tries[i_tries_count++] = VLC_FOURCC('f','l','3','2');
- }
+ /* ALSA doesn't understand "default" for S/PDIF. Cheat a little. */
+ char psz_iecdev[128];
- /* Read in ALSA device preferences from configuration */
- psz_userdev = config_GetPsz( p_aout, "alsa-device" );
-
- for( i = 0 ; ( i_snd_rc < 0 ) && ( i < i_tries_count ) ; ++i )
- {
- if( i_format_tries[i] == VLC_FOURCC('s','p','d','i') )
+ if ( !strcmp( "default", psz_device ) )
{
- if( psz_userdev )
- {
- psz_device = psz_userdev;
- }
- else
- {
- /* Will probably need some little modification in the case
- we want to send some data at a different rate
- (32000, 44100 and 48000 are the possibilities) -- bozo */
- unsigned char s[4];
- s[0] = IEC958_AES0_CON_EMPHASIS_NONE | IEC958_AES0_NONAUDIO;
- s[1] = IEC958_AES1_CON_ORIGINAL | IEC958_AES1_CON_PCM_CODER;
- s[2] = 0;
- s[3] = IEC958_AES3_CON_FS_48000;
- sprintf( psz_alsadev,
- "iec958:AES0=0x%x,AES1=0x%x,AES2=0x%x,AES3=0x%x",
- s[0], s[1], s[2], s[3] );
- psz_device = psz_alsadev;
- }
+ snprintf( psz_iecdev, sizeof(psz_iecdev),
+ "iec958:AES0=0x%x,AES1=0x%x,AES2=0x%x,AES3=0x%x",
+ IEC958_AES0_CON_EMPHASIS_NONE | IEC958_AES0_NONAUDIO,
+ IEC958_AES1_CON_ORIGINAL | IEC958_AES1_CON_PCM_CODER,
+ 0,
+ (p_aout->output.output.i_rate == 48000 ?
+ IEC958_AES3_CON_FS_48000 :
+ (p_aout->output.output.i_rate == 44100 ?
+ IEC958_AES3_CON_FS_44100 : IEC958_AES3_CON_FS_32000)) );
}
else
{
- if( psz_userdev )
- psz_device = psz_userdev;
- else
- psz_device = "default";
+ strncat( psz_iecdev, psz_device, sizeof(psz_iecdev) );
}
- /* Open device */
- i_snd_rc = snd_pcm_open( &p_sys->p_snd_pcm, psz_device,
- SND_PCM_STREAM_PLAYBACK, SND_PCM_NONBLOCK);
- }
+ if ( (i_snd_rc = snd_pcm_open( &p_sys->p_snd_pcm, psz_iecdev,
+ SND_PCM_STREAM_PLAYBACK, SND_PCM_NONBLOCK)) < 0 )
+ {
+ /* No S/PDIF. */
+ msg_Warn( p_aout, "cannot open S/PDIF ALSA device `%s' (%s)",
+ psz_device, snd_strerror(i_snd_rc) );
+ p_aout->output.output.i_format = VLC_FOURCC('f','l','3','2');
+ }
+ else
+ {
+ i_buffer_size = ALSA_SPDIF_BUFFER_SIZE;
+ i_format = SND_PCM_FORMAT_S16_NE;
- if( i_snd_rc < 0 )
- {
- msg_Err( p_aout, "cannot open ALSA device `%s' (%s)",
- psz_device, snd_strerror(i_snd_rc) );
- if( psz_userdev )
- free( psz_userdev );
- p_sys->p_snd_pcm = NULL;
- return -1;
+ p_aout->output.i_nb_samples = ALSA_SPDIF_PERIOD_SIZE;
+ p_aout->output.output.i_format = VLC_FOURCC('s','p','d','i');
+ p_aout->output.output.i_bytes_per_frame = AOUT_SPDIF_SIZE;
+ p_aout->output.output.i_frame_length = A52_FRAME_NB;
+
+ aout_VolumeNoneInit( p_aout );
+ }
}
- if( psz_userdev )
- free( psz_userdev );
+ if ( !AOUT_FMT_NON_LINEAR( &p_aout->output.output ) )
+ {
+ if ( (i_snd_rc = snd_pcm_open( &p_sys->p_snd_pcm, psz_device,
+ SND_PCM_STREAM_PLAYBACK, SND_PCM_NONBLOCK)) < 0 )
+ {
+ msg_Err( p_aout, "cannot open ALSA device `%s' (%s)",
+ psz_device, snd_strerror(i_snd_rc) );
+ free( p_sys );
+ free( psz_device );
+ return VLC_EGENERIC;
+ }
- p_aout->output.output.i_format = i_format_tries[i - 1];
+ if ( p_aout->p_libvlc->i_cpu & CPU_CAPABILITY_FPU )
+ {
+ p_aout->output.output.i_format = VLC_FOURCC('f','l','3','2');
+ i_format = SND_PCM_FORMAT_FLOAT;
+ }
+ else
+ {
+ p_aout->output.output.i_format = AOUT_FMT_S16_NE;
+ i_format = SND_PCM_FORMAT_S16_NE;
+ }
- /* Default settings */
- p_sys->b_can_sleek = VLC_FALSE;
- i_channels = p_aout->output.output.i_channels;
- if ( p_aout->output.output.i_format == VLC_FOURCC('s','p','d','i') )
- {
- p_sys->i_buffer_size = ALSA_SPDIF_BUFFER_SIZE;
- p_aout->output.i_nb_samples = ALSA_SPDIF_PERIOD_SIZE;
- aout_VolumeNoneInit( p_aout );
- }
- else
- {
- p_sys->i_buffer_size = ALSA_DEFAULT_BUFFER_SIZE;
+ i_buffer_size = ALSA_DEFAULT_BUFFER_SIZE;
p_aout->output.i_nb_samples = ALSA_DEFAULT_PERIOD_SIZE;
+
aout_VolumeSoftInit( p_aout );
}
- /* Compute the settings */
- switch (p_aout->output.output.i_format)
- {
- case VLC_FOURCC('f','l','3','2'):
- i_format = SND_PCM_FORMAT_FLOAT;
- break;
-
- case VLC_FOURCC('s','p','d','i'):
- /* Override some settings to make S/PDIF work */
- p_sys->b_can_sleek = VLC_TRUE;
- i_format = SND_PCM_FORMAT_S16_LE;
- i_channels = 2;
- p_aout->output.output.i_bytes_per_frame = AOUT_SPDIF_SIZE;
- p_aout->output.output.i_frame_length = ALSA_SPDIF_PERIOD_SIZE;
- break;
- default:
- msg_Err( p_aout, "audio output format '%.4s' not supported",
- &p_aout->output.output.i_format );
- return -1;
- break;
- }
+ free( psz_device );
+ p_aout->output.pf_play = Play;
snd_pcm_hw_params_alloca(&p_hw);
snd_pcm_sw_params_alloca(&p_sw);
- i_snd_rc = snd_pcm_hw_params_any( p_sys->p_snd_pcm, p_hw );
- if( i_snd_rc < 0 )
+ if ( snd_pcm_hw_params_any( p_sys->p_snd_pcm, p_hw ) < 0 )
{
msg_Err( p_aout, "unable to retrieve initial hardware parameters" );
- return -1;
+ goto error;
}
- i_snd_rc = snd_pcm_hw_params_set_access( p_sys->p_snd_pcm, p_hw,
- SND_PCM_ACCESS_RW_INTERLEAVED );
- if( i_snd_rc < 0 )
- {
- msg_Err( p_aout, "unable to set interleaved stream format" );
- return -1;
- }
-
- i_snd_rc = snd_pcm_hw_params_set_format( p_sys->p_snd_pcm, p_hw, i_format );
- if( i_snd_rc < 0 )
+ /* Set format. */
+ if ( snd_pcm_hw_params_set_format( p_sys->p_snd_pcm, p_hw, i_format ) < 0 )
{
msg_Err( p_aout, "unable to set stream sample size and word order" );
- return -1;
+ goto error;
}
- i_snd_rc = snd_pcm_hw_params_set_channels( p_sys->p_snd_pcm, p_hw,
- i_channels );
- if( i_snd_rc < 0 )
+ if ( !AOUT_FMT_NON_LINEAR( &p_aout->output.output ) )
{
- msg_Err( p_aout, "unable to set number of output channels" );
- return -1;
- }
+ int i_nb_channels;
- i_snd_rc = snd_pcm_hw_params_set_rate_near( p_sys->p_snd_pcm, p_hw,
- p_aout->output.output.i_rate,
- NULL );
- if( i_snd_rc < 0 )
- {
- msg_Err( p_aout, "unable to set sample rate" );
- return -1;
+ if ( snd_pcm_hw_params_set_access( p_sys->p_snd_pcm, p_hw,
+ SND_PCM_ACCESS_RW_INTERLEAVED ) < 0 )
+ {
+ msg_Err( p_aout, "unable to set interleaved stream format" );
+ goto error;
+ }
+
+ /* Set channels. */
+ i_nb_channels = aout_FormatNbChannels( &p_aout->output.output );
+
+ if ( (i_snd_rc = snd_pcm_hw_params_set_channels( p_sys->p_snd_pcm,
+ p_hw, i_nb_channels )) < 0 )
+ {
+ msg_Err( p_aout, "unable to set number of output channels" );
+ goto error;
+ }
+ if ( i_snd_rc != i_nb_channels )
+ {
+ switch ( i_snd_rc )
+ {
+ case 1: p_aout->output.output.i_channels = AOUT_CHAN_MONO; break;
+ case 2: p_aout->output.output.i_channels = AOUT_CHAN_STEREO; break;
+ case 4: p_aout->output.output.i_channels = AOUT_CHAN_2F2R; break;
+ default:
+ msg_Err( p_aout, "Unsupported downmixing (%d)", i_snd_rc );
+ goto error;
+ }
+ }
+
+ /* Set rate. */
+ if ( (i_snd_rc = snd_pcm_hw_params_set_rate_near( p_sys->p_snd_pcm,
+ p_hw, p_aout->output.output.i_rate,
+ NULL )) < 0 )
+ {
+ msg_Err( p_aout, "unable to set sample rate" );
+ goto error;
+ }
+ p_aout->output.output.i_rate = i_snd_rc;
}
- p_aout->output.output.i_rate = i_snd_rc;
+ /* Set buffer size. */
i_snd_rc = snd_pcm_hw_params_set_buffer_size_near( p_sys->p_snd_pcm, p_hw,
p_sys->i_buffer_size );
if( i_snd_rc < 0 )
{
- msg_Err( p_aout, "unable to set buffer time" );
- return -1;
+ msg_Err( p_aout, "unable to set buffer size" );
+ goto error;
}
- p_sys->i_buffer_size = i_snd_rc;
+ /* Set period size. */
i_snd_rc = snd_pcm_hw_params_set_period_size_near(
- p_sys->p_snd_pcm, p_hw, p_aout->output.i_nb_samples, NULL );
+ p_sys->p_snd_pcm, p_hw, p_aout->output.i_nb_samples, NULL );
if( i_snd_rc < 0 )
{
msg_Err( p_aout, "unable to set period size" );
- return -1;
+ goto error;
}
p_aout->output.i_nb_samples = i_snd_rc;
- i_snd_rc = snd_pcm_hw_params( p_sys->p_snd_pcm, p_hw );
- if (i_snd_rc < 0)
+ /* Write hardware configuration. */
+ if ( snd_pcm_hw_params( p_sys->p_snd_pcm, p_hw ) < 0 )
{
msg_Err( p_aout, "unable to set hardware configuration" );
- return -1;
+ goto error;
}
p_sys->i_period_time = snd_pcm_hw_params_get_period_time( p_hw, NULL );
i_snd_rc = snd_pcm_sw_params_set_avail_min( p_sys->p_snd_pcm, p_sw,
p_aout->output.i_nb_samples );
- i_snd_rc = snd_pcm_sw_params( p_sys->p_snd_pcm, p_sw );
- if( i_snd_rc < 0 )
+ /* Write software configuration. */
+ if ( snd_pcm_sw_params( p_sys->p_snd_pcm, p_sw ) < 0 )
{
msg_Err( p_aout, "unable to set software configuration" );
- return -1;
+ goto error;
}
#ifdef DEBUG
VLC_THREAD_PRIORITY_OUTPUT, VLC_FALSE ) )
{
msg_Err( p_aout, "cannot create ALSA thread (%s)", strerror(errno) );
- free( p_sys );
- return -1;
+ goto error;
}
return 0;
+
+error:
+ snd_pcm_close( p_sys->p_snd_pcm );
+#ifdef DEBUG
+ snd_output_close( p_sys->p_snd_stderr );
+#endif
+ free( p_sys );
+ return VLC_EGENERIC;
}
/*****************************************************************************
}
/*****************************************************************************
- * Close: close the Alsa device
+ * Close: close the ALSA device
*****************************************************************************/
static void Close( vlc_object_t *p_this )
{
p_aout->b_die = 1;
vlc_thread_join( p_aout );
- if( p_sys->p_snd_pcm )
- {
- i_snd_rc = snd_pcm_close( p_sys->p_snd_pcm );
+ i_snd_rc = snd_pcm_close( p_sys->p_snd_pcm );
- if( i_snd_rc > 0 )
- {
- msg_Err( p_aout, "failed closing ALSA device (%s)",
- snd_strerror( i_snd_rc ) );
- }
+ if( i_snd_rc > 0 )
+ {
+ msg_Err( p_aout, "failed closing ALSA device (%s)",
+ snd_strerror( i_snd_rc ) );
}
#ifdef DEBUG
/* Sleep during less than one period to avoid a lot of buffer
underruns */
+
+ /* Why do we need to sleep ? --Meuuh */
msleep( p_sys->i_period_time >> 2 );
}
i_snd_rc = snd_pcm_wait( p_sys->p_snd_pcm, THREAD_SLEEP );
if( i_snd_rc < 0 )
{
- msg_Err( p_aout, "alsa device not ready !!! (%s)",
+ msg_Err( p_aout, "ALSA device not ready !!! (%s)",
snd_strerror( i_snd_rc ) );
return;
}
/* Fill in the buffer until space or audio output buffer shortage */
- while( VLC_TRUE )
+ for ( ; ; )
{
/* Get the status */
i_snd_rc = snd_pcm_status( p_sys->p_snd_pcm, p_status );
next_date = (mtime_t)ts_next.tv_sec * 1000000 + ts_next.tv_usec;
p_buffer = aout_OutputNextBuffer( p_aout, next_date,
- p_sys->b_can_sleek );
+ (p_aout->output.output.i_format !=
+ VLC_FOURCC('s','p','d','i')) );
/* Audio output buffer shortage -> stop the fill process and
wait in ALSAThread */
msg_Err( p_aout, "write failed (%s)",
snd_strerror( i_snd_rc ) );
}
- else
- {
- aout_BufferFree( p_buffer );
- }
+
+ aout_BufferFree( p_buffer );
}
}
}
* arts.c : aRts module
*****************************************************************************
* Copyright (C) 2001-2002 VideoLAN
- * $Id: arts.c,v 1.13 2002/10/04 18:07:21 sam Exp $
+ * $Id: arts.c,v 1.14 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Emmanuel Blindauer <manu@agat.net>
* Samuel Hocevar <sam@zoy.org>
aout_instance_t *p_aout = (aout_instance_t *)p_this;
struct aout_sys_t * p_sys;
int i_err;
+ int i_nb_channels;
/* Allocate structure */
p_sys = malloc( sizeof( aout_sys_t ) );
p_aout->output.pf_play = Play;
aout_VolumeSoftInit( p_aout );
- p_sys->stream = NULL;
-
- if( p_sys->stream )
+ p_aout->output.output.i_format = AOUT_FMT_S16_NE;
+ i_nb_channels = aout_FormatNbChannels( &p_aout->output.output );
+ if ( i_nb_channels > 2 )
{
- arts_close_stream( p_sys->stream );
+ /* aRts doesn't support more than two channels. */
+ i_nb_channels = 2;
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
}
/* Open a socket for playing a stream, set format to 16 bits */
p_sys->stream = arts_play_stream( p_aout->output.output.i_rate, 16,
- p_aout->output.output.i_channels, "vlc" );
+ i_nb_channels, "vlc" );
if( p_sys->stream == NULL )
{
msg_Err( p_aout, "cannot open aRts socket" );
+ free( p_sys );
return -1;
}
arts_stream_get( p_sys->stream, ARTS_P_PACKET_COUNT ),
arts_stream_get( p_sys->stream, ARTS_P_PACKET_SIZE ) );
- p_aout->output.output.i_format = AOUT_FMT_S16_NE;
- p_aout->output.i_nb_samples = p_sys->i_size
- / sizeof(u16)
- / p_aout->output.output.i_channels;
+ p_aout->output.i_nb_samples = p_sys->i_size / sizeof(u16) / i_nb_channels;
/* Create aRts thread and wait for its readiness. */
if( vlc_thread_create( p_aout, "aout", aRtsThread,
VLC_THREAD_PRIORITY_OUTPUT, VLC_FALSE ) )
{
msg_Err( p_aout, "cannot create aRts thread (%s)", strerror(errno) );
+ arts_close_stream( p_sys->stream );
+ arts_free();
free( p_sys );
return -1;
}
p_aout->b_die = 1;
vlc_thread_join( p_aout );
- if( p_sys->stream )
- {
- arts_close_stream( p_sys->stream );
- }
-
+ arts_close_stream( p_sys->stream );
arts_free();
free( p_sys );
}
/*****************************************************************************
- * aout.c: Windows DirectX audio output method
+ * directx.c: Windows DirectX audio output method
*****************************************************************************
* Copyright (C) 2001 VideoLAN
- * $Id: directx.c,v 1.3 2002/10/11 10:08:06 gbazin Exp $
+ * $Id: directx.c,v 1.4 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Gildas Bazin <gbazin@netcourrier.com>
*
if( p_aout->output.p_sys == NULL )
{
msg_Err( p_aout, "out of memory" );
- return 1;
+ return VLC_EGENERIC;
}
/* Initialize some variables */
error:
CloseAudio( VLC_OBJECT(p_aout) );
- return 1;
+ return VLC_EGENERIC;
}
/*****************************************************************************
if( p_aout->output.p_sys->hdsound_dll )
FreeLibrary( p_aout->output.p_sys->hdsound_dll );
- /* Close the Output. */
- if ( p_aout->output.p_sys )
- {
- free( p_aout->output.p_sys );
- p_aout->output.p_sys = NULL;
- }
+ free( p_aout->output.p_sys );
}
/*****************************************************************************
WAVEFORMATEX waveformat;
DSBUFFERDESC dsbdesc;
DSBCAPS dsbcaps;
+ int i_nb_channels;
- if( p_aout->output.output.i_channels > 2 )
- p_aout->output.output.i_channels = 2;
+ i_nb_channels = aout_FormatNbChannels( &p_aout->output.output );
+ if ( i_nb_channels > 2 )
+ {
+ i_nb_channels = 2;
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
+ }
/* First set the buffer format */
memset(&waveformat, 0, sizeof(WAVEFORMATEX));
waveformat.wFormatTag = WAVE_FORMAT_PCM;
- waveformat.nChannels = p_aout->output.output.i_channels;
+ waveformat.nChannels = i_nb_channels;
waveformat.nSamplesPerSec = p_aout->output.output.i_rate;
waveformat.wBitsPerSample = 16;
waveformat.nBlockAlign = waveformat.wBitsPerSample / 8 *
| DSBCAPS_CTRLPOSITIONNOTIFY /* We need notification */
| DSBCAPS_GLOBALFOCUS; /* Allows background playing */
dsbdesc.dwBufferBytes = FRAME_SIZE * 2 /* frames*/ * /* buffer size */
- sizeof(s16) * p_aout->output.output.i_channels;
+ sizeof(s16) * i_nb_channels;
dsbdesc.lpwfxFormat = &waveformat;
if( IDirectSound_CreateSoundBuffer( p_aout->output.p_sys->p_dsobject,
/* backup the size of a frame */
p_aout->output.p_sys->p_notif->i_buffer_size = FRAME_SIZE * sizeof(s16)
- * p_aout->output.output.i_channels;
+ * i_nb_channels;
memset(&dsbcaps, 0, sizeof(DSBCAPS));
dsbcaps.dwSize = sizeof(DSBCAPS);
IDirectSoundBuffer_Release( p_aout->output.p_sys->p_dsbuffer );
p_aout->output.p_sys->p_dsnotify = NULL;
}
- return 1;
+ return VLC_EGENERIC;
}
/*****************************************************************************
* esd.c : EsounD module
*****************************************************************************
* Copyright (C) 2000, 2001 VideoLAN
- * $Id: esd.c,v 1.13 2002/09/18 21:21:23 massiot Exp $
+ * $Id: esd.c,v 1.14 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Samuel Hocevar <sam@zoy.org>
*
{
aout_instance_t *p_aout = (aout_instance_t *)p_this;
struct aout_sys_t * p_sys;
+ int i_nb_channels;
/* Allocate structure */
p_sys = malloc( sizeof( aout_sys_t ) );
p_sys->esd_format = ESD_BITS16 | ESD_STREAM | ESD_PLAY;
p_sys->esd_format &= ~ESD_MASK_CHAN;
- switch( p_aout->output.output.i_channels )
+ p_aout->output.output.i_format = AOUT_FMT_S16_NE;
+ i_nb_channels = aout_FormatNbChannels( &p_aout->output.output );
+ if ( i_nb_channels > 2 )
+ {
+ /* EsounD doesn't support more than two channels. */
+ i_nb_channels = 2;
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
+ }
+
+ switch( i_nb_channels )
{
case 1:
p_sys->esd_format |= ESD_MONO;
case 2:
p_sys->esd_format |= ESD_STEREO;
break;
- default:
- return -1;
}
/* open a socket for playing a stream
{
msg_Err( p_aout, "cannot open esound socket (format 0x%08x at %ld Hz)",
p_sys->esd_format, p_aout->output.output.i_rate );
+ free( p_sys );
return -1;
}
- p_aout->output.output.i_format = AOUT_FMT_S16_NE;
p_aout->output.i_nb_samples = ESD_BUF_SIZE * 2;
/* ESD latency is calculated for 44100 Hz. We don't have any way to get the
VLC_THREAD_PRIORITY_OUTPUT, VLC_FALSE ) )
{
msg_Err( p_aout, "cannot create ESD thread (%s)", strerror(errno) );
+ close( p_sys->i_fd );
free( p_sys );
return -1;
}
* file.c : audio output which writes the samples to a file
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: file.c,v 1.12 2002/09/30 21:32:32 massiot Exp $
+ * $Id: file.c,v 1.13 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
if ( p_file == NULL ) return -1;
p_aout->output.pf_play = Play;
- aout_VolumeSoftInit( p_aout );
while ( *ppsz_compare != NULL )
{
}
p_aout->output.output.i_format = format_int[i];
- if ( p_aout->output.output.i_format == VLC_FOURCC('s','p','d','i') )
+ if ( AOUT_FMT_NON_LINEAR( &p_aout->output.output ) )
{
p_aout->output.i_nb_samples = A52_FRAME_NB;
p_aout->output.output.i_bytes_per_frame = AOUT_SPDIF_SIZE;
p_aout->output.output.i_frame_length = A52_FRAME_NB;
+ aout_VolumeNoneInit( p_aout );
}
else
{
p_aout->output.i_nb_samples = FRAME_SIZE;
+ aout_VolumeSoftInit( p_aout );
}
return 0;
}
* oss.c : OSS /dev/dsp module for vlc
*****************************************************************************
* Copyright (C) 2000-2002 VideoLAN
- * $Id: oss.c,v 1.29 2002/10/02 15:37:58 sigmunau Exp $
+ * $Id: oss.c,v 1.30 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Samuel Hocevar <sam@zoy.org>
int i_fd;
};
+/* This must be a power of 2. */
#define FRAME_SIZE 1024
#define FRAME_COUNT 8
#define A52_FRAME_NB 1536
*****************************************************************************/
vlc_module_begin();
add_category_hint( N_("OSS"), NULL );
- add_file( "dspdev", "/dev/dsp", NULL, N_("OSS dsp device"), NULL );
+ add_file( "dspdev", "/dev/dsp", aout_FindAndRestart,
+ N_("OSS dsp device"), NULL );
set_description( _("Linux OSS /dev/dsp module") );
set_capability( "audio output", 100 );
- add_shortcut( "dsp" );
+ add_shortcut( "oss" );
set_callbacks( Open, Close );
vlc_module_end();
aout_instance_t * p_aout = (aout_instance_t *)p_this;
struct aout_sys_t * p_sys;
char * psz_device;
- int i_format, i_format_orig;
- int i_rate;
- int i_frame_size;
- int i_fragments;
- vlc_bool_t b_stereo;
/* Allocate structure */
p_aout->output.p_sys = p_sys = malloc( sizeof( aout_sys_t ) );
return VLC_ENOMEM;
}
- /* Initialize some variables */
+ /* Get device name */
if( (psz_device = config_GetPsz( p_aout, "dspdev" )) == NULL )
{
msg_Err( p_aout, "no audio device given (maybe /dev/dsp ?)" );
if( ioctl( p_sys->i_fd, SNDCTL_DSP_RESET, NULL ) < 0 )
{
msg_Err( p_aout, "cannot reset OSS audio device" );
+ close( p_sys->i_fd );
+ free( p_sys );
return VLC_EGENERIC;
}
- /* Set the fragment size
- * i_fragment = xxxxyyyy where: xxxx is fragtotal
- * 1 << yyyy is fragsize */
- i_fragments = 0;
- i_frame_size = FRAME_SIZE;
- while( i_frame_size >>= 1 )
- {
- ++i_fragments;
- }
- i_fragments |= FRAME_COUNT << 16;
- if( ioctl( p_sys->i_fd, SNDCTL_DSP_SETFRAGMENT, &i_fragments ) < 0 )
- {
- msg_Err( p_aout, "cannot set fragment size (%.8x)", i_fragments );
- return VLC_EGENERIC;
- }
-
/* Set the output format */
- if ( p_aout->output.output.i_format == VLC_FOURCC('s','p','d','i') )
+ if ( AOUT_FMT_NON_LINEAR( &p_aout->output.output ) )
{
- i_format = AFMT_AC3;
- i_format_orig = AFMT_AC3;
- p_aout->output.i_nb_samples = A52_FRAME_NB;
- p_aout->output.output.i_bytes_per_frame = AOUT_SPDIF_SIZE;
- p_aout->output.output.i_frame_length = A52_FRAME_NB;
+ int i_format = AFMT_AC3;
- aout_VolumeNoneInit( p_aout );
+ if( ioctl( p_sys->i_fd, SNDCTL_DSP_SETFMT, &i_format ) < 0
+ || i_format != AFMT_AC3 )
+ {
+ p_aout->output.output.i_format = AOUT_FMT_S16_NE;
+ }
+ else
+ {
+ p_aout->output.output.i_format = VLC_FOURCC('s','p','d','i');
+ p_aout->output.i_nb_samples = A52_FRAME_NB;
+ p_aout->output.output.i_bytes_per_frame = AOUT_SPDIF_SIZE;
+ p_aout->output.output.i_frame_length = A52_FRAME_NB;
+
+ aout_VolumeNoneInit( p_aout );
+ }
}
- else
+
+ if ( !AOUT_FMT_NON_LINEAR( &p_aout->output.output ) )
{
+ int i_format = AFMT_S16_NE;
+ int i_frame_size, i_fragments;
+ int i_rate;
+ int i_nb_channels;
+
+ if( ioctl( p_sys->i_fd, SNDCTL_DSP_SETFMT, &i_format ) < 0 )
+ {
+ msg_Err( p_aout, "cannot set audio output format" );
+ close( p_sys->i_fd );
+ free( p_sys );
+ return VLC_EGENERIC;
+ }
+
+ switch ( i_format )
+ {
+ case AFMT_U8:
+ p_aout->output.output.i_format = VLC_FOURCC('u','8',' ',' ');
+ break;
+ case AFMT_S8:
+ p_aout->output.output.i_format = VLC_FOURCC('s','8',' ',' ');
+ break;
+ case AFMT_U16_LE:
+ p_aout->output.output.i_format = VLC_FOURCC('u','1','6','l');
+ break;
+ case AFMT_S16_LE:
+ p_aout->output.output.i_format = VLC_FOURCC('s','1','6','l');
+ break;
+ case AFMT_U16_BE:
+ p_aout->output.output.i_format = VLC_FOURCC('u','1','6','b');
+ break;
+ case AFMT_S16_BE:
+ p_aout->output.output.i_format = VLC_FOURCC('s','1','6','b');
+ break;
+ default:
+ msg_Err( p_aout, "OSS fell back to an unknown format (%d)",
+ i_format );
+ close( p_sys->i_fd );
+ free( p_sys );
+ return VLC_EGENERIC;
+ }
+
p_aout->output.output.i_format = AOUT_FMT_S16_NE;
- i_format = AFMT_S16_NE;
- i_format_orig = AFMT_S16_NE;
p_aout->output.i_nb_samples = FRAME_SIZE;
aout_VolumeSoftInit( p_aout );
- }
- if( ioctl( p_sys->i_fd, SNDCTL_DSP_SETFMT, &i_format ) < 0
- || i_format != i_format_orig )
- {
- if ( i_format_orig == AFMT_AC3 )
+ /* Set the fragment size
+ * i_fragment = xxxxyyyy where: xxxx is fragtotal
+ * 1 << yyyy is fragsize */
+ i_fragments = 0;
+ i_frame_size = FRAME_SIZE;
+ while( i_frame_size >>= 1 )
{
- /* Retry with S16 */
- msg_Warn( p_aout, "cannot set audio output format (%i)", i_format_orig );
- p_aout->output.output.i_format = AOUT_FMT_S16_NE;
- i_format = AFMT_S16_NE;
- i_format_orig = AFMT_S16_NE;
- p_aout->output.i_nb_samples = FRAME_SIZE;
- if( ioctl( p_sys->i_fd, SNDCTL_DSP_SETFMT, &i_format ) < 0
- || i_format != i_format_orig )
- {
- msg_Err( p_aout, "cannot set audio output format (%i)",
- i_format_orig );
- return VLC_EGENERIC;
- }
+ ++i_fragments;
}
- else
+ i_fragments |= FRAME_COUNT << 16;
+ if( ioctl( p_sys->i_fd, SNDCTL_DSP_SETFRAGMENT, &i_fragments ) < 0 )
{
- msg_Err( p_aout, "cannot set audio output format (%i)", i_format_orig );
- return VLC_EGENERIC;
+ msg_Warn( p_aout, "cannot set fragment size (%.8x)", i_fragments );
}
- }
- if ( p_aout->output.output.i_format != VLC_FOURCC('s','p','d','i') )
- {
- /* FIXME */
- if ( p_aout->output.output.i_channels > 2 )
+ /* These cases are desperate because of the OSS API and A/52 spec. */
+ switch ( p_aout->output.output.i_channels )
{
- msg_Warn( p_aout, "only two channels are supported at the moment" );
- /* Trigger downmixing */
- p_aout->output.output.i_channels = 2;
+ case AOUT_CHAN_3F:
+ case AOUT_CHAN_2F1R:
+ case AOUT_CHAN_3F1R:
+ case AOUT_CHAN_STEREO | AOUT_CHAN_LFE:
+ case AOUT_CHAN_2F1R | AOUT_CHAN_LFE:
+ case AOUT_CHAN_3F1R | AOUT_CHAN_LFE:
+ case AOUT_CHAN_DOLBY | AOUT_CHAN_LFE:
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
+ break;
+ case AOUT_CHAN_CHANNEL | AOUT_CHAN_LFE:
+ case AOUT_CHAN_CHANNEL1 | AOUT_CHAN_LFE:
+ case AOUT_CHAN_CHANNEL2 | AOUT_CHAN_LFE:
+ case AOUT_CHAN_MONO | AOUT_CHAN_LFE:
+ case AOUT_CHAN_2F2R | AOUT_CHAN_LFE:
+ p_aout->output.output.i_channels &= ~AOUT_CHAN_LFE;
+ break;
+ case AOUT_CHAN_3F2R:
+ p_aout->output.output.i_channels = AOUT_CHAN_2F2R;
+ break;
}
+ /* In a nutshell, possible types : AOUT_CHAN_STEREO (and al.),
+ AOUT_CHAN_2F2R, AOUT_CHAN_3F1R | AOUT_CHAN_LFE. */
- /* Set the number of channels */
- b_stereo = p_aout->output.output.i_channels - 1;
+ i_nb_channels = aout_FormatNbChannels( &p_aout->output.output );
+
+ if ( i_nb_channels > 2 )
+ {
+ /* Check that the device supports this. */
+
+#ifdef SNDCTL_DSP_GETCHANNELMASK
+ int i_chanmask;
+ if ( ioctl( p_sys->i_fd, SNDCTL_DSP_GETCHANNELMASK,
+ &i_chanmask ) == 0 )
+ {
+ if ( !(i_chanmask & DSP_BIND_FRONT) )
+ {
+ msg_Err( p_aout, "No front channels ! (%x)",
+ i_chanmask );
+ close( p_sys->i_fd );
+ free( p_sys );
+ return VLC_EGENERIC;
+ }
+
+ if ( !(i_chanmask & DSP_BIND_SURR) )
+ {
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
+ i_nb_channels = 2;
+ }
+
+ if ( p_aout->output.output.i_channels ==
+ (AOUT_CHAN_3F2R | AOUT_CHAN_LFE)
+ && !(i_chanmask & DSP_BIND_CENTER_LFE) )
+ {
+ p_aout->output.output.i_channels = AOUT_CHAN_2F2R;
+ i_nb_channels = 4;
+ }
+ }
+ else
+#endif
+ {
+ /* The driver doesn't support this call, assume it is stereo. */
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
+ i_nb_channels = 2;
+ }
+ }
- if( ioctl( p_sys->i_fd, SNDCTL_DSP_STEREO, &b_stereo ) < 0 )
+ /* Set the number of channels */
+ if( ioctl( p_sys->i_fd, SNDCTL_DSP_CHANNELS, &i_nb_channels ) < 0 )
{
msg_Err( p_aout, "cannot set number of audio channels (%i)",
p_aout->output.output.i_channels );
+ close( p_sys->i_fd );
+ free( p_sys );
return VLC_EGENERIC;
}
- if ( b_stereo + 1 != p_aout->output.output.i_channels )
+ if ( i_nb_channels != aout_FormatNbChannels( &p_aout->output.output ) )
{
- msg_Warn( p_aout, "driver forced up/downmixing %li->%li",
- p_aout->output.output.i_channels,
- b_stereo + 1 );
- p_aout->output.output.i_channels = b_stereo + 1;
+ switch ( i_nb_channels )
+ {
+ case 1: p_aout->output.output.i_channels = AOUT_CHAN_MONO; break;
+ case 2: p_aout->output.output.i_channels = AOUT_CHAN_STEREO; break;
+ case 4: p_aout->output.output.i_channels = AOUT_CHAN_2F2R; break;
+ default:
+ msg_Err( p_aout, "Unsupported downmixing (%d)", i_nb_channels );
+ close( p_sys->i_fd );
+ free( p_sys );
+ return VLC_EGENERIC;
+ }
}
/* Set the output rate */
{
msg_Err( p_aout, "cannot set audio output rate (%i)",
p_aout->output.output.i_rate );
+ close( p_sys->i_fd );
+ free( p_sys );
return VLC_EGENERIC;
}
if( i_rate != p_aout->output.output.i_rate )
{
- msg_Warn( p_aout, "driver forced resampling %li->%li",
- p_aout->output.output.i_rate, i_rate );
p_aout->output.output.i_rate = i_rate;
}
}
* waveout.c : Windows waveOut plugin for vlc
*****************************************************************************
* Copyright (C) 2001 VideoLAN
- * $Id: waveout.c,v 1.8 2002/10/11 10:08:06 gbazin Exp $
+ * $Id: waveout.c,v 1.9 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Gildas Bazin <gbazin@netcourrier.com>
*
{
aout_instance_t *p_aout = (aout_instance_t *)p_this;
aout_buffer_t *p_buffer;
+ int i_nb_channels;
/* Allocate structure */
p_aout->output.p_sys = malloc( sizeof( aout_sys_t ) );
if( p_aout->output.p_sys == NULL )
{
msg_Err( p_aout, "out of memory" );
- return 1;
+ return VLC_EGENERIC;
}
p_aout->output.pf_play = Play;
aout_VolumeSoftInit( p_aout );
- /* FIXME */
- if ( p_aout->output.output.i_channels > 2 )
+ i_nb_channels = aout_FormatNbChannels( &p_aout->output.output );
+ if ( i_nb_channels > 2 )
{
- msg_Warn( p_aout, "only two channels are supported at the moment" );
- /* Trigger downmixing */
- p_aout->output.output.i_channels = 2;
+ /* Waveout doesn't support more than two channels. */
+ i_nb_channels = 2;
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
}
/* We need to open the device with default values to be sure it is
* available */
- if ( OpenWaveOut( p_aout, WAVE_FORMAT_PCM,
- p_aout->output.output.i_channels,
+ if ( OpenWaveOut( p_aout, WAVE_FORMAT_PCM, i_nb_channels,
p_aout->output.output.i_rate ) )
{
msg_Err( p_aout, "cannot open waveout audio device with output "
"rate (%i)",
p_aout->output.output.i_rate );
- return 1;
+ return VLC_EGENERIC;
- if ( OpenWaveOut( p_aout, WAVE_FORMAT_PCM,
- p_aout->output.output.i_channels,
+ if ( OpenWaveOut( p_aout, WAVE_FORMAT_PCM, i_nb_channels,
44100 ) )
{
msg_Err( p_aout, "cannot open waveout audio device with output "
"rate (44100)" );
- return 1;
+ return VLC_EGENERIC;
}
+ p_aout->output.output.i_rate = 44100;
}
waveOutReset( p_aout->output.p_sys->h_waveout );
- /* calculate the frame size in bytes */
+ /* Calculate the frame size in bytes */
p_aout->output.p_sys->i_buffer_size = FRAME_SIZE * sizeof(s16)
* p_aout->output.p_sys->waveformat.nChannels;
/* Allocate silence buffer */
/* Free silence buffer */
free( p_aout->output.p_sys->p_silence_buffer );
- if( p_aout->output.p_sys != NULL )
- {
- free( p_aout->output.p_sys );
- p_aout->output.p_sys = NULL;
- }
+ free( p_aout->output.p_sys );
}
/*****************************************************************************
* idctaltivec.c : AltiVec IDCT module
*****************************************************************************
* Copyright (C) 2001 VideoLAN
- * $Id: idctaltivec.c,v 1.1 2002/08/04 17:23:42 sam Exp $
+ * $Id: idctaltivec.c,v 1.2 2002/10/20 12:23:47 massiot Exp $
*
- * Authors: Christophe Massiot <massiot@via.ecp.fr>
+ * Authors: Michel Lespinasse <walken@zoy.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* vpar_synchro.c : frame dropping routines
*****************************************************************************
* Copyright (C) 1999-2001 VideoLAN
- * $Id: synchro.c,v 1.2 2002/08/04 18:39:41 sam Exp $
+ * $Id: synchro.c,v 1.3 2002/10/20 12:23:47 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
* Samuel Hocevar <sam@via.ecp.fr>
if( p_vpar->synchro.i_eta_p
&& p_vpar->synchro.i_eta_p != p_vpar->synchro.i_n_p )
{
- msg_Warn( p_vpar->p_fifo,
- "stream periodicity changed from P[%d] to P[%d]",
- p_vpar->synchro.i_n_p, p_vpar->synchro.i_eta_p );
+ msg_Dbg( p_vpar->p_fifo,
+ "stream periodicity changed from P[%d] to P[%d]",
+ p_vpar->synchro.i_n_p, p_vpar->synchro.i_eta_p );
p_vpar->synchro.i_n_p = p_vpar->synchro.i_eta_p;
}
p_vpar->synchro.i_eta_p = p_vpar->synchro.i_eta_b = 0;
* system.c: helper module for TS, PS and PES management
*****************************************************************************
* Copyright (C) 1998-2002 VideoLAN
- * $Id: system.c,v 1.5 2002/10/03 21:45:16 massiot Exp $
+ * $Id: system.c,v 1.6 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
* Michel Lespinasse <walken@via.ecp.fr>
p_es->i_cat = AUDIO_ES;
break;
case A52_AUDIO_ES:
+ case A52DVB_AUDIO_ES:
p_es->i_fourcc = VLC_FOURCC('a','5','2','b');
p_es->i_cat = AUDIO_ES;
break;
* system.h: MPEG demultiplexing.
*****************************************************************************
* Copyright (C) 1999-2002 VideoLAN
- * $Id: system.h,v 1.2 2002/08/30 22:22:24 massiot Exp $
+ * $Id: system.h,v 1.3 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
#define MPEG2_VIDEO_ES 0x02
#define MPEG1_AUDIO_ES 0x03
#define MPEG2_AUDIO_ES 0x04
+#define A52DVB_AUDIO_ES 0x06
#define A52_AUDIO_ES 0x81
/* These ones might violate the usage : */
#define DVD_SPU_ES 0x82
* mpeg_ts.c : Transport Stream input module for vlc
*****************************************************************************
* Copyright (C) 2000-2001 VideoLAN
- * $Id: ts.c,v 1.7 2002/10/12 21:31:56 gbazin Exp $
+ * $Id: ts.c,v 1.8 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Henri Fallon <henri@via.ecp.fr>
* Johan Bilien <jobi@via.ecp.fr>
p_new_es->i_cat = AUDIO_ES;
break;
case A52_AUDIO_ES:
+ case A52DVB_AUDIO_ES:
if ( !b_vls_compat )
p_new_es->i_fourcc = VLC_FOURCC('a','5','2',' ');
else
p_new_es->i_cat = AUDIO_ES;
break;
case A52_AUDIO_ES:
+ case A52DVB_AUDIO_ES:
if ( !b_vls_compat )
p_new_es->i_fourcc = VLC_FOURCC('a','5','2',' ');
else
strcat( p_new_es->psz_desc, " (lpcm)" );
break;
case A52_AUDIO_ES:
+ case A52DVB_AUDIO_ES:
case A52B_AUDIO_ES:
strcat( p_new_es->psz_desc, " (A52)" );
break;
* common.c : audio output management of common data structures
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: common.c,v 1.2 2002/09/30 21:32:33 massiot Exp $
+ * $Id: common.c,v 1.3 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
p_format->i_frame_length = 1;
}
+/*****************************************************************************
+ * FormatPrintChannels : print a channel in a human-readable form
+ *****************************************************************************/
+static const char * FormatPrintChannels( int i_channels )
+{
+ switch ( i_channels )
+ {
+ case AOUT_CHAN_CHANNEL: return "CHANNEL";
+ case AOUT_CHAN_CHANNEL1: return "CHANNEL1";
+ case AOUT_CHAN_CHANNEL2: return "CHANNEL2";
+ case AOUT_CHAN_MONO: return "MONO";
+ case AOUT_CHAN_STEREO: return "STEREO";
+ case AOUT_CHAN_3F: return "3F";
+ case AOUT_CHAN_2F1R: return "2F1R";
+ case AOUT_CHAN_3F1R: return "3F1R";
+ case AOUT_CHAN_2F2R: return "2F2R";
+ case AOUT_CHAN_3F2R: return "3F2R";
+ case AOUT_CHAN_DOLBY: return "DOLBY";
+ case AOUT_CHAN_CHANNEL | AOUT_CHAN_LFE: return "CHANNEL|LFE";
+ case AOUT_CHAN_CHANNEL1 | AOUT_CHAN_LFE: return "CHANNEL1|LFE";
+ case AOUT_CHAN_CHANNEL2 | AOUT_CHAN_LFE: return "CHANNEL2|LFE";
+ case AOUT_CHAN_MONO | AOUT_CHAN_LFE: return "MONO|LFE";
+ case AOUT_CHAN_STEREO | AOUT_CHAN_LFE: return "STEREO|LFE";
+ case AOUT_CHAN_3F | AOUT_CHAN_LFE: return "3F|LFE";
+ case AOUT_CHAN_2F1R | AOUT_CHAN_LFE: return "2F1R|LFE";
+ case AOUT_CHAN_3F1R | AOUT_CHAN_LFE: return "3F1R|LFE";
+ case AOUT_CHAN_2F2R | AOUT_CHAN_LFE: return "2F2R|LFE";
+ case AOUT_CHAN_3F2R | AOUT_CHAN_LFE: return "3F2R|LFE";
+ case AOUT_CHAN_DOLBY | AOUT_CHAN_LFE: return "DOLBY|LFE";
+ }
+
+ return "ERROR";
+}
+
+/*****************************************************************************
+ * aout_FormatPrint : print a format in a human-readable form
+ *****************************************************************************/
+void aout_FormatPrint( aout_instance_t * p_aout, const char * psz_text,
+ audio_sample_format_t * p_format )
+{
+ msg_Dbg( p_aout, "%s format='%4.4s' rate=%d channels=%s", psz_text,
+ (char *)&p_format->i_format, p_format->i_rate,
+ FormatPrintChannels( p_format->i_channels ) );
+}
+
+/*****************************************************************************
+ * aout_FormatsPrint : print two formats in a human-readable form
+ *****************************************************************************/
+void aout_FormatsPrint( aout_instance_t * p_aout, const char * psz_text,
+ audio_sample_format_t * p_format1,
+ audio_sample_format_t * p_format2 )
+{
+ msg_Dbg( p_aout, "%s format='%4.4s'->'%4.4s' rate=%d->%d channels=%s->%s",
+ psz_text,
+ (char *)&p_format1->i_format, (char *)&p_format2->i_format,
+ p_format1->i_rate, p_format2->i_rate,
+ FormatPrintChannels( p_format1->i_channels ),
+ FormatPrintChannels( p_format2->i_channels ) );
+}
+
/*
* FIFO management (internal) - please understand that solving race conditions
* filters.c : audio output filters management
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: filters.c,v 1.11 2002/09/30 21:32:33 massiot Exp $
+ * $Id: filters.c,v 1.12 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
return 0;
}
- msg_Dbg( p_aout, "filter(s) format=%4.4s->%4.4s rate=%d->%d channels=%d->%d",
- (char *)&p_input_format->i_format,
- (char *)&p_output_format->i_format,
- p_input_format->i_rate, p_output_format->i_rate,
- p_input_format->i_channels, p_output_format->i_channels );
+ aout_FormatsPrint( p_aout, "filter(s)", p_input_format, p_output_format );
/* Try to find a filter to do the whole conversion. */
pp_filters[0] = FindFilter( p_aout, p_input_format, p_output_format );
* input.c : internal management of input streams for the audio output
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: input.c,v 1.16 2002/10/09 22:54:22 massiot Exp $
+ * $Id: input.c,v 1.17 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
{
audio_sample_format_t intermediate_format;
+ aout_FormatPrint( p_aout, "input", &p_input->input );
+
/* Prepare FIFO. */
aout_FifoInit( p_aout, &p_input->fifo, p_aout->mixer.mixer.i_rate );
p_input->p_first_byte_to_mix = NULL;
* pauses the stream (or if the decoder is buggy, which cannot
* happen :). */
msg_Warn( p_aout, "computed PTS is out of range (%lld), clearing out",
- start_date );
+ mdate() - start_date );
vlc_mutex_lock( &p_aout->input_fifos_lock );
aout_FifoSet( p_aout, &p_input->fifo, 0 );
vlc_mutex_unlock( &p_aout->input_fifos_lock );
* intf.c : audio output API towards the interface modules
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: intf.c,v 1.4 2002/09/26 22:40:25 massiot Exp $
+ * $Id: intf.c,v 1.5 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
return b_error;
}
+/*****************************************************************************
+ * aout_FindAndRestart : find the audio output instance and restart
+ *****************************************************************************/
+void aout_FindAndRestart( vlc_object_t * p_this )
+{
+ aout_instance_t * p_aout = vlc_object_find( p_this, VLC_OBJECT_AOUT,
+ FIND_ANYWHERE );
+
+ if ( p_aout == NULL ) return;
+
+ aout_Restart( p_aout );
+ vlc_object_release( p_aout );
+}
* mixer.c : audio output mixing operations
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: mixer.c,v 1.17 2002/09/28 13:05:16 massiot Exp $
+ * $Id: mixer.c,v 1.18 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
if ( p_input->b_error ) continue;
p_buffer = p_fifo->p_first;
+ while ( p_buffer != NULL && p_buffer->start_date < mdate() )
+ {
+ msg_Warn( p_aout, "input PTS is out of range (%lld), trashing",
+ mdate() - p_buffer->start_date );
+ aout_BufferFree( aout_FifoPop( p_aout, p_fifo ) );
+ p_buffer = p_fifo->p_first;
+ }
+
if ( p_buffer == NULL )
{
break;
* output.c : internal management of output streams for the audio output
*****************************************************************************
* Copyright (C) 2002 VideoLAN
- * $Id: output.c,v 1.17 2002/10/03 18:56:09 sam Exp $
+ * $Id: output.c,v 1.18 2002/10/20 12:23:48 massiot Exp $
*
* Authors: Christophe Massiot <massiot@via.ecp.fr>
*
= (p_aout->p_libvlc->i_cpu & CPU_CAPABILITY_FPU) ?
VLC_FOURCC('f','l','3','2') :
VLC_FOURCC('f','i','3','2');
+
+ if ( p_aout->output.output.i_channels == AOUT_CHAN_DOLBY )
+ {
+ /* Do not do Dolby surround unless the user requests it. */
+ p_aout->output.output.i_channels = AOUT_CHAN_STEREO;
+ }
}
aout_FormatPrepare( &p_aout->output.output );
vlc_mutex_unlock( &p_aout->output_fifo_lock );
- msg_Dbg( p_aout, "output format=%4.4s rate=%d channels=%d",
- (char *)&p_aout->output.output.i_format,
- p_aout->output.output.i_rate,
- p_aout->output.output.i_channels );
+ aout_FormatPrint( p_aout, "output", &p_aout->output.output );
/* Calculate the resulting mixer output format. */
memcpy( &p_aout->mixer.mixer, &p_aout->output.output,
p_aout->mixer.mixer.i_format = p_format->i_format;
}
- msg_Dbg( p_aout, "mixer format=%4.4s rate=%d channels=%d",
- (char *)&p_aout->mixer.mixer.i_format, p_aout->mixer.mixer.i_rate,
- p_aout->mixer.mixer.i_channels );
+ aout_FormatPrint( p_aout, "mixer", &p_aout->output.output );
/* Create filters. */
if ( aout_FiltersCreatePipeline( p_aout, p_aout->output.pp_filters,