pack-write: lift and expose index-pack report parsing
Once git-index-pack(1) finishes writing a packfile, it reports the hexadecimal name of that packfile on stdout prefixed with either "pack" or "keep" depending on whether a ".keep" file was also created alongside it. Callers that are required to manage the lifecycle of ".keep" files parse this report via `index_pack_lockfile()`, which provides the path to the temporary ".keep" file. In a subsequent commit, the "files" ODB transaction begins creating the pack lockfiles during transaction commit instead of eagerly staging them in the transaction quarantine directory with the packfile. Extract the generic parsing logic for the git-index-pack(1) output into `read_index_pack_report()` in preparation for recording the names of newly written packfiles. Signed-off-by: Justin Tobler <jltobler@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
1 parent
5e106cb22b
commit
21bb64feef
2 files changed
+51
-15
No files matched your search
+41
-15
@@ -469,11 +469,16 @@ void fixup_pack_header_footer(const struct git_hash_algo *hash_algo,
|
||||
fsync_component_or_die(FSYNC_COMPONENT_PACK, pack_fd, pack_name);
|
||||
}
|
||||
|
||||
char *index_pack_lockfile(struct odb_source *source, int ip_out,
|
||||
int *is_well_formed)
|
||||
int read_index_pack_report(struct repository *repo, int ip_out,
|
||||
struct strbuf *pack_name, int *is_keep)
|
||||
{
|
||||
const int len = repo->hash_algo->hexsz + 6;
|
||||
char packname[GIT_MAX_HEXSZ + 6];
|
||||
const int len = source->odb->repo->hash_algo->hexsz + 6;
|
||||
int is_keep_ignored;
|
||||
const char *name;
|
||||
|
||||
if (!is_keep)
|
||||
is_keep = &is_keep_ignored;
|
||||
|
||||
/*
|
||||
* The first thing we expect from index-pack's output is
|
||||
@@ -482,24 +487,45 @@ char *index_pack_lockfile(struct odb_source *source, int ip_out,
|
||||
* bytes of prefix, `hexsz` bytes of name, and a trailing newline. A
|
||||
* "keep" prefix tells us that index-pack has also created the
|
||||
* corresponding ".keep" file.
|
||||
*
|
||||
* In the "keep" case, we need it to remove the corresponding ".keep"
|
||||
* file later on. If we don't get that then tough luck with it.
|
||||
*/
|
||||
if (read_in_full(ip_out, packname, len) == len && packname[len-1] == '\n') {
|
||||
const char *name;
|
||||
if (read_in_full(ip_out, packname, len) != len || packname[len - 1] != '\n')
|
||||
return -1;
|
||||
|
||||
packname[len - 1] = 0;
|
||||
if (skip_prefix(packname, "pack\t", &name))
|
||||
*is_keep = 0;
|
||||
else if (skip_prefix(packname, "keep\t", &name))
|
||||
*is_keep = 1;
|
||||
else
|
||||
return -1;
|
||||
|
||||
strbuf_addstr(pack_name, name);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
char *index_pack_lockfile(struct odb_source *source, int ip_out,
|
||||
int *is_well_formed)
|
||||
{
|
||||
struct strbuf pack_name = STRBUF_INIT;
|
||||
char *lockfile = NULL;
|
||||
int is_keep = 0;
|
||||
|
||||
if (read_index_pack_report(source->odb->repo, ip_out, &pack_name, &is_keep)) {
|
||||
if (is_well_formed)
|
||||
*is_well_formed = 1;
|
||||
packname[len-1] = 0;
|
||||
if (skip_prefix(packname, "keep\t", &name))
|
||||
return xstrfmt("%s/pack/pack-%s.keep",
|
||||
source->path, name);
|
||||
*is_well_formed = 0;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (is_well_formed)
|
||||
*is_well_formed = 0;
|
||||
return NULL;
|
||||
*is_well_formed = 1;
|
||||
|
||||
/* If there is no ".keep" file, then there is no lockfile to return. */
|
||||
if (is_keep)
|
||||
lockfile = xstrfmt("%s/pack/pack-%s.keep", source->path, pack_name.buf);
|
||||
|
||||
strbuf_release(&pack_name);
|
||||
return lockfile;
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -106,6 +106,16 @@ off_t write_pack_header(struct hashfile *f, uint32_t);
|
||||
void fixup_pack_header_footer(const struct git_hash_algo *, int,
|
||||
unsigned char *, const char *, uint32_t,
|
||||
unsigned char *, off_t);
|
||||
|
||||
/*
|
||||
* Read the report that git-index-pack(1) writes to its standard output after
|
||||
* the packfile is written. The hexadecimal name of the packfile is appended to
|
||||
* `pack_name` and, if `is_keep` is non-NULL, it is set to indicate whether a
|
||||
* ".keep" file was written. Return 0 on success and a negative error code on
|
||||
* failure.
|
||||
*/
|
||||
int read_index_pack_report(struct repository *repo, int ip_out,
|
||||
struct strbuf *pack_name, int *is_keep);
|
||||
char *index_pack_lockfile(struct odb_source *source, int fd,
|
||||
int *is_well_formed);
|
||||
|
||||
|
||||
Reference in new issue
Block a user