summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlexander Larsson <alexl@redhat.com>2020-10-14 15:54:41 +0200
committerAlexander Larsson <alexander.larsson@gmail.com>2020-10-29 15:30:35 +0100
commit096daf91f2b4db0b6fbd6ea17be0b8ace040b83a (patch)
tree646cf926fb6173e033b1490e66d3317cd4e4dd8a
parentb09458554543097adcd9d9abe34dbfcdd74b2df5 (diff)
downloadflatpak-096daf91f2b4db0b6fbd6ea17be0b8ace040b83a.tar.gz
summary: Implement a new, more efficient, summary format
This drops the deltas from the summary and uses the per-commit metadata field to add the cache data to avoid the need for the separate xa.cache and xa.sparse-cache indexes. This way we avoid repeating the refs in multiple places. Nothing uses this format yet, but we still pass make check if we enable it.
-rw-r--r--app/flatpak-builtins-repo.c239
-rw-r--r--common/flatpak-dir-private.h1
-rw-r--r--common/flatpak-dir.c122
-rw-r--r--common/flatpak-utils-private.h8
-rw-r--r--common/flatpak-utils.c145
5 files changed, 336 insertions, 179 deletions
diff --git a/app/flatpak-builtins-repo.c b/app/flatpak-builtins-repo.c
index 0360c9dd..6207b8f1 100644
--- a/app/flatpak-builtins-repo.c
+++ b/app/flatpak-builtins-repo.c
@@ -70,9 +70,8 @@ ostree_repo_mode_to_string (OstreeRepoMode mode,
static void
print_info (OstreeRepo *repo,
- GVariant *meta)
+ GVariant *summary)
{
- g_autoptr(GVariant) cache = NULL;
const char *title;
const char *comment;
const char *description;
@@ -87,11 +86,15 @@ print_info (OstreeRepo *repo,
g_autoptr(GVariant) gpg_keys = NULL;
OstreeRepoMode mode;
const char *mode_string = "unknown";
+ g_autoptr(GVariant) meta = NULL;
+ g_autoptr(GVariant) refs = NULL;
mode = ostree_repo_get_mode (repo);
ostree_repo_mode_to_string (mode, &mode_string, NULL);
g_print (_("Repo mode: %s\n"), mode_string);
+ meta = g_variant_get_child_value (summary, 1);
+
if (g_variant_lookup (meta, "xa.title", "&s", &title))
g_print (_("Title: %s\n"), title);
@@ -134,44 +137,50 @@ print_info (OstreeRepo *repo,
g_print (_("GPG key hash: %s\n"), gpg_data_checksum);
}
- cache = g_variant_lookup_value (meta, "xa.cache", NULL);
- if (cache)
- {
- g_autoptr(GVariant) refdata = NULL;
-
- refdata = g_variant_get_variant (cache);
- g_print (_("%zd branches\n"), g_variant_n_children (refdata));
- }
+ refs = g_variant_get_child_value (summary, 0);
+ g_print (_("%zd branches\n"), g_variant_n_children (refs));
}
static void
-print_branches (GVariant *meta)
+print_branches (GVariant *summary)
{
- g_autoptr(GVariant) cache = NULL;
- g_autoptr(GVariant) sparse_cache = NULL;
+ g_autoptr(GVariant) meta = NULL;
+ guint summary_version = 0;
+ FlatpakTablePrinter *printer;
+
+ meta = g_variant_get_child_value (summary, 1);
+
+ g_variant_lookup (meta, "xa.summary-version", "u", &summary_version);
- g_variant_lookup (meta, "xa.sparse-cache", "@a{sa{sv}}", &sparse_cache);
- cache = g_variant_lookup_value (meta, "xa.cache", NULL);
- if (cache)
+ printer = flatpak_table_printer_new ();
+ flatpak_table_printer_set_column_title (printer, 0, _("Ref"));
+ flatpak_table_printer_set_column_title (printer, 1, _("Installed"));
+ flatpak_table_printer_set_column_title (printer, 2, _("Download"));
+ flatpak_table_printer_set_column_title (printer, 3, _("Options"));
+
+ if (summary_version == 1)
{
- g_autoptr(GVariant) refdata = NULL;
+ g_autoptr(GVariant) refs = g_variant_get_child_value (summary, 0);
GVariantIter iter;
const char *ref;
- guint64 installed_size;
- guint64 download_size;
- const char *metadata;
- FlatpakTablePrinter *printer;
-
- printer = flatpak_table_printer_new ();
- flatpak_table_printer_set_column_title (printer, 0, _("Ref"));
- flatpak_table_printer_set_column_title (printer, 1, _("Installed"));
- flatpak_table_printer_set_column_title (printer, 2, _("Download"));
- flatpak_table_printer_set_column_title (printer, 3, _("Options"));
-
- refdata = g_variant_get_variant (cache);
- g_variant_iter_init (&iter, refdata);
- while (g_variant_iter_next (&iter, "{&s(tt&s)}", &ref, &installed_size, &download_size, &metadata))
+ GVariant *refdata_iter = NULL;
+
+ g_variant_iter_init (&iter, refs);
+ while (g_variant_iter_next (&iter, "(&s@(taya{sv}))", &ref, &refdata_iter))
{
+ g_autoptr(GVariant) refdata = refdata_iter;
+ g_autoptr(GVariant) ref_meta = g_variant_get_child_value (refdata, 2);
+ g_autoptr(GVariant) data = g_variant_lookup_value (ref_meta, "xa.data", NULL);
+ guint64 installed_size;
+ guint64 download_size;
+ const char *metadata;
+ const char *eol;
+
+ if (data == NULL)
+ continue;
+
+ g_variant_get (data, "(tt&s)", &installed_size, &download_size, &metadata);
+
g_autofree char *installed = g_format_size (GUINT64_FROM_BE (installed_size));
g_autofree char *download = g_format_size (GUINT64_FROM_BE (download_size));
@@ -181,49 +190,120 @@ print_branches (GVariant *meta)
flatpak_table_printer_add_column (printer, ""); /* Options */
- if (sparse_cache)
+ if (g_variant_lookup (ref_meta, FLATPAK_SPARSE_CACHE_KEY_ENDOFLINE, "&s", &eol))
+ flatpak_table_printer_append_with_comma_printf (printer, "eol=%s", eol);
+ if (g_variant_lookup (ref_meta, FLATPAK_SPARSE_CACHE_KEY_ENDOFLINE_REBASE, "&s", &eol))
+ flatpak_table_printer_append_with_comma_printf (printer, "eol-rebase=%s", eol);
+
+ flatpak_table_printer_finish_row (printer);
+ }
+ }
+ else
+ {
+ g_autoptr(GVariant) cache = NULL;
+ g_autoptr(GVariant) sparse_cache = NULL;
+
+ g_variant_lookup (meta, "xa.sparse-cache", "@a{sa{sv}}", &sparse_cache);
+ cache = g_variant_lookup_value (meta, "xa.cache", NULL);
+ if (cache)
+ {
+ g_autoptr(GVariant) refdata = NULL;
+ GVariantIter iter;
+ const char *ref;
+ guint64 installed_size;
+ guint64 download_size;
+ const char *metadata;
+
+ refdata = g_variant_get_variant (cache);
+ g_variant_iter_init (&iter, refdata);
+ while (g_variant_iter_next (&iter, "{&s(tt&s)}", &ref, &installed_size, &download_size, &metadata))
{
- g_autoptr(GVariant) sparse = NULL;
- if (g_variant_lookup (sparse_cache, ref, "@a{sv}", &sparse))
+ g_autofree char *installed = g_format_size (GUINT64_FROM_BE (installed_size));
+ g_autofree char *download = g_format_size (GUINT64_FROM_BE (download_size));
+
+ flatpak_table_printer_add_column (printer, ref);
+ flatpak_table_printer_add_decimal_column (printer, installed);
+ flatpak_table_printer_add_decimal_column (printer, download);
+
+ flatpak_table_printer_add_column (printer, ""); /* Options */
+
+ if (sparse_cache)
{
- const char *eol;
- if (g_variant_lookup (sparse, FLATPAK_SPARSE_CACHE_KEY_ENDOFLINE, "&s", &eol))
- flatpak_table_printer_append_with_comma_printf (printer, "eol=%s", eol);
- if (g_variant_lookup (sparse, FLATPAK_SPARSE_CACHE_KEY_ENDOFLINE_REBASE, "&s", &eol))
- flatpak_table_printer_append_with_comma_printf (printer, "eol-rebase=%s", eol);
+ g_autoptr(GVariant) sparse = NULL;
+ if (g_variant_lookup (sparse_cache, ref, "@a{sv}", &sparse))
+ {
+ const char *eol;
+ if (g_variant_lookup (sparse, FLATPAK_SPARSE_CACHE_KEY_ENDOFLINE, "&s", &eol))
+ flatpak_table_printer_append_with_comma_printf (printer, "eol=%s", eol);
+ if (g_variant_lookup (sparse, FLATPAK_SPARSE_CACHE_KEY_ENDOFLINE_REBASE, "&s", &eol))
+ flatpak_table_printer_append_with_comma_printf (printer, "eol-rebase=%s", eol);
+ }
}
+
+ flatpak_table_printer_finish_row (printer);
}
- flatpak_table_printer_finish_row (printer);
}
-
- flatpak_table_printer_print (printer);
- flatpak_table_printer_free (printer);
}
+
+ flatpak_table_printer_print (printer);
+ flatpak_table_printer_free (printer);
}
static void
-print_metadata (GVariant *meta,
+print_metadata (GVariant *summary,
const char *branch)
{
- g_autoptr(GVariant) cache = NULL;
+ g_autoptr(GVariant) meta = NULL;
+ guint summary_version = 0;
+ guint64 installed_size;
+ guint64 download_size;
+ const char *metadata;
+ GVariantIter iter;
+ const char *ref;
+
+ meta = g_variant_get_child_value (summary, 1);
- cache = g_variant_lookup_value (meta, "xa.cache", NULL);
- if (cache)
+ g_variant_lookup (meta, "xa.summary-version", "u", &summary_version);
+
+ if (summary_version == 1)
{
- g_autoptr(GVariant) refdata = NULL;
- GVariantIter iter;
- const char *ref;
- guint64 installed_size;
- guint64 download_size;
- const char *metadata;
+ g_autoptr(GVariant) refs = g_variant_get_child_value (summary, 0);
+ GVariant *refdata_iter = NULL;
- refdata = g_variant_get_variant (cache);
- g_variant_iter_init (&iter, refdata);
- while (g_variant_iter_next (&iter, "{&s(tt&s)}", &ref, &installed_size, &download_size, &metadata))
+ g_variant_iter_init (&iter, refs);
+ while (g_variant_iter_next (&iter, "(&s@(taya{sv}))", &ref, &refdata_iter))
{
+ g_autoptr(GVariant) refdata = refdata_iter;
+ g_autoptr(GVariant) ref_meta = g_variant_get_child_value (refdata, 2);
+
if (strcmp (branch, ref) == 0)
- g_print ("%s\n", metadata);
+ {
+ g_autoptr(GVariant) data = g_variant_lookup_value (ref_meta, "xa.data", NULL);
+ if (data)
+ {
+ g_variant_get (data, "(tt&s)", &installed_size, &download_size, &metadata);
+ g_print ("%s\n", metadata);
+ break;
+ }
+ }
+ }
+ }
+ else /* Version 0 */
+ {
+ g_autoptr(GVariant) cache = g_variant_lookup_value (meta, "xa.cache", NULL);
+ if (cache)
+ {
+ g_autoptr(GVariant) refdata = g_variant_get_variant (cache);
+ g_variant_iter_init (&iter, refdata);
+ while (g_variant_iter_next (&iter, "{&s(tt&s)}", &ref, &installed_size, &download_size, &metadata))
+ {
+ if (strcmp (branch, ref) == 0)
+ {
+ g_print ("%s\n", metadata);
+ break;
+ }
+ }
}
}
}
@@ -419,10 +499,8 @@ flatpak_builtin_repo (int argc, char **argv,
{
g_autoptr(GOptionContext) context = NULL;
g_autoptr(GFile) location = NULL;
- g_autoptr(GVariant) meta = NULL;
g_autoptr(OstreeRepo) repo = NULL;
- const char *ostree_metadata_ref = NULL;
- g_autofree char *ostree_metadata_checksum = NULL;
+ g_autoptr(GVariant) summary = NULL;
const char *collection_id;
context = g_option_context_new (_("LOCATION - Repository maintenance"));
@@ -441,38 +519,11 @@ flatpak_builtin_repo (int argc, char **argv,
collection_id = ostree_repo_get_collection_id (repo);
- /* Try loading the metadata from the ostree-metadata branch first. If that
- * fails, fall back to the summary file. */
- ostree_metadata_ref = OSTREE_REPO_METADATA_REF;
- if (!flatpak_repo_resolve_rev (repo, collection_id, NULL, ostree_metadata_ref,
- TRUE, &ostree_metadata_checksum, cancellable, error))
- return FALSE;
-
- if (ostree_metadata_checksum != NULL)
- {
- g_autoptr(GVariant) commit_v = NULL;
-
- if (!ostree_repo_load_commit (repo, ostree_metadata_checksum, &commit_v, NULL, error))
- {
- g_prefix_error (error, "Error getting repository metadata from %s ref: ", ostree_metadata_ref);
- return FALSE;
- }
-
- meta = g_variant_get_child_value (commit_v, 0);
- g_debug ("Using repository metadata from the ostree-metadata branch");
- }
- else
+ summary = flatpak_repo_load_summary (repo, error);
+ if (summary == NULL)
{
- g_autoptr(GVariant) summary = NULL;
-
- summary = flatpak_repo_load_summary (repo, error);
- if (summary == NULL)
- {
- g_prefix_error (error, "Error getting repository metadata from summary file: ");
- return FALSE;
- }
- meta = g_variant_get_child_value (summary, 1);
- g_debug ("Using repository metadata from the summary file");
+ g_prefix_error (error, "Error getting repository metadata from summary file: ");
+ return FALSE;
}
if (!opt_info && !opt_branches && !opt_metadata_branch && !opt_commits_branch)
@@ -480,13 +531,13 @@ flatpak_builtin_repo (int argc, char **argv,
/* Print out the metadata. */
if (opt_info)
- print_info (repo, meta);
+ print_info (repo, summary);
if (opt_branches)
- print_branches (meta);
+ print_branches (summary);
if (opt_metadata_branch)
- print_metadata (meta, opt_metadata_branch);
+ print_metadata (summary, opt_metadata_branch);
if (opt_commits_branch)
{
diff --git a/common/flatpak-dir-private.h b/common/flatpak-dir-private.h
index a4cdf14d..2e84db35 100644
--- a/common/flatpak-dir-private.h
+++ b/common/flatpak-dir-private.h
@@ -119,6 +119,7 @@ typedef struct
{
char *remote_name;
char *collection_id;
+ guint summary_version;
GVariant *summary;
GBytes *summary_bytes;
GBytes *summary_sig_bytes;
diff --git a/common/flatpak-dir.c b/common/flatpak-dir.c
index 1e7aff4f..9135e340 100644
--- a/common/flatpak-dir.c
+++ b/common/flatpak-dir.c
@@ -604,53 +604,74 @@ flatpak_remote_state_get_cache_version (FlatpakRemoteState *self)
return GUINT32_FROM_LE (var_metadata_lookup_uint32 (meta, "xa.cache-version", 0));
}
-static gboolean
-flatpak_remote_state_get_cache (FlatpakRemoteState *self,
- VarCacheRef *out,
- GError **error)
+gboolean
+flatpak_remote_state_lookup_cache (FlatpakRemoteState *self,
+ const char *ref,
+ guint64 *out_download_size,
+ guint64 *out_installed_size,
+ const char **out_metadata,
+ GError **error)
{
+ VarCacheDataRef cache_data;
VarMetadataRef meta;
- VarVariantRef cache_vv;
- VarVariantRef cache_v;
VarSummaryRef summary;
+ guint32 summary_version;
if (!flatpak_remote_state_ensure_summary (self, error))
return FALSE;
summary = var_summary_from_gvariant (self->summary);
meta = var_summary_get_metadata (summary);
- if (!var_metadata_lookup (meta, "xa.cache", NULL, &cache_vv))
+
+ summary_version = GUINT32_FROM_LE (var_metadata_lookup_uint32 (meta, "xa.summary-version", 0));
+
+ if (summary_version == 0)
{
- flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("No summary or Flatpak cache available for remote %s"),
- self->remote_name);
- return FALSE;
- }
+ VarCacheRef cache;
+ gsize pos;
+ VarVariantRef cache_vv;
+ VarVariantRef cache_v;
- /* For stupid historical reasons the xa.cache is double-wrapped in a variant */
- cache_v = var_variant_from_variant (cache_vv);
- *out = var_cache_from_variant (cache_v);
- return TRUE;
-}
+ if (!var_metadata_lookup (meta, "xa.cache", NULL, &cache_vv))
+ {
+ flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("No summary or Flatpak cache available for remote %s"),
+ self->remote_name);
+ return FALSE;
+ }
-gboolean
-flatpak_remote_state_lookup_cache (FlatpakRemoteState *self,
- const char *ref,
- guint64 *out_download_size,
- guint64 *out_installed_size,
- const char **out_metadata,
- GError **error)
-{
- VarCacheRef cache;
- VarCacheDataRef cache_data;
- gsize pos;
+ /* For stupid historical reasons the xa.cache is double-wrapped in a variant */
+ cache_v = var_variant_from_variant (cache_vv);
+ cache = var_cache_from_variant (cache_v);
- if (!flatpak_remote_state_get_cache (self, &cache, error))
- return FALSE;
+ if (!var_cache_lookup (cache, ref, &pos, &cache_data))
+ return flatpak_fail_error (error, FLATPAK_ERROR_REF_NOT_FOUND,
+ _("No entry for %s in remote '%s' summary flatpak cache "),
+ ref, self->remote_name);
+ }
+ else if (summary_version == 1)
+ {
+ VarRefMapRef ref_map = var_summary_get_ref_map (summary);
+ VarRefInfoRef info;
+ VarMetadataRef commit_metadata;
+ VarVariantRef cache_data_v;
- if (!var_cache_lookup (cache, ref, &pos, &cache_data))
- return flatpak_fail_error (error, FLATPAK_ERROR_REF_NOT_FOUND,
- _("No entry for %s in remote '%s' summary flatpak cache "),
- ref, self->remote_name);
+ if (!flatpak_var_ref_map_lookup_ref (ref_map, ref, &info))
+ return flatpak_fail_error (error, FLATPAK_ERROR_REF_NOT_FOUND,
+ _("No entry for %s in remote '%s' summary cache "),
+ ref, self->remote_name);
+
+ commit_metadata = var_ref_info_get_metadata (info);
+ if (!var_metadata_lookup (commit_metadata, "xa.data", NULL, &cache_data_v))
+ return flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("Missing xa.data in summary for remote %s"),
+ self->remote_name);
+ cache_data = var_cache_data_from_variant (cache_data_v);
+ }
+ else
+ {
+ flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("Unsupported summary version %d for remote %s"),
+ summary_version, self->remote_name);
+ return FALSE;
+ }
if (out_installed_size)
*out_installed_size = var_cache_data_get_installed_size (cache_data);
@@ -1025,22 +1046,45 @@ flatpak_remote_state_lookup_sparse_cache (FlatpakRemoteState *self,
VarSummaryRef summary;
VarMetadataRef meta;
VarVariantRef sparse_cache_v;
+ guint32 summary_version;
if (!flatpak_remote_state_ensure_summary (self, error))
return FALSE;
summary = var_summary_from_gvariant (self->summary);
meta = var_summary_get_metadata (summary);
- if (var_metadata_lookup (meta, "xa.sparse-cache", NULL, &sparse_cache_v))
+
+ summary_version = GUINT32_FROM_LE (var_metadata_lookup_uint32 (meta, "xa.summary-version", 0));
+
+ if (summary_version == 0)
{
- VarSparseCacheRef sparse_cache = var_sparse_cache_from_variant (sparse_cache_v);
- return var_sparse_cache_lookup (sparse_cache, ref, NULL, out_metadata);
+ if (var_metadata_lookup (meta, "xa.sparse-cache", NULL, &sparse_cache_v))
+ {
+ VarSparseCacheRef sparse_cache = var_sparse_cache_from_variant (sparse_cache_v);
+ if (var_sparse_cache_lookup (sparse_cache, ref, NULL, out_metadata))
+ return TRUE;
+ }
}
+ else if (summary_version == 1)
+ {
+ VarRefMapRef ref_map = var_summary_get_ref_map (summary);
+ VarRefInfoRef info;
- g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
- _("No entry for %s in remote summary flatpak sparse cache "), ref);
+ if (flatpak_var_ref_map_lookup_ref (ref_map, ref, &info))
+ {
+ *out_metadata = var_ref_info_get_metadata (info);
+ return TRUE;
+ }
+ }
+ else
+ {
+ flatpak_fail_error (error, FLATPAK_ERROR_INVALID_DATA, _("Unsupported summary version %d for remote %s"),
+ summary_version, self->remote_name);
+ return FALSE;
+ }
- return FALSE;
+ return flatpak_fail_error (error, FLATPAK_ERROR_REF_NOT_FOUND,
+ _("No entry for %s in remote summary flatpak sparse cache "), ref);
}
static DirExtraData *
diff --git a/common/flatpak-utils-private.h b/common/flatpak-utils-private.h
index 7f55a0fa..c280419d 100644
--- a/common/flatpak-utils-private.h
+++ b/common/flatpak-utils-private.h
@@ -57,6 +57,11 @@
#define FLATPAK_XA_CACHE_VERSION 1
/* version 1 added extra data download size */
+#define FLATPAK_XA_SUMMARY_VERSION 1
+/* version 0/missing is standard ostree summary,
+ * version 1 is compact format with inline cache and no deltas
+ */
+
gboolean flatpak_set_tty_echo (gboolean echo);
void flatpak_get_window_size (int *rows,
int *cols);
@@ -170,6 +175,9 @@ gboolean flatpak_summary_lookup_ref (GVariant *summary,
gboolean flatpak_summary_find_ref_map (VarSummaryRef summary,
const char *collection_id,
VarRefMapRef *refs_out);
+gboolean flatpak_var_ref_map_lookup_ref (VarRefMapRef ref_map,
+ const char *ref,
+ VarRefInfoRef *out_info);
gboolean flatpak_name_matches_one_wildcard_prefix (const char *string,
const char * const *maybe_wildcard_prefixes,
gboolean require_exact_match);
diff --git a/common/flatpak-utils.c b/common/flatpak-utils.c
index 0bc74133..aa37d79b 100644
--- a/common/flatpak-utils.c
+++ b/common/flatpak-utils.c
@@ -2605,7 +2605,7 @@ flatpak_variant_save (GFile *dest,
/* This special cases the ref lookup which by doing a
bsearch since the array is sorted */
-static gboolean
+gboolean
flatpak_var_ref_map_lookup_ref (VarRefMapRef ref_map,
const char *ref,
VarRefInfoRef *out_info)
@@ -3469,6 +3469,7 @@ populate_commit_data_cache (GVariant *metadata,
g_autoptr(GVariant) sparse_cache = NULL;
gsize n, i;
guint32 cache_version = 0;
+ guint32 summary_version = 0;
const char *old_collection_id;
if (!g_variant_lookup (metadata, "ostree.summary.collection-id", "&s", &old_collection_id))
@@ -3486,6 +3487,11 @@ populate_commit_data_cache (GVariant *metadata,
if (cache_version < FLATPAK_XA_CACHE_VERSION)
return; /* We need to rebuild the cache with the current version */
+ if (g_variant_lookup (metadata, "xa.summary-version", "u", &summary_version))
+ summary_version = GUINT32_FROM_LE (summary_version);
+ else
+ summary_version = 0;
+
cache = g_variant_get_child_value (cache_v, 0);
sparse_cache = g_variant_lookup_value (metadata, "xa.sparse-cache", NULL);
@@ -3778,11 +3784,33 @@ flatpak_get_arch_for_ref (const char *ref)
return NULL;
}
+static void
+variant_dict_merge (GVariantDict *dict,
+ GVariant *to_merge)
+{
+ GVariantIter iter;
+ gchar *key;
+ GVariant *value;
+
+ if (to_merge)
+ {
+ g_variant_iter_init (&iter, to_merge);
+ while (g_variant_iter_next (&iter, "{sv}", &key, &value))
+ {
+ g_variant_dict_insert_value (dict, key, value);
+ g_variant_unref (value);
+ g_free (key);
+ }
+ }
+}
+
static GVariant *
generate_summary (OstreeRepo *repo,
+ gboolean compat_format,
GHashTable *refs,
GHashTable *commit_data_cache,
GPtrArray *delta_names,
+ const char **summary_arches,
const char **gpg_key_ids,
const char *gpg_homedir,
GCancellable *cancellable,
@@ -3805,7 +3833,6 @@ generate_summary (OstreeRepo *repo,
g_autofree char *authenticator_name = NULL;
g_autofree char *gpg_keys = NULL;
g_auto(GStrv) config_keys = NULL;
- g_auto(GStrv) summary_arches = NULL;
g_autoptr(GHashTable) summary_arches_ht = NULL;
int authenticator_install = -1;
g_autoptr(GHashTable) commits = NULL;
@@ -3837,7 +3864,6 @@ generate_summary (OstreeRepo *repo,
if (g_key_file_has_key (config, "flatpak", "authenticator-install", NULL))
authenticator_install = g_key_file_get_boolean (config, "flatpak", "authenticator-install", NULL);
- summary_arches = g_key_file_get_string_list (config, "flatpak", "summary-arches", NULL, NULL);
config_keys = g_key_file_get_keys (config, "flatpak", NULL, NULL);
}
@@ -3976,6 +4002,7 @@ generate_summary (OstreeRepo *repo,
{
const char *ref = l->data;
const char *rev = g_hash_table_lookup (refs, ref);
+ const CommitData *rev_data = NULL;
g_auto(GVariantDict) commit_metadata_builder = FLATPAK_VARIANT_BUILDER_INITIALIZER;
g_autoptr(GVariant) commit_obj = NULL;
@@ -3985,18 +4012,10 @@ generate_summary (OstreeRepo *repo,
if (!ostree_repo_load_variant (repo, OSTREE_OBJECT_TYPE_COMMIT, rev, &commit_obj, error))
return NULL;
- g_variant_dict_init (&commit_metadata_builder, NULL);
- g_variant_builder_add_value (refs_builder,
- g_variant_new ("(s(t@ay@a{sv}))", ref,
- (guint64) g_variant_get_size (commit_obj),
- ostree_checksum_to_bytes_v (rev),
- g_variant_dict_end (&commit_metadata_builder)));
-
/* Only add CommitData for flatpak refs */
if (is_flatpak_ref (ref))
{
- const CommitData *rev_data = g_hash_table_lookup (commit_data_cache, rev);
-
+ rev_data = g_hash_table_lookup (commit_data_cache, rev);
if (rev_data == NULL)
{
rev_data = read_commit_data (repo, ref, rev, cancellable, error);
@@ -4005,7 +4024,25 @@ generate_summary (OstreeRepo *repo,
g_hash_table_insert (commit_data_cache, g_strdup (rev), (CommitData *)rev_data);
}
+ }
+ g_variant_dict_init (&commit_metadata_builder, NULL);
+ if (!compat_format && rev_data)
+ {
+ g_variant_dict_insert (&commit_metadata_builder, "xa.data", "(tts)",
+ GUINT64_TO_BE (rev_data->installed_size),
+ GUINT64_TO_BE (rev_data->download_size),
+ rev_data->metadata_contents);
+ variant_dict_merge (&commit_metadata_builder, rev_data->sparse_data);
+ }
+ g_variant_builder_add_value (refs_builder,
+ g_variant_new ("(s(t@ay@a{sv}))", ref,
+ (guint64) g_variant_get_size (commit_obj),
+ ostree_checksum_to_bytes_v (rev),
+ g_variant_dict_end (&commit_metadata_builder)));
+
+ if (compat_format && rev_data)
+ {
g_variant_builder_add (ref_data_builder, "{s(tts)}",
ref,
GUINT64_TO_BE (rev_data->installed_size),
@@ -4017,48 +4054,57 @@ generate_summary (OstreeRepo *repo,
}
}
- {
- g_auto(GVariantDict) deltas_builder = FLATPAK_VARIANT_BUILDER_INITIALIZER;
+ if (delta_names)
+ {
+ g_auto(GVariantDict) deltas_builder = FLATPAK_VARIANT_BUILDER_INITIALIZER;
- g_variant_dict_init (&deltas_builder, NULL);
- for (guint i = 0; i < delta_names->len; i++)
- {
- g_autofree char *from = NULL;
- g_autofree char *to = NULL;
- GVariant *digest;
+ g_variant_dict_init (&deltas_builder, NULL);
+ for (guint i = 0; i < delta_names->len; i++)
+ {
+ g_autofree char *from = NULL;
+ g_autofree char *to = NULL;
+ GVariant *digest;
- _ostree_parse_delta_name (delta_names->pdata[i], &from, &to);
+ _ostree_parse_delta_name (delta_names->pdata[i], &from, &to);
- /* Only keep deltas going to a ref that is in the summary
- * (i.e. not arch filtered or random) */
- if (!g_hash_table_contains (commits, to))
- continue;
+ /* Only keep deltas going to a ref that is in the summary
+ * (i.e. not arch filtered or random) */
+ if (!g_hash_table_contains (commits, to))
+ continue;
- digest = _ostree_repo_static_delta_superblock_digest (repo,
- (from && from[0]) ? from : NULL,
- to, cancellable, error);
- if (digest == NULL)
- return FALSE;
+ digest = _ostree_repo_static_delta_superblock_digest (repo,
+ (from && from[0]) ? from : NULL,
+ to, cancellable, error);
+ if (digest == NULL)
+ return FALSE;
- g_variant_dict_insert_value (&deltas_builder, delta_names->pdata[i], digest);
- }
+ g_variant_dict_insert_value (&deltas_builder, delta_names->pdata[i], digest);
+ }
- if (delta_names->len > 0)
- g_variant_builder_add (metadata_builder, "{sv}", "ostree.static-deltas", g_variant_dict_end (&deltas_builder));
- }
+ if (delta_names->len > 0)
+ g_variant_builder_add (metadata_builder, "{sv}", "ostree.static-deltas", g_variant_dict_end (&deltas_builder));
+ }
- /* Note: xa.cache doesn’t need to support collection IDs for the refs listed
- * in it, because the xa.cache metadata is stored on the ostree-metadata ref,
- * which is itself strongly bound to a collection ID — so that collection ID
- * is bound to all the refs in xa.cache. If a client is using the xa.cache
- * data from a summary file (rather than an ostree-metadata branch), they are
- * too old to care about collection IDs anyway. */
- g_variant_builder_add (metadata_builder, "{sv}", "xa.cache",
- g_variant_new_variant (g_variant_builder_end (ref_data_builder)));
+ if (compat_format)
+ {
+ /* Note: xa.cache doesn’t need to support collection IDs for the refs listed
+ * in it, because the xa.cache metadata is stored on the ostree-metadata ref,
+ * which is itself strongly bound to a collection ID — so that collection ID
+ * is bound to all the refs in xa.cache. If a client is using the xa.cache
+ * data from a summary file (rather than an ostree-metadata branch), they are
+ * too old to care about collection IDs anyway. */
+ g_variant_builder_add (metadata_builder, "{sv}", "xa.cache",
+ g_variant_new_variant (g_variant_builder_end (ref_data_builder)));
+ g_variant_builder_add (metadata_builder, "{sv}", "xa.sparse-cache",
+ g_variant_builder_end (ref_sparse_data_builder));
+ }
+ else
+ {
+ g_variant_builder_add (metadata_builder, "{sv}", "xa.summary-version",
+ g_variant_new_uint32 (GUINT32_TO_LE (FLATPAK_XA_SUMMARY_VERSION)));
+ }
g_variant_builder_add (metadata_builder, "{sv}", "xa.cache-version",
g_variant_new_uint32 (GUINT32_TO_LE (FLATPAK_XA_CACHE_VERSION)));
- g_variant_builder_add (metadata_builder, "{sv}", "xa.sparse-cache",
- g_variant_builder_end (ref_sparse_data_builder));
g_variant_builder_add_value (summary_builder, g_variant_builder_end (refs_builder));
g_variant_builder_add_value (summary_builder, g_variant_builder_end (metadata_builder));
@@ -4091,9 +4137,13 @@ flatpak_repo_update (OstreeRepo *repo,
g_autoptr(GVariant) old_summary = NULL;
g_autoptr(GVariant) new_summary = NULL;
g_autoptr(GPtrArray) delta_names = NULL;
+ g_auto(GStrv) summary_arches = NULL;
g_autoptr(GHashTable) refs = NULL;
+ GKeyFile *config;
int repo_dfd;
+ config = ostree_repo_get_config (repo);
+
if (!ostree_repo_list_refs_ext (repo, NULL, &refs,
OSTREE_REPO_LIST_REFS_EXT_EXCLUDE_REMOTES | OSTREE_REPO_LIST_REFS_EXT_EXCLUDE_MIRRORS,
cancellable, error))
@@ -4112,7 +4162,10 @@ flatpak_repo_update (OstreeRepo *repo,
if (!ostree_repo_list_static_delta_names (repo, &delta_names, cancellable, error))
return FALSE;
- new_summary = generate_summary (repo, refs, commit_data_cache, delta_names,
+ if (config)
+ summary_arches = g_key_file_get_string_list (config, "flatpak", "summary-arches", NULL, NULL);
+
+ new_summary = generate_summary (repo, TRUE, refs, commit_data_cache, delta_names, (const char **)summary_arches,
gpg_key_ids, gpg_homedir, cancellable, error);
if (new_summary == NULL)
return FALSE;