X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=gio%2Fgunionvolumemonitor.c;h=4c3049b958014f8cee3db5d5832e188b32e25a05;hb=7e5e3e142f856ac80e83a9a5110b51aa4b5b0821;hp=d6cecee3252fe2856ebeb11f3b19195940484e58;hpb=aef5a4b0abb20e7583dd3706e4b1b548c5056caf;p=platform%2Fupstream%2Fglib.git diff --git a/gio/gunionvolumemonitor.c b/gio/gunionvolumemonitor.c index d6cecee..4c3049b 100644 --- a/gio/gunionvolumemonitor.c +++ b/gio/gunionvolumemonitor.c @@ -1,3 +1,5 @@ +/* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */ + /* GIO - GLib Input, Output and Streaming Library * * Copyright (C) 2006-2007 Red Hat, Inc. @@ -13,15 +15,13 @@ * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General - * Public License along with this library; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place, Suite 330, - * Boston, MA 02111-1307, USA. + * Public License along with this library; if not, see . * * Author: Alexander Larsson * David Zeuthen */ -#include +#include "config.h" #include @@ -36,7 +36,6 @@ #include "glibintl.h" -#include "gioalias.h" struct _GUnionVolumeMonitor { GVolumeMonitor parent; @@ -51,8 +50,8 @@ static void g_union_volume_monitor_remove_monitor (GUnionVolumeMonitor *union_mo #define g_union_volume_monitor_get_type _g_union_volume_monitor_get_type G_DEFINE_TYPE (GUnionVolumeMonitor, g_union_volume_monitor, G_TYPE_VOLUME_MONITOR); +static GRecMutex the_volume_monitor_mutex; -G_LOCK_DEFINE_STATIC(the_volume_monitor); static GUnionVolumeMonitor *the_volume_monitor = NULL; static void @@ -63,31 +62,38 @@ g_union_volume_monitor_finalize (GObject *object) monitor = G_UNION_VOLUME_MONITOR (object); - while (monitor->monitors != NULL) { - child_monitor = monitor->monitors->data; - g_union_volume_monitor_remove_monitor (monitor, - child_monitor); - g_object_unref (child_monitor); - } + while (monitor->monitors != NULL) + { + child_monitor = monitor->monitors->data; + g_union_volume_monitor_remove_monitor (monitor, + child_monitor); + g_object_unref (child_monitor); + } - - if (G_OBJECT_CLASS (g_union_volume_monitor_parent_class)->finalize) - (*G_OBJECT_CLASS (g_union_volume_monitor_parent_class)->finalize) (object); + G_OBJECT_CLASS (g_union_volume_monitor_parent_class)->finalize (object); } static void g_union_volume_monitor_dispose (GObject *object) { GUnionVolumeMonitor *monitor; - + GVolumeMonitor *child_monitor; + GList *l; + monitor = G_UNION_VOLUME_MONITOR (object); - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); the_volume_monitor = NULL; - G_UNLOCK (the_volume_monitor); + + for (l = monitor->monitors; l != NULL; l = l->next) + { + child_monitor = l->data; + g_object_run_dispose (G_OBJECT (child_monitor)); + } - if (G_OBJECT_CLASS (g_union_volume_monitor_parent_class)->dispose) - (*G_OBJECT_CLASS (g_union_volume_monitor_parent_class)->dispose) (object); + g_rec_mutex_unlock (&the_volume_monitor_mutex); + + G_OBJECT_CLASS (g_union_volume_monitor_parent_class)->dispose (object); } static GList * @@ -102,7 +108,7 @@ get_mounts (GVolumeMonitor *volume_monitor) res = NULL; - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); for (l = monitor->monitors; l != NULL; l = l->next) { @@ -111,7 +117,7 @@ get_mounts (GVolumeMonitor *volume_monitor) res = g_list_concat (res, g_volume_monitor_get_mounts (child_monitor)); } - G_UNLOCK (the_volume_monitor); + g_rec_mutex_unlock (&the_volume_monitor_mutex); return res; } @@ -128,7 +134,7 @@ get_volumes (GVolumeMonitor *volume_monitor) res = NULL; - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); for (l = monitor->monitors; l != NULL; l = l->next) { @@ -137,7 +143,7 @@ get_volumes (GVolumeMonitor *volume_monitor) res = g_list_concat (res, g_volume_monitor_get_volumes (child_monitor)); } - G_UNLOCK (the_volume_monitor); + g_rec_mutex_unlock (&the_volume_monitor_mutex); return res; } @@ -154,7 +160,7 @@ get_connected_drives (GVolumeMonitor *volume_monitor) res = NULL; - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); for (l = monitor->monitors; l != NULL; l = l->next) { @@ -163,7 +169,7 @@ get_connected_drives (GVolumeMonitor *volume_monitor) res = g_list_concat (res, g_volume_monitor_get_connected_drives (child_monitor)); } - G_UNLOCK (the_volume_monitor); + g_rec_mutex_unlock (&the_volume_monitor_mutex); return res; } @@ -180,7 +186,7 @@ get_volume_for_uuid (GVolumeMonitor *volume_monitor, const char *uuid) volume = NULL; - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); for (l = monitor->monitors; l != NULL; l = l->next) { @@ -192,7 +198,7 @@ get_volume_for_uuid (GVolumeMonitor *volume_monitor, const char *uuid) } - G_UNLOCK (the_volume_monitor); + g_rec_mutex_unlock (&the_volume_monitor_mutex); return volume; } @@ -209,7 +215,7 @@ get_mount_for_uuid (GVolumeMonitor *volume_monitor, const char *uuid) mount = NULL; - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); for (l = monitor->monitors; l != NULL; l = l->next) { @@ -221,7 +227,7 @@ get_mount_for_uuid (GVolumeMonitor *volume_monitor, const char *uuid) } - G_UNLOCK (the_volume_monitor); + g_rec_mutex_unlock (&the_volume_monitor_mutex); return mount; } @@ -248,7 +254,7 @@ child_volume_added (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "volume_added", + "volume-added", child_volume); } @@ -258,7 +264,7 @@ child_volume_removed (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "volume_removed", + "volume-removed", child_volume); } @@ -268,7 +274,7 @@ child_volume_changed (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "volume_changed", + "volume-changed", child_volume); } @@ -278,7 +284,7 @@ child_mount_added (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "mount_added", + "mount-added", child_mount); } @@ -288,7 +294,7 @@ child_mount_removed (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "mount_removed", + "mount-removed", child_mount); } @@ -298,7 +304,7 @@ child_mount_pre_unmount (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "mount_pre_unmount", + "mount-pre-unmount", child_mount); } @@ -309,7 +315,7 @@ child_mount_changed (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "mount_changed", + "mount-changed", child_mount); } @@ -319,7 +325,7 @@ child_drive_connected (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "drive_connected", + "drive-connected", child_drive); } @@ -329,7 +335,7 @@ child_drive_disconnected (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "drive_disconnected", + "drive-disconnected", child_drive); } @@ -339,7 +345,27 @@ child_drive_changed (GVolumeMonitor *child_monitor, GUnionVolumeMonitor *union_monitor) { g_signal_emit_by_name (union_monitor, - "drive_changed", + "drive-changed", + child_drive); +} + +static void +child_drive_eject_button (GVolumeMonitor *child_monitor, + GDrive *child_drive, + GUnionVolumeMonitor *union_monitor) +{ + g_signal_emit_by_name (union_monitor, + "drive-eject-button", + child_drive); +} + +static void +child_drive_stop_button (GVolumeMonitor *child_monitor, + GDrive *child_drive, + GUnionVolumeMonitor *union_monitor) +{ + g_signal_emit_by_name (union_monitor, + "drive-stop-button", child_drive); } @@ -354,16 +380,18 @@ g_union_volume_monitor_add_monitor (GUnionVolumeMonitor *union_monitor, g_list_prepend (union_monitor->monitors, g_object_ref (volume_monitor)); - g_signal_connect (volume_monitor, "volume_added", (GCallback)child_volume_added, union_monitor); - g_signal_connect (volume_monitor, "volume_removed", (GCallback)child_volume_removed, union_monitor); - g_signal_connect (volume_monitor, "volume_changed", (GCallback)child_volume_changed, union_monitor); - g_signal_connect (volume_monitor, "mount_added", (GCallback)child_mount_added, union_monitor); - g_signal_connect (volume_monitor, "mount_removed", (GCallback)child_mount_removed, union_monitor); - g_signal_connect (volume_monitor, "mount_pre_unmount", (GCallback)child_mount_pre_unmount, union_monitor); - g_signal_connect (volume_monitor, "mount_changed", (GCallback)child_mount_changed, union_monitor); - g_signal_connect (volume_monitor, "drive_connected", (GCallback)child_drive_connected, union_monitor); - g_signal_connect (volume_monitor, "drive_disconnected", (GCallback)child_drive_disconnected, union_monitor); - g_signal_connect (volume_monitor, "drive_changed", (GCallback)child_drive_changed, union_monitor); + g_signal_connect (volume_monitor, "volume-added", (GCallback)child_volume_added, union_monitor); + g_signal_connect (volume_monitor, "volume-removed", (GCallback)child_volume_removed, union_monitor); + g_signal_connect (volume_monitor, "volume-changed", (GCallback)child_volume_changed, union_monitor); + g_signal_connect (volume_monitor, "mount-added", (GCallback)child_mount_added, union_monitor); + g_signal_connect (volume_monitor, "mount-removed", (GCallback)child_mount_removed, union_monitor); + g_signal_connect (volume_monitor, "mount-pre-unmount", (GCallback)child_mount_pre_unmount, union_monitor); + g_signal_connect (volume_monitor, "mount-changed", (GCallback)child_mount_changed, union_monitor); + g_signal_connect (volume_monitor, "drive-connected", (GCallback)child_drive_connected, union_monitor); + g_signal_connect (volume_monitor, "drive-disconnected", (GCallback)child_drive_disconnected, union_monitor); + g_signal_connect (volume_monitor, "drive-changed", (GCallback)child_drive_changed, union_monitor); + g_signal_connect (volume_monitor, "drive-eject-button", (GCallback)child_drive_eject_button, union_monitor); + g_signal_connect (volume_monitor, "drive-stop-button", (GCallback)child_drive_stop_button, union_monitor); } static void @@ -388,56 +416,18 @@ g_union_volume_monitor_remove_monitor (GUnionVolumeMonitor *union_monitor, g_signal_handlers_disconnect_by_func (child_monitor, child_drive_connected, union_monitor); g_signal_handlers_disconnect_by_func (child_monitor, child_drive_disconnected, union_monitor); g_signal_handlers_disconnect_by_func (child_monitor, child_drive_changed, union_monitor); -} - -/* Note: This compares in reverse order. - Higher prio -> sort first - */ -static gint -compare_monitor_type (gconstpointer a, - gconstpointer b, - gpointer user_data) -{ - GType a_type, b_type; - char *a_name, *b_name; - int a_prio, b_prio; - gint res; - const char *use_this_monitor; - GQuark private_q, name_q; - - private_q = g_quark_from_static_string ("gio-prio"); - name_q = g_quark_from_static_string ("gio-name"); - - use_this_monitor = user_data; - a_type = *(GType *)a; - b_type = *(GType *)b; - a_prio = GPOINTER_TO_INT (g_type_get_qdata (a_type, private_q)); - a_name = g_type_get_qdata (a_type, name_q); - b_prio = GPOINTER_TO_INT (g_type_get_qdata (b_type, private_q)); - b_name = g_type_get_qdata (b_type, name_q); - - if (a_type == b_type) - res = 0; - else if (use_this_monitor != NULL && - strcmp (a_name, use_this_monitor) == 0) - res = -1; - else if (use_this_monitor != NULL && - strcmp (b_name, use_this_monitor) == 0) - res = 1; - else - res = b_prio - a_prio; - - return res; + g_signal_handlers_disconnect_by_func (child_monitor, child_drive_eject_button, union_monitor); + g_signal_handlers_disconnect_by_func (child_monitor, child_drive_stop_button, union_monitor); } static GType get_default_native_class (gpointer data) { GNativeVolumeMonitorClass *klass, *native_class, **native_class_out; - GType *monitors; - guint n_monitors; const char *use_this; - int i; + GIOExtensionPoint *ep; + GIOExtension *extension; + GList *l; native_class_out = data; @@ -446,28 +436,37 @@ get_default_native_class (gpointer data) /* Ensure vfs in modules loaded */ _g_io_modules_ensure_loaded (); - monitors = g_type_children (G_TYPE_NATIVE_VOLUME_MONITOR, &n_monitors); - - g_qsort_with_data (monitors, - n_monitors, - sizeof (GType), - compare_monitor_type, - (gpointer)use_this); + ep = g_io_extension_point_lookup (G_NATIVE_VOLUME_MONITOR_EXTENSION_POINT_NAME); native_class = NULL; - for (i = 0; i < n_monitors; i++) - { - klass = g_type_class_ref (monitors[i]); - if (G_VOLUME_MONITOR_CLASS (klass)->is_supported()) + if (use_this) + { + extension = g_io_extension_point_get_extension_by_name (ep, use_this); + if (extension) { - native_class = klass; - break; + klass = G_NATIVE_VOLUME_MONITOR_CLASS (g_io_extension_ref_class (extension)); + if (G_VOLUME_MONITOR_CLASS (klass)->is_supported()) + native_class = klass; + else + g_type_class_unref (klass); } - else - g_type_class_unref (klass); } - g_free (monitors); + if (native_class == NULL) + { + for (l = g_io_extension_point_get_extensions (ep); l != NULL; l = l->next) + { + extension = l->data; + klass = G_NATIVE_VOLUME_MONITOR_CLASS (g_io_extension_ref_class (extension)); + if (G_VOLUME_MONITOR_CLASS (klass)->is_supported()) + { + native_class = klass; + break; + } + else + g_type_class_unref (klass); + } + } if (native_class) { @@ -484,7 +483,7 @@ get_default_native_class (gpointer data) * instance on the first call. */ static GNativeVolumeMonitorClass * -get_native_class () +get_native_class (void) { static GOnce once_init = G_ONCE_INIT; GTypeClass *type_class; @@ -492,7 +491,7 @@ get_native_class () type_class = NULL; g_once (&once_init, (GThreadFunc)get_default_native_class, &type_class); - if (type_class == NULL && once_init.retval != G_TYPE_INVALID) + if (type_class == NULL && once_init.retval != GUINT_TO_POINTER(G_TYPE_INVALID)) type_class = g_type_class_ref ((GType)once_init.retval); return (GNativeVolumeMonitorClass *)type_class; @@ -501,12 +500,17 @@ get_native_class () static void g_union_volume_monitor_init (GUnionVolumeMonitor *union_monitor) { +} + +static void +populate_union_monitor (GUnionVolumeMonitor *union_monitor) +{ GVolumeMonitor *monitor; - GType *monitors; - guint n_monitors; GNativeVolumeMonitorClass *native_class; GVolumeMonitorClass *klass; - int i; + GIOExtensionPoint *ep; + GIOExtension *extension; + GList *l; native_class = get_native_class (); @@ -517,26 +521,21 @@ g_union_volume_monitor_init (GUnionVolumeMonitor *union_monitor) g_object_unref (monitor); g_type_class_unref (native_class); } - - monitors = g_type_children (G_TYPE_VOLUME_MONITOR, &n_monitors); - - for (i = 0; i < n_monitors; i++) - { - if (monitors[i] == G_TYPE_UNION_VOLUME_MONITOR || - g_type_is_a (monitors[i], G_TYPE_NATIVE_VOLUME_MONITOR)) - continue; - klass = g_type_class_ref (monitors[i]); + ep = g_io_extension_point_lookup (G_VOLUME_MONITOR_EXTENSION_POINT_NAME); + for (l = g_io_extension_point_get_extensions (ep); l != NULL; l = l->next) + { + extension = l->data; + + klass = G_VOLUME_MONITOR_CLASS (g_io_extension_ref_class (extension)); if (klass->is_supported == NULL || klass->is_supported()) { - monitor = g_object_new (monitors[i], NULL); + monitor = g_object_new (g_io_extension_get_type (extension), NULL); g_union_volume_monitor_add_monitor (union_monitor, monitor); g_object_unref (monitor); } g_type_class_unref (klass); } - - g_free (monitors); } static GUnionVolumeMonitor * @@ -554,7 +553,7 @@ g_union_volume_monitor_new (void) * * Gets the volume monitor used by gio. * - * Returns: a reference to the #GVolumeMonitor used by gio. Call + * Returns: (transfer full): a reference to the #GVolumeMonitor used by gio. Call * g_object_unref() when done with it. **/ GVolumeMonitor * @@ -562,30 +561,24 @@ g_volume_monitor_get (void) { GVolumeMonitor *vm; - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); if (the_volume_monitor) vm = G_VOLUME_MONITOR (g_object_ref (the_volume_monitor)); else { the_volume_monitor = g_union_volume_monitor_new (); + populate_union_monitor (the_volume_monitor); vm = G_VOLUME_MONITOR (the_volume_monitor); } - G_UNLOCK (the_volume_monitor); + g_rec_mutex_unlock (&the_volume_monitor_mutex); return vm; } -/** - * _g_mount_get_for_mount_path: - * @mountpoint: a string. - * @cancellable: a #GCancellable, or %NULL - * - * Returns: a #GMount for given @mount_path or %NULL. - **/ GMount * -_g_mount_get_for_mount_path (const char *mount_path, +_g_mount_get_for_mount_path (const gchar *mount_path, GCancellable *cancellable) { GNativeVolumeMonitorClass *klass; @@ -599,9 +592,9 @@ _g_mount_get_for_mount_path (const char *mount_path, if (klass->get_mount_for_mount_path) { - G_LOCK (the_volume_monitor); + g_rec_mutex_lock (&the_volume_monitor_mutex); mount = klass->get_mount_for_mount_path (mount_path, cancellable); - G_UNLOCK (the_volume_monitor); + g_rec_mutex_unlock (&the_volume_monitor_mutex); } /* TODO: How do we know this succeeded? Keep in mind that the native @@ -628,14 +621,14 @@ _g_mount_get_for_mount_path (const char *mount_path, * * If the return value is not %NULL, the caller must associate the * returned #GVolume object with the #GMount. This involves returning - * it in it's g_mount_get_volume() implementation. The caller must + * it in its g_mount_get_volume() implementation. The caller must * also listen for the "removed" signal on the returned object - * and give up it's reference when handling that signal + * and give up its reference when handling that signal * * Similary, if implementing g_volume_monitor_adopt_orphan_mount(), * the implementor must take a reference to @mount and return it in - * it's g_volume_get_mount() implemented. Also, the implementor must - * listen for the "unmounted" signal on @mount and give up it's + * its g_volume_get_mount() implemented. Also, the implementor must + * listen for the "unmounted" signal on @mount and give up its * reference upon handling that signal. * * There are two main use cases for this function. @@ -643,15 +636,21 @@ _g_mount_get_for_mount_path (const char *mount_path, * One is when implementing a user space file system driver that reads * blocks of a block device that is already represented by the native * volume monitor (for example a CD Audio file system driver). Such - * a driver will generate it's own #GMount object that needs to be - * assoicated with the #GVolume object that represents the volume. + * a driver will generate its own #GMount object that needs to be + * associated with the #GVolume object that represents the volume. * * The other is for implementing a #GVolumeMonitor whose sole purpose * is to return #GVolume objects representing entries in the users * "favorite servers" list or similar. * - * Returns: the #GVolume object that is the parent for @mount or %NULL + * Returns: (transfer full): the #GVolume object that is the parent for @mount or %NULL * if no wants to adopt the #GMount. + * + * Deprecated: 2.20: Instead of using this function, #GVolumeMonitor + * implementations should instead create shadow mounts with the URI of + * the mount they intend to adopt. See the proxy volume monitor in + * gvfs for an example of this. Also see g_mount_is_shadowed(), + * g_mount_shadow() and g_mount_unshadow() functions. */ GVolume * g_volume_monitor_adopt_orphan_mount (GMount *mount) @@ -668,9 +667,7 @@ g_volume_monitor_adopt_orphan_mount (GMount *mount) volume = NULL; - /* TODO: nasty locking issues because current VM's don't emit signals in idle */ - - /*G_LOCK (the_volume_monitor);*/ + g_rec_mutex_lock (&the_volume_monitor_mutex); for (l = the_volume_monitor->monitors; l != NULL; l = l->next) { @@ -679,17 +676,13 @@ g_volume_monitor_adopt_orphan_mount (GMount *mount) if (child_monitor_class->adopt_orphan_mount != NULL) { - volume = child_monitor_class->adopt_orphan_mount (mount); + volume = child_monitor_class->adopt_orphan_mount (mount, child_monitor); if (volume != NULL) break; } } - /*G_UNLOCK (the_volume_monitor);*/ + g_rec_mutex_unlock (&the_volume_monitor_mutex); return volume; } - - -#define __G_UNION_VOLUME_MONITOR_C__ -#include "gioaliasdef.c"