Commit 2fa6c9ce authored by Sam Hocevar's avatar Sam Hocevar

* ./src/misc/cpu.c: libvlc now plays nice with SIGILL and restores the

    signal handler to its previous value after use.
  * ./src/libvlc.c: moved signal handling to vlc.c.
parent 9c669a9f
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* vlc.h: global header for vlc * vlc.h: global header for vlc
***************************************************************************** *****************************************************************************
* Copyright (C) 1998, 1999, 2000 VideoLAN * Copyright (C) 1998, 1999, 2000 VideoLAN
* $Id: vlc.h,v 1.8 2002/08/14 17:06:53 sam Exp $ * $Id: vlc.h,v 1.9 2002/08/19 11:13:44 sam Exp $
* *
* This program is free software; you can redistribute it and/or modify * 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 * it under the terms of the GNU General Public License as published by
...@@ -114,6 +114,7 @@ vlc_status_t vlc_status ( void ); ...@@ -114,6 +114,7 @@ vlc_status_t vlc_status ( void );
vlc_error_t vlc_create ( void ); vlc_error_t vlc_create ( void );
vlc_error_t vlc_init ( int, char *[] ); vlc_error_t vlc_init ( int, char *[] );
vlc_error_t vlc_run ( void ); vlc_error_t vlc_run ( void );
vlc_error_t vlc_die ( void );
vlc_error_t vlc_stop ( void ); vlc_error_t vlc_stop ( void );
vlc_error_t vlc_end ( void ); vlc_error_t vlc_end ( void );
vlc_error_t vlc_destroy ( void ); vlc_error_t vlc_destroy ( void );
...@@ -129,6 +130,7 @@ vlc_status_t vlc_status_r ( vlc_t * ); ...@@ -129,6 +130,7 @@ vlc_status_t vlc_status_r ( vlc_t * );
vlc_t * vlc_create_r ( void ); vlc_t * vlc_create_r ( void );
vlc_error_t vlc_init_r ( vlc_t *, int, char *[] ); vlc_error_t vlc_init_r ( vlc_t *, int, char *[] );
vlc_error_t vlc_run_r ( vlc_t * ); vlc_error_t vlc_run_r ( vlc_t * );
vlc_error_t vlc_die_r ( vlc_t * );
vlc_error_t vlc_stop_r ( vlc_t * ); vlc_error_t vlc_stop_r ( vlc_t * );
vlc_error_t vlc_end_r ( vlc_t * ); vlc_error_t vlc_end_r ( vlc_t * );
vlc_error_t vlc_destroy_r ( vlc_t * ); vlc_error_t vlc_destroy_r ( vlc_t * );
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* libvlc.c: main libvlc source * libvlc.c: main libvlc source
***************************************************************************** *****************************************************************************
* Copyright (C) 1998-2002 VideoLAN * Copyright (C) 1998-2002 VideoLAN
* $Id: libvlc.c,v 1.27 2002/08/18 13:49:20 sam Exp $ * $Id: libvlc.c,v 1.28 2002/08/19 11:13:45 sam Exp $
* *
* Authors: Vincent Seguin <seguin@via.ecp.fr> * Authors: Vincent Seguin <seguin@via.ecp.fr>
* Samuel Hocevar <sam@zoy.org> * Samuel Hocevar <sam@zoy.org>
...@@ -37,7 +37,6 @@ ...@@ -37,7 +37,6 @@
#include <stdio.h> /* sprintf() */ #include <stdio.h> /* sprintf() */
#include <string.h> /* strerror() */ #include <string.h> /* strerror() */
#include <stdlib.h> /* free() */ #include <stdlib.h> /* free() */
#include <signal.h> /* SIGHUP, SIGINT, SIGKILL */
#include <vlc/vlc.h> #include <vlc/vlc.h>
...@@ -102,11 +101,6 @@ static void Usage ( vlc_t *, const char *psz_module_name ); ...@@ -102,11 +101,6 @@ static void Usage ( vlc_t *, const char *psz_module_name );
static void ListModules ( vlc_t * ); static void ListModules ( vlc_t * );
static void Version ( void ); static void Version ( void );
#ifndef WIN32
static void InitSignalHandler ( void );
static void FatalSignalHandler ( int i_signal );
#endif
#ifdef WIN32 #ifdef WIN32
static void ShowConsole ( void ); static void ShowConsole ( void );
#endif #endif
...@@ -115,12 +109,45 @@ static void ShowConsole ( void ); ...@@ -115,12 +109,45 @@ static void ShowConsole ( void );
* vlc_create: allocate a vlc_t structure, and initialize libvlc if needed. * vlc_create: allocate a vlc_t structure, and initialize libvlc if needed.
***************************************************************************** *****************************************************************************
* This function allocates a vlc_t structure and returns NULL in case of * This function allocates a vlc_t structure and returns NULL in case of
* failure. Also, the thread system and the signal handlers are initialized. * failure. Also, the thread system is initialized.
*****************************************************************************/ *****************************************************************************/
vlc_error_t vlc_create( void ) vlc_error_t vlc_create( void )
{ {
vlc_t * p_vlc = vlc_create_r(); vlc_t * p_vlc;
return p_vlc ? VLC_SUCCESS : VLC_EGENERIC; vlc_bool_t b_failed = VLC_FALSE;
/* This gives us a rather good protection against concurrent calls, but
* an additional check will be necessary for complete thread safety. */
if( i_vlc )
{
return VLC_EGENERIC;
}
p_vlc = vlc_create_r();
if( p_vlc == NULL )
{
return VLC_EGENERIC;
}
/* We have created an object, which ensures us that p_global_lock has
* been properly initialized. We can now atomically check that we are
* the only p_vlc object. */
vlc_mutex_lock( p_vlc->p_global_lock );
if( i_vlc != 1 )
{
b_failed = VLC_TRUE;
}
vlc_mutex_unlock( p_vlc->p_global_lock );
/* There can be only one */
if( b_failed )
{
vlc_destroy_r( p_vlc );
return VLC_EGENERIC;
}
return VLC_SUCCESS;
} }
vlc_t * vlc_create_r( void ) vlc_t * vlc_create_r( void )
...@@ -149,11 +176,6 @@ vlc_t * vlc_create_r( void ) ...@@ -149,11 +176,6 @@ vlc_t * vlc_create_r( void )
vlc_mutex_init( p_vlc, &p_vlc->config_lock ); vlc_mutex_init( p_vlc, &p_vlc->config_lock );
vlc_mutex_init( p_vlc, &p_vlc->structure_lock ); vlc_mutex_init( p_vlc, &p_vlc->structure_lock );
/* Set signal handling policy for all threads */
#ifndef WIN32
InitSignalHandler( );
#endif
/* Store our newly allocated structure in the global list */ /* Store our newly allocated structure in the global list */
vlc_mutex_lock( p_vlc->p_global_lock ); vlc_mutex_lock( p_vlc->p_global_lock );
pp_vlc = realloc( pp_vlc, (i_vlc+1) * sizeof( vlc_t * ) ); pp_vlc = realloc( pp_vlc, (i_vlc+1) * sizeof( vlc_t * ) );
...@@ -180,7 +202,7 @@ vlc_t * vlc_create_r( void ) ...@@ -180,7 +202,7 @@ vlc_t * vlc_create_r( void )
*****************************************************************************/ *****************************************************************************/
vlc_error_t vlc_init( int i_argc, char *ppsz_argv[] ) vlc_error_t vlc_init( int i_argc, char *ppsz_argv[] )
{ {
return vlc_init_r( ( i_vlc == 1 ) ? *pp_vlc : NULL, i_argc, ppsz_argv ); return vlc_init_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL, i_argc, ppsz_argv );
} }
vlc_error_t vlc_init_r( vlc_t *p_vlc, int i_argc, char *ppsz_argv[] ) vlc_error_t vlc_init_r( vlc_t *p_vlc, int i_argc, char *ppsz_argv[] )
...@@ -197,8 +219,6 @@ vlc_error_t vlc_init_r( vlc_t *p_vlc, int i_argc, char *ppsz_argv[] ) ...@@ -197,8 +219,6 @@ vlc_error_t vlc_init_r( vlc_t *p_vlc, int i_argc, char *ppsz_argv[] )
return VLC_ESTATUS; return VLC_ESTATUS;
} }
fprintf( stderr, COPYRIGHT_MESSAGE "\n" );
/* Guess what CPU we have */ /* Guess what CPU we have */
p_vlc->i_cpu = CPUCapabilities( p_vlc ); p_vlc->i_cpu = CPUCapabilities( p_vlc );
...@@ -511,7 +531,7 @@ vlc_error_t vlc_init_r( vlc_t *p_vlc, int i_argc, char *ppsz_argv[] ) ...@@ -511,7 +531,7 @@ vlc_error_t vlc_init_r( vlc_t *p_vlc, int i_argc, char *ppsz_argv[] )
*****************************************************************************/ *****************************************************************************/
vlc_error_t vlc_run( void ) vlc_error_t vlc_run( void )
{ {
return vlc_run_r( ( i_vlc == 1 ) ? *pp_vlc : NULL ); return vlc_run_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL );
} }
vlc_error_t vlc_run_r( vlc_t *p_vlc ) vlc_error_t vlc_run_r( vlc_t *p_vlc )
...@@ -539,7 +559,7 @@ vlc_error_t vlc_run_r( vlc_t *p_vlc ) ...@@ -539,7 +559,7 @@ vlc_error_t vlc_run_r( vlc_t *p_vlc )
*****************************************************************************/ *****************************************************************************/
vlc_error_t vlc_add_intf( const char *psz_module, vlc_bool_t b_block ) vlc_error_t vlc_add_intf( const char *psz_module, vlc_bool_t b_block )
{ {
return vlc_add_intf_r( ( i_vlc == 1 ) ? *pp_vlc : NULL, return vlc_add_intf_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL,
psz_module, b_block ); psz_module, b_block );
} }
...@@ -602,7 +622,7 @@ vlc_error_t vlc_add_intf_r( vlc_t *p_vlc, const char *psz_module, ...@@ -602,7 +622,7 @@ vlc_error_t vlc_add_intf_r( vlc_t *p_vlc, const char *psz_module,
*****************************************************************************/ *****************************************************************************/
vlc_error_t vlc_stop( void ) vlc_error_t vlc_stop( void )
{ {
return vlc_stop_r( ( i_vlc == 1 ) ? *pp_vlc : NULL ); return vlc_stop_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL );
} }
vlc_error_t vlc_stop_r( vlc_t *p_vlc ) vlc_error_t vlc_stop_r( vlc_t *p_vlc )
...@@ -679,7 +699,7 @@ vlc_error_t vlc_stop_r( vlc_t *p_vlc ) ...@@ -679,7 +699,7 @@ vlc_error_t vlc_stop_r( vlc_t *p_vlc )
*****************************************************************************/ *****************************************************************************/
vlc_error_t vlc_end( void ) vlc_error_t vlc_end( void )
{ {
return vlc_end_r( ( i_vlc == 1 ) ? *pp_vlc : NULL ); return vlc_end_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL );
} }
vlc_error_t vlc_end_r( vlc_t *p_vlc ) vlc_error_t vlc_end_r( vlc_t *p_vlc )
...@@ -737,7 +757,7 @@ vlc_error_t vlc_end_r( vlc_t *p_vlc ) ...@@ -737,7 +757,7 @@ vlc_error_t vlc_end_r( vlc_t *p_vlc )
*****************************************************************************/ *****************************************************************************/
vlc_error_t vlc_destroy( void ) vlc_error_t vlc_destroy( void )
{ {
return vlc_destroy_r( ( i_vlc == 1 ) ? *pp_vlc : NULL ); return vlc_destroy_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL );
} }
vlc_error_t vlc_destroy_r( vlc_t *p_vlc ) vlc_error_t vlc_destroy_r( vlc_t *p_vlc )
...@@ -802,9 +822,38 @@ vlc_error_t vlc_destroy_r( vlc_t *p_vlc ) ...@@ -802,9 +822,38 @@ vlc_error_t vlc_destroy_r( vlc_t *p_vlc )
return VLC_SUCCESS; return VLC_SUCCESS;
} }
/*****************************************************************************
* vlc_die: ask vlc to die.
*****************************************************************************
* This function sets p_vlc->b_die to VLC_TRUE, but does not do any other
* task. It is your duty to call vlc_end and vlc_destroy afterwards.
*****************************************************************************/
vlc_error_t vlc_die( void )
{
return vlc_die_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL );
}
vlc_error_t vlc_die_r( vlc_t *p_vlc )
{
if( !p_vlc )
{
fprintf( stderr, "error: invalid status (!EXIST)\n" );
return VLC_ESTATUS;
}
p_vlc->b_die = VLC_TRUE;
return VLC_SUCCESS;
}
/*****************************************************************************
* vlc_status: return the current vlc status.
*****************************************************************************
* This function returns the current value of p_vlc->i_status.
*****************************************************************************/
vlc_status_t vlc_status( void ) vlc_status_t vlc_status( void )
{ {
return vlc_status_r( ( i_vlc == 1 ) ? *pp_vlc : NULL ); return vlc_status_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL );
} }
vlc_status_t vlc_status_r( vlc_t *p_vlc ) vlc_status_t vlc_status_r( vlc_t *p_vlc )
...@@ -817,9 +866,15 @@ vlc_status_t vlc_status_r( vlc_t *p_vlc ) ...@@ -817,9 +866,15 @@ vlc_status_t vlc_status_r( vlc_t *p_vlc )
return p_vlc->i_status; return p_vlc->i_status;
} }
/*****************************************************************************
* vlc_add_target: adds a target for playing.
*****************************************************************************
* This function adds psz_target to the current playlist. If a playlist does
* not exist, it will create one.
*****************************************************************************/
vlc_error_t vlc_add_target( const char *psz_target, int i_mode, int i_pos ) vlc_error_t vlc_add_target( const char *psz_target, int i_mode, int i_pos )
{ {
return vlc_add_target_r( ( i_vlc == 1 ) ? *pp_vlc : NULL, return vlc_add_target_r( ( i_vlc == 1 ) ? pp_vlc[0] : NULL,
psz_target, i_mode, i_pos ); psz_target, i_mode, i_pos );
} }
...@@ -1177,69 +1232,3 @@ static void ShowConsole( void ) ...@@ -1177,69 +1232,3 @@ static void ShowConsole( void )
} }
#endif #endif
#ifndef WIN32
/*****************************************************************************
* InitSignalHandler: system signal handler initialization
*****************************************************************************
* Set the signal handlers. SIGTERM is not intercepted, because we need at
* at least a method to kill the program when all other methods failed, and
* when we don't want to use SIGKILL.
*****************************************************************************/
static void InitSignalHandler( void )
{
/* Termination signals */
signal( SIGINT, FatalSignalHandler );
signal( SIGHUP, FatalSignalHandler );
signal( SIGQUIT, FatalSignalHandler );
/* Other signals */
signal( SIGALRM, SIG_IGN );
signal( SIGPIPE, SIG_IGN );
}
/*****************************************************************************
* FatalSignalHandler: system signal handler
*****************************************************************************
* This function is called when a fatal signal is received by the program.
* It tries to end the program in a clean way.
*****************************************************************************/
static void FatalSignalHandler( int i_signal )
{
static mtime_t abort_time = 0;
static volatile vlc_bool_t b_die = VLC_FALSE;
int i_index;
/* Once a signal has been trapped, the termination sequence will be
* armed and following signals will be ignored to avoid sending messages
* to an interface having been destroyed */
if( !b_die )
{
b_die = VLC_TRUE;
abort_time = mdate();
fprintf( stderr, "signal %d received, terminating libvlc - do it "
"again in case your process gets stuck\n", i_signal );
/* Try to terminate everything - this is done by requesting the end of
* all the p_vlc structures */
for( i_index = 0 ; i_index < i_vlc ; i_index++ )
{
/* Acknowledge the signal received */
pp_vlc[ i_index ]->b_die = VLC_TRUE;
}
}
else if( mdate() > abort_time + 1000000 )
{
/* If user asks again 1 second later, die badly */
signal( SIGINT, SIG_IGN );
signal( SIGHUP, SIG_IGN );
signal( SIGQUIT, SIG_IGN );
fprintf( stderr, "user insisted too much, dying badly\n" );
exit( 1 );
}
}
#endif
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* cpu.c: CPU detection code * cpu.c: CPU detection code
***************************************************************************** *****************************************************************************
* Copyright (C) 1998-2002 VideoLAN * Copyright (C) 1998-2002 VideoLAN
* $Id: cpu.c,v 1.4 2002/06/07 14:30:41 sam Exp $ * $Id: cpu.c,v 1.5 2002/08/19 11:13:45 sam Exp $
* *
* Authors: Samuel Hocevar <sam@zoy.org> * Authors: Samuel Hocevar <sam@zoy.org>
* Christophe Massiot <massiot@via.ecp.fr> * Christophe Massiot <massiot@via.ecp.fr>
...@@ -43,7 +43,8 @@ ...@@ -43,7 +43,8 @@
/***************************************************************************** /*****************************************************************************
* Local prototypes * Local prototypes
*****************************************************************************/ *****************************************************************************/
static void IllegalSignalHandler( int i_signal ); static void SigHandler ( int );
static u32 Capabilities ( vlc_object_t * );
/***************************************************************************** /*****************************************************************************
* Global variables - they're needed for signal handling * Global variables - they're needed for signal handling
...@@ -55,11 +56,27 @@ static char *psz_capability; ...@@ -55,11 +56,27 @@ static char *psz_capability;
#endif #endif
/***************************************************************************** /*****************************************************************************
* CPUCapabilities: list the processors MMX support and other capabilities * CPUCapabilities: get the CPU capabilities
***************************************************************************** *****************************************************************************
* This function is called to list extensions the CPU may have. * This function is a wrapper around Capabilities().
*****************************************************************************/ *****************************************************************************/
u32 __CPUCapabilities( vlc_object_t *p_this ) u32 __CPUCapabilities( vlc_object_t *p_this )
{
u32 i_capabilities;
vlc_mutex_lock( p_this->p_vlc->p_global_lock );
i_capabilities = Capabilities( p_this );
vlc_mutex_unlock( p_this->p_vlc->p_global_lock );
return i_capabilities;
}
/*****************************************************************************
* Capabilities: list the processors MMX support and other capabilities
*****************************************************************************
* This function is called to list extensions the CPU may have.
*****************************************************************************/
static u32 Capabilities( vlc_object_t *p_this )
{ {
volatile u32 i_capabilities = CPU_CAPABILITY_NONE; volatile u32 i_capabilities = CPU_CAPABILITY_NONE;
...@@ -112,12 +129,12 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -112,12 +129,12 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
: "a" ( a ) \ : "a" ( a ) \
: "cc" ); : "cc" );
i_capabilities |= CPU_CAPABILITY_FPU;
# if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW ) # if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW )
signal( SIGILL, IllegalSignalHandler ); sighandler_t pf_sigill = signal( SIGILL, SigHandler );
# endif # endif
i_capabilities |= CPU_CAPABILITY_FPU;
/* test for a 486 CPU */ /* test for a 486 CPU */
asm volatile ( "pushl %%ebx\n\t" asm volatile ( "pushl %%ebx\n\t"
"pushfl\n\t" "pushfl\n\t"
...@@ -138,7 +155,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -138,7 +155,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
if( i_eax == i_ebx ) if( i_eax == i_ebx )
{ {
# if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW ) # if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW )
signal( SIGILL, NULL ); signal( SIGILL, pf_sigill );
# endif # endif
return i_capabilities; return i_capabilities;
} }
...@@ -151,7 +168,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -151,7 +168,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
if( !i_eax ) if( !i_eax )
{ {
# if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW ) # if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW )
signal( SIGILL, NULL ); signal( SIGILL, pf_sigill );
# endif # endif
return i_capabilities; return i_capabilities;
} }
...@@ -169,7 +186,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -169,7 +186,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
if( ! (i_edx & 0x00800000) ) if( ! (i_edx & 0x00800000) )
{ {
# if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW ) # if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW )
signal( SIGILL, NULL ); signal( SIGILL, pf_sigill );
# endif # endif
return i_capabilities; return i_capabilities;
} }
...@@ -185,13 +202,11 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -185,13 +202,11 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
psz_capability = "SSE"; psz_capability = "SSE";
i_illegal = 0; i_illegal = 0;
vlc_mutex_lock( p_this->p_vlc->p_global_lock );
if( setjmp( env ) == 0 ) if( setjmp( env ) == 0 )
{ {
/* Test a SSE instruction */ /* Test a SSE instruction */
__asm__ __volatile__ ( "xorps %%xmm0,%%xmm0\n" : : ); __asm__ __volatile__ ( "xorps %%xmm0,%%xmm0\n" : : );
} }
vlc_mutex_unlock( p_this->p_vlc->p_global_lock );
if( i_illegal == 0 ) if( i_illegal == 0 )
{ {
...@@ -206,7 +221,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -206,7 +221,7 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
if( i_eax < 0x80000001 ) if( i_eax < 0x80000001 )
{ {
# if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW ) # if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW )
signal( SIGILL, NULL ); signal( SIGILL, pf_sigill );
# endif # endif
return i_capabilities; return i_capabilities;
} }
...@@ -220,13 +235,11 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -220,13 +235,11 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
psz_capability = "3D Now!"; psz_capability = "3D Now!";
i_illegal = 0; i_illegal = 0;
vlc_mutex_lock( p_this->p_vlc->p_global_lock );
if( setjmp( env ) == 0 ) if( setjmp( env ) == 0 )
{ {
/* Test a 3D Now! instruction */ /* Test a 3D Now! instruction */
__asm__ __volatile__ ( "pfadd %%mm0,%%mm0\n" "femms\n" : : ); __asm__ __volatile__ ( "pfadd %%mm0,%%mm0\n" "femms\n" : : );
} }
vlc_mutex_unlock( p_this->p_vlc->p_global_lock );
if( i_illegal == 0 ) if( i_illegal == 0 )
{ {
...@@ -241,20 +254,19 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -241,20 +254,19 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
} }
# if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW ) # if defined( CAN_COMPILE_SSE ) || defined ( CAN_COMPILE_3DNOW )
signal( SIGILL, NULL ); signal( SIGILL, pf_sigill );
# endif # endif
return i_capabilities; return i_capabilities;
#elif defined( __powerpc__ ) #elif defined( __powerpc__ )
i_capabilities |= CPU_CAPABILITY_FPU;
# ifdef CAN_COMPILE_ALTIVEC # ifdef CAN_COMPILE_ALTIVEC
signal( SIGILL, IllegalSignalHandler ); sighandler_t pf_sigill = signal( SIGILL, SigHandler );
i_capabilities |= CPU_CAPABILITY_FPU;
i_illegal = 0; i_illegal = 0;
vlc_mutex_lock( p_this->p_vlc->p_global_lock );
if( setjmp( env ) == 0 ) if( setjmp( env ) == 0 )
{ {
asm volatile ("mtspr 256, %0\n\t" asm volatile ("mtspr 256, %0\n\t"
...@@ -262,14 +274,13 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -262,14 +274,13 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
: :
: "r" (-1)); : "r" (-1));
} }
vlc_mutex_unlock( p_this->p_vlc->p_global_lock );
if( i_illegal == 0 ) if( i_illegal == 0 )
{ {
i_capabilities |= CPU_CAPABILITY_ALTIVEC; i_capabilities |= CPU_CAPABILITY_ALTIVEC;
} }
signal( SIGILL, NULL ); signal( SIGILL, pf_sigill );
# endif # endif
return i_capabilities; return i_capabilities;
...@@ -287,12 +298,12 @@ u32 __CPUCapabilities( vlc_object_t *p_this ) ...@@ -287,12 +298,12 @@ u32 __CPUCapabilities( vlc_object_t *p_this )
} }
/***************************************************************************** /*****************************************************************************
* IllegalSignalHandler: system signal handler * SigHandler: system signal handler
***************************************************************************** *****************************************************************************
* This function is called when an illegal instruction signal is received by * This function is called when an illegal instruction signal is received by
* the program. We use this function to test OS and CPU capabilities * the program. We use this function to test OS and CPU capabilities
*****************************************************************************/ *****************************************************************************/
static void IllegalSignalHandler( int i_signal ) static void SigHandler( int i_signal )
{ {
/* Acknowledge the signal received */ /* Acknowledge the signal received */
i_illegal = 1; i_illegal = 1;
......
...@@ -2,11 +2,12 @@ ...@@ -2,11 +2,12 @@
* vlc.c: the vlc player * vlc.c: the vlc player
***************************************************************************** *****************************************************************************
* Copyright (C) 1998-2001 VideoLAN * Copyright (C) 1998-2001 VideoLAN
* $Id: vlc.c,v 1.8 2002/08/08 00:35:11 sam Exp $ * $Id: vlc.c,v 1.9 2002/08/19 11:13:45 sam Exp $
* *
* Authors: Vincent Seguin <seguin@via.ecp.fr> * Authors: Vincent Seguin <seguin@via.ecp.fr>
* Samuel Hocevar <sam@zoy.org> * Samuel Hocevar <sam@zoy.org>
* Gildas Bazin <gbazin@netcourrier.com> * Gildas Bazin <gbazin@netcourrier.com>
* Lots of other people, see the libvlc AUTHORS file
* *
* This program is free software; you can redistribute it and/or modify * 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 * it under the terms of the GNU General Public License as published by
...@@ -22,19 +23,30 @@ ...@@ -22,19 +23,30 @@
* along with this program; if not, write to the Free Software * along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA.
*****************************************************************************/ *****************************************************************************/
#include <signal.h> /* SIGHUP, SIGINT, SIGKILL */ #include <signal.h> /* SIGHUP, SIGINT, SIGKILL */
#include <stdio.h> /* fprintf() */ #include <stdio.h> /* fprintf() */
#include <stdlib.h> /* putenv(), strtol(), */ #include <stdlib.h> /* putenv(), strtol(), */
#include <signal.h> /* SIGHUP, SIGINT, SIGKILL */
#include <vlc/vlc.h> #include <vlc/vlc.h>
/*****************************************************************************
* Local prototypes.
*****************************************************************************/
#ifndef WIN32
static void SigHandler ( int i_signal );
#endif
/***************************************************************************** /*****************************************************************************
* main: parse command line, start interface and spawn threads * main: parse command line, start interface and spawn threads
*****************************************************************************/ *****************************************************************************/
int main(int i_argc, char *ppsz_argv[]) int main( int i_argc, char *ppsz_argv[] )
{ {
vlc_error_t err; vlc_error_t err;
fprintf( stderr, COPYRIGHT_MESSAGE "\n" );
#ifdef SYS_LINUX #ifdef SYS_LINUX
# ifdef DEBUG # ifdef DEBUG
/* Activate malloc checking routines to detect heap corruptions. */ /* Activate malloc checking routines to detect heap corruptions. */
...@@ -45,14 +57,28 @@ int main(int i_argc, char *ppsz_argv[]) ...@@ -45,14 +57,28 @@ int main(int i_argc, char *ppsz_argv[])
# endif # endif
#endif #endif
/* Create the vlc structure */ /* Create a libvlc structure */
err = vlc_create(); err = vlc_create();
if( err != VLC_SUCCESS ) if( err != VLC_SUCCESS )
{ {
return err; return err;
} }
/* Initialize vlc */ #ifndef WIN32
/* Set the signal handlers. SIGTERM is not intercepted, because we need at
* least one method to kill the program when all other methods failed, and
* when we don't want to use SIGKILL.
* Note that we set the signals after the vlc_create call. */
signal( SIGINT, SigHandler );
signal( SIGHUP, SigHandler );
signal( SIGQUIT, SigHandler );
/* Other signals */
signal( SIGALRM, SIG_IGN );
signal( SIGPIPE, SIG_IGN );
#endif
/* Initialize libvlc */
err = vlc_init( i_argc, ppsz_argv ); err = vlc_init( i_argc, ppsz_argv );
if( err != VLC_SUCCESS ) if( err != VLC_SUCCESS )
{ {
...@@ -60,7 +86,7 @@ int main(int i_argc, char *ppsz_argv[]) ...@@ -60,7 +86,7 @@ int main(int i_argc, char *ppsz_argv[])
return err; return err;
} }
/* Run vlc, in non-blocking mode */ /* Run libvlc, in non-blocking mode */
err = vlc_run(); err = vlc_run();
/* Add background interfaces */ /* Add background interfaces */
...@@ -83,9 +109,52 @@ int main(int i_argc, char *ppsz_argv[]) ...@@ -83,9 +109,52 @@ int main(int i_argc, char *ppsz_argv[])
/* Finish all threads */ /* Finish all threads */
vlc_end(); vlc_end();
/* Destroy the vlc structure */ /* Destroy the libvlc structure */
vlc_destroy(); vlc_destroy();
return err; return err;
} }
#ifndef WIN32
/*****************************************************************************
* SigHandler: system signal handler
*****************************************************************************
* This function is called when a fatal signal is received by the program.
* It tries to end the program in a clean way.
*****************************************************************************/
static void SigHandler( int i_signal )
{
static mtime_t abort_time = 0;
static volatile vlc_bool_t b_die = VLC_FALSE;
/* Once a signal has been trapped, the termination sequence will be
* armed and subsequent signals will be ignored to avoid sending signals
* to a libvlc structure having been destroyed */
if( !b_die )
{
b_die = VLC_TRUE;
abort_time = mdate();
fprintf( stderr, "signal %d received, terminating vlc - do it "
"again in case it gets stuck\n", i_signal );
/* Acknowledge the signal received */
vlc_die();
}
else if( mdate() > abort_time + 1000000 )
{
/* If user asks again 1 second later, die badly */
signal( SIGINT, SIG_DFL );
signal( SIGHUP, SIG_DFL );
signal( SIGQUIT, SIG_DFL );
signal( SIGALRM, SIG_DFL );
signal( SIGPIPE, SIG_DFL );
fprintf( stderr, "user insisted too much, dying badly\n" );
exit( 1 );
}
}
#endif
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment