[glib] GSocket – GSocketSource finalizing not threa dsafe on Windows
- From: Sebastian Dröge <sdroege src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [glib] GSocket – GSocketSource finalizing not threa dsafe on Windows
- Date: Thu, 22 Aug 2013 14:15:08 +0000 (UTC)
commit ab6b7dbc2efc506e43616941ac70f14fc20de574
Author: Sebastian Dröge <slomo circular-chaos org>
Date: Sun Jul 28 16:43:44 2013 +0200
GSocket – GSocketSource finalizing not threadsafe on Windows
The requested_conditions list access is not threadsafe. When passing
the socket ownership from a GSource callback to another thread, which
also creates a GSocketSource for the socket, it can happen that the
original GSocketSource is finalized at the same time as the new one
is created. This would cause inconsistencies in the requested_conditions
list and can cause assertions or completely undefined behaviour.
https://bugzilla.gnome.org/show_bug.cgi?id=705027
gio/gsocket.c | 7 +++++++
1 files changed, 7 insertions(+), 0 deletions(-)
---
diff --git a/gio/gsocket.c b/gio/gsocket.c
index b606171..7f99a60 100644
--- a/gio/gsocket.c
+++ b/gio/gsocket.c
@@ -172,6 +172,7 @@ struct _GSocketPrivate
int current_errors;
int selected_events;
GList *requested_conditions; /* list of requested GIOCondition * */
+ GMutex win32_source_lock;
#endif
struct {
@@ -759,6 +760,7 @@ g_socket_finalize (GObject *object)
}
g_assert (socket->priv->requested_conditions == NULL);
+ g_mutex_clear (&socket->priv->win32_source_lock);
#endif
for (i = 0; i < RECV_ADDR_CACHE_SIZE; i++)
@@ -970,6 +972,7 @@ g_socket_init (GSocket *socket)
socket->priv->construct_error = NULL;
#ifdef G_OS_WIN32
socket->priv->event = WSA_INVALID_EVENT;
+ g_mutex_init (&socket->priv->win32_source_lock);
#endif
}
@@ -3074,24 +3077,28 @@ static void
add_condition_watch (GSocket *socket,
GIOCondition *condition)
{
+ g_mutex_lock (&socket->priv->win32_source_lock);
g_assert (g_list_find (socket->priv->requested_conditions, condition) == NULL);
socket->priv->requested_conditions =
g_list_prepend (socket->priv->requested_conditions, condition);
update_select_events (socket);
+ g_mutex_unlock (&socket->priv->win32_source_lock);
}
static void
remove_condition_watch (GSocket *socket,
GIOCondition *condition)
{
+ g_mutex_lock (&socket->priv->win32_source_lock);
g_assert (g_list_find (socket->priv->requested_conditions, condition) != NULL);
socket->priv->requested_conditions =
g_list_remove (socket->priv->requested_conditions, condition);
update_select_events (socket);
+ g_mutex_unlock (&socket->priv->win32_source_lock);
}
static GIOCondition
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]