gphoto2 backend fixes



Hey,

Here's a patch that fixes a couple of problems with gphoto2 devices

 - The support for multiple storage heads broke some buggy devices (such
   as the iPhone) for which the basedir of the storage head changes
   every time the device is initialized.

 - There was a silly logical bug that prevented us from detecting music
   players reported by HAL.

 - Minor cleanups in the gphoto2 volume monitor.

The next item on my list is to make the rest of the desktop handles
shadowed mounts. There are two ways to fix this

 1. Go through all GVolumeMonitor users and make them honor the
    g_mount_is_shadowed() flag; or

 2. Add new API to GVolumeMonitor

     get_shadowed_mounts()
     ::shadowed-mount-added
     ::shadowed-mount-removed
     ::shadowed-mount-pre-unmount
     ::shadowed-mount-changed

    and a) port the volume monitors we have in gio+gvfs to this.

So I think 2. is probably the best solution but I wanted to check here
first.

   David
Index: ChangeLog
===================================================================
--- ChangeLog	(revision 2206)
+++ ChangeLog	(working copy)
@@ -1,3 +1,21 @@
+2009-02-10  David Zeuthen  <davidz redhat com>
+
+	Make the gphoto2 backend work with buggy devices (such as the
+	iPhone) where the basedir of the store changes.
+
+	* daemon/gvfsbackendgphoto2.c: Revert the patch from #520123 that
+	removed the ignore_prefix handling. Change ensure_ignore_prefix()
+	to only use an ignore prefix if there is exactly one storage head.
+
+	* monitor/gphoto2/ggphoto2volumemonitor.c: Nuke orphan mount
+	handling since that is superseeded by shadow mounts. Also avoid
+	appending the store name if there is only one storage head.
+
+	* monitor/gphoto2/ggphoto2volume.[ch]: Rename foreign_mount_root
+	to activation_root since that is really what it is now. Also
+	fix a silly logical bug whereby music players (as reported by
+	HAL) weren't detected.
+
 2009-02-05  Bastien Nocera  <hadess hadess net>
 
 	Bug 563788 – GNOME Goal: Clean up GLib and GTK+ includes
Index: monitor/gphoto2/ggphoto2volume.c
===================================================================
--- monitor/gphoto2/ggphoto2volume.c	(revision 2206)
+++ monitor/gphoto2/ggphoto2volume.c	(working copy)
@@ -47,8 +47,7 @@
   HalDevice *device;
   HalDevice *drive_device;
 
-  GFile *foreign_mount_root;
-  GMount *foreign_mount;
+  GFile *activation_root;
 
   char *name;
   char *icon;
@@ -70,12 +69,9 @@
   if (volume->device != NULL)
     g_object_unref (volume->device);
 
-  if (volume->foreign_mount_root != NULL)
-    g_object_unref (volume->foreign_mount_root);
+  if (volume->activation_root != NULL)
+    g_object_unref (volume->activation_root);
 
-  if (volume->foreign_mount != NULL)
-    g_object_unref (volume->foreign_mount);
-
   if (volume->volume_monitor != NULL)
     g_object_remove_weak_pointer (G_OBJECT (volume->volume_monitor), (gpointer) &(volume->volume_monitor));
 
