aboutsummaryrefslogtreecommitdiffstats
path: root/refs.c
diff options
context:
space:
mode:
Diffstat (limited to 'refs.c')
-rw-r--r--refs.c57
1 files changed, 37 insertions, 20 deletions
diff --git a/refs.c b/refs.c
index bb90a18875..74de3d3009 100644
--- a/refs.c
+++ b/refs.c
@@ -2,8 +2,6 @@
* The backend-independent part of the reference module.
*/
-#define USE_THE_REPOSITORY_VARIABLE
-
#include "git-compat-util.h"
#include "advice.h"
#include "config.h"
@@ -318,6 +316,11 @@ int check_refname_format(const char *refname, int flags)
return check_or_sanitize_refname(refname, flags, NULL);
}
+int refs_fsck(struct ref_store *refs, struct fsck_options *o)
+{
+ return refs->be->fsck(refs, o);
+}
+
void sanitize_refname_component(const char *refname, struct strbuf *out)
{
if (check_or_sanitize_refname(refname, REFNAME_ALLOW_ONELEVEL, out))
@@ -414,7 +417,7 @@ int refs_ref_exists(struct ref_store *refs, const char *refname)
NULL, NULL);
}
-static int for_each_filter_refs(const char *refname,
+static int for_each_filter_refs(const char *refname, const char *referent,
const struct object_id *oid,
int flags, void *data)
{
@@ -424,7 +427,7 @@ static int for_each_filter_refs(const char *refname,
return 0;
if (filter->prefix)
skip_prefix(refname, filter->prefix, &refname);
- return filter->fn(refname, oid, flags, filter->cb_data);
+ return filter->fn(refname, referent, oid, flags, filter->cb_data);
}
struct warn_if_dangling_data {
@@ -435,7 +438,7 @@ struct warn_if_dangling_data {
const char *msg_fmt;
};
-static int warn_if_dangling_symref(const char *refname,
+static int warn_if_dangling_symref(const char *refname, const char *referent UNUSED,
const struct object_id *oid UNUSED,
int flags, void *cb_data)
{
@@ -506,7 +509,7 @@ int refs_head_ref_namespaced(struct ref_store *refs, each_ref_fn fn, void *cb_da
strbuf_addf(&buf, "%sHEAD", get_git_namespace());
if (!refs_read_ref_full(refs, buf.buf, RESOLVE_REF_READING, &oid, &flag))
- ret = fn(buf.buf, &oid, flag, cb_data);
+ ret = fn(buf.buf, NULL, &oid, flag, cb_data);
strbuf_release(&buf);
return ret;
@@ -1547,7 +1550,7 @@ int refs_head_ref(struct ref_store *refs, each_ref_fn fn, void *cb_data)
if (refs_resolve_ref_unsafe(refs, "HEAD", RESOLVE_REF_READING,
&oid, &flag))
- return fn("HEAD", &oid, flag, cb_data);
+ return fn("HEAD", NULL, &oid, flag, cb_data);
return 0;
}
@@ -1754,8 +1757,8 @@ static int refs_read_special_head(struct ref_store *ref_store,
goto done;
}
- result = parse_loose_ref_contents(content.buf, oid, referent, type,
- failure_errno);
+ result = parse_loose_ref_contents(ref_store->repo->hash_algo, content.buf,
+ oid, referent, type, failure_errno);
done:
strbuf_release(&full_path);
@@ -1838,7 +1841,7 @@ const char *refs_resolve_ref_unsafe(struct ref_store *refs,
failure_errno != ENOTDIR)
return NULL;
- oidclr(oid, the_repository->hash_algo);
+ oidclr(oid, refs->repo->hash_algo);
if (*flags & REF_BAD_NAME)
*flags |= REF_ISBROKEN;
return refname;
@@ -1848,7 +1851,7 @@ const char *refs_resolve_ref_unsafe(struct ref_store *refs,
if (!(read_flags & REF_ISSYMREF)) {
if (*flags & REF_BAD_NAME) {
- oidclr(oid, the_repository->hash_algo);
+ oidclr(oid, refs->repo->hash_algo);
*flags |= REF_ISBROKEN;
}
return refname;
@@ -1856,7 +1859,7 @@ const char *refs_resolve_ref_unsafe(struct ref_store *refs,
refname = sb_refname.buf;
if (resolve_flags & RESOLVE_REF_NO_RECURSE) {
- oidclr(oid, the_repository->hash_algo);
+ oidclr(oid, refs->repo->hash_algo);
return refname;
}
if (check_refname_format(refname, REFNAME_ALLOW_ONELEVEL)) {
@@ -2011,7 +2014,7 @@ struct ref_store *repo_get_submodule_ref_store(struct repository *repo,
free(subrepo);
goto done;
}
- refs = ref_store_init(subrepo, the_repository->ref_storage_format,
+ refs = ref_store_init(subrepo, subrepo->ref_storage_format,
submodule_sb.buf,
REF_STORE_READ | REF_STORE_ODB);
register_ref_store_map(&repo->submodule_ref_stores, "submodule",
@@ -2045,7 +2048,7 @@ struct ref_store *get_worktree_ref_store(const struct worktree *wt)
common_path.buf, REF_STORE_ALL_CAPS);
strbuf_release(&common_path);
} else {
- refs = ref_store_init(wt->repo, the_repository->ref_storage_format,
+ refs = ref_store_init(wt->repo, wt->repo->ref_storage_format,
wt->repo->commondir, REF_STORE_ALL_CAPS);
}
@@ -2387,7 +2390,7 @@ struct do_for_each_reflog_help {
void *cb_data;
};
-static int do_for_each_reflog_helper(const char *refname,
+static int do_for_each_reflog_helper(const char *refname, const char *referent,
const struct object_id *oid UNUSED,
int flags,
void *cb_data)
@@ -2593,7 +2596,7 @@ struct migration_data {
struct strbuf *errbuf;
};
-static int migrate_one_ref(const char *refname, const struct object_id *oid,
+static int migrate_one_ref(const char *refname, const char *referent UNUSED, const struct object_id *oid,
int flags, void *cb_data)
{
struct migration_data *data = cb_data;
@@ -2844,6 +2847,14 @@ int repo_migrate_ref_storage_format(struct repository *repo,
}
/*
+ * Release the new ref store such that any potentially-open files will
+ * be closed. This is required for platforms like Cygwin, where
+ * renaming an open file results in EPERM.
+ */
+ ref_store_release(new_refs);
+ FREE_AND_NULL(new_refs);
+
+ /*
* Until now we were in the non-destructive phase, where we only
* populated the new ref store. From hereon though we are about
* to get hands by deleting the old ref store and then moving
@@ -2874,10 +2885,14 @@ int repo_migrate_ref_storage_format(struct repository *repo,
*/
initialize_repository_version(hash_algo_by_ptr(repo->hash_algo), format, 1);
- free(new_refs->gitdir);
- new_refs->gitdir = xstrdup(old_refs->gitdir);
- repo->refs_private = new_refs;
+ /*
+ * Unset the old ref store and release it. `get_main_ref_store()` will
+ * make sure to lazily re-initialize the repository's ref store with
+ * the new format.
+ */
ref_store_release(old_refs);
+ FREE_AND_NULL(old_refs);
+ repo->refs_private = NULL;
ret = 0;
@@ -2888,8 +2903,10 @@ done:
new_gitdir.buf);
}
- if (ret && new_refs)
+ if (new_refs) {
ref_store_release(new_refs);
+ free(new_refs);
+ }
ref_transaction_free(transaction);
strbuf_release(&new_gitdir);
return ret;