diff --git a/apidoc/ostree-sections.txt b/apidoc/ostree-sections.txt index 4e474d8d..d60e8f2a 100644 --- a/apidoc/ostree-sections.txt +++ b/apidoc/ostree-sections.txt @@ -320,6 +320,7 @@ ostree_repo_set_alias_ref_immediate ostree_repo_set_cache_dir ostree_repo_sign_delta ostree_repo_has_object +ostree_repo_mark_commit_partial ostree_repo_write_metadata ostree_repo_write_metadata_async ostree_repo_write_metadata_finish diff --git a/src/libostree/libostree-devel.sym b/src/libostree/libostree-devel.sym index 36926ce1..ca3afa87 100644 --- a/src/libostree/libostree-devel.sym +++ b/src/libostree/libostree-devel.sym @@ -21,6 +21,7 @@ LIBOSTREE_2017.15 { ostree_repo_fsck_object; + ostree_repo_mark_commit_partial; } LIBOSTREE_2017.14; /* Stub section for the stable release *after* this development one; don't diff --git a/src/libostree/ostree-repo-commit.c b/src/libostree/ostree-repo-commit.c index 50ffeac5..4392f700 100644 --- a/src/libostree/ostree-repo-commit.c +++ b/src/libostree/ostree-repo-commit.c @@ -1589,6 +1589,48 @@ ensure_txn_refs (OstreeRepo *self) g_free); } +/** + * ostree_repo_mark_commit_partial: + * @self: Repo + * @checksum: Commit SHA-256 + * @is_partial: Whether or not this commit is partial + * @error: Error + * + * Commits in "partial" state do not have all their child objects written. This + * occurs in various situations, such as during a pull, but also if a "subpath" + * pull is used, as well as "commit only" pulls. + * + * This function is used by ostree_repo_pull_with_options(); you + * should use this if you are implementing a different type of transport. + * + * Since: 2017.15 + */ +gboolean +ostree_repo_mark_commit_partial (OstreeRepo *self, + const char *checksum, + gboolean is_partial, + GError **error) +{ + g_autofree char *commitpartial_path = _ostree_get_commitpartial_path (checksum); + if (is_partial) + { + glnx_autofd int fd = openat (self->repo_dir_fd, commitpartial_path, + O_EXCL | O_CREAT | O_WRONLY | O_CLOEXEC | O_NOCTTY, 0644); + if (fd == -1) + { + if (errno != EEXIST) + return glnx_throw_errno_prefix (error, "open(%s)", commitpartial_path); + } + } + else + { + if (!ot_ensure_unlinked_at (self->repo_dir_fd, commitpartial_path, 0)) + return FALSE; + } + + return TRUE; +} + /** * ostree_repo_transaction_set_refspec: * @self: An #OstreeRepo diff --git a/src/libostree/ostree-repo-prune.c b/src/libostree/ostree-repo-prune.c index 9eec4ebe..1b65ae1c 100644 --- a/src/libostree/ostree-repo-prune.c +++ b/src/libostree/ostree-repo-prune.c @@ -36,16 +36,6 @@ typedef struct { guint64 freed_bytes; } OtPruneData; -static gboolean -prune_commitpartial_file (OstreeRepo *repo, - const char *checksum, - GCancellable *cancellable, - GError **error) -{ - g_autofree char *path = _ostree_get_commitpartial_path (checksum); - return ot_ensure_unlinked_at (repo->repo_dir_fd, path, error); -} - static gboolean maybe_prune_loose_object (OtPruneData *data, OstreeRepoPruneFlags flags, @@ -68,7 +58,7 @@ maybe_prune_loose_object (OtPruneData *data, if (objtype == OSTREE_OBJECT_TYPE_COMMIT) { - if (!prune_commitpartial_file (data->repo, checksum, cancellable, error)) + if (!ostree_repo_mark_commit_partial (data->repo, checksum, FALSE, error)) return FALSE; } diff --git a/src/libostree/ostree-repo-pull.c b/src/libostree/ostree-repo-pull.c index 4de2e8f3..2e6e308c 100644 --- a/src/libostree/ostree-repo-pull.c +++ b/src/libostree/ostree-repo-pull.c @@ -558,21 +558,6 @@ fetch_uri_contents_utf8_sync (OstreeFetcher *fetcher, cancellable, error); } -static gboolean -write_commitpartial_for (OtPullData *pull_data, - const char *checksum, - GError **error) -{ - g_autofree char *commitpartial_path = _ostree_get_commitpartial_path (checksum); - glnx_autofd int fd = openat (pull_data->repo->repo_dir_fd, commitpartial_path, O_EXCL | O_CREAT | O_WRONLY | O_CLOEXEC | O_NOCTTY, 0644); - if (fd == -1) - { - if (errno != EEXIST) - return glnx_throw_errno_prefix (error, "open(%s)", commitpartial_path); - } - return TRUE; -} - static void enqueue_one_object_request (OtPullData *pull_data, const char *checksum, @@ -1267,7 +1252,7 @@ meta_fetch_on_complete (GObject *object, pull_data->cancellable, error)) goto out; - if (!write_commitpartial_for (pull_data, checksum, error)) + if (!ostree_repo_mark_commit_partial (pull_data->repo, checksum, TRUE, error)) goto out; } @@ -1821,7 +1806,7 @@ scan_one_metadata_object (OtPullData *pull_data, if (objtype == OSTREE_OBJECT_TYPE_COMMIT) { /* mark as partial to ensure we scan the commit below */ - if (!write_commitpartial_for (pull_data, checksum, error)) + if (!ostree_repo_mark_commit_partial (pull_data->repo, checksum, TRUE, error)) return FALSE; } @@ -1854,7 +1839,7 @@ scan_one_metadata_object (OtPullData *pull_data, if (objtype == OSTREE_OBJECT_TYPE_COMMIT) { /* mark as partial to ensure we scan the commit below */ - if (!write_commitpartial_for (pull_data, checksum, error)) + if (!ostree_repo_mark_commit_partial (pull_data->repo, checksum, TRUE, error)) return FALSE; } if (!_ostree_repo_import_object (pull_data->repo, refd_repo, @@ -4340,15 +4325,13 @@ ostree_repo_pull_with_options (OstreeRepo *self, { GLNX_HASH_TABLE_FOREACH_V (requested_refs_to_fetch, const char*, checksum) { - g_autofree char *commitpartial_path = _ostree_get_commitpartial_path (checksum); - if (!ot_ensure_unlinked_at (pull_data->repo->repo_dir_fd, commitpartial_path, 0)) + if (!ostree_repo_mark_commit_partial (pull_data->repo, checksum, FALSE, error)) goto out; } GLNX_HASH_TABLE_FOREACH_V (commits_to_fetch, const char*, commit) { - g_autofree char *commitpartial_path = _ostree_get_commitpartial_path (commit); - if (!ot_ensure_unlinked_at (pull_data->repo->repo_dir_fd, commitpartial_path, 0)) + if (!ostree_repo_mark_commit_partial (pull_data->repo, commit, FALSE, error)) goto out; } } diff --git a/src/libostree/ostree-repo.h b/src/libostree/ostree-repo.h index 5ef12bb9..e2608d84 100644 --- a/src/libostree/ostree-repo.h +++ b/src/libostree/ostree-repo.h @@ -362,6 +362,12 @@ gboolean ostree_repo_abort_transaction (OstreeRepo *self, GCancellable *cancellable, GError **error); +_OSTREE_PUBLIC +gboolean ostree_repo_mark_commit_partial (OstreeRepo *self, + const char *checksum, + gboolean is_partial, + GError **error); + _OSTREE_PUBLIC void ostree_repo_transaction_set_refspec (OstreeRepo *self, const char *refspec,