Commit 018248d1 authored by Jean-Paul Saman's avatar Jean-Paul Saman

Fixed crash on vlc exit/quit and added sanity checking for pointers in the module init/exit paths.

parent c2a9cb1a
...@@ -94,8 +94,8 @@ ...@@ -94,8 +94,8 @@
* The evil global variable. We handle it with care, don't worry. * The evil global variable. We handle it with care, don't worry.
*****************************************************************************/ *****************************************************************************/
static libvlc_global_data_t libvlc_global; static libvlc_global_data_t libvlc_global;
static libvlc_global_data_t * p_libvlc_global; static libvlc_global_data_t * p_libvlc_global = NULL;
static libvlc_int_t * p_static_vlc; static libvlc_int_t * p_static_vlc = NULL;
static volatile unsigned int i_instances = 0; static volatile unsigned int i_instances = 0;
/***************************************************************************** /*****************************************************************************
...@@ -150,7 +150,7 @@ libvlc_int_t * libvlc_InternalCreate( void ) ...@@ -150,7 +150,7 @@ libvlc_int_t * libvlc_InternalCreate( void )
int i_ret; int i_ret;
libvlc_int_t * p_libvlc = NULL; libvlc_int_t * p_libvlc = NULL;
vlc_value_t lockval; vlc_value_t lockval;
char *psz_env; char *psz_env = NULL;
/* &libvlc_global never changes, /* &libvlc_global never changes,
* so we can safely call this multiple times. */ * so we can safely call this multiple times. */
...@@ -183,7 +183,11 @@ libvlc_int_t * libvlc_InternalCreate( void ) ...@@ -183,7 +183,11 @@ libvlc_int_t * libvlc_InternalCreate( void )
/* Allocate a libvlc instance object */ /* Allocate a libvlc instance object */
p_libvlc = vlc_object_create( p_libvlc_global, VLC_OBJECT_LIBVLC ); p_libvlc = vlc_object_create( p_libvlc_global, VLC_OBJECT_LIBVLC );
if( p_libvlc == NULL ) { i_instances--; return NULL; } if( p_libvlc == NULL )
{
i_instances--;
return NULL;
}
p_libvlc->thread_id = 0; p_libvlc->thread_id = 0;
p_libvlc->p_playlist = NULL; p_libvlc->p_playlist = NULL;
p_libvlc->psz_object_name = "libvlc"; p_libvlc->psz_object_name = "libvlc";
...@@ -993,6 +997,9 @@ int libvlc_InternalDestroy( libvlc_int_t *p_libvlc, vlc_bool_t b_release ) ...@@ -993,6 +997,9 @@ int libvlc_InternalDestroy( libvlc_int_t *p_libvlc, vlc_bool_t b_release )
{ {
vlc_value_t lockval; vlc_value_t lockval;
if( !p_libvlc )
return VLC_EGENERIC;
if( p_libvlc->p_memcpy_module ) if( p_libvlc->p_memcpy_module )
{ {
module_Unneed( p_libvlc, p_libvlc->p_memcpy_module ); module_Unneed( p_libvlc, p_libvlc->p_memcpy_module );
...@@ -1032,6 +1039,7 @@ int libvlc_InternalDestroy( libvlc_int_t *p_libvlc, vlc_bool_t b_release ) ...@@ -1032,6 +1039,7 @@ int libvlc_InternalDestroy( libvlc_int_t *p_libvlc, vlc_bool_t b_release )
if( b_release ) vlc_object_release( p_libvlc ); if( b_release ) vlc_object_release( p_libvlc );
vlc_object_destroy( p_libvlc ); vlc_object_destroy( p_libvlc );
p_libvlc = NULL;
/* Stop thread system: last one out please shut the door! /* Stop thread system: last one out please shut the door!
* The number of initializations of the thread system is counted, we * The number of initializations of the thread system is counted, we
...@@ -1722,7 +1730,7 @@ static void InitDeviceValues( libvlc_int_t *p_vlc ) ...@@ -1722,7 +1730,7 @@ static void InitDeviceValues( libvlc_int_t *p_vlc )
char **devices; char **devices;
char *block_dev; char *block_dev;
dbus_bool_t b_dvd; dbus_bool_t b_dvd;
DBusConnection *p_connection; DBusConnection *p_connection = NULL;
DBusError error; DBusError error;
#ifdef HAVE_HAL_1 #ifdef HAVE_HAL_1
......
...@@ -1256,6 +1256,8 @@ int config_AutoSaveConfigFile( vlc_object_t *p_this ) ...@@ -1256,6 +1256,8 @@ int config_AutoSaveConfigFile( vlc_object_t *p_this )
vlc_list_t *p_list; vlc_list_t *p_list;
int i_index, i_count; int i_index, i_count;
if( !p_this ) return -1;
/* Check if there's anything to save */ /* Check if there's anything to save */
vlc_mutex_lock( &p_this->p_libvlc->config_lock ); vlc_mutex_lock( &p_this->p_libvlc->config_lock );
p_list = vlc_list_find( p_this, VLC_OBJECT_MODULE, FIND_ANYWHERE ); p_list = vlc_list_find( p_this, VLC_OBJECT_MODULE, FIND_ANYWHERE );
......
...@@ -173,7 +173,7 @@ static void module_LoadMain( vlc_object_t *p_this ); ...@@ -173,7 +173,7 @@ static void module_LoadMain( vlc_object_t *p_this );
*****************************************************************************/ *****************************************************************************/
void __module_InitBank( vlc_object_t *p_this ) void __module_InitBank( vlc_object_t *p_this )
{ {
module_bank_t *p_bank; module_bank_t *p_bank = NULL;
vlc_value_t lockval; vlc_value_t lockval;
var_Create( p_this->p_libvlc_global, "libvlc", VLC_VAR_MUTEX ); var_Create( p_this->p_libvlc_global, "libvlc", VLC_VAR_MUTEX );
...@@ -190,6 +190,8 @@ void __module_InitBank( vlc_object_t *p_this ) ...@@ -190,6 +190,8 @@ void __module_InitBank( vlc_object_t *p_this )
var_Destroy( p_this->p_libvlc_global, "libvlc" ); var_Destroy( p_this->p_libvlc_global, "libvlc" );
p_bank = vlc_object_create( p_this, sizeof(module_bank_t) ); p_bank = vlc_object_create( p_this, sizeof(module_bank_t) );
if( !p_bank )
return;
p_bank->psz_object_name = "module bank"; p_bank->psz_object_name = "module bank";
p_bank->i_usage = 1; p_bank->i_usage = 1;
p_bank->i_cache = p_bank->i_loaded_cache = 0; p_bank->i_cache = p_bank->i_loaded_cache = 0;
...@@ -209,8 +211,6 @@ void __module_InitBank( vlc_object_t *p_this ) ...@@ -209,8 +211,6 @@ void __module_InitBank( vlc_object_t *p_this )
vlc_object_attach( p_bank, p_this->p_libvlc_global ); vlc_object_attach( p_bank, p_this->p_libvlc_global );
module_LoadMain( p_this ); module_LoadMain( p_this );
return;
} }
/***************************************************************************** /*****************************************************************************
...@@ -233,7 +233,7 @@ void __module_ResetBank( vlc_object_t *p_this ) ...@@ -233,7 +233,7 @@ void __module_ResetBank( vlc_object_t *p_this )
*****************************************************************************/ *****************************************************************************/
void __module_EndBank( vlc_object_t *p_this ) void __module_EndBank( vlc_object_t *p_this )
{ {
module_t * p_next; module_t * p_next = NULL;
vlc_value_t lockval; vlc_value_t lockval;
var_Create( p_this->p_libvlc_global, "libvlc", VLC_VAR_MUTEX ); var_Create( p_this->p_libvlc_global, "libvlc", VLC_VAR_MUTEX );
...@@ -261,20 +261,30 @@ void __module_EndBank( vlc_object_t *p_this ) ...@@ -261,20 +261,30 @@ void __module_EndBank( vlc_object_t *p_this )
if( p_bank->b_cache ) CacheSave( p_this ); if( p_bank->b_cache ) CacheSave( p_this );
while( p_bank->i_loaded_cache-- ) while( p_bank->i_loaded_cache-- )
{ {
DeleteModule (p_bank->pp_loaded_cache[p_bank->i_loaded_cache]->p_module); if( p_bank->pp_loaded_cache[p_bank->i_loaded_cache] )
free( p_bank->pp_loaded_cache[p_bank->i_loaded_cache]->psz_file ); {
free( p_bank->pp_loaded_cache[p_bank->i_loaded_cache] ); DeleteModule (p_bank->pp_loaded_cache[p_bank->i_loaded_cache]->p_module);
free( p_bank->pp_loaded_cache[p_bank->i_loaded_cache]->psz_file );
free( p_bank->pp_loaded_cache[p_bank->i_loaded_cache] );
p_bank->pp_loaded_cache[p_bank->i_loaded_cache] = NULL;
}
} }
if( p_bank->pp_loaded_cache ) if( p_bank->pp_loaded_cache )
{
free( p_bank->pp_loaded_cache ); free( p_bank->pp_loaded_cache );
p_bank->pp_loaded_cache = NULL;
}
while( p_bank->i_cache-- ) while( p_bank->i_cache-- )
{ {
free( p_bank->pp_cache[p_bank->i_cache]->psz_file ); free( p_bank->pp_cache[p_bank->i_cache]->psz_file );
free( p_bank->pp_cache[p_bank->i_cache] ); free( p_bank->pp_cache[p_bank->i_cache] );
p_bank->pp_cache[p_bank->i_cache] = NULL;
} }
if( p_bank->pp_cache ) if( p_bank->pp_cache )
{
free( p_bank->pp_cache ); free( p_bank->pp_cache );
p_bank->pp_cache = NULL;
}
#undef p_bank #undef p_bank
#endif #endif
...@@ -987,7 +997,7 @@ static void AllocatePluginDir( vlc_object_t *p_this, const char *psz_dir, ...@@ -987,7 +997,7 @@ static void AllocatePluginDir( vlc_object_t *p_this, const char *psz_dir,
static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file, static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file,
int64_t i_file_time, int64_t i_file_size ) int64_t i_file_time, int64_t i_file_size )
{ {
module_t * p_module; module_t * p_module = NULL;
module_cache_t *p_cache_entry = NULL; module_cache_t *p_cache_entry = NULL;
/* /*
...@@ -1009,7 +1019,7 @@ static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file, ...@@ -1009,7 +1019,7 @@ static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file,
} }
else else
{ {
module_config_t *p_item, *p_end; module_config_t *p_item = NULL, *p_end = NULL;
p_module = p_cache_entry->p_module; p_module = p_cache_entry->p_module;
p_module->b_loaded = VLC_FALSE; p_module->b_loaded = VLC_FALSE;
...@@ -1036,21 +1046,24 @@ static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file, ...@@ -1036,21 +1046,24 @@ static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file,
p_module->psz_object_name, p_module->psz_longname ); */ p_module->psz_object_name, p_module->psz_longname ); */
vlc_object_attach( p_module, p_this->p_libvlc_global->p_module_bank ); vlc_object_attach( p_module, p_this->p_libvlc_global->p_module_bank );
}
if( !p_this->p_libvlc_global->p_module_bank->b_cache ) return 0; if( !p_this->p_libvlc_global->p_module_bank->b_cache )
return 0;
/* Add entry to cache */ /* Add entry to cache */
#define p_bank p_this->p_libvlc_global->p_module_bank #define p_bank p_this->p_libvlc_global->p_module_bank
p_bank->pp_cache = p_bank->pp_cache =
realloc( p_bank->pp_cache, (p_bank->i_cache + 1) * sizeof(void *) ); realloc( p_bank->pp_cache, (p_bank->i_cache + 1) * sizeof(void *) );
p_bank->pp_cache[p_bank->i_cache] = malloc( sizeof(module_cache_t) ); p_bank->pp_cache[p_bank->i_cache] = malloc( sizeof(module_cache_t) );
p_bank->pp_cache[p_bank->i_cache]->psz_file = strdup( psz_file ); if( !p_bank->pp_cache[p_bank->i_cache] )
p_bank->pp_cache[p_bank->i_cache]->i_time = i_file_time; return -1;
p_bank->pp_cache[p_bank->i_cache]->i_size = i_file_size; p_bank->pp_cache[p_bank->i_cache]->psz_file = strdup( psz_file );
p_bank->pp_cache[p_bank->i_cache]->b_junk = p_module ? 0 : 1; p_bank->pp_cache[p_bank->i_cache]->i_time = i_file_time;
p_bank->pp_cache[p_bank->i_cache]->p_module = p_module; p_bank->pp_cache[p_bank->i_cache]->i_size = i_file_size;
p_bank->i_cache++; p_bank->pp_cache[p_bank->i_cache]->b_junk = p_module ? 0 : 1;
p_bank->pp_cache[p_bank->i_cache]->p_module = p_module;
p_bank->i_cache++;
}
return p_module ? 0 : -1; return p_module ? 0 : -1;
} }
...@@ -1064,10 +1077,11 @@ static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file, ...@@ -1064,10 +1077,11 @@ static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file,
*****************************************************************************/ *****************************************************************************/
static module_t * AllocatePlugin( vlc_object_t * p_this, char * psz_file ) static module_t * AllocatePlugin( vlc_object_t * p_this, char * psz_file )
{ {
module_t * p_module; module_t * p_module = NULL;
module_handle_t handle; module_handle_t handle;
if( LoadModule( p_this, psz_file, &handle ) ) return NULL; if( LoadModule( p_this, psz_file, &handle ) )
return NULL;
/* Now that we have successfully loaded the module, we can /* Now that we have successfully loaded the module, we can
* allocate a structure for it */ * allocate a structure for it */
...@@ -1222,6 +1236,7 @@ static int AllocateBuiltinModule( vlc_object_t * p_this, ...@@ -1222,6 +1236,7 @@ static int AllocateBuiltinModule( vlc_object_t * p_this,
*****************************************************************************/ *****************************************************************************/
static int DeleteModule( module_t * p_module ) static int DeleteModule( module_t * p_module )
{ {
if( !p_module ) return VLC_EGENERIC;
vlc_object_detach( p_module ); vlc_object_detach( p_module );
/* We free the structures that we strdup()ed in Allocate*Module(). */ /* We free the structures that we strdup()ed in Allocate*Module(). */
...@@ -1247,7 +1262,7 @@ static int DeleteModule( module_t * p_module ) ...@@ -1247,7 +1262,7 @@ static int DeleteModule( module_t * p_module )
config_Free( p_module ); config_Free( p_module );
vlc_object_destroy( p_module ); vlc_object_destroy( p_module );
p_module = NULL;
return 0; return 0;
} }
......
...@@ -90,7 +90,7 @@ static vlc_mutex_t structure_lock; ...@@ -90,7 +90,7 @@ static vlc_mutex_t structure_lock;
vlc_object_t *vlc_custom_create( vlc_object_t *p_this, size_t i_size, vlc_object_t *vlc_custom_create( vlc_object_t *p_this, size_t i_size,
int i_type, const char *psz_type ) int i_type, const char *psz_type )
{ {
vlc_object_t * p_new; vlc_object_t * p_new = NULL;
if( i_type == VLC_OBJECT_GLOBAL ) if( i_type == VLC_OBJECT_GLOBAL )
{ {
...@@ -429,7 +429,10 @@ void __vlc_object_destroy( vlc_object_t *p_this ) ...@@ -429,7 +429,10 @@ void __vlc_object_destroy( vlc_object_t *p_this )
/* global is not dynamically allocated by vlc_object_create */ /* global is not dynamically allocated by vlc_object_create */
if( p_this->i_object_type != VLC_OBJECT_GLOBAL ) if( p_this->i_object_type != VLC_OBJECT_GLOBAL )
{
free( p_this ); free( p_this );
p_this = NULL;
}
} }
/** /**
...@@ -575,6 +578,8 @@ void __vlc_object_release( vlc_object_t *p_this ) ...@@ -575,6 +578,8 @@ void __vlc_object_release( vlc_object_t *p_this )
*****************************************************************************/ *****************************************************************************/
void __vlc_object_attach( vlc_object_t *p_this, vlc_object_t *p_parent ) void __vlc_object_attach( vlc_object_t *p_this, vlc_object_t *p_parent )
{ {
if( !p_this ) return;
vlc_mutex_lock( &structure_lock ); vlc_mutex_lock( &structure_lock );
/* Attach the parent to its child */ /* Attach the parent to its child */
...@@ -601,6 +606,8 @@ void __vlc_object_attach( vlc_object_t *p_this, vlc_object_t *p_parent ) ...@@ -601,6 +606,8 @@ void __vlc_object_attach( vlc_object_t *p_this, vlc_object_t *p_parent )
*****************************************************************************/ *****************************************************************************/
void __vlc_object_detach( vlc_object_t *p_this ) void __vlc_object_detach( vlc_object_t *p_this )
{ {
if( !p_this ) return;
vlc_mutex_lock( &structure_lock ); vlc_mutex_lock( &structure_lock );
if( !p_this->p_parent ) if( !p_this->p_parent )
{ {
...@@ -617,6 +624,7 @@ void __vlc_object_detach( vlc_object_t *p_this ) ...@@ -617,6 +624,7 @@ void __vlc_object_detach( vlc_object_t *p_this )
DetachObject( p_this ); DetachObject( p_this );
vlc_mutex_unlock( &structure_lock ); vlc_mutex_unlock( &structure_lock );
p_this = NULL;
} }
/** /**
......
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