[gnome-software/1196-race-condition-under-gs_plugin_icons_load_cached] gs-plugin-icons: Lock GsApp to prevent thread race condition
- From: Milan Crha <mcrha src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-software/1196-race-condition-under-gs_plugin_icons_load_cached] gs-plugin-icons: Lock GsApp to prevent thread race condition
- Date: Fri, 26 Mar 2021 10:47:58 +0000 (UTC)
commit bfc9e8a67ce12ac7a44883a677ff948aec67211b
Author: Milan Crha <mcrha redhat com>
Date: Fri Mar 26 11:45:58 2021 +0100
gs-plugin-icons: Lock GsApp to prevent thread race condition
Hold a GsApp lock when ensuring remote application icons are cached
locally, to avoid race condition when it's done from multiple threads
for the same application.
Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1196
lib/gs-app.c | 292 +++++++++++++++++++++++------------------
lib/gs-app.h | 2 +
plugins/core/gs-plugin-icons.c | 4 +
3 files changed, 169 insertions(+), 129 deletions(-)
---
diff --git a/lib/gs-app.c b/lib/gs-app.c
index 12ee9a292..8f3dc665e 100644
--- a/lib/gs-app.c
+++ b/lib/gs-app.c
@@ -54,7 +54,7 @@ typedef struct
{
GObject parent_instance;
- GMutex mutex;
+ GRecMutex mutex;
gchar *id;
gchar *unique_id;
gboolean unique_id_valid;
@@ -782,9 +782,9 @@ void
gs_app_set_id (GsApp *app, const gchar *id)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (_g_set_str (&priv->id, id))
priv->unique_id_valid = FALSE;
}
@@ -1151,9 +1151,9 @@ void
gs_app_set_progress (GsApp *app, guint percentage)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (priv->progress == percentage)
return;
if (percentage != GS_APP_PROGRESS_UNKNOWN && percentage > 100) {
@@ -1180,9 +1180,9 @@ void
gs_app_set_allow_cancel (GsApp *app, gboolean allow_cancel)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (priv->allow_cancel == allow_cancel)
return;
priv->allow_cancel = allow_cancel;
@@ -1229,10 +1229,10 @@ void
gs_app_set_state (GsApp *app, GsAppState state)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (gs_app_set_state_internal (app, state)) {
/* since the state changed, and the pending-action refers to
@@ -1287,11 +1287,11 @@ gs_app_set_kind (GsApp *app, AsComponentKind kind)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
gboolean state_change_ok = FALSE;
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* same */
if (priv->kind == kind)
@@ -1356,9 +1356,9 @@ const gchar *
gs_app_get_unique_id (GsApp *app)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_val_if_fail (GS_IS_APP (app), NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
return gs_app_get_unique_id_unlocked (app);
}
@@ -1375,10 +1375,10 @@ void
gs_app_set_unique_id (GsApp *app, const gchar *unique_id)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* check for sanity */
if (!as_utils_data_id_valid (unique_id))
@@ -1421,10 +1421,10 @@ void
gs_app_set_name (GsApp *app, GsAppQuality quality, const gchar *name)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* only save this if the data is sufficiently high quality */
if (quality < priv->name_quality)
@@ -1466,9 +1466,9 @@ void
gs_app_set_renamed_from (GsApp *app, const gchar *renamed_from)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_str (&priv->renamed_from, renamed_from);
}
@@ -1503,9 +1503,9 @@ void
gs_app_set_branch (GsApp *app, const gchar *branch)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (_g_set_str (&priv->branch, branch))
priv->unique_id_valid = FALSE;
}
@@ -1545,12 +1545,12 @@ gs_app_add_source (GsApp *app, const gchar *source)
GsAppPrivate *priv = gs_app_get_instance_private (app);
const gchar *tmp;
guint i;
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (source != NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* check source doesn't already exist */
for (i = 0; i < priv->sources->len; i++) {
@@ -1594,9 +1594,9 @@ void
gs_app_set_sources (GsApp *app, GPtrArray *sources)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_ptr_array (&priv->sources, sources);
}
@@ -1650,9 +1650,9 @@ void
gs_app_clear_source_ids (GsApp *app)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_ptr_array_set_size (priv->source_ids, 0);
}
@@ -1670,9 +1670,9 @@ void
gs_app_set_source_ids (GsApp *app, GPtrArray *source_ids)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_ptr_array (&priv->source_ids, source_ids);
}
@@ -1755,9 +1755,9 @@ void
gs_app_set_project_group (GsApp *app, const gchar *project_group)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_str (&priv->project_group, project_group);
}
@@ -1774,9 +1774,9 @@ void
gs_app_set_developer_name (GsApp *app, const gchar *developer_name)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_str (&priv->developer_name, developer_name);
}
@@ -1946,11 +1946,11 @@ void
gs_app_add_icon (GsApp *app, GIcon *icon)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (G_IS_ICON (icon));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (priv->icons == NULL)
priv->icons = g_ptr_array_new_with_free_func ((GDestroyNotify) g_object_unref);
@@ -1973,9 +1973,9 @@ void
gs_app_remove_all_icons (GsApp *app)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (priv->icons != NULL)
g_ptr_array_set_size (priv->icons, 0);
@@ -2053,9 +2053,9 @@ void
gs_app_set_agreement (GsApp *app, const gchar *agreement)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_str (&priv->agreement, agreement);
}
@@ -2092,9 +2092,9 @@ void
gs_app_set_local_file (GsApp *app, GFile *local_file)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_set_object (&priv->local_file, local_file);
}
@@ -2129,9 +2129,9 @@ void
gs_app_set_content_rating (GsApp *app, AsContentRating *content_rating)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_set_object (&priv->content_rating, content_rating);
}
@@ -2166,11 +2166,11 @@ void
gs_app_set_runtime (GsApp *app, GsApp *runtime)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (GS_IS_APP (runtime));
g_return_if_fail (app != runtime);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_set_object (&priv->runtime, runtime);
}
@@ -2187,9 +2187,9 @@ void
gs_app_set_action_screenshot (GsApp *app, AsScreenshot *action_screenshot)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_set_object (&priv->action_screenshot, action_screenshot);
}
@@ -2353,10 +2353,10 @@ void
gs_app_set_version (GsApp *app, const gchar *version)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (_g_set_str (&priv->version, version)) {
gs_app_ui_versions_invalidate (app);
@@ -2396,10 +2396,10 @@ void
gs_app_set_summary (GsApp *app, GsAppQuality quality, const gchar *summary)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* only save this if the data is sufficiently high quality */
if (quality < priv->summary_quality)
@@ -2441,10 +2441,10 @@ void
gs_app_set_description (GsApp *app, GsAppQuality quality, const gchar *description)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* only save this if the data is sufficiently high quality */
if (quality < priv->description_quality)
@@ -2468,9 +2468,9 @@ const gchar *
gs_app_get_url (GsApp *app, AsUrlKind kind)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_val_if_fail (GS_IS_APP (app), NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
return g_hash_table_lookup (priv->urls, as_url_kind_to_string (kind));
}
@@ -2488,9 +2488,9 @@ void
gs_app_set_url (GsApp *app, AsUrlKind kind, const gchar *url)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_hash_table_insert (priv->urls,
g_strdup (as_url_kind_to_string (kind)),
g_strdup (url));
@@ -2511,9 +2511,9 @@ const gchar *
gs_app_get_url_missing (GsApp *app)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_val_if_fail (GS_IS_APP (app), NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
return priv->url_missing;
}
@@ -2531,9 +2531,9 @@ void
gs_app_set_url_missing (GsApp *app, const gchar *url)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (g_strcmp0 (priv->url_missing, url) == 0)
return;
@@ -2576,9 +2576,9 @@ void
gs_app_set_launchable (GsApp *app, AsLaunchableKind kind, const gchar *launchable)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_hash_table_insert (priv->launchables,
g_strdup (as_launchable_kind_to_string (kind)),
g_strdup (launchable));
@@ -2634,11 +2634,11 @@ void
gs_app_set_license (GsApp *app, GsAppQuality quality, const gchar *license)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* only save this if the data is sufficiently high quality */
if (quality <= priv->license_quality)
@@ -2683,9 +2683,9 @@ void
gs_app_set_summary_missing (GsApp *app, const gchar *summary_missing)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_str (&priv->summary_missing, summary_missing);
}
@@ -2772,9 +2772,9 @@ void
gs_app_set_menu_path (GsApp *app, gchar **menu_path)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_strv (&priv->menu_path, menu_path);
}
@@ -2809,10 +2809,10 @@ void
gs_app_set_origin (GsApp *app, const gchar *origin)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* same */
if (g_strcmp0 (origin, priv->origin) == 0)
@@ -2865,10 +2865,10 @@ void
gs_app_set_origin_appstream (GsApp *app, const gchar *origin_appstream)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* same */
if (g_strcmp0 (origin_appstream, priv->origin_appstream) == 0)
@@ -2915,14 +2915,14 @@ void
gs_app_set_origin_hostname (GsApp *app, const gchar *origin_hostname)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_autoptr(SoupURI) uri = NULL;
guint i;
const gchar *prefixes[] = { "download.", "mirrors.", NULL };
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* same */
if (g_strcmp0 (origin_hostname, priv->origin_hostname) == 0)
@@ -2961,12 +2961,12 @@ void
gs_app_add_screenshot (GsApp *app, AsScreenshot *screenshot)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (AS_IS_SCREENSHOT (screenshot));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_ptr_array_add (priv->screenshots, g_object_ref (screenshot));
}
@@ -3052,9 +3052,9 @@ void
gs_app_set_update_version (GsApp *app, const gchar *update_version)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
gs_app_set_update_version_internal (app, update_version);
gs_app_queue_notify (app, obj_props[PROP_VERSION]);
}
@@ -3090,9 +3090,9 @@ void
gs_app_set_update_details (GsApp *app, const gchar *update_details)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_str (&priv->update_details, update_details);
}
@@ -3174,10 +3174,10 @@ void
gs_app_set_management_plugin (GsApp *app, const gchar *management_plugin)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* plugins cannot adopt wildcard packages */
if (gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD)) {
@@ -3237,9 +3237,9 @@ void
gs_app_set_rating (GsApp *app, gint rating)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (rating == priv->rating)
return;
priv->rating = rating;
@@ -3277,9 +3277,9 @@ void
gs_app_set_review_ratings (GsApp *app, GArray *review_ratings)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_array (&priv->review_ratings, review_ratings);
}
@@ -3314,10 +3314,10 @@ void
gs_app_add_review (GsApp *app, AsReview *review)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (AS_IS_REVIEW (review));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_ptr_array_add (priv->reviews, g_object_ref (review));
}
@@ -3334,9 +3334,9 @@ void
gs_app_remove_review (GsApp *app, AsReview *review)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
g_ptr_array_remove (priv->reviews, review);
}
@@ -3399,13 +3399,13 @@ gs_app_add_provided_item (GsApp *app, AsProvidedKind kind, const gchar *item)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
AsProvided *prov;
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (item != NULL);
g_return_if_fail (kind != AS_PROVIDED_KIND_UNKNOWN && kind < AS_PROVIDED_KIND_LAST);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
prov = gs_app_get_provided_for_kind (app, kind);
if (prov == NULL) {
prov = as_provided_new ();
@@ -3608,12 +3608,12 @@ void
gs_app_set_metadata_variant (GsApp *app, const gchar *key, GVariant *value)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
GVariant *found;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* if no value, then remove the key */
if (value == NULL) {
@@ -3674,12 +3674,12 @@ void
gs_app_add_addon (GsApp *app, GsApp *addon)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (GS_IS_APP (addon));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
gs_app_list_add (priv->addons, addon);
}
@@ -3696,10 +3696,10 @@ void
gs_app_remove_addon (GsApp *app, GsApp *addon)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (GS_IS_APP (addon));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
gs_app_list_remove (priv->addons, addon);
}
@@ -3735,12 +3735,12 @@ gs_app_add_related (GsApp *app, GsApp *app2)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
GsAppPrivate *priv2 = gs_app_get_instance_private (app2);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (GS_IS_APP (app2));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
/* if the app is updatable-live and any related app is not then
* degrade to the offline state */
@@ -3782,10 +3782,10 @@ void
gs_app_add_history (GsApp *app, GsApp *app2)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (GS_IS_APP (app2));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
gs_app_list_add (priv->history, app2);
}
@@ -3967,10 +3967,10 @@ void
gs_app_set_categories (GsApp *app, GPtrArray *categories)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (categories != NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_ptr_array (&priv->categories, categories);
}
@@ -3987,10 +3987,10 @@ void
gs_app_add_category (GsApp *app, const gchar *category)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (category != NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (gs_app_has_category (app, category))
return;
g_ptr_array_add (priv->categories, g_strdup (category));
@@ -4013,11 +4013,11 @@ gs_app_remove_category (GsApp *app, const gchar *category)
GsAppPrivate *priv = gs_app_get_instance_private (app);
const gchar *tmp;
guint i;
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_val_if_fail (GS_IS_APP (app), FALSE);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
for (i = 0; i < priv->categories->len; i++) {
tmp = g_ptr_array_index (priv->categories, i);
@@ -4207,10 +4207,10 @@ void
gs_app_set_key_colors (GsApp *app, GArray *key_colors)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (key_colors != NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (_g_set_array (&priv->key_colors, key_colors))
gs_app_queue_notify (app, obj_props[PROP_KEY_COLORS]);
}
@@ -4440,14 +4440,14 @@ void
gs_app_add_quirk (GsApp *app, GsAppQuirk quirk)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
/* same */
if ((priv->quirk & quirk) > 0)
return;
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
priv->quirk |= quirk;
gs_app_queue_notify (app, obj_props[PROP_QUIRK]);
}
@@ -4465,14 +4465,14 @@ void
gs_app_remove_quirk (GsApp *app, GsAppQuirk quirk)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
/* same */
if ((priv->quirk & quirk) == 0)
return;
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
priv->quirk &= ~quirk;
gs_app_queue_notify (app, obj_props[PROP_QUIRK]);
}
@@ -4574,11 +4574,11 @@ gs_app_get_cancellable (GsApp *app)
{
g_autoptr(GCancellable) cancellable = NULL;
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_val_if_fail (GS_IS_APP (app), NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (priv->cancellable == NULL || g_cancellable_is_cancelled (priv->cancellable)) {
cancellable = g_cancellable_new ();
@@ -4599,9 +4599,9 @@ GsPluginAction
gs_app_get_pending_action (GsApp *app)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_val_if_fail (GS_IS_APP (app), GS_PLUGIN_ACTION_UNKNOWN);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
return priv->pending_action;
}
@@ -4617,9 +4617,9 @@ gs_app_set_pending_action (GsApp *app,
GsPluginAction action)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
gs_app_set_pending_action_internal (app, action);
}
@@ -4791,7 +4791,7 @@ gs_app_finalize (GObject *object)
GsApp *app = GS_APP (object);
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_mutex_clear (&priv->mutex);
+ g_rec_mutex_clear (&priv->mutex);
g_free (priv->id);
g_free (priv->unique_id);
g_free (priv->branch);
@@ -5023,7 +5023,7 @@ gs_app_init (GsApp *app)
g_free,
g_free);
priv->allow_cancel = TRUE;
- g_mutex_init (&priv->mutex);
+ g_rec_mutex_init (&priv->mutex);
}
/**
@@ -5135,7 +5135,7 @@ gchar *
gs_app_get_origin_ui (GsApp *app)
{
GsAppPrivate *priv;
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_autoptr(GsOsRelease) os_release = NULL;
g_autofree gchar *packaging_format = NULL;
const gchar *origin_str = NULL;
@@ -5150,7 +5150,7 @@ gs_app_get_origin_ui (GsApp *app)
}
priv = gs_app_get_instance_private (app);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (!origin_str) {
origin_str = priv->origin_ui;
@@ -5185,12 +5185,12 @@ gs_app_set_origin_ui (GsApp *app,
const gchar *origin_ui)
{
GsAppPrivate *priv;
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
priv = gs_app_get_instance_private (app);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
if (origin_ui && !*origin_ui)
origin_ui = NULL;
@@ -5351,9 +5351,43 @@ void
gs_app_set_version_history (GsApp *app, GPtrArray *version_history)
{
GsAppPrivate *priv = gs_app_get_instance_private (app);
- g_autoptr(GMutexLocker) locker = NULL;
+ g_autoptr(GRecMutexLocker) locker = NULL;
g_return_if_fail (GS_IS_APP (app));
g_return_if_fail (version_history != NULL);
- locker = g_mutex_locker_new (&priv->mutex);
+ locker = g_rec_mutex_locker_new (&priv->mutex);
_g_set_ptr_array (&priv->version_history, version_history);
}
+
+/**
+ * gs_app_lock:
+ * @app: a #GsApp
+ *
+ * Acquire the @app property lock. Release the lock with gs_app_unlock().
+ *
+ * Since: 41
+ **/
+void
+gs_app_lock (GsApp *app)
+{
+ GsAppPrivate *priv;
+ g_return_if_fail (GS_IS_APP (app));
+ priv = gs_app_get_instance_private (app);
+ g_rec_mutex_lock (&priv->mutex);
+}
+
+/**
+ * gs_app_unlock:
+ * @app: a #GsApp
+ *
+ * Release the @app property lock, previously acquired with gs_app_lock().
+ *
+ * Since: 41
+ **/
+void
+gs_app_unlock (GsApp *app)
+{
+ GsAppPrivate *priv;
+ g_return_if_fail (GS_IS_APP (app));
+ priv = gs_app_get_instance_private (app);
+ g_rec_mutex_unlock (&priv->mutex);
+}
diff --git a/lib/gs-app.h b/lib/gs-app.h
index 3136b639f..eb1544f7c 100644
--- a/lib/gs-app.h
+++ b/lib/gs-app.h
@@ -471,5 +471,7 @@ void gs_app_set_update_permissions (GsApp *app,
GPtrArray *gs_app_get_version_history (GsApp *app);
void gs_app_set_version_history (GsApp *app,
GPtrArray *version_history);
+void gs_app_lock (GsApp *app);
+void gs_app_unlock (GsApp *app);
G_END_DECLS
diff --git a/plugins/core/gs-plugin-icons.c b/plugins/core/gs-plugin-icons.c
index 34bf52442..a5f594c2b 100644
--- a/plugins/core/gs-plugin-icons.c
+++ b/plugins/core/gs-plugin-icons.c
@@ -59,6 +59,8 @@ refine_app (GsPlugin *plugin,
/* Currently a 160px icon is needed for #GsFeatureTile, at most. */
maximum_icon_size = 160 * gs_plugin_get_scale (plugin);
+ gs_app_lock (app);
+
/* process all icons */
icons = gs_app_get_icons (app);
for (i = 0; icons != NULL && i < icons->len; i++) {
@@ -81,6 +83,8 @@ refine_app (GsPlugin *plugin,
}
}
+ gs_app_unlock (app);
+
return TRUE;
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]