summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--apidoc/ostree-sections.txt1
-rw-r--r--src/libostree/libostree-devel.sym1
-rw-r--r--src/libostree/ostree-repo-commit.c61
-rw-r--r--src/libostree/ostree-repo.c15
-rw-r--r--src/libostree/ostree-repo.h44
-rw-r--r--src/ostree/ot-builtin-fsck.c12
6 files changed, 100 insertions, 34 deletions
diff --git a/apidoc/ostree-sections.txt b/apidoc/ostree-sections.txt
index e8faeb10..252a563a 100644
--- a/apidoc/ostree-sections.txt
+++ b/apidoc/ostree-sections.txt
@@ -333,6 +333,7 @@ ostree_repo_set_cache_dir
ostree_repo_sign_delta
ostree_repo_has_object
ostree_repo_mark_commit_partial
+ostree_repo_mark_commit_partial_reason
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 f552bcea..58d35f55 100644
--- a/src/libostree/libostree-devel.sym
+++ b/src/libostree/libostree-devel.sym
@@ -19,6 +19,7 @@
/* Add new symbols here. Release commits should copy this section into -released.sym. */
LIBOSTREE_2019.4 {
+ ostree_repo_mark_commit_partial_reason;
} LIBOSTREE_2019.3;
/* 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 e7bc9820..0aaebbdb 100644
--- a/src/libostree/ostree-repo-commit.c
+++ b/src/libostree/ostree-repo-commit.c
@@ -1874,26 +1874,29 @@ ensure_txn_refs (OstreeRepo *self)
}
/**
- * ostree_repo_mark_commit_partial:
+ * ostree_repo_mark_commit_partial_reason:
* @self: Repo
* @checksum: Commit SHA-256
* @is_partial: Whether or not this commit is partial
+ * @in_state: Reason bitmask for partial commit
* @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.
+ * Allows the setting of a reason code for a partial commit. Presently
+ * it only supports setting reason bitmask to
+ * OSTREE_REPO_COMMIT_STATE_FSCK_PARTIAL, or
+ * OSTREE_REPO_COMMIT_STATE_NORMAL. This will allow successive ostree
+ * fsck operations to exit properly with an error code if the
+ * repository has been truncated as a result of fsck trying to repair
+ * it.
*
- * 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
+ * Since: 2019.4
*/
gboolean
-ostree_repo_mark_commit_partial (OstreeRepo *self,
- const char *checksum,
- gboolean is_partial,
- GError **error)
+ostree_repo_mark_commit_partial_reason (OstreeRepo *self,
+ const char *checksum,
+ gboolean is_partial,
+ OstreeRepoCommitState in_state,
+ GError **error)
{
g_autofree char *commitpartial_path = _ostree_get_commitpartial_path (checksum);
if (is_partial)
@@ -1905,6 +1908,12 @@ ostree_repo_mark_commit_partial (OstreeRepo *self,
if (errno != EEXIST)
return glnx_throw_errno_prefix (error, "open(%s)", commitpartial_path);
}
+ else
+ {
+ if (in_state & OSTREE_REPO_COMMIT_STATE_FSCK_PARTIAL)
+ if (glnx_loop_write (fd, "f", 1) < 0)
+ return glnx_throw_errno_prefix (error, "write(%s)", commitpartial_path);
+ }
}
else
{
@@ -1916,6 +1925,34 @@ ostree_repo_mark_commit_partial (OstreeRepo *self,
}
/**
+ * ostree_repo_mark_commit_partial:
+ * @self: Repo
+ * @checksum: Commit SHA-256
+ * @is_partial: Whether or not this commit is partial
+ * @error: Error
+ *
+ * Commits in the "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)
+{
+ return ostree_repo_mark_commit_partial_reason (self, checksum, is_partial,
+ OSTREE_REPO_COMMIT_STATE_NORMAL,
+ error);
+}
+
+/**
* ostree_repo_transaction_set_refspec:
* @self: An #OstreeRepo
* @refspec: The refspec to write
diff --git a/src/libostree/ostree-repo.c b/src/libostree/ostree-repo.c
index eb652bef..b654aff2 100644
--- a/src/libostree/ostree-repo.c
+++ b/src/libostree/ostree-repo.c
@@ -3768,10 +3768,19 @@ load_metadata_internal (OstreeRepo *self,
g_autofree char *commitpartial_path = _ostree_get_commitpartial_path (sha256);
*out_state = 0;
- if (!glnx_fstatat_allow_noent (self->repo_dir_fd, commitpartial_path, NULL, 0, error))
+ glnx_autofd int fd = -1;
+ if (!ot_openat_ignore_enoent (self->repo_dir_fd, commitpartial_path, &fd, error))
return FALSE;
- if (errno == 0)
- *out_state |= OSTREE_REPO_COMMIT_STATE_PARTIAL;
+ if (fd != -1)
+ {
+ *out_state |= OSTREE_REPO_COMMIT_STATE_PARTIAL;
+ char reason;
+ if (read (fd, &reason, 1) == 1)
+ {
+ if (reason == 'f')
+ *out_state |= OSTREE_REPO_COMMIT_STATE_FSCK_PARTIAL;
+ }
+ }
}
}
else if (self->parent_repo)
diff --git a/src/libostree/ostree-repo.h b/src/libostree/ostree-repo.h
index 038bbd41..aaaaa622 100644
--- a/src/libostree/ostree-repo.h
+++ b/src/libostree/ostree-repo.h
@@ -249,6 +249,26 @@ gboolean ostree_repo_write_config (OstreeRepo *self,
GError **error);
/**
+ * OstreeRepoCommitState:
+ * @OSTREE_REPO_COMMIT_STATE_NORMAL: Commit is complete. This is the default.
+ * (Since: 2017.14.)
+ * @OSTREE_REPO_COMMIT_STATE_PARTIAL: One or more objects are missing from the
+ * local copy of the commit, but metadata is present. (Since: 2015.7.)
+ * @OSTREE_REPO_COMMIT_STATE_FSCK_PARTIAL: One or more objects are missing from the
+ * local copy of the commit, due to an fsck --delete. (Since: 2019.3.)
+ *
+ * Flags representing the state of a commit in the local repository, as returned
+ * by ostree_repo_load_commit().
+ *
+ * Since: 2015.7
+ */
+typedef enum {
+ OSTREE_REPO_COMMIT_STATE_NORMAL = 0,
+ OSTREE_REPO_COMMIT_STATE_PARTIAL = (1 << 0),
+ OSTREE_REPO_COMMIT_STATE_FSCK_PARTIAL = (1 << 1),
+} OstreeRepoCommitState;
+
+/**
* OstreeRepoTransactionStats:
* @metadata_objects_total: The total number of metadata objects
* in the repository after this transaction has completed.
@@ -316,6 +336,13 @@ gboolean ostree_repo_mark_commit_partial (OstreeRepo *self,
GError **error);
_OSTREE_PUBLIC
+gboolean ostree_repo_mark_commit_partial_reason (OstreeRepo *self,
+ const char *checksum,
+ gboolean is_partial,
+ OstreeRepoCommitState in_state,
+ GError **error);
+
+_OSTREE_PUBLIC
void ostree_repo_transaction_set_refspec (OstreeRepo *self,
const char *refspec,
const char *checksum);
@@ -526,23 +553,6 @@ gboolean ostree_repo_load_variant_if_exists (OstreeRepo *self,
GVariant **out_variant,
GError **error);
-/**
- * OstreeRepoCommitState:
- * @OSTREE_REPO_COMMIT_STATE_NORMAL: Commit is complete. This is the default.
- * (Since: 2017.14.)
- * @OSTREE_REPO_COMMIT_STATE_PARTIAL: One or more objects are missing from the
- * local copy of the commit, but metadata is present. (Since: 2015.7.)
- *
- * Flags representing the state of a commit in the local repository, as returned
- * by ostree_repo_load_commit().
- *
- * Since: 2015.7
- */
-typedef enum {
- OSTREE_REPO_COMMIT_STATE_NORMAL = 0,
- OSTREE_REPO_COMMIT_STATE_PARTIAL = (1 << 0),
-} OstreeRepoCommitState;
-
_OSTREE_PUBLIC
gboolean ostree_repo_load_commit (OstreeRepo *self,
const char *checksum,
diff --git a/src/ostree/ot-builtin-fsck.c b/src/ostree/ot-builtin-fsck.c
index a7ecd3d0..44e98a76 100644
--- a/src/ostree/ot-builtin-fsck.c
+++ b/src/ostree/ot-builtin-fsck.c
@@ -127,7 +127,7 @@ fsck_one_object (OstreeRepo *repo,
if ((state & OSTREE_REPO_COMMIT_STATE_PARTIAL) == 0)
{
g_printerr ("Marking commit as partial: %s\n", parent_commit);
- if (!ostree_repo_mark_commit_partial (repo, parent_commit, TRUE, error))
+ if (!ostree_repo_mark_commit_partial_reason (repo, parent_commit, TRUE, OSTREE_REPO_COMMIT_STATE_FSCK_PARTIAL, error))
return FALSE;
}
}
@@ -302,6 +302,7 @@ ostree_builtin_fsck (int argc, char **argv, OstreeCommandInvocation *invocation,
opt_verify_bindings = TRUE;
guint n_partial = 0;
+ guint n_fsck_partial = 0;
g_hash_table_iter_init (&hash_iter, objects);
while (g_hash_table_iter_next (&hash_iter, &key, &value))
{
@@ -410,7 +411,11 @@ ostree_builtin_fsck (int argc, char **argv, OstreeCommandInvocation *invocation,
}
if (commitstate & OSTREE_REPO_COMMIT_STATE_PARTIAL)
- n_partial++;
+ {
+ n_partial++;
+ if (commitstate & OSTREE_REPO_COMMIT_STATE_FSCK_PARTIAL)
+ n_fsck_partial++;
+ }
else
g_hash_table_add (commits, g_variant_ref (serialized_key));
}
@@ -450,5 +455,8 @@ ostree_builtin_fsck (int argc, char **argv, OstreeCommandInvocation *invocation,
if (found_corruption)
return glnx_throw (error, "Repository corruption encountered");
+ if (n_fsck_partial > 0)
+ return glnx_throw (error, "%u fsck deleted partial commits not verified", n_partial);
+
return TRUE;
}