@@ -248,7 +244,7 @@
 g_gphoto2_volume_new (GVolumeMonitor   *volume_monitor,
                       HalDevice        *device,
                       HalPool          *pool,
-                      GFile            *foreign_mount_root)
+                      GFile            *activation_root)
 {
   GGPhoto2Volume *volume;
   HalDevice *drive_device;
@@ -258,11 +254,11 @@
   g_return_val_if_fail (volume_monitor != NULL, NULL);
   g_return_val_if_fail (device != NULL, NULL);
   g_return_val_if_fail (pool != NULL, NULL);
-  g_return_val_if_fail (foreign_mount_root != NULL, NULL);
+  g_return_val_if_fail (activation_root != NULL, NULL);
 
-  if (!hal_device_has_capability (device, "camera") ||
-      (hal_device_has_capability (device, "portable_audio_player") &&
-       hal_device_get_property_bool (device, "camera.libgphoto2.support")))
+  if (!(hal_device_has_capability (device, "camera") ||
+        (hal_device_has_capability (device, "portable_audio_player") &&
+         hal_device_get_property_bool (device, "camera.libgphoto2.support"))))
     return NULL;
 
   /* OK, so we abuse storage_udi and drive_device for the USB main
@@ -287,7 +283,7 @@
   volume->device_path = g_strdup (device_path);
   volume->device = g_object_ref (device);
   volume->drive_device = g_object_ref (drive_device);
-  volume->foreign_mount_root = foreign_mount_root != NULL ? g_object_ref (foreign_mount_root) : NULL;
+  volume->activation_root = g_object_ref (activation_root);
 
   g_signal_connect_object (device, "hal_property_changed", (GCallback) hal_changed, volume, 0);
   g_signal_connect_object (drive_device, "hal_property_changed", (GCallback) hal_changed, volume, 0);
@@ -361,16 +357,7 @@
 static GMount *
 g_gphoto2_volume_get_mount (GVolume *volume)
 {
-  GGPhoto2Volume *gphoto2_volume = G_GPHOTO2_VOLUME (volume);
-  GMount *mount;
-
-  G_LOCK (gphoto2_volume);
-  mount = NULL;
-  if (gphoto2_volume->foreign_mount != NULL)
-    mount = g_object_ref (gphoto2_volume->foreign_mount);
-  G_UNLOCK (gphoto2_volume);
-
-  return mount;
+  return NULL;
 }
 
 gboolean
@@ -388,101 +375,51 @@
   return res;
 }
 
-static void
-foreign_mount_unmounted (GMount *mount, gpointer user_data)
-{
-  GGPhoto2Volume *volume = G_GPHOTO2_VOLUME (user_data);
-  gboolean check;
-
-  G_LOCK (gphoto2_volume);
-  check = volume->foreign_mount == mount;
-  G_UNLOCK (gphoto2_volume);
-  if (check)
-    g_gphoto2_volume_adopt_foreign_mount (volume, NULL);
-}
-
-void
-g_gphoto2_volume_adopt_foreign_mount (GGPhoto2Volume *volume, GMount *foreign_mount)
-{
-  G_LOCK (gphoto2_volume);
-  if (volume->foreign_mount != NULL)
-    g_object_unref (volume->foreign_mount);
-
-  if (foreign_mount != NULL)
-    {
-      volume->foreign_mount =  g_object_ref (foreign_mount);
-      g_signal_connect_object (foreign_mount, "unmounted", (GCallback) foreign_mount_unmounted, volume, 0);
-    }
-  else
-    volume->foreign_mount =  NULL;
-
-  g_idle_add (changed_in_idle, g_object_ref (volume));
-  G_UNLOCK (gphoto2_volume);
-}
-
-gboolean
-g_gphoto2_volume_has_foreign_mount_root (GGPhoto2Volume       *volume,
-                                     GFile            *mount_root)
-{
-  GGPhoto2Volume *gphoto2_volume = G_GPHOTO2_VOLUME (volume);
-  gboolean res;
-
-  G_LOCK (gphoto2_volume);
-  res = FALSE;
-  if (gphoto2_volume->foreign_mount_root != NULL)
-    res = g_file_equal (gphoto2_volume->foreign_mount_root, mount_root);
-  G_UNLOCK (gphoto2_volume);
-
-  return res;
-}
-
-
-
 typedef struct
 {
   GGPhoto2Volume *enclosing_volume;
   GAsyncReadyCallback  callback;
   gpointer user_data;
-} ForeignMountOp;
+} ActivationMountOp;
 
 static void
-mount_foreign_callback (GObject *source_object,
+mount_callback (GObject *source_object,
                         GAsyncResult *res,
                         gpointer user_data)
 {
-  ForeignMountOp *data = user_data;
+  ActivationMountOp *data = user_data;
   data->callback (G_OBJECT (data->enclosing_volume), res, data->user_data);
   g_free (data);
 }
 
 static void
 g_gphoto2_volume_mount (GVolume             *volume,
-                    GMountMountFlags     flags,
-                    GMountOperation     *mount_operation,
-                    GCancellable        *cancellable,
-                    GAsyncReadyCallback  callback,
-                    gpointer             user_data)
+                        GMountMountFlags     flags,
+                        GMountOperation     *mount_operation,
+                        GCancellable        *cancellable,
+                        GAsyncReadyCallback  callback,
+                        gpointer             user_data)
 {
   GGPhoto2Volume *gphoto2_volume = G_GPHOTO2_VOLUME (volume);
-  ForeignMountOp *data;
+  ActivationMountOp *data;
 
   /*g_warning ("gphoto2_volume_mount (can_mount=%d foreign=%p device_path=%s)",
               g_gphoto2_volume_can_mount (volume),
-              gphoto2_volume->foreign_mount_root,
+              gphoto2_volume->activation_root,
               gphoto2_volume->device_path);*/
 
   G_LOCK (gphoto2_volume);
 
-  data = g_new0 (ForeignMountOp, 1);
+  data = g_new0 (ActivationMountOp, 1);
   data->enclosing_volume = gphoto2_volume;
   data->callback = callback;
   data->user_data = user_data;
 
-  g_file_mount_enclosing_volume (gphoto2_volume->foreign_mount_root,
+  g_file_mount_enclosing_volume (gphoto2_volume->activation_root,
                                  0,
                                  mount_operation,
                                  cancellable,
-                                 mount_foreign_callback,
+                                 mount_callback,
                                  data);
 
   G_UNLOCK (gphoto2_volume);
@@ -497,7 +434,7 @@
   gboolean res;
 
   G_LOCK (gphoto2_volume);
-  res = g_file_mount_enclosing_volume_finish (gphoto2_volume->foreign_mount_root, result, error);
+  res = g_file_mount_enclosing_volume_finish (gphoto2_volume->activation_root, result, error);
   G_UNLOCK (gphoto2_volume);
 
   return res;
@@ -551,7 +488,7 @@
 {
   GGPhoto2Volume *gphoto2_volume = G_GPHOTO2_VOLUME (volume);
 
-  return g_object_ref (gphoto2_volume->foreign_mount_root);
+  return g_object_ref (gphoto2_volume->activation_root);
 }
 
 static void
Index: monitor/gphoto2/ggphoto2volume.h
===================================================================
--- monitor/gphoto2/ggphoto2volume.h	(revision 2206)
+++ monitor/gphoto2/ggphoto2volume.h	(working copy)
@@ -48,17 +48,11 @@
 GGPhoto2Volume *g_gphoto2_volume_new            (GVolumeMonitor   *volume_monitor,
                                                  HalDevice        *device,
                                                  HalPool          *pool,
-                                                 GFile            *foreign_mount_root);
+                                                 GFile            *activation_root);
 
 gboolean    g_gphoto2_volume_has_udi        (GGPhoto2Volume       *volume,
                                              const char       *udi);
 
-gboolean    g_gphoto2_volume_has_foreign_mount_root (GGPhoto2Volume       *volume,
-                                                     GFile            *mount_root);
-
-void        g_gphoto2_volume_adopt_foreign_mount (GGPhoto2Volume *volume,
-                                                  GMount *foreign_mount);
-
 void        g_gphoto2_volume_removed        (GGPhoto2Volume       *volume);
 
 G_END_DECLS
Index: monitor/gphoto2/ggphoto2volumemonitor.c
===================================================================
--- monitor/gphoto2/ggphoto2volumemonitor.c	(revision 2206)
+++ monitor/gphoto2/ggphoto2volumemonitor.c	(working copy)
@@ -234,48 +234,6 @@
   return get_hal_pool() != NULL;
 }
 
