checkout: provide better conflict hunk description with detached HEAD

When running 'git checkout -m' and using diff3 style conflict markers, we want all the conflict hunks (left-side, "common" or "merge base", and right-side) to have label markers letting the user know where each came from. The "common" hunk label (o.ancestor) came from old_branch_info->name, but that is NULL when HEAD is detached, which resulted in a blank label. Check for that case and provide an abbreviated commit hash instead. (Incidentally, this was the only case in the git codebase where merge_trees() was called with opt->ancestor being NULL. A subsequent commit will prevent similar problems by enforcing that merge_trees() always be called with opt->ancestor != NULL.) Signed-off-by: Elijah Newren <newren@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>

Elijah Newren committed Aug 15, 2019 at 14:40 UTC 65c01c644250fb0a92f929c2fc61f33771bf480f
1 file changed +8
builtin/checkout.c
+8
@@ -713,6 +713,7 @@ static int merge_working_tree(const struct checkout_opts *opts,
713 struct tree *old_tree;
714 struct merge_options o;
715 struct strbuf sb = STRBUF_INIT;
716 + struct strbuf old_commit_shortname = STRBUF_INIT;
717
718 if (!opts->merge)
719 return 1;
@@ -768,6 +769,12 @@ static int merge_working_tree(const struct checkout_opts *opts,
769 if (ret)
770 return ret;
771 o.ancestor = old_branch_info->name;
772 + if (old_branch_info->name == NULL) {
773 + strbuf_add_unique_abbrev(&old_commit_shortname,
774 + &old_branch_info->commit->object.oid,
775 + DEFAULT_ABBREV);
776 + o.ancestor = old_commit_shortname.buf;
777 + }
778 o.branch1 = new_branch_info->name;
779 o.branch2 = "local";
780 ret = merge_trees(&o,
@@ -781,6 +788,7 @@ static int merge_working_tree(const struct checkout_opts *opts,
788 opts, 0,
789 writeout_error);
790 strbuf_release(&o.obuf);
791 + strbuf_release(&old_commit_shortname);
792 if (ret)
793 return ret;
794 }