[grilo] core: Make resolve() a cancellable operation
- From: Juan A. Suarez Romero <jasuarez src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [grilo] core: Make resolve() a cancellable operation
- Date: Wed, 13 Apr 2011 10:15:02 +0000 (UTC)
commit 97c9bd000ffc4d75c6707f793ee4bfaf201058a0
Author: Juan A. Suarez Romero <jasuarez igalia com>
Date: Wed Apr 6 06:42:57 2011 +0000
core: Make resolve() a cancellable operation
Fixes https://bugzilla.gnome.org/show_bug.cgi?id=644383
Signed-off-by: Juan A. Suarez Romero <jasuarez igalia com>
src/grl-media-source.c | 6 +++-
src/grl-metadata-source.c | 48 +++++++++++++++++++++++++++++++++++++-------
src/grl-metadata-source.h | 18 ++++++++++------
3 files changed, 55 insertions(+), 17 deletions(-)
---
diff --git a/src/grl-media-source.c b/src/grl-media-source.c
index e8444c1..5693743 100644
--- a/src/grl-media-source.c
+++ b/src/grl-media-source.c
@@ -978,6 +978,7 @@ full_resolution_check_waiting_list (GList **waiting_list,
static void
full_resolution_done_cb (GrlMetadataSource *source,
+ guint resolve_id,
GrlMedia *media,
gpointer user_data,
const GError *error)
@@ -1116,7 +1117,7 @@ full_resolution_ctl_cb (GrlMediaSource *source,
full_resolution_done_cb, so we fake the resolution to get into that
callback */
done_info->pending_callbacks = 1;
- full_resolution_done_cb (NULL, media, done_info, error);
+ full_resolution_done_cb (NULL, 0, media, done_info, error);
} else {
GList *sources, *iter;
/* Start full-resolution: save all the data we need to emit the result
@@ -1153,13 +1154,14 @@ full_resolution_ctl_cb (GrlMediaSource *source,
if (!done_info->pending_callbacks) {
done_info->pending_callbacks = 1;
- full_resolution_done_cb (NULL, media, done_info, NULL);
+ full_resolution_done_cb (NULL, 0, media, done_info, NULL);
}
}
}
static void
metadata_full_resolution_done_cb (GrlMetadataSource *source,
+ guint operation_id,
GrlMedia *media,
gpointer user_data,
const GError *error)
diff --git a/src/grl-metadata-source.c b/src/grl-metadata-source.c
index ebac1a4..568f7e5 100644
--- a/src/grl-metadata-source.c
+++ b/src/grl-metadata-source.c
@@ -350,16 +350,37 @@ set_metadata_ctl_cb (GrlMetadataSource *source,
static void
resolve_result_relay_cb (GrlMetadataSource *source,
+ guint resolve_id,
GrlMedia *media,
gpointer user_data,
const GError *error)
{
+ gboolean should_free_error = FALSE;
+ GError *_error = (GError *) error;
+
GRL_DEBUG ("resolve_result_relay_cb");
struct ResolveRelayCb *rrc;
rrc = (struct ResolveRelayCb *) user_data;
- rrc->user_callback (source, media, rrc->user_data, error);
+
+ if (grl_metadata_source_operation_is_cancelled (source,
+ rrc->spec->resolve_id)) {
+ /* if the plugin already set an error, we don't care because we're
+ * cancelled */
+ _error = g_error_new (GRL_CORE_ERROR, GRL_CORE_ERROR_OPERATION_CANCELLED,
+ "Operation was cancelled");
+ /* yet, we should free the error we just created (if we didn't create it,
+ * the plugin owns it) */
+ should_free_error = TRUE;
+ }
+
+ rrc->user_callback (source, rrc->spec->resolve_id, media,
+ rrc->user_data, _error);
+
+ if (should_free_error && _error) {
+ g_error_free (_error);
+ }
g_object_unref (rrc->spec->source);
g_object_unref (rrc->spec->media);
@@ -380,6 +401,7 @@ resolve_idle (gpointer user_data)
static void
resolve_result_async_cb (GrlMetadataSource *source,
+ guint resolve_id,
GrlMedia *media,
gpointer user_data,
const GError *error)
@@ -888,11 +910,13 @@ grl_metadata_source_may_resolve (GrlMetadataSource *source,
* This is the main method of the #GrlMetadataSource class. It will fetch the
* metadata of the requested keys.
*
- * This function is asynchronous and uses the Glib's main loop.
+ * This function is asynchronous.
+ *
+ * Returns: the operation identifier
*
* Since: 0.1.4
*/
-void
+guint
grl_metadata_source_resolve (GrlMetadataSource *source,
const GList *keys,
GrlMedia *media,
@@ -903,14 +927,15 @@ grl_metadata_source_resolve (GrlMetadataSource *source,
GrlMetadataSourceResolveSpec *rs;
GList *_keys;
struct ResolveRelayCb *rrc;
+ guint resolve_id;
GRL_DEBUG ("grl_metadata_source_resolve");
- g_return_if_fail (GRL_IS_METADATA_SOURCE (source));
- g_return_if_fail (callback != NULL);
- g_return_if_fail (media != NULL);
- g_return_if_fail (grl_metadata_source_supported_operations (source) &
- GRL_OP_RESOLVE);
+ g_return_val_if_fail (GRL_IS_METADATA_SOURCE (source), 0);
+ g_return_val_if_fail (callback != NULL, 0);
+ g_return_val_if_fail (media != NULL, 0);
+ g_return_val_if_fail (grl_metadata_source_supported_operations (source) &
+ GRL_OP_RESOLVE, 0);
_keys = g_list_copy ((GList *) keys);
@@ -918,6 +943,9 @@ grl_metadata_source_resolve (GrlMetadataSource *source,
grl_metadata_source_filter_slow (source, &_keys, FALSE);
}
+ resolve_id =
+ grl_metadata_source_gen_operation_id (GRL_METADATA_SOURCE (source));
+
/* Always hook an own relay callback so we can do some
post-processing before handing out the results
to the user */
@@ -927,6 +955,7 @@ grl_metadata_source_resolve (GrlMetadataSource *source,
rs = g_new0 (GrlMetadataSourceResolveSpec, 1);
rs->source = g_object_ref (source);
+ rs->resolve_id = resolve_id;
rs->keys = _keys;
rs->media = g_object_ref (media);
rs->flags = flags;
@@ -937,11 +966,14 @@ grl_metadata_source_resolve (GrlMetadataSource *source,
user_data so that we can free the spec there */
rrc->spec = rs;
+ grl_metadata_source_set_operation_ongoing (source, resolve_id);
g_idle_add_full (flags & GRL_RESOLVE_IDLE_RELAY?
G_PRIORITY_DEFAULT_IDLE: G_PRIORITY_HIGH_IDLE,
resolve_idle,
rs,
NULL);
+
+ return resolve_id;
}
/**
diff --git a/src/grl-metadata-source.h b/src/grl-metadata-source.h
index d20b4d9..5638813 100644
--- a/src/grl-metadata-source.h
+++ b/src/grl-metadata-source.h
@@ -111,6 +111,7 @@ struct _GrlMetadataSource {
/**
* GrlMetadataSourceResolveCb:
* @source: a metadata source
+ * @operation_id: operation identifier
* @media: (transfer full): a #GrlMedia transfer object
* @user_data: user data passed to grl_metadata_source_resolve()
* @error: (type uint): possible #GError generated when resolving the metadata
@@ -118,6 +119,7 @@ struct _GrlMetadataSource {
* Prototype for the callback passed to grl_metadata_source_resolve()
*/
typedef void (*GrlMetadataSourceResolveCb) (GrlMetadataSource *source,
+ guint operation_id,
GrlMedia *media,
gpointer user_data,
const GError *error);
@@ -144,6 +146,7 @@ typedef void (*GrlMetadataSourceSetMetadataCb) (GrlMetadataSource *source,
/**
* GrlMetadataSourceResolveSpec:
* @source: a metadata source
+ * @resolve_id: operation identifier
* @keys: the #GList of #GrlKeyID to fetch and store
* @media: a #GrlMedia transfer object
* @flags: bitwise mask of #GrlMetadataResolutionFlags with the resolution
@@ -156,6 +159,7 @@ typedef void (*GrlMetadataSourceSetMetadataCb) (GrlMetadataSource *source,
*/
typedef struct {
GrlMetadataSource *source;
+ guint resolve_id;
GList *keys;
GrlMedia *media;
GrlMetadataResolutionFlags flags;
@@ -163,7 +167,7 @@ typedef struct {
gpointer user_data;
/*< private >*/
- gpointer _grl_reserved[GRL_PADDING];
+ gpointer _grl_reserved[GRL_PADDING - 1];
} GrlMetadataSourceResolveSpec;
/**
@@ -313,12 +317,12 @@ gboolean grl_metadata_source_may_resolve (GrlMetadataSource *source,
GrlKeyID key_id,
GList **missing_keys);
-void grl_metadata_source_resolve (GrlMetadataSource *source,
- const GList *keys,
- GrlMedia *media,
- GrlMetadataResolutionFlags flags,
- GrlMetadataSourceResolveCb callback,
- gpointer user_data);
+guint grl_metadata_source_resolve (GrlMetadataSource *source,
+ const GList *keys,
+ GrlMedia *media,
+ GrlMetadataResolutionFlags flags,
+ GrlMetadataSourceResolveCb callback,
+ gpointer user_data);
GrlMedia *grl_metadata_source_resolve_sync (GrlMetadataSource *source,
const GList *keys,
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]