-static GVolume *
-adopt_orphan_mount (GMount *mount, GVolumeMonitor *monitor)
-{
-  GList *l;
-  GFile *mount_root;
-  GVolume *ret;
-
-  /* This is called by the union volume monitor which does
-     have a ref to this. So its guaranteed to live, unfortunately
-     the pointer is not passed as an argument :/
-  */
-  ret = NULL;
-
-  G_LOCK (hal_vm);
-  if (the_volume_monitor == NULL)
-    {
-      G_UNLOCK (hal_vm);
-      return NULL;
-    }
-
-  mount_root = g_mount_get_root (mount);
-
-  /* gphoto2:// are foreign mounts */
-  for (l = the_volume_monitor->camera_volumes; l != NULL; l = l->next)
-    {
-      GGPhoto2Volume *volume = l->data;
-
-      if (g_gphoto2_volume_has_foreign_mount_root (volume, mount_root))
-        {
-          g_gphoto2_volume_adopt_foreign_mount (volume, mount);
-          ret = g_object_ref (volume);
-          goto found;
-        }
-    }
-
- found:
-  g_object_unref (mount_root);
-
-  G_UNLOCK (hal_vm);
-  return ret;
-}
-
 static void
 g_gphoto2_volume_monitor_class_init (GGPhoto2VolumeMonitorClass *klass)
 {
@@ -291,7 +249,6 @@
   monitor_class->get_connected_drives = get_connected_drives;
   monitor_class->get_volume_for_uuid = get_volume_for_uuid;
   monitor_class->get_mount_for_uuid = get_mount_for_uuid;
-  monitor_class->adopt_orphan_mount = adopt_orphan_mount;
   monitor_class->is_supported = is_supported;
 }
 
