gnome-vfs is going down, down, down

Work on the Nautilus gio-branch continues. We’re now down to 203 gnome-vfs calls in nautilus (803 initially) and zero in eel (92 originally). Now, 203 calls still sounds like a lot, but lets take a look at what uses gnome-vfs:

  1 libnautilus-private/nautilus-file-operations-progress.c
  3 libnautilus-private/nautilus-file.c
  4 libnautilus-private/nautilus-program-choosing.c
126 libnautilus-private/nautilus-file-operations.c
  3 libnautilus-private/nautilus-vfs-utils.c
  5 libnautilus-private/nautilus-file-utilities.c
  9 libnautilus-private/nautilus-dnd.c
  7 src/file-manager/fm-tree-view.c
  4 src/file-manager/fm-icon-view.c
  1 src/file-manager/fm-directory-view.c
  1 src/file-manager/fm-error-reporting.c
  8 src/file-manager/fm-directory-view-old.c
  5 src/nautilus-main.c
  1 src/nautilus-window-manage-views.c
 23 src/nautilus-connect-server-dialog.c

Almost all of it is in nautilus-file-operations.c, which is the implementation of things like copying/moving files, and displaying progress and other dialogs for that. This is certainly very important functionality, and it will be a bunch of work converting it, especially since it heavily uses the gnome_vfs_xfer API, which (thankfully) doesn’t exist in gio. But apart from that almost all gnome-vfs use in Nautilus is gone

I’ve also cleaned up the code in several places, removing crufty, old and unused code, in places replacing it with more modern Gtk+/glib functionality. Eel especially has dropped a lot of code. Lots of creds go to Paolo Borelli who has done a bunch of work on this.

On a slightly more end-user interesting tangent, today I updated the fuse code that hpj wrote (it had stopped working due to some internal changes) and integrated it with the gvfs backend for libgio. This means g_file_get_path() will now return a local fuse path even for non-local files. In practice this mean applications that do not access files via gio can still load and save files on e.g. remote shares like smb, ftp, sftp, etc.

I made a screencast to show this off. Check it out!

You can pick any new feature you want, as long as it is this one

This last week I’ve been working on the icon and thumbnail handling on the nautilus gio-branch. gnome-vfs doesn’t really handle icons at all in the API, so all the code related to selecting and rendering icons for files was done entirely in nautilus. The way this was done was also a bit weird compared to how other things worked.

Nautilus has this abstraction called NautilusFile that contains all the information we know about the file. You can request for it to load specific information, and to get notified when it changes. However, icons were not handled by this. Instead there is a class called NautilusIconFactory that lets you map from file to icon (and incidentally handle things like icon caching, loading thumbnails, etc). Sometimes the icons can change though, like when the icon theme is changed, so all consumers had to also watch the icons_changes signal on the icon factory (in addition to the changed signal on the NautilusFile).

gio adds support for icons (and to some extents thumbnails) directly in the vfs. In the normal case we decide what icon to use for a file in the same way (based on the mimetype). However, this happens in the gio backend, so if the backend has special needs for icons it can do whatever it wants.

This is great stuff and will allow backends to be more expressive, and applications need less code to handle icons. It does however mean that the code in Nautilus doesn’t really match the new APIs. So, since I had to completely restructure the code anyway, its with great pleasure I can announce that since yesterday NautilusIconFactory has been removed from the gio-branch, and the new icon and thumbnailing code is integrated with the NautilusFile object in a much saner way.

Most of this work is just changes needed to work with gio rather than new features. I did however add one new feature. If you resize icons so that they are larger that the thumbnail generated for them (i.e. 128 pixels) they look very blurry. I’ve seen a lot of people with such scaled up pictures of pets or loved ones on the desktop, and it looks quite ugly. So, I made the thumbnail loader try to use the file itself as thumbnail if the icon is scaled above 128 pixels:

Wax On!

Wax Off!

None of this work significantly brings down the number of gnome-vfs calls in nautilus mentioned in my last blog. We’re now down from 803 to 510 compared to 531 in last entry. I think I will need to convert the GnomeVFSVolumeManager calls to gio now, as that will bite of a large chunk of this.

Nautilus: now eats 33% less babies

The work on the nautilus-gio branch continues:

[alex@localhost nautilus-gio]$ find -name "*.c" | xargs grep gnome_vfs_ |  wc -l

Where it originally was:

[alex@localhost nautilus]$ find -name "*.[ch]" | xargs grep gnome_vfs_ |  wc -l

So, 33% of all gnome vfs calls have been removed.
This doesn’t seem like a lot, but much of the core of nautilus has moved over.

