From: RĂ©mi Denis-Courmont Date: Mon, 22 Oct 2007 16:30:00 +0000 (+0000) Subject: Reference count libvlc. API break. X-Git-Tag: 0.9.0-test0~4851 X-Git-Url: https://git.sesse.net/?a=commitdiff_plain;h=f297b344ed9a1bf4841c62c5630439cf0e9741fa;p=vlc Reference count libvlc. API break. --- diff --git a/include/vlc/libvlc.h b/include/vlc/libvlc.h index 687933c7f4..82e6362328 100644 --- a/include/vlc/libvlc.h +++ b/include/vlc/libvlc.h @@ -102,7 +102,7 @@ libvlc_exception_get_message( const libvlc_exception_t *p_exception ); */ /** - * Create an initialized libvlc instance + * Create an initialized libvlc instance. * \param argc the number of arguments * \param argv command-line-type arguments * \param exception an initialized exception pointer @@ -119,10 +119,17 @@ libvlc_new( int , const char *const *, libvlc_exception_t *); VLC_PUBLIC_API int libvlc_get_vlc_id( libvlc_instance_t *p_instance ); /** - * Destroy a libvlc instance. + * Decrements the reference count of a libvlc instance, and destroys it + * if it reaches zero. * \param p_instance the instance to destroy */ -VLC_PUBLIC_API void libvlc_destroy( libvlc_instance_t *, libvlc_exception_t * ); +VLC_PUBLIC_API void libvlc_release( libvlc_instance_t *, libvlc_exception_t * ); + +/** + * Increments the reference count of a libvlc instance. + * The reference count is initially one when libvlc_new() returns. + */ +VLC_PUBLIC_API void libvlc_retain( libvlc_instance_t * ); /** @}*/ diff --git a/src/control/core.c b/src/control/core.c index d52023597f..a3cf347bf0 100644 --- a/src/control/core.c +++ b/src/control/core.c @@ -20,12 +20,15 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. *****************************************************************************/ -#include #include "libvlc_internal.h" #include #include +#include +#include +#include + static const char nomemstr[] = "Insufficient memory"; /************************************************************************* @@ -106,6 +109,7 @@ libvlc_instance_t * libvlc_new( int argc, const char *const *argv, p_new->p_libvlc_int = p_libvlc_int; p_new->p_vlm = NULL; p_new->b_playlist_locked = 0; + p_new->ref_count = 1; p_new->p_callback_list = NULL; vlc_mutex_init(p_libvlc_int, &p_new->instance_lock); vlc_mutex_init(p_libvlc_int, &p_new->event_callback_lock); @@ -115,14 +119,37 @@ libvlc_instance_t * libvlc_new( int argc, const char *const *argv, return p_new; } -void libvlc_destroy( libvlc_instance_t *p_instance, libvlc_exception_t *p_e ) +void libvlc_retain( libvlc_instance_t *p_instance ) +{ + assert( p_instance != NULL ); + assert( p_instance->ref_count < UINT_MAX ); + + vlc_mutex_lock( &p_instance->instance_lock ); + p_instance->ref_count++; + vlc_mutex_unlock( &p_instance->instance_lock ); +} + +void libvlc_release( libvlc_instance_t *p_instance, libvlc_exception_t *p_e ) { - libvlc_event_fini( p_instance, p_e ); - vlc_mutex_destroy( &p_instance->instance_lock ); - vlc_mutex_destroy( &p_instance->event_callback_lock); - libvlc_InternalCleanup( p_instance->p_libvlc_int ); - libvlc_InternalDestroy( p_instance->p_libvlc_int, VLC_FALSE ); - free( p_instance ); + vlc_mutex_t *lock = &p_instance->instance_lock; + int refs; + + assert( p_instance->ref_count > 0 ); + + vlc_mutex_lock( &p_instance->instance_lock ); + refs = --p_instance->ref_count; + if( refs == 0 ) + libvlc_event_fini( p_instance, p_e ); + vlc_mutex_unlock( &p_instance->instance_lock ); + + if( refs == 0 ) + { + vlc_mutex_destroy( &p_instance->instance_lock ); + vlc_mutex_destroy( &p_instance->event_callback_lock ); + libvlc_InternalCleanup( p_instance->p_libvlc_int ); + libvlc_InternalDestroy( p_instance->p_libvlc_int, VLC_FALSE ); + free( p_instance ); + } } int libvlc_get_vlc_id( libvlc_instance_t *p_instance ) diff --git a/src/control/libvlc_internal.h b/src/control/libvlc_internal.h index f6aa779e6d..764cd6adf7 100644 --- a/src/control/libvlc_internal.h +++ b/src/control/libvlc_internal.h @@ -67,6 +67,7 @@ struct libvlc_instance_t libvlc_int_t *p_libvlc_int; vlm_t *p_vlm; int b_playlist_locked; + unsigned ref_count; vlc_mutex_t instance_lock; vlc_mutex_t event_callback_lock; struct libvlc_callback_entry_list_t *p_callback_list; diff --git a/src/control/mediacontrol_core.c b/src/control/mediacontrol_core.c index 85d7f92308..48fd354915 100644 --- a/src/control/mediacontrol_core.c +++ b/src/control/mediacontrol_core.c @@ -88,7 +88,7 @@ mediacontrol_exit( mediacontrol_Instance *self ) libvlc_exception_t ex; libvlc_exception_init( &ex ); - libvlc_destroy( self->p_instance, &ex ); + libvlc_release( self->p_instance, &ex ); } libvlc_instance_t* diff --git a/src/control/testapi.c b/src/control/testapi.c index 21d28692f8..529b2acc96 100644 --- a/src/control/testapi.c +++ b/src/control/testapi.c @@ -74,7 +74,10 @@ int main (int argc, char *argv[]) libvlc_playlist_clear (vlc, &ex); catch (); - libvlc_destroy (vlc, &ex); + libvlc_retain (vlc); + libvlc_release (vlc, &ex); + catch (); + libvlc_release (vlc, &ex); catch (); return 0; }