lib/pull: Split verify_bindings() out into a cmdprivate method
authorPhilip Withnall <withnall@endlessm.com>
Mon, 20 Nov 2017 12:37:24 +0000 (12:37 +0000)
committerAtomic Bot <atomic-devel@projectatomic.io>
Thu, 14 Dec 2017 14:18:44 +0000 (14:18 +0000)
It will be used by the fsck utility in future. We could expose it
publicly in future too, if needed.

Signed-off-by: Philip Withnall <withnall@endlessm.com>
Closes: #1347
Approved by: cgwalters

Makefile-libostree.am
apidoc/Makefile.am
src/libostree/ostree-cmdprivate.c
src/libostree/ostree-cmdprivate.h
src/libostree/ostree-repo-pull-private.h [new file with mode: 0644]
src/libostree/ostree-repo-pull.c

index 39dc0d1416edab39d5bf22b4f49abef9d609ead7..0a4de6de170b4fa61af88aa398ea8c96150711ec 100644 (file)
@@ -101,6 +101,7 @@ libostree_1_la_SOURCES = \
        src/libostree/ostree-repo-checkout.c \
        src/libostree/ostree-repo-commit.c \
        src/libostree/ostree-repo-pull.c \
+       src/libostree/ostree-repo-pull-private.h \
        src/libostree/ostree-repo-libarchive.c \
        src/libostree/ostree-repo-prune.c \
        src/libostree/ostree-repo-refs.c \
index f3405fb0794e881fede6f47d486361faaac4df0e..d46eac786a342984902563073c5438f907b23691 100644 (file)
@@ -83,6 +83,7 @@ IGNORE_HFILES= \
        ostree-metalink.h \
        ostree-repo-file-enumerator.h \
        ostree-repo-private.h \
+       ostree-repo-pull-private.h \
        ostree-repo-static-delta-private.h \
        ostree-sysroot-private.h \
        ostree-tls-cert-interaction.h \
index 3e60b125a4ea72dad003bcbdc010072f2df9b687..5637e98b68988d392c53cda1badf473ca1f36a54 100644 (file)
@@ -22,6 +22,7 @@
 #include "ostree-cmdprivate.h"
 #include "ostree-repo-private.h"
 #include "ostree-core-private.h"
+#include "ostree-repo-pull-private.h"
 #include "ostree-repo-static-delta-private.h"
 #include "ostree-sysroot.h"
 #include "ostree-bootloader-grub2.h"
@@ -48,7 +49,8 @@ ostree_cmd__private__ (void)
     impl_ostree_generate_grub2_config,
     _ostree_repo_static_delta_dump,
     _ostree_repo_static_delta_query_exists,
-    _ostree_repo_static_delta_delete
+    _ostree_repo_static_delta_delete,
+    _ostree_repo_verify_bindings
   };
 
   return &table;
index f636ab15e67bfc19f06d1184b1af9ecb5dbd4f7f..2ba535ec16370bb3b1629e2cda4fa1bf83a0a78e 100644 (file)
@@ -31,6 +31,7 @@ typedef struct {
   gboolean (* ostree_static_delta_dump) (OstreeRepo *repo, const char *delta_id, GCancellable *cancellable, GError **error);
   gboolean (* ostree_static_delta_query_exists) (OstreeRepo *repo, const char *delta_id, gboolean *out_exists, GCancellable *cancellable, GError **error);
   gboolean (* ostree_static_delta_delete) (OstreeRepo *repo, const char *delta_id, GCancellable *cancellable, GError **error);
+  gboolean (* ostree_repo_verify_bindings) (const char *collection_id, const char *ref_name, GVariant *commit, GError **error);
 } OstreeCmdPrivateVTable;
 
 /* Note this not really "public", we just export the symbol, but not the header */
diff --git a/src/libostree/ostree-repo-pull-private.h b/src/libostree/ostree-repo-pull-private.h
new file mode 100644 (file)
index 0000000..ba30b15
--- /dev/null
@@ -0,0 +1,32 @@
+/*
+ * Copyright © 2017 Endless Mobile, Inc.
+ *
+ * This library 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 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, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 02111-1307, USA.
+ */
+
+#pragma once
+
+#include "ostree-core.h"
+
+G_BEGIN_DECLS
+
+gboolean
+_ostree_repo_verify_bindings (const char  *collection_id,
+                              const char  *ref_name,
+                              GVariant    *commit,
+                              GError     **error);
+
+G_END_DECLS
index 8ac4850655635f8d378f3cd194068161391825e1..42d802b2798a8de316d6f61409a2625bc2e7a3ce 100644 (file)
@@ -32,6 +32,7 @@
 
 #include "ostree-core-private.h"
 #include "ostree-repo-private.h"
+#include "ostree-repo-pull-private.h"
 #include "ostree-repo-static-delta-private.h"
 #include "ostree-metalink.h"
 #include "ostree-fetcher-util.h"
@@ -1475,30 +1476,40 @@ get_remote_repo_collection_id (OtPullData *pull_data)
 }
 #endif  /* OSTREE_ENABLE_EXPERIMENTAL_API */
 
