diff --git a/app/flatpak-builtins-utils.c b/app/flatpak-builtins-utils.c index 5e1908004..5e36586ac 100644 --- a/app/flatpak-builtins-utils.c +++ b/app/flatpak-builtins-utils.c @@ -619,11 +619,6 @@ get_file_age (GFile *file) return (guint64) (now - mtime); } -static void -no_progress_cb (OstreeAsyncProgress *progress, gpointer user_data) -{ -} - static guint64 get_appstream_timestamp (FlatpakDir *dir, const char *remote, @@ -650,7 +645,6 @@ update_appstream (GPtrArray *dirs, GError **error) { gboolean changed; - gboolean res; int i, j; g_return_val_if_fail (dirs != NULL, FALSE); @@ -672,7 +666,6 @@ update_appstream (GPtrArray *dirs, for (i = 0; remotes[i] != NULL; i++) { g_autoptr(GError) local_error = NULL; - g_autoptr(OstreeAsyncProgressFinish) progress = NULL; guint64 ts_file_age; ts_file_age = get_appstream_timestamp (dir, remotes[i], arch); @@ -708,9 +701,8 @@ update_appstream (GPtrArray *dirs, g_print ("\n"); } } - progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); if (!flatpak_dir_update_appstream (dir, remotes[i], arch, &changed, - progress, cancellable, &local_error)) + NULL, cancellable, &local_error)) { if (quiet) g_debug ("%s: %s", _("Error updating"), local_error->message); @@ -730,7 +722,6 @@ update_appstream (GPtrArray *dirs, if (flatpak_dir_has_remote (dir, remote, NULL)) { - g_autoptr(OstreeAsyncProgressFinish) progress = NULL; guint64 ts_file_age; found = TRUE; @@ -744,10 +735,8 @@ update_appstream (GPtrArray *dirs, else g_debug ("%s:%s appstream age %" G_GUINT64_FORMAT " is greater than ttl %" G_GUINT64_FORMAT, remote, arch, ts_file_age, ttl); - progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); - res = flatpak_dir_update_appstream (dir, remote, arch, &changed, - progress, cancellable, error); - if (!res) + if (!flatpak_dir_update_appstream (dir, remote, arch, &changed, + NULL, cancellable, error)) return FALSE; } } diff --git a/common/Makefile.am.inc b/common/Makefile.am.inc index d9779c488..2717e5d0b 100644 --- a/common/Makefile.am.inc +++ b/common/Makefile.am.inc @@ -139,6 +139,8 @@ libflatpak_common_la_SOURCES = \ common/flatpak-oci-registry.c \ common/flatpak-portal-error.c \ common/flatpak-portal-error.h \ + common/flatpak-progress-private.h \ + common/flatpak-progress.c \ common/flatpak-ref.c \ common/flatpak-related-ref-private.h \ common/flatpak-related-ref.c \ diff --git a/common/flatpak-dir-private.h b/common/flatpak-dir-private.h index 1dc077e3b..3a40cf02e 100644 --- a/common/flatpak-dir-private.h +++ b/common/flatpak-dir-private.h @@ -25,6 +25,7 @@ #include "flatpak-common-types-private.h" #include "flatpak-context-private.h" +#include "flatpak-progress-private.h" #include "flatpak-variant-private.h" #include "libglnx/libglnx.h" @@ -561,7 +562,7 @@ gboolean flatpak_dir_update_appstream (FlatpakDir *self, const char *remote, const char *arch, gboolean *out_changed, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error); gboolean flatpak_dir_pull (FlatpakDir *self, @@ -575,7 +576,7 @@ gboolean flatpak_dir_pull (FlatpakDir *self, OstreeRepo *repo, FlatpakPullFlags flatpak_flags, OstreeRepoPullFlags flags, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error); gboolean flatpak_dir_pull_untrusted_local (FlatpakDir *self, @@ -583,7 +584,7 @@ gboolean flatpak_dir_pull_untrusted_local (FlatpakDir *self, const char *remote_name, const char *ref, const char **subpaths, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error); gboolean flatpak_dir_list_refs_for_name (FlatpakDir *self, @@ -679,7 +680,7 @@ gboolean flatpak_dir_install (FlatpakDir *self, GFile *sideload_repo, GBytes *require_metadata, const char *token, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error); char *flatpak_dir_ensure_bundle_remote (FlatpakDir *self, @@ -730,7 +731,7 @@ gboolean flatpak_dir_update (FlatpakDir *self, GFile *sideload_repo, GBytes *require_metadata, const char *token, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error); gboolean flatpak_dir_uninstall (FlatpakDir *self, diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c index 3f591c9c4..24168bbbf 100644 --- a/common/flatpak-dir.c +++ b/common/flatpak-dir.c @@ -113,7 +113,7 @@ static gboolean flatpak_dir_mirror_oci (FlatpakDir *self, const char *ref, const char *skip_if_current_is, const char *token, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error); @@ -4112,7 +4112,7 @@ flatpak_dir_update_appstream_oci (FlatpakDir *self, const char *remote, const char *arch, gboolean *out_changed, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -4190,7 +4190,7 @@ flatpak_dir_update_appstream (FlatpakDir *self, const char *remote, const char *arch, gboolean *out_changed, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -4382,7 +4382,7 @@ get_common_pull_options (GVariantBuilder *builder, const char *current_local_checksum, gboolean force_disable_deltas, OstreeRepoPullFlags flags, - OstreeAsyncProgress *progress) + FlatpakProgress *progress) { guint32 update_interval = 0; GVariantBuilder hdr_builder; @@ -4422,7 +4422,7 @@ get_common_pull_options (GVariantBuilder *builder, g_variant_new_variant (g_variant_new_string ("flatpak/" PACKAGE_VERSION))); if (progress != NULL) - update_interval = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (progress), "update-interval")); + update_interval = flatpak_progress_get_update_interval (progress); if (update_interval == 0) update_interval = FLATPAK_DEFAULT_UPDATE_INTERVAL_MS; @@ -4456,7 +4456,7 @@ repo_pull (OstreeRepo *self, const char *token, FlatpakPullFlags flatpak_flags, OstreeRepoPullFlags flags, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -4542,9 +4542,11 @@ repo_pull (OstreeRepo *self, options = g_variant_ref_sink (g_variant_builder_end (&builder)); + g_autoptr(FlatpakMainContext) context = flatpak_progress_push_main_context (progress); + if (!ostree_repo_pull_with_options (self, sideload_url ? sideload_url : state->remote_name, - options, progress, cancellable, error)) + options, context->ostree_progress, cancellable, error)) return translate_ostree_repo_pull_errors (error); if (old_commit && @@ -4579,21 +4581,14 @@ ensure_soup_session (FlatpakDir *self) } } -typedef struct -{ - OstreeAsyncProgress *progress; - guint64 previous_dl; -} ExtraDataProgress; - static void extra_data_progress_report (guint64 downloaded_bytes, gpointer user_data) { - ExtraDataProgress *extra_progress = user_data; + FlatpakProgress *progress = FLATPAK_PROGRESS (user_data); - if (extra_progress->progress) - ostree_async_progress_set_uint64 (extra_progress->progress, "transferred-extra-data-bytes", - extra_progress->previous_dl + downloaded_bytes); + if (progress) + flatpak_progress_update_extra_data (progress, downloaded_bytes); } static gboolean @@ -4605,7 +4600,7 @@ flatpak_dir_setup_extra_data (FlatpakDir *self, GFile *sideload_repo, const char *token, FlatpakPullFlags flatpak_flags, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -4681,26 +4676,11 @@ flatpak_dir_setup_extra_data (FlatpakDir *self, } if (progress) - { - ostree_async_progress_set (progress, - "outstanding-extra-data", "t", n_extra_data, - "total-extra-data", "t", n_extra_data, - "total-extra-data-bytes", "t", total_download_size, - "transferred-extra-data-bytes", "t", (guint64) 0, - "downloading-extra-data", "u", 0, - NULL); - } + flatpak_progress_init_extra_data (progress, n_extra_data, total_download_size); return TRUE; } -static inline void -reset_async_progress_extra_data (OstreeAsyncProgress *progress) -{ - if (progress) - ostree_async_progress_set_uint (progress, "downloading-extra-data", 0); -} - static gboolean flatpak_dir_pull_extra_data (FlatpakDir *self, OstreeRepo *repo, @@ -4708,7 +4688,7 @@ flatpak_dir_pull_extra_data (FlatpakDir *self, const char *ref, const char *rev, FlatpakPullFlags flatpak_flags, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -4721,7 +4701,6 @@ flatpak_dir_pull_extra_data (FlatpakDir *self, g_autoptr(GFile) base_dir = NULL; int i; gsize n_extra_data; - ExtraDataProgress extra_data_progress = { NULL }; extra_data_sources = flatpak_repo_get_extra_data_sources (repo, rev, cancellable, NULL); if (extra_data_sources == NULL) @@ -4738,14 +4717,7 @@ flatpak_dir_pull_extra_data (FlatpakDir *self, /* Other fields were already set in flatpak_dir_setup_extra_data() */ if (progress) - { - ostree_async_progress_set (progress, - "start-time-extra-data", "t", g_get_monotonic_time (), - "downloading-extra-data", "u", 1, - NULL); - } - - extra_data_progress.progress = progress; + flatpak_progress_start_extra_data (progress); base_dir = flatpak_get_user_base_dir_location (); @@ -4780,7 +4752,7 @@ flatpak_dir_pull_extra_data (FlatpakDir *self, if (!g_str_has_prefix (extra_data_uri, "http:") && !g_str_has_prefix (extra_data_uri, "https:")) { - reset_async_progress_extra_data (progress); + flatpak_progress_reset_extra_data (progress); return flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("Unsupported extra data uri %s"), extra_data_uri); } @@ -4806,31 +4778,33 @@ flatpak_dir_pull_extra_data (FlatpakDir *self, { ensure_soup_session (self); bytes = flatpak_load_http_uri (self->soup_session, extra_data_uri, 0, NULL, - extra_data_progress_report, &extra_data_progress, + extra_data_progress_report, progress, cancellable, error); } if (bytes == NULL) { - reset_async_progress_extra_data (progress); + if (progress) + flatpak_progress_reset_extra_data (progress); g_prefix_error (error, _("While downloading %s: "), extra_data_uri); return FALSE; } if (g_bytes_get_size (bytes) != download_size) { - reset_async_progress_extra_data (progress); + if (progress) + flatpak_progress_reset_extra_data (progress); return flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("Wrong size for extra data %s"), extra_data_uri); } - extra_data_progress.previous_dl += download_size; - if (progress) - ostree_async_progress_set_uint64 (progress, "outstanding-extra-data", n_extra_data - i - 1); + guint64 n_extra_data_remaining = n_extra_data - i - 1; + flatpak_progress_complete_extra_data_download (progress, download_size, n_extra_data_remaining); sha256 = g_compute_checksum_for_bytes (G_CHECKSUM_SHA256, bytes); if (strcmp (sha256, extra_data_sha256) != 0) { - reset_async_progress_extra_data (progress); + if (progress) + flatpak_progress_reset_extra_data (progress); return flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("Invalid checksum for extra data %s"), extra_data_uri); } @@ -4842,7 +4816,8 @@ flatpak_dir_pull_extra_data (FlatpakDir *self, extra_data = g_variant_ref_sink (g_variant_builder_end (extra_data_builder)); - reset_async_progress_extra_data (progress); + if (progress) + flatpak_progress_reset_extra_data (progress); if (!ostree_repo_read_commit_detached_metadata (repo, rev, &detached_metadata, cancellable, error)) @@ -4897,65 +4872,15 @@ lookup_oci_registry_uri_from_summary (GVariant *summary, return g_steal_pointer (®istry_uri); } -static void -oci_pull_init_progress (OstreeAsyncProgress *progress) -{ - guint64 start_time = g_get_monotonic_time () - 2; - - if (progress == NULL) - return; - - ostree_async_progress_set (progress, - "outstanding-fetches", "u", 0, - "outstanding-writes", "u", 0, - "fetched", "u", 0, - "requested", "u", 0, - "scanning", "u", 0, - "scanned-metadata", "u", 0, - "bytes-transferred", "t", (guint64) 0, - "start-time", "t", start_time, - "outstanding-metadata-fetches", "u", 0, - "metadata-fetched", "u", 0, - "outstanding-extra-data", "t", (guint64) 0, - "total-extra-data", "t", (guint64) 0, - "total-extra-data-bytes", "t", (guint64) 0, - "transferred-extra-data-bytes", "t", (guint64) 0, - "downloading-extra-data", "u", 0, - "fetched-delta-parts", "u", 0, - "total-delta-parts", "u", 0, - "fetched-delta-fallbacks", "u", 0, - "total-delta-fallbacks", "u", 0, - "fetched-delta-part-size", "t", (guint64) 0, - "total-delta-part-size", "t", (guint64) 0, - "total-delta-part-usize", "t", (guint64) 0, - "total-delta-superblocks", "u", 0, - "status", "s", "", - "caught-error", "b", FALSE, - NULL); -} - static void oci_pull_progress_cb (guint64 total_size, guint64 pulled_size, guint32 n_layers, guint32 pulled_layers, gpointer data) { - OstreeAsyncProgress *progress = data; + FlatpakProgress *progress = data; - if (progress == NULL) - return; - - /* Deltas */ - ostree_async_progress_set (progress, - "outstanding-fetches", "u", n_layers - pulled_layers, - "fetched-delta-parts", "u", pulled_layers, - "total-delta-parts", "u", n_layers, - "fetched-delta-fallbacks", "u", 0, - "total-delta-fallbacks", "u", 0, - "bytes-transferred", "t", pulled_size, - "total-delta-part-size", "t", total_size, - "total-delta-part-usize", "t", total_size, - "total-delta-superblocks", "u", 0, - NULL); + if (progress) + flatpak_progress_update_oci_pull (progress, total_size, pulled_size, n_layers, pulled_layers); } static gboolean @@ -4965,7 +4890,7 @@ flatpak_dir_mirror_oci (FlatpakDir *self, const char *ref, const char *skip_if_current_is, const char *token, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -5008,8 +4933,8 @@ flatpak_dir_mirror_oci (FlatpakDir *self, flatpak_oci_registry_set_token (registry, token); - g_assert (progress != NULL); - oci_pull_init_progress (progress); + if (progress) + flatpak_progress_start_oci_pull (progress); g_debug ("Mirroring OCI image %s", oci_digest); @@ -5030,7 +4955,7 @@ flatpak_dir_pull_oci (FlatpakDir *self, FlatpakPullFlags flatpak_flags, OstreeRepoPullFlags flags, const char *token, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -5096,8 +5021,8 @@ flatpak_dir_pull_oci (FlatpakDir *self, if (repo == NULL) repo = self->repo; - g_assert (progress != NULL); - oci_pull_init_progress (progress); + if (progress) + flatpak_progress_start_oci_pull (progress); g_debug ("Pulling OCI image %s", oci_digest); @@ -5136,7 +5061,7 @@ flatpak_dir_pull (FlatpakDir *self, OstreeRepo *repo, FlatpakPullFlags flatpak_flags, OstreeRepoPullFlags flags, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -5173,8 +5098,6 @@ flatpak_dir_pull (FlatpakDir *self, if (*url == 0) return TRUE; /* Empty url, silently disables updates */ - g_assert (progress != NULL); - /* We get the rev ahead of time so that we know it for looking up e.g. extra-data and to make sure we're atomically using a single rev if we happen to do multiple pulls (e.g. with subpaths) */ @@ -5300,7 +5223,7 @@ repo_pull_local_untrusted (FlatpakDir *self, const char **dirs_to_pull, const char *ref, const char *checksum, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -5318,8 +5241,6 @@ repo_pull_local_untrusted (FlatpakDir *self, if (error == NULL) error = &dummy_error; - g_assert (progress != NULL); - refs[0] = ref; commits[0] = checksum; @@ -5350,8 +5271,9 @@ repo_pull_local_untrusted (FlatpakDir *self, } options = g_variant_ref_sink (g_variant_builder_end (&builder)); + g_autoptr(FlatpakMainContext) main_context = flatpak_progress_push_main_context (progress); res = ostree_repo_pull_with_options (repo, url, options, - progress, cancellable, error); + main_context->ostree_progress, cancellable, error); if (!res) translate_ostree_repo_pull_errors (error); @@ -5364,7 +5286,7 @@ flatpak_dir_pull_untrusted_local (FlatpakDir *self, const char *remote_name, const char *ref, const char **subpaths, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -8392,7 +8314,7 @@ flatpak_dir_install (FlatpakDir *self, GFile *sideload_repo, GBytes *require_metadata, const char *token, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { @@ -9131,7 +9053,7 @@ flatpak_dir_update (FlatpakDir *self, GFile *sideload_repo, GBytes *require_metadata, const char *token, - OstreeAsyncProgress *progress, + FlatpakProgress *progress, GCancellable *cancellable, GError **error) { diff --git a/common/flatpak-installation.c b/common/flatpak-installation.c index 174f4b599..48c61fafe 100644 --- a/common/flatpak-installation.c +++ b/common/flatpak-installation.c @@ -35,6 +35,7 @@ #include "flatpak-installed-ref-private.h" #include "flatpak-instance-private.h" #include "flatpak-related-ref-private.h" +#include "flatpak-progress-private.h" #include "flatpak-remote-private.h" #include "flatpak-remote-ref-private.h" #include "flatpak-run-private.h" @@ -87,11 +88,6 @@ enum { PROP_0, }; -static void -no_progress_cb (OstreeAsyncProgress *progress, gpointer user_data) -{ -} - static void flatpak_installation_finalize (GObject *object) { @@ -1769,7 +1765,7 @@ flatpak_installation_install_full (FlatpakInstallation *self, const char *arch, const char *branch, const char * const *subpaths, - FlatpakProgressCallback progress, + FlatpakProgressCallback progress_cb, gpointer progress_data, GCancellable *cancellable, GError **error) @@ -1777,10 +1773,9 @@ flatpak_installation_install_full (FlatpakInstallation *self, g_autoptr(FlatpakDir) dir = NULL; g_autofree char *ref = NULL; g_autoptr(FlatpakDir) dir_clone = NULL; - g_autoptr(OstreeAsyncProgressFinish) ostree_progress = NULL; + g_autoptr(FlatpakProgress) progress = NULL; g_autoptr(GFile) deploy_dir = NULL; g_autoptr(FlatpakRemoteState) state = NULL; - g_autoptr(GMainContextPopDefault) main_context = NULL; dir = flatpak_installation_get_dir (self, error); if (dir == NULL) @@ -1807,13 +1802,8 @@ flatpak_installation_install_full (FlatpakInstallation *self, if (!flatpak_dir_ensure_repo (dir_clone, cancellable, error)) return NULL; - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); - - if (progress) - ostree_progress = flatpak_progress_new (progress, progress_data); - else - ostree_progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); + if (progress_cb) + progress = flatpak_progress_new (progress_cb, progress_data); if (!flatpak_dir_install (dir_clone, (flags & FLATPAK_INSTALL_FLAGS_NO_PULL) != 0, @@ -1821,7 +1811,7 @@ flatpak_installation_install_full (FlatpakInstallation *self, (flags & FLATPAK_INSTALL_FLAGS_NO_STATIC_DELTAS) != 0, FALSE, FALSE, state, ref, NULL, (const char **) subpaths, NULL, NULL, NULL, NULL, - ostree_progress, cancellable, error)) + progress, cancellable, error)) return NULL; if (!(flags & FLATPAK_INSTALL_FLAGS_NO_TRIGGERS) && @@ -1928,7 +1918,7 @@ flatpak_installation_update_full (FlatpakInstallation *self, const char *arch, const char *branch, const char * const *subpaths, - FlatpakProgressCallback progress, + FlatpakProgressCallback progress_cb, gpointer progress_data, GCancellable *cancellable, GError **error) @@ -1937,12 +1927,11 @@ flatpak_installation_update_full (FlatpakInstallation *self, g_autofree char *ref = NULL; g_autoptr(GFile) deploy_dir = NULL; g_autoptr(FlatpakDir) dir_clone = NULL; - g_autoptr(OstreeAsyncProgressFinish) ostree_progress = NULL; + g_autoptr(FlatpakProgress) progress = NULL; g_autofree char *remote_name = NULL; FlatpakInstalledRef *result = NULL; g_autofree char *target_commit = NULL; g_autoptr(FlatpakRemoteState) state = NULL; - g_autoptr(GMainContextPopDefault) main_context = NULL; dir = flatpak_installation_get_dir (self, error); if (dir == NULL) @@ -1980,13 +1969,8 @@ flatpak_installation_update_full (FlatpakInstallation *self, if (!flatpak_dir_ensure_repo (dir_clone, cancellable, error)) return NULL; - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); - - if (progress) - ostree_progress = flatpak_progress_new (progress, progress_data); - else - ostree_progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); + if (progress_cb) + progress = flatpak_progress_new (progress_cb, progress_data); if (!flatpak_dir_update (dir_clone, (flags & FLATPAK_UPDATE_FLAGS_NO_PULL) != 0, @@ -1995,7 +1979,7 @@ flatpak_installation_update_full (FlatpakInstallation *self, FALSE, FALSE, FALSE, state, ref, target_commit, (const char **) subpaths, NULL, NULL, NULL, NULL, - ostree_progress, cancellable, error)) + progress, cancellable, error)) return NULL; if (!(flags & FLATPAK_UPDATE_FLAGS_NO_TRIGGERS) && @@ -2010,7 +1994,6 @@ flatpak_installation_update_full (FlatpakInstallation *self, if (!(flags & FLATPAK_UPDATE_FLAGS_NO_PULL) && !(flags & FLATPAK_UPDATE_FLAGS_NO_PRUNE)) flatpak_dir_prune (dir_clone, cancellable, NULL); - return result; } @@ -2509,7 +2492,7 @@ gboolean flatpak_installation_update_appstream_full_sync (FlatpakInstallation *self, const char *remote_name, const char *arch, - FlatpakProgressCallback progress, + FlatpakProgressCallback progress_cb, gpointer progress_data, gboolean *out_changed, GCancellable *cancellable, @@ -2517,9 +2500,7 @@ flatpak_installation_update_appstream_full_sync (FlatpakInstallation *self, { g_autoptr(FlatpakDir) dir = NULL; g_autoptr(FlatpakDir) dir_clone = NULL; - g_autoptr(OstreeAsyncProgressFinish) ostree_progress = NULL; - gboolean res; - g_autoptr(GMainContextPopDefault) main_context = NULL; + g_autoptr(FlatpakProgress) progress = NULL; dir = flatpak_installation_get_dir (self, error); if (dir == NULL) @@ -2530,23 +2511,16 @@ flatpak_installation_update_appstream_full_sync (FlatpakInstallation *self, if (!flatpak_dir_ensure_repo (dir_clone, cancellable, error)) return FALSE; - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); + if (progress_cb) + progress = flatpak_progress_new (progress_cb, progress_data); - if (progress) - ostree_progress = flatpak_progress_new (progress, progress_data); - else - ostree_progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); - - res = flatpak_dir_update_appstream (dir_clone, - remote_name, - arch, - out_changed, - ostree_progress, - cancellable, - error); - - return res; + return flatpak_dir_update_appstream (dir_clone, + remote_name, + arch, + out_changed, + progress, + cancellable, + error); } diff --git a/common/flatpak-progress-private.h b/common/flatpak-progress-private.h new file mode 100644 index 000000000..ba3a9ccac --- /dev/null +++ b/common/flatpak-progress-private.h @@ -0,0 +1,84 @@ +/* + * Copyright © 2019 Endless Mobile, Inc + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * 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, see . + * + * Authors: + * Philip Chimento + */ + +#ifndef FLATPAK_PROGRESS_H +#define FLATPAK_PROGRESS_H + +#include +#include + +#include "flatpak-installation.h" + +#define FLATPAK_TYPE_PROGRESS flatpak_progress_get_type () + +G_DECLARE_FINAL_TYPE (FlatpakProgress, flatpak_progress, FLATPAK, PROGRESS, GObject); + +struct _FlatpakMainContext { + FlatpakProgress *progress; + GMainContext *context; + OstreeAsyncProgress *ostree_progress; +}; +typedef struct _FlatpakMainContext FlatpakMainContext; + +void flatpak_main_context_wait (FlatpakMainContext *self, + gpointer *watch_location); +void flatpak_main_context_finish (FlatpakMainContext *self); + +G_DEFINE_AUTOPTR_CLEANUP_FUNC (FlatpakMainContext, flatpak_main_context_finish); + +FlatpakProgress *flatpak_progress_new (FlatpakProgressCallback callback, + gpointer user_data); + +void flatpak_progress_init_extra_data (FlatpakProgress *self, + guint64 n_extra_data, + guint64 total_download_size); +gboolean flatpak_progress_get_extra_data_initialized (FlatpakProgress *self); +void flatpak_progress_start_extra_data (FlatpakProgress *self); +void flatpak_progress_reset_extra_data (FlatpakProgress *self); +void flatpak_progress_update_extra_data (FlatpakProgress *self, + guint64 downloaded_bytes); +void flatpak_progress_complete_extra_data_download (FlatpakProgress *self, + guint64 download_size, + guint64 n_extra_data_remaining); + +void flatpak_progress_start_oci_pull (FlatpakProgress *self); +void flatpak_progress_update_oci_pull (FlatpakProgress *self, + guint64 total_size, + guint64 pulled_size, + guint32 n_layers, + guint32 pulled_layers); + +guint32 flatpak_progress_get_update_interval (FlatpakProgress *self); +void flatpak_progress_set_update_interval (FlatpakProgress *self, + guint32 interval); + +guint64 flatpak_progress_get_bytes_transferred (FlatpakProgress *self); +guint64 flatpak_progress_get_transferred_extra_data_bytes (FlatpakProgress *self); +guint64 flatpak_progress_get_start_time (FlatpakProgress *self); +const char *flatpak_progress_get_status (FlatpakProgress *self); +int flatpak_progress_get_progress (FlatpakProgress *self); +gboolean flatpak_progress_get_estimating (FlatpakProgress *self); + +gboolean flatpak_progress_is_done (FlatpakProgress *self); +void flatpak_progress_done (FlatpakProgress *self); + +FlatpakMainContext *flatpak_progress_push_main_context (FlatpakProgress *maybe_progress); + +#endif /* FLATPAK_PROGRESS_H */ diff --git a/common/flatpak-progress.c b/common/flatpak-progress.c new file mode 100644 index 000000000..515b85916 --- /dev/null +++ b/common/flatpak-progress.c @@ -0,0 +1,568 @@ +/* + * Copyright © 2019 Endless Mobile, Inc + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * 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, see . + * + * Authors: + * Philip Chimento + */ + +#include "config.h" + +#include +#include + +#include "flatpak-progress-private.h" + +static OstreeAsyncProgress *flatpak_progress_issue_ostree_progress (FlatpakProgress *self); +static void flatpak_progress_revoke_ostree_progress (FlatpakProgress *self, + OstreeAsyncProgress *ostree_progress); + +void +flatpak_main_context_wait (FlatpakMainContext *self, + gpointer *watch_location) +{ + while (*watch_location == NULL) + g_main_context_iteration (self->context, TRUE); +} + +void +flatpak_main_context_finish (FlatpakMainContext *self) +{ + if (self->progress) + flatpak_progress_revoke_ostree_progress (self->progress, self->ostree_progress); + else + g_object_unref (self->ostree_progress); + + if (self->context) + g_main_context_pop_thread_default (self->context); + + g_slice_free(FlatpakMainContext, self); +} + +FlatpakMainContext * +flatpak_progress_push_main_context (FlatpakProgress *maybe_progress) +{ + FlatpakMainContext *retval = g_slice_new0 (FlatpakMainContext); + retval->progress = maybe_progress; + + retval->context = g_main_context_new (); + g_main_context_push_thread_default (retval->context); + + if (maybe_progress) + retval->ostree_progress = flatpak_progress_issue_ostree_progress (maybe_progress); + else + retval->ostree_progress = ostree_async_progress_new (); + + return retval; +} + + +struct _FlatpakProgress +{ + GObject parent; + + /* Callback */ + FlatpakProgressCallback callback; + gpointer user_data; + + char *status; + + /* Extra data information */ + + guint64 start_time_extra_data; + guint64 outstanding_extra_data; + guint64 total_extra_data; + guint64 transferred_extra_data_bytes; + guint64 total_extra_data_bytes; /* the sum of all extra data file sizes (in bytes) */ + guint64 extra_data_previous_dl; + + /* OCI pull information */ + char *ostree_status; /* only sent by OSTree when the pull ends (with or without an error) */ + guint64 start_time; + guint64 bytes_transferred; /* every and all transferred data (in bytes) */ + guint64 fetched_delta_part_size; /* the size (in bytes) of already fetched static deltas */ + guint64 total_delta_part_size; /* the total size (in bytes) of static deltas */ + guint64 total_delta_part_usize; + guint outstanding_fetches; /* missing fetches (metadata + content + deltas) */ + guint outstanding_writes; /* all missing writes (sum of outstanding content, metadata and delta writes) */ + guint fetched; /* sum of content + metadata fetches */ + guint requested; /* sum of requested content + metadata fetches */ + guint scanning; + guint scanned_metadata; + guint outstanding_metadata_fetches; /* missing metadata-only fetches */ + guint metadata_fetched; /* the number of fetched metadata objects */ + guint fetched_delta_parts; + guint total_delta_parts; + guint fetched_delta_fallbacks; + guint total_delta_fallbacks; + guint total_delta_superblocks; + + /* Self-progress-reporting fields, not from OSTree */ + guint progress; + guint last_total; + + guint32 update_interval; + + /* Flags */ + gboolean downloading_extra_data : 1; /* whether extra-data files are being downloaded or not */ + gboolean caught_error : 1; + gboolean estimating : 1; + gboolean last_was_metadata : 1; + gboolean done : 1; +}; + +G_DEFINE_TYPE (FlatpakProgress, flatpak_progress, G_TYPE_OBJECT); + +static void +flatpak_progress_finalize (GObject *object) +{ + FlatpakProgress *self = FLATPAK_PROGRESS (object); + + g_clear_pointer (&self->status, g_free); + g_clear_pointer (&self->ostree_status, g_free); + + G_OBJECT_CLASS (flatpak_progress_parent_class)->finalize (object); +} + +static void +flatpak_progress_class_init (FlatpakProgressClass *klass) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + gobject_class->finalize = flatpak_progress_finalize; +} + +static void +flatpak_progress_init (FlatpakProgress *self) +{ + self->status = g_strdup ("Initializing"); + self->ostree_status = g_strdup (""); + self->estimating = TRUE; + self->last_was_metadata = TRUE; +} + +FlatpakProgress * +flatpak_progress_new (FlatpakProgressCallback callback, + gpointer user_data) +{ + FlatpakProgress *retval; + + retval = g_object_new (FLATPAK_TYPE_PROGRESS, NULL); + retval->callback = callback; + retval->user_data = user_data; + + return retval; +} + +static inline guint +get_write_progress (guint outstanding_writes) +{ + return outstanding_writes > 0 ? (guint) (3 / (gdouble) outstanding_writes) : 3; +} + +static void +update_status_progress_and_estimating (FlatpakProgress *self) +{ + GString *buf; + guint64 total = 0; + guint64 elapsed_time; + guint new_progress = 0; + gboolean estimating = FALSE; + guint64 total_transferred; + gboolean last_was_metadata = self->last_was_metadata; + g_autofree gchar *formatted_bytes_total_transferred = NULL; + + buf = g_string_new (""); + + /* We get some extra calls before we've really started due to the initialization of the + extra data, so ignore those */ + if (self->requested == 0) + { + return; + } + + /* The heuristic here goes as follows: + * - While fetching metadata, grow up to 5% + * - Download goes up to 97% + * - Writing objects adds the last 3% + */ + + elapsed_time = (g_get_monotonic_time () - self->start_time) / G_USEC_PER_SEC; + + /* When we receive the status, it means that the ostree pull operation is + * finished. We only have to be careful about the extra-data fields. */ + if (*self->ostree_status && self->total_extra_data_bytes == 0) + { + g_string_append (buf, self->ostree_status); + new_progress = 100; + goto out; + } + + total_transferred = self->bytes_transferred + self->transferred_extra_data_bytes; + formatted_bytes_total_transferred = g_format_size_full (total_transferred, 0); + + self->last_was_metadata = FALSE; + + if (self->total_delta_parts == 0 && + (self->outstanding_metadata_fetches > 0 || last_was_metadata) && + self->metadata_fetched < 20) + { + /* We need to hit two callbacks with no metadata outstanding, because + sometimes we get called when we just handled a metadata, but did + not yet process it and add more metadata */ + if (self->outstanding_metadata_fetches > 0) + self->last_was_metadata = TRUE; + + /* At this point we don't really know how much data there is, so we have to make a guess. + * Since its really hard to figure out early how much data there is we report 1% until + * all objects are scanned. */ + + estimating = TRUE; + + g_string_append_printf (buf, _("Downloading metadata: %u/(estimating) %s"), + self->fetched, formatted_bytes_total_transferred); + + /* Go up to 5% until the metadata is all fetched */ + new_progress = 0; + if (self->requested > 0) + new_progress = self->fetched * 5 / self->requested; + } + else + { + if (self->total_delta_parts > 0) + { + g_autofree gchar *formatted_bytes_total = NULL; + + /* We're only using deltas, so we can ignore regular objects + * and get perfect sizes. + * + * fetched_delta_part_size is the total size of all the + * delta parts and fallback objects that were already + * available at the start and need not be downloaded. + */ + total = self->total_delta_part_size - self->fetched_delta_part_size + self->total_extra_data_bytes; + formatted_bytes_total = g_format_size_full (total, 0); + + g_string_append_printf (buf, _("Downloading: %s/%s"), + formatted_bytes_total_transferred, + formatted_bytes_total); + } + else + { + /* Non-deltas, so we can't know anything other than object + counts, except the additional extra data which we know + the byte size of. To be able to compare them with the + extra data we use the average object size to estimate a + total size. */ + double average_object_size = 1; + if (self->fetched > 0) + average_object_size = self->bytes_transferred / (double) self->fetched; + + total = average_object_size * self->requested + self->total_extra_data_bytes; + + if (self->downloading_extra_data) + { + g_autofree gchar *formatted_bytes_total = g_format_size_full (total, 0); + g_string_append_printf (buf, _("Downloading extra data: %s/%s"), + formatted_bytes_total_transferred, + formatted_bytes_total); + } + else + g_string_append_printf (buf, _("Downloading files: %d/%d %s"), + self->fetched, self->requested, formatted_bytes_total_transferred); + } + + /* The download progress goes up to 97% */ + if (total > 0) + { + new_progress = 5 + ((total_transferred / (gdouble) total) * 92); + } + else + { + new_progress = 97; + } + + /* And the writing of the objects adds 3% to the progress */ + new_progress += get_write_progress (self->outstanding_writes); + } + + if (elapsed_time > 0) // Ignore first second + { + g_autofree gchar *formatted_bytes_sec = g_format_size (total_transferred / elapsed_time); + g_string_append_printf (buf, " (%s/s)", formatted_bytes_sec); + } + +out: + if (new_progress < self->progress && self->last_total == total) + new_progress = self->progress; + self->last_total = total; + + g_free (self->status); + self->status = g_string_free (buf, FALSE); + self->progress = new_progress; + self->estimating = estimating; +} + +void +flatpak_progress_init_extra_data (FlatpakProgress *self, + guint64 n_extra_data, + guint64 total_download_size) +{ + self->outstanding_extra_data = n_extra_data; + self->total_extra_data = n_extra_data; + self->transferred_extra_data_bytes = 0; + self->total_extra_data_bytes = total_download_size; + self->downloading_extra_data = FALSE; + self->progress = 0; + update_status_progress_and_estimating (self); +} + +void +flatpak_progress_start_extra_data (FlatpakProgress *self) +{ + self->start_time_extra_data = g_get_monotonic_time (); + self->downloading_extra_data = TRUE; + update_status_progress_and_estimating (self); +} + +void +flatpak_progress_reset_extra_data (FlatpakProgress *self) +{ + self->downloading_extra_data = FALSE; + update_status_progress_and_estimating (self); +} + +void +flatpak_progress_update_extra_data (FlatpakProgress *self, + guint64 downloaded_bytes) +{ + self->transferred_extra_data_bytes = self->extra_data_previous_dl + downloaded_bytes; + update_status_progress_and_estimating (self); +} + +void +flatpak_progress_complete_extra_data_download (FlatpakProgress *self, + guint64 download_size, + guint64 n_extra_data_remaining) +{ + self->extra_data_previous_dl += download_size; + self->outstanding_extra_data = n_extra_data_remaining; + update_status_progress_and_estimating (self); +} + +void +flatpak_progress_start_oci_pull (FlatpakProgress *self) +{ + self->start_time = g_get_monotonic_time () - 2; + self->outstanding_fetches = 0; + self->outstanding_writes = 0; + self->fetched = 0; + self->requested = 0; + self->scanning = 0; + self->scanned_metadata = 0; + self->bytes_transferred = 0; + self->outstanding_metadata_fetches = 0; + self->metadata_fetched = 0; + self->outstanding_extra_data = 0; + self->total_extra_data = 0; + self->total_extra_data_bytes = 0; + self->downloading_extra_data = FALSE; + self->fetched_delta_parts = 0; + self->total_delta_parts = 0; + self->fetched_delta_fallbacks = 0; + self->total_delta_fallbacks = 0; + self->fetched_delta_part_size = 0; + self->total_delta_part_size = 0; + self->total_delta_part_usize = 0; + self->total_delta_superblocks = 0; + self->caught_error = FALSE; + update_status_progress_and_estimating (self); +} + +void +flatpak_progress_update_oci_pull (FlatpakProgress *self, + guint64 total_size, + guint64 pulled_size, + guint32 n_layers, + guint32 pulled_layers) +{ + self->outstanding_fetches = n_layers - pulled_layers; + self->fetched_delta_parts = pulled_layers; + self->total_delta_parts = n_layers; + self->fetched_delta_fallbacks = 0; + self->total_delta_fallbacks = 0; + self->bytes_transferred = pulled_size; + self->total_delta_part_size = total_size; + self->total_delta_part_usize = total_size; + self->total_delta_superblocks = 0; + update_status_progress_and_estimating (self); +} + +guint32 +flatpak_progress_get_update_interval (FlatpakProgress *self) +{ + return self->update_interval; +} + +void +flatpak_progress_set_update_interval (FlatpakProgress *self, + guint32 interval) +{ + self->update_interval = interval; +} + +guint64 +flatpak_progress_get_bytes_transferred (FlatpakProgress *self) +{ + return self->bytes_transferred; +} + +guint64 +flatpak_progress_get_transferred_extra_data_bytes (FlatpakProgress *self) +{ + return self->transferred_extra_data_bytes; +} + +guint64 +flatpak_progress_get_start_time (FlatpakProgress *self) +{ + return self->start_time; +} + +const char * +flatpak_progress_get_status (FlatpakProgress *self) +{ + return self->status; +} + +int +flatpak_progress_get_progress (FlatpakProgress *self) +{ + return self->progress; +} + +gboolean +flatpak_progress_get_estimating (FlatpakProgress *self) +{ + return self->estimating; +} + +static void +copy_ostree_progress_state (OstreeAsyncProgress *ostree_progress, + FlatpakProgress *self) +{ + gboolean downloading_extra_data, caught_error; + + g_clear_pointer (&self->ostree_status, g_free); + + ostree_async_progress_get (ostree_progress, + "start-time-extra-data", "t", &self->start_time_extra_data, + "outstanding-extra-data", "t", &self->outstanding_extra_data, + "total-extra-data", "t", &self->total_extra_data, + "transferred-extra-data-bytes", "t", &self->transferred_extra_data_bytes, + "total-extra-data-bytes", "t", &self->total_extra_data_bytes, + "status", "s", &self->ostree_status, + "start-time", "t", &self->start_time, + "bytes-transferred", "t", &self->bytes_transferred, + "fetched-delta-part-size", "t", &self->fetched_delta_part_size, + "total-delta-part-size", "t", &self->total_delta_part_size, + "total-delta-part-usize", "t", &self->total_delta_part_usize, + "outstanding-fetches", "u", &self->outstanding_fetches, + "outstanding-writes", "u", &self->outstanding_writes, + "fetched", "u", &self->fetched, + "requested", "u", &self->requested, + "scanning", "u", &self->scanning, + "scanned-metadata", "u", &self->scanned_metadata, + "outstanding-metadata-fetches", "u", &self->outstanding_metadata_fetches, + "metadata-fetched", "u", &self->metadata_fetched, + "fetched-delta-parts", "u", &self->fetched_delta_parts, + "total-delta-parts", "u", &self->total_delta_parts, + "fetched-delta-fallbacks", "u", &self->fetched_delta_fallbacks, + "total-delta-fallbacks", "u", &self->total_delta_fallbacks, + "total-delta-superblocks", "u", &self->total_delta_superblocks, + "downloading-extra-data", "u", &downloading_extra_data, + "caught-error", "b", &caught_error, + NULL); + /* Bitfield members */ + self->downloading_extra_data = downloading_extra_data; + self->caught_error = caught_error; + + update_status_progress_and_estimating (self); +} + +static void +invoke_callback (OstreeAsyncProgress *ostree_progress, + FlatpakProgress *progress) +{ + copy_ostree_progress_state (ostree_progress, progress); + progress->callback (progress->status, progress->progress, progress->estimating, progress->user_data); +} + +static OstreeAsyncProgress * +flatpak_progress_issue_ostree_progress (FlatpakProgress *self) +{ + OstreeAsyncProgress *ostree_progress = ostree_async_progress_new (); + ostree_async_progress_set (ostree_progress, + "start-time-extra-data", "t", self->start_time_extra_data, + "outstanding-extra-data", "t", self->outstanding_extra_data, + "total-extra-data", "t", self->total_extra_data, + "transferred-extra-data-bytes", "t", self->transferred_extra_data_bytes, + "total-extra-data-bytes", "t", self->total_extra_data_bytes, + "status", "s", self->ostree_status, + "start-time", "t", self->start_time, + "bytes-transferred", "t", self->bytes_transferred, + "fetched-delta-part-size", "t", self->fetched_delta_part_size, + "total-delta-part-size", "t", self->total_delta_part_size, + "total-delta-part-usize", "t", self->total_delta_part_usize, + "outstanding-fetches", "u", self->outstanding_fetches, + "outstanding-writes", "u", self->outstanding_writes, + "fetched", "u", self->fetched, + "requested", "u", self->requested, + "scanning", "u", self->scanning, + "scanned-metadata", "u", self->scanned_metadata, + "outstanding-metadata-fetches", "u", self->outstanding_metadata_fetches, + "metadata-fetched", "u", self->metadata_fetched, + "fetched-delta-parts", "u", self->fetched_delta_parts, + "total-delta-parts", "u", self->total_delta_parts, + "fetched-delta-fallbacks", "u", self->fetched_delta_fallbacks, + "total-delta-fallbacks", "u", self->total_delta_fallbacks, + "total-delta-superblocks", "u", self->total_delta_superblocks, + "downloading-extra-data", "u", (guint) self->downloading_extra_data, + "caught-error", "b", self->caught_error, + NULL); + g_signal_connect (ostree_progress, "changed", G_CALLBACK (invoke_callback), self); + + return ostree_progress; +} + +static void +flatpak_progress_revoke_ostree_progress (FlatpakProgress *self, + OstreeAsyncProgress *ostree_progress) +{ + ostree_async_progress_finish (ostree_progress); + copy_ostree_progress_state (ostree_progress, self); + g_object_unref (ostree_progress); +} + +gboolean +flatpak_progress_is_done (FlatpakProgress *self) +{ + return self->done; +} + +void +flatpak_progress_done (FlatpakProgress *self) +{ + self->done = TRUE; +} diff --git a/common/flatpak-transaction.c b/common/flatpak-transaction.c index a91064f51..da877d9fd 100644 --- a/common/flatpak-transaction.c +++ b/common/flatpak-transaction.c @@ -27,6 +27,7 @@ #include "flatpak-auth-private.h" #include "flatpak-error.h" #include "flatpak-installation-private.h" +#include "flatpak-progress-private.h" #include "flatpak-transaction-private.h" #include "flatpak-utils-private.h" #include "flatpak-variant-impl-private.h" @@ -209,14 +210,7 @@ struct _FlatpakTransactionProgress { GObject parent; - OstreeAsyncProgress *ostree_progress; - char *status; - gboolean estimating; - int progress; - guint64 total_transferred; - guint64 start_time; - - gboolean done; + FlatpakProgress *progress_obj; }; enum { @@ -276,7 +270,7 @@ void flatpak_transaction_progress_set_update_frequency (FlatpakTransactionProgress *self, guint update_interval) { - g_object_set_data (G_OBJECT (self->ostree_progress), "update-interval", GUINT_TO_POINTER (update_interval)); + flatpak_progress_set_update_interval (self->progress_obj, update_interval); } /** @@ -290,7 +284,7 @@ flatpak_transaction_progress_set_update_frequency (FlatpakTransactionProgress *s char * flatpak_transaction_progress_get_status (FlatpakTransactionProgress *self) { - return g_strdup (self->status); + return g_strdup (flatpak_progress_get_status (self->progress_obj)); } /** @@ -304,7 +298,7 @@ flatpak_transaction_progress_get_status (FlatpakTransactionProgress *self) gboolean flatpak_transaction_progress_get_is_estimating (FlatpakTransactionProgress *self) { - return self->estimating; + return flatpak_progress_get_estimating (self->progress_obj); } /** @@ -318,7 +312,7 @@ flatpak_transaction_progress_get_is_estimating (FlatpakTransactionProgress *self int flatpak_transaction_progress_get_progress (FlatpakTransactionProgress *self) { - return self->progress; + return flatpak_progress_get_progress (self->progress_obj); } /** @@ -333,7 +327,12 @@ flatpak_transaction_progress_get_progress (FlatpakTransactionProgress *self) guint64 flatpak_transaction_progress_get_bytes_transferred (FlatpakTransactionProgress *self) { - return self->total_transferred; + guint64 bytes_transferred, transferred_extra_data_bytes; + + bytes_transferred = flatpak_progress_get_bytes_transferred (self->progress_obj); + transferred_extra_data_bytes = flatpak_progress_get_transferred_extra_data_bytes (self->progress_obj); + + return bytes_transferred + transferred_extra_data_bytes; } /** @@ -348,7 +347,7 @@ flatpak_transaction_progress_get_bytes_transferred (FlatpakTransactionProgress * guint64 flatpak_transaction_progress_get_start_time (FlatpakTransactionProgress *self) { - return self->start_time; + return flatpak_progress_get_start_time (self->progress_obj); } static void @@ -356,8 +355,7 @@ flatpak_transaction_progress_finalize (GObject *object) { FlatpakTransactionProgress *self = (FlatpakTransactionProgress *) object; - g_free (self->status); - g_object_unref (self->ostree_progress); + g_object_unref (self->progress_obj); G_OBJECT_CLASS (flatpak_transaction_progress_parent_class)->finalize (object); } @@ -392,40 +390,21 @@ got_progress_cb (const char *status, gpointer user_data) { FlatpakTransactionProgress *p = user_data; - guint64 bytes_transferred; - guint64 transferred_extra_data_bytes; - guint64 start_time; - ostree_async_progress_get (p->ostree_progress, - "bytes-transferred", "t", &bytes_transferred, - "transferred-extra-data-bytes", "t", &transferred_extra_data_bytes, - "start-time", "t", &start_time, - NULL); - - g_free (p->status); - p->status = g_strdup (status); - p->progress = progress; - p->estimating = estimating; - p->total_transferred = bytes_transferred + transferred_extra_data_bytes; - p->start_time = start_time; - - if (!p->done) + if (!flatpak_progress_is_done (p->progress_obj)) g_signal_emit (p, progress_signals[CHANGED], 0); } static void flatpak_transaction_progress_init (FlatpakTransactionProgress *self) { - self->status = g_strdup ("Initializing"); - self->estimating = TRUE; - self->ostree_progress = flatpak_progress_new (got_progress_cb, self); + self->progress_obj = flatpak_progress_new (got_progress_cb, self); } static void flatpak_transaction_progress_done (FlatpakTransactionProgress *self) { - ostree_async_progress_finish (self->ostree_progress); - self->done = TRUE; + flatpak_progress_done (self->progress_obj); } static FlatpakTransactionProgress * @@ -3672,7 +3651,7 @@ _run_op_kind (FlatpakTransaction *self, op->resolved_sideload_path, op->resolved_metadata, op->resolved_token, - progress->ostree_progress, + progress->progress_obj, cancellable, error); flatpak_transaction_progress_done (progress); @@ -3723,7 +3702,7 @@ _run_op_kind (FlatpakTransaction *self, op->resolved_sideload_path, op->resolved_metadata, op->resolved_token, - progress->ostree_progress, + progress->progress_obj, cancellable, &local_error); flatpak_transaction_progress_done (progress); @@ -3816,7 +3795,6 @@ flatpak_transaction_real_run (FlatpakTransaction *self, gboolean succeeded = TRUE; gboolean needs_prune = FALSE; gboolean needs_triggers = FALSE; - g_autoptr(GMainContextPopDefault) main_context = NULL; gboolean ready_res = FALSE; int i; @@ -3844,9 +3822,6 @@ flatpak_transaction_real_run (FlatpakTransaction *self, !flatpak_transaction_update_metadata (self, cancellable, error)) return FALSE; - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); - if (!flatpak_transaction_add_auto_install (self, cancellable, error)) return FALSE; diff --git a/common/flatpak-utils-private.h b/common/flatpak-utils-private.h index 9038f2a8d..7d1014704 100644 --- a/common/flatpak-utils-private.h +++ b/common/flatpak-utils-private.h @@ -832,38 +832,6 @@ void flatpak_format_choices (const char **choices, const char *prompt, ...) G_GNUC_PRINTF (2, 3); -typedef void (*FlatpakProgressCallback)(const char *status, - guint progress, - gboolean estimating, - gpointer user_data); - -OstreeAsyncProgress *flatpak_progress_new (FlatpakProgressCallback progress, - gpointer progress_data); - -#if OSTREE_CHECK_VERSION (2019, 6) -#define FLATPAK_DO_CHAIN_PROGRESS 1 -#endif - -#ifdef FLATPAK_DO_CHAIN_PROGRESS -void flatpak_chained_progress_finish (OstreeAsyncProgress *progress); -#endif - -static inline void -flatpak_progress_unchain (OstreeAsyncProgress *chained_progress) -{ -#ifdef FLATPAK_DO_CHAIN_PROGRESS - if (chained_progress != NULL) - { - flatpak_chained_progress_finish (chained_progress); - g_object_unref (chained_progress); - } -#endif -} - -typedef OstreeAsyncProgress FlatpakAsyncProgressChained; -G_DEFINE_AUTOPTR_CLEANUP_FUNC (FlatpakAsyncProgressChained, flatpak_progress_unchain); - -FlatpakAsyncProgressChained *flatpak_progress_chain (OstreeAsyncProgress *progress); static inline void flatpak_ostree_progress_finish (OstreeAsyncProgress *progress) diff --git a/common/flatpak-utils.c b/common/flatpak-utils.c index 09d51cd15..27fd33e2a 100644 --- a/common/flatpak-utils.c +++ b/common/flatpak-utils.c @@ -45,6 +45,7 @@ #include "flatpak-dir-private.h" #include "flatpak-error.h" #include "flatpak-oci-registry-private.h" +#include "flatpak-progress-private.h" #include "flatpak-run-private.h" #include "flatpak-utils-base-private.h" #include "flatpak-utils-private.h" @@ -6389,367 +6390,6 @@ flatpak_get_current_locale_langs (void) return (char **) g_ptr_array_free (langs, FALSE); } -static inline guint -get_write_progress (guint outstanding_writes) -{ - return outstanding_writes > 0 ? (guint) (3 / (gdouble) outstanding_writes) : 3; -} - -static void -progress_cb (OstreeAsyncProgress *progress, gpointer user_data) -{ - gboolean last_was_metadata = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (progress), "last-was-metadata")); - FlatpakProgressCallback progress_cb = g_object_get_data (G_OBJECT (progress), "callback"); - guint last_progress = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (progress), "last_progress")); - guint last_total = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (progress), "last_total")); - GString *buf; - g_autofree char *status = NULL; - guint outstanding_fetches; - guint outstanding_metadata_fetches; - guint outstanding_writes; - guint64 bytes_transferred; - guint64 fetched_delta_part_size; - guint64 total_delta_part_size; - guint64 outstanding_extra_data; - guint64 total_extra_data_bytes; - guint64 transferred_extra_data_bytes; - guint64 total = 0; - guint metadata_fetched; - guint64 start_time; - guint64 elapsed_time; - guint new_progress = 0; - gboolean estimating = FALSE; - gboolean downloading_extra_data; - gboolean scanning; - guint n_scanned_metadata; - guint fetched_delta_parts; - guint total_delta_parts; - guint fetched_delta_part_fallbacks; - guint total_delta_part_fallbacks; - guint fetched; - guint requested; - guint64 total_transferred; - g_autofree gchar *formatted_bytes_total_transferred = NULL; - g_autoptr(GVariant) outstanding_fetchesv = NULL; - g_autoptr(GVariant) outstanding_extra_datav = NULL; - - /* We get some extra calls before we've really started due to the initialization of the - extra data, so ignore those */ - outstanding_fetchesv = ostree_async_progress_get_variant (progress, "outstanding-fetches"); - outstanding_extra_datav = ostree_async_progress_get_variant (progress, "outstanding-extra-data"); - if (outstanding_fetchesv == NULL || outstanding_extra_datav == NULL) - return; - - buf = g_string_new (""); - - /* The heuristic here goes as follows: - * - While fetching metadata, grow up to 5% - * - Download goes up to 97% - * - Writing objects adds the last 3% - * - * - * Meaning of each variable: - * - * Status: - * - status: only sent by OSTree when the pull ends (with or without an error) - * - * Fetches: - * - fetched: sum of content + metadata fetches - * - requested: sum of requested content and metadata fetches - * - bytes_transferred: every and all transferred data (in bytes) - * - metadata_fetched: the number of fetched metadata objects - * - outstanding_fetches: missing fetches (metadata + content + deltas) - * - outstanding_delta_fetches: missing delta-only fetches - * - outstanding_metadata_fetches: missing metadata-only fetches - * - fetched_content_bytes: the estimated downloaded size of content (in bytes) - * - total_content_bytes: the estimated total size of content, based on average bytes per object (in bytes) - * - * Writes: - * - outstanding_writes: all missing writes (sum of outstanding content, metadata and delta writes) - * - * Static deltas: - * - total_delta_part_size: the total size (in bytes) of static deltas - * - fetched_delta_part_size: the size (in bytes) of already fetched static deltas - * - * Extra data: - * - total_extra_data_bytes: the sum of all extra data file sizes (in bytes) - * - downloading_extra_data: whether extra-data files are being downloaded or not - */ - - /* We request everything in one go to make sure we don't race with the update from - the async download and get mixed results */ - ostree_async_progress_get (progress, - "outstanding-fetches", "u", &outstanding_fetches, - "outstanding-metadata-fetches", "u", &outstanding_metadata_fetches, - "outstanding-writes", "u", &outstanding_writes, - "scanning", "u", &scanning, - "scanned-metadata", "u", &n_scanned_metadata, - "fetched-delta-parts", "u", &fetched_delta_parts, - "total-delta-parts", "u", &total_delta_parts, - "fetched-delta-fallbacks", "u", &fetched_delta_part_fallbacks, - "total-delta-fallbacks", "u", &total_delta_part_fallbacks, - "fetched-delta-part-size", "t", &fetched_delta_part_size, - "total-delta-part-size", "t", &total_delta_part_size, - "bytes-transferred", "t", &bytes_transferred, - "fetched", "u", &fetched, - "metadata-fetched", "u", &metadata_fetched, - "requested", "u", &requested, - "start-time", "t", &start_time, - "status", "s", &status, - "outstanding-extra-data", "t", &outstanding_extra_data, - "total-extra-data-bytes", "t", &total_extra_data_bytes, - "transferred-extra-data-bytes", "t", &transferred_extra_data_bytes, - "downloading-extra-data", "u", &downloading_extra_data, - NULL); - - elapsed_time = (g_get_monotonic_time () - start_time) / G_USEC_PER_SEC; - - /* When we receive the status, it means that the ostree pull operation is - * finished. We only have to be careful about the extra-data fields. */ - if (status && *status && total_extra_data_bytes == 0) - { - g_string_append (buf, status); - new_progress = 100; - goto out; - } - - total_transferred = bytes_transferred + transferred_extra_data_bytes; - formatted_bytes_total_transferred = g_format_size_full (total_transferred, 0); - - g_object_set_data (G_OBJECT (progress), "last-was-metadata", GUINT_TO_POINTER (FALSE)); - - if (total_delta_parts == 0 && - (outstanding_metadata_fetches > 0 || last_was_metadata) && - metadata_fetched < 20) - { - /* We need to hit two callbacks with no metadata outstanding, because - sometimes we get called when we just handled a metadata, but did - not yet process it and add more metadata */ - if (outstanding_metadata_fetches > 0) - g_object_set_data (G_OBJECT (progress), "last-was-metadata", GUINT_TO_POINTER (TRUE)); - - /* At this point we don't really know how much data there is, so we have to make a guess. - * Since its really hard to figure out early how much data there is we report 1% until - * all objects are scanned. */ - - estimating = TRUE; - - g_string_append_printf (buf, _("Downloading metadata: %u/(estimating) %s"), - fetched, formatted_bytes_total_transferred); - - /* Go up to 5% until the metadata is all fetched */ - new_progress = 0; - if (requested > 0) - new_progress = fetched * 5 / requested; - } - else - { - if (total_delta_parts > 0) - { - g_autofree gchar *formatted_bytes_total = NULL; - - /* We're only using deltas, so we can ignore regular objects - * and get perfect sizes. - * - * fetched_delta_part_size is the total size of all the - * delta parts and fallback objects that were already - * available at the start and need not be downloaded. - */ - total = total_delta_part_size - fetched_delta_part_size + total_extra_data_bytes; - formatted_bytes_total = g_format_size_full (total, 0); - - g_string_append_printf (buf, _("Downloading: %s/%s"), - formatted_bytes_total_transferred, - formatted_bytes_total); - } - else - { - /* Non-deltas, so we can't know anything other than object - counts, except the additional extra data which we know - the byte size of. To be able to compare them with the - extra data we use the average object size to estimate a - total size. */ - double average_object_size = 1; - if (fetched > 0) - average_object_size = bytes_transferred / (double) fetched; - - total = average_object_size * requested + total_extra_data_bytes; - - if (downloading_extra_data) - { - g_autofree gchar *formatted_bytes_total = g_format_size_full (total, 0); - g_string_append_printf (buf, _("Downloading extra data: %s/%s"), - formatted_bytes_total_transferred, - formatted_bytes_total); - } - else - g_string_append_printf (buf, _("Downloading files: %d/%d %s"), - fetched, requested, formatted_bytes_total_transferred); - } - - /* The download progress goes up to 97% */ - if (total > 0) - { - new_progress = 5 + ((total_transferred / (gdouble) total) * 92); - } - else - { - new_progress = 97; - } - - /* And the writing of the objects adds 3% to the progress */ - new_progress += get_write_progress (outstanding_writes); - } - - if (elapsed_time > 0) // Ignore first second - { - g_autofree gchar *formatted_bytes_sec = g_format_size (total_transferred / elapsed_time); - g_string_append_printf (buf, " (%s/s)", formatted_bytes_sec); - } - -out: - if (new_progress < last_progress && last_total == total) - new_progress = last_progress; - g_object_set_data (G_OBJECT (progress), "last_progress", GUINT_TO_POINTER (new_progress)); - g_object_set_data (G_OBJECT (progress), "last_total", GUINT_TO_POINTER (total)); - - progress_cb (buf->str, new_progress, estimating, user_data); - - g_string_free (buf, TRUE); -} - -OstreeAsyncProgress * -flatpak_progress_new (FlatpakProgressCallback progress, - gpointer progress_data) -{ - OstreeAsyncProgress *ostree_progress = - ostree_async_progress_new_and_connect (progress_cb, - progress_data); - - g_object_set_data (G_OBJECT (ostree_progress), "callback", progress); - g_object_set_data (G_OBJECT (ostree_progress), "callback_data", progress_data); - g_object_set_data (G_OBJECT (ostree_progress), "last_progress", GUINT_TO_POINTER (0)); - g_object_set_data (G_OBJECT (ostree_progress), "last_total", GUINT_TO_POINTER (0)); - g_object_set_data (G_OBJECT (ostree_progress), "chained_from", NULL); - - return ostree_progress; -} - -#ifdef FLATPAK_DO_CHAIN_PROGRESS -static void -progress_trigger_change (OstreeAsyncProgress *progress) -{ - guint chain_count; - - /* Trigger changed signal in original progress by changing *something* */ - chain_count = ostree_async_progress_get_uint (progress, "flatpak-chain-count"); - ostree_async_progress_set_uint (progress, "flatpak-chain-count", chain_count + 1); -} - -static void -handle_chained_progress (OstreeAsyncProgress *chained_progress, - gpointer user_data) -{ - OstreeAsyncProgress *original_progress = (OstreeAsyncProgress *) user_data; - - /* Sync the chained progress's state back to the original instance, to take - * into account any updates received while a different GMainContext was - * active */ - ostree_async_progress_copy_state (chained_progress, original_progress); - progress_trigger_change (original_progress); - -} - -void -flatpak_chained_progress_finish (OstreeAsyncProgress *progress) -{ - /* At this point there might be outstanding idle events with changes in - * the chained progress, so we need to call ostree_async_progress_finish() to - * emit the changed signal which will call handle_chained_progress, - * copying the data to the original progress. - * - * Unfortunately it will first mark the chained progress dead - * which makes ostree_async_progress_copy_state() not actually copy - * anything. So, to fix this we do a copy ahead of time in case it - * was needed. - * - * We still need to call the regular finish() though to avoid some - * idle callback hanging around unresolved forever (and to cause - * the changed signal to be emitted). - */ - OstreeAsyncProgress *original_progress = OSTREE_ASYNC_PROGRESS (g_object_get_data (G_OBJECT (progress), "chained-from")); - - ostree_async_progress_copy_state (progress, original_progress); - ostree_async_progress_finish (progress); -} -#endif /* FLATPAK_DO_CHAIN_PROGRESS */ - -/* - * This is necessary when pushing a temporary GMainContext to be the thread - * default with flatpak_main_context_new_default() in order to call an async - * operation as if it were sync, if you have an OstreeAsyncProgress object that - * would otherwise be forwarded into the async operation. - * - * This is because the original OstreeAsyncProgress object won't receive any - * signals while the temporary GMainContext is active, since the GMainContext it - * was created with won't be iterated. - * - * Note that this should only be done when the two GMainContexts are in the same - * thread. If they are in different threads, then the progress's update callback - * will be called from the wrong thread. - * - * tl;dr instead of this: - * - * my_operation (OstreeAsyncProgress *progress) - * { - * g_autoptr(GMainContextPopDefault) context = NULL; - * context = flatpak_main_context_new_default (); - * ostree_some_async_op (progress, some_callback_setting_some_flag, data); - * while (wait_for_flag) - * g_main_context_iteration (context, TRUE); - * } - * - * do this: - * - * my_operation (OstreeAsyncProgress *progress) - * { - * g_autoptr(GMainContextPopDefault) context = NULL; - * g_autoptr(FlatpakAsyncProgressChained) chained_progress = NULL; - * context = flatpak_main_context_new_default (); - * chained_progress = flatpak_progress_chain (progress); - * ostree_some_async_op (chained_progress, - * some_callback_setting_some_flag, data); - * while (wait_for_flag) - * g_main_context_iteration (context, TRUE); - * } - * - * This is a no-op, preserving the current behaviour where progress events are - * not fired, if the libostree version isn't new enough. - */ -FlatpakAsyncProgressChained * -flatpak_progress_chain (OstreeAsyncProgress *progress) -{ -#ifdef FLATPAK_DO_CHAIN_PROGRESS - if (progress == NULL) - return NULL; - - OstreeAsyncProgress *chained_progress = ostree_async_progress_new (); - - /* Copy the OstreeAsyncProgress's state to the chained instance */ - ostree_async_progress_copy_state (progress, chained_progress); - - g_object_set_data (G_OBJECT (chained_progress), "chained-from", progress); - - g_signal_connect_data (chained_progress, "changed", - G_CALLBACK (handle_chained_progress), - g_object_ref (progress), (GClosureNotify)g_object_unref, 0); - - return chained_progress; -#else /* !FLATPAK_DO_CHAIN_PROGRESS */ - return progress; -#endif -} - void flatpak_log_dir_access (FlatpakDir *dir) { diff --git a/doc/reference/Makefile.am b/doc/reference/Makefile.am index 1b2533376..bd32d1ea3 100644 --- a/doc/reference/Makefile.am +++ b/doc/reference/Makefile.am @@ -26,6 +26,7 @@ IGNORE_HFILES = \ flatpak-json-oci-private.h \ flatpak-json-private.h \ flatpak-oci-registry-private.h \ + flatpak-progress-private.h \ flatpak-remote-private.h \ flatpak-remote-ref-private.h \ flatpak-run-private.h \ diff --git a/system-helper/flatpak-system-helper.c b/system-helper/flatpak-system-helper.c index 6c06e5a67..6d3ade264 100644 --- a/system-helper/flatpak-system-helper.c +++ b/system-helper/flatpak-system-helper.c @@ -38,6 +38,7 @@ #include "flatpak-dir-private.h" #include "flatpak-error.h" #include "flatpak-oci-registry-private.h" +#include "flatpak-progress-private.h" #include "flatpak-utils-base-private.h" #include "flatpak-utils-private.h" @@ -242,11 +243,6 @@ dir_get_system (const char *installation, return system; } -static void -no_progress_cb (OstreeAsyncProgress *progress, gpointer user_data) -{ -} - #define DBUS_NAME_DBUS "org.freedesktop.DBus" #define DBUS_INTERFACE_DBUS DBUS_NAME_DBUS #define DBUS_PATH_DBUS "/org/freedesktop/DBus" @@ -389,7 +385,6 @@ handle_deploy (FlatpakSystemHelper *object, g_autoptr(GFile) repo_file = g_file_new_for_path (arg_repo_path); g_autoptr(GError) error = NULL; g_autoptr(GFile) deploy_dir = NULL; - g_autoptr(OstreeAsyncProgressFinish) ostree_progress = NULL; gboolean is_oci; gboolean is_update; gboolean no_deploy; @@ -620,19 +615,11 @@ handle_deploy (FlatpakSystemHelper *object, } else if (strlen (arg_repo_path) > 0) { - g_autoptr(GMainContextPopDefault) main_context = NULL; - - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); - - ostree_progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); - if (!flatpak_dir_pull_untrusted_local (system, arg_repo_path, arg_origin, arg_ref, (const char **) arg_subpaths, - ostree_progress, - NULL, &error)) + NULL, NULL, &error)) { flatpak_invocation_return_error (invocation, error, "Error pulling from repo"); return TRUE; @@ -640,7 +627,6 @@ handle_deploy (FlatpakSystemHelper *object, } else if (local_pull) { - g_autoptr(GMainContextPopDefault) main_context = NULL; g_autoptr(FlatpakRemoteState) state = NULL; if (!ostree_repo_remote_get_url (flatpak_dir_get_repo (system), arg_origin, @@ -665,13 +651,8 @@ handle_deploy (FlatpakSystemHelper *object, return TRUE; } - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); - - ostree_progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); - if (!flatpak_dir_pull (system, state, arg_ref, NULL, (const char **) arg_subpaths, NULL, NULL, NULL, NULL, - FLATPAK_PULL_FLAGS_NONE, OSTREE_REPO_PULL_FLAGS_UNTRUSTED, ostree_progress, + FLATPAK_PULL_FLAGS_NONE, OSTREE_REPO_PULL_FLAGS_UNTRUSTED, NULL, NULL, &error)) { flatpak_invocation_return_error (invocation, error, "Error pulling from repo"); @@ -813,11 +794,11 @@ handle_deploy_appstream (FlatpakSystemHelper *object, if (is_oci) { - g_autoptr(GMainContextPopDefault) context = NULL; + g_autoptr(FlatpakMainContext) context = NULL; /* This does soup http requests spinning the current mainloop, so we need one for this thread. */ - context = flatpak_main_context_new_default (); + context = flatpak_progress_push_main_context (NULL); /* In the OCI case, we just do the full update, including network i/o, in the * system helper, see comment in flatpak_dir_update_appstream() */ @@ -840,26 +821,19 @@ handle_deploy_appstream (FlatpakSystemHelper *object, { g_autoptr(GError) first_error = NULL; g_autoptr(GError) second_error = NULL; - g_autoptr(GMainContextPopDefault) main_context = NULL; - g_autoptr(OstreeAsyncProgressFinish) ostree_progress = NULL; - - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); - - ostree_progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); if (!flatpak_dir_pull_untrusted_local (system, arg_repo_path, arg_origin, new_branch, NULL, - ostree_progress, + NULL, NULL, &first_error)) { if (!flatpak_dir_pull_untrusted_local (system, arg_repo_path, arg_origin, old_branch, NULL, - ostree_progress, + NULL, NULL, &second_error)) { g_prefix_error (&first_error, "Error updating appstream2: "); @@ -873,11 +847,9 @@ handle_deploy_appstream (FlatpakSystemHelper *object, else /* empty path == local pull */ { g_autoptr(FlatpakRemoteState) state = NULL; - g_autoptr(OstreeAsyncProgressFinish) ostree_progress = NULL; g_autoptr(GError) first_error = NULL; g_autoptr(GError) second_error = NULL; g_autofree char *url = NULL; - g_autoptr(GMainContextPopDefault) main_context = NULL; if (!ostree_repo_remote_get_url (flatpak_dir_get_repo (system), arg_origin, @@ -902,17 +874,12 @@ handle_deploy_appstream (FlatpakSystemHelper *object, return TRUE; } - /* Work around ostree-pull spinning the default main context for the sync calls */ - main_context = flatpak_main_context_new_default (); - - ostree_progress = ostree_async_progress_new_and_connect (no_progress_cb, NULL); - if (!flatpak_dir_pull (system, state, new_branch, NULL, NULL, NULL, NULL, NULL, NULL, - FLATPAK_PULL_FLAGS_NONE, OSTREE_REPO_PULL_FLAGS_UNTRUSTED, ostree_progress, + FLATPAK_PULL_FLAGS_NONE, OSTREE_REPO_PULL_FLAGS_UNTRUSTED, NULL, NULL, &first_error)) { if (!flatpak_dir_pull (system, state, old_branch, NULL, NULL, NULL, NULL, NULL, NULL, - FLATPAK_PULL_FLAGS_NONE, OSTREE_REPO_PULL_FLAGS_UNTRUSTED, ostree_progress, + FLATPAK_PULL_FLAGS_NONE, OSTREE_REPO_PULL_FLAGS_UNTRUSTED, NULL, NULL, &second_error)) { g_prefix_error (&first_error, "Error updating appstream2: ");