rev-parse: fix parent shorthands with --symbolic

The try_parent_shorthands() function shows each parent via show_rev(). We pass the correct parent sha1, but our "name" parameter still points at the original refname. So asking for a regular rev-parse works fine (it prints the sha1s), but asking for the symbolic name gives nonsense like: $ git rev-parse --symbolic HEAD^-1 HEAD ^HEAD which is always an empty set of commits. Asking for "^!" is likewise broken, with the added bonus that its prints ^HEAD for _each_ parent. And "^@" just prints HEAD repeatedly. Arguably it would be correct to just pass NULL as the name here, and always get the parent expressed as a sha1. The "--symbolic" documentaton claims only "as close to the original input as possible", and we certainly fallback to sha1s where necessary. But it's pretty easy to generate a symbolic name on the fly from the original. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>

Jeff King committed Nov 16, 2016 at 00:46 UTC a2e7b04c443e63696d3c61bac0734486132eedbf
2 files changed +24 -1
builtin/rev-parse.c
+6 -1
@@ -342,11 +342,16 @@ static int try_parent_shorthands(const char *arg)
342 for (parents = commit->parents, parent_number = 1;
343 parents;
344 parents = parents->next, parent_number++) {
345 + char *name = NULL;
346 +
347 if (exclude_parent && parent_number != exclude_parent)
348 continue;
349
350 + if (symbolic)
351 + name = xstrfmt("%s^%d", arg, parent_number);
352 show_rev(include_parents ? NORMAL : REVERSED,
349 - parents->item->object.oid.hash, arg);
353 + parents->item->object.oid.hash, name);
354 + free(name);
355 }
356
357 *dotdot = '^';
t/t6101-rev-parse-parents.sh
+18
@@ -83,12 +83,24 @@ test_expect_success 'final^1^@ = final^1^1 final^1^2' '
83 test_cmp expect actual
84 '
85
86 +test_expect_success 'symbolic final^1^@ = final^1^1 final^1^2' '
87 + git rev-parse --symbolic final^1^1 final^1^2 >expect &&
88 + git rev-parse --symbolic final^1^@ >actual &&
89 + test_cmp expect actual
90 +'
91 +
92 test_expect_success 'final^1^! = final^1 ^final^1^1 ^final^1^2' '
93 git rev-parse final^1 ^final^1^1 ^final^1^2 >expect &&
94 git rev-parse final^1^! >actual &&
95 test_cmp expect actual
96 '
97
98 +test_expect_success 'symbolic final^1^! = final^1 ^final^1^1 ^final^1^2' '
99 + git rev-parse --symbolic final^1 ^final^1^1 ^final^1^2 >expect &&
100 + git rev-parse --symbolic final^1^! >actual &&
101 + test_cmp expect actual
102 +'
103 +
104 test_expect_success 'large graft octopus' '
105 test_cmp_rev_output b31 "git rev-parse --verify b1^30"
106 '
@@ -143,6 +155,12 @@ test_expect_success 'rev-parse merge^-2 = merge^2..merge' '
155 test_cmp expect actual
156 '
157
158 +test_expect_success 'symbolic merge^-1 = merge^1..merge' '
159 + git rev-parse --symbolic merge^1..merge >expect &&
160 + git rev-parse --symbolic merge^-1 >actual &&
161 + test_cmp expect actual
162 +'
163 +
164 test_expect_success 'rev-parse merge^-0 (invalid parent)' '
165 test_must_fail git rev-parse merge^-0
166 '