summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorBen Straub <bs@github.com>2012-10-08 15:25:44 -0700
committerBen Straub <bs@github.com>2012-10-08 15:25:44 -0700
commit9adfa7d147b319593789cbaeea94a97141b1e4f8 (patch)
treebd9a22164040adc03d389aa101e9d480cb2ce775 /src
parent543864b677704845660085d2b2b2249cabb084a4 (diff)
parentbf0e62a2b8b6116ae61dae37f95a3eb840246ec6 (diff)
downloadlibgit2-9adfa7d147b319593789cbaeea94a97141b1e4f8.tar.gz
Merge pull request #949 from nulltoken/topic/deploy_repository_set_head
Deploy git_repository_set_head()
Diffstat (limited to 'src')
-rw-r--r--src/branch.c50
-rw-r--r--src/clone.c283
-rw-r--r--src/refs.c31
-rw-r--r--src/refspec.c18
-rw-r--r--src/refspec.h11
-rw-r--r--src/remote.h2
-rw-r--r--src/repository.c11
-rw-r--r--src/reset.c7
-rw-r--r--src/revparse.c12
-rw-r--r--src/submodule.c4
10 files changed, 292 insertions, 137 deletions
diff --git a/src/branch.c b/src/branch.c
index 103dfe621..6d497b055 100644
--- a/src/branch.c
+++ b/src/branch.c
@@ -92,7 +92,7 @@ cleanup:
int git_branch_delete(git_reference *branch)
{
- git_reference *head = NULL;
+ int is_head;
assert(branch);
@@ -102,27 +102,16 @@ int git_branch_delete(git_reference *branch)
return -1;
}
- if (git_reference_lookup(&head, git_reference_owner(branch), GIT_HEAD_FILE) < 0) {
- giterr_set(GITERR_REFERENCE, "Cannot locate HEAD.");
- goto on_error;
- }
+ if ((is_head = git_branch_is_head(branch)) < 0)
+ return is_head;
- if ((git_reference_type(head) == GIT_REF_SYMBOLIC)
- && (strcmp(git_reference_target(head), git_reference_name(branch)) == 0)) {
- giterr_set(GITERR_REFERENCE,
- "Cannot delete branch '%s' as it is the current HEAD of the repository.", git_reference_name(branch));
- goto on_error;
+ if (is_head) {
+ giterr_set(GITERR_REFERENCE,
+ "Cannot delete branch '%s' as it is the current HEAD of the repository.", git_reference_name(branch));
+ return -1;
}
- if (git_reference_delete(branch) < 0)
- goto on_error;
-
- git_reference_free(head);
- return 0;
-
-on_error:
- git_reference_free(head);
- return -1;
+ return git_reference_delete(branch);
}
typedef struct {
@@ -271,3 +260,26 @@ cleanup:
git_buf_free(&buf);
return error;
}
+
+int git_branch_is_head(
+ git_reference *branch)
+{
+ git_reference *head;
+ bool is_same = false;
+
+ assert(branch);
+
+ if (!git_reference_is_branch(branch))
+ return false;
+
+ if (git_repository_head(&head, git_reference_owner(branch)) < 0)
+ return -1;
+
+ is_same = strcmp(
+ git_reference_name(branch),
+ git_reference_name(head)) == 0;
+
+ git_reference_free(head);
+
+ return is_same;
+}
diff --git a/src/clone.c b/src/clone.c
index 80a13d0f2..a5f4867db 100644
--- a/src/clone.c
+++ b/src/clone.c
@@ -22,112 +22,219 @@
#include "refs.h"
#include "path.h"
-struct HeadInfo {
- git_repository *repo;
- git_oid remote_head_oid;
- git_buf branchname;
-};
-
-static int create_tracking_branch(git_repository *repo, const git_oid *target, const char *name)
+static int create_branch(
+ git_reference **branch,
+ git_repository *repo,
+ const git_oid *target,
+ const char *name)
{
git_object *head_obj = NULL;
git_reference *branch_ref;
- int retcode = GIT_ERROR;
+ int error;
/* Find the target commit */
- if (git_object_lookup(&head_obj, repo, target, GIT_OBJ_ANY) < 0)
- return GIT_ERROR;
+ if ((error = git_object_lookup(&head_obj, repo, target, GIT_OBJ_ANY)) < 0)
+ return error;
/* Create the new branch */
- if (!git_branch_create(&branch_ref, repo, name, head_obj, 0)) {
- git_config *cfg;
+ error = git_branch_create(&branch_ref, repo, name, head_obj, 0);
+ git_object_free(head_obj);
+
+ if (!error)
+ *branch = branch_ref;
+ else
git_reference_free(branch_ref);
- /* Set up tracking */
- if (!git_repository_config(&cfg, repo)) {
- git_buf remote = GIT_BUF_INIT;
- git_buf merge = GIT_BUF_INIT;
- git_buf merge_target = GIT_BUF_INIT;
- if (!git_buf_printf(&remote, "branch.%s.remote", name) &&
- !git_buf_printf(&merge, "branch.%s.merge", name) &&
- !git_buf_printf(&merge_target, "refs/heads/%s", name) &&
- !git_config_set_string(cfg, git_buf_cstr(&remote), "origin") &&
- !git_config_set_string(cfg, git_buf_cstr(&merge), git_buf_cstr(&merge_target))) {
- retcode = 0;
- }
- git_buf_free(&remote);
- git_buf_free(&merge);
- git_buf_free(&merge_target);
- git_config_free(cfg);
- }
- }
- git_object_free(head_obj);
- return retcode;
+ return error;
}
-static int reference_matches_remote_head(const char *head_name, void *payload)
+static int setup_tracking_config(
+ git_repository *repo,
+ const char *branch_name,
+ const char *remote_name,
+ const char *merge_target)
{
- struct HeadInfo *head_info = (struct HeadInfo *)payload;
+ git_config *cfg;
+ git_buf remote_key = GIT_BUF_INIT, merge_key = GIT_BUF_INIT;
+ int error = -1;
+
+ if (git_repository_config__weakptr(&cfg, repo) < 0)
+ return -1;
+
+ if (git_buf_printf(&remote_key, "branch.%s.remote", branch_name) < 0)
+ goto cleanup;
+
+ if (git_buf_printf(&merge_key, "branch.%s.merge", branch_name) < 0)
+ goto cleanup;
+
+ if (git_config_set_string(cfg, git_buf_cstr(&remote_key), remote_name) < 0)
+ goto cleanup;
+
+ if (git_config_set_string(cfg, git_buf_cstr(&merge_key), merge_target) < 0)
+ goto cleanup;
+
+ error = 0;
+
+cleanup:
+ git_buf_free(&remote_key);
+ git_buf_free(&merge_key);
+ return error;
+}
+
+static int create_tracking_branch(
+ git_reference **branch,
+ git_repository *repo,
+ const git_oid *target,
+ const char *branch_name)
+{
+ int error;
+
+ if ((error = create_branch(branch, repo, target, branch_name)) < 0)
+ return error;
+
+ return setup_tracking_config(
+ repo,
+ branch_name,
+ GIT_REMOTE_ORIGIN,
+ git_reference_name(*branch));
+}
+
+struct head_info {
+ git_repository *repo;
+ git_oid remote_head_oid;
+ git_buf branchname;
+ const git_refspec *refspec;
+};
+
+static int reference_matches_remote_head(
+ const char *reference_name,
+ void *payload)
+{
+ struct head_info *head_info = (struct head_info *)payload;
git_oid oid;
+ /* TODO: Should we guard against references
+ * which name doesn't start with refs/heads/ ?
+ */
+
/* Stop looking if we've already found a match */
- if (git_buf_len(&head_info->branchname) > 0) return 0;
+ if (git_buf_len(&head_info->branchname) > 0)
+ return 0;
+
+ if (git_reference_name_to_oid(
+ &oid,
+ head_info->repo,
+ reference_name) < 0) {
+ /* TODO: How to handle not found references?
+ */
+ return -1;
+ }
- if (!git_reference_name_to_oid(&oid, head_info->repo, head_name) &&
- !git_oid_cmp(&head_info->remote_head_oid, &oid)) {
- git_buf_puts(&head_info->branchname,
- head_name+strlen("refs/remotes/origin/"));
+ if (git_oid_cmp(&head_info->remote_head_oid, &oid) == 0) {
+ /* Determine the local reference name from the remote tracking one */
+ if (git_refspec_transform_l(
+ &head_info->branchname,
+ head_info->refspec,
+ reference_name) < 0)
+ return -1;
+
+ if (git_buf_sets(
+ &head_info->branchname,
+ git_buf_cstr(&head_info->branchname) + strlen(GIT_REFS_HEADS_DIR)) < 0)
+ return -1;
}
+
return 0;
}
-static int update_head_to_new_branch(git_repository *repo, const git_oid *target, const char *name)
+static int update_head_to_new_branch(
+ git_repository *repo,
+ const git_oid *target,
+ const char *name)
{
- int retcode = GIT_ERROR;
+ git_reference *tracking_branch;
+ int error;
- if (!create_tracking_branch(repo, target, name)) {
- git_reference *head;
- if (!git_reference_lookup(&head, repo, GIT_HEAD_FILE)) {
- git_buf targetbuf = GIT_BUF_INIT;
- if (!git_buf_printf(&targetbuf, "refs/heads/%s", name)) {
- retcode = git_reference_set_target(head, git_buf_cstr(&targetbuf));
- }
- git_buf_free(&targetbuf);
- git_reference_free(head);
- }
- }
+ if ((error = create_tracking_branch(
+ &tracking_branch,
+ repo,
+ target,
+ name)) < 0)
+ return error;
- return retcode;
+ error = git_repository_set_head(repo, git_reference_name(tracking_branch));
+
+ git_reference_free(tracking_branch);
+
+ return error;
}
static int update_head_to_remote(git_repository *repo, git_remote *remote)
{
- int retcode = GIT_ERROR;
+ int retcode = -1;
git_remote_head *remote_head;
- git_oid oid;
- struct HeadInfo head_info;
+ struct head_info head_info;
+ git_buf remote_master_name = GIT_BUF_INIT;
+
+ /* Did we just clone an empty repository? */
+ if (remote->refs.length == 0) {
+ return setup_tracking_config(
+ repo,
+ "master",
+ GIT_REMOTE_ORIGIN,
+ GIT_REFS_HEADS_MASTER_FILE);
+ }
/* Get the remote's HEAD. This is always the first ref in remote->refs. */
remote_head = remote->refs.contents[0];
git_oid_cpy(&head_info.remote_head_oid, &remote_head->oid);
git_buf_init(&head_info.branchname, 16);
head_info.repo = repo;
-
- /* Check to see if "master" matches the remote head */
- if (!git_reference_name_to_oid(&oid, repo, "refs/remotes/origin/master") &&
- !git_oid_cmp(&remote_head->oid, &oid)) {
- retcode = update_head_to_new_branch(repo, &oid, "master");
+ head_info.refspec = git_remote_fetchspec(remote);
+
+ /* Determine the remote tracking reference name from the local master */
+ if (git_refspec_transform_r(
+ &remote_master_name,
+ head_info.refspec,
+ GIT_REFS_HEADS_MASTER_FILE) < 0)
+ return -1;
+
+ /* Check to see if the remote HEAD points to the remote master */
+ if (reference_matches_remote_head(git_buf_cstr(&remote_master_name), &head_info) < 0)
+ goto cleanup;
+
+ if (git_buf_len(&head_info.branchname) > 0) {
+ retcode = update_head_to_new_branch(
+ repo,
+ &head_info.remote_head_oid,
+ git_buf_cstr(&head_info.branchname));
+
+ goto cleanup;
}
+
/* Not master. Check all the other refs. */
- else if (!git_reference_foreach(repo, GIT_REF_LISTALL,
- reference_matches_remote_head,
- &head_info) &&
- git_buf_len(&head_info.branchname) > 0) {
- retcode = update_head_to_new_branch(repo, &head_info.remote_head_oid,
- git_buf_cstr(&head_info.branchname));
+ if (git_reference_foreach(
+ repo,
+ GIT_REF_LISTALL,
+ reference_matches_remote_head,
+ &head_info) < 0)
+ goto cleanup;
+
+ if (git_buf_len(&head_info.branchname) > 0) {
+ retcode = update_head_to_new_branch(
+ repo,
+ &head_info.remote_head_oid,
+ git_buf_cstr(&head_info.branchname));
+
+ goto cleanup;
+ } else {
+ /* TODO: What should we do if nothing has been found?
+ */
}
+cleanup:
+ git_buf_free(&remote_master_name);
git_buf_free(&head_info.branchname);
return retcode;
}
@@ -150,7 +257,7 @@ static int setup_remotes_and_fetch(git_repository *repo,
if (!fetch_stats) fetch_stats = &dummy_stats;
/* Create the "origin" remote */
- if (!git_remote_add(&origin, repo, "origin", origin_url)) {
+ if (!git_remote_add(&origin, repo, GIT_REMOTE_ORIGIN, origin_url)) {
/* Connect and download everything */
if (!git_remote_connect(origin, GIT_DIR_FETCH)) {
if (!git_remote_download(origin, &bytes, fetch_stats)) {
@@ -184,11 +291,14 @@ static bool path_is_okay(const char *path)
}
-static int clone_internal(git_repository **out,
- const char *origin_url,
- const char *path,
- git_indexer_stats *fetch_stats,
- int is_bare)
+static int clone_internal(
+ git_repository **out,
+ const char *origin_url,
+ const char *path,
+ git_indexer_stats *fetch_stats,
+ git_indexer_stats *checkout_stats,
+ git_checkout_opts *checkout_opts,
+ int is_bare)
{
int retcode = GIT_ERROR;
git_repository *repo = NULL;
@@ -211,6 +321,9 @@ static int clone_internal(git_repository **out,
}
}
+ if (!retcode && !is_bare && !git_repository_head_orphan(repo))
+ retcode = git_checkout_head(*out, checkout_opts, checkout_stats);
+
return retcode;
}
@@ -220,7 +333,15 @@ int git_clone_bare(git_repository **out,
git_indexer_stats *fetch_stats)
{
assert(out && origin_url && dest_path);
- return clone_internal(out, origin_url, dest_path, fetch_stats, 1);
+
+ return clone_internal(
+ out,
+ origin_url,
+ dest_path,
+ fetch_stats,
+ NULL,
+ NULL,
+ 1);
}
@@ -231,12 +352,14 @@ int git_clone(git_repository **out,
git_indexer_stats *checkout_stats,
git_checkout_opts *checkout_opts)
{
- int retcode = GIT_ERROR;
-
assert(out && origin_url && workdir_path);
- if (!(retcode = clone_internal(out, origin_url, workdir_path, fetch_stats, 0)))
- retcode = git_checkout_head(*out, checkout_opts, checkout_stats);
-
- return retcode;
+ return clone_internal(
+ out,
+ origin_url,
+ workdir_path,
+ fetch_stats,
+ checkout_stats,
+ checkout_opts,
+ 0);
}
diff --git a/src/refs.c b/src/refs.c
index bd6fbee0e..9dc422e1b 100644
--- a/src/refs.c
+++ b/src/refs.c
@@ -15,6 +15,7 @@
#include <git2/tag.h>
#include <git2/object.h>
#include <git2/oid.h>
+#include <git2/branch.h>
GIT__USE_STRMAP;
@@ -1343,9 +1344,7 @@ int git_reference_rename(git_reference *ref, const char *new_name, int force)
unsigned int normalization_flags;
git_buf aux_path = GIT_BUF_INIT;
char normalized[GIT_REFNAME_MAX];
-
- const char *head_target = NULL;
- git_reference *head = NULL;
+ bool should_head_be_updated = false;
normalization_flags = ref->flags & GIT_REF_SYMBOLIC ?
GIT_REF_FORMAT_ALLOW_ONELEVEL
@@ -1367,6 +1366,12 @@ int git_reference_rename(git_reference *ref, const char *new_name, int force)
return -1;
/*
+ * Check if we have to update HEAD.
+ */
+ if ((should_head_be_updated = git_branch_is_head(ref)) < 0)
+ goto cleanup;
+
+ /*
* Now delete the old ref and remove an possibly existing directory
* named `new_name`. Note that using the internal `reference_delete`
* method deletes the ref from disk but doesn't free the pointer, so
@@ -1390,25 +1395,13 @@ int git_reference_rename(git_reference *ref, const char *new_name, int force)
goto rollback;
/*
- * Check if we have to update HEAD.
+ * Update HEAD it was poiting to the reference being renamed.
*/
- if (git_reference_lookup(&head, ref->owner, GIT_HEAD_FILE) < 0) {
- giterr_set(GITERR_REFERENCE,
- "Failed to update HEAD after renaming reference");
- goto cleanup;
- }
-
- head_target = git_reference_target(head);
-
- if (head_target && !strcmp(head_target, ref->name)) {
- git_reference_free(head);
- head = NULL;
-
- if (git_reference_create_symbolic(&head, ref->owner, "HEAD", new_name, 1) < 0) {
+ if (should_head_be_updated &&
+ git_repository_set_head(ref->owner, new_name) < 0) {
giterr_set(GITERR_REFERENCE,
"Failed to update HEAD after renaming reference");
goto cleanup;
- }
}
/*
@@ -1426,12 +1419,10 @@ int git_reference_rename(git_reference *ref, const char *new_name, int force)
/* The reference is no longer packed */
ref->flags &= ~GIT_REF_PACKED;
- git_reference_free(head);
git_buf_free(&aux_path);
return 0;
cleanup:
- git_reference_free(head);
git_buf_free(&aux_path);
return -1;
diff --git a/src/refspec.c b/src/refspec.c
index cd3a528bd..b1790b32c 100644
--- a/src/refspec.c
+++ b/src/refspec.c
@@ -194,20 +194,20 @@ int git_refspec_transform(char *out, size_t outlen, const git_refspec *spec, con
return 0;
}
-int git_refspec_transform_r(git_buf *out, const git_refspec *spec, const char *name)
+static int refspec_transform(git_buf *out, const char *from, const char *to, const char *name)
{
- if (git_buf_sets(out, spec->dst) < 0)
+ if (git_buf_sets(out, to) < 0)
return -1;
/*
- * No '*' at the end means that it's mapped to one specific local
+ * No '*' at the end means that it's mapped to one specific
* branch, so no actual transformation is needed.
*/
if (git_buf_len(out) > 0 && out->ptr[git_buf_len(out) - 1] != '*')
return 0;
git_buf_truncate(out, git_buf_len(out) - 1); /* remove trailing '*' */
- git_buf_puts(out, name + strlen(spec->src) - 1);
+ git_buf_puts(out, name + strlen(from) - 1);
if (git_buf_oom(out))
return -1;
@@ -215,3 +215,13 @@ int git_refspec_transform_r(git_buf *out, const git_refspec *spec, const char *n
return 0;
}
+int git_refspec_transform_r(git_buf *out, const git_refspec *spec, const char *name)
+{
+ return refspec_transform(out, spec->src, spec->dst, name);
+}
+
+int git_refspec_transform_l(git_buf *out, const git_refspec *spec, const char *name)
+{
+ return refspec_transform(out, spec->dst, spec->src, name);
+}
+
diff --git a/src/refspec.h b/src/refspec.h
index a5df458c6..6e0596a55 100644
--- a/src/refspec.h
+++ b/src/refspec.h
@@ -40,4 +40,15 @@ void git_refspec__free(git_refspec *refspec);
*/
int git_refspec_transform_r(git_buf *out, const git_refspec *spec, const char *name);
+/**
+ * Transform a reference from its target following the refspec's rules,
+ * and writes the results into a git_buf.
+ *
+ * @param out where to store the source name
+ * @param spec the refspec
+ * @param name the name of the reference to transform
+ * @return 0 or error if buffer allocation fails
+ */
+int git_refspec_transform_l(git_buf *out, const git_refspec *spec, const char *name);
+
#endif
diff --git a/src/remote.h b/src/remote.h
index b8bb2c55d..05073db8c 100644
--- a/src/remote.h
+++ b/src/remote.h
@@ -13,6 +13,8 @@
#include "transport.h"
#include "repository.h"
+#define GIT_REMOTE_ORIGIN "origin"
+
struct git_remote {
char *name;
char *url;
diff --git a/src/repository.c b/src/repository.c
index 1a46db0a5..1b49228fb 100644
--- a/src/repository.c
+++ b/src/repository.c
@@ -19,6 +19,7 @@
#include "refs.h"
#include "filter.h"
#include "odb.h"
+#include "remote.h"
#define GIT_FILE_CONTENT_PREFIX "gitdir:"
@@ -654,10 +655,10 @@ static int repo_init_create_head(const char *git_dir, const char *ref_name)
if (!ref_name)
ref_name = GIT_BRANCH_MASTER;
- if (git__prefixcmp(ref_name, "refs/") == 0)
+ if (git__prefixcmp(ref_name, GIT_REFS_DIR) == 0)
fmt = "ref: %s\n";
else
- fmt = "ref: refs/heads/%s\n";
+ fmt = "ref: " GIT_REFS_HEADS_DIR "%s\n";
if (git_filebuf_printf(&ref, fmt, ref_name) < 0 ||
git_filebuf_commit(&ref, GIT_REFS_FILE_MODE) < 0)
@@ -1095,7 +1096,7 @@ static int repo_init_create_origin(git_repository *repo, const char *url)
int error;
git_remote *remote;
- if (!(error = git_remote_add(&remote, repo, "origin", url))) {
+ if (!(error = git_remote_add(&remote, repo, GIT_REMOTE_ORIGIN, url))) {
error = git_remote_save(remote);
git_remote_free(remote);
}
@@ -1219,7 +1220,7 @@ int git_repository_is_empty(git_repository *repo)
git_reference *head = NULL, *branch = NULL;
int error;
- if (git_reference_lookup(&head, repo, "HEAD") < 0)
+ if (git_reference_lookup(&head, repo, GIT_HEAD_FILE) < 0)
return -1;
if (git_reference_type(head) != GIT_REF_SYMBOLIC) {
@@ -1227,7 +1228,7 @@ int git_repository_is_empty(git_repository *repo)
return 0;
}
- if (strcmp(git_reference_target(head), "refs/heads/master") != 0) {
+ if (strcmp(git_reference_target(head), GIT_REFS_HEADS_DIR "master") != 0) {
git_reference_free(head);
return 0;
}
diff --git a/src/reset.c b/src/reset.c
index 4ce21e2cf..c536e75b8 100644
--- a/src/reset.c
+++ b/src/reset.c
@@ -29,6 +29,7 @@ int git_reset(
git_tree *tree = NULL;
int error = -1;
git_checkout_opts opts;
+ git_reference *head = NULL;
assert(repo && target);
assert(reset_type == GIT_RESET_SOFT
@@ -49,7 +50,10 @@ int git_reset(
//TODO: Check for unmerged entries
- if (git_reference__update(repo, git_object_id(commit), GIT_HEAD_FILE) < 0)
+ if (git_repository_head(&head, repo) < 0)
+ goto cleanup;
+
+ if (git_reference_set_oid(head, git_object_id(commit)) < 0)
goto cleanup;
if (reset_type == GIT_RESET_SOFT) {
@@ -96,6 +100,7 @@ int git_reset(
error = 0;
cleanup:
+ git_reference_free(head);
git_object_free(commit);
git_index_free(index);
git_tree_free(tree);
diff --git a/src/revparse.c b/src/revparse.c
index 5e2db99cd..191f6374c 100644
--- a/src/revparse.c
+++ b/src/revparse.c
@@ -28,11 +28,11 @@ static int disambiguate_refname(git_reference **out, git_repository *repo, const
static const char* formatters[] = {
"%s",
- "refs/%s",
- "refs/tags/%s",
- "refs/heads/%s",
- "refs/remotes/%s",
- "refs/remotes/%s/HEAD",
+ GIT_REFS_DIR "%s",
+ GIT_REFS_TAGS_DIR "%s",
+ GIT_REFS_HEADS_DIR "%s",
+ GIT_REFS_REMOTES_DIR "%s",
+ GIT_REFS_REMOTES_DIR "%s/" GIT_HEAD_FILE,
NULL
};
@@ -520,7 +520,7 @@ static int handle_grep_syntax(git_object **out, git_repository *repo, const git_
if (spec_oid == NULL) {
// TODO: @carlosmn: The glob should be refs/* but this makes git_revwalk_next() fails
- if (git_revwalk_push_glob(walk, "refs/heads/*") < 0)
+ if (git_revwalk_push_glob(walk, GIT_REFS_HEADS_DIR "*") < 0)
goto cleanup;
} else if (git_revwalk_push(walk, spec_oid) < 0)
goto cleanup;
diff --git a/src/submodule.c b/src/submodule.c
index a2162496a..180528641 100644
--- a/src/submodule.c
+++ b/src/submodule.c
@@ -1315,7 +1315,7 @@ static int lookup_head_remote(git_buf *url, git_repository *repo)
/* remote should refer to something like refs/remotes/ORIGIN/BRANCH */
if (git_reference_type(remote) != GIT_REF_SYMBOLIC ||
- git__prefixcmp(git_reference_target(remote), "refs/remotes/") != 0)
+ git__prefixcmp(git_reference_target(remote), GIT_REFS_REMOTES_DIR) != 0)
{
giterr_set(GITERR_SUBMODULE,
"Cannot resolve relative URL when HEAD is not symbolic");
@@ -1323,7 +1323,7 @@ static int lookup_head_remote(git_buf *url, git_repository *repo)
goto cleanup;
}
- scan = tgt = git_reference_target(remote) + strlen("refs/remotes/");
+ scan = tgt = git_reference_target(remote) + strlen(GIT_REFS_REMOTES_DIR);
while (*scan && (*scan != '/' || (scan > tgt && scan[-1] != '\\')))
scan++; /* find non-escaped slash to end ORIGIN name */