-/* Verify the ref and collection bindings.
+#endif  /* HAVE_LIBCURL_OR_LIBSOUP */
+
+/**
+ * _ostree_repo_verify_bindings:
+ * @collection_id: (nullable): Locally specified collection ID for the remote
+ *    the @commit was retrieved from, or %NULL if none is configured
+ * @ref_name: (nullable): Ref name the commit was retrieved using, or %NULL if
+ *    the commit was retrieved by checksum
+ * @commit: Commit data to check
+ * @error: Return location for a #GError, or %NULL
+ *
+ * Verify the ref and collection bindings.
  *
  * The ref binding is verified only if it exists. But if we have the
- * collection ID specified in the remote configuration then the ref
- * binding must exist, otherwise the verification will fail. Parts of
- * the verification can be skipped by passing NULL to the requested_ref
- * parameter (in case we requested a checksum directly, without looking it up
- * from a ref).
+ * collection ID specified in the remote configuration (@collection_id is
+ * non-%NULL) then the ref binding must exist, otherwise the verification will
+ * fail. Parts of the verification can be skipped by passing %NULL to the
+ * @ref_name parameter (in case we requested a checksum directly, without
+ * looking it up from a ref).
  *
  * The collection binding is verified only when we have collection ID
  * specified in the remote configuration. If it is specified, then the
  * binding must exist and must be equal to the remote repository
  * collection ID.
+ *
+ * Returns: %TRUE if bindings are correct, %FALSE otherwise
+ * Since: 2017.14
  */
-static gboolean
-verify_bindings (OtPullData                 *pull_data,
-                 GVariant                   *commit,
-                 const OstreeCollectionRef  *requested_ref,
-                 GError                    **error)
+gboolean
+_ostree_repo_verify_bindings (const char  *collection_id,
+                              const char  *ref_name,
+                              GVariant    *commit,
+                              GError     **error)
 {
-  g_autofree char *remote_collection_id = NULL;
-#ifdef OSTREE_ENABLE_EXPERIMENTAL_API
-  remote_collection_id = get_remote_repo_collection_id (pull_data);
-#endif  /* OSTREE_ENABLE_EXPERIMENTAL_API */
   g_autoptr(GVariant) metadata = g_variant_get_child_value (commit, 0);
   g_autofree const char **refs = NULL;
   if (!g_variant_lookup (metadata,
@@ -1510,7 +1521,7 @@ verify_bindings (OtPullData                 *pull_data,
        * we certainly will not verify the collection binding in the
        * commit.
        */
-      if (remote_collection_id == NULL)
+      if (collection_id == NULL)
         return TRUE;
 
       return glnx_throw (error,
@@ -1518,9 +1529,9 @@ verify_bindings (OtPullData                 *pull_data,
                          "binding information, found none");
     }
 
-  if (requested_ref != NULL)
+  if (ref_name != NULL)
     {
-      if (!g_strv_contains ((const char *const *) refs, requested_ref->ref_name))
+      if (!g_strv_contains ((const char *const *) refs, ref_name))
         {
           g_autoptr(GString) refs_dump = g_string_new (NULL);
           const char *refs_str;
@@ -1545,33 +1556,35 @@ verify_bindings (OtPullData                 *pull_data,
 
           return glnx_throw (error, "commit has no requested ref ‘%s’ "
                              "in ref binding metadata (%s)",
-                             requested_ref->ref_name, refs_str);
+                             ref_name, refs_str);
         }
     }
 
-  if (remote_collection_id != NULL)
+  if (collection_id != NULL)
     {
 #ifdef OSTREE_ENABLE_EXPERIMENTAL_API
-      const char *collection_id;
+      const char *collection_id_binding;
       if (!g_variant_lookup (metadata,
                              OSTREE_COMMIT_META_KEY_COLLECTION_BINDING,
                              "&s",
-                             &collection_id))
+                             &collection_id_binding))
         return glnx_throw (error,
                            "expected commit metadata to have collection ID "
                            "binding information, found none");
-      if (!g_str_equal (collection_id, remote_collection_id))
+      if (!g_str_equal (collection_id_binding, collection_id))
         return glnx_throw (error,
                            "commit has collection ID ‘%s’ in collection binding "
                            "metadata, while the remote it came from has "
                            "collection ID ‘%s’",
-                           collection_id, remote_collection_id);
+                           collection_id_binding, collection_id);
 #endif
     }
 
   return TRUE;
 }
 
+#ifdef HAVE_LIBCURL_OR_LIBSOUP
+
 /* Look at a commit object, and determine whether there are
  * more things to fetch.
  */
@@ -1626,7 +1639,13 @@ scan_commit_object (OtPullData                 *pull_data,
   /* If ref is non-NULL then the commit we fetched was requested through the
    * branch, otherwise we requested a commit checksum without specifying a branch.
    */
-  if (!verify_bindings (pull_data, commit, ref, error))
+  g_autofree char *remote_collection_id = NULL;
+#ifdef OSTREE_ENABLE_EXPERIMENTAL_API
+  remote_collection_id = get_remote_repo_collection_id (pull_data);
+#endif  /* OSTREE_ENABLE_EXPERIMENTAL_API */
+  if (!_ostree_repo_verify_bindings (remote_collection_id,
+                                     (ref != NULL) ? ref->ref_name : NULL,
+                                     commit, error))
     return glnx_prefix_error (error, "Commit %s", checksum);
 
   if (pull_data->timestamp_check)