Skip to content

Commit

Permalink
app: List apps that use a runtime extension when it's EOL
Browse files Browse the repository at this point in the history
Currently if a runtime extension, e.g.
org.freedesktop.Platform.html5-codecs//18.08 is used by a runtime
org.kde.Platform//5.12 which itself is used by one or more apps, when we
print a message to the user about html5-codecs being EOL, we don't find
any apps using it and don't print any. Fix this by including apps that
indirectly use a runtime extension in the "Applications using this
runtime:" list.

In a later commit we can re-use the helper function added here to add a
confirmation dialog if the user tries to remove a runtime extension
that's being used; currently we just let them remove it.

This is limited to only looking in the current flatpak installation, so
a per-user app using a system-wide runtime extension would not be found.

Helps: #3531
  • Loading branch information
mwleeds committed Jun 20, 2022
1 parent e9030fe commit d8dfdc2
Show file tree
Hide file tree
Showing 5 changed files with 103 additions and 4 deletions.
5 changes: 5 additions & 0 deletions app/flatpak-cli-transaction.c
Original file line number Diff line number Diff line change
Expand Up @@ -793,6 +793,11 @@ end_of_lifed_with_rebase (FlatpakTransaction *transaction,
if (flatpak_decomposed_is_runtime (ref) && !rebased_to_ref)
{
g_autoptr(GPtrArray) apps = flatpak_dir_list_app_refs_with_runtime (dir, ref, NULL, NULL);
g_autoptr(GPtrArray) indirect_apps = flatpak_dir_list_app_refs_with_runtime_extension (dir, ref, NULL, NULL);

/* Include apps which are using the ref as an extension of their runtime */
g_ptr_array_extend_and_steal (apps, g_steal_pointer (&indirect_apps));

if (apps && apps->len > 0)
{
g_print (_("Applications using this runtime:\n"));
Expand Down
4 changes: 4 additions & 0 deletions common/flatpak-dir-private.h
Original file line number Diff line number Diff line change
Expand Up @@ -650,6 +650,10 @@ GPtrArray * flatpak_dir_list_app_refs_with_runtime (Fla
FlatpakDecomposed *runtime_ref,
GCancellable *cancellable,
GError **error);
GPtrArray * flatpak_dir_list_app_refs_with_runtime_extension (FlatpakDir *self,
FlatpakDecomposed *runtime_ext_ref,
GCancellable *cancellable,
GError **error);
GVariant * flatpak_dir_read_latest_commit (FlatpakDir *self,
const char *remote,
FlatpakDecomposed *ref,
Expand Down
80 changes: 76 additions & 4 deletions common/flatpak-dir.c
Original file line number Diff line number Diff line change
Expand Up @@ -6702,12 +6702,84 @@ flatpak_dir_list_app_refs_with_runtime (FlatpakDir *self,
FlatpakDecomposed *app_ref = g_ptr_array_index (app_refs, i);
/* deploy v4 guarantees runtime info */
g_autoptr(GBytes) app_deploy_data = flatpak_dir_get_deploy_data (self, app_ref, 4, NULL, NULL);
const char *app_runtime;

if (app_deploy_data)
if (app_deploy_data == NULL)
continue;

app_runtime = flatpak_deploy_data_get_runtime (app_deploy_data);
if (g_strcmp0 (app_runtime, runtime_pref) == 0)
g_ptr_array_add (apps, flatpak_decomposed_ref (app_ref));
}

return g_steal_pointer (&apps);
}

GPtrArray *
flatpak_dir_list_app_refs_with_runtime_extension (FlatpakDir *self,
FlatpakDecomposed *runtime_ext_ref,
GCancellable *cancellable,
GError **error)
{
g_autoptr(GPtrArray) app_refs = NULL;
g_autoptr(GPtrArray) runtime_refs = NULL;
g_autoptr(GPtrArray) apps = g_ptr_array_new_with_free_func ((GDestroyNotify)flatpak_decomposed_unref);
g_autoptr(GPtrArray) matching_runtimes = g_ptr_array_new ();
g_autoptr(GBytes) ext_deploy_data = NULL;

/* deploy v4 guarantees extension-of info */
ext_deploy_data = flatpak_dir_get_deploy_data (self, runtime_ext_ref, 4, NULL, NULL);
/* Don't waste time if it's not an extension */
if (ext_deploy_data && flatpak_deploy_data_get_extension_of (ext_deploy_data) == NULL)
return g_steal_pointer (&apps);

/* First find runtimes that have @runtime_ref as an extension */
runtime_refs = flatpak_dir_list_refs (self, FLATPAK_KINDS_RUNTIME, NULL, NULL);
for (int i = 0; runtime_refs != NULL && i < runtime_refs->len; i++)
{
FlatpakDecomposed *runtime_ref = g_ptr_array_index (runtime_refs, i);
g_autoptr(GPtrArray) related = NULL;

if (flatpak_decomposed_id_is_subref (runtime_ref))
continue;

related = flatpak_dir_find_local_related (self, runtime_ref, NULL, TRUE, cancellable, error);
if (related == NULL)
return NULL;

for (int j = 0; j < related->len; j++)
{
const char *app_runtime = flatpak_deploy_data_get_runtime (app_deploy_data);
if (g_strcmp0 (app_runtime, runtime_pref) == 0)
g_ptr_array_add (apps, flatpak_decomposed_ref (app_ref));
FlatpakRelated *rel = g_ptr_array_index (related, j);
if (flatpak_decomposed_equal (rel->ref, runtime_ext_ref))
g_ptr_array_add (matching_runtimes, runtime_ref);
}
}

if (matching_runtimes->len == 0)
return g_steal_pointer (&apps);

/* Then find apps that use those matching runtimes */
app_refs = flatpak_dir_list_refs (self, FLATPAK_KINDS_APP, NULL, NULL);
for (int i = 0; app_refs != NULL && i < app_refs->len; i++)
{
FlatpakDecomposed *app_ref = g_ptr_array_index (app_refs, i);
/* deploy v4 guarantees runtime info */
g_autoptr(GBytes) app_deploy_data = flatpak_dir_get_deploy_data (self, app_ref, 4, NULL, NULL);
const char *app_runtime;

if (app_deploy_data == NULL)
continue;

app_runtime = flatpak_deploy_data_get_runtime (app_deploy_data);
for (int j = 0; j < matching_runtimes->len; j++)
{
FlatpakDecomposed *matching_runtime = g_ptr_array_index (matching_runtimes, j);
const char *matching_runtime_pref = flatpak_decomposed_get_pref (matching_runtime);
if (g_strcmp0 (app_runtime, matching_runtime_pref) == 0)
{
g_ptr_array_add (apps, flatpak_decomposed_ref (app_ref));
break;
}
}
}

Expand Down
5 changes: 5 additions & 0 deletions common/flatpak-utils-private.h
Original file line number Diff line number Diff line change
Expand Up @@ -359,6 +359,11 @@ g_hash_table_steal_extended (GHashTable *hash_table,
}
#endif

#if !GLIB_CHECK_VERSION (2, 62, 0)
void g_ptr_array_extend_and_steal (GPtrArray *array_to_extend,
GPtrArray *array);
#endif

#if !GLIB_CHECK_VERSION (2, 68, 0)
guint g_string_replace (GString *string,
const gchar *find,
Expand Down
13 changes: 13 additions & 0 deletions common/flatpak-utils.c
Original file line number Diff line number Diff line change
Expand Up @@ -9210,6 +9210,19 @@ running_under_sudo (void)
return FALSE;
}

#if !GLIB_CHECK_VERSION (2, 62, 0)
void
g_ptr_array_extend_and_steal (GPtrArray *array_to_extend,
GPtrArray *array)
{
/* Walk @array backwards so we can remove without shuffling pointers around. */
for (gsize i = array->len; i > 0; i--)
g_ptr_array_add (array_to_extend, g_ptr_array_steal_index_fast (array, i - 1));

g_ptr_array_unref (array);
}
#endif

#if !GLIB_CHECK_VERSION (2, 68, 0)
/* All this code is backported directly from glib */
guint
Expand Down

0 comments on commit d8dfdc2

Please sign in to comment.