diff options
Diffstat (limited to 'builtin/branch.c')
-rw-r--r-- | builtin/branch.c | 25 |
1 files changed, 15 insertions, 10 deletions
diff --git a/builtin/branch.c b/builtin/branch.c index e1e486e4c5..7095718c13 100644 --- a/builtin/branch.c +++ b/builtin/branch.c @@ -104,6 +104,7 @@ static int branch_merged(int kind, const char *name, */ struct commit *reference_rev = NULL; const char *reference_name = NULL; + void *reference_name_to_free = NULL; int merged; if (kind == REF_LOCAL_BRANCH) { @@ -114,11 +115,9 @@ static int branch_merged(int kind, const char *name, branch->merge && branch->merge[0] && branch->merge[0]->dst && - (reference_name = - resolve_ref(branch->merge[0]->dst, sha1, 1, NULL)) != NULL) { - reference_name = xstrdup(reference_name); + (reference_name = reference_name_to_free = + resolve_refdup(branch->merge[0]->dst, sha1, 1, NULL)) != NULL) reference_rev = lookup_commit_reference(sha1); - } } if (!reference_rev) reference_rev = head_rev; @@ -143,7 +142,7 @@ static int branch_merged(int kind, const char *name, " '%s', even though it is merged to HEAD."), name, reference_name); } - free((char *)reference_name); + free(reference_name_to_free); return merged; } @@ -253,7 +252,7 @@ static char *resolve_symref(const char *src, const char *prefix) int flag; const char *dst, *cp; - dst = resolve_ref(src, sha1, 0, &flag); + dst = resolve_ref_unsafe(src, sha1, 0, &flag); if (!(dst && (flag & REF_ISSYMREF))) return NULL; if (prefix && (cp = skip_prefix(dst, prefix))) @@ -570,6 +569,7 @@ static void rename_branch(const char *oldname, const char *newname, int force) struct strbuf oldref = STRBUF_INIT, newref = STRBUF_INIT, logmsg = STRBUF_INIT; struct strbuf oldsection = STRBUF_INIT, newsection = STRBUF_INIT; int recovery = 0; + int clobber_head_ok; if (!oldname) die(_("cannot rename the current branch while not on any.")); @@ -585,7 +585,13 @@ static void rename_branch(const char *oldname, const char *newname, int force) die(_("Invalid branch name: '%s'"), oldname); } - validate_new_branchname(newname, &newref, force, 0); + /* + * A command like "git branch -M currentbranch currentbranch" cannot + * cause the worktree to become inconsistent with HEAD, so allow it. + */ + clobber_head_ok = !strcmp(oldname, newname); + + validate_new_branchname(newname, &newref, force, clobber_head_ok); strbuf_addf(&logmsg, "Branch: renamed %s to %s", oldref.buf, newref.buf); @@ -731,10 +737,9 @@ int cmd_branch(int argc, const char **argv, const char *prefix) track = git_branch_track; - head = resolve_ref("HEAD", head_sha1, 0, NULL); + head = resolve_refdup("HEAD", head_sha1, 0, NULL); if (!head) die(_("Failed to resolve HEAD as a valid ref.")); - head = xstrdup(head); if (!strcmp(head, "HEAD")) { detached = 1; } else { @@ -784,7 +789,7 @@ int cmd_branch(int argc, const char **argv, const char *prefix) if (kinds != REF_LOCAL_BRANCH) die(_("-a and -r options to 'git branch' do not make sense with a branch name")); create_branch(head, argv[0], (argc == 2) ? argv[1] : head, - force_create, reflog, track); + force_create, reflog, 0, track); } else usage_with_options(builtin_branch_usage, options); |