[nautilus] monitor: watch for removal of non-native mounts on GVolumeMonitor



commit 3891241ba760c59d284b7579dbd340651c8d4d29
Author: Cosimo Cecchi <cosimoc gnome org>
Date:   Fri Oct 19 17:39:43 2012 -0400

    monitor: watch for removal of non-native mounts on GVolumeMonitor
    
    Nowadays, we rely on G_FILE_MONITOR_EVENT_UNMOUNTED to be emitted when a
    mount disappears, since we already monitor the directory, in order to
    switch the view to a different location.
    Since non-native mounts very likely won't have file monitoring though,
    we're not going to receive such events in that case, and fail to
    redirect the view as a consequence.
    This patch fixes it by listening to the mount-removed signal on
    GVolumeMonitor when a monitor is requested for a non-native mount, and
    emulating a file removal in that case.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=684226

 libnautilus-private/nautilus-monitor.c |   57 +++++++++++++++++++++++++++----
 1 files changed, 49 insertions(+), 8 deletions(-)
---
diff --git a/libnautilus-private/nautilus-monitor.c b/libnautilus-private/nautilus-monitor.c
index feeeb9b..487c308 100644
--- a/libnautilus-private/nautilus-monitor.c
+++ b/libnautilus-private/nautilus-monitor.c
@@ -33,6 +33,9 @@
 
 struct NautilusMonitor {
 	GFileMonitor *monitor;
+	GVolumeMonitor *volume_monitor;
+	GMount *mount;
+	GFile *location;
 };
 
 gboolean
@@ -70,6 +73,28 @@ call_consume_changes_idle_cb (gpointer not_used)
 }
 
 static void
+schedule_call_consume_changes (void)
+{
+	if (call_consume_changes_idle_id == 0) {
+		call_consume_changes_idle_id =
+			g_idle_add (call_consume_changes_idle_cb, NULL);
+	}
+}
+
+static void
+mount_removed (GVolumeMonitor *volume_monitor,
+	       GMount *mount,
+	       gpointer user_data)
+{
+	NautilusMonitor *monitor = user_data;
+
+	if (mount == monitor->mount) {
+		nautilus_file_changes_queue_file_removed (monitor->location);
+		schedule_call_consume_changes ();
+	}
+}
+
+static void
 dir_changed (GFileMonitor* monitor,
 	     GFile *child,
 	     GFile *other_file,
@@ -105,10 +130,7 @@ dir_changed (GFileMonitor* monitor,
 	g_free (uri);
 	g_free (to_uri);
 
-	if (call_consume_changes_idle_id == 0) {
-		call_consume_changes_idle_id = 
-			g_idle_add (call_consume_changes_idle_cb, NULL);
-	}
+	schedule_call_consume_changes ();
 }
  
 NautilusMonitor *
@@ -117,13 +139,25 @@ nautilus_monitor_directory (GFile *location)
 	GFileMonitor *dir_monitor;
 	NautilusMonitor *ret;
 
+	ret = g_new0 (NautilusMonitor, 1);
 	dir_monitor = g_file_monitor_directory (location, G_FILE_MONITOR_WATCH_MOUNTS, NULL, NULL);
 
-	ret = g_new0 (NautilusMonitor, 1);
-	ret->monitor = dir_monitor;
+	if (dir_monitor != NULL) {
+		ret->monitor = dir_monitor;
+	} else if (!g_file_is_native (location)) {
+		ret->mount = nautilus_get_mounted_mount_for_root (location);
+		ret->location = g_object_ref (location);
+		ret->volume_monitor = g_volume_monitor_get ();
+	}
+
+	if (ret->monitor != NULL) {
+		g_signal_connect (ret->monitor, "changed",
+				  G_CALLBACK (dir_changed), ret);
+	}
 
-	if (ret->monitor) {
-		g_signal_connect (ret->monitor, "changed", (GCallback)dir_changed, ret);
+	if (ret->volume_monitor != NULL) {
+		g_signal_connect (ret->volume_monitor, "mount-removed",
+				  G_CALLBACK (mount_removed), ret);
 	}
 
 	/* We return a monitor even on failure, so we can avoid later trying again */
@@ -139,5 +173,12 @@ nautilus_monitor_cancel (NautilusMonitor *monitor)
 		g_object_unref (monitor->monitor);
 	}
 
+	if (monitor->volume_monitor != NULL) {
+		g_signal_handlers_disconnect_by_func (monitor->volume_monitor, mount_removed, monitor);
+		g_object_unref (monitor->volume_monitor);
+	}
+
+	g_clear_object (&monitor->location);
+	g_clear_object (&monitor->mount);
 	g_free (monitor);
 }



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