From 5643c9ba08abfca48787d49ae762dbbf504ded07 Mon Sep 17 00:00:00 2001 From: Miguel Freitas Date: Thu, 21 Jul 2005 02:51:14 +0000 Subject: - change frontend_lock and config_lock to recursive mutexes to fix reentrancy problems (as reported by Reinhard Nissl and Darren Salt) - add a new recursive mutex support check to configure so we should fail nicely if system doesn't provides it (please test) CVS patchset: 7670 CVS date: 2005/07/21 02:51:14 --- configure.ac | 20 ++++++++++++++++++++ src/xine-engine/configfile.c | 38 ++++++++++++++++++++++---------------- src/xine-engine/xine.c | 11 +++++++++-- 3 files changed, 51 insertions(+), 18 deletions(-) diff --git a/configure.ac b/configure.ac index 44b81b73e..a5116003b 100644 --- a/configure.ac +++ b/configure.ac @@ -265,6 +265,26 @@ dnl WIN32 platform AC_SUBST(WIN32_CPPFLAGS) AM_CONDITIONAL(WIN32, test x$SYS = "xmingw32") +dnl +AC_MSG_CHECKING(for recursive mutex support in pthread) +AC_DEFINE(_GNU_SOURCE) +have_recursive_mutex=no +saved_libs="$LIBS" +LIBS="$THREAD_LIBS" +AC_TRY_LINK([ + #include + ],[ + pthread_mutexattr_t attr; + pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE); + ],[ + have_recursive_mutex=yes + ],[ + AC_MSG_ERROR(recursive mutex support is needed - please report) + ]) +AC_MSG_RESULT($have_recursive_mutex) +LIBS="$saved_libs" + + dnl --------------------------------------------- dnl dynamic linker dnl --------------------------------------------- diff --git a/src/xine-engine/configfile.c b/src/xine-engine/configfile.c index a663fa815..2eec9e830 100644 --- a/src/xine-engine/configfile.c +++ b/src/xine-engine/configfile.c @@ -17,7 +17,7 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * - * $Id: configfile.c,v 1.77 2005/07/17 23:05:09 dsalt Exp $ + * $Id: configfile.c,v 1.78 2005/07/21 02:51:14 miguelfreitas Exp $ * * config object (was: file) management - implementation * @@ -801,11 +801,14 @@ static void config_update_num (config_values_t *this, xine_cfg_entry_t cb_entry; config_shallow_copy(&cb_entry, entry); - /* do not enter the callback from within a locked context */ - pthread_mutex_unlock(&this->config_lock); + + /* it is safe to enter the callback from within a locked context + * because we use a recursive mutex. + */ entry->callback (entry->callback_data, &cb_entry); - } else - pthread_mutex_unlock(&this->config_lock); + } + + pthread_mutex_unlock(&this->config_lock); } static void config_update_string (config_values_t *this, @@ -814,7 +817,6 @@ static void config_update_string (config_values_t *this, cfg_entry_t *entry; char *str_free = NULL; - static pthread_mutex_t update_lock = PTHREAD_MUTEX_INITIALIZER; lprintf ("updating %s to %s\n", key, value); @@ -841,7 +843,6 @@ static void config_update_string (config_values_t *this, return; } - pthread_mutex_lock (&update_lock); pthread_mutex_lock(&this->config_lock); if (value != entry->str_value) { str_free = entry->str_value; @@ -852,17 +853,16 @@ static void config_update_string (config_values_t *this, xine_cfg_entry_t cb_entry; config_shallow_copy(&cb_entry, entry); - free (str_free); - pthread_mutex_unlock (&this->config_lock); - + + /* it is safe to enter the callback from within a locked context + * because we use a recursive mutex. + */ entry->callback (entry->callback_data, &cb_entry); } - else - { + + if (str_free) free(str_free); - pthread_mutex_unlock(&this->config_lock); - } - pthread_mutex_unlock (&update_lock); + pthread_mutex_unlock(&this->config_lock); } /* @@ -1164,6 +1164,7 @@ config_values_t *_x_config_init (void) { volatile /* is this a (old, 2.91.66) irix gcc bug?!? */ #endif config_values_t *this; + pthread_mutexattr_t attr; if (!(this = xine_xmalloc(sizeof(config_values_t)))) { @@ -1175,7 +1176,12 @@ config_values_t *_x_config_init (void) { this->last = NULL; this->current_version = 0; - pthread_mutex_init(&this->config_lock, NULL); + /* warning: config_lock is a recursive mutex. it must NOT be + * used with neither pthread_cond_wait() or pthread_cond_timedwait() + */ + pthread_mutexattr_init(&attr); + pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE); + pthread_mutex_init(&this->config_lock, &attr); this->register_string = config_register_string; this->register_range = config_register_range; diff --git a/src/xine-engine/xine.c b/src/xine-engine/xine.c index 7a701cf22..40f8eb465 100644 --- a/src/xine-engine/xine.c +++ b/src/xine-engine/xine.c @@ -17,7 +17,7 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * - * $Id: xine.c,v 1.313 2005/06/13 00:32:13 miguelfreitas Exp $ + * $Id: xine.c,v 1.314 2005/07/21 02:51:14 miguelfreitas Exp $ */ /* @@ -459,6 +459,7 @@ xine_stream_t *xine_stream_new (xine_t *this, xine_stream_t *stream; int i; + pthread_mutexattr_t attr; xprintf (this, XINE_VERBOSITY_DEBUG, "xine_stream_new\n"); @@ -523,7 +524,6 @@ xine_stream_t *xine_stream_new (xine_t *this, pthread_mutex_init (&stream->info_mutex, NULL); pthread_mutex_init (&stream->meta_mutex, NULL); pthread_mutex_init (&stream->demux_lock, NULL); - pthread_mutex_init (&stream->frontend_lock, NULL); pthread_mutex_init (&stream->event_queues_lock, NULL); pthread_mutex_init (&stream->counter_lock, NULL); pthread_cond_init (&stream->counter_changed, NULL); @@ -531,6 +531,13 @@ xine_stream_t *xine_stream_new (xine_t *this, pthread_cond_init (&stream->first_frame_reached, NULL); pthread_mutex_init (&stream->current_extra_info_lock, NULL); + /* warning: frontend_lock is a recursive mutex. it must NOT be + * used with neither pthread_cond_wait() or pthread_cond_timedwait() + */ + pthread_mutexattr_init(&attr); + pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE); + pthread_mutex_init (&stream->frontend_lock, &attr); + /* * Clear meta/stream info */ -- cgit v1.2.3