These are the current uses of gnome vfs in nautilus-gio:

      2 gnome_vfs_async_cancel
      1 gnome_vfs_async_close
      1 gnome_vfs_async_load_directory_uri
      1 gnome_vfs_async_open
      2 gnome_vfs_async_read
      2 gnome_vfs_async_set_file_info
      6 gnome_vfs_async_xfer
      1 gnome_vfs_check_same_fs_uris
      2 gnome_vfs_close
      2 gnome_vfs_connect_to_server
      1 gnome_vfs_directory_list_load
      1 gnome_vfs_directory_visit_uri
      2 gnome_vfs_drive_compare
      3 gnome_vfs_drive_eject
      2 gnome_vfs_drive_get_activation_uri
      1 gnome_vfs_drive_get_device_path
      8 gnome_vfs_drive_get_device_type
      2 gnome_vfs_drive_get_display_name
      1 gnome_vfs_drive_get_icon
      2 gnome_vfs_drive_get_mounted_volumes
      8 gnome_vfs_drive_is_mounted
      1 gnome_vfs_drive_is_user_visible
      5 gnome_vfs_drive_mount
      3 gnome_vfs_drive_ref
      3 gnome_vfs_drive_unmount
     17 gnome_vfs_drive_unref
      1 gnome_vfs_error_quark
      5 gnome_vfs_escape_path_string
      1 gnome_vfs_escape_slashes
      6 gnome_vfs_escape_string
      5 gnome_vfs_file_info_list_free
      8 gnome_vfs_file_info_new
      1 gnome_vfs_file_info_to_gio
      9 gnome_vfs_file_info_unref
      2 gnome_vfs_file_type_from_g_file_type
      2 gnome_vfs_file_type_to_g_file_type
      9 gnome_vfs_find_directory
      5 gnome_vfs_get_file_info
      1 gnome_vfs_get_uri_scheme
      1 gnome_vfs_get_volume_free_space
     18 gnome_vfs_get_volume_monitor
      2 gnome_vfs_init
      1 gnome_vfs_make_directory
      1 gnome_vfs_make_directory_for_uri
      5 gnome_vfs_make_uri_from_input
      1 gnome_vfs_make_uri_from_input_with_trailing_ws
      1 gnome_vfs_make_uri_from_shell_arg
      1 gnome_vfs_method_get
      2 gnome_vfs_monitor_add
      2 gnome_vfs_monitor_cancel
      1 gnome_vfs_open
      1 gnome_vfs_read
      1 gnome_vfs_result_to_error
      7 gnome_vfs_result_to_string
      5 gnome_vfs_shutdown
      4 gnome_vfs_unescape_string
      4 gnome_vfs_unescape_string_for_display
      2 gnome_vfs_unlink
      7 gnome_vfs_uri_append_file_name
      3 gnome_vfs_uri_append_string
      1 gnome_vfs_uri_dup
      7 gnome_vfs_uri_equal
      2 gnome_vfs_uri_exists
      4 gnome_vfs_uri_extract_dirname
      4 gnome_vfs_uri_extract_short_name
      2 gnome_vfs_uri_extract_short_path_name
      7 gnome_vfs_uri_get_host_name
      1 gnome_vfs_uri_get_host_port
      9 gnome_vfs_uri_get_parent
      2 gnome_vfs_uri_get_path
      2 gnome_vfs_uri_get_scheme
      3 gnome_vfs_uri_get_user_name
      3 gnome_vfs_uri_has_parent
      1 gnome_vfs_uri_is_local
      6 gnome_vfs_uri_is_parent
      1 gnome_vfs_uri_list_extract_uris
      8 gnome_vfs_uri_list_free
      2 gnome_vfs_uri_make_full_from_relative
     54 gnome_vfs_uri_new
      4 gnome_vfs_uri_ref
     12 gnome_vfs_uris_match
     18 gnome_vfs_uri_to_string
     68 gnome_vfs_uri_unref
      1 gnome_vfs_url_show_with_env
      4 gnome_vfs_volume_compare
      4 gnome_vfs_volume_eject
     12 gnome_vfs_volume_get_activation_uri
      6 gnome_vfs_volume_get_device_type
      7 gnome_vfs_volume_get_display_name
      2 gnome_vfs_volume_get_drive
      1 gnome_vfs_volume_get_filesystem_type
      5 gnome_vfs_volume_get_icon
      2 gnome_vfs_volume_get_volume_type
      1 gnome_vfs_volume_handles_trash
      1 gnome_vfs_volume_is_read_only
      6 gnome_vfs_volume_is_user_visible
      2 gnome_vfs_volume_monitor_get_connected_drives
      1 gnome_vfs_volume_monitor_get_drive_by_id
      7 gnome_vfs_volume_monitor_get_mounted_volumes
      1 gnome_vfs_volume_monitor_get_volume_by_id
      5 gnome_vfs_volume_monitor_get_volume_for_path
      6 gnome_vfs_volume_ref
      3 gnome_vfs_volume_unmount
     29 gnome_vfs_volume_unref
      1 gnome_vfs_xfer_uri

A lot of these are low hanging fruit. For instance, there are 163 calls to the gnome vfs volume monitoring API, which has more or less a direct translation to GIO. Another large part is uri handling which should be translatable to GFile manipulation with some work. So it should be possible to get these numbers a lot lower fast.

However, other parts, like gnome_vfs_xfer() needs significant work. It is only called once, but is a large part of nautilus functionallity, basically doing all sorts of file copies and moves.

So, we’re going places, but we’re far from there yet.