[gtk-vnc-devel] [PATCH] Fix vnc_display_open followed by immediate vnc_display_close



If you call one of the vnc_display_open* functions followed quickly by vnc_display_close, then the library segfaults.

The reason is that the vnc_display_open* functions register an idle callback to launch the coroutine, but if vnc_display_close is called before the idle loop has had a moment to run, this idle callback remains. The coroutine later runs - in my case, after the plugin I'm writing has been unmapped from memory, with unhappy consequences.

The attached patch fixes this by remembering the callback ID and unregistering it if necessary.

Rich.

--
Emerging Technologies, Red Hat - http://et.redhat.com/~rjones/
Registered Address: Red Hat UK Ltd, Amberley Place, 107-111 Peascod
Street, Windsor, Berkshire, SL4 1TE, United Kingdom.  Registered in
England and Wales under Company Registration No. 03798903
diff -r 95f570fc49e1 src/vncdisplay.c
--- a/src/vncdisplay.c	Wed Jan 09 23:54:24 2008 -0500
+++ b/src/vncdisplay.c	Thu Jan 10 17:29:22 2008 +0000
@@ -40,6 +40,8 @@ struct _VncDisplayPrivate
 	struct gvnc_framebuffer fb;
 	struct coroutine coroutine;
 	struct gvnc *gvnc;
+
+	guint open_id;
 
 	gboolean in_pointer_grab;
 	gboolean in_keyboard_grab;
@@ -889,6 +891,8 @@ static gboolean do_vnc_display_open(gpoi
 		return FALSE;
 	}
 
+	obj->priv->open_id = 0;
+
 	co = &obj->priv->coroutine;
 
 	co->stack_size = 16 << 20;
@@ -911,7 +915,7 @@ gboolean vnc_display_open_fd(VncDisplay 
 	obj->priv->port = NULL;
 
 	g_object_ref(G_OBJECT(obj)); /* Unref'd when co-routine exits */
-	g_idle_add(do_vnc_display_open, obj);
+	obj->priv->open_id = g_idle_add(do_vnc_display_open, obj);
 
 	return TRUE;
 }
@@ -933,7 +937,7 @@ gboolean vnc_display_open_host(VncDispla
 	}
 
 	g_object_ref(G_OBJECT(obj)); /* Unref'd when co-routine exits */
-	g_idle_add(do_vnc_display_open, obj);
+	obj->priv->open_id = g_idle_add(do_vnc_display_open, obj);
 	return TRUE;
 }
 
@@ -946,6 +950,11 @@ gboolean vnc_display_is_open(VncDisplay 
 
 void vnc_display_close(VncDisplay *obj)
 {
+	if (obj->priv->open_id) {
+		g_source_remove (obj->priv->open_id);
+		obj->priv->open_id = 0;
+	}
+
 	if (obj->priv->gvnc == NULL)
 		return;
 

Attachment: smime.p7s
Description: S/MIME Cryptographic Signature



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]