@@ -575,11 +532,11 @@
   for (l = added; l != NULL; l = l->next)
     {
       HalDevice *d = l->data;
-      GFile *foreign_mount_root;
       int usb_bus_num;
       int usb_device_num;
       gboolean found;
       GList *store_heads, *l;
+      guint num_store_heads;
 
       /* Look for the device in the added volumes, so as
        * not to add devices that are both audio players, and cameras */
@@ -600,32 +557,44 @@
       usb_device_num = hal_device_get_property_int (d, "usb.linux.device_number");
 
       store_heads = get_stores_for_camera (usb_bus_num, usb_device_num);
+      num_store_heads = g_list_length (store_heads);
       for (l = store_heads ; l != NULL; l = l->next)
         {
           char *store_path = (char *) l->data;
-          char *uri;
+          GFile *activation_mount_root;
+          gchar *uri;
 
-	  uri = g_strdup_printf ("gphoto2://[usb:%03d,%03d]/%s", usb_bus_num, usb_device_num,
-	  			 store_path[0] == '/' ? store_path + 1 : store_path);
+          /* If we only have a single store, don't use the store name at all. The backend automatically
+           * prepend the storename; this is to work around bugs with devices (like the iPhone) for which
+           * the store name changes every time the camera is initialized (e.g. mounted).
+           */
+          if (num_store_heads == 1)
+            {
+              uri = g_strdup_printf ("gphoto2://[usb:%03d,%03d]", usb_bus_num, usb_device_num);
+            }
+          else
+            {
+              uri = g_strdup_printf ("gphoto2://[usb:%03d,%03d]/%s", usb_bus_num, usb_device_num,
+                                     store_path[0] == '/' ? store_path + 1 : store_path);
+            }
+          activation_mount_root = g_file_new_for_uri (uri);
+          g_free (uri);
 
-	  foreign_mount_root = g_file_new_for_uri (uri);
-	  g_free (uri);
-
-	  udi = hal_device_get_udi (d);
-	  volume = g_gphoto2_volume_new (G_VOLUME_MONITOR (monitor),
-					 d,
-					 monitor->pool,
-					 foreign_mount_root);
-	  g_object_unref (foreign_mount_root);
-	  if (volume != NULL)
+          udi = hal_device_get_udi (d);
+          volume = g_gphoto2_volume_new (G_VOLUME_MONITOR (monitor),
+                                         d,
+                                         monitor->pool,
+                                         activation_mount_root);
+          if (volume != NULL)
             {
-	      monitor->camera_volumes = g_list_prepend (monitor->camera_volumes, volume);
-	      *added_volumes = g_list_prepend (*added_volumes, g_object_ref (volume));
-	    }
+              monitor->camera_volumes = g_list_prepend (monitor->camera_volumes, volume);
+              *added_volumes = g_list_prepend (*added_volumes, g_object_ref (volume));
+            }
 
-	  g_free (l->data);
-
+          if (activation_mount_root != NULL)
+            g_object_unref (activation_mount_root);
         }
+      g_list_foreach (store_heads, (GFunc) g_free, NULL);
       g_list_free (store_heads);
     }
 
Index: daemon/gvfsbackendgphoto2.c
===================================================================
--- daemon/gvfsbackendgphoto2.c	(revision 2206)
+++ daemon/gvfsbackendgphoto2.c	(working copy)
@@ -172,6 +172,9 @@
   GPContext *context;
   Camera *camera;
 
+  /* see comment in ensure_ignore_prefix() */
+  char *ignore_prefix;
+
   /* list of open files */
   int num_open_files_for_reading;
 
@@ -226,7 +229,7 @@
 /* ------------------------------------------------------------------------------------------------- */
 
 typedef struct {
-  /* this is the path of the dir/file */
+  /* this is the path of the dir/file including ignore_prefix */
   char *path;
   GVfsMonitor *vfs_monitor;
 } MonitorProxy;
@@ -348,6 +351,8 @@
   GList *l;
   char *filepath;
 
+  g_return_if_fail (g_str_has_prefix (dir, gphoto2_backend->ignore_prefix));
+
   DEBUG ("monitors_emit_internal() %s for '%s' '%s'", event_name, dir, name);
 
   for (l = gphoto2_backend->dir_monitor_proxies; l != NULL; l = l->next)
@@ -356,7 +361,7 @@
       if (strcmp (proxy->path, dir) == 0)
         {
           char *path;
-          path = g_build_filename (dir, name, NULL);
+          path = g_build_filename (dir + strlen (gphoto2_backend->ignore_prefix), name, NULL);
           g_vfs_monitor_emit_event (proxy->vfs_monitor, event, path, NULL);
           DEBUG ("  emitted %s for '%s' on dir monitor for '%s'", event_name, path, dir);
           g_free (path);
@@ -369,8 +374,9 @@
       MonitorProxy *proxy = l->data;
       if (strcmp (proxy->path, filepath) == 0)
         {
-          g_vfs_monitor_emit_event (proxy->vfs_monitor, event, filepath, NULL);
-          DEBUG ("  emitted %s for '%s' on file monitor", event_name, filepath);
+          const char *path = filepath + strlen (gphoto2_backend->ignore_prefix);
+          g_vfs_monitor_emit_event (proxy->vfs_monitor, event, path, NULL);
+          DEBUG ("  emitted %s for '%s' on file monitor", event_name, path);
         }
     }
   g_free (filepath);
