diff --git a/Documentation/git-am.txt b/Documentation/git-am.txt index 624a6e6fe4..69d5cc9f21 100644 --- a/Documentation/git-am.txt +++ b/Documentation/git-am.txt @@ -18,7 +18,7 @@ SYNOPSIS [--quoted-cr=] [--empty=(stop|drop|keep)] [( | )...] -'git am' (--continue | --skip | --abort | --quit | --show-current-patch[=(diff|raw)] | --allow-empty) +'git am' (--continue | --skip | --abort | --quit | --retry | --show-current-patch[=(diff|raw)] | --allow-empty) DESCRIPTION ----------- @@ -208,6 +208,12 @@ Valid for the `--whitespace` option are: Abort the patching operation but keep HEAD and the index untouched. +--retry:: + Try to apply the last conflicting patch again. This is generally + only useful for passing extra options to the retry attempt + (e.g., `--3way`), since otherwise you'll just see the same + failure again. + --show-current-patch[=(diff|raw)]:: Show the message at which `git am` has stopped due to conflicts. If `raw` is specified, show the raw contents of diff --git a/builtin/am.c b/builtin/am.c index 36839029d2..926592691a 100644 --- a/builtin/am.c +++ b/builtin/am.c @@ -2393,6 +2393,9 @@ int cmd_am(int argc, const char **argv, const char *prefix) N_("show the patch being applied"), PARSE_OPT_CMDMODE | PARSE_OPT_OPTARG | PARSE_OPT_NONEG | PARSE_OPT_LITERAL_ARGHELP, parse_opt_show_current_patch, RESUME_SHOW_PATCH_RAW }, + OPT_CMDMODE(0, "retry", &resume_mode, + N_("try to apply current patch again"), + RESUME_APPLY), OPT_CMDMODE(0, "allow-empty", &resume_mode, N_("record the empty patch as an empty commit"), RESUME_ALLOW_EMPTY), diff --git a/t/t4153-am-resume-override-opts.sh b/t/t4153-am-resume-override-opts.sh index 4add7c7757..a32cec42aa 100755 --- a/t/t4153-am-resume-override-opts.sh +++ b/t/t4153-am-resume-override-opts.sh @@ -3,7 +3,6 @@ test_description='git-am command-line options override saved options' . ./test-lib.sh -. "$TEST_DIRECTORY"/lib-terminal.sh format_patch () { git format-patch --stdout -1 "$1" >"$1".eml @@ -27,7 +26,12 @@ test_expect_success 'setup' ' format_patch side2 ' -test_expect_success TTY '--3way overrides --no-3way' ' +test_expect_success '--retry fails without in-progress operation' ' + test_must_fail git am --retry 2>err && + test_grep "operation not in progress" err +' + +test_expect_success '--3way overrides --no-3way' ' rm -fr .git/rebase-apply && git reset --hard && git checkout renamed-file && @@ -40,7 +44,7 @@ test_expect_success TTY '--3way overrides --no-3way' ' # Applying side1 with am --3way will succeed due to the threeway-merge. # Applying side2 will fail as --3way does not apply to it. - test_must_fail test_terminal git am --3way &", $out; open STDERR, ">&", $err; - close $in; close $out; exec(@$argv) or die "cannot exec '$argv->[0]': $!" } @@ -51,17 +49,6 @@ sub xsendfile { copy($in, $out, 4096) or $!{EIO} or die "cannot copy from child: $!"; } -sub copy_stdin { - my ($in) = @_; - my $pid = fork; - if (!$pid) { - xsendfile($in, \*STDIN); - exit 0; - } - close($in); - return $pid; -} - sub copy_stdio { my ($out, $err) = @_; my $pid = fork; @@ -81,25 +68,15 @@ sub copy_stdio { die "usage: test-terminal program args"; } $ENV{TERM} = 'vt100'; -my $parent_in = new IO::Pty; my $parent_out = new IO::Pty; my $parent_err = new IO::Pty; -$parent_in->set_raw(); $parent_out->set_raw(); $parent_err->set_raw(); -$parent_in->slave->set_raw(); $parent_out->slave->set_raw(); $parent_err->slave->set_raw(); -my $pid = start_child(\@ARGV, $parent_in->slave, $parent_out->slave, $parent_err->slave); -close $parent_in->slave; +my $pid = start_child(\@ARGV, $parent_out->slave, $parent_err->slave); close $parent_out->slave; close $parent_err->slave; -my $in_pid = copy_stdin($parent_in); copy_stdio($parent_out, $parent_err); my $ret = finish_child($pid); -# If the child process terminates before our copy_stdin() process is able to -# write all of its data to $parent_in, the copy_stdin() process could stall. -# Send SIGTERM to it to ensure it terminates. -kill 'TERM', $in_pid; -finish_child($in_pid); exit($ret);