summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorOpenShift Merge Robot <openshift-merge-robot@users.noreply.github.com>2020-09-11 11:07:00 -0400
committerGitHub <noreply@github.com>2020-09-11 11:07:00 -0400
commit71acef2d33ec406dd7937742adb4d32fdd46100b (patch)
tree09311ac0c02104a50c540fc96513c1ac6cbe915b
parent69282a3dd3ef6a05339b31d46c095adfab92c4c1 (diff)
parentb7d1a9746b51fdb4cf14aa173e46e7d165cfe6e4 (diff)
downloadostree-71acef2d33ec406dd7937742adb4d32fdd46100b.tar.gz
Merge pull request #2193 from alexlarsson/preparatory-cleanup
Preparatory cleanup for summary work
-rw-r--r--src/libostree/libostree-devel.sym2
-rw-r--r--src/libostree/libostree-released.sym5
-rw-r--r--src/libostree/ostree-core.c2
-rw-r--r--src/libostree/ostree-repo-pull.c584
-rw-r--r--src/libostree/ostree-repo-static-delta-core.c24
-rw-r--r--src/libostree/ostree-repo-static-delta-private.h6
-rw-r--r--src/libostree/ostree-repo.c21
-rw-r--r--src/libotutil/ot-checksum-utils.c10
-rw-r--r--src/libotutil/ot-checksum-utils.h3
-rw-r--r--src/libotutil/otutil.h25
-rwxr-xr-xtests/test-symbols.sh2
11 files changed, 374 insertions, 310 deletions
diff --git a/src/libostree/libostree-devel.sym b/src/libostree/libostree-devel.sym
index 21669c4a..7f1f7e3e 100644
--- a/src/libostree/libostree-devel.sym
+++ b/src/libostree/libostree-devel.sym
@@ -17,7 +17,7 @@
Boston, MA 02111-1307, USA.
***/
-LIBOSTREE_2020.5 {
+LIBOSTREE_2020.6 {
global:
/* Add symbols here, and uncomment the bits in
* Makefile-libostree.am to enable this too.
diff --git a/src/libostree/libostree-released.sym b/src/libostree/libostree-released.sym
index 5c63f78f..aee434cb 100644
--- a/src/libostree/libostree-released.sym
+++ b/src/libostree/libostree-released.sym
@@ -593,6 +593,9 @@ global:
ostree_sysroot_set_mount_namespace_in_use;
} LIBOSTREE_2019.6;
+/* No new symbols in 2020.2 */
+/* No new symbols in 2020.3 */
+
/* Add new symbols here. Release commits should copy this section into -released.sym. */
LIBOSTREE_2020.4 {
global:
@@ -615,7 +618,7 @@ global:
ostree_sign_summary;
} LIBOSTREE_2020.1;
-/* No new symbols in 2020.2 */
+/* No new symbols in 2020.5 */
/* NOTE: Only add more content here in release commits! See the
* comments at the top of this file.
diff --git a/src/libostree/ostree-core.c b/src/libostree/ostree-core.c
index 523f57c0..29528fa5 100644
--- a/src/libostree/ostree-core.c
+++ b/src/libostree/ostree-core.c
@@ -2675,7 +2675,7 @@ _ostree_detached_metadata_append_gpg_sig (GVariant *existing_metadata,
_OSTREE_METADATA_GPGSIGS_NAME,
g_variant_builder_end (signature_builder));
- return g_variant_dict_end (&metadata_dict);
+ return g_variant_ref_sink (g_variant_dict_end (&metadata_dict));
}
#endif /* OSTREE_DISABLE_GPGME */
diff --git a/src/libostree/ostree-repo-pull.c b/src/libostree/ostree-repo-pull.c
index d817575b..2a791e59 100644
--- a/src/libostree/ostree-repo-pull.c
+++ b/src/libostree/ostree-repo-pull.c
@@ -2513,10 +2513,7 @@ on_superblock_fetched (GObject *src,
const guchar *expected_summary_digest = g_hash_table_lookup (pull_data->summary_deltas_checksums, delta);
guint8 actual_summary_digest[OSTREE_SHA256_DIGEST_LEN];
- g_auto(OtChecksum) hasher = { 0, };
- ot_checksum_init (&hasher);
- ot_checksum_update_bytes (&hasher, delta_superblock_data);
- ot_checksum_get_digest (&hasher, actual_summary_digest, sizeof (actual_summary_digest));
+ ot_checksum_bytes (delta_superblock_data, actual_summary_digest);
#ifndef OSTREE_DISABLE_GPGME
/* At this point we've GPG verified the data, so in theory
@@ -2626,88 +2623,198 @@ validate_variant_is_csum (GVariant *csum,
return ostree_validate_structureof_csum_v (csum, error);
}
+static gboolean
+_ostree_repo_verify_summary (OstreeRepo *self,
+ const char *name,
+ gboolean gpg_verify_summary,
+ GPtrArray *signapi_summary_verifiers,
+ GBytes *summary,
+ GBytes *signatures,
+ GCancellable *cancellable,
+ GError **error)
+{
+ if (gpg_verify_summary)
+ {
+ if (summary == NULL)
+ {
+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
+ "GPG verification enabled, but no summary found (check that the configured URL in remote config is correct)");
+ return FALSE;
+ }
+
+ if (signatures == NULL)
+ {
+ g_set_error (error, OSTREE_GPG_ERROR, OSTREE_GPG_ERROR_NO_SIGNATURE,
+ "GPG verification enabled, but no summary signatures found (use gpg-verify-summary=false in remote config to disable)");
+ return FALSE;
+ }
+
+ /* Verify any summary signatures. */
+ if (summary != NULL && signatures != NULL)
+ {
+ g_autoptr(OstreeGpgVerifyResult) result = NULL;
+
+ result = ostree_repo_verify_summary (self,
+ name,
+ summary,
+ signatures,
+ cancellable,
+ error);
+ if (!ostree_gpg_verify_result_require_valid_signature (result, error))
+ return FALSE;
+ }
+ }
+
+ if (signapi_summary_verifiers)
+ {
+ if (summary == NULL)
+ {
+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
+ "Signature verification enabled, but no summary found (check that the configured URL in remote config is correct)");
+ return FALSE;
+ }
+
+ if (signatures == NULL)
+ {
+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
+ "Signature verification enabled, but no summary signatures found (use sign-verify-summary=false in remote config to disable)");
+ return FALSE;
+ }
+
+ /* Verify any summary signatures. */
+ if (summary != NULL && signatures != NULL)
+ {
+ g_autoptr(GVariant) sig_variant = NULL;
+
+ sig_variant = g_variant_new_from_bytes (OSTREE_SUMMARY_SIG_GVARIANT_FORMAT,
+ signatures, FALSE);
+
+ if (!_sign_verify_for_remote (signapi_summary_verifiers, summary, sig_variant, NULL, error))
+ return FALSE;
+ }
+ }
+
+ return TRUE;
+}
+
+static gboolean
+_ostree_repo_load_cache_summary_file (OstreeRepo *self,
+ const char *filename,
+ const char *extension,
+ GBytes **out_data,
+ GCancellable *cancellable,
+ GError **error)
+{
+ const char *file = glnx_strjoina (_OSTREE_SUMMARY_CACHE_DIR, "/", filename, extension);
+ glnx_autofd int fd = -1;
+ g_autoptr(GBytes) data = NULL;
+
+ *out_data = NULL;
+
+ if (self->cache_dir_fd == -1)
+ return TRUE;
+
+ fd = openat (self->cache_dir_fd, file, O_CLOEXEC | O_RDONLY);
+ if (fd < 0)
+ {
+ if (errno == ENOENT)
+ return TRUE;
+ return glnx_throw_errno_prefix (error, "openat(%s)", file);
+ }
+
+ data = ot_fd_readall_or_mmap (fd, 0, error);
+ if (!data)
+ return FALSE;
+
+ *out_data =g_steal_pointer (&data);
+ return TRUE;
+}
+
/* Load the summary from the cache if the provided .sig file is the same as the
cached version. */
static gboolean
_ostree_repo_load_cache_summary_if_same_sig (OstreeRepo *self,
const char *remote,
GBytes *summary_sig,
- GBytes **summary,
+ GBytes **out_summary,
GCancellable *cancellable,
GError **error)
{
- if (self->cache_dir_fd == -1)
- return TRUE;
+ g_autoptr(GBytes) old_sig_contents = NULL;
- const char *summary_cache_sig_file = glnx_strjoina (_OSTREE_SUMMARY_CACHE_DIR, "/", remote, ".sig");
- glnx_autofd int prev_fd = -1;
- if (!ot_openat_ignore_enoent (self->cache_dir_fd, summary_cache_sig_file, &prev_fd, error))
- return FALSE;
- if (prev_fd < 0)
- return TRUE; /* Note early return */
+ *out_summary = NULL;
- g_autoptr(GBytes) old_sig_contents = ot_fd_readall_or_mmap (prev_fd, 0, error);
- if (!old_sig_contents)
+ if (!_ostree_repo_load_cache_summary_file (self, remote, ".sig",
+ &old_sig_contents,
+ cancellable, error))
return FALSE;
- if (g_bytes_compare (old_sig_contents, summary_sig) == 0)
+ if (old_sig_contents != NULL &&
+ g_bytes_compare (old_sig_contents, summary_sig) == 0)
{
- const char *summary_cache_file = glnx_strjoina (_OSTREE_SUMMARY_CACHE_DIR, "/", remote);
- glnx_autofd int summary_fd = -1;
- GBytes *summary_data;
+ g_autoptr(GBytes) summary_data = NULL;
+ if (!_ostree_repo_load_cache_summary_file (self, remote, NULL,
+ &summary_data,
+ cancellable, error))
+ return FALSE;
- summary_fd = openat (self->cache_dir_fd, summary_cache_file, O_CLOEXEC | O_RDONLY);
- if (summary_fd < 0)
+ if (summary_data == NULL)
{
- if (errno == ENOENT)
- {
- (void) unlinkat (self->cache_dir_fd, summary_cache_sig_file, 0);
- return TRUE; /* Note early return */
- }
-
- return glnx_throw_errno_prefix (error, "openat(%s)", summary_cache_file);
+ /* Cached signature without cached summary, remove the signature */
+ const char *summary_cache_sig_file = glnx_strjoina (_OSTREE_SUMMARY_CACHE_DIR, "/", remote, ".sig");
+ (void) unlinkat (self->cache_dir_fd, summary_cache_sig_file, 0);
}
-
- summary_data = glnx_fd_readall_bytes (summary_fd, cancellable, error);
- if (!summary_data)
- return FALSE;
- *summary = summary_data;
+ else
+ *out_summary = g_steal_pointer (&summary_data);
}
+
return TRUE;
}
-/* Replace the current summary+signature with new versions */
static gboolean
-_ostree_repo_cache_summary (OstreeRepo *self,
- const char *remote,
- GBytes *summary,
- GBytes *summary_sig,
- GCancellable *cancellable,
- GError **error)
+_ostree_repo_save_cache_summary_file (OstreeRepo *self,
+ const char *filename,
+ const char *extension,
+ GBytes *data,
+ GCancellable *cancellable,
+ GError **error)
{
+ const char *file = glnx_strjoina (_OSTREE_SUMMARY_CACHE_DIR, "/", filename, extension);
+ glnx_autofd int fd = -1;
+
if (self->cache_dir_fd == -1)
return TRUE;
if (!glnx_shutil_mkdir_p_at (self->cache_dir_fd, _OSTREE_SUMMARY_CACHE_DIR, DEFAULT_DIRECTORY_MODE, cancellable, error))
return FALSE;
- const char *summary_cache_file = glnx_strjoina (_OSTREE_SUMMARY_CACHE_DIR, "/", remote);
if (!glnx_file_replace_contents_at (self->cache_dir_fd,
- summary_cache_file,
- g_bytes_get_data (summary, NULL),
- g_bytes_get_size (summary),
+ file,
+ g_bytes_get_data (data, NULL),
+ g_bytes_get_size (data),
self->disable_fsync ? GLNX_FILE_REPLACE_NODATASYNC : GLNX_FILE_REPLACE_DATASYNC_NEW,
cancellable, error))
return FALSE;
- const char *summary_cache_sig_file = glnx_strjoina (_OSTREE_SUMMARY_CACHE_DIR, "/", remote, ".sig");
- if (!glnx_file_replace_contents_at (self->cache_dir_fd,
- summary_cache_sig_file,
- g_bytes_get_data (summary_sig, NULL),
- g_bytes_get_size (summary_sig),
- self->disable_fsync ? GLNX_FILE_REPLACE_NODATASYNC : GLNX_FILE_REPLACE_DATASYNC_NEW,
- cancellable, error))
+ return TRUE;
+}
+
+/* Replace the current summary+signature with new versions */
+static gboolean
+_ostree_repo_cache_summary (OstreeRepo *self,
+ const char *remote,
+ GBytes *summary,
+ GBytes *summary_sig,
+ GCancellable *cancellable,
+ GError **error)
+{
+ if (!_ostree_repo_save_cache_summary_file (self, remote, NULL,
+ summary, cancellable, error))
+ return FALSE;
+
+ if (!_ostree_repo_save_cache_summary_file (self, remote, ".sig",
+ summary_sig, cancellable, error))
return FALSE;
return TRUE;
@@ -2717,6 +2824,8 @@ static OstreeFetcher *
_ostree_repo_remote_new_fetcher (OstreeRepo *self,
const char *remote_name,
gboolean gzip,
+ GVariant *extra_headers,
+ const char *append_user_agent,
OstreeFetcherSecurityState *out_state,
GError **error)
{
@@ -2830,6 +2939,12 @@ _ostree_repo_remote_new_fetcher (OstreeRepo *self,
_ostree_fetcher_set_cookie_jar (fetcher, jar_path);
}
+ if (extra_headers)
+ _ostree_fetcher_set_extra_headers (fetcher, extra_headers);
+
+ if (append_user_agent)
+ _ostree_fetcher_set_extra_user_agent (fetcher, append_user_agent);
+
success = TRUE;
out:
@@ -2977,127 +3092,43 @@ fetch_mirrorlist (OstreeFetcher *fetcher,
}
static gboolean
-repo_remote_fetch_summary (OstreeRepo *self,
- const char *name,
- const char *metalink_url_string,
- GVariant *options,
- GBytes **out_summary,
- GBytes **out_signatures,
- gboolean *out_from_cache,
- GCancellable *cancellable,
- GError **error)
+compute_effective_mirrorlist (OstreeRepo *self,
+ const char *remote_name_or_baseurl,
+ const char *url_override,
+ OstreeFetcher *fetcher,
+ guint n_network_retries,
+ GPtrArray **out_mirrorlist,
+ GCancellable *cancellable,
+ GError **error)
{
- g_autoptr(OstreeFetcher) fetcher = NULL;
- g_autoptr(GMainContext) mainctx = NULL;
- gboolean ret = FALSE;
- gboolean from_cache = FALSE;
- const char *url_override = NULL;
- g_autoptr(GVariant) extra_headers = NULL;
- g_autoptr(GPtrArray) mirrorlist = NULL;
- const char *append_user_agent = NULL;
- guint n_network_retries = DEFAULT_N_NETWORK_RETRIES;
+ g_autofree char *baseurl = NULL;
- if (options)
- {
- (void) g_variant_lookup (options, "override-url", "&s", &url_override);
- (void) g_variant_lookup (options, "http-headers", "@a(ss)", &extra_headers);
- (void) g_variant_lookup (options, "append-user-agent", "&s", &append_user_agent);
- (void) g_variant_lookup (options, "n-network-retries", "&u", &n_network_retries);
- }
-
- mainctx = g_main_context_new ();
- g_main_context_push_thread_default (mainctx);
-
- fetcher = _ostree_repo_remote_new_fetcher (self, name, TRUE, NULL, error);
- if (fetcher == NULL)
- goto out;
-
- if (extra_headers)
- _ostree_fetcher_set_extra_headers (fetcher, extra_headers);
-
- if (append_user_agent)
- _ostree_fetcher_set_extra_user_agent (fetcher, append_user_agent);
-
- {
- g_autofree char *url_string = NULL;
- if (metalink_url_string)
- url_string = g_strdup (metalink_url_string);
- else if (url_override)
- url_string = g_strdup (url_override);
- else if (!ostree_repo_remote_get_url (self, name, &url_string, error))
- goto out;
-
- if (metalink_url_string == NULL &&
- g_str_has_prefix (url_string, "mirrorlist="))
- {
- if (!fetch_mirrorlist (fetcher, url_string + strlen ("mirrorlist="),
- n_network_retries, &mirrorlist, cancellable, error))
- goto out;
- }
- else
- {
- g_autoptr(OstreeFetcherURI) uri = _ostree_fetcher_uri_parse (url_string, error);
-
- if (!uri)
- goto out;
-
- mirrorlist =
- g_ptr_array_new_with_free_func ((GDestroyNotify) _ostree_fetcher_uri_free);
- g_ptr_array_add (mirrorlist, g_steal_pointer (&uri));
- }
- }
-
- /* FIXME: Send the ETag from the cache with the request for summary.sig to
- * avoid downloading summary.sig unnecessarily. This won’t normally provide
- * any benefits (but won’t do any harm) since summary.sig is typically 500B
- * in size. But if a repository has multiple keys, the signature file will
- * grow and this optimisation may be useful. */
- if (!_ostree_preload_metadata_file (self,
- fetcher,
- mirrorlist,
- "summary.sig",
- metalink_url_string ? TRUE : FALSE,
- n_network_retries,
- out_signatures,
- cancellable,
- error))
- goto out;
+ if (url_override != NULL)
+ baseurl = g_strdup (url_override);
+ else if (!ostree_repo_remote_get_url (self, remote_name_or_baseurl, &baseurl, error))
+ return FALSE;
- if (*out_signatures)
+ if (g_str_has_prefix (baseurl, "mirrorlist="))
{
- if (!_ostree_repo_load_cache_summary_if_same_sig (self,
- name,
- *out_signatures,
- out_summary,
- cancellable,
- error))
- goto out;
+ if (!fetch_mirrorlist (fetcher,
+ baseurl + strlen ("mirrorlist="),
+ n_network_retries,
+ out_mirrorlist,
+ cancellable, error))
+ return FALSE;
}
-
- if (*out_summary)
- from_cache = TRUE;
else
{
- if (!_ostree_preload_metadata_file (self,
- fetcher,
- mirrorlist,
- "summary",
- metalink_url_string ? TRUE : FALSE,
- n_network_retries,
- out_summary,
- cancellable,
- error))
- goto out;
- }
+ g_autoptr(OstreeFetcherURI) baseuri = _ostree_fetcher_uri_parse (baseurl, error);
- ret = TRUE;
-
- out:
- if (mainctx)
- g_main_context_pop_thread_default (mainctx);
+ if (!baseuri)
+ return FALSE;
- *out_from_cache = from_cache;
- return ret;
+ *out_mirrorlist =
+ g_ptr_array_new_with_free_func ((GDestroyNotify) _ostree_fetcher_uri_free);
+ g_ptr_array_add (*out_mirrorlist, g_steal_pointer (&baseuri));
+ }
+ return TRUE;
}
/* Create the fetcher by unioning options from the remote config, plus
@@ -3109,17 +3140,13 @@ reinitialize_fetcher (OtPullData *pull_data, const char *remote_name,
{
g_clear_object (&pull_data->fetcher);
pull_data->fetcher = _ostree_repo_remote_new_fetcher (pull_data->repo, remote_name, FALSE,
+ pull_data->extra_headers,
+ pull_data->append_user_agent,
&pull_data->fetcher_security_state,
error);
if (pull_data->fetcher == NULL)
return FALSE;
- if (pull_data->extra_headers)
- _ostree_fetcher_set_extra_headers (pull_data->fetcher, pull_data->extra_headers);
-
- if (pull_data->append_user_agent)
- _ostree_fetcher_set_extra_user_agent (pull_data->fetcher, pull_data->append_user_agent);
-
return TRUE;
}
@@ -3631,33 +3658,13 @@ ostree_repo_pull_with_options (OstreeRepo *self,
if (!metalink_url_str)
{
- g_autofree char *baseurl = NULL;
-
- if (url_override != NULL)
- baseurl = g_strdup (url_override);
- else if (!ostree_repo_remote_get_url (self, remote_name_or_baseurl, &baseurl, error))
+ if (!compute_effective_mirrorlist (self, remote_name_or_baseurl,
+ url_override,
+ pull_data->fetcher,
+ pull_data->n_network_retries,
+ &pull_data->meta_mirrorlist,
+ cancellable, error))
goto out;
-
- if (g_str_has_prefix (baseurl, "mirrorlist="))
- {
- if (!fetch_mirrorlist (pull_data->fetcher,
- baseurl + strlen ("mirrorlist="),
- pull_data->n_network_retries,
- &pull_data->meta_mirrorlist,
- cancellable, error))
- goto out;
- }
- else
- {
- g_autoptr(OstreeFetcherURI) baseuri = _ostree_fetcher_uri_parse (baseurl, error);
-
- if (!baseuri)
- goto out;
-
- pull_data->meta_mirrorlist =
- g_ptr_array_new_with_free_func ((GDestroyNotify) _ostree_fetcher_uri_free);
- g_ptr_array_add (pull_data->meta_mirrorlist, g_steal_pointer (&baseuri));
- }
}
else
{
@@ -3716,27 +3723,13 @@ ostree_repo_pull_with_options (OstreeRepo *self,
}
else
{
- if (g_str_has_prefix (contenturl, "mirrorlist="))
- {
- if (!fetch_mirrorlist (pull_data->fetcher,
- contenturl + strlen ("mirrorlist="),
- pull_data->n_network_retries,
- &pull_data->content_mirrorlist,
- cancellable, error))
- goto out;
- }
- else
- {
- g_autoptr(OstreeFetcherURI) contenturi = _ostree_fetcher_uri_parse (contenturl, error);
-
- if (!contenturi)
- goto out;
-
- pull_data->content_mirrorlist =
- g_ptr_array_new_with_free_func ((GDestroyNotify) _ostree_fetcher_uri_free);
- g_ptr_array_add (pull_data->content_mirrorlist,
- g_steal_pointer (&contenturi));
- }
+ if (!compute_effective_mirrorlist (self, remote_name_or_baseurl,
+ contenturl,
+ pull_data->fetcher,
+ pull_data->n_network_retries,
+ &pull_data->content_mirrorlist,
+ cancellable, error))
+ goto out;
}
}
@@ -5471,7 +5464,7 @@ find_remotes_cb (GObject *obj,
goto error;
fetcher = _ostree_repo_remote_new_fetcher (self, result->remote->name,
- TRUE, NULL, &error);
+ TRUE, NULL, NULL, NULL, &error);
if (fetcher == NULL)
goto error;
@@ -6093,96 +6086,108 @@ ostree_repo_remote_fetch_summary_with_options (OstreeRepo *self,
g_autoptr(GBytes) signatures = NULL;
gboolean gpg_verify_summary;
g_autoptr(GPtrArray) signapi_summary_verifiers = NULL;
- gboolean ret = FALSE;
- gboolean summary_is_from_cache;
+ gboolean summary_is_from_cache = FALSE;
+ g_autoptr(OstreeFetcher) fetcher = NULL;
+ g_autoptr(GMainContextPopDefault) mainctx = NULL;
+ const char *url_override = NULL;
+ g_autoptr(GVariant) extra_headers = NULL;
+ g_autoptr(GPtrArray) mirrorlist = NULL;
+ const char *append_user_agent = NULL;
+ guint n_network_retries = DEFAULT_N_NETWORK_RETRIES;
g_return_val_if_fail (OSTREE_REPO (self), FALSE);
g_return_val_if_fail (name != NULL, FALSE);
if (!ostree_repo_get_remote_option (self, name, "metalink", NULL,
&metalink_url_string, error))
- goto out;
-
- if (!repo_remote_fetch_summary (self,
- name,
- metalink_url_string,
- options,
- &summary,
- &signatures,
- &summary_is_from_cache,
- cancellable,
- error))
- goto out;
-
- if (!ostree_repo_remote_get_gpg_verify_summary (self, name, &gpg_verify_summary, error))
- goto out;
+ return FALSE;
- if (gpg_verify_summary)
+ if (options)
{
- if (summary == NULL)
- {
- g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
- "GPG verification enabled, but no summary found (check that the configured URL in remote config is correct)");
- goto out;
- }
-
- if (signatures == NULL)
- {
- g_set_error (error, OSTREE_GPG_ERROR, OSTREE_GPG_ERROR_NO_SIGNATURE,
- "GPG verification enabled, but no summary signatures found (use gpg-verify-summary=false in remote config to disable)");
- goto out;
- }
-
- /* Verify any summary signatures. */
- if (summary != NULL && signatures != NULL)
- {
- g_autoptr(OstreeGpgVerifyResult) result = NULL;
-
- result = ostree_repo_verify_summary (self,
- name,
- summary,
- signatures,
- cancellable,
- error);
- if (!ostree_gpg_verify_result_require_valid_signature (result, error))
- goto out;
- }
+ (void) g_variant_lookup (options, "override-url", "&s", &url_override);
+ (void) g_variant_lookup (options, "http-headers", "@a(ss)", &extra_headers);
+ (void) g_variant_lookup (options, "append-user-agent", "&s", &append_user_agent);
+ (void) g_variant_lookup (options, "n-network-retries", "&u", &n_network_retries);
}
+ if (!ostree_repo_remote_get_gpg_verify_summary (self, name, &gpg_verify_summary, error))
+ return FALSE;
+
if (!_signapi_init_for_remote (self, name, NULL,
&signapi_summary_verifiers,
error))
- goto out;
+ return FALSE;
- if (signapi_summary_verifiers)
+ mainctx = _ostree_main_context_new_default ();
+
+ fetcher = _ostree_repo_remote_new_fetcher (self, name, TRUE, extra_headers, append_user_agent, NULL, error);
+ if (fetcher == NULL)
+ return FALSE;
+
+ if (metalink_url_string)
{
- if (summary == NULL)
- {
- g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
- "Signature verification enabled, but no summary found (check that the configured URL in remote config is correct)");
- goto out;
- }
+ g_autoptr(OstreeFetcherURI) uri = _ostree_fetcher_uri_parse (metalink_url_string, error);
+ if (!uri)
+ return FALSE;
- if (signatures == NULL)
- {
- g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
- "Signature verification enabled, but no summary signatures found (use sign-verify-summary=false in remote config to disable)");
- goto out;
- }
+ mirrorlist =
+ g_ptr_array_new_with_free_func ((GDestroyNotify) _ostree_fetcher_uri_free);
+ g_ptr_array_add (mirrorlist, g_steal_pointer (&uri));
+ }
+ else if (!compute_effective_mirrorlist (self, name, url_override,
+ fetcher, n_network_retries,
+ &mirrorlist, cancellable, error))
+ return FALSE;
- /* Verify any summary signatures. */
- if (summary != NULL && signatures != NULL)
- {
- g_autoptr(GVariant) sig_variant = NULL;
+ /* FIXME: Send the ETag from the cache with the request for summary.sig to
+ * avoid downloading summary.sig unnecessarily. This won’t normally provide
+ * any benefits (but won’t do any harm) since summary.sig is typically 500B
+ * in size. But if a repository has multiple keys, the signature file will
+ * grow and this optimisation may be useful. */
+ if (!_ostree_preload_metadata_file (self,
+ fetcher,
+ mirrorlist,
+ "summary.sig",
+ metalink_url_string ? TRUE : FALSE,
+ n_network_retries,
+ &signatures,
+ cancellable,
+ error))
+ return FALSE;
- sig_variant = g_variant_new_from_bytes (OSTREE_SUMMARY_SIG_GVARIANT_FORMAT,
- signatures, FALSE);
+ if (signatures)
+ {
+ if (!_ostree_repo_load_cache_summary_if_same_sig (self,
+ name,
+ signatures,
+ &summary,
+ cancellable,
+ error))
+ return FALSE;
+ }
- if (!_sign_verify_for_remote (signapi_summary_verifiers, summary, sig_variant, NULL, error))
- goto out;
- }
+ if (summary)
+ summary_is_from_cache = TRUE;
+ else
+ {
+ if (!_ostree_preload_metadata_file (self,
+ fetcher,
+ mirrorlist,
+ "summary",
+ metalink_url_string ? TRUE : FALSE,
+ n_network_retries,
+ &summary,
+ cancellable,
+ error))
+ return FALSE;
}
+ if (!_ostree_repo_verify_summary (self, name,
+ gpg_verify_summary, signapi_summary_verifiers,
+ summary, signatures,
+ cancellable, error))
+ return FALSE;
+
if (!summary_is_from_cache && summary && signatures)
{
g_autoptr(GError) temp_error = NULL;
@@ -6199,7 +6204,7 @@ ostree_repo_remote_fetch_summary_with_options (OstreeRepo *self,
else
{
g_propagate_error (error, g_steal_pointer (&temp_error));
- goto out;
+ return FALSE;
}
}
}
@@ -6210,10 +6215,7 @@ ostree_repo_remote_fetch_summary_with_options (OstreeRepo *self,
if (out_signatures != NULL)
*out_signatures = g_steal_pointer (&signatures);
- ret = TRUE;
-
-out:
- return ret;
+ return TRUE;
}
#else /* HAVE_LIBCURL_OR_LIBSOUP */
diff --git a/src/libostree/ostree-repo-static-delta-core.c b/src/libostree/ostree-repo-static-delta-core.c
index ade4e9df..835ec7f3 100644
--- a/src/libostree/ostree-repo-static-delta-core.c
+++ b/src/libostree/ostree-repo-static-delta-core.c
@@ -54,6 +54,28 @@ _ostree_static_delta_parse_checksum_array (GVariant *array,
return TRUE;
}
+GVariant *
+_ostree_repo_static_delta_superblock_digest (OstreeRepo *repo,
+ const char *from,
+ const char *to,
+ GCancellable *cancellable,
+ GError **error)
+{
+ g_autofree char *superblock = _ostree_get_relative_static_delta_superblock_path ((from && from[0]) ? from : NULL, to);
+ glnx_autofd int superblock_file_fd = -1;
+ guint8 digest[OSTREE_SHA256_DIGEST_LEN];
+
+ if (!glnx_openat_rdonly (repo->repo_dir_fd, superblock, TRUE, &superblock_file_fd, error))
+ return NULL;
+
+ g_autoptr(GBytes) superblock_content = ot_fd_readall_or_mmap (superblock_file_fd, 0, error);
+ if (!superblock_content)
+ return NULL;
+
+ ot_checksum_bytes (superblock_content, digest);
+
+ return ot_gvariant_new_bytearray (digest, sizeof (digest));
+}
/**
* ostree_repo_list_static_delta_names:
@@ -109,7 +131,7 @@ ostree_repo_list_static_delta_names (OstreeRepo *self,
return FALSE;
if (sub_dent == NULL)
break;
- if (dent->d_type != DT_DIR)
+ if (sub_dent->d_type != DT_DIR)
continue;
const char *name1 = dent->d_name;
diff --git a/src/libostree/ostree-repo-static-delta-private.h b/src/libostree/ostree-repo-static-delta-private.h
index 155acd52..ff8de9d4 100644
--- a/src/libostree/ostree-repo-static-delta-private.h
+++ b/src/libostree/ostree-repo-static-delta-private.h
@@ -190,6 +190,12 @@ _ostree_repo_static_delta_query_exists (OstreeRepo *repo,
gboolean *out_exists,
GCancellable *cancellable,
GError **error);
+GVariant *
+_ostree_repo_static_delta_superblock_digest (OstreeRepo *repo,
+ const char *from,
+ const char *to,
+ GCancellable *cancellable,
+ GError **error);
gboolean
_ostree_repo_static_delta_dump (OstreeRepo *repo,
diff --git a/src/libostree/ostree-repo.c b/src/libostree/ostree-repo.c
index 95eb0efc..621668d7 100644
--- a/src/libostree/ostree-repo.c
+++ b/src/libostree/ostree-repo.c
@@ -5793,25 +5793,18 @@ ostree_repo_regenerate_summary (OstreeRepo *self,
{
g_autofree char *from = NULL;
g_autofree char *to = NULL;
- if (!_ostree_parse_delta_name (delta_names->pdata[i], &from, &to, error))
- return FALSE;
+ GVariant *digest;
- g_autofree char *superblock = _ostree_get_relative_static_delta_superblock_path ((from && from[0]) ? from : NULL, to);
- glnx_autofd int superblock_file_fd = -1;
-
- if (!glnx_openat_rdonly (self->repo_dir_fd, superblock, TRUE, &superblock_file_fd, error))
+ if (!_ostree_parse_delta_name (delta_names->pdata[i], &from, &to, error))
return FALSE;
- g_autoptr(GBytes) superblock_content = ot_fd_readall_or_mmap (superblock_file_fd, 0, error);
- if (!superblock_content)
+ digest = _ostree_repo_static_delta_superblock_digest (self,
+ (from && from[0]) ? from : NULL,
+ to, cancellable, error);
+ if (digest == NULL)
return FALSE;
- g_auto(OtChecksum) hasher = { 0, };
- ot_checksum_init (&hasher);
- ot_checksum_update_bytes (&hasher, superblock_content);
- guint8 digest[OSTREE_SHA256_DIGEST_LEN];
- ot_checksum_get_digest (&hasher, digest, sizeof (digest));
- g_variant_dict_insert_value (&deltas_builder, delta_names->pdata[i], ot_gvariant_new_bytearray (digest, sizeof (digest)));
+ g_variant_dict_insert_value (&deltas_builder, delta_names->pdata[i], digest);
}
if (delta_names->len > 0)
diff --git a/src/libotutil/ot-checksum-utils.c b/src/libotutil/ot-checksum-utils.c
index 66767368..26e0280a 100644
--- a/src/libotutil/ot-checksum-utils.c
+++ b/src/libotutil/ot-checksum-utils.c
@@ -275,3 +275,13 @@ ot_checksum_file_at (int dfd,
ot_checksum_get_hexdigest (&checksum, hexdigest, sizeof (hexdigest));
return g_strdup (hexdigest);
}
+
+void
+ot_checksum_bytes (GBytes *data,
+ guint8 out_digest[_OSTREE_SHA256_DIGEST_LEN])
+{
+ g_auto(OtChecksum) hasher = { 0, };
+ ot_checksum_init (&hasher);
+ ot_checksum_update_bytes (&hasher, data);
+ ot_checksum_get_digest (&hasher, out_digest, _OSTREE_SHA256_DIGEST_LEN);
+}
diff --git a/src/libotutil/ot-checksum-utils.h b/src/libotutil/ot-checksum-utils.h
index 411ef25d..5432c81e 100644
--- a/src/libotutil/ot-checksum-utils.h
+++ b/src/libotutil/ot-checksum-utils.h
@@ -96,4 +96,7 @@ char * ot_checksum_file_at (int dfd,
GCancellable *cancellable,
GError **error);
+void ot_checksum_bytes (GBytes *data,
+ guint8 out_digest[_OSTREE_SHA256_DIGEST_LEN]);
+
G_END_DECLS
diff --git a/src/libotutil/otutil.h b/src/libotutil/otutil.h
index cd312365..7db7270d 100644
--- a/src/libotutil/otutil.h
+++ b/src/libotutil/otutil.h
@@ -52,6 +52,31 @@
#define ot_journal_print(...) {}
#endif
+typedef GMainContext GMainContextPopDefault;
+static inline void
+_ostree_main_context_pop_default_destroy (void *p)
+{
+ GMainContext *main_context = p;
+
+ if (main_context)
+ {
+ g_main_context_pop_thread_default (main_context);
+ g_main_context_unref (main_context);
+ }
+}
+
+static inline GMainContextPopDefault *
+_ostree_main_context_new_default (void)
+{
+ GMainContext *main_context = g_main_context_new ();
+
+ g_main_context_push_thread_default (main_context);
+ return main_context;
+}
+
+G_DEFINE_AUTOPTR_CLEANUP_FUNC (GMainContextPopDefault, _ostree_main_context_pop_default_destroy)
+
+
#include <ot-keyfile-utils.h>
#include <ot-gio-utils.h>
#include <ot-fs-utils.h>
diff --git a/tests/test-symbols.sh b/tests/test-symbols.sh
index 75df37e1..a0781618 100755
--- a/tests/test-symbols.sh
+++ b/tests/test-symbols.sh
@@ -66,7 +66,7 @@ echo 'ok documented symbols'
# ONLY update this checksum in release commits!
cat > released-sha256.txt <<EOF
-1f83814b9a785f9f612ee8f707dadb86d0dcbdc22603937575b7beefb26b50cc ${released_syms}
+55f21380aa7f9ecc447a680b5c091692f2a0b98aa96ea00fba6aa6406aa69a5a ${released_syms}
EOF
sha256sum -c released-sha256.txt