@@ -555,6 +561,9 @@
   g_free (gphoto2_backend->hal_icon_name);
   gphoto2_backend->hal_icon_name = NULL;
 
+  g_free (gphoto2_backend->ignore_prefix);
+  gphoto2_backend->ignore_prefix = NULL;
+
   if (gphoto2_backend->info_cache != NULL)
     {
       g_hash_table_unref (gphoto2_backend->info_cache);
@@ -903,15 +912,15 @@
 /* ------------------------------------------------------------------------------------------------- */
 
 static void
-split_filename (GVfsBackendGphoto2 *gphoto2_backend, const char *filename, char **dir, char **name)
+split_filename_with_ignore_prefix (GVfsBackendGphoto2 *gphoto2_backend, const char *filename, char **dir, char **name)
 {
   char *s;
 
   s = g_path_get_dirname (filename);
   if (s[0] == '/')
-    *dir = g_strconcat ("/", s + 1, NULL);
+    *dir = g_strconcat (gphoto2_backend->ignore_prefix, s + 1, NULL);
   else
-    *dir = g_strconcat ("/", s, NULL);
+    *dir = g_strconcat (gphoto2_backend->ignore_prefix, s, NULL);
   g_free (s);
 
   if (strcmp (filename, "/") == 0)
@@ -923,11 +932,28 @@
   if (s[strlen(s)] == '/')
     s[strlen(s)] = '\0';
 
-  /*DEBUG ("split_filename: '%s' -> '%s' '%s'", filename, *dir, *name);*/
+  /*DEBUG ("split_filename_with_ignore_prefix: '%s' -> '%s' '%s'", filename, *dir, *name);*/
 }
 
 /* ------------------------------------------------------------------------------------------------- */
 
+static char *
+add_ignore_prefix (GVfsBackendGphoto2 *gphoto2_backend, const char *filename)
+{
+  char *result;
+
+  if (filename[0] == '/')
+    result = g_strconcat (gphoto2_backend->ignore_prefix, filename + 1, NULL);
+  else
+    result = g_strconcat (gphoto2_backend->ignore_prefix, filename, NULL);
+
+  /*DEBUG ("add_ignore_prefix: '%s' -> '%s'", filename, result);*/
+  return result;
+}
+
+/* ------------------------------------------------------------------------------------------------- */
+
+/* the passed 'dir' variable must contain ignore_prefix */
 static gboolean
 file_get_info (GVfsBackendGphoto2 *gphoto2_backend, 
                const char *dir, 
@@ -951,7 +977,7 @@
   full_path = g_build_filename (dir, name, NULL);
   DEBUG ("file_get_info() try_cache_only=%d dir='%s', name='%s'\n"
          "                full_path='%s'", 
-         try_cache_only, dir, name, full_path);
+         try_cache_only, dir, name, full_path, gphoto2_backend->ignore_prefix);
 
 
   /* first look up cache */
@@ -978,7 +1004,7 @@
   g_file_info_unset_attribute_mask (info);
 
   /* handle root directory */
-  if (strcmp (full_path, "/") == 0)
+  if (strcmp (full_path, gphoto2_backend->ignore_prefix) == 0 || strcmp (full_path, "/") == 0)
     {
       char *display_name;
       display_name = compute_display_name (gphoto2_backend);
@@ -1110,7 +1136,7 @@
       GMountSpec *mount_spec;
 
       mount_spec = g_vfs_backend_get_mount_spec (G_VFS_BACKEND (gphoto2_backend));
-      icon_id = g_strdup_printf ("preview:%s/%s", dir, name);
+      icon_id = g_strdup_printf ("preview:%s/%s", dir + strlen (gphoto2_backend->ignore_prefix), name);
       icon = g_vfs_icon_new (mount_spec,
                              icon_id);
       g_file_info_set_attribute_object (info,
@@ -1268,6 +1294,54 @@
 
 /* ------------------------------------------------------------------------------------------------- */
 
+/* If we only have a single storage head, the gphoto2 volume monitor
+ * will not use activation roots into our mount. This is mainly to
+ * work around buggy devices where the basedir of the storage head
+ * changes on every camera initialization, e.g. the iPhone.
+ *
+ * So, if we have only one storage head, do use basedir of that
+ * head as ignore_prefix.
+ *
+ * See also update_cameras() in ggphoto2volumemonitor.c.
+ *
+ * This function needs to be called from do_mount().
+ */
+static gboolean
+ensure_ignore_prefix (GVfsBackendGphoto2 *gphoto2_backend, GVfsJob *job)
+{
+  gchar *prefix;
+  CameraStorageInformation *storage_info;
+  int num_storage_info;
+
+  /* already set */
+  if (gphoto2_backend->ignore_prefix != NULL)
+    return TRUE;
+
+  prefix = NULL;
+
+  if (gp_camera_get_storageinfo (gphoto2_backend->camera,
+                                 &storage_info,
+                                 &num_storage_info,
+                                 gphoto2_backend->context) != 0)
+    goto out;
+
+  if (num_storage_info > 1)
+    goto out;
+
+  prefix = g_strdup_printf ("%s/", storage_info[0].basedir);
+
+ out:
+
+  if (prefix == NULL)
+    gphoto2_backend->ignore_prefix = g_strdup ("/");
+  else
+    gphoto2_backend->ignore_prefix = prefix;
+
+  return TRUE;
+}
+
+/* ------------------------------------------------------------------------------------------------- */
+
 static void
 do_mount (GVfsBackend *backend,
 	  GVfsJobMount *job,
@@ -1443,6 +1517,12 @@
       return;
     }
 
+  if (!ensure_ignore_prefix (gphoto2_backend, G_VFS_JOB (job)))
+    {
+      release_device (gphoto2_backend);
+      return;
+    }
+
   /* Translator: %s represents the device, e.g. usb:001,042  */
   fuse_name = g_strdup_printf (_("gphoto2 mount on %s"), gphoto2_backend->gphoto2_port);
   icon_name = compute_icon_name (gphoto2_backend);
@@ -1589,7 +1669,7 @@
 
   ensure_not_dirty (gphoto2_backend);
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   if (is_directory (gphoto2_backend, dir, name))
     {
@@ -1819,7 +1899,7 @@
 
   DEBUG ("query_info (%s)", filename);
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   error = NULL;
   if (!file_get_info (gphoto2_backend, dir, name, info, &error, FALSE))
@@ -1855,7 +1935,7 @@
 
   ret = FALSE;
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   if (!file_get_info (gphoto2_backend, dir, name, info, NULL, TRUE))
     {
@@ -1889,6 +1969,7 @@
   CameraList *list;
   int n;
   int rc;
+  char *filename;
   gboolean using_cached_dir_list;
   gboolean using_cached_file_list;
   char *as_dir;
@@ -1898,9 +1979,10 @@
   using_cached_dir_list = FALSE;
   using_cached_file_list = FALSE;
 
+  filename = add_ignore_prefix (gphoto2_backend, given_filename);
   DEBUG ("enumerate (%s)", given_filename);
 
-  split_filename (gphoto2_backend, given_filename, &as_dir, &as_name);
+  split_filename_with_ignore_prefix (gphoto2_backend, given_filename, &as_dir, &as_name);
   if (!is_directory (gphoto2_backend, as_dir, as_name))
     {
       if (is_regular (gphoto2_backend, as_dir, as_name))
@@ -1924,18 +2006,18 @@
 
   /* first, list the folders */
   g_mutex_lock (gphoto2_backend->lock);
-  list = g_hash_table_lookup (gphoto2_backend->dir_name_cache, given_filename);
+  list = g_hash_table_lookup (gphoto2_backend->dir_name_cache, filename);
   if (list == NULL)
     {
       g_mutex_unlock (gphoto2_backend->lock);
 
       ensure_not_dirty (gphoto2_backend);
 
-      DEBUG ("  Generating dir list for dir '%s'", given_filename);
+      DEBUG ("  Generating dir list for dir '%s'", filename);
 
       gp_list_new (&list);
       rc = gp_camera_folder_list_folders (gphoto2_backend->camera, 
-                                          given_filename, 
+                                          filename, 
                                           list, 
                                           gphoto2_backend->context);
       if (rc != 0)
@@ -1943,12 +2025,13 @@
           error = get_error_from_gphoto2 (_("Failed to get folder list"), rc);
           g_vfs_job_failed_from_error (G_VFS_JOB (job), error);
           g_error_free (error);
+          g_free (filename);
           return;
         }  
     }
   else
     {
-      DEBUG ("  Using cached dir list for dir '%s'", given_filename);
+      DEBUG ("  Using cached dir list for dir '%s'", filename);
       using_cached_dir_list = TRUE;
       gp_list_ref (list);
       g_mutex_unlock (gphoto2_backend->lock);
@@ -1961,7 +2044,7 @@
       DEBUG ("  enum folder '%s'", name);
       info = g_file_info_new ();
       error = NULL;
-      if (!file_get_info (gphoto2_backend, given_filename, name, info, &error, FALSE))
+      if (!file_get_info (gphoto2_backend, filename, name, info, &error, FALSE))
         {
           g_vfs_job_failed_from_error (G_VFS_JOB (job), error);
           g_error_free (error);
@@ -1976,7 +2059,7 @@
     {
 #ifndef DEBUG_NO_CACHING
       g_mutex_lock (gphoto2_backend->lock);
-      g_hash_table_insert (gphoto2_backend->dir_name_cache, g_strdup (given_filename), list);
+      g_hash_table_insert (gphoto2_backend->dir_name_cache, g_strdup (filename), list);
       g_mutex_unlock (gphoto2_backend->lock);
 #endif
     }
@@ -1990,17 +2073,17 @@
 
   /* then list the files in each folder */
   g_mutex_lock (gphoto2_backend->lock);
-  list = g_hash_table_lookup (gphoto2_backend->file_name_cache, given_filename);
+  list = g_hash_table_lookup (gphoto2_backend->file_name_cache, filename);
   if (list == NULL)
     {
       g_mutex_unlock (gphoto2_backend->lock);
       ensure_not_dirty (gphoto2_backend);
 
-      DEBUG ("  Generating file list for dir '%s'", given_filename);
+      DEBUG ("  Generating file list for dir '%s'", filename);
 
       gp_list_new (&list);
       rc = gp_camera_folder_list_files (gphoto2_backend->camera, 
-                                        given_filename,
+                                        filename, 
                                         list, 
                                         gphoto2_backend->context);
       if (rc != 0)
@@ -2008,12 +2091,13 @@
           error = get_error_from_gphoto2 (_("Failed to get file list"), rc);
           g_vfs_job_failed_from_error (G_VFS_JOB (job), error);
           g_error_free (error);
+          g_free (filename);
           return;
         }
     }
   else
     {
-      DEBUG ("  Using cached file list for dir '%s'", given_filename);
+      DEBUG ("  Using cached file list for dir '%s'", filename);
       using_cached_file_list = TRUE;
       gp_list_ref (list);
       g_mutex_unlock (gphoto2_backend->lock);
@@ -2027,7 +2111,7 @@
 
       info = g_file_info_new ();
       error = NULL;
-      if (!file_get_info (gphoto2_backend, given_filename, name, info, &error, FALSE))
+      if (!file_get_info (gphoto2_backend, filename, name, info, &error, FALSE))
         {
           g_vfs_job_failed_from_error (G_VFS_JOB (job), error);
           g_error_free (error);
@@ -2042,7 +2126,7 @@
     {
 #ifndef DEBUG_NO_CACHING
       g_mutex_lock (gphoto2_backend->lock);
-      g_hash_table_insert (gphoto2_backend->file_name_cache, g_strdup (given_filename), list);
+      g_hash_table_insert (gphoto2_backend->file_name_cache, g_strdup (filename), list);
       g_mutex_unlock (gphoto2_backend->lock);
 #endif
     }
@@ -2060,6 +2144,8 @@
   g_list_foreach (l, (GFunc) g_object_unref, NULL);
   g_list_free (l);
   g_vfs_job_enumerate_done (job);
+
+  g_free (filename);
 }
 
 /* ------------------------------------------------------------------------------------------------- */
@@ -2077,15 +2163,17 @@
   GError *error;
   CameraList *list;
   int n;
+  char *filename;
   const char *name;
 
   l = NULL;
 
+  filename = add_ignore_prefix (gphoto2_backend, given_filename);
   DEBUG ("try_enumerate (%s)", given_filename);
 
   /* first, list the folders */
   g_mutex_lock (gphoto2_backend->lock);
-  list = g_hash_table_lookup (gphoto2_backend->dir_name_cache, given_filename);
+  list = g_hash_table_lookup (gphoto2_backend->dir_name_cache, filename);
   if (list == NULL)
     {
       g_mutex_unlock (gphoto2_backend->lock);
@@ -2098,7 +2186,7 @@
       gp_list_get_name (list, n, &name);
       DEBUG ("  try_enum folder '%s'", name);
       info = g_file_info_new ();
-      if (!file_get_info (gphoto2_backend, given_filename, name, info, &error, TRUE))
+      if (!file_get_info (gphoto2_backend, filename, name, info, &error, TRUE))
         {
           g_mutex_lock (gphoto2_backend->lock);
           gp_list_unref (list);
@@ -2113,7 +2201,7 @@
 
   /* then list the files in each folder */
   g_mutex_lock (gphoto2_backend->lock);
-  list = g_hash_table_lookup (gphoto2_backend->file_name_cache, given_filename);
+  list = g_hash_table_lookup (gphoto2_backend->file_name_cache, filename);
   if (list == NULL)
     {
       g_mutex_unlock (gphoto2_backend->lock);
@@ -2127,7 +2215,7 @@
       DEBUG ("  try_enum file '%s'", name);
 
       info = g_file_info_new ();
-      if (!file_get_info (gphoto2_backend, given_filename, name, info, &error, TRUE))
+      if (!file_get_info (gphoto2_backend, filename, name, info, &error, TRUE))
         {
           g_mutex_lock (gphoto2_backend->lock);
           gp_list_unref (list);
@@ -2148,6 +2236,7 @@
   g_list_free (l);
   g_vfs_job_enumerate_done (job);
 
+  g_free (filename);
   DEBUG ("  YAY got info from cache for try_enumerate (%s)", given_filename);
   return TRUE;
 
@@ -2155,6 +2244,7 @@
   g_list_foreach (l, (GFunc) g_object_unref, NULL);
   g_list_free (l);
 
+  g_free (filename);
   DEBUG ("  BUU no info from cache for try_enumerate (%s)", given_filename);
   return FALSE;
 }
@@ -2282,7 +2372,7 @@
       goto out;
     }
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   rc = gp_camera_folder_make_dir (gphoto2_backend->camera,
                                   dir,
@@ -2491,7 +2581,7 @@
       goto out;
     }
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   /* refuse is desired name is already taken */
   if (is_directory (gphoto2_backend, dir, display_name) ||
@@ -2546,7 +2636,7 @@
   monitors_emit_deleted (gphoto2_backend, dir, name);
   monitors_emit_created (gphoto2_backend, dir, display_name);
 
-  new_name = g_build_filename (dir, display_name, NULL);
+  new_name = g_build_filename (dir + strlen (gphoto2_backend->ignore_prefix), display_name, NULL);
   g_vfs_job_set_display_name_set_new_path (job, new_name);
 
   g_vfs_job_succeeded (G_VFS_JOB (job));
@@ -2588,11 +2678,12 @@
       goto out;
     }
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   if (is_directory (gphoto2_backend, dir, name))
     {
-      if (!is_directory_empty (gphoto2_backend, filename))
+      dir_name = add_ignore_prefix (gphoto2_backend, filename);
+      if (!is_directory_empty (gphoto2_backend, dir_name))
         {
           g_vfs_job_failed (G_VFS_JOB (job), G_IO_ERROR,
                             G_IO_ERROR_NOT_EMPTY,
@@ -2680,7 +2771,7 @@
       goto out;
     }
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   if (is_directory (gphoto2_backend, dir, name))
     {
@@ -2838,7 +2929,7 @@
 
   dir = NULL;
   name = NULL;
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
   
   /* write a new file
    * - will delete the existing one when done in do_close_write() 
@@ -2865,7 +2956,7 @@
 
   dir = NULL;
   name = NULL;
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
   
   /* write a new file
    * - will read existing data in do_create_internal
@@ -3085,8 +3176,8 @@
 
   ensure_not_dirty (gphoto2_backend);
 
-  split_filename (gphoto2_backend, source, &src_dir, &src_name);
-  split_filename (gphoto2_backend, destination, &dst_dir, &dst_name);
+  split_filename_with_ignore_prefix (gphoto2_backend, source, &src_dir, &src_name);
+  split_filename_with_ignore_prefix (gphoto2_backend, destination, &dst_dir, &dst_name);
 
   /* this is an limited implementation that can only move files / folders in the same directory */
   if (strcmp (src_dir, dst_dir) != 0)
@@ -3220,10 +3311,10 @@
 
   DEBUG ("create_dir_monitor (%s)", filename);
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   proxy = g_new0 (MonitorProxy, 1);
-  proxy->path = g_strdup (filename);
+  proxy->path = add_ignore_prefix (gphoto2_backend, filename);
   proxy->vfs_monitor = g_vfs_monitor_new (backend);
 
   gphoto2_backend->dir_monitor_proxies = g_list_prepend (gphoto2_backend->dir_monitor_proxies, proxy);
@@ -3270,10 +3361,10 @@
 
   DEBUG ("create_file_monitor (%s)", filename);
 
-  split_filename (gphoto2_backend, filename, &dir, &name);
+  split_filename_with_ignore_prefix (gphoto2_backend, filename, &dir, &name);
 
   proxy = g_new0 (MonitorProxy, 1);
-  proxy->path = g_strdup (filename);
+  proxy->path = add_ignore_prefix (gphoto2_backend, filename);
   proxy->vfs_monitor = g_vfs_monitor_new (backend);
 
   gphoto2_backend->file_monitor_proxies = g_list_prepend (gphoto2_backend->file_monitor_proxies, proxy);


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