{"thread":{"id":"51682","subject":"[RFC PATCH 5/5] Signing API: Duplicated signing tests using new config aliases","startedAt":"2019-08-19T21:20:18Z","lastAt":"2019-08-19T21:20:18Z","messageCount":1,"participants":["Ibrahim El"],"isPatch":true,"patchVersion":1,"patchTotal":5},"messages":[{"id":"380735","messageId":"74R10RrvOffzj20d_Owd_1WFMh1bWq8mIhEEBSzbhkHfbvW5BLHZj-L-AgHYnpqkxgZdCfW5b72GoIvKHucQz7tdiGZEzietp0IKpU1_wuI=@pm.me","threadId":"51682","inReplyTo":null,"subject":"[RFC PATCH 5/5] Signing API: Duplicated signing tests using new config aliases","fromName":"Ibrahim El","fromEmail":"ibrahim.el@pm.me","sentAt":"2019-08-19T21:19:33Z","receivedAt":"2019-08-19T21:20:18Z","isPatch":true,"sender":{"key":"ibrahim.el@pm.me","avatar":null},"body":"From: Ibrahim El Rhezzali <ibrahim.el@pm.me>\n\nc6a1d1c21 Duplicated signing tests using new config aliases\n\nDuplicating existing tests that are signature related and updating them to use the new config aliases\n\nSigned-off-by: Ibrahim El <ibrahim.el@pm.me>\n---\n t/t3431-rebase-interactive-signconfig.sh | 1480 +++++++++++++++++++++\n t/t4215-log-signconfig.sh                | 1710 ++++++++++++++++++++++++\n t/t5548-push-signed-signconfig.sh        |  276 ++++\n t/t7013-tag-signconfig.sh                | 2074 ++++++++++++++++++++++++++++++\n t/t7031-verify-tag-signconfig.sh         |  175 +++\n t/t7522-signed-commit-signconfig.sh      |  288 +++++\n 6 files changed, 6003 insertions(+)\n create mode 100755 t/t3431-rebase-interactive-signconfig.sh\n create mode 100755 t/t4215-log-signconfig.sh\n create mode 100755 t/t5548-push-signed-signconfig.sh\n create mode 100755 t/t7013-tag-signconfig.sh\n create mode 100755 t/t7031-verify-tag-signconfig.sh\n create mode 100755 t/t7522-signed-commit-signconfig.sh\n\ndiff --git a/t/t3431-rebase-interactive-signconfig.sh b/t/t3431-rebase-interactive-signconfig.sh\nnew file mode 100755\nindex 000000000..ffa409292\n--- /dev/null\n+++ b/t/t3431-rebase-interactive-signconfig.sh\n@@ -0,0 +1,1480 @@\n+#!/bin/sh\n+#\n+# Copyright (c) 2007 Johannes E. Schindelin\n+#\n+\n+test_description='git rebase interactive\n+\n+This test runs git rebase \"interactively\", by faking an edit, and verifies\n+that the result still makes sense.\n+\n+Initial setup:\n+\n+     one - two - three - four (conflict-branch)\n+   /\n+ A - B - C - D - E            (master)\n+ | \\\n+ |   F - G - H                (branch1)\n+ |     \\\n+ |\\      I                    (branch2)\n+ | \\\n+ |   J - K - L - M            (no-conflict-branch)\n+  \\\n+    N - O - P                 (no-ff-branch)\n+\n+ where A, B, D and G all touch file1, and one, two, three, four all\n+ touch file \"conflict\".\n+'\n+. ./test-lib.sh\n+\n+. \"$TEST_DIRECTORY\"/lib-rebase.sh\n+\n+# WARNING: Modifications to the initial repository can change the SHA ID used\n+# in the expect2 file for the 'stop on conflicting pick' test.\n+\n+test_expect_success 'setup' '\n+\ttest_commit A file1 &&\n+\ttest_commit B file1 &&\n+\ttest_commit C file2 &&\n+\ttest_commit D file1 &&\n+\ttest_commit E file3 &&\n+\tgit checkout -b branch1 A &&\n+\ttest_commit F file4 &&\n+\ttest_commit G file1 &&\n+\ttest_commit H file5 &&\n+\tgit checkout -b branch2 F &&\n+\ttest_commit I file6 &&\n+\tgit checkout -b conflict-branch A &&\n+\ttest_commit one conflict &&\n+\ttest_commit two conflict &&\n+\ttest_commit three conflict &&\n+\ttest_commit four conflict &&\n+\tgit checkout -b no-conflict-branch A &&\n+\ttest_commit J fileJ &&\n+\ttest_commit K fileK &&\n+\ttest_commit L fileL &&\n+\ttest_commit M fileM &&\n+\tgit checkout -b no-ff-branch A &&\n+\ttest_commit N fileN &&\n+\ttest_commit O fileO &&\n+\ttest_commit P fileP\n+'\n+\n+# \"exec\" commands are run with the user shell by default, but this may\n+# be non-POSIX. For example, if SHELL=zsh then \">file\" doesn't work\n+# to create a file. Unsetting SHELL avoids such non-portable behavior\n+# in tests. It must be exported for it to take effect where needed.\n+SHELL=\n+export SHELL\n+\n+test_expect_success 'rebase --keep-empty' '\n+\tgit checkout -b emptybranch master &&\n+\tgit commit --allow-empty -m \"empty\" &&\n+\tgit rebase --keep-empty -i HEAD~2 &&\n+\tgit log --oneline >actual &&\n+\ttest_line_count = 6 actual\n+'\n+\n+cat > expect <<EOF\n+error: nothing to do\n+EOF\n+\n+test_expect_success 'rebase -i with empty HEAD' '\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 exec_true\" git rebase -i HEAD^ >actual 2>&1 &&\n+\ttest_i18ncmp expect actual\n+'\n+\n+test_expect_success 'rebase -i with the exec command' '\n+\tgit checkout master &&\n+\t(\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 exec_>touch-one\n+\t\t2 exec_>touch-two exec_false exec_>touch-three\n+\t\t3 4 exec_>\\\"touch-file__name_with_spaces\\\";_>touch-after-semicolon 5\" &&\n+\texport FAKE_LINES &&\n+\ttest_must_fail git rebase -i A\n+\t) &&\n+\ttest_path_is_file touch-one &&\n+\ttest_path_is_file touch-two &&\n+\ttest_path_is_missing touch-three \" (should have stopped before)\" &&\n+\ttest_cmp_rev C HEAD &&\n+\tgit rebase --continue &&\n+\ttest_path_is_file touch-three &&\n+\ttest_path_is_file \"touch-file  name with spaces\" &&\n+\ttest_path_is_file touch-after-semicolon &&\n+\ttest_cmp_rev master HEAD &&\n+\trm -f touch-*\n+'\n+\n+test_expect_success 'rebase -i with the exec command runs from tree root' '\n+\tgit checkout master &&\n+\tmkdir subdir && (cd subdir &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 exec_>touch-subdir\" \\\n+\t\tgit rebase -i HEAD^\n+\t) &&\n+\ttest_path_is_file touch-subdir &&\n+\trm -fr subdir\n+'\n+\n+test_expect_success 'rebase -i with exec allows git commands in subdirs' '\n+\ttest_when_finished \"rm -rf subdir\" &&\n+\ttest_when_finished \"git rebase --abort ||:\" &&\n+\tgit checkout master &&\n+\tmkdir subdir && (cd subdir &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 x_cd_subdir_&&_git_rev-parse_--is-inside-work-tree\" \\\n+\t\tgit rebase -i HEAD^\n+\t)\n+'\n+\n+test_expect_success 'rebase -i sets work tree properly' '\n+\ttest_when_finished \"rm -rf subdir\" &&\n+\ttest_when_finished \"test_might_fail git rebase --abort\" &&\n+\tmkdir subdir &&\n+\tgit rebase -x \"(cd subdir && git rev-parse --show-toplevel)\" HEAD^ \\\n+\t\t>actual &&\n+\t! grep \"/subdir$\" actual\n+'\n+\n+test_expect_success 'rebase -i with the exec command checks tree cleanness' '\n+\tgit checkout master &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"exec_echo_foo_>file1 1\" git rebase -i HEAD^ &&\n+\ttest_cmp_rev master^ HEAD &&\n+\tgit reset --hard &&\n+\tgit rebase --continue\n+'\n+\n+test_expect_success 'rebase -x with empty command fails' '\n+\ttest_when_finished \"git rebase --abort ||:\" &&\n+\ttest_must_fail env git rebase -x \"\" @ 2>actual &&\n+\ttest_write_lines \"error: empty exec command\" >expected &&\n+\ttest_i18ncmp expected actual &&\n+\ttest_must_fail env git rebase -x \" \" @ 2>actual &&\n+\ttest_i18ncmp expected actual\n+'\n+\n+LF='\n+'\n+test_expect_success 'rebase -x with newline in command fails' '\n+\ttest_when_finished \"git rebase --abort ||:\" &&\n+\ttest_must_fail env git rebase -x \"a${LF}b\" @ 2>actual &&\n+\ttest_write_lines \"error: exec commands cannot contain newlines\" \\\n+\t\t\t >expected &&\n+\ttest_i18ncmp expected actual\n+'\n+\n+test_expect_success 'rebase -i with exec of inexistent command' '\n+\tgit checkout master &&\n+\ttest_when_finished \"git rebase --abort\" &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"exec_this-command-does-not-exist 1\" \\\n+\tgit rebase -i HEAD^ >actual 2>&1 &&\n+\t! grep \"Maybe git-rebase is broken\" actual\n+'\n+\n+test_expect_success 'implicit interactive rebase does not invoke sequence editor' '\n+\ttest_when_finished \"git rebase --abort ||:\" &&\n+\tGIT_SEQUENCE_EDITOR=\"echo bad >\" git rebase -x\"echo one\" @^\n+'\n+\n+test_expect_success 'no changes are a nop' '\n+\tgit checkout branch2 &&\n+\tset_fake_editor &&\n+\tgit rebase -i F &&\n+\ttest \"$(git symbolic-ref -q HEAD)\" = \"refs/heads/branch2\" &&\n+\ttest $(git rev-parse I) = $(git rev-parse HEAD)\n+'\n+\n+test_expect_success 'test the [branch] option' '\n+\tgit checkout -b dead-end &&\n+\tgit rm file6 &&\n+\tgit commit -m \"stop here\" &&\n+\tset_fake_editor &&\n+\tgit rebase -i F branch2 &&\n+\ttest \"$(git symbolic-ref -q HEAD)\" = \"refs/heads/branch2\" &&\n+\ttest $(git rev-parse I) = $(git rev-parse branch2) &&\n+\ttest $(git rev-parse I) = $(git rev-parse HEAD)\n+'\n+\n+test_expect_success 'test --onto <branch>' '\n+\tgit checkout -b test-onto branch2 &&\n+\tset_fake_editor &&\n+\tgit rebase -i --onto branch1 F &&\n+\ttest \"$(git symbolic-ref -q HEAD)\" = \"refs/heads/test-onto\" &&\n+\ttest $(git rev-parse HEAD^) = $(git rev-parse branch1) &&\n+\ttest $(git rev-parse I) = $(git rev-parse branch2)\n+'\n+\n+test_expect_success 'rebase on top of a non-conflicting commit' '\n+\tgit checkout branch1 &&\n+\tgit tag original-branch1 &&\n+\tset_fake_editor &&\n+\tgit rebase -i branch2 &&\n+\ttest file6 = $(git diff --name-only original-branch1) &&\n+\ttest \"$(git symbolic-ref -q HEAD)\" = \"refs/heads/branch1\" &&\n+\ttest $(git rev-parse I) = $(git rev-parse branch2) &&\n+\ttest $(git rev-parse I) = $(git rev-parse HEAD~2)\n+'\n+\n+test_expect_success 'reflog for the branch shows state before rebase' '\n+\ttest $(git rev-parse branch1@{1}) = $(git rev-parse original-branch1)\n+'\n+\n+test_expect_success 'reflog for the branch shows correct finish message' '\n+\tprintf \"rebase -i (finish): refs/heads/branch1 onto %s\\n\" \\\n+\t\t\"$(git rev-parse branch2)\" >expected &&\n+\tgit log -g --pretty=%gs -1 refs/heads/branch1 >actual &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'exchange two commits' '\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"2 1\" git rebase -i HEAD~2 &&\n+\ttest H = $(git cat-file commit HEAD^ | sed -ne \\$p) &&\n+\ttest G = $(git cat-file commit HEAD | sed -ne \\$p)\n+'\n+\n+cat > expect << EOF\n+diff --git a/file1 b/file1\n+index f70f10e..fd79235 100644\n+--- a/file1\n++++ b/file1\n+@@ -1 +1 @@\n+-A\n++G\n+EOF\n+\n+cat > expect2 << EOF\n+<<<<<<< HEAD\n+D\n+=======\n+G\n+>>>>>>> 5d18e54... G\n+EOF\n+\n+test_expect_success 'stop on conflicting pick' '\n+\tgit tag new-branch1 &&\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -i master &&\n+\ttest \"$(git rev-parse HEAD~3)\" = \"$(git rev-parse master)\" &&\n+\ttest_cmp expect .git/rebase-merge/patch &&\n+\ttest_cmp expect2 file1 &&\n+\ttest \"$(git diff --name-status |\n+\t\tsed -n -e \"/^U/s/^U[^a-z]*//p\")\" = file1 &&\n+\ttest 4 = $(grep -v \"^#\" < .git/rebase-merge/done | wc -l) &&\n+\ttest 0 = $(grep -c \"^[^#]\" < .git/rebase-merge/git-rebase-todo)\n+'\n+\n+test_expect_success 'show conflicted patch' '\n+\tGIT_TRACE=1 git rebase --show-current-patch >/dev/null 2>stderr &&\n+\tgrep \"show.*REBASE_HEAD\" stderr &&\n+\t# the original stopped-sha1 is abbreviated\n+\tstopped_sha1=\"$(git rev-parse $(cat \".git/rebase-merge/stopped-sha\"))\" &&\n+\ttest \"$(git rev-parse REBASE_HEAD)\" = \"$stopped_sha1\"\n+'\n+\n+test_expect_success 'abort' '\n+\tgit rebase --abort &&\n+\ttest $(git rev-parse new-branch1) = $(git rev-parse HEAD) &&\n+\ttest \"$(git symbolic-ref -q HEAD)\" = \"refs/heads/branch1\" &&\n+\ttest_path_is_missing .git/rebase-merge\n+'\n+\n+test_expect_success 'abort with error when new base cannot be checked out' '\n+\tgit rm --cached file1 &&\n+\tgit commit -m \"remove file in base\" &&\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -i master > output 2>&1 &&\n+\ttest_i18ngrep \"The following untracked working tree files would be overwritten by checkout:\" \\\n+\t\toutput &&\n+\ttest_i18ngrep \"file1\" output &&\n+\ttest_path_is_missing .git/rebase-merge &&\n+\tgit reset --hard HEAD^\n+'\n+\n+test_expect_success 'retain authorship' '\n+\techo A > file7 &&\n+\tgit add file7 &&\n+\ttest_tick &&\n+\tGIT_AUTHOR_NAME=\"Twerp Snog\" git commit -m \"different author\" &&\n+\tgit tag twerp &&\n+\tset_fake_editor &&\n+\tgit rebase -i --onto master HEAD^ &&\n+\tgit show HEAD | grep \"^Author: Twerp Snog\"\n+'\n+\n+test_expect_success 'retain authorship w/ conflicts' '\n+\toGIT_AUTHOR_NAME=$GIT_AUTHOR_NAME &&\n+\ttest_when_finished \"GIT_AUTHOR_NAME=\\$oGIT_AUTHOR_NAME\" &&\n+\n+\tgit reset --hard twerp &&\n+\ttest_commit a conflict a conflict-a &&\n+\tgit reset --hard twerp &&\n+\n+\tGIT_AUTHOR_NAME=AttributeMe &&\n+\texport GIT_AUTHOR_NAME &&\n+\ttest_commit b conflict b conflict-b &&\n+\tGIT_AUTHOR_NAME=$oGIT_AUTHOR_NAME &&\n+\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -i conflict-a &&\n+\techo resolved >conflict &&\n+\tgit add conflict &&\n+\tgit rebase --continue &&\n+\ttest $(git rev-parse conflict-a^0) = $(git rev-parse HEAD^) &&\n+\tgit show >out &&\n+\tgrep AttributeMe out\n+'\n+\n+test_expect_success 'squash' '\n+\tgit reset --hard twerp &&\n+\techo B > file7 &&\n+\ttest_tick &&\n+\tGIT_AUTHOR_NAME=\"Nitfol\" git commit -m \"nitfol\" file7 &&\n+\techo \"******************************\" &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 squash 2\" EXPECT_HEADER_COUNT=2 \\\n+\t\tgit rebase -i --onto master HEAD~2 &&\n+\ttest B = $(cat file7) &&\n+\ttest $(git rev-parse HEAD^) = $(git rev-parse master)\n+'\n+\n+test_expect_success 'retain authorship when squashing' '\n+\tgit show HEAD | grep \"^Author: Twerp Snog\"\n+'\n+\n+test_expect_success REBASE_P '-p handles \"no changes\" gracefully' '\n+\tHEAD=$(git rev-parse HEAD) &&\n+\tset_fake_editor &&\n+\tgit rebase -i -p HEAD^ &&\n+\tgit update-index --refresh &&\n+\tgit diff-files --quiet &&\n+\tgit diff-index --quiet --cached HEAD -- &&\n+\ttest $HEAD = $(git rev-parse HEAD)\n+'\n+\n+test_expect_failure REBASE_P 'exchange two commits with -p' '\n+\tgit checkout H &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"2 1\" git rebase -i -p HEAD~2 &&\n+\ttest H = $(git cat-file commit HEAD^ | sed -ne \\$p) &&\n+\ttest G = $(git cat-file commit HEAD | sed -ne \\$p)\n+'\n+\n+test_expect_success REBASE_P 'preserve merges with -p' '\n+\tgit checkout -b to-be-preserved master^ &&\n+\t: > unrelated-file &&\n+\tgit add unrelated-file &&\n+\ttest_tick &&\n+\tgit commit -m \"unrelated\" &&\n+\tgit checkout -b another-branch master &&\n+\techo B > file1 &&\n+\ttest_tick &&\n+\tgit commit -m J file1 &&\n+\ttest_tick &&\n+\tgit merge to-be-preserved &&\n+\techo C > file1 &&\n+\ttest_tick &&\n+\tgit commit -m K file1 &&\n+\techo D > file1 &&\n+\ttest_tick &&\n+\tgit commit -m L1 file1 &&\n+\tgit checkout HEAD^ &&\n+\techo 1 > unrelated-file &&\n+\ttest_tick &&\n+\tgit commit -m L2 unrelated-file &&\n+\ttest_tick &&\n+\tgit merge another-branch &&\n+\techo E > file1 &&\n+\ttest_tick &&\n+\tgit commit -m M file1 &&\n+\tgit checkout -b to-be-rebased &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tgit rebase -i -p --onto branch1 master &&\n+\tgit update-index --refresh &&\n+\tgit diff-files --quiet &&\n+\tgit diff-index --quiet --cached HEAD -- &&\n+\ttest $(git rev-parse HEAD~6) = $(git rev-parse branch1) &&\n+\ttest $(git rev-parse HEAD~4^2) = $(git rev-parse to-be-preserved) &&\n+\ttest $(git rev-parse HEAD^^2^) = $(git rev-parse HEAD^^^) &&\n+\ttest $(git show HEAD~5:file1) = B &&\n+\ttest $(git show HEAD~3:file1) = C &&\n+\ttest $(git show HEAD:file1) = E &&\n+\ttest $(git show HEAD:unrelated-file) = 1\n+'\n+\n+test_expect_success REBASE_P 'edit ancestor with -p' '\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 2 edit 3 4\" git rebase -i -p HEAD~3 &&\n+\techo 2 > unrelated-file &&\n+\ttest_tick &&\n+\tgit commit -m L2-modified --amend unrelated-file &&\n+\tgit rebase --continue &&\n+\tgit update-index --refresh &&\n+\tgit diff-files --quiet &&\n+\tgit diff-index --quiet --cached HEAD -- &&\n+\ttest $(git show HEAD:unrelated-file) = 2\n+'\n+\n+test_expect_success '--continue tries to commit' '\n+\tgit reset --hard D &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -i --onto new-branch1 HEAD^ &&\n+\techo resolved > file1 &&\n+\tgit add file1 &&\n+\tFAKE_COMMIT_MESSAGE=\"chouette!\" git rebase --continue &&\n+\ttest $(git rev-parse HEAD^) = $(git rev-parse new-branch1) &&\n+\tgit show HEAD | grep chouette\n+'\n+\n+test_expect_success 'verbose flag is heeded, even after --continue' '\n+\tgit reset --hard master@{1} &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -v -i --onto new-branch1 HEAD^ &&\n+\techo resolved > file1 &&\n+\tgit add file1 &&\n+\tgit rebase --continue > output &&\n+\tgrep \"^ file1 | 2 +-$\" output\n+'\n+\n+test_expect_success C_LOCALE_OUTPUT 'multi-squash only fires up editor once' '\n+\tbase=$(git rev-parse HEAD~4) &&\n+\tset_fake_editor &&\n+\tFAKE_COMMIT_AMEND=\"ONCE\" FAKE_LINES=\"1 squash 2 squash 3 squash 4\" \\\n+\t\tEXPECT_HEADER_COUNT=4 \\\n+\t\tgit rebase -i $base &&\n+\ttest $base = $(git rev-parse HEAD^) &&\n+\ttest 1 = $(git show | grep ONCE | wc -l)\n+'\n+\n+test_expect_success C_LOCALE_OUTPUT 'multi-fixup does not fire up editor' '\n+\tgit checkout -b multi-fixup E &&\n+\tbase=$(git rev-parse HEAD~4) &&\n+\tset_fake_editor &&\n+\tFAKE_COMMIT_AMEND=\"NEVER\" FAKE_LINES=\"1 fixup 2 fixup 3 fixup 4\" \\\n+\t\tgit rebase -i $base &&\n+\ttest $base = $(git rev-parse HEAD^) &&\n+\ttest 0 = $(git show | grep NEVER | wc -l) &&\n+\tgit checkout @{-1} &&\n+\tgit branch -D multi-fixup\n+'\n+\n+test_expect_success 'commit message used after conflict' '\n+\tgit checkout -b conflict-fixup conflict-branch &&\n+\tbase=$(git rev-parse HEAD~4) &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 fixup 3 fixup 4\" git rebase -i $base &&\n+\techo three > conflict &&\n+\tgit add conflict &&\n+\tFAKE_COMMIT_AMEND=\"ONCE\" EXPECT_HEADER_COUNT=2 \\\n+\t\tgit rebase --continue &&\n+\ttest $base = $(git rev-parse HEAD^) &&\n+\ttest 1 = $(git show | grep ONCE | wc -l) &&\n+\tgit checkout @{-1} &&\n+\tgit branch -D conflict-fixup\n+'\n+\n+test_expect_success 'commit message retained after conflict' '\n+\tgit checkout -b conflict-squash conflict-branch &&\n+\tbase=$(git rev-parse HEAD~4) &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 fixup 3 squash 4\" git rebase -i $base &&\n+\techo three > conflict &&\n+\tgit add conflict &&\n+\tFAKE_COMMIT_AMEND=\"TWICE\" EXPECT_HEADER_COUNT=2 \\\n+\t\tgit rebase --continue &&\n+\ttest $base = $(git rev-parse HEAD^) &&\n+\ttest 2 = $(git show | grep TWICE | wc -l) &&\n+\tgit checkout @{-1} &&\n+\tgit branch -D conflict-squash\n+'\n+\n+cat > expect-squash-fixup << EOF\n+B\n+\n+D\n+\n+ONCE\n+EOF\n+\n+test_expect_success C_LOCALE_OUTPUT 'squash and fixup generate correct log messages' '\n+\tgit checkout -b squash-fixup E &&\n+\tbase=$(git rev-parse HEAD~4) &&\n+\tset_fake_editor &&\n+\tFAKE_COMMIT_AMEND=\"ONCE\" FAKE_LINES=\"1 fixup 2 squash 3 fixup 4\" \\\n+\t\tEXPECT_HEADER_COUNT=4 \\\n+\t\tgit rebase -i $base &&\n+\tgit cat-file commit HEAD | sed -e 1,/^\\$/d > actual-squash-fixup &&\n+\ttest_cmp expect-squash-fixup actual-squash-fixup &&\n+\tgit cat-file commit HEAD@{2} |\n+\t\tgrep \"^# This is a combination of 3 commits\\.\"  &&\n+\tgit cat-file commit HEAD@{3} |\n+\t\tgrep \"^# This is a combination of 2 commits\\.\"  &&\n+\tgit checkout @{-1} &&\n+\tgit branch -D squash-fixup\n+'\n+\n+test_expect_success C_LOCALE_OUTPUT 'squash ignores comments' '\n+\tgit checkout -b skip-comments E &&\n+\tbase=$(git rev-parse HEAD~4) &&\n+\tset_fake_editor &&\n+\tFAKE_COMMIT_AMEND=\"ONCE\" FAKE_LINES=\"# 1 # squash 2 # squash 3 # squash 4 #\" \\\n+\t\tEXPECT_HEADER_COUNT=4 \\\n+\t\tgit rebase -i $base &&\n+\ttest $base = $(git rev-parse HEAD^) &&\n+\ttest 1 = $(git show | grep ONCE | wc -l) &&\n+\tgit checkout @{-1} &&\n+\tgit branch -D skip-comments\n+'\n+\n+test_expect_success C_LOCALE_OUTPUT 'squash ignores blank lines' '\n+\tgit checkout -b skip-blank-lines E &&\n+\tbase=$(git rev-parse HEAD~4) &&\n+\tset_fake_editor &&\n+\tFAKE_COMMIT_AMEND=\"ONCE\" FAKE_LINES=\"> 1 > squash 2 > squash 3 > squash 4 >\" \\\n+\t\tEXPECT_HEADER_COUNT=4 \\\n+\t\tgit rebase -i $base &&\n+\ttest $base = $(git rev-parse HEAD^) &&\n+\ttest 1 = $(git show | grep ONCE | wc -l) &&\n+\tgit checkout @{-1} &&\n+\tgit branch -D skip-blank-lines\n+'\n+\n+test_expect_success 'squash works as expected' '\n+\tgit checkout -b squash-works no-conflict-branch &&\n+\tone=$(git rev-parse HEAD~3) &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 s 3 2\" EXPECT_HEADER_COUNT=2 \\\n+\t\tgit rebase -i HEAD~3 &&\n+\ttest $one = $(git rev-parse HEAD~2)\n+'\n+\n+test_expect_success 'interrupted squash works as expected' '\n+\tgit checkout -b interrupted-squash conflict-branch &&\n+\tone=$(git rev-parse HEAD~3) &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 squash 3 2\" git rebase -i HEAD~3 &&\n+\ttest_write_lines one two four > conflict &&\n+\tgit add conflict &&\n+\ttest_must_fail git rebase --continue &&\n+\techo resolved > conflict &&\n+\tgit add conflict &&\n+\tgit rebase --continue &&\n+\ttest $one = $(git rev-parse HEAD~2)\n+'\n+\n+test_expect_success 'interrupted squash works as expected (case 2)' '\n+\tgit checkout -b interrupted-squash2 conflict-branch &&\n+\tone=$(git rev-parse HEAD~3) &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"3 squash 1 2\" git rebase -i HEAD~3 &&\n+\ttest_write_lines one four > conflict &&\n+\tgit add conflict &&\n+\ttest_must_fail git rebase --continue &&\n+\ttest_write_lines one two four > conflict &&\n+\tgit add conflict &&\n+\ttest_must_fail git rebase --continue &&\n+\techo resolved > conflict &&\n+\tgit add conflict &&\n+\tgit rebase --continue &&\n+\ttest $one = $(git rev-parse HEAD~2)\n+'\n+\n+test_expect_success '--continue tries to commit, even for \"edit\"' '\n+\techo unrelated > file7 &&\n+\tgit add file7 &&\n+\ttest_tick &&\n+\tgit commit -m \"unrelated change\" &&\n+\tparent=$(git rev-parse HEAD^) &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1\" git rebase -i HEAD^ &&\n+\techo edited > file7 &&\n+\tgit add file7 &&\n+\tFAKE_COMMIT_MESSAGE=\"chouette!\" git rebase --continue &&\n+\ttest edited = $(git show HEAD:file7) &&\n+\tgit show HEAD | grep chouette &&\n+\ttest $parent = $(git rev-parse HEAD^)\n+'\n+\n+test_expect_success 'aborted --continue does not squash commits after \"edit\"' '\n+\told=$(git rev-parse HEAD) &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1\" git rebase -i HEAD^ &&\n+\techo \"edited again\" > file7 &&\n+\tgit add file7 &&\n+\ttest_must_fail env FAKE_COMMIT_MESSAGE=\" \" git rebase --continue &&\n+\ttest $old = $(git rev-parse HEAD) &&\n+\tgit rebase --abort\n+'\n+\n+test_expect_success 'auto-amend only edited commits after \"edit\"' '\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1\" git rebase -i HEAD^ &&\n+\techo \"edited again\" > file7 &&\n+\tgit add file7 &&\n+\tFAKE_COMMIT_MESSAGE=\"edited file7 again\" git commit &&\n+\techo \"and again\" > file7 &&\n+\tgit add file7 &&\n+\ttest_tick &&\n+\ttest_must_fail env FAKE_COMMIT_MESSAGE=\"and again\" git rebase --continue &&\n+\tgit rebase --abort\n+'\n+\n+test_expect_success 'clean error after failed \"exec\"' '\n+\ttest_tick &&\n+\ttest_when_finished \"git rebase --abort || :\" &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 exec_false\" git rebase -i HEAD^ &&\n+\techo \"edited again\" > file7 &&\n+\tgit add file7 &&\n+\ttest_must_fail git rebase --continue 2>error &&\n+\ttest_i18ngrep \"you have staged changes in your working tree\" error\n+'\n+\n+test_expect_success 'rebase a detached HEAD' '\n+\tgrandparent=$(git rev-parse HEAD~2) &&\n+\tgit checkout $(git rev-parse HEAD) &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"2 1\" git rebase -i HEAD~2 &&\n+\ttest $grandparent = $(git rev-parse HEAD~2)\n+'\n+\n+test_expect_success 'rebase a commit violating pre-commit' '\n+\n+\tmkdir -p .git/hooks &&\n+\twrite_script .git/hooks/pre-commit <<-\\EOF &&\n+\ttest -z \"$(git diff --cached --check)\"\n+\tEOF\n+\techo \"monde! \" >> file1 &&\n+\ttest_tick &&\n+\ttest_must_fail git commit -m doesnt-verify file1 &&\n+\tgit commit -m doesnt-verify --no-verify file1 &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=2 git rebase -i HEAD~2\n+\n+'\n+\n+test_expect_success 'rebase with a file named HEAD in worktree' '\n+\n+\trm -fr .git/hooks &&\n+\tgit reset --hard &&\n+\tgit checkout -b branch3 A &&\n+\n+\t(\n+\t\tGIT_AUTHOR_NAME=\"Squashed Away\" &&\n+\t\texport GIT_AUTHOR_NAME &&\n+\t\t>HEAD &&\n+\t\tgit add HEAD &&\n+\t\tgit commit -m \"Add head\" &&\n+\t\t>BODY &&\n+\t\tgit add BODY &&\n+\t\tgit commit -m \"Add body\"\n+\t) &&\n+\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 squash 2\" git rebase -i @{-1} &&\n+\ttest \"$(git show -s --pretty=format:%an)\" = \"Squashed Away\"\n+\n+'\n+\n+test_expect_success 'do \"noop\" when there is nothing to cherry-pick' '\n+\n+\tgit checkout -b branch4 HEAD &&\n+\tGIT_EDITOR=: git commit --amend \\\n+\t\t--author=\"Somebody else <somebody@else.com>\" &&\n+\ttest $(git rev-parse branch3) != $(git rev-parse branch4) &&\n+\tset_fake_editor &&\n+\tgit rebase -i branch3 &&\n+\ttest $(git rev-parse branch3) = $(git rev-parse branch4)\n+\n+'\n+\n+test_expect_success 'submodule rebase setup' '\n+\tgit checkout A &&\n+\tmkdir sub &&\n+\t(\n+\t\tcd sub && git init && >elif &&\n+\t\tgit add elif && git commit -m \"submodule initial\"\n+\t) &&\n+\techo 1 >file1 &&\n+\tgit add file1 sub &&\n+\ttest_tick &&\n+\tgit commit -m \"One\" &&\n+\techo 2 >file1 &&\n+\ttest_tick &&\n+\tgit commit -a -m \"Two\" &&\n+\t(\n+\t\tcd sub && echo 3 >elif &&\n+\t\tgit commit -a -m \"submodule second\"\n+\t) &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tgit commit -a -m \"Three changes submodule\"\n+'\n+\n+test_expect_success 'submodule rebase -i' '\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 squash 2 3\" git rebase -i A\n+'\n+\n+test_expect_success 'submodule conflict setup' '\n+\tgit tag submodule-base &&\n+\tgit checkout HEAD^ &&\n+\t(\n+\t\tcd sub && git checkout HEAD^ && echo 4 >elif &&\n+\t\tgit add elif && git commit -m \"submodule conflict\"\n+\t) &&\n+\tgit add sub &&\n+\ttest_tick &&\n+\tgit commit -m \"Conflict in submodule\" &&\n+\tgit tag submodule-topic\n+'\n+\n+test_expect_success 'rebase -i continue with only submodule staged' '\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -i submodule-base &&\n+\tgit add sub &&\n+\tgit rebase --continue &&\n+\ttest $(git rev-parse submodule-base) != $(git rev-parse HEAD)\n+'\n+\n+test_expect_success 'rebase -i continue with unstaged submodule' '\n+\tgit checkout submodule-topic &&\n+\tgit reset --hard &&\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -i submodule-base &&\n+\tgit reset &&\n+\tgit rebase --continue &&\n+\ttest $(git rev-parse submodule-base) = $(git rev-parse HEAD)\n+'\n+\n+test_expect_success 'avoid unnecessary reset' '\n+\tgit checkout master &&\n+\tgit reset --hard &&\n+\ttest-tool chmtime =123456789 file3 &&\n+\tgit update-index --refresh &&\n+\tHEAD=$(git rev-parse HEAD) &&\n+\tset_fake_editor &&\n+\tgit rebase -i HEAD~4 &&\n+\ttest $HEAD = $(git rev-parse HEAD) &&\n+\tMTIME=$(test-tool chmtime --get file3) &&\n+\ttest 123456789 = $MTIME\n+'\n+\n+test_expect_success 'reword' '\n+\tgit checkout -b reword-branch master &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 2 3 reword 4\" FAKE_COMMIT_MESSAGE=\"E changed\" git rebase -i A &&\n+\tgit show HEAD | grep \"E changed\" &&\n+\ttest $(git rev-parse master) != $(git rev-parse HEAD) &&\n+\ttest $(git rev-parse master^) = $(git rev-parse HEAD^) &&\n+\tFAKE_LINES=\"1 2 reword 3 4\" FAKE_COMMIT_MESSAGE=\"D changed\" git rebase -i A &&\n+\tgit show HEAD^ | grep \"D changed\" &&\n+\tFAKE_LINES=\"reword 1 2 3 4\" FAKE_COMMIT_MESSAGE=\"B changed\" git rebase -i A &&\n+\tgit show HEAD~3 | grep \"B changed\" &&\n+\tFAKE_LINES=\"1 r 2 pick 3 p 4\" FAKE_COMMIT_MESSAGE=\"C changed\" git rebase -i A &&\n+\tgit show HEAD~2 | grep \"C changed\"\n+'\n+\n+test_expect_success 'rebase -i can copy notes' '\n+\tgit config notes.rewrite.rebase true &&\n+\tgit config notes.rewriteRef \"refs/notes/*\" &&\n+\ttest_commit n1 &&\n+\ttest_commit n2 &&\n+\ttest_commit n3 &&\n+\tgit notes add -m\"a note\" n3 &&\n+\tset_fake_editor &&\n+\tgit rebase -i --onto n1 n2 &&\n+\ttest \"a note\" = \"$(git notes show HEAD)\"\n+'\n+\n+cat >expect <<EOF\n+an earlier note\n+\n+a note\n+EOF\n+\n+test_expect_success 'rebase -i can copy notes over a fixup' '\n+\tgit reset --hard n3 &&\n+\tgit notes add -m\"an earlier note\" n2 &&\n+\tset_fake_editor &&\n+\tGIT_NOTES_REWRITE_MODE=concatenate FAKE_LINES=\"1 f 2\" git rebase -i n1 &&\n+\tgit notes show > output &&\n+\ttest_cmp expect output\n+'\n+\n+test_expect_success 'rebase while detaching HEAD' '\n+\tgit symbolic-ref HEAD &&\n+\tgrandparent=$(git rev-parse HEAD~2) &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"2 1\" git rebase -i HEAD~2 HEAD^0 &&\n+\ttest $grandparent = $(git rev-parse HEAD~2) &&\n+\ttest_must_fail git symbolic-ref HEAD\n+'\n+\n+test_tick # Ensure that the rebased commits get a different timestamp.\n+test_expect_success 'always cherry-pick with --no-ff' '\n+\tgit checkout no-ff-branch &&\n+\tgit tag original-no-ff-branch &&\n+\tset_fake_editor &&\n+\tgit rebase -i --no-ff A &&\n+\tfor p in 0 1 2\n+\tdo\n+\t\ttest ! $(git rev-parse HEAD~$p) = $(git rev-parse original-no-ff-branch~$p) &&\n+\t\tgit diff HEAD~$p original-no-ff-branch~$p > out &&\n+\t\ttest_must_be_empty out\n+\tdone &&\n+\ttest $(git rev-parse HEAD~3) = $(git rev-parse original-no-ff-branch~3) &&\n+\tgit diff HEAD~3 original-no-ff-branch~3 > out &&\n+\ttest_must_be_empty out\n+'\n+\n+test_expect_success 'set up commits with funny messages' '\n+\tgit checkout -b funny A &&\n+\techo >>file1 &&\n+\ttest_tick &&\n+\tgit commit -a -m \"end with slash\\\\\" &&\n+\techo >>file1 &&\n+\ttest_tick &&\n+\tgit commit -a -m \"something (\\000) that looks like octal\" &&\n+\techo >>file1 &&\n+\ttest_tick &&\n+\tgit commit -a -m \"something (\\n) that looks like a newline\" &&\n+\techo >>file1 &&\n+\ttest_tick &&\n+\tgit commit -a -m \"another commit\"\n+'\n+\n+test_expect_success 'rebase-i history with funny messages' '\n+\tgit rev-list A..funny >expect &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 2 3 4\" git rebase -i A &&\n+\tgit rev-list A.. >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'prepare for rebase -i --exec' '\n+\tgit checkout master &&\n+\tgit checkout -b execute &&\n+\ttest_commit one_exec main.txt one_exec &&\n+\ttest_commit two_exec main.txt two_exec &&\n+\ttest_commit three_exec main.txt three_exec\n+'\n+\n+test_expect_success 'running \"git rebase -i --exec git show HEAD\"' '\n+\tset_fake_editor &&\n+\tgit rebase -i --exec \"git show HEAD\" HEAD~2 >actual &&\n+\t(\n+\t\tFAKE_LINES=\"1 exec_git_show_HEAD 2 exec_git_show_HEAD\" &&\n+\t\texport FAKE_LINES &&\n+\t\tgit rebase -i HEAD~2 >expect\n+\t) &&\n+\tsed -e \"1,9d\" expect >expected &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'running \"git rebase --exec git show HEAD -i\"' '\n+\tgit reset --hard execute &&\n+\tset_fake_editor &&\n+\tgit rebase --exec \"git show HEAD\" -i HEAD~2 >actual &&\n+\t(\n+\t\tFAKE_LINES=\"1 exec_git_show_HEAD 2 exec_git_show_HEAD\" &&\n+\t\texport FAKE_LINES &&\n+\t\tgit rebase -i HEAD~2 >expect\n+\t) &&\n+\tsed -e \"1,9d\" expect >expected &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'running \"git rebase -ix git show HEAD\"' '\n+\tgit reset --hard execute &&\n+\tset_fake_editor &&\n+\tgit rebase -ix \"git show HEAD\" HEAD~2 >actual &&\n+\t(\n+\t\tFAKE_LINES=\"1 exec_git_show_HEAD 2 exec_git_show_HEAD\" &&\n+\t\texport FAKE_LINES &&\n+\t\tgit rebase -i HEAD~2 >expect\n+\t) &&\n+\tsed -e \"1,9d\" expect >expected &&\n+\ttest_cmp expected actual\n+'\n+\n+\n+test_expect_success 'rebase -ix with several <CMD>' '\n+\tgit reset --hard execute &&\n+\tset_fake_editor &&\n+\tgit rebase -ix \"git show HEAD; pwd\" HEAD~2 >actual &&\n+\t(\n+\t\tFAKE_LINES=\"1 exec_git_show_HEAD;_pwd 2 exec_git_show_HEAD;_pwd\" &&\n+\t\texport FAKE_LINES &&\n+\t\tgit rebase -i HEAD~2 >expect\n+\t) &&\n+\tsed -e \"1,9d\" expect >expected &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'rebase -ix with several instances of --exec' '\n+\tgit reset --hard execute &&\n+\tset_fake_editor &&\n+\tgit rebase -i --exec \"git show HEAD\" --exec \"pwd\" HEAD~2 >actual &&\n+\t(\n+\t\tFAKE_LINES=\"1 exec_git_show_HEAD exec_pwd 2\n+\t\t\t\texec_git_show_HEAD exec_pwd\" &&\n+\t\texport FAKE_LINES &&\n+\t\tgit rebase -i HEAD~2 >expect\n+\t) &&\n+\tsed -e \"1,11d\" expect >expected &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success C_LOCALE_OUTPUT 'rebase -ix with --autosquash' '\n+\tgit reset --hard execute &&\n+\tgit checkout -b autosquash &&\n+\techo second >second.txt &&\n+\tgit add second.txt &&\n+\tgit commit -m \"fixup! two_exec\" &&\n+\techo bis >bis.txt &&\n+\tgit add bis.txt &&\n+\tgit commit -m \"fixup! two_exec\" &&\n+\tset_fake_editor &&\n+\t(\n+\t\tgit checkout -b autosquash_actual &&\n+\t\tgit rebase -i --exec \"git show HEAD\" --autosquash HEAD~4 >actual\n+\t) &&\n+\tgit checkout autosquash &&\n+\t(\n+\t\tgit checkout -b autosquash_expected &&\n+\t\tFAKE_LINES=\"1 fixup 3 fixup 4 exec_git_show_HEAD 2 exec_git_show_HEAD\" &&\n+\t\texport FAKE_LINES &&\n+\t\tgit rebase -i HEAD~4 >expect\n+\t) &&\n+\tsed -e \"1,13d\" expect >expected &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'rebase --exec works without -i ' '\n+\tgit reset --hard execute &&\n+\trm -rf exec_output &&\n+\tEDITOR=\"echo >invoked_editor\" git rebase --exec \"echo a line >>exec_output\"  HEAD~2 2>actual &&\n+\ttest_i18ngrep  \"Successfully rebased and updated\" actual &&\n+\ttest_line_count = 2 exec_output &&\n+\ttest_path_is_missing invoked_editor\n+'\n+\n+test_expect_success 'rebase -i --exec without <CMD>' '\n+\tgit reset --hard execute &&\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase -i --exec 2>actual &&\n+\ttest_i18ngrep \"requires a value\" actual &&\n+\tgit checkout master\n+'\n+\n+test_expect_success 'rebase -i --root re-order and drop commits' '\n+\tgit checkout E &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"3 1 2 5\" git rebase -i --root &&\n+\ttest E = $(git cat-file commit HEAD | sed -ne \\$p) &&\n+\ttest B = $(git cat-file commit HEAD^ | sed -ne \\$p) &&\n+\ttest A = $(git cat-file commit HEAD^^ | sed -ne \\$p) &&\n+\ttest C = $(git cat-file commit HEAD^^^ | sed -ne \\$p) &&\n+\ttest 0 = $(git cat-file commit HEAD^^^ | grep -c ^parent\\ )\n+'\n+\n+test_expect_success 'rebase -i --root retain root commit author and message' '\n+\tgit checkout A &&\n+\techo B >file7 &&\n+\tgit add file7 &&\n+\tGIT_AUTHOR_NAME=\"Twerp Snog\" git commit -m \"different author\" &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"2\" git rebase -i --root &&\n+\tgit cat-file commit HEAD | grep -q \"^author Twerp Snog\" &&\n+\tgit cat-file commit HEAD | grep -q \"^different author$\"\n+'\n+\n+test_expect_success 'rebase -i --root temporary sentinel commit' '\n+\tgit checkout B &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"2\" git rebase -i --root &&\n+\tgit cat-file commit HEAD | grep \"^tree 4b825dc642cb\" &&\n+\tgit rebase --abort\n+'\n+\n+test_expect_success 'rebase -i --root fixup root commit' '\n+\tgit checkout B &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 fixup 2\" git rebase -i --root &&\n+\ttest A = $(git cat-file commit HEAD | sed -ne \\$p) &&\n+\ttest B = $(git show HEAD:file1) &&\n+\ttest 0 = $(git cat-file commit HEAD | grep -c ^parent\\ )\n+'\n+\n+test_expect_success 'rebase -i --root reword root commit' '\n+\ttest_when_finished \"test_might_fail git rebase --abort\" &&\n+\tgit checkout -b reword-root-branch master &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"reword 1 2\" FAKE_COMMIT_MESSAGE=\"A changed\" \\\n+\tgit rebase -i --root &&\n+\tgit show HEAD^ | grep \"A changed\" &&\n+\ttest -z \"$(git show -s --format=%p HEAD^)\"\n+'\n+\n+test_expect_success 'rebase -i --root when root has untracked file confilct' '\n+\ttest_when_finished \"reset_rebase\" &&\n+\tgit checkout -b failing-root-pick A &&\n+\techo x >file2 &&\n+\tgit rm file1 &&\n+\tgit commit -m \"remove file 1 add file 2\" &&\n+\techo z >file1 &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 2\" git rebase -i --root &&\n+\trm file1 &&\n+\tgit rebase --continue &&\n+\ttest \"$(git log -1 --format=%B)\" = \"remove file 1 add file 2\" &&\n+\ttest \"$(git rev-list --count HEAD)\" = 2\n+'\n+\n+test_expect_success 'rebase -i --root reword root when root has untracked file conflict' '\n+\ttest_when_finished \"reset_rebase\" &&\n+\techo z>file1 &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"reword 1 2\" \\\n+\t\tFAKE_COMMIT_MESSAGE=\"Modified A\" git rebase -i --root &&\n+\trm file1 &&\n+\tFAKE_COMMIT_MESSAGE=\"Reworded A\" git rebase --continue &&\n+\ttest \"$(git log -1 --format=%B HEAD^)\" = \"Reworded A\" &&\n+\ttest \"$(git rev-list --count HEAD)\" = 2\n+'\n+\n+test_expect_success C_LOCALE_OUTPUT 'rebase --edit-todo does not work on non-interactive rebase' '\n+\tgit checkout reword-root-branch &&\n+\tgit reset --hard &&\n+\tgit checkout conflict-branch &&\n+\tset_fake_editor &&\n+\ttest_must_fail git rebase --onto HEAD~2 HEAD~ &&\n+\ttest_must_fail git rebase --edit-todo &&\n+\tgit rebase --abort\n+'\n+\n+test_expect_success 'rebase --edit-todo can be used to modify todo' '\n+\tgit reset --hard &&\n+\tgit checkout no-conflict-branch^0 &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1 2 3\" git rebase -i HEAD~3 &&\n+\tFAKE_LINES=\"2 1\" git rebase --edit-todo &&\n+\tgit rebase --continue &&\n+\ttest M = $(git cat-file commit HEAD^ | sed -ne \\$p) &&\n+\ttest L = $(git cat-file commit HEAD | sed -ne \\$p)\n+'\n+\n+test_expect_success 'rebase -i produces readable reflog' '\n+\tgit reset --hard &&\n+\tgit branch -f branch-reflog-test H &&\n+\tset_fake_editor &&\n+\tgit rebase -i --onto I F branch-reflog-test &&\n+\tcat >expect <<-\\EOF &&\n+\trebase -i (finish): returning to refs/heads/branch-reflog-test\n+\trebase -i (pick): H\n+\trebase -i (pick): G\n+\trebase -i (start): checkout I\n+\tEOF\n+\tgit reflog -n4 HEAD |\n+\tsed \"s/[^:]*: //\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'rebase -i respects core.commentchar' '\n+\tgit reset --hard &&\n+\tgit checkout E^0 &&\n+\ttest_config core.commentchar \"\\\\\" &&\n+\twrite_script remove-all-but-first.sh <<-\\EOF &&\n+\tsed -e \"2,\\$s/^/\\\\\\\\/\" \"$1\" >\"$1.tmp\" &&\n+\tmv \"$1.tmp\" \"$1\"\n+\tEOF\n+\ttest_set_editor \"$(pwd)/remove-all-but-first.sh\" &&\n+\tgit rebase -i B &&\n+\ttest B = $(git cat-file commit HEAD^ | sed -ne \\$p)\n+'\n+\n+test_expect_success 'rebase -i respects core.commentchar=auto' '\n+\ttest_config core.commentchar auto &&\n+\twrite_script copy-edit-script.sh <<-\\EOF &&\n+\tcp \"$1\" edit-script\n+\tEOF\n+\ttest_set_editor \"$(pwd)/copy-edit-script.sh\" &&\n+\ttest_when_finished \"git rebase --abort || :\" &&\n+\tgit rebase -i HEAD^ &&\n+\ttest -z \"$(grep -ve \"^#\" -e \"^\\$\" -e \"^pick\" edit-script)\"\n+'\n+\n+test_expect_success 'rebase -i, with <onto> and <upstream> specified as :/quuxery' '\n+\ttest_when_finished \"git branch -D torebase\" &&\n+\tgit checkout -b torebase branch1 &&\n+\tupstream=$(git rev-parse \":/J\") &&\n+\tonto=$(git rev-parse \":/A\") &&\n+\tgit rebase --onto $onto $upstream &&\n+\tgit reset --hard branch1 &&\n+\tgit rebase --onto \":/A\" \":/J\" &&\n+\tgit checkout branch1\n+'\n+\n+test_expect_success 'rebase -i with --strategy and -X' '\n+\tgit checkout -b conflict-merge-use-theirs conflict-branch &&\n+\tgit reset --hard HEAD^ &&\n+\techo five >conflict &&\n+\techo Z >file1 &&\n+\tgit commit -a -m \"one file conflict\" &&\n+\tEDITOR=true git rebase -i --strategy=recursive -Xours conflict-branch &&\n+\ttest $(git show conflict-branch:conflict) = $(cat conflict) &&\n+\ttest $(cat file1) = Z\n+'\n+\n+test_expect_success 'interrupted rebase -i with --strategy and -X' '\n+\tgit checkout -b conflict-merge-use-theirs-interrupted conflict-branch &&\n+\tgit reset --hard HEAD^ &&\n+\t>breakpoint &&\n+\tgit add breakpoint &&\n+\tgit commit -m \"breakpoint for interactive mode\" &&\n+\techo five >conflict &&\n+\techo Z >file1 &&\n+\tgit commit -a -m \"one file conflict\" &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1 2\" git rebase -i --strategy=recursive -Xours conflict-branch &&\n+\tgit rebase --continue &&\n+\ttest $(git show conflict-branch:conflict) = $(cat conflict) &&\n+\ttest $(cat file1) = Z\n+'\n+\n+test_expect_success 'rebase -i error on commits with \\ in message' '\n+\tcurrent_head=$(git rev-parse HEAD) &&\n+\ttest_when_finished \"git rebase --abort; git reset --hard $current_head; rm -f error\" &&\n+\ttest_commit TO-REMOVE will-conflict old-content &&\n+\ttest_commit \"\\temp\" will-conflict new-content dummy &&\n+\ttest_must_fail env EDITOR=true git rebase -i HEAD^ --onto HEAD^^ 2>error &&\n+\ttest_expect_code 1 grep  \"\temp\" error\n+'\n+\n+test_expect_success 'short SHA-1 setup' '\n+\ttest_when_finished \"git checkout master\" &&\n+\tgit checkout --orphan collide &&\n+\tgit rm -rf . &&\n+\t(\n+\tunset test_tick &&\n+\ttest_commit collide1 collide &&\n+\ttest_commit --notick collide2 collide &&\n+\ttest_commit --notick collide3 collide\n+\t)\n+'\n+\n+test_expect_success 'short SHA-1 collide' '\n+\ttest_when_finished \"reset_rebase && git checkout master\" &&\n+\tgit checkout collide &&\n+\t(\n+\tunset test_tick &&\n+\ttest_tick &&\n+\tset_fake_editor &&\n+\tFAKE_COMMIT_MESSAGE=\"collide2 ac4f2ee\" \\\n+\tFAKE_LINES=\"reword 1 2\" git rebase -i HEAD~2\n+\t)\n+'\n+\n+test_expect_success 'respect core.abbrev' '\n+\tgit config core.abbrev 12 &&\n+\tset_cat_todo_editor &&\n+\ttest_must_fail git rebase -i HEAD~4 >todo-list &&\n+\ttest 4 = $(grep -c \"pick [0-9a-f]\\{12,\\}\" todo-list)\n+'\n+\n+test_expect_success 'todo count' '\n+\twrite_script dump-raw.sh <<-\\EOF &&\n+\t\tcat \"$1\"\n+\tEOF\n+\ttest_set_editor \"$(pwd)/dump-raw.sh\" &&\n+\tgit rebase -i HEAD~4 >actual &&\n+\ttest_i18ngrep \"^# Rebase ..* onto ..* ([0-9]\" actual\n+'\n+\n+test_expect_success 'rebase -i commits that overwrite untracked files (pick)' '\n+\tgit checkout --force branch2 &&\n+\tgit clean -f &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1 2\" git rebase -i A &&\n+\ttest_cmp_rev HEAD F &&\n+\ttest_path_is_missing file6 &&\n+\t>file6 &&\n+\ttest_must_fail git rebase --continue &&\n+\ttest_cmp_rev HEAD F &&\n+\trm file6 &&\n+\tgit rebase --continue &&\n+\ttest_cmp_rev HEAD I\n+'\n+\n+test_expect_success 'rebase -i commits that overwrite untracked files (squash)' '\n+\tgit checkout --force branch2 &&\n+\tgit clean -f &&\n+\tgit tag original-branch2 &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1 squash 2\" git rebase -i A &&\n+\ttest_cmp_rev HEAD F &&\n+\ttest_path_is_missing file6 &&\n+\t>file6 &&\n+\ttest_must_fail git rebase --continue &&\n+\ttest_cmp_rev HEAD F &&\n+\trm file6 &&\n+\tgit rebase --continue &&\n+\ttest $(git cat-file commit HEAD | sed -ne \\$p) = I &&\n+\tgit reset --hard original-branch2\n+'\n+\n+test_expect_success 'rebase -i commits that overwrite untracked files (no ff)' '\n+\tgit checkout --force branch2 &&\n+\tgit clean -f &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1 2\" git rebase -i --no-ff A &&\n+\ttest $(git cat-file commit HEAD | sed -ne \\$p) = F &&\n+\ttest_path_is_missing file6 &&\n+\t>file6 &&\n+\ttest_must_fail git rebase --continue &&\n+\ttest $(git cat-file commit HEAD | sed -ne \\$p) = F &&\n+\trm file6 &&\n+\tgit rebase --continue &&\n+\ttest $(git cat-file commit HEAD | sed -ne \\$p) = I\n+'\n+\n+test_expect_success 'rebase --continue removes CHERRY_PICK_HEAD' '\n+\tgit checkout -b commit-to-skip &&\n+\tfor double in X 3 1\n+\tdo\n+\t\ttest_seq 5 | sed \"s/$double/&&/\" >seq &&\n+\t\tgit add seq &&\n+\t\ttest_tick &&\n+\t\tgit commit -m seq-$double\n+\tdone &&\n+\tgit tag seq-onto &&\n+\tgit reset --hard HEAD~2 &&\n+\tgit cherry-pick seq-onto &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES= git rebase -i seq-onto &&\n+\ttest -d .git/rebase-merge &&\n+\tgit rebase --continue &&\n+\tgit diff --exit-code seq-onto &&\n+\ttest ! -d .git/rebase-merge &&\n+\ttest ! -f .git/CHERRY_PICK_HEAD\n+'\n+\n+rebase_setup_and_clean () {\n+\ttest_when_finished \"\n+\t\tgit checkout master &&\n+\t\ttest_might_fail git branch -D $1 &&\n+\t\ttest_might_fail git rebase --abort\n+\t\" &&\n+\tgit checkout -b $1 ${2:-master}\n+}\n+\n+test_expect_success 'drop' '\n+\trebase_setup_and_clean drop-test &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 drop 2 3 d 4 5\" git rebase -i --root &&\n+\ttest E = $(git cat-file commit HEAD | sed -ne \\$p) &&\n+\ttest C = $(git cat-file commit HEAD^ | sed -ne \\$p) &&\n+\ttest A = $(git cat-file commit HEAD^^ | sed -ne \\$p)\n+'\n+\n+test_expect_success 'rebase -i respects rebase.missingCommitsCheck = ignore' '\n+\ttest_config rebase.missingCommitsCheck ignore &&\n+\trebase_setup_and_clean missing-commit &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 2 3 4\" \\\n+\t\tgit rebase -i --root 2>actual &&\n+\ttest D = $(git cat-file commit HEAD | sed -ne \\$p) &&\n+\ttest_i18ngrep \\\n+\t\t\"Successfully rebased and updated refs/heads/missing-commit\" \\\n+\t\tactual\n+'\n+\n+cat >expect <<EOF\n+Warning: some commits may have been dropped accidentally.\n+Dropped commits (newer to older):\n+ - $(git rev-list --pretty=oneline --abbrev-commit -1 master)\n+To avoid this message, use \"drop\" to explicitly remove a commit.\n+\n+Use 'git config rebase.missingCommitsCheck' to change the level of warnings.\n+The possible behaviours are: ignore, warn, error.\n+\n+Rebasing (1/4)\n+Rebasing (2/4)\n+Rebasing (3/4)\n+Rebasing (4/4)\n+Successfully rebased and updated refs/heads/missing-commit.\n+EOF\n+\n+cr_to_nl () {\n+\ttr '\\015' '\\012'\n+}\n+\n+test_expect_success 'rebase -i respects rebase.missingCommitsCheck = warn' '\n+\ttest_config rebase.missingCommitsCheck warn &&\n+\trebase_setup_and_clean missing-commit &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"1 2 3 4\" \\\n+\t\tgit rebase -i --root 2>actual.2 &&\n+\tcr_to_nl <actual.2 >actual &&\n+\ttest_i18ncmp expect actual &&\n+\ttest D = $(git cat-file commit HEAD | sed -ne \\$p)\n+'\n+\n+cat >expect <<EOF\n+Warning: some commits may have been dropped accidentally.\n+Dropped commits (newer to older):\n+ - $(git rev-list --pretty=oneline --abbrev-commit -1 master)\n+ - $(git rev-list --pretty=oneline --abbrev-commit -1 master~2)\n+To avoid this message, use \"drop\" to explicitly remove a commit.\n+\n+Use 'git config rebase.missingCommitsCheck' to change the level of warnings.\n+The possible behaviours are: ignore, warn, error.\n+\n+You can fix this with 'git rebase --edit-todo' and then run 'git rebase --continue'.\n+Or you can abort the rebase with 'git rebase --abort'.\n+EOF\n+\n+test_expect_success 'rebase -i respects rebase.missingCommitsCheck = error' '\n+\ttest_config rebase.missingCommitsCheck error &&\n+\trebase_setup_and_clean missing-commit &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 2 4\" \\\n+\t\tgit rebase -i --root 2>actual &&\n+\ttest_i18ncmp expect actual &&\n+\tcp .git/rebase-merge/git-rebase-todo.backup \\\n+\t\t.git/rebase-merge/git-rebase-todo &&\n+\tFAKE_LINES=\"1 2 drop 3 4 drop 5\" \\\n+\t\tgit rebase --edit-todo &&\n+\tgit rebase --continue &&\n+\ttest D = $(git cat-file commit HEAD | sed -ne \\$p) &&\n+\ttest B = $(git cat-file commit HEAD^ | sed -ne \\$p)\n+'\n+\n+test_expect_success 'respects rebase.abbreviateCommands with fixup, squash and exec' '\n+\trebase_setup_and_clean abbrevcmd &&\n+\ttest_commit \"first\" file1.txt \"first line\" first &&\n+\ttest_commit \"second\" file1.txt \"another line\" second &&\n+\ttest_commit \"fixup! first\" file2.txt \"first line again\" first_fixup &&\n+\ttest_commit \"squash! second\" file1.txt \"another line here\" second_squash &&\n+\tcat >expected <<-EOF &&\n+\tp $(git rev-list --abbrev-commit -1 first) first\n+\tf $(git rev-list --abbrev-commit -1 first_fixup) fixup! first\n+\tx git show HEAD\n+\tp $(git rev-list --abbrev-commit -1 second) second\n+\ts $(git rev-list --abbrev-commit -1 second_squash) squash! second\n+\tx git show HEAD\n+\tEOF\n+\tgit checkout abbrevcmd &&\n+\tset_cat_todo_editor &&\n+\ttest_config rebase.abbreviateCommands true &&\n+\ttest_must_fail git rebase -i --exec \"git show HEAD\" \\\n+\t\t--autosquash master >actual &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'static check of bad command' '\n+\trebase_setup_and_clean bad-cmd &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 2 3 bad 4 5\" \\\n+\t\tgit rebase -i --root 2>actual &&\n+\ttest_i18ngrep \"badcmd $(git rev-list --oneline -1 master~1)\" actual &&\n+\ttest_i18ngrep \"You can fix this with .git rebase --edit-todo..\" actual &&\n+\tFAKE_LINES=\"1 2 3 drop 4 5\" git rebase --edit-todo &&\n+\tgit rebase --continue &&\n+\ttest E = $(git cat-file commit HEAD | sed -ne \\$p) &&\n+\ttest C = $(git cat-file commit HEAD^ | sed -ne \\$p)\n+'\n+\n+test_expect_success 'tabs and spaces are accepted in the todolist' '\n+\trebase_setup_and_clean indented-comment &&\n+\twrite_script add-indent.sh <<-\\EOF &&\n+\t(\n+\t\t# Turn single spaces into space/tab mix\n+\t\tsed \"1s/ /\t/g; 2s/ /  /g; 3s/ / \t/g\" \"$1\"\n+\t\tprintf \"\\n\\t# comment\\n #more\\n\\t # comment\\n\"\n+\t) >\"$1.new\"\n+\tmv \"$1.new\" \"$1\"\n+\tEOF\n+\ttest_set_editor \"$(pwd)/add-indent.sh\" &&\n+\tgit rebase -i HEAD^^^ &&\n+\ttest E = $(git cat-file commit HEAD | sed -ne \\$p)\n+'\n+\n+test_expect_success 'static check of bad SHA-1' '\n+\trebase_setup_and_clean bad-sha &&\n+\tset_fake_editor &&\n+\ttest_must_fail env FAKE_LINES=\"1 2 edit fakesha 3 4 5 #\" \\\n+\t\tgit rebase -i --root 2>actual &&\n+\ttest_i18ngrep \"edit XXXXXXX False commit\" actual &&\n+\ttest_i18ngrep \"You can fix this with .git rebase --edit-todo..\" actual &&\n+\tFAKE_LINES=\"1 2 4 5 6\" git rebase --edit-todo &&\n+\tgit rebase --continue &&\n+\ttest E = $(git cat-file commit HEAD | sed -ne \\$p)\n+'\n+\n+test_expect_success 'editor saves as CR/LF' '\n+\tgit checkout -b with-crlf &&\n+\twrite_script add-crs.sh <<-\\EOF &&\n+\tsed -e \"s/\\$/Q/\" <\"$1\" | tr Q \"\\\\015\" >\"$1\".new &&\n+\tmv -f \"$1\".new \"$1\"\n+\tEOF\n+\t(\n+\t\ttest_set_editor \"$(pwd)/add-crs.sh\" &&\n+\t\tgit rebase -i HEAD^\n+\t)\n+'\n+\n+SQ=\"'\"\n+test_expect_success 'rebase -i --gpg-sign=<key-id>' '\n+\ttest_when_finished \"test_might_fail git rebase --abort\" &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1\" git rebase -i --gpg-sign=\"\\\"S I Gner\\\"\" HEAD^ \\\n+\t\t>out 2>err &&\n+\ttest_i18ngrep \"$SQ-S\\\"S I Gner\\\"$SQ\" err\n+'\n+\n+test_expect_success 'rebase -i --gpg-sign=<key-id> overrides commit.sign' '\n+\ttest_when_finished \"test_might_fail git rebase --abort\" &&\n+\ttest_config commit.sign true &&\n+\tset_fake_editor &&\n+\tFAKE_LINES=\"edit 1\" git rebase -i --gpg-sign=\"\\\"S I Gner\\\"\" HEAD^ \\\n+\t\t>out 2>err &&\n+\ttest_i18ngrep \"$SQ-S\\\"S I Gner\\\"$SQ\" err\n+'\n+\n+test_expect_success 'valid author header after --root swap' '\n+\trebase_setup_and_clean author-header no-conflict-branch &&\n+\tset_fake_editor &&\n+\tgit commit --amend --author=\"Au ${SQ}thor <author@example.com>\" --no-edit &&\n+\tgit cat-file commit HEAD | grep ^author >expected &&\n+\tFAKE_LINES=\"5 1\" git rebase -i --root &&\n+\tgit cat-file commit HEAD^ | grep ^author >actual &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'valid author header when author contains single quote' '\n+\trebase_setup_and_clean author-header no-conflict-branch &&\n+\tset_fake_editor &&\n+\tgit commit --amend --author=\"Au ${SQ}thor <author@example.com>\" --no-edit &&\n+\tgit cat-file commit HEAD | grep ^author >expected &&\n+\tFAKE_LINES=\"2\" git rebase -i HEAD~2 &&\n+\tgit cat-file commit HEAD | grep ^author >actual &&\n+\ttest_cmp expected actual\n+'\n+\n+test_done\ndiff --git a/t/t4215-log-signconfig.sh b/t/t4215-log-signconfig.sh\nnew file mode 100755\nindex 000000000..a2f2342b0\n--- /dev/null\n+++ b/t/t4215-log-signconfig.sh\n@@ -0,0 +1,1710 @@\n+#!/bin/sh\n+\n+test_description='git log'\n+\n+. ./test-lib.sh\n+. \"$TEST_DIRECTORY/lib-gpg.sh\"\n+. \"$TEST_DIRECTORY/lib-terminal.sh\"\n+\n+test_expect_success setup '\n+\n+\techo one >one &&\n+\tgit add one &&\n+\ttest_tick &&\n+\tgit commit -m initial &&\n+\n+\techo ichi >one &&\n+\tgit add one &&\n+\ttest_tick &&\n+\tgit commit -m second &&\n+\n+\tgit mv one ichi &&\n+\ttest_tick &&\n+\tgit commit -m third &&\n+\n+\tcp ichi ein &&\n+\tgit add ein &&\n+\ttest_tick &&\n+\tgit commit -m fourth &&\n+\n+\tmkdir a &&\n+\techo ni >a/two &&\n+\tgit add a/two &&\n+\ttest_tick &&\n+\tgit commit -m fifth  &&\n+\n+\tgit rm a/two &&\n+\ttest_tick &&\n+\tgit commit -m sixth\n+\n+'\n+\n+printf \"sixth\\nfifth\\nfourth\\nthird\\nsecond\\ninitial\" > expect\n+test_expect_success 'pretty' '\n+\n+\tgit log --pretty=\"format:%s\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+printf \"sixth\\nfifth\\nfourth\\nthird\\nsecond\\ninitial\\n\" > expect\n+test_expect_success 'pretty (tformat)' '\n+\n+\tgit log --pretty=\"tformat:%s\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'pretty (shortcut)' '\n+\n+\tgit log --pretty=\"%s\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'format' '\n+\n+\tgit log --format=\"%s\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect << EOF\n+ This is\n+  the sixth\n+  commit.\n+ This is\n+  the fifth\n+  commit.\n+EOF\n+\n+test_expect_success 'format %w(11,1,2)' '\n+\n+\tgit log -2 --format=\"%w(11,1,2)This is the %s commit.\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'format %w(,1,2)' '\n+\n+\tgit log -2 --format=\"%w(,1,2)This is%nthe %s%ncommit.\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect << EOF\n+804a787 sixth\n+394ef78 fifth\n+5d31159 fourth\n+2fbe8c0 third\n+f7dab8e second\n+3a2fdcb initial\n+EOF\n+test_expect_success 'oneline' '\n+\n+\tgit log --oneline > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'diff-filter=A' '\n+\n+\tgit log --no-renames --pretty=\"format:%s\" --diff-filter=A HEAD > actual &&\n+\tgit log --no-renames --pretty=\"format:%s\" --diff-filter A HEAD > actual-separate &&\n+\tprintf \"fifth\\nfourth\\nthird\\ninitial\" > expect &&\n+\ttest_cmp expect actual &&\n+\ttest_cmp expect actual-separate\n+\n+'\n+\n+test_expect_success 'diff-filter=M' '\n+\n+\tactual=$(git log --pretty=\"format:%s\" --diff-filter=M HEAD) &&\n+\texpect=$(echo second) &&\n+\tverbose test \"$actual\" = \"$expect\"\n+\n+'\n+\n+test_expect_success 'diff-filter=D' '\n+\n+\tactual=$(git log --no-renames --pretty=\"format:%s\" --diff-filter=D HEAD) &&\n+\texpect=$(echo sixth ; echo third) &&\n+\tverbose test \"$actual\" = \"$expect\"\n+\n+'\n+\n+test_expect_success 'diff-filter=R' '\n+\n+\tactual=$(git log -M --pretty=\"format:%s\" --diff-filter=R HEAD) &&\n+\texpect=$(echo third) &&\n+\tverbose test \"$actual\" = \"$expect\"\n+\n+'\n+\n+test_expect_success 'diff-filter=C' '\n+\n+\tactual=$(git log -C -C --pretty=\"format:%s\" --diff-filter=C HEAD) &&\n+\texpect=$(echo fourth) &&\n+\tverbose test \"$actual\" = \"$expect\"\n+\n+'\n+\n+test_expect_success 'git log --follow' '\n+\n+\tactual=$(git log --follow --pretty=\"format:%s\" ichi) &&\n+\texpect=$(echo third ; echo second ; echo initial) &&\n+\tverbose test \"$actual\" = \"$expect\"\n+'\n+\n+test_expect_success 'git config log.follow works like --follow' '\n+\ttest_config log.follow true &&\n+\tactual=$(git log --pretty=\"format:%s\" ichi) &&\n+\texpect=$(echo third ; echo second ; echo initial) &&\n+\tverbose test \"$actual\" = \"$expect\"\n+'\n+\n+test_expect_success 'git config log.follow does not die with multiple paths' '\n+\ttest_config log.follow true &&\n+\tgit log --pretty=\"format:%s\" ichi ein\n+'\n+\n+test_expect_success 'git config log.follow does not die with no paths' '\n+\ttest_config log.follow true &&\n+\tgit log --\n+'\n+\n+test_expect_success 'git config log.follow is overridden by --no-follow' '\n+\ttest_config log.follow true &&\n+\tactual=$(git log --no-follow --pretty=\"format:%s\" ichi) &&\n+\texpect=\"third\" &&\n+\tverbose test \"$actual\" = \"$expect\"\n+'\n+\n+cat > expect << EOF\n+804a787 sixth\n+394ef78 fifth\n+5d31159 fourth\n+EOF\n+test_expect_success 'git log --no-walk <commits> sorts by commit time' '\n+\tgit log --no-walk --oneline 5d31159 804a787 394ef78 > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'git log --no-walk=sorted <commits> sorts by commit time' '\n+\tgit log --no-walk=sorted --oneline 5d31159 804a787 394ef78 > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect << EOF\n+=== 804a787 sixth\n+=== 394ef78 fifth\n+=== 5d31159 fourth\n+EOF\n+test_expect_success 'git log --line-prefix=\"=== \" --no-walk <commits> sorts by commit time' '\n+\tgit log --line-prefix=\"=== \" --no-walk --oneline 5d31159 804a787 394ef78 > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect << EOF\n+5d31159 fourth\n+804a787 sixth\n+394ef78 fifth\n+EOF\n+test_expect_success 'git log --no-walk=unsorted <commits> leaves list of commits as given' '\n+\tgit log --no-walk=unsorted --oneline 5d31159 804a787 394ef78 > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'git show <commits> leaves list of commits as given' '\n+\tgit show --oneline -s 5d31159 804a787 394ef78 > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'setup case sensitivity tests' '\n+\techo case >one &&\n+\ttest_tick &&\n+\tgit add one &&\n+\tgit commit -a -m Second\n+'\n+\n+test_expect_success 'log --grep' '\n+\techo second >expect &&\n+\tgit log -1 --pretty=\"tformat:%s\" --grep=sec >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect << EOF\n+second\n+initial\n+EOF\n+test_expect_success 'log --invert-grep --grep' '\n+\t# Fixed\n+\tgit -c grep.patternType=fixed log --pretty=\"tformat:%s\" --invert-grep --grep=th --grep=Sec >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# POSIX basic\n+\tgit -c grep.patternType=basic log --pretty=\"tformat:%s\" --invert-grep --grep=t[h] --grep=S[e]c >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# POSIX extended\n+\tgit -c grep.patternType=basic log --pretty=\"tformat:%s\" --invert-grep --grep=t[h] --grep=S[e]c >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# PCRE\n+\tif test_have_prereq PCRE\n+\tthen\n+\t\tgit -c grep.patternType=perl log --pretty=\"tformat:%s\" --invert-grep --grep=t[h] --grep=S[e]c >actual &&\n+\t\ttest_cmp expect actual\n+\tfi\n+'\n+\n+test_expect_success 'log --invert-grep --grep -i' '\n+\techo initial >expect &&\n+\n+\t# Fixed\n+\tgit -c grep.patternType=fixed log --pretty=\"tformat:%s\" --invert-grep -i --grep=th --grep=Sec >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# POSIX basic\n+\tgit -c grep.patternType=basic log --pretty=\"tformat:%s\" --invert-grep -i --grep=t[h] --grep=S[e]c >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# POSIX extended\n+\tgit -c grep.patternType=extended log --pretty=\"tformat:%s\" --invert-grep -i --grep=t[h] --grep=S[e]c >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# PCRE\n+\tif test_have_prereq PCRE\n+\tthen\n+\t\tgit -c grep.patternType=perl log --pretty=\"tformat:%s\" --invert-grep -i --grep=t[h] --grep=S[e]c >actual &&\n+\t\ttest_cmp expect actual\n+\tfi\n+'\n+\n+test_expect_success 'log --grep option parsing' '\n+\techo second >expect &&\n+\tgit log -1 --pretty=\"tformat:%s\" --grep sec >actual &&\n+\ttest_cmp expect actual &&\n+\ttest_must_fail git log -1 --pretty=\"tformat:%s\" --grep\n+'\n+\n+test_expect_success 'log -i --grep' '\n+\techo Second >expect &&\n+\tgit log -1 --pretty=\"tformat:%s\" -i --grep=sec >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'log --grep -i' '\n+\techo Second >expect &&\n+\n+\t# Fixed\n+\tgit log -1 --pretty=\"tformat:%s\" --grep=sec -i >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# POSIX basic\n+\tgit -c grep.patternType=basic log -1 --pretty=\"tformat:%s\" --grep=s[e]c -i >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# POSIX extended\n+\tgit -c grep.patternType=extended log -1 --pretty=\"tformat:%s\" --grep=s[e]c -i >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# PCRE\n+\tif test_have_prereq PCRE\n+\tthen\n+\t\tgit -c grep.patternType=perl log -1 --pretty=\"tformat:%s\" --grep=s[e]c -i >actual &&\n+\t\ttest_cmp expect actual\n+\tfi\n+'\n+\n+test_expect_success 'log -F -E --grep=<ere> uses ere' '\n+\techo second >expect &&\n+\t# basic would need \\(s\\) to do the same\n+\tgit log -1 --pretty=\"tformat:%s\" -F -E --grep=\"(s).c.nd\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success PCRE 'log -F -E --perl-regexp --grep=<pcre> uses PCRE' '\n+\ttest_when_finished \"rm -rf num_commits\" &&\n+\tgit init num_commits &&\n+\t(\n+\t\tcd num_commits &&\n+\t\ttest_commit 1d &&\n+\t\ttest_commit 2e\n+\t) &&\n+\n+\t# In PCRE \\d in [\\d] is like saying \"0-9\", and matches the 2\n+\t# in 2e...\n+\techo 2e >expect &&\n+\tgit -C num_commits log -1 --pretty=\"tformat:%s\" -F -E --perl-regexp --grep=\"[\\d]\" >actual &&\n+\ttest_cmp expect actual &&\n+\n+\t# ...in POSIX basic and extended it is the same as [d],\n+\t# i.e. \"d\", which matches 1d, but does not match 2e.\n+\techo 1d >expect &&\n+\tgit -C num_commits log -1 --pretty=\"tformat:%s\" -F -E --grep=\"[\\d]\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'log with grep.patternType configuration' '\n+\tgit -c grep.patterntype=fixed \\\n+\tlog -1 --pretty=tformat:%s --grep=s.c.nd >actual &&\n+\ttest_must_be_empty actual\n+'\n+\n+test_expect_success 'log with grep.patternType configuration and command line' '\n+\techo second >expect &&\n+\tgit -c grep.patterntype=fixed \\\n+\tlog -1 --pretty=tformat:%s --basic-regexp --grep=s.c.nd >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success !FAIL_PREREQS 'log with various grep.patternType configurations & command-lines' '\n+\tgit init pattern-type &&\n+\t(\n+\t\tcd pattern-type &&\n+\t\ttest_commit 1 file A &&\n+\n+\t\t# The tagname is overridden here because creating a\n+\t\t# tag called \"(1|2)\" as test_commit would otherwise\n+\t\t# implicitly do would fail on e.g. MINGW.\n+\t\ttest_commit \"(1|2)\" file B 2 &&\n+\n+\t\techo \"(1|2)\" >expect.fixed &&\n+\t\tcp expect.fixed expect.basic &&\n+\t\tcp expect.fixed expect.extended &&\n+\t\tcp expect.fixed expect.perl &&\n+\n+\t\t# A strcmp-like match with fixed.\n+\t\tgit -c grep.patternType=fixed log --pretty=tformat:%s \\\n+\t\t\t--grep=\"(1|2)\" >actual.fixed &&\n+\n+\t\t# POSIX basic matches (, | and ) literally.\n+\t\tgit -c grep.patternType=basic log --pretty=tformat:%s \\\n+\t\t\t--grep=\"(.|.)\" >actual.basic &&\n+\n+\t\t# POSIX extended needs to have | escaped to match it\n+\t\t# literally, whereas under basic this is the same as\n+\t\t# (|2), i.e. it would also match \"1\". This test checks\n+\t\t# for extended by asserting that it is not matching\n+\t\t# what basic would match.\n+\t\tgit -c grep.patternType=extended log --pretty=tformat:%s \\\n+\t\t\t--grep=\"\\|2\" >actual.extended &&\n+\t\tif test_have_prereq PCRE\n+\t\tthen\n+\t\t\t# Only PCRE would match [\\d]\\| with only\n+\t\t\t# \"(1|2)\" due to [\\d]. POSIX basic would match\n+\t\t\t# both it and \"1\" since similarly to the\n+\t\t\t# extended match above it is the same as\n+\t\t\t# \\([\\d]\\|\\). POSIX extended would\n+\t\t\t# match neither.\n+\t\t\tgit -c grep.patternType=perl log --pretty=tformat:%s \\\n+\t\t\t\t--grep=\"[\\d]\\|\" >actual.perl &&\n+\t\t\ttest_cmp expect.perl actual.perl\n+\t\tfi &&\n+\t\ttest_cmp expect.fixed actual.fixed &&\n+\t\ttest_cmp expect.basic actual.basic &&\n+\t\ttest_cmp expect.extended actual.extended &&\n+\n+\t\tgit log --pretty=tformat:%s -F \\\n+\t\t\t--grep=\"(1|2)\" >actual.fixed.short-arg &&\n+\t\tgit log --pretty=tformat:%s -E \\\n+\t\t\t--grep=\"\\|2\" >actual.extended.short-arg &&\n+\t\tif test_have_prereq PCRE\n+\t\tthen\n+\t\t\tgit log --pretty=tformat:%s -P \\\n+\t\t\t\t--grep=\"[\\d]\\|\" >actual.perl.short-arg\n+\t\telse\n+\t\t\ttest_must_fail git log -P \\\n+\t\t\t\t--grep=\"[\\d]\\|\"\n+\t\tfi &&\n+\t\ttest_cmp expect.fixed actual.fixed.short-arg &&\n+\t\ttest_cmp expect.extended actual.extended.short-arg &&\n+\t\tif test_have_prereq PCRE\n+\t\tthen\n+\t\t\ttest_cmp expect.perl actual.perl.short-arg\n+\t\tfi &&\n+\n+\t\tgit log --pretty=tformat:%s --fixed-strings \\\n+\t\t\t--grep=\"(1|2)\" >actual.fixed.long-arg &&\n+\t\tgit log --pretty=tformat:%s --basic-regexp \\\n+\t\t\t--grep=\"(.|.)\" >actual.basic.long-arg &&\n+\t\tgit log --pretty=tformat:%s --extended-regexp \\\n+\t\t\t--grep=\"\\|2\" >actual.extended.long-arg &&\n+\t\tif test_have_prereq PCRE\n+\t\tthen\n+\t\t\tgit log --pretty=tformat:%s --perl-regexp \\\n+\t\t\t\t--grep=\"[\\d]\\|\" >actual.perl.long-arg &&\n+\t\t\ttest_cmp expect.perl actual.perl.long-arg\n+\t\telse\n+\t\t\ttest_must_fail git log --perl-regexp \\\n+\t\t\t\t--grep=\"[\\d]\\|\"\n+\t\tfi &&\n+\t\ttest_cmp expect.fixed actual.fixed.long-arg &&\n+\t\ttest_cmp expect.basic actual.basic.long-arg &&\n+\t\ttest_cmp expect.extended actual.extended.long-arg\n+\t)\n+'\n+\n+cat > expect <<EOF\n+* Second\n+* sixth\n+* fifth\n+* fourth\n+* third\n+* second\n+* initial\n+EOF\n+\n+test_expect_success 'simple log --graph' '\n+\tgit log --graph --pretty=tformat:%s >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect <<EOF\n+123 * Second\n+123 * sixth\n+123 * fifth\n+123 * fourth\n+123 * third\n+123 * second\n+123 * initial\n+EOF\n+\n+test_expect_success 'simple log --graph --line-prefix=\"123 \"' '\n+\tgit log --graph --line-prefix=\"123 \" --pretty=tformat:%s >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'set up merge history' '\n+\tgit checkout -b side HEAD~4 &&\n+\ttest_commit side-1 1 1 &&\n+\ttest_commit side-2 2 2 &&\n+\tgit checkout master &&\n+\tgit merge side\n+'\n+\n+cat > expect <<\\EOF\n+*   Merge branch 'side'\n+|\\\n+| * side-2\n+| * side-1\n+* | Second\n+* | sixth\n+* | fifth\n+* | fourth\n+|/\n+* third\n+* second\n+* initial\n+EOF\n+\n+test_expect_success 'log --graph with merge' '\n+\tgit log --graph --date-order --pretty=tformat:%s |\n+\t\tsed \"s/ *\\$//\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect <<\\EOF\n+| | | *   Merge branch 'side'\n+| | | |\\\n+| | | | * side-2\n+| | | | * side-1\n+| | | * | Second\n+| | | * | sixth\n+| | | * | fifth\n+| | | * | fourth\n+| | | |/\n+| | | * third\n+| | | * second\n+| | | * initial\n+EOF\n+\n+test_expect_success 'log --graph --line-prefix=\"| | | \" with merge' '\n+\tgit log --line-prefix=\"| | | \" --graph --date-order --pretty=tformat:%s |\n+\t\tsed \"s/ *\\$//\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat > expect.colors <<\\EOF\n+*   Merge branch 'side'\n+<BLUE>|<RESET><CYAN>\\<RESET>\n+<BLUE>|<RESET> * side-2\n+<BLUE>|<RESET> * side-1\n+* <CYAN>|<RESET> Second\n+* <CYAN>|<RESET> sixth\n+* <CYAN>|<RESET> fifth\n+* <CYAN>|<RESET> fourth\n+<CYAN>|<RESET><CYAN>/<RESET>\n+* third\n+* second\n+* initial\n+EOF\n+\n+test_expect_success 'log --graph with merge with log.graphColors' '\n+\ttest_config log.graphColors \" blue,invalid-color, cyan, red  , \" &&\n+\tgit log --color=always --graph --date-order --pretty=tformat:%s |\n+\t\ttest_decode_color | sed \"s/ *\\$//\" >actual &&\n+\ttest_cmp expect.colors actual\n+'\n+\n+test_expect_success 'log --raw --graph -m with merge' '\n+\tgit log --raw --graph --oneline -m master | head -n 500 >actual &&\n+\tgrep \"initial\" actual\n+'\n+\n+test_expect_success 'diff-tree --graph' '\n+\tgit diff-tree --graph master^ | head -n 500 >actual &&\n+\tgrep \"one\" actual\n+'\n+\n+cat > expect <<\\EOF\n+*   commit master\n+|\\  Merge: A B\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     Merge branch 'side'\n+| |\n+| * commit tags/side-2\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     side-2\n+| |\n+| * commit tags/side-1\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     side-1\n+| |\n+* | commit master~1\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     Second\n+| |\n+* | commit master~2\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     sixth\n+| |\n+* | commit master~3\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     fifth\n+| |\n+* | commit master~4\n+|/  Author: A U Thor <author@example.com>\n+|\n+|       fourth\n+|\n+* commit tags/side-1~1\n+| Author: A U Thor <author@example.com>\n+|\n+|     third\n+|\n+* commit tags/side-1~2\n+| Author: A U Thor <author@example.com>\n+|\n+|     second\n+|\n+* commit tags/side-1~3\n+  Author: A U Thor <author@example.com>\n+\n+      initial\n+EOF\n+\n+test_expect_success 'log --graph with full output' '\n+\tgit log --graph --date-order --pretty=short |\n+\t\tgit name-rev --name-only --stdin |\n+\t\tsed \"s/Merge:.*/Merge: A B/;s/ *\\$//\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'set up more tangled history' '\n+\tgit checkout -b tangle HEAD~6 &&\n+\ttest_commit tangle-a tangle-a a &&\n+\tgit merge master~3 &&\n+\tgit merge side~1 &&\n+\tgit checkout master &&\n+\tgit merge tangle &&\n+\tgit checkout -b reach &&\n+\ttest_commit reach &&\n+\tgit checkout master &&\n+\tgit checkout -b octopus-a &&\n+\ttest_commit octopus-a &&\n+\tgit checkout master &&\n+\tgit checkout -b octopus-b &&\n+\ttest_commit octopus-b &&\n+\tgit checkout master &&\n+\ttest_commit seventh &&\n+\tgit merge octopus-a octopus-b &&\n+\tgit merge reach\n+'\n+\n+cat > expect <<\\EOF\n+*   Merge tag 'reach'\n+|\\\n+| \\\n+|  \\\n+*-. \\   Merge tags 'octopus-a' and 'octopus-b'\n+|\\ \\ \\\n+* | | | seventh\n+| | * | octopus-b\n+| |/ /\n+|/| |\n+| * | octopus-a\n+|/ /\n+| * reach\n+|/\n+*   Merge branch 'tangle'\n+|\\\n+| *   Merge branch 'side' (early part) into tangle\n+| |\\\n+| * \\   Merge branch 'master' (early part) into tangle\n+| |\\ \\\n+| * | | tangle-a\n+* | | |   Merge branch 'side'\n+|\\ \\ \\ \\\n+| * | | | side-2\n+| | |_|/\n+| |/| |\n+| * | | side-1\n+* | | | Second\n+* | | | sixth\n+| |_|/\n+|/| |\n+* | | fifth\n+* | | fourth\n+|/ /\n+* | third\n+|/\n+* second\n+* initial\n+EOF\n+\n+test_expect_success 'log --graph with merge' '\n+\tgit log --graph --date-order --pretty=tformat:%s |\n+\t\tsed \"s/ *\\$//\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'log.decorate configuration' '\n+\tgit log --oneline --no-decorate >expect.none &&\n+\tgit log --oneline --decorate >expect.short &&\n+\tgit log --oneline --decorate=full >expect.full &&\n+\n+\techo \"[log] decorate\" >>.git/config &&\n+\tgit log --oneline >actual &&\n+\ttest_cmp expect.short actual &&\n+\n+\ttest_config log.decorate true &&\n+\tgit log --oneline >actual &&\n+\ttest_cmp expect.short actual &&\n+\tgit log --oneline --decorate=full >actual &&\n+\ttest_cmp expect.full actual &&\n+\tgit log --oneline --decorate=no >actual &&\n+\ttest_cmp expect.none actual &&\n+\n+\ttest_config log.decorate no &&\n+\tgit log --oneline >actual &&\n+\ttest_cmp expect.none actual &&\n+\tgit log --oneline --decorate >actual &&\n+\ttest_cmp expect.short actual &&\n+\tgit log --oneline --decorate=full >actual &&\n+\ttest_cmp expect.full actual &&\n+\n+\ttest_config log.decorate 1 &&\n+\tgit log --oneline >actual &&\n+\ttest_cmp expect.short actual &&\n+\tgit log --oneline --decorate=full >actual &&\n+\ttest_cmp expect.full actual &&\n+\tgit log --oneline --decorate=no >actual &&\n+\ttest_cmp expect.none actual &&\n+\n+\ttest_config log.decorate short &&\n+\tgit log --oneline >actual &&\n+\ttest_cmp expect.short actual &&\n+\tgit log --oneline --no-decorate >actual &&\n+\ttest_cmp expect.none actual &&\n+\tgit log --oneline --decorate=full >actual &&\n+\ttest_cmp expect.full actual &&\n+\n+\ttest_config log.decorate full &&\n+\tgit log --oneline >actual &&\n+\ttest_cmp expect.full actual &&\n+\tgit log --oneline --no-decorate >actual &&\n+\ttest_cmp expect.none actual &&\n+\tgit log --oneline --decorate >actual &&\n+\ttest_cmp expect.short actual &&\n+\n+\ttest_unconfig log.decorate &&\n+\tgit log --pretty=raw >expect.raw &&\n+\ttest_config log.decorate full &&\n+\tgit log --pretty=raw >actual &&\n+\ttest_cmp expect.raw actual\n+\n+'\n+\n+test_expect_success 'decorate-refs with glob' '\n+\tcat >expect.decorate <<-\\EOF &&\n+\tMerge-tag-reach\n+\tMerge-tags-octopus-a-and-octopus-b\n+\tseventh\n+\toctopus-b (octopus-b)\n+\toctopus-a (octopus-a)\n+\treach\n+\tEOF\n+\tgit log -n6 --decorate=short --pretty=\"tformat:%f%d\" \\\n+\t\t--decorate-refs=\"heads/octopus*\" >actual &&\n+\ttest_cmp expect.decorate actual\n+'\n+\n+test_expect_success 'decorate-refs without globs' '\n+\tcat >expect.decorate <<-\\EOF &&\n+\tMerge-tag-reach\n+\tMerge-tags-octopus-a-and-octopus-b\n+\tseventh\n+\toctopus-b\n+\toctopus-a\n+\treach (tag: reach)\n+\tEOF\n+\tgit log -n6 --decorate=short --pretty=\"tformat:%f%d\" \\\n+\t\t--decorate-refs=\"tags/reach\" >actual &&\n+\ttest_cmp expect.decorate actual\n+'\n+\n+test_expect_success 'multiple decorate-refs' '\n+\tcat >expect.decorate <<-\\EOF &&\n+\tMerge-tag-reach\n+\tMerge-tags-octopus-a-and-octopus-b\n+\tseventh\n+\toctopus-b (octopus-b)\n+\toctopus-a (octopus-a)\n+\treach (tag: reach)\n+\tEOF\n+\tgit log -n6 --decorate=short --pretty=\"tformat:%f%d\" \\\n+\t\t--decorate-refs=\"heads/octopus*\" \\\n+\t\t--decorate-refs=\"tags/reach\" >actual &&\n+    test_cmp expect.decorate actual\n+'\n+\n+test_expect_success 'decorate-refs-exclude with glob' '\n+\tcat >expect.decorate <<-\\EOF &&\n+\tMerge-tag-reach (HEAD -> master)\n+\tMerge-tags-octopus-a-and-octopus-b\n+\tseventh (tag: seventh)\n+\toctopus-b (tag: octopus-b)\n+\toctopus-a (tag: octopus-a)\n+\treach (tag: reach, reach)\n+\tEOF\n+\tgit log -n6 --decorate=short --pretty=\"tformat:%f%d\" \\\n+\t\t--decorate-refs-exclude=\"heads/octopus*\" >actual &&\n+\ttest_cmp expect.decorate actual\n+'\n+\n+test_expect_success 'decorate-refs-exclude without globs' '\n+\tcat >expect.decorate <<-\\EOF &&\n+\tMerge-tag-reach (HEAD -> master)\n+\tMerge-tags-octopus-a-and-octopus-b\n+\tseventh (tag: seventh)\n+\toctopus-b (tag: octopus-b, octopus-b)\n+\toctopus-a (tag: octopus-a, octopus-a)\n+\treach (reach)\n+\tEOF\n+\tgit log -n6 --decorate=short --pretty=\"tformat:%f%d\" \\\n+\t\t--decorate-refs-exclude=\"tags/reach\" >actual &&\n+\ttest_cmp expect.decorate actual\n+'\n+\n+test_expect_success 'multiple decorate-refs-exclude' '\n+\tcat >expect.decorate <<-\\EOF &&\n+\tMerge-tag-reach (HEAD -> master)\n+\tMerge-tags-octopus-a-and-octopus-b\n+\tseventh (tag: seventh)\n+\toctopus-b (tag: octopus-b)\n+\toctopus-a (tag: octopus-a)\n+\treach (reach)\n+\tEOF\n+\tgit log -n6 --decorate=short --pretty=\"tformat:%f%d\" \\\n+\t\t--decorate-refs-exclude=\"heads/octopus*\" \\\n+\t\t--decorate-refs-exclude=\"tags/reach\" >actual &&\n+\ttest_cmp expect.decorate actual\n+'\n+\n+test_expect_success 'decorate-refs and decorate-refs-exclude' '\n+\tcat >expect.decorate <<-\\EOF &&\n+\tMerge-tag-reach (master)\n+\tMerge-tags-octopus-a-and-octopus-b\n+\tseventh\n+\toctopus-b\n+\toctopus-a\n+\treach (reach)\n+\tEOF\n+\tgit log -n6 --decorate=short --pretty=\"tformat:%f%d\" \\\n+\t\t--decorate-refs=\"heads/*\" \\\n+\t\t--decorate-refs-exclude=\"heads/oc*\" >actual &&\n+\ttest_cmp expect.decorate actual\n+'\n+\n+test_expect_success 'log.decorate config parsing' '\n+\tgit log --oneline --decorate=full >expect.full &&\n+\tgit log --oneline --decorate=short >expect.short &&\n+\n+\ttest_config log.decorate full &&\n+\ttest_config log.mailmap true &&\n+\tgit log --oneline >actual &&\n+\ttest_cmp expect.full actual &&\n+\tgit log --oneline --decorate=short >actual &&\n+\ttest_cmp expect.short actual\n+'\n+\n+test_expect_success TTY 'log output on a TTY' '\n+\tgit log --color --oneline --decorate >expect.short &&\n+\n+\ttest_terminal git log --oneline >actual &&\n+\ttest_cmp expect.short actual\n+'\n+\n+test_expect_success 'reflog is expected format' '\n+\tgit log -g --abbrev-commit --pretty=oneline >expect &&\n+\tgit reflog >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'whatchanged is expected format' '\n+\tgit log --no-merges --raw >expect &&\n+\tgit whatchanged >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'log.abbrevCommit configuration' '\n+\tgit log --abbrev-commit >expect.log.abbrev &&\n+\tgit log --no-abbrev-commit >expect.log.full &&\n+\tgit log --pretty=raw >expect.log.raw &&\n+\tgit reflog --abbrev-commit >expect.reflog.abbrev &&\n+\tgit reflog --no-abbrev-commit >expect.reflog.full &&\n+\tgit whatchanged --abbrev-commit >expect.whatchanged.abbrev &&\n+\tgit whatchanged --no-abbrev-commit >expect.whatchanged.full &&\n+\n+\ttest_config log.abbrevCommit true &&\n+\n+\tgit log >actual &&\n+\ttest_cmp expect.log.abbrev actual &&\n+\tgit log --no-abbrev-commit >actual &&\n+\ttest_cmp expect.log.full actual &&\n+\n+\tgit log --pretty=raw >actual &&\n+\ttest_cmp expect.log.raw actual &&\n+\n+\tgit reflog >actual &&\n+\ttest_cmp expect.reflog.abbrev actual &&\n+\tgit reflog --no-abbrev-commit >actual &&\n+\ttest_cmp expect.reflog.full actual &&\n+\n+\tgit whatchanged >actual &&\n+\ttest_cmp expect.whatchanged.abbrev actual &&\n+\tgit whatchanged --no-abbrev-commit >actual &&\n+\ttest_cmp expect.whatchanged.full actual\n+'\n+\n+test_expect_success 'show added path under \"--follow -M\"' '\n+\t# This tests for a regression introduced in v1.7.2-rc0~103^2~2\n+\ttest_create_repo regression &&\n+\t(\n+\t\tcd regression &&\n+\t\ttest_commit needs-another-commit &&\n+\t\ttest_commit foo.bar &&\n+\t\tgit log -M --follow -p foo.bar.t &&\n+\t\tgit log -M --follow --stat foo.bar.t &&\n+\t\tgit log -M --follow --name-only foo.bar.t\n+\t)\n+'\n+\n+test_expect_success 'git log -c --follow' '\n+\ttest_create_repo follow-c &&\n+\t(\n+\t\tcd follow-c &&\n+\t\ttest_commit initial file original &&\n+\t\tgit rm file &&\n+\t\ttest_commit rename file2 original &&\n+\t\tgit reset --hard initial &&\n+\t\ttest_commit modify file foo &&\n+\t\tgit merge -m merge rename &&\n+\t\tgit log -c --follow file2\n+\t)\n+'\n+\n+cat >expect <<\\EOF\n+*   commit COMMIT_OBJECT_NAME\n+|\\  Merge: MERGE_PARENTS\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     Merge HEADS DESCRIPTION\n+| |\n+| * commit COMMIT_OBJECT_NAME\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     reach\n+| | ---\n+| |  reach.t | 1 +\n+| |  1 file changed, 1 insertion(+)\n+| |\n+| | diff --git a/reach.t b/reach.t\n+| | new file mode 100644\n+| | index 0000000..10c9591\n+| | --- /dev/null\n+| | +++ b/reach.t\n+| | @@ -0,0 +1 @@\n+| | +reach\n+| |\n+|  \\\n+*-. \\   commit COMMIT_OBJECT_NAME\n+|\\ \\ \\  Merge: MERGE_PARENTS\n+| | | | Author: A U Thor <author@example.com>\n+| | | |\n+| | | |     Merge HEADS DESCRIPTION\n+| | | |\n+| | * | commit COMMIT_OBJECT_NAME\n+| | |/  Author: A U Thor <author@example.com>\n+| | |\n+| | |       octopus-b\n+| | |   ---\n+| | |    octopus-b.t | 1 +\n+| | |    1 file changed, 1 insertion(+)\n+| | |\n+| | |   diff --git a/octopus-b.t b/octopus-b.t\n+| | |   new file mode 100644\n+| | |   index 0000000..d5fcad0\n+| | |   --- /dev/null\n+| | |   +++ b/octopus-b.t\n+| | |   @@ -0,0 +1 @@\n+| | |   +octopus-b\n+| | |\n+| * | commit COMMIT_OBJECT_NAME\n+| |/  Author: A U Thor <author@example.com>\n+| |\n+| |       octopus-a\n+| |   ---\n+| |    octopus-a.t | 1 +\n+| |    1 file changed, 1 insertion(+)\n+| |\n+| |   diff --git a/octopus-a.t b/octopus-a.t\n+| |   new file mode 100644\n+| |   index 0000000..11ee015\n+| |   --- /dev/null\n+| |   +++ b/octopus-a.t\n+| |   @@ -0,0 +1 @@\n+| |   +octopus-a\n+| |\n+* | commit COMMIT_OBJECT_NAME\n+|/  Author: A U Thor <author@example.com>\n+|\n+|       seventh\n+|   ---\n+|    seventh.t | 1 +\n+|    1 file changed, 1 insertion(+)\n+|\n+|   diff --git a/seventh.t b/seventh.t\n+|   new file mode 100644\n+|   index 0000000..9744ffc\n+|   --- /dev/null\n+|   +++ b/seventh.t\n+|   @@ -0,0 +1 @@\n+|   +seventh\n+|\n+*   commit COMMIT_OBJECT_NAME\n+|\\  Merge: MERGE_PARENTS\n+| | Author: A U Thor <author@example.com>\n+| |\n+| |     Merge branch 'tangle'\n+| |\n+| *   commit COMMIT_OBJECT_NAME\n+| |\\  Merge: MERGE_PARENTS\n+| | | Author: A U Thor <author@example.com>\n+| | |\n+| | |     Merge branch 'side' (early part) into tangle\n+| | |\n+| * |   commit COMMIT_OBJECT_NAME\n+| |\\ \\  Merge: MERGE_PARENTS\n+| | | | Author: A U Thor <author@example.com>\n+| | | |\n+| | | |     Merge branch 'master' (early part) into tangle\n+| | | |\n+| * | | commit COMMIT_OBJECT_NAME\n+| | | | Author: A U Thor <author@example.com>\n+| | | |\n+| | | |     tangle-a\n+| | | | ---\n+| | | |  tangle-a | 1 +\n+| | | |  1 file changed, 1 insertion(+)\n+| | | |\n+| | | | diff --git a/tangle-a b/tangle-a\n+| | | | new file mode 100644\n+| | | | index 0000000..7898192\n+| | | | --- /dev/null\n+| | | | +++ b/tangle-a\n+| | | | @@ -0,0 +1 @@\n+| | | | +a\n+| | | |\n+* | | |   commit COMMIT_OBJECT_NAME\n+|\\ \\ \\ \\  Merge: MERGE_PARENTS\n+| | | | | Author: A U Thor <author@example.com>\n+| | | | |\n+| | | | |     Merge branch 'side'\n+| | | | |\n+| * | | | commit COMMIT_OBJECT_NAME\n+| | |_|/  Author: A U Thor <author@example.com>\n+| |/| |\n+| | | |       side-2\n+| | | |   ---\n+| | | |    2 | 1 +\n+| | | |    1 file changed, 1 insertion(+)\n+| | | |\n+| | | |   diff --git a/2 b/2\n+| | | |   new file mode 100644\n+| | | |   index 0000000..0cfbf08\n+| | | |   --- /dev/null\n+| | | |   +++ b/2\n+| | | |   @@ -0,0 +1 @@\n+| | | |   +2\n+| | | |\n+| * | | commit COMMIT_OBJECT_NAME\n+| | | | Author: A U Thor <author@example.com>\n+| | | |\n+| | | |     side-1\n+| | | | ---\n+| | | |  1 | 1 +\n+| | | |  1 file changed, 1 insertion(+)\n+| | | |\n+| | | | diff --git a/1 b/1\n+| | | | new file mode 100644\n+| | | | index 0000000..d00491f\n+| | | | --- /dev/null\n+| | | | +++ b/1\n+| | | | @@ -0,0 +1 @@\n+| | | | +1\n+| | | |\n+* | | | commit COMMIT_OBJECT_NAME\n+| | | | Author: A U Thor <author@example.com>\n+| | | |\n+| | | |     Second\n+| | | | ---\n+| | | |  one | 1 +\n+| | | |  1 file changed, 1 insertion(+)\n+| | | |\n+| | | | diff --git a/one b/one\n+| | | | new file mode 100644\n+| | | | index 0000000..9a33383\n+| | | | --- /dev/null\n+| | | | +++ b/one\n+| | | | @@ -0,0 +1 @@\n+| | | | +case\n+| | | |\n+* | | | commit COMMIT_OBJECT_NAME\n+| |_|/  Author: A U Thor <author@example.com>\n+|/| |\n+| | |       sixth\n+| | |   ---\n+| | |    a/two | 1 -\n+| | |    1 file changed, 1 deletion(-)\n+| | |\n+| | |   diff --git a/a/two b/a/two\n+| | |   deleted file mode 100644\n+| | |   index 9245af5..0000000\n+| | |   --- a/a/two\n+| | |   +++ /dev/null\n+| | |   @@ -1 +0,0 @@\n+| | |   -ni\n+| | |\n+* | | commit COMMIT_OBJECT_NAME\n+| | | Author: A U Thor <author@example.com>\n+| | |\n+| | |     fifth\n+| | | ---\n+| | |  a/two | 1 +\n+| | |  1 file changed, 1 insertion(+)\n+| | |\n+| | | diff --git a/a/two b/a/two\n+| | | new file mode 100644\n+| | | index 0000000..9245af5\n+| | | --- /dev/null\n+| | | +++ b/a/two\n+| | | @@ -0,0 +1 @@\n+| | | +ni\n+| | |\n+* | | commit COMMIT_OBJECT_NAME\n+|/ /  Author: A U Thor <author@example.com>\n+| |\n+| |       fourth\n+| |   ---\n+| |    ein | 1 +\n+| |    1 file changed, 1 insertion(+)\n+| |\n+| |   diff --git a/ein b/ein\n+| |   new file mode 100644\n+| |   index 0000000..9d7e69f\n+| |   --- /dev/null\n+| |   +++ b/ein\n+| |   @@ -0,0 +1 @@\n+| |   +ichi\n+| |\n+* | commit COMMIT_OBJECT_NAME\n+|/  Author: A U Thor <author@example.com>\n+|\n+|       third\n+|   ---\n+|    ichi | 1 +\n+|    one  | 1 -\n+|    2 files changed, 1 insertion(+), 1 deletion(-)\n+|\n+|   diff --git a/ichi b/ichi\n+|   new file mode 100644\n+|   index 0000000..9d7e69f\n+|   --- /dev/null\n+|   +++ b/ichi\n+|   @@ -0,0 +1 @@\n+|   +ichi\n+|   diff --git a/one b/one\n+|   deleted file mode 100644\n+|   index 9d7e69f..0000000\n+|   --- a/one\n+|   +++ /dev/null\n+|   @@ -1 +0,0 @@\n+|   -ichi\n+|\n+* commit COMMIT_OBJECT_NAME\n+| Author: A U Thor <author@example.com>\n+|\n+|     second\n+| ---\n+|  one | 2 +-\n+|  1 file changed, 1 insertion(+), 1 deletion(-)\n+|\n+| diff --git a/one b/one\n+| index 5626abf..9d7e69f 100644\n+| --- a/one\n+| +++ b/one\n+| @@ -1 +1 @@\n+| -one\n+| +ichi\n+|\n+* commit COMMIT_OBJECT_NAME\n+  Author: A U Thor <author@example.com>\n+\n+      initial\n+  ---\n+   one | 1 +\n+   1 file changed, 1 insertion(+)\n+\n+  diff --git a/one b/one\n+  new file mode 100644\n+  index 0000000..5626abf\n+  --- /dev/null\n+  +++ b/one\n+  @@ -0,0 +1 @@\n+  +one\n+EOF\n+\n+sanitize_output () {\n+\tsed -e 's/ *$//' \\\n+\t    -e 's/commit [0-9a-f]*$/commit COMMIT_OBJECT_NAME/' \\\n+\t    -e 's/Merge: [ 0-9a-f]*$/Merge: MERGE_PARENTS/' \\\n+\t    -e 's/Merge tag.*/Merge HEADS DESCRIPTION/' \\\n+\t    -e 's/Merge commit.*/Merge HEADS DESCRIPTION/' \\\n+\t    -e 's/, 0 deletions(-)//' \\\n+\t    -e 's/, 0 insertions(+)//' \\\n+\t    -e 's/ 1 files changed, / 1 file changed, /' \\\n+\t    -e 's/, 1 deletions(-)/, 1 deletion(-)/' \\\n+\t    -e 's/, 1 insertions(+)/, 1 insertion(+)/'\n+}\n+\n+test_expect_success 'log --graph with diff and stats' '\n+\tgit log --no-renames --graph --pretty=short --stat -p >actual &&\n+\tsanitize_output >actual.sanitized <actual &&\n+\ttest_i18ncmp expect actual.sanitized\n+'\n+\n+cat >expect <<\\EOF\n+*** *   commit COMMIT_OBJECT_NAME\n+*** |\\  Merge: MERGE_PARENTS\n+*** | | Author: A U Thor <author@example.com>\n+*** | |\n+*** | |     Merge HEADS DESCRIPTION\n+*** | |\n+*** | * commit COMMIT_OBJECT_NAME\n+*** | | Author: A U Thor <author@example.com>\n+*** | |\n+*** | |     reach\n+*** | | ---\n+*** | |  reach.t | 1 +\n+*** | |  1 file changed, 1 insertion(+)\n+*** | |\n+*** | | diff --git a/reach.t b/reach.t\n+*** | | new file mode 100644\n+*** | | index 0000000..10c9591\n+*** | | --- /dev/null\n+*** | | +++ b/reach.t\n+*** | | @@ -0,0 +1 @@\n+*** | | +reach\n+*** | |\n+*** |  \\\n+*** *-. \\   commit COMMIT_OBJECT_NAME\n+*** |\\ \\ \\  Merge: MERGE_PARENTS\n+*** | | | | Author: A U Thor <author@example.com>\n+*** | | | |\n+*** | | | |     Merge HEADS DESCRIPTION\n+*** | | | |\n+*** | | * | commit COMMIT_OBJECT_NAME\n+*** | | |/  Author: A U Thor <author@example.com>\n+*** | | |\n+*** | | |       octopus-b\n+*** | | |   ---\n+*** | | |    octopus-b.t | 1 +\n+*** | | |    1 file changed, 1 insertion(+)\n+*** | | |\n+*** | | |   diff --git a/octopus-b.t b/octopus-b.t\n+*** | | |   new file mode 100644\n+*** | | |   index 0000000..d5fcad0\n+*** | | |   --- /dev/null\n+*** | | |   +++ b/octopus-b.t\n+*** | | |   @@ -0,0 +1 @@\n+*** | | |   +octopus-b\n+*** | | |\n+*** | * | commit COMMIT_OBJECT_NAME\n+*** | |/  Author: A U Thor <author@example.com>\n+*** | |\n+*** | |       octopus-a\n+*** | |   ---\n+*** | |    octopus-a.t | 1 +\n+*** | |    1 file changed, 1 insertion(+)\n+*** | |\n+*** | |   diff --git a/octopus-a.t b/octopus-a.t\n+*** | |   new file mode 100644\n+*** | |   index 0000000..11ee015\n+*** | |   --- /dev/null\n+*** | |   +++ b/octopus-a.t\n+*** | |   @@ -0,0 +1 @@\n+*** | |   +octopus-a\n+*** | |\n+*** * | commit COMMIT_OBJECT_NAME\n+*** |/  Author: A U Thor <author@example.com>\n+*** |\n+*** |       seventh\n+*** |   ---\n+*** |    seventh.t | 1 +\n+*** |    1 file changed, 1 insertion(+)\n+*** |\n+*** |   diff --git a/seventh.t b/seventh.t\n+*** |   new file mode 100644\n+*** |   index 0000000..9744ffc\n+*** |   --- /dev/null\n+*** |   +++ b/seventh.t\n+*** |   @@ -0,0 +1 @@\n+*** |   +seventh\n+*** |\n+*** *   commit COMMIT_OBJECT_NAME\n+*** |\\  Merge: MERGE_PARENTS\n+*** | | Author: A U Thor <author@example.com>\n+*** | |\n+*** | |     Merge branch 'tangle'\n+*** | |\n+*** | *   commit COMMIT_OBJECT_NAME\n+*** | |\\  Merge: MERGE_PARENTS\n+*** | | | Author: A U Thor <author@example.com>\n+*** | | |\n+*** | | |     Merge branch 'side' (early part) into tangle\n+*** | | |\n+*** | * |   commit COMMIT_OBJECT_NAME\n+*** | |\\ \\  Merge: MERGE_PARENTS\n+*** | | | | Author: A U Thor <author@example.com>\n+*** | | | |\n+*** | | | |     Merge branch 'master' (early part) into tangle\n+*** | | | |\n+*** | * | | commit COMMIT_OBJECT_NAME\n+*** | | | | Author: A U Thor <author@example.com>\n+*** | | | |\n+*** | | | |     tangle-a\n+*** | | | | ---\n+*** | | | |  tangle-a | 1 +\n+*** | | | |  1 file changed, 1 insertion(+)\n+*** | | | |\n+*** | | | | diff --git a/tangle-a b/tangle-a\n+*** | | | | new file mode 100644\n+*** | | | | index 0000000..7898192\n+*** | | | | --- /dev/null\n+*** | | | | +++ b/tangle-a\n+*** | | | | @@ -0,0 +1 @@\n+*** | | | | +a\n+*** | | | |\n+*** * | | |   commit COMMIT_OBJECT_NAME\n+*** |\\ \\ \\ \\  Merge: MERGE_PARENTS\n+*** | | | | | Author: A U Thor <author@example.com>\n+*** | | | | |\n+*** | | | | |     Merge branch 'side'\n+*** | | | | |\n+*** | * | | | commit COMMIT_OBJECT_NAME\n+*** | | |_|/  Author: A U Thor <author@example.com>\n+*** | |/| |\n+*** | | | |       side-2\n+*** | | | |   ---\n+*** | | | |    2 | 1 +\n+*** | | | |    1 file changed, 1 insertion(+)\n+*** | | | |\n+*** | | | |   diff --git a/2 b/2\n+*** | | | |   new file mode 100644\n+*** | | | |   index 0000000..0cfbf08\n+*** | | | |   --- /dev/null\n+*** | | | |   +++ b/2\n+*** | | | |   @@ -0,0 +1 @@\n+*** | | | |   +2\n+*** | | | |\n+*** | * | | commit COMMIT_OBJECT_NAME\n+*** | | | | Author: A U Thor <author@example.com>\n+*** | | | |\n+*** | | | |     side-1\n+*** | | | | ---\n+*** | | | |  1 | 1 +\n+*** | | | |  1 file changed, 1 insertion(+)\n+*** | | | |\n+*** | | | | diff --git a/1 b/1\n+*** | | | | new file mode 100644\n+*** | | | | index 0000000..d00491f\n+*** | | | | --- /dev/null\n+*** | | | | +++ b/1\n+*** | | | | @@ -0,0 +1 @@\n+*** | | | | +1\n+*** | | | |\n+*** * | | | commit COMMIT_OBJECT_NAME\n+*** | | | | Author: A U Thor <author@example.com>\n+*** | | | |\n+*** | | | |     Second\n+*** | | | | ---\n+*** | | | |  one | 1 +\n+*** | | | |  1 file changed, 1 insertion(+)\n+*** | | | |\n+*** | | | | diff --git a/one b/one\n+*** | | | | new file mode 100644\n+*** | | | | index 0000000..9a33383\n+*** | | | | --- /dev/null\n+*** | | | | +++ b/one\n+*** | | | | @@ -0,0 +1 @@\n+*** | | | | +case\n+*** | | | |\n+*** * | | | commit COMMIT_OBJECT_NAME\n+*** | |_|/  Author: A U Thor <author@example.com>\n+*** |/| |\n+*** | | |       sixth\n+*** | | |   ---\n+*** | | |    a/two | 1 -\n+*** | | |    1 file changed, 1 deletion(-)\n+*** | | |\n+*** | | |   diff --git a/a/two b/a/two\n+*** | | |   deleted file mode 100644\n+*** | | |   index 9245af5..0000000\n+*** | | |   --- a/a/two\n+*** | | |   +++ /dev/null\n+*** | | |   @@ -1 +0,0 @@\n+*** | | |   -ni\n+*** | | |\n+*** * | | commit COMMIT_OBJECT_NAME\n+*** | | | Author: A U Thor <author@example.com>\n+*** | | |\n+*** | | |     fifth\n+*** | | | ---\n+*** | | |  a/two | 1 +\n+*** | | |  1 file changed, 1 insertion(+)\n+*** | | |\n+*** | | | diff --git a/a/two b/a/two\n+*** | | | new file mode 100644\n+*** | | | index 0000000..9245af5\n+*** | | | --- /dev/null\n+*** | | | +++ b/a/two\n+*** | | | @@ -0,0 +1 @@\n+*** | | | +ni\n+*** | | |\n+*** * | | commit COMMIT_OBJECT_NAME\n+*** |/ /  Author: A U Thor <author@example.com>\n+*** | |\n+*** | |       fourth\n+*** | |   ---\n+*** | |    ein | 1 +\n+*** | |    1 file changed, 1 insertion(+)\n+*** | |\n+*** | |   diff --git a/ein b/ein\n+*** | |   new file mode 100644\n+*** | |   index 0000000..9d7e69f\n+*** | |   --- /dev/null\n+*** | |   +++ b/ein\n+*** | |   @@ -0,0 +1 @@\n+*** | |   +ichi\n+*** | |\n+*** * | commit COMMIT_OBJECT_NAME\n+*** |/  Author: A U Thor <author@example.com>\n+*** |\n+*** |       third\n+*** |   ---\n+*** |    ichi | 1 +\n+*** |    one  | 1 -\n+*** |    2 files changed, 1 insertion(+), 1 deletion(-)\n+*** |\n+*** |   diff --git a/ichi b/ichi\n+*** |   new file mode 100644\n+*** |   index 0000000..9d7e69f\n+*** |   --- /dev/null\n+*** |   +++ b/ichi\n+*** |   @@ -0,0 +1 @@\n+*** |   +ichi\n+*** |   diff --git a/one b/one\n+*** |   deleted file mode 100644\n+*** |   index 9d7e69f..0000000\n+*** |   --- a/one\n+*** |   +++ /dev/null\n+*** |   @@ -1 +0,0 @@\n+*** |   -ichi\n+*** |\n+*** * commit COMMIT_OBJECT_NAME\n+*** | Author: A U Thor <author@example.com>\n+*** |\n+*** |     second\n+*** | ---\n+*** |  one | 2 +-\n+*** |  1 file changed, 1 insertion(+), 1 deletion(-)\n+*** |\n+*** | diff --git a/one b/one\n+*** | index 5626abf..9d7e69f 100644\n+*** | --- a/one\n+*** | +++ b/one\n+*** | @@ -1 +1 @@\n+*** | -one\n+*** | +ichi\n+*** |\n+*** * commit COMMIT_OBJECT_NAME\n+***   Author: A U Thor <author@example.com>\n+***\n+***       initial\n+***   ---\n+***    one | 1 +\n+***    1 file changed, 1 insertion(+)\n+***\n+***   diff --git a/one b/one\n+***   new file mode 100644\n+***   index 0000000..5626abf\n+***   --- /dev/null\n+***   +++ b/one\n+***   @@ -0,0 +1 @@\n+***   +one\n+EOF\n+\n+test_expect_success 'log --line-prefix=\"*** \" --graph with diff and stats' '\n+\tgit log --line-prefix=\"*** \" --no-renames --graph --pretty=short --stat -p >actual &&\n+\tsanitize_output >actual.sanitized <actual &&\n+\ttest_i18ncmp expect actual.sanitized\n+'\n+\n+cat >expect <<-\\EOF\n+* reach\n+|\n+| A\treach.t\n+* Merge branch 'tangle'\n+*   Merge branch 'side'\n+|\\\n+| * side-2\n+|\n+|   A\t2\n+* Second\n+|\n+| A\tone\n+* sixth\n+\n+  D\ta/two\n+EOF\n+\n+test_expect_success 'log --graph with --name-status' '\n+\tgit log --graph --format=%s --name-status tangle..reach >actual &&\n+\tsanitize_output <actual >actual.sanitized &&\n+\ttest_cmp expect actual.sanitized\n+'\n+\n+cat >expect <<-\\EOF\n+* reach\n+|\n+| reach.t\n+* Merge branch 'tangle'\n+*   Merge branch 'side'\n+|\\\n+| * side-2\n+|\n+|   2\n+* Second\n+|\n+| one\n+* sixth\n+\n+  a/two\n+EOF\n+\n+test_expect_success 'log --graph with --name-only' '\n+\tgit log --graph --format=%s --name-only tangle..reach >actual &&\n+\tsanitize_output <actual >actual.sanitized &&\n+\ttest_cmp expect actual.sanitized\n+'\n+\n+test_expect_success 'dotdot is a parent directory' '\n+\tmkdir -p a/b &&\n+\t( echo sixth && echo fifth ) >expect &&\n+\t( cd a/b && git log --format=%s .. ) >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'setup signed branch' '\n+\ttest_when_finished \"git reset --hard && git checkout master\" &&\n+\tgit checkout -b signed master &&\n+\techo foo >foo &&\n+\tgit add foo &&\n+\tgit commit -S -m signed_commit\n+'\n+\n+test_expect_success GPGSM 'setup signed branch x509' '\n+\ttest_when_finished \"git reset --hard && git checkout master\" &&\n+\tgit checkout -b signed-x509 master &&\n+\techo foo >foo &&\n+\tgit add foo &&\n+\ttest_config signing.default x509 &&\n+\ttest_config user.signingkey $GIT_COMMITTER_EMAIL &&\n+\tgit commit -S -m signed_commit\n+'\n+\n+test_expect_success GPG 'log --graph --show-signature' '\n+\tgit log --graph --show-signature -n1 signed >actual &&\n+\tgrep \"^| gpg: Signature made\" actual &&\n+\tgrep \"^| gpg: Good signature\" actual\n+'\n+\n+test_expect_success GPGSM 'log --graph --show-signature x509' '\n+\tgit log --graph --show-signature -n1 signed-x509 >actual &&\n+\tgrep \"^| gpgsm: Signature made\" actual &&\n+\tgrep \"^| gpgsm: Good signature\" actual\n+'\n+\n+test_expect_success GPG 'log --graph --show-signature for merged tag' '\n+\ttest_when_finished \"git reset --hard && git checkout master\" &&\n+\tgit checkout -b plain master &&\n+\techo aaa >bar &&\n+\tgit add bar &&\n+\tgit commit -m bar_commit &&\n+\tgit checkout -b tagged master &&\n+\techo bbb >baz &&\n+\tgit add baz &&\n+\tgit commit -m baz_commit &&\n+\tgit tag -s -m signed_tag_msg signed_tag &&\n+\tgit checkout plain &&\n+\tgit merge --no-ff -m msg signed_tag &&\n+\tgit log --graph --show-signature -n1 plain >actual &&\n+\tgrep \"^|\\\\\\  merged tag\" actual &&\n+\tgrep \"^| | gpg: Signature made\" actual &&\n+\tgrep \"^| | gpg: Good signature\" actual\n+'\n+\n+test_expect_success GPGSM 'log --graph --show-signature for merged tag x509' '\n+\ttest_when_finished \"git reset --hard && git checkout master\" &&\n+\ttest_config signing.default x509 &&\n+\ttest_config user.signingkey $GIT_COMMITTER_EMAIL &&\n+\tgit checkout -b plain-x509 master &&\n+\techo aaa >bar &&\n+\tgit add bar &&\n+\tgit commit -m bar_commit &&\n+\tgit checkout -b tagged-x509 master &&\n+\techo bbb >baz &&\n+\tgit add baz &&\n+\tgit commit -m baz_commit &&\n+\tgit tag -s -m signed_tag_msg signed_tag_x509 &&\n+\tgit checkout plain-x509 &&\n+\tgit merge --no-ff -m msg signed_tag_x509 &&\n+\tgit log --graph --show-signature -n1 plain-x509 >actual &&\n+\tgrep \"^|\\\\\\  merged tag\" actual &&\n+\tgrep \"^| | gpgsm: Signature made\" actual &&\n+\tgrep \"^| | gpgsm: Good signature\" actual\n+'\n+\n+test_expect_success GPG '--no-show-signature overrides --show-signature' '\n+\tgit log -1 --show-signature --no-show-signature signed >actual &&\n+\t! grep \"^gpg:\" actual\n+'\n+\n+test_expect_success GPG 'log.showsignature=true behaves like --show-signature' '\n+\ttest_config log.showsignature true &&\n+\tgit log -1 signed >actual &&\n+\tgrep \"gpg: Signature made\" actual &&\n+\tgrep \"gpg: Good signature\" actual\n+'\n+\n+test_expect_success GPG '--no-show-signature overrides log.showsignature=true' '\n+\ttest_config log.showsignature true &&\n+\tgit log -1 --no-show-signature signed >actual &&\n+\t! grep \"^gpg:\" actual\n+'\n+\n+test_expect_success GPG '--show-signature overrides log.showsignature=false' '\n+\ttest_config log.showsignature false &&\n+\tgit log -1 --show-signature signed >actual &&\n+\tgrep \"gpg: Signature made\" actual &&\n+\tgrep \"gpg: Good signature\" actual\n+'\n+\n+test_expect_success 'log --graph --no-walk is forbidden' '\n+\ttest_must_fail git log --graph --no-walk\n+'\n+\n+test_expect_success 'log diagnoses bogus HEAD' '\n+\tgit init empty &&\n+\ttest_must_fail git -C empty log 2>stderr &&\n+\ttest_i18ngrep does.not.have.any.commits stderr &&\n+\techo 1234abcd >empty/.git/refs/heads/master &&\n+\ttest_must_fail git -C empty log 2>stderr &&\n+\ttest_i18ngrep broken stderr &&\n+\techo \"ref: refs/heads/invalid.lock\" >empty/.git/HEAD &&\n+\ttest_must_fail git -C empty log 2>stderr &&\n+\ttest_i18ngrep broken stderr &&\n+\ttest_must_fail git -C empty log --default totally-bogus 2>stderr &&\n+\ttest_i18ngrep broken stderr\n+'\n+\n+test_expect_success 'log does not default to HEAD when rev input is given' '\n+\tgit log --branches=does-not-exist >actual &&\n+\ttest_must_be_empty actual\n+'\n+\n+test_expect_success 'set up --source tests' '\n+\tgit checkout --orphan source-a &&\n+\ttest_commit one &&\n+\ttest_commit two &&\n+\tgit checkout -b source-b HEAD^ &&\n+\ttest_commit three\n+'\n+\n+test_expect_success 'log --source paints branch names' '\n+\tcat >expect <<-\\EOF &&\n+\t09e12a9\tsource-b three\n+\t8e393e1\tsource-a two\n+\t1ac6c77\tsource-b one\n+\tEOF\n+\tgit log --oneline --source source-a source-b >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'log --source paints tag names' '\n+\tgit tag -m tagged source-tag &&\n+\tcat >expect <<-\\EOF &&\n+\t09e12a9\tsource-tag three\n+\t8e393e1\tsource-a two\n+\t1ac6c77\tsource-tag one\n+\tEOF\n+\tgit log --oneline --source source-tag source-a >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'log --source paints symmetric ranges' '\n+\tcat >expect <<-\\EOF &&\n+\t09e12a9\tsource-b three\n+\t8e393e1\tsource-a two\n+\tEOF\n+\tgit log --oneline --source source-a...source-b >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--exclude-promisor-objects does not BUG-crash' '\n+\ttest_must_fail git log --exclude-promisor-objects source-a\n+'\n+\n+test_done\ndiff --git a/t/t5548-push-signed-signconfig.sh b/t/t5548-push-signed-signconfig.sh\nnew file mode 100755\nindex 000000000..f39b2e9dc\n--- /dev/null\n+++ b/t/t5548-push-signed-signconfig.sh\n@@ -0,0 +1,276 @@\n+#!/bin/sh\n+\n+test_description='signed push'\n+\n+. ./test-lib.sh\n+. \"$TEST_DIRECTORY\"/lib-gpg.sh\n+\n+prepare_dst () {\n+\trm -fr dst &&\n+\ttest_create_repo dst &&\n+\n+\tgit push dst master:noop master:ff master:noff\n+}\n+\n+test_expect_success setup '\n+\t# master, ff and noff branches pointing at the same commit\n+\ttest_tick &&\n+\tgit commit --allow-empty -m initial &&\n+\n+\tgit checkout -b noop &&\n+\tgit checkout -b ff &&\n+\tgit checkout -b noff &&\n+\n+\t# noop stays the same, ff advances, noff rewrites\n+\ttest_tick &&\n+\tgit commit --allow-empty --amend -m rewritten &&\n+\tgit checkout ff &&\n+\n+\ttest_tick &&\n+\tgit commit --allow-empty -m second\n+'\n+\n+test_expect_success 'unsigned push does not send push certificate' '\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\twrite_script dst/.git/hooks/post-receive <<-\\EOF &&\n+\t# discard the update list\n+\tcat >/dev/null\n+\t# record the push certificate\n+\tif test -n \"${GIT_PUSH_CERT-}\"\n+\tthen\n+\t\tgit cat-file blob $GIT_PUSH_CERT >../push-cert\n+\tfi\n+\tEOF\n+\n+\tgit push dst noop ff +noff &&\n+\t! test -f dst/push-cert\n+'\n+\n+test_expect_success 'talking with a receiver without push certificate support' '\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\twrite_script dst/.git/hooks/post-receive <<-\\EOF &&\n+\t# discard the update list\n+\tcat >/dev/null\n+\t# record the push certificate\n+\tif test -n \"${GIT_PUSH_CERT-}\"\n+\tthen\n+\t\tgit cat-file blob $GIT_PUSH_CERT >../push-cert\n+\tfi\n+\tEOF\n+\n+\tgit push dst noop ff +noff &&\n+\t! test -f dst/push-cert\n+'\n+\n+test_expect_success 'push --signed fails with a receiver without push certificate support' '\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\ttest_must_fail git push --signed dst noop ff +noff 2>err &&\n+\ttest_i18ngrep \"the receiving end does not support\" err\n+'\n+\n+test_expect_success 'push --signed=1 is accepted' '\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\ttest_must_fail git push --signed=1 dst noop ff +noff 2>err &&\n+\ttest_i18ngrep \"the receiving end does not support\" err\n+'\n+\n+test_expect_success GPG 'no certificate for a signed push with no update' '\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\twrite_script dst/.git/hooks/post-receive <<-\\EOF &&\n+\tif test -n \"${GIT_PUSH_CERT-}\"\n+\tthen\n+\t\tgit cat-file blob $GIT_PUSH_CERT >../push-cert\n+\tfi\n+\tEOF\n+\tgit push dst noop &&\n+\t! test -f dst/push-cert\n+'\n+\n+test_expect_success GPG 'signed push sends push certificate' '\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\tgit -C dst config receive.certnonceseed sekrit &&\n+\twrite_script dst/.git/hooks/post-receive <<-\\EOF &&\n+\t# discard the update list\n+\tcat >/dev/null\n+\t# record the push certificate\n+\tif test -n \"${GIT_PUSH_CERT-}\"\n+\tthen\n+\t\tgit cat-file blob $GIT_PUSH_CERT >../push-cert\n+\tfi &&\n+\n+\tcat >../push-cert-status <<E_O_F\n+\tSIGNER=${GIT_PUSH_CERT_SIGNER-nobody}\n+\tKEY=${GIT_PUSH_CERT_KEY-nokey}\n+\tSTATUS=${GIT_PUSH_CERT_STATUS-nostatus}\n+\tNONCE_STATUS=${GIT_PUSH_CERT_NONCE_STATUS-nononcestatus}\n+\tNONCE=${GIT_PUSH_CERT_NONCE-nononce}\n+\tE_O_F\n+\n+\tEOF\n+\n+\tgit push --signed dst noop ff +noff &&\n+\n+\t(\n+\t\tcat <<-\\EOF &&\n+\t\tSIGNER=C O Mitter <committer@example.com>\n+\t\tKEY=13B6F51ECDDE430D\n+\t\tSTATUS=G\n+\t\tNONCE_STATUS=OK\n+\t\tEOF\n+\t\tsed -n -e \"s/^nonce /NONCE=/p\" -e \"/^$/q\" dst/push-cert\n+\t) >expect &&\n+\n+\tnoop=$(git rev-parse noop) &&\n+\tff=$(git rev-parse ff) &&\n+\tnoff=$(git rev-parse noff) &&\n+\tgrep \"$noop $ff refs/heads/ff\" dst/push-cert &&\n+\tgrep \"$noop $noff refs/heads/noff\" dst/push-cert &&\n+\ttest_cmp expect dst/push-cert-status\n+'\n+\n+test_expect_success GPG 'inconsistent push options in signed push not allowed' '\n+\t# First, invoke receive-pack with dummy input to obtain its preamble.\n+\tprepare_dst &&\n+\tgit -C dst config receive.certnonceseed sekrit &&\n+\tgit -C dst config receive.advertisepushoptions 1 &&\n+\tprintf xxxx | test_might_fail git receive-pack dst >preamble &&\n+\n+\t# Then, invoke push. Simulate a receive-pack that sends the preamble we\n+\t# obtained, followed by a dummy packet.\n+\twrite_script myscript <<-\\EOF &&\n+\t\tcat preamble &&\n+\t\tprintf xxxx &&\n+\t\tcat >push\n+\tEOF\n+\ttest_might_fail git push --push-option=\"foo\" --push-option=\"bar\" \\\n+\t\t--receive-pack=\"\\\"$(pwd)/myscript\\\"\" --signed dst --delete ff &&\n+\n+\t# Replay the push output on a fresh dst, checking that ff is truly\n+\t# deleted.\n+\tprepare_dst &&\n+\tgit -C dst config receive.certnonceseed sekrit &&\n+\tgit -C dst config receive.advertisepushoptions 1 &&\n+\tgit receive-pack dst <push &&\n+\ttest_must_fail git -C dst rev-parse ff &&\n+\n+\t# Tweak the push output to make the push option outside the cert\n+\t# different, then replay it on a fresh dst, checking that ff is not\n+\t# deleted.\n+\tperl -pe \"s/([^ ])bar/\\$1baz/\" push >push.tweak &&\n+\tprepare_dst &&\n+\tgit -C dst config receive.certnonceseed sekrit &&\n+\tgit -C dst config receive.advertisepushoptions 1 &&\n+\tgit receive-pack dst <push.tweak >out &&\n+\tgit -C dst rev-parse ff &&\n+\tgrep \"inconsistent push options\" out\n+'\n+\n+test_expect_success GPG 'fail without key and heed user.signingkey' '\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\tgit -C dst config receive.certnonceseed sekrit &&\n+\twrite_script dst/.git/hooks/post-receive <<-\\EOF &&\n+\t# discard the update list\n+\tcat >/dev/null\n+\t# record the push certificate\n+\tif test -n \"${GIT_PUSH_CERT-}\"\n+\tthen\n+\t\tgit cat-file blob $GIT_PUSH_CERT >../push-cert\n+\tfi &&\n+\n+\tcat >../push-cert-status <<E_O_F\n+\tSIGNER=${GIT_PUSH_CERT_SIGNER-nobody}\n+\tKEY=${GIT_PUSH_CERT_KEY-nokey}\n+\tSTATUS=${GIT_PUSH_CERT_STATUS-nostatus}\n+\tNONCE_STATUS=${GIT_PUSH_CERT_NONCE_STATUS-nononcestatus}\n+\tNONCE=${GIT_PUSH_CERT_NONCE-nononce}\n+\tE_O_F\n+\n+\tEOF\n+\n+\ttest_config user.email hasnokey@nowhere.com &&\n+\t(\n+\t\tsane_unset GIT_COMMITTER_EMAIL &&\n+\t\ttest_must_fail git push --signed dst noop ff +noff\n+\t) &&\n+\ttest_config user.signingkey $GIT_COMMITTER_EMAIL &&\n+\tgit push --signed dst noop ff +noff &&\n+\n+\t(\n+\t\tcat <<-\\EOF &&\n+\t\tSIGNER=C O Mitter <committer@example.com>\n+\t\tKEY=13B6F51ECDDE430D\n+\t\tSTATUS=G\n+\t\tNONCE_STATUS=OK\n+\t\tEOF\n+\t\tsed -n -e \"s/^nonce /NONCE=/p\" -e \"/^$/q\" dst/push-cert\n+\t) >expect &&\n+\n+\tnoop=$(git rev-parse noop) &&\n+\tff=$(git rev-parse ff) &&\n+\tnoff=$(git rev-parse noff) &&\n+\tgrep \"$noop $ff refs/heads/ff\" dst/push-cert &&\n+\tgrep \"$noop $noff refs/heads/noff\" dst/push-cert &&\n+\ttest_cmp expect dst/push-cert-status\n+'\n+\n+test_expect_success GPGSM 'fail without key and heed user.signingkey x509' '\n+\ttest_config signing.default x509 &&\n+\tprepare_dst &&\n+\tmkdir -p dst/.git/hooks &&\n+\tgit -C dst config receive.certnonceseed sekrit &&\n+\twrite_script dst/.git/hooks/post-receive <<-\\EOF &&\n+\t# discard the update list\n+\tcat >/dev/null\n+\t# record the push certificate\n+\tif test -n \"${GIT_PUSH_CERT-}\"\n+\tthen\n+\t\tgit cat-file blob $GIT_PUSH_CERT >../push-cert\n+\tfi &&\n+\n+\tcat >../push-cert-status <<E_O_F\n+\tSIGNER=${GIT_PUSH_CERT_SIGNER-nobody}\n+\tKEY=${GIT_PUSH_CERT_KEY-nokey}\n+\tSTATUS=${GIT_PUSH_CERT_STATUS-nostatus}\n+\tNONCE_STATUS=${GIT_PUSH_CERT_NONCE_STATUS-nononcestatus}\n+\tNONCE=${GIT_PUSH_CERT_NONCE-nononce}\n+\tE_O_F\n+\n+\tEOF\n+\n+\ttest_config user.email hasnokey@nowhere.com &&\n+\ttest_config user.signingkey \"\" &&\n+\t(\n+\t\tsane_unset GIT_COMMITTER_EMAIL &&\n+\t\ttest_must_fail git push --signed dst noop ff +noff\n+\t) &&\n+\ttest_config user.signingkey $GIT_COMMITTER_EMAIL &&\n+\tgit push --signed dst noop ff +noff &&\n+\n+\t(\n+\t\tcat <<-\\EOF &&\n+\t\tSIGNER=/CN=C O Mitter/O=Example/SN=C O/GN=Mitter\n+\t\tKEY=\n+\t\tSTATUS=G\n+\t\tNONCE_STATUS=OK\n+\t\tEOF\n+\t\tsed -n -e \"s/^nonce /NONCE=/p\" -e \"/^$/q\" dst/push-cert\n+\t) >expect.in &&\n+\tkey=$(cat \"${GNUPGHOME}/trustlist.txt\" | cut -d\" \" -f1 | tr -d \":\") &&\n+\tsed -e \"s/^KEY=/KEY=${key}/\" expect.in >expect &&\n+\n+\tnoop=$(git rev-parse noop) &&\n+\tff=$(git rev-parse ff) &&\n+\tnoff=$(git rev-parse noff) &&\n+\tgrep \"$noop $ff refs/heads/ff\" dst/push-cert &&\n+\tgrep \"$noop $noff refs/heads/noff\" dst/push-cert &&\n+\ttest_cmp expect dst/push-cert-status\n+'\n+\n+test_done\ndiff --git a/t/t7013-tag-signconfig.sh b/t/t7013-tag-signconfig.sh\nnew file mode 100755\nindex 000000000..691ab7b7e\n--- /dev/null\n+++ b/t/t7013-tag-signconfig.sh\n@@ -0,0 +1,2074 @@\n+#!/bin/sh\n+#\n+# Copyright (c) 2007 Carlos Rica\n+#\n+\n+test_description='git tag\n+\n+Tests for operations with tags.'\n+\n+. ./test-lib.sh\n+. \"$TEST_DIRECTORY\"/lib-gpg.sh\n+. \"$TEST_DIRECTORY\"/lib-terminal.sh\n+\n+# creating and listing lightweight tags:\n+\n+tag_exists () {\n+\tgit show-ref --quiet --verify refs/tags/\"$1\"\n+}\n+\n+test_expect_success 'listing all tags in an empty tree should succeed' '\n+\tgit tag -l &&\n+\tgit tag\n+'\n+\n+test_expect_success 'listing all tags in an empty tree should output nothing' '\n+\ttest $(git tag -l | wc -l) -eq 0 &&\n+\ttest $(git tag | wc -l) -eq 0\n+'\n+\n+test_expect_success 'sort tags, ignore case' '\n+\t(\n+\t\tgit init sort &&\n+\t\tcd sort &&\n+\t\ttest_commit initial &&\n+\t\tgit tag tag-one &&\n+\t\tgit tag TAG-two &&\n+\t\tgit tag -l >actual &&\n+\t\tcat >expected <<-\\EOF &&\n+\t\tTAG-two\n+\t\tinitial\n+\t\ttag-one\n+\t\tEOF\n+\t\ttest_cmp expected actual &&\n+\t\tgit tag -l -i >actual &&\n+\t\tcat >expected <<-\\EOF &&\n+\t\tinitial\n+\t\ttag-one\n+\t\tTAG-two\n+\t\tEOF\n+\t\ttest_cmp expected actual\n+\t)\n+'\n+\n+test_expect_success 'looking for a tag in an empty tree should fail' \\\n+\t'! (tag_exists mytag)'\n+\n+test_expect_success 'creating a tag in an empty tree should fail' '\n+\ttest_must_fail git tag mynotag &&\n+\t! tag_exists mynotag\n+'\n+\n+test_expect_success 'creating a tag for HEAD in an empty tree should fail' '\n+\ttest_must_fail git tag mytaghead HEAD &&\n+\t! tag_exists mytaghead\n+'\n+\n+test_expect_success 'creating a tag for an unknown revision should fail' '\n+\ttest_must_fail git tag mytagnorev aaaaaaaaaaa &&\n+\t! tag_exists mytagnorev\n+'\n+\n+# commit used in the tests, test_tick is also called here to freeze the date:\n+test_expect_success 'creating a tag using default HEAD should succeed' '\n+\ttest_config core.logAllRefUpdates true &&\n+\ttest_tick &&\n+\techo foo >foo &&\n+\tgit add foo &&\n+\tgit commit -m Foo &&\n+\tgit tag mytag &&\n+\ttest_must_fail git reflog exists refs/tags/mytag\n+'\n+\n+test_expect_success 'creating a tag with --create-reflog should create reflog' '\n+\tgit log -1 \\\n+\t\t--format=\"format:tag: tagging %h (%s, %cd)%n\" \\\n+\t\t--date=format:%Y-%m-%d >expected &&\n+\ttest_when_finished \"git tag -d tag_with_reflog\" &&\n+\tgit tag --create-reflog tag_with_reflog &&\n+\tgit reflog exists refs/tags/tag_with_reflog &&\n+\tsed -e \"s/^.*\t//\" .git/logs/refs/tags/tag_with_reflog >actual &&\n+\ttest_i18ncmp expected actual\n+'\n+\n+test_expect_success 'annotated tag with --create-reflog has correct message' '\n+\tgit log -1 \\\n+\t\t--format=\"format:tag: tagging %h (%s, %cd)%n\" \\\n+\t\t--date=format:%Y-%m-%d >expected &&\n+\ttest_when_finished \"git tag -d tag_with_reflog\" &&\n+\tgit tag -m \"annotated tag\" --create-reflog tag_with_reflog &&\n+\tgit reflog exists refs/tags/tag_with_reflog &&\n+\tsed -e \"s/^.*\t//\" .git/logs/refs/tags/tag_with_reflog >actual &&\n+\ttest_i18ncmp expected actual\n+'\n+\n+test_expect_success '--create-reflog does not create reflog on failure' '\n+\ttest_must_fail git tag --create-reflog mytag &&\n+\ttest_must_fail git reflog exists refs/tags/mytag\n+'\n+\n+test_expect_success 'option core.logAllRefUpdates=always creates reflog' '\n+\ttest_when_finished \"git tag -d tag_with_reflog\" &&\n+\ttest_config core.logAllRefUpdates always &&\n+\tgit tag tag_with_reflog &&\n+\tgit reflog exists refs/tags/tag_with_reflog\n+'\n+\n+test_expect_success 'listing all tags if one exists should succeed' '\n+\tgit tag -l &&\n+\tgit tag\n+'\n+\n+cat >expect <<EOF\n+mytag\n+EOF\n+test_expect_success 'Multiple -l or --list options are equivalent to one -l option' '\n+\tgit tag -l -l >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag --list --list >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag --list -l --list >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'listing all tags if one exists should output that tag' '\n+\ttest $(git tag -l) = mytag &&\n+\ttest $(git tag) = mytag\n+'\n+\n+# pattern matching:\n+\n+test_expect_success 'listing a tag using a matching pattern should succeed' \\\n+\t'git tag -l mytag'\n+\n+test_expect_success 'listing a tag with --ignore-case' \\\n+\t'test $(git tag -l --ignore-case MYTAG) = mytag'\n+\n+test_expect_success \\\n+\t'listing a tag using a matching pattern should output that tag' \\\n+\t'test $(git tag -l mytag) = mytag'\n+\n+test_expect_success \\\n+\t'listing tags using a non-matching pattern should succeed' \\\n+\t'git tag -l xxx'\n+\n+test_expect_success \\\n+\t'listing tags using a non-matching pattern should output nothing' \\\n+\t'test $(git tag -l xxx | wc -l) -eq 0'\n+\n+# special cases for creating tags:\n+\n+test_expect_success \\\n+\t'trying to create a tag with the name of one existing should fail' \\\n+\t'test_must_fail git tag mytag'\n+\n+test_expect_success \\\n+\t'trying to create a tag with a non-valid name should fail' '\n+\ttest $(git tag -l | wc -l) -eq 1 &&\n+\ttest_must_fail git tag \"\" &&\n+\ttest_must_fail git tag .othertag &&\n+\ttest_must_fail git tag \"other tag\" &&\n+\ttest_must_fail git tag \"othertag^\" &&\n+\ttest_must_fail git tag \"other~tag\" &&\n+\ttest $(git tag -l | wc -l) -eq 1\n+'\n+\n+test_expect_success 'creating a tag using HEAD directly should succeed' '\n+\tgit tag myhead HEAD &&\n+\ttag_exists myhead\n+'\n+\n+test_expect_success '--force can create a tag with the name of one existing' '\n+\ttag_exists mytag &&\n+\tgit tag --force mytag &&\n+\ttag_exists mytag'\n+\n+test_expect_success '--force is moot with a non-existing tag name' '\n+\ttest_when_finished git tag -d newtag forcetag &&\n+\tgit tag newtag >expect &&\n+\tgit tag --force forcetag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+# deleting tags:\n+\n+test_expect_success 'trying to delete an unknown tag should fail' '\n+\t! tag_exists unknown-tag &&\n+\ttest_must_fail git tag -d unknown-tag\n+'\n+\n+cat >expect <<EOF\n+myhead\n+mytag\n+EOF\n+test_expect_success \\\n+\t'trying to delete tags without params should succeed and do nothing' '\n+\tgit tag -l > actual && test_cmp expect actual &&\n+\tgit tag -d &&\n+\tgit tag -l > actual && test_cmp expect actual\n+'\n+\n+test_expect_success \\\n+\t'deleting two existing tags in one command should succeed' '\n+\ttag_exists mytag &&\n+\ttag_exists myhead &&\n+\tgit tag -d mytag myhead &&\n+\t! tag_exists mytag &&\n+\t! tag_exists myhead\n+'\n+\n+test_expect_success \\\n+\t'creating a tag with the name of another deleted one should succeed' '\n+\t! tag_exists mytag &&\n+\tgit tag mytag &&\n+\ttag_exists mytag\n+'\n+\n+test_expect_success \\\n+\t'trying to delete two tags, existing and not, should fail in the 2nd' '\n+\ttag_exists mytag &&\n+\t! tag_exists myhead &&\n+\ttest_must_fail git tag -d mytag anothertag &&\n+\t! tag_exists mytag &&\n+\t! tag_exists myhead\n+'\n+\n+test_expect_success 'trying to delete an already deleted tag should fail' \\\n+\t'test_must_fail git tag -d mytag'\n+\n+# listing various tags with pattern matching:\n+\n+cat >expect <<EOF\n+a1\n+aa1\n+cba\n+t210\n+t211\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+EOF\n+test_expect_success 'listing all tags should print them ordered' '\n+\tgit tag v1.0.1 &&\n+\tgit tag t211 &&\n+\tgit tag aa1 &&\n+\tgit tag v0.2.1 &&\n+\tgit tag v1.1.3 &&\n+\tgit tag cba &&\n+\tgit tag a1 &&\n+\tgit tag v1.0 &&\n+\tgit tag t210 &&\n+\tgit tag -l > actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >expect <<EOF\n+a1\n+aa1\n+cba\n+EOF\n+test_expect_success \\\n+\t'listing tags with substring as pattern must print those matching' '\n+\trm *a* &&\n+\tgit tag -l \"*a*\" > current &&\n+\ttest_cmp expect current\n+'\n+\n+cat >expect <<EOF\n+v0.2.1\n+v1.0.1\n+EOF\n+test_expect_success \\\n+\t'listing tags with a suffix as pattern must print those matching' '\n+\tgit tag -l \"*.1\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >expect <<EOF\n+t210\n+t211\n+EOF\n+test_expect_success \\\n+\t'listing tags with a prefix as pattern must print those matching' '\n+\tgit tag -l \"t21*\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >expect <<EOF\n+a1\n+EOF\n+test_expect_success \\\n+\t'listing tags using a name as pattern must print that one matching' '\n+\tgit tag -l a1 > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >expect <<EOF\n+v1.0\n+EOF\n+test_expect_success \\\n+\t'listing tags using a name as pattern must print that one matching' '\n+\tgit tag -l v1.0 > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >expect <<EOF\n+v1.0.1\n+v1.1.3\n+EOF\n+test_expect_success \\\n+\t'listing tags with ? in the pattern should print those matching' '\n+\tgit tag -l \"v1.?.?\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success \\\n+\t'listing tags using v.* should print nothing because none have v.' '\n+\tgit tag -l \"v.*\" > actual &&\n+\ttest_must_be_empty actual\n+'\n+\n+cat >expect <<EOF\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+EOF\n+test_expect_success \\\n+\t'listing tags using v* should print only those having v' '\n+\tgit tag -l \"v*\" > actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'tag -l can accept multiple patterns' '\n+\tgit tag -l \"v1*\" \"v0*\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+# Between v1.7.7 & v2.13.0 a fair reading of the git-tag documentation\n+# could leave you with the impression that \"-l <pattern> -l <pattern>\"\n+# was how we wanted to accept multiple patterns.\n+#\n+# This test should not imply that this is a sane thing to support. but\n+# since the documentation was worded like it was let's at least find\n+# out if we're going to break this long-documented form of taking\n+# multiple patterns.\n+test_expect_success 'tag -l <pattern> -l <pattern> works, as our buggy documentation previously suggested' '\n+\tgit tag -l \"v1*\" -l \"v0*\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'listing tags in column' '\n+\tCOLUMNS=41 git tag -l --column=row >actual &&\n+\tcat >expected <<\\EOF &&\n+a1      aa1     cba     t210    t211\n+v0.2.1  v1.0    v1.0.1  v1.1.3\n+EOF\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'listing tags in column with column.*' '\n+\ttest_config column.tag row &&\n+\ttest_config column.ui dense &&\n+\tCOLUMNS=40 git tag -l >actual &&\n+\tcat >expected <<\\EOF &&\n+a1      aa1   cba     t210    t211\n+v0.2.1  v1.0  v1.0.1  v1.1.3\n+EOF\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'listing tag with -n --column should fail' '\n+\ttest_must_fail git tag --column -n\n+'\n+\n+test_expect_success 'listing tags -n in column with column.ui ignored' '\n+\ttest_config column.ui \"row dense\" &&\n+\tCOLUMNS=40 git tag -l -n >actual &&\n+\tcat >expected <<\\EOF &&\n+a1              Foo\n+aa1             Foo\n+cba             Foo\n+t210            Foo\n+t211            Foo\n+v0.2.1          Foo\n+v1.0            Foo\n+v1.0.1          Foo\n+v1.1.3          Foo\n+EOF\n+\ttest_cmp expected actual\n+'\n+\n+# creating and verifying lightweight tags:\n+\n+test_expect_success \\\n+\t'a non-annotated tag created without parameters should point to HEAD' '\n+\tgit tag non-annotated-tag &&\n+\ttest $(git cat-file -t non-annotated-tag) = commit &&\n+\ttest $(git rev-parse non-annotated-tag) = $(git rev-parse HEAD)\n+'\n+\n+test_expect_success 'trying to verify an unknown tag should fail' \\\n+\t'test_must_fail git tag -v unknown-tag'\n+\n+test_expect_success \\\n+\t'trying to verify a non-annotated and non-signed tag should fail' \\\n+\t'test_must_fail git tag -v non-annotated-tag'\n+\n+test_expect_success \\\n+\t'trying to verify many non-annotated or unknown tags, should fail' \\\n+\t'test_must_fail git tag -v unknown-tag1 non-annotated-tag unknown-tag2'\n+\n+# creating annotated tags:\n+\n+get_tag_msg () {\n+\tgit cat-file tag \"$1\" | sed -e \"/BEGIN PGP/q\"\n+}\n+\n+# run test_tick before committing always gives the time in that timezone\n+get_tag_header () {\n+cat <<EOF\n+object $2\n+type $3\n+tag $1\n+tagger C O Mitter <committer@example.com> $4 -0700\n+\n+EOF\n+}\n+\n+commit=$(git rev-parse HEAD)\n+time=$test_tick\n+\n+get_tag_header annotated-tag $commit commit $time >expect\n+echo \"A message\" >>expect\n+test_expect_success \\\n+\t'creating an annotated tag with -m message should succeed' '\n+\tgit tag -m \"A message\" annotated-tag &&\n+\tget_tag_msg annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header annotated-tag-edit $commit commit $time >expect\n+echo \"An edited message\" >>expect\n+test_expect_success 'set up editor' '\n+\twrite_script fakeeditor <<-\\EOF\n+\tsed -e \"s/A message/An edited message/g\" <\"$1\" >\"$1-\"\n+\tmv \"$1-\" \"$1\"\n+\tEOF\n+'\n+test_expect_success \\\n+\t'creating an annotated tag with -m message --edit should succeed' '\n+\tGIT_EDITOR=./fakeeditor git tag -m \"A message\" --edit annotated-tag-edit &&\n+\tget_tag_msg annotated-tag-edit >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >msgfile <<EOF\n+Another message\n+in a file.\n+EOF\n+get_tag_header file-annotated-tag $commit commit $time >expect\n+cat msgfile >>expect\n+test_expect_success \\\n+\t'creating an annotated tag with -F messagefile should succeed' '\n+\tgit tag -F msgfile file-annotated-tag &&\n+\tget_tag_msg file-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header file-annotated-tag-edit $commit commit $time >expect\n+sed -e \"s/Another message/Another edited message/g\" msgfile >>expect\n+test_expect_success 'set up editor' '\n+\twrite_script fakeeditor <<-\\EOF\n+\tsed -e \"s/Another message/Another edited message/g\" <\"$1\" >\"$1-\"\n+\tmv \"$1-\" \"$1\"\n+\tEOF\n+'\n+test_expect_success \\\n+\t'creating an annotated tag with -F messagefile --edit should succeed' '\n+\tGIT_EDITOR=./fakeeditor git tag -F msgfile --edit file-annotated-tag-edit &&\n+\tget_tag_msg file-annotated-tag-edit >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >inputmsg <<EOF\n+A message from the\n+standard input\n+EOF\n+get_tag_header stdin-annotated-tag $commit commit $time >expect\n+cat inputmsg >>expect\n+test_expect_success 'creating an annotated tag with -F - should succeed' '\n+\tgit tag -F - stdin-annotated-tag <inputmsg &&\n+\tget_tag_msg stdin-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success \\\n+\t'trying to create a tag with a non-existing -F file should fail' '\n+\t! test -f nonexistingfile &&\n+\t! tag_exists notag &&\n+\ttest_must_fail git tag -F nonexistingfile notag &&\n+\t! tag_exists notag\n+'\n+\n+test_expect_success \\\n+\t'trying to create tags giving both -m or -F options should fail' '\n+\techo \"message file 1\" >msgfile1 &&\n+\techo \"message file 2\" >msgfile2 &&\n+\t! tag_exists msgtag &&\n+\ttest_must_fail git tag -m \"message 1\" -F msgfile1 msgtag &&\n+\t! tag_exists msgtag &&\n+\ttest_must_fail git tag -F msgfile1 -m \"message 1\" msgtag &&\n+\t! tag_exists msgtag &&\n+\ttest_must_fail git tag -m \"message 1\" -F msgfile1 \\\n+\t\t-m \"message 2\" msgtag &&\n+\t! tag_exists msgtag\n+'\n+\n+# blank and empty messages:\n+\n+get_tag_header empty-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with an empty -m message should succeed' '\n+\tgit tag -m \"\" empty-annotated-tag &&\n+\tget_tag_msg empty-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+>emptyfile\n+get_tag_header emptyfile-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with an empty -F messagefile should succeed' '\n+\tgit tag -F emptyfile emptyfile-annotated-tag &&\n+\tget_tag_msg emptyfile-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+printf '\\n\\n  \\n\\t\\nLeading blank lines\\n' >blanksfile\n+printf '\\n\\t \\t  \\nRepeated blank lines\\n' >>blanksfile\n+printf '\\n\\n\\nTrailing spaces      \\t  \\n' >>blanksfile\n+printf '\\nTrailing blank lines\\n\\n\\t \\n\\n' >>blanksfile\n+get_tag_header blanks-annotated-tag $commit commit $time >expect\n+cat >>expect <<EOF\n+Leading blank lines\n+\n+Repeated blank lines\n+\n+Trailing spaces\n+\n+Trailing blank lines\n+EOF\n+test_expect_success \\\n+\t'extra blanks in the message for an annotated tag should be removed' '\n+\tgit tag -F blanksfile blanks-annotated-tag &&\n+\tget_tag_msg blanks-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header blank-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with blank -m message with spaces should succeed' '\n+\tgit tag -m \"     \" blank-annotated-tag &&\n+\tget_tag_msg blank-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+echo '     ' >blankfile\n+echo ''      >>blankfile\n+echo '  '    >>blankfile\n+get_tag_header blankfile-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with blank -F messagefile with spaces should succeed' '\n+\tgit tag -F blankfile blankfile-annotated-tag &&\n+\tget_tag_msg blankfile-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+printf '      ' >blanknonlfile\n+get_tag_header blanknonlfile-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with -F file of spaces and no newline should succeed' '\n+\tgit tag -F blanknonlfile blanknonlfile-annotated-tag &&\n+\tget_tag_msg blanknonlfile-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+# messages with commented lines:\n+\n+cat >commentsfile <<EOF\n+# A comment\n+\n+############\n+The message.\n+############\n+One line.\n+\n+\n+# commented lines\n+# commented lines\n+\n+Another line.\n+# comments\n+\n+Last line.\n+EOF\n+get_tag_header comments-annotated-tag $commit commit $time >expect\n+cat >>expect <<EOF\n+The message.\n+One line.\n+\n+Another line.\n+\n+Last line.\n+EOF\n+test_expect_success \\\n+\t'creating a tag using a -F messagefile with #comments should succeed' '\n+\tgit tag -F commentsfile comments-annotated-tag &&\n+\tget_tag_msg comments-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header comment-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with a #comment in the -m message should succeed' '\n+\tgit tag -m \"#comment\" comment-annotated-tag &&\n+\tget_tag_msg comment-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+echo '#comment' >commentfile\n+echo ''         >>commentfile\n+echo '####'     >>commentfile\n+get_tag_header commentfile-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with #comments in the -F messagefile should succeed' '\n+\tgit tag -F commentfile commentfile-annotated-tag &&\n+\tget_tag_msg commentfile-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+printf '#comment' >commentnonlfile\n+get_tag_header commentnonlfile-annotated-tag $commit commit $time >expect\n+test_expect_success \\\n+\t'creating a tag with a file of #comment and no newline should succeed' '\n+\tgit tag -F commentnonlfile commentnonlfile-annotated-tag &&\n+\tget_tag_msg commentnonlfile-annotated-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+# listing messages for annotated non-signed tags:\n+\n+test_expect_success \\\n+\t'listing the one-line message of a non-signed tag should succeed' '\n+\tgit tag -m \"A msg\" tag-one-line &&\n+\n+\techo \"tag-one-line\" >expect &&\n+\tgit tag -l | grep \"^tag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l | grep \"^tag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l tag-one-line >actual &&\n+\ttest_cmp expect actual &&\n+\n+\tgit tag -n0 | grep \"^tag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 tag-one-line >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"tag-one-line    A msg\" >expect &&\n+\tgit tag -n1 -l | grep \"^tag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n -l | grep \"^tag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n1 -l tag-one-line >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n2 -l tag-one-line >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n999 -l tag-one-line >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'The -n 100 invocation means -n --list 100, not -n100' '\n+\tgit tag -n 100 >actual &&\n+\ttest_must_be_empty actual &&\n+\n+\tgit tag -m \"A msg\" 100 &&\n+\techo \"100             A msg\" >expect &&\n+\tgit tag -n 100 >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success \\\n+\t'listing the zero-lines message of a non-signed tag should succeed' '\n+\tgit tag -m \"\" tag-zero-lines &&\n+\n+\techo \"tag-zero-lines\" >expect &&\n+\tgit tag -l | grep \"^tag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l | grep \"^tag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l tag-zero-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"tag-zero-lines  \" >expect &&\n+\tgit tag -n1 -l | grep \"^tag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n -l | grep \"^tag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n1 -l tag-zero-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n2 -l tag-zero-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n999 -l tag-zero-lines >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+echo 'tag line one' >annotagmsg\n+echo 'tag line two' >>annotagmsg\n+echo 'tag line three' >>annotagmsg\n+test_expect_success \\\n+\t'listing many message lines of a non-signed tag should succeed' '\n+\tgit tag -F annotagmsg tag-lines &&\n+\n+\techo \"tag-lines\" >expect &&\n+\tgit tag -l | grep \"^tag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l | grep \"^tag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l tag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"tag-lines       tag line one\" >expect &&\n+\tgit tag -n1 -l | grep \"^tag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n -l | grep \"^tag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n1 -l tag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"    tag line two\" >>expect &&\n+\tgit tag -n2 -l | grep \"^ *tag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n2 -l tag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"    tag line three\" >>expect &&\n+\tgit tag -n3 -l | grep \"^ *tag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n3 -l tag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n4 -l | grep \"^ *tag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n4 -l tag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n99 -l | grep \"^ *tag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n99 -l tag-lines >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'annotations for blobs are empty' '\n+\tblob=$(git hash-object -w --stdin <<-\\EOF\n+\tBlob paragraph 1.\n+\n+\tBlob paragraph 2.\n+\tEOF\n+\t) &&\n+\tgit tag tag-blob $blob &&\n+\techo \"tag-blob        \" >expect &&\n+\tgit tag -n1 -l tag-blob >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+# trying to verify annotated non-signed tags:\n+\n+test_expect_success GPG \\\n+\t'trying to verify an annotated non-signed tag should fail' '\n+\ttag_exists annotated-tag &&\n+\ttest_must_fail git tag -v annotated-tag\n+'\n+\n+test_expect_success GPG \\\n+\t'trying to verify a file-annotated non-signed tag should fail' '\n+\ttag_exists file-annotated-tag &&\n+\ttest_must_fail git tag -v file-annotated-tag\n+'\n+\n+test_expect_success GPG \\\n+\t'trying to verify two annotated non-signed tags should fail' '\n+\ttag_exists annotated-tag file-annotated-tag &&\n+\ttest_must_fail git tag -v annotated-tag file-annotated-tag\n+'\n+\n+# creating and verifying signed tags:\n+\n+get_tag_header signed-tag $commit commit $time >expect\n+echo 'A signed tag message' >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG 'creating a signed tag with -m message should succeed' '\n+\tgit tag -s -m \"A signed tag message\" signed-tag &&\n+\tget_tag_msg signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header u-signed-tag $commit commit $time >expect\n+echo 'Another message' >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG 'sign with a given key id' '\n+\n+\tgit tag -u committer@example.com -m \"Another message\" u-signed-tag &&\n+\tget_tag_msg u-signed-tag >actual &&\n+\ttest_cmp expect actual\n+\n+'\n+\n+test_expect_success GPG 'sign with an unknown id (1)' '\n+\n+\ttest_must_fail git tag -u author@example.com \\\n+\t\t-m \"Another message\" o-signed-tag\n+\n+'\n+\n+test_expect_success GPG 'sign with an unknown id (2)' '\n+\n+\ttest_must_fail git tag -u DEADBEEF -m \"Another message\" o-signed-tag\n+\n+'\n+\n+cat >fakeeditor <<'EOF'\n+#!/bin/sh\n+test -n \"$1\" && exec >\"$1\"\n+echo A signed tag message\n+echo from a fake editor.\n+EOF\n+chmod +x fakeeditor\n+\n+get_tag_header implied-sign $commit commit $time >expect\n+./fakeeditor >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG '-u implies signed tag' '\n+\tGIT_EDITOR=./fakeeditor git tag -u CDDE430D implied-sign &&\n+\tget_tag_msg implied-sign >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >sigmsgfile <<EOF\n+Another signed tag\n+message in a file.\n+EOF\n+get_tag_header file-signed-tag $commit commit $time >expect\n+cat sigmsgfile >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with -F messagefile should succeed' '\n+\tgit tag -s -F sigmsgfile file-signed-tag &&\n+\tget_tag_msg file-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >siginputmsg <<EOF\n+A signed tag message from\n+the standard input\n+EOF\n+get_tag_header stdin-signed-tag $commit commit $time >expect\n+cat siginputmsg >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG 'creating a signed tag with -F - should succeed' '\n+\tgit tag -s -F - stdin-signed-tag <siginputmsg &&\n+\tget_tag_msg stdin-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header implied-annotate $commit commit $time >expect\n+./fakeeditor >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG '-s implies annotated tag' '\n+\tGIT_EDITOR=./fakeeditor git tag -s implied-annotate &&\n+\tget_tag_msg implied-annotate >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header forcesignannotated-implied-sign $commit commit $time >expect\n+echo \"A message\" >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'git tag -s implied if configured with tag.forcesignannotated' \\\n+\t'test_config tag.forcesignannotated true &&\n+\tgit tag -m \"A message\" forcesignannotated-implied-sign &&\n+\tget_tag_msg forcesignannotated-implied-sign >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG \\\n+\t'lightweight with no message when configured with tag.forcesignannotated' \\\n+\t'test_config tag.forcesignannotated true &&\n+\tgit tag forcesignannotated-lightweight &&\n+\ttag_exists forcesignannotated-lightweight &&\n+\ttest_must_fail git tag -v forcesignannotated-no-message\n+'\n+\n+get_tag_header forcesignannotated-annotate $commit commit $time >expect\n+echo \"A message\" >>expect\n+test_expect_success GPG \\\n+\t'git tag -a disable configured tag.forcesignannotated' \\\n+\t'test_config tag.forcesignannotated true &&\n+\tgit tag -a -m \"A message\" forcesignannotated-annotate &&\n+\tget_tag_msg forcesignannotated-annotate >actual &&\n+\ttest_cmp expect actual &&\n+\ttest_must_fail git tag -v forcesignannotated-annotate\n+'\n+\n+get_tag_header forcesignannotated-disabled $commit commit $time >expect\n+echo \"A message\" >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'git tag --sign enable GPG sign' \\\n+\t'test_config tag.forcesignannotated false &&\n+\tgit tag --sign -m \"A message\" forcesignannotated-disabled &&\n+\tget_tag_msg forcesignannotated-disabled >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG \\\n+\t'trying to create a signed tag with non-existing -F file should fail' '\n+\t! test -f nonexistingfile &&\n+\t! tag_exists nosigtag &&\n+\ttest_must_fail git tag -s -F nonexistingfile nosigtag &&\n+\t! tag_exists nosigtag\n+'\n+\n+test_expect_success GPG 'verifying a signed tag should succeed' \\\n+\t'git tag -v signed-tag'\n+\n+test_expect_success GPG 'verifying two signed tags in one command should succeed' \\\n+\t'git tag -v signed-tag file-signed-tag'\n+\n+test_expect_success GPG \\\n+\t'verifying many signed and non-signed tags should fail' '\n+\ttest_must_fail git tag -v signed-tag annotated-tag &&\n+\ttest_must_fail git tag -v file-annotated-tag file-signed-tag &&\n+\ttest_must_fail git tag -v annotated-tag \\\n+\t\tfile-signed-tag file-annotated-tag &&\n+\ttest_must_fail git tag -v signed-tag annotated-tag file-signed-tag\n+'\n+\n+test_expect_success GPG 'verifying a forged tag should fail' '\n+\tforged=$(git cat-file tag signed-tag |\n+\t\tsed -e \"s/signed-tag/forged-tag/\" |\n+\t\tgit mktag) &&\n+\tgit tag forged-tag $forged &&\n+\ttest_must_fail git tag -v forged-tag\n+'\n+\n+test_expect_success GPG 'verifying a proper tag with --format pass and format accordingly' '\n+\tcat >expect <<-\\EOF &&\n+\ttagname : signed-tag\n+\tEOF\n+\tgit tag -v --format=\"tagname : %(tag)\" \"signed-tag\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'verifying a forged tag with --format should fail silently' '\n+\ttest_must_fail git tag -v --format=\"tagname : %(tag)\" \"forged-tag\" >actual &&\n+\ttest_must_be_empty actual\n+'\n+\n+# blank and empty messages for signed tags:\n+\n+get_tag_header empty-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with an empty -m message should succeed' '\n+\tgit tag -s -m \"\" empty-signed-tag &&\n+\tget_tag_msg empty-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v empty-signed-tag\n+'\n+\n+>sigemptyfile\n+get_tag_header emptyfile-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with an empty -F messagefile should succeed' '\n+\tgit tag -s -F sigemptyfile emptyfile-signed-tag &&\n+\tget_tag_msg emptyfile-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v emptyfile-signed-tag\n+'\n+\n+printf '\\n\\n  \\n\\t\\nLeading blank lines\\n' > sigblanksfile\n+printf '\\n\\t \\t  \\nRepeated blank lines\\n' >>sigblanksfile\n+printf '\\n\\n\\nTrailing spaces      \\t  \\n' >>sigblanksfile\n+printf '\\nTrailing blank lines\\n\\n\\t \\n\\n' >>sigblanksfile\n+get_tag_header blanks-signed-tag $commit commit $time >expect\n+cat >>expect <<EOF\n+Leading blank lines\n+\n+Repeated blank lines\n+\n+Trailing spaces\n+\n+Trailing blank lines\n+EOF\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'extra blanks in the message for a signed tag should be removed' '\n+\tgit tag -s -F sigblanksfile blanks-signed-tag &&\n+\tget_tag_msg blanks-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v blanks-signed-tag\n+'\n+\n+get_tag_header blank-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with a blank -m message should succeed' '\n+\tgit tag -s -m \"     \" blank-signed-tag &&\n+\tget_tag_msg blank-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v blank-signed-tag\n+'\n+\n+echo '     ' >sigblankfile\n+echo ''      >>sigblankfile\n+echo '  '    >>sigblankfile\n+get_tag_header blankfile-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with blank -F file with spaces should succeed' '\n+\tgit tag -s -F sigblankfile blankfile-signed-tag &&\n+\tget_tag_msg blankfile-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v blankfile-signed-tag\n+'\n+\n+printf '      ' >sigblanknonlfile\n+get_tag_header blanknonlfile-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with spaces and no newline should succeed' '\n+\tgit tag -s -F sigblanknonlfile blanknonlfile-signed-tag &&\n+\tget_tag_msg blanknonlfile-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v blanknonlfile-signed-tag\n+'\n+\n+test_expect_success GPG 'signed tag with embedded PGP message' '\n+\tcat >msg <<-\\EOF &&\n+\t-----BEGIN PGP MESSAGE-----\n+\n+\tthis is not a real PGP message\n+\t-----END PGP MESSAGE-----\n+\tEOF\n+\tgit tag -s -F msg confusing-pgp-message &&\n+\tgit tag -v confusing-pgp-message\n+'\n+\n+# messages with commented lines for signed tags:\n+\n+cat >sigcommentsfile <<EOF\n+# A comment\n+\n+############\n+The message.\n+############\n+One line.\n+\n+\n+# commented lines\n+# commented lines\n+\n+Another line.\n+# comments\n+\n+Last line.\n+EOF\n+get_tag_header comments-signed-tag $commit commit $time >expect\n+cat >>expect <<EOF\n+The message.\n+One line.\n+\n+Another line.\n+\n+Last line.\n+EOF\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with a -F file with #comments should succeed' '\n+\tgit tag -s -F sigcommentsfile comments-signed-tag &&\n+\tget_tag_msg comments-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v comments-signed-tag\n+'\n+\n+get_tag_header comment-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with #commented -m message should succeed' '\n+\tgit tag -s -m \"#comment\" comment-signed-tag &&\n+\tget_tag_msg comment-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v comment-signed-tag\n+'\n+\n+echo '#comment' >sigcommentfile\n+echo ''         >>sigcommentfile\n+echo '####'     >>sigcommentfile\n+get_tag_header commentfile-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with #commented -F messagefile should succeed' '\n+\tgit tag -s -F sigcommentfile commentfile-signed-tag &&\n+\tget_tag_msg commentfile-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v commentfile-signed-tag\n+'\n+\n+printf '#comment' >sigcommentnonlfile\n+get_tag_header commentnonlfile-signed-tag $commit commit $time >expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag with a #comment and no newline should succeed' '\n+\tgit tag -s -F sigcommentnonlfile commentnonlfile-signed-tag &&\n+\tget_tag_msg commentnonlfile-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -v commentnonlfile-signed-tag\n+'\n+\n+# listing messages for signed tags:\n+\n+test_expect_success GPG \\\n+\t'listing the one-line message of a signed tag should succeed' '\n+\tgit tag -s -m \"A message line signed\" stag-one-line &&\n+\n+\techo \"stag-one-line\" >expect &&\n+\tgit tag -l | grep \"^stag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l | grep \"^stag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l stag-one-line >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"stag-one-line   A message line signed\" >expect &&\n+\tgit tag -n1 -l | grep \"^stag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n -l | grep \"^stag-one-line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n1 -l stag-one-line >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n2 -l stag-one-line >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n999 -l stag-one-line >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG \\\n+\t'listing the zero-lines message of a signed tag should succeed' '\n+\tgit tag -s -m \"\" stag-zero-lines &&\n+\n+\techo \"stag-zero-lines\" >expect &&\n+\tgit tag -l | grep \"^stag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l | grep \"^stag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l stag-zero-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"stag-zero-lines \" >expect &&\n+\tgit tag -n1 -l | grep \"^stag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n -l | grep \"^stag-zero-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n1 -l stag-zero-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n2 -l stag-zero-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n999 -l stag-zero-lines >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+echo 'stag line one' >sigtagmsg\n+echo 'stag line two' >>sigtagmsg\n+echo 'stag line three' >>sigtagmsg\n+test_expect_success GPG \\\n+\t'listing many message lines of a signed tag should succeed' '\n+\tgit tag -s -F sigtagmsg stag-lines &&\n+\n+\techo \"stag-lines\" >expect &&\n+\tgit tag -l | grep \"^stag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l | grep \"^stag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n0 -l stag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"stag-lines      stag line one\" >expect &&\n+\tgit tag -n1 -l | grep \"^stag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n -l | grep \"^stag-lines\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n1 -l stag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"    stag line two\" >>expect &&\n+\tgit tag -n2 -l | grep \"^ *stag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n2 -l stag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\n+\techo \"    stag line three\" >>expect &&\n+\tgit tag -n3 -l | grep \"^ *stag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n3 -l stag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n4 -l | grep \"^ *stag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n4 -l stag-lines >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n99 -l | grep \"^ *stag.line\" >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -n99 -l stag-lines >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+# tags pointing to objects different from commits:\n+\n+tree=$(git rev-parse HEAD^{tree})\n+blob=$(git rev-parse HEAD:foo)\n+tag=$(git rev-parse signed-tag 2>/dev/null)\n+\n+get_tag_header tree-signed-tag $tree tree $time >expect\n+echo \"A message for a tree\" >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag pointing to a tree should succeed' '\n+\tgit tag -s -m \"A message for a tree\" tree-signed-tag HEAD^{tree} &&\n+\tget_tag_msg tree-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header blob-signed-tag $blob blob $time >expect\n+echo \"A message for a blob\" >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag pointing to a blob should succeed' '\n+\tgit tag -s -m \"A message for a blob\" blob-signed-tag HEAD:foo &&\n+\tget_tag_msg blob-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+get_tag_header tag-signed-tag $tag tag $time >expect\n+echo \"A message for another tag\" >>expect\n+echo '-----BEGIN PGP SIGNATURE-----' >>expect\n+test_expect_success GPG \\\n+\t'creating a signed tag pointing to another tag should succeed' '\n+\tgit tag -s -m \"A message for another tag\" tag-signed-tag signed-tag &&\n+\tget_tag_msg tag-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+# usage with rfc1991 signatures\n+get_tag_header rfc1991-signed-tag $commit commit $time >expect\n+echo \"RFC1991 signed tag\" >>expect\n+echo '-----BEGIN PGP MESSAGE-----' >>expect\n+test_expect_success GPG,RFC1991 \\\n+\t'creating a signed tag with rfc1991' '\n+\techo \"rfc1991\" >gpghome/gpg.conf &&\n+\tgit tag -s -m \"RFC1991 signed tag\" rfc1991-signed-tag $commit &&\n+\tget_tag_msg rfc1991-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+cat >fakeeditor <<'EOF'\n+#!/bin/sh\n+cp \"$1\" actual\n+EOF\n+chmod +x fakeeditor\n+\n+test_expect_success GPG,RFC1991 \\\n+\t'reediting a signed tag body omits signature' '\n+\techo \"rfc1991\" >gpghome/gpg.conf &&\n+\techo \"RFC1991 signed tag\" >expect &&\n+\tGIT_EDITOR=./fakeeditor git tag -f -s rfc1991-signed-tag $commit &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG,RFC1991 \\\n+\t'verifying rfc1991 signature' '\n+\techo \"rfc1991\" >gpghome/gpg.conf &&\n+\tgit tag -v rfc1991-signed-tag\n+'\n+\n+test_expect_success GPG,RFC1991 \\\n+\t'list tag with rfc1991 signature' '\n+\techo \"rfc1991\" >gpghome/gpg.conf &&\n+\techo \"rfc1991-signed-tag RFC1991 signed tag\" >expect &&\n+\tgit tag -l -n1 rfc1991-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -l -n2 rfc1991-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -l -n999 rfc1991-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+rm -f gpghome/gpg.conf\n+\n+test_expect_success GPG,RFC1991 \\\n+\t'verifying rfc1991 signature without --rfc1991' '\n+\tgit tag -v rfc1991-signed-tag\n+'\n+\n+test_expect_success GPG,RFC1991 \\\n+\t'list tag with rfc1991 signature without --rfc1991' '\n+\techo \"rfc1991-signed-tag RFC1991 signed tag\" >expect &&\n+\tgit tag -l -n1 rfc1991-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -l -n2 rfc1991-signed-tag >actual &&\n+\ttest_cmp expect actual &&\n+\tgit tag -l -n999 rfc1991-signed-tag >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG,RFC1991 \\\n+\t'reediting a signed tag body omits signature' '\n+\techo \"RFC1991 signed tag\" >expect &&\n+\tGIT_EDITOR=./fakeeditor git tag -f -s rfc1991-signed-tag $commit &&\n+\ttest_cmp expect actual\n+'\n+\n+# try to sign with bad user.signingkey\n+test_expect_success GPG \\\n+\t'git tag -s fails if gpg is misconfigured (bad key)' \\\n+\t'test_config user.signingkey BobTheMouse &&\n+\ttest_must_fail git tag -s -m tail tag-gpg-failure'\n+\n+# try to produce invalid signature\n+test_expect_success GPG \\\n+\t'git tag -s fails if gpg is misconfigured (bad signature format)' \\\n+\t'test_config signing.openpgp.program echo &&\n+\t test_must_fail git tag -s -m tail tag-gpg-failure'\n+\n+# try to sign with bad user.signingkey\n+test_expect_success GPGSM \\\n+\t'git tag -s fails if gpgsm is misconfigured (bad key)' \\\n+\t'test_config user.signingkey BobTheMouse &&\n+\t test_config signing.default x509 &&\n+\t test_must_fail git tag -s -m tail tag-gpg-failure'\n+\n+# try to produce invalid signature\n+test_expect_success GPGSM \\\n+\t'git tag -s fails if gpgsm is misconfigured (bad signature format)' \\\n+\t'test_config signing.x509.program echo &&\n+\t test_config signing.default x509 &&\n+\t test_must_fail git tag -s -m tail tag-gpg-failure'\n+\n+# try to verify without gpg:\n+\n+rm -rf gpghome\n+test_expect_success GPG \\\n+\t'verify signed tag fails when public key is not present' \\\n+\t'test_must_fail git tag -v signed-tag'\n+\n+test_expect_success \\\n+\t'git tag -a fails if tag annotation is empty' '\n+\t! (GIT_EDITOR=cat git tag -a initial-comment)\n+'\n+\n+test_expect_success \\\n+\t'message in editor has initial comment' '\n+\t! (GIT_EDITOR=cat git tag -a initial-comment > actual)\n+'\n+\n+test_expect_success 'message in editor has initial comment: first line' '\n+\t# check the first line --- should be empty\n+\techo >first.expect &&\n+\tsed -e 1q <actual >first.actual &&\n+\ttest_i18ncmp first.expect first.actual\n+'\n+\n+test_expect_success \\\n+\t'message in editor has initial comment: remainder' '\n+\t# remove commented lines from the remainder -- should be empty\n+\tsed -e 1d -e \"/^#/d\" <actual >rest.actual &&\n+\ttest_must_be_empty rest.actual\n+'\n+\n+get_tag_header reuse $commit commit $time >expect\n+echo \"An annotation to be reused\" >> expect\n+test_expect_success \\\n+\t'overwriting an annoted tag should use its previous body' '\n+\tgit tag -a -m \"An annotation to be reused\" reuse &&\n+\tGIT_EDITOR=true git tag -f -a reuse &&\n+\tget_tag_msg reuse >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'filename for the message is relative to cwd' '\n+\tmkdir subdir &&\n+\techo \"Tag message in top directory\" >msgfile-5 &&\n+\techo \"Tag message in sub directory\" >subdir/msgfile-5 &&\n+\t(\n+\t\tcd subdir &&\n+\t\tgit tag -a -F msgfile-5 tag-from-subdir\n+\t) &&\n+\tgit cat-file tag tag-from-subdir | grep \"in sub directory\"\n+'\n+\n+test_expect_success 'filename for the message is relative to cwd' '\n+\techo \"Tag message in sub directory\" >subdir/msgfile-6 &&\n+\t(\n+\t\tcd subdir &&\n+\t\tgit tag -a -F msgfile-6 tag-from-subdir-2\n+\t) &&\n+\tgit cat-file tag tag-from-subdir-2 | grep \"in sub directory\"\n+'\n+\n+# create a few more commits to test --contains\n+\n+hash1=$(git rev-parse HEAD)\n+\n+test_expect_success 'creating second commit and tag' '\n+\techo foo-2.0 >foo &&\n+\tgit add foo &&\n+\tgit commit -m second &&\n+\tgit tag v2.0\n+'\n+\n+hash2=$(git rev-parse HEAD)\n+\n+test_expect_success 'creating third commit without tag' '\n+\techo foo-dev >foo &&\n+\tgit add foo &&\n+\tgit commit -m third\n+'\n+\n+hash3=$(git rev-parse HEAD)\n+\n+# simple linear checks of --continue\n+\n+cat > expected <<EOF\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+v2.0\n+EOF\n+\n+test_expect_success 'checking that first commit is in all tags (hash)' \"\n+\tgit tag -l --contains $hash1 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+# other ways of specifying the commit\n+test_expect_success 'checking that first commit is in all tags (tag)' \"\n+\tgit tag -l --contains v1.0 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+test_expect_success 'checking that first commit is in all tags (relative)' \"\n+\tgit tag -l --contains HEAD~2 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+# All the --contains tests above, but with --no-contains\n+test_expect_success 'checking that first commit is not listed in any tag with --no-contains  (hash)' \"\n+\tgit tag -l --no-contains $hash1 v* >actual &&\n+\ttest_must_be_empty actual\n+\"\n+\n+test_expect_success 'checking that first commit is in all tags (tag)' \"\n+\tgit tag -l --no-contains v1.0 v* >actual &&\n+\ttest_must_be_empty actual\n+\"\n+\n+test_expect_success 'checking that first commit is in all tags (relative)' \"\n+\tgit tag -l --no-contains HEAD~2 v* >actual &&\n+\ttest_must_be_empty actual\n+\"\n+\n+cat > expected <<EOF\n+v2.0\n+EOF\n+\n+test_expect_success 'checking that second commit only has one tag' \"\n+\tgit tag -l --contains $hash2 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+cat > expected <<EOF\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+EOF\n+\n+test_expect_success 'inverse of the last test, with --no-contains' \"\n+\tgit tag -l --no-contains $hash2 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+test_expect_success 'checking that third commit has no tags' \"\n+\tgit tag -l --contains $hash3 v* >actual &&\n+\ttest_must_be_empty actual\n+\"\n+\n+cat > expected <<EOF\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+v2.0\n+EOF\n+\n+test_expect_success 'conversely --no-contains on the third commit lists all tags' \"\n+\tgit tag -l --no-contains $hash3 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+# how about a simple merge?\n+\n+test_expect_success 'creating simple branch' '\n+\tgit branch stable v2.0 &&\n+        git checkout stable &&\n+\techo foo-3.0 > foo &&\n+\tgit commit foo -m fourth &&\n+\tgit tag v3.0\n+'\n+\n+hash4=$(git rev-parse HEAD)\n+\n+cat > expected <<EOF\n+v3.0\n+EOF\n+\n+test_expect_success 'checking that branch head only has one tag' \"\n+\tgit tag -l --contains $hash4 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+cat > expected <<EOF\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+v2.0\n+EOF\n+\n+test_expect_success 'checking that branch head with --no-contains lists all but one tag' \"\n+\tgit tag -l --no-contains $hash4 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+test_expect_success 'merging original branch into this branch' '\n+\tgit merge --strategy=ours master &&\n+        git tag v4.0\n+'\n+\n+cat > expected <<EOF\n+v4.0\n+EOF\n+\n+test_expect_success 'checking that original branch head has one tag now' \"\n+\tgit tag -l --contains $hash3 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+cat > expected <<EOF\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+v2.0\n+v3.0\n+EOF\n+\n+test_expect_success 'checking that original branch head with --no-contains lists all but one tag now' \"\n+\tgit tag -l --no-contains $hash3 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+cat > expected <<EOF\n+v0.2.1\n+v1.0\n+v1.0.1\n+v1.1.3\n+v2.0\n+v3.0\n+v4.0\n+EOF\n+\n+test_expect_success 'checking that initial commit is in all tags' \"\n+\tgit tag -l --contains $hash1 v* >actual &&\n+\ttest_cmp expected actual\n+\"\n+\n+test_expect_success 'checking that --contains can be used in non-list mode' '\n+\tgit tag --contains $hash1 v* >actual &&\n+\ttest_cmp expected actual\n+'\n+\n+test_expect_success 'checking that initial commit is in all tags with --no-contains' \"\n+\tgit tag -l --no-contains $hash1 v* >actual &&\n+\ttest_must_be_empty actual\n+\"\n+\n+# mixing modes and options:\n+\n+test_expect_success 'mixing incompatibles modes and options is forbidden' '\n+\ttest_must_fail git tag -a &&\n+\ttest_must_fail git tag -a -l &&\n+\ttest_must_fail git tag -s &&\n+\ttest_must_fail git tag -s -l &&\n+\ttest_must_fail git tag -m &&\n+\ttest_must_fail git tag -m -l &&\n+\ttest_must_fail git tag -m \"hlagh\" &&\n+\ttest_must_fail git tag -m \"hlagh\" -l &&\n+\ttest_must_fail git tag -F &&\n+\ttest_must_fail git tag -F -l &&\n+\ttest_must_fail git tag -f &&\n+\ttest_must_fail git tag -f -l &&\n+\ttest_must_fail git tag -a -s -m -F &&\n+\ttest_must_fail git tag -a -s -m -F -l &&\n+\ttest_must_fail git tag -l -v &&\n+\ttest_must_fail git tag -l -d &&\n+\ttest_must_fail git tag -l -v -d &&\n+\ttest_must_fail git tag -n 100 -v &&\n+\ttest_must_fail git tag -l -m msg &&\n+\ttest_must_fail git tag -l -F some file &&\n+\ttest_must_fail git tag -v -s &&\n+\ttest_must_fail git tag --contains tag-tree &&\n+\ttest_must_fail git tag --contains tag-blob &&\n+\ttest_must_fail git tag --no-contains tag-tree &&\n+\ttest_must_fail git tag --no-contains tag-blob &&\n+\ttest_must_fail git tag --contains --no-contains &&\n+\ttest_must_fail git tag --no-with HEAD &&\n+\ttest_must_fail git tag --no-without HEAD\n+'\n+\n+for option in --contains --with --no-contains --without --merged --no-merged --points-at\n+do\n+\ttest_expect_success \"mixing incompatible modes with $option is forbidden\" \"\n+\t\ttest_must_fail git tag -d $option HEAD &&\n+\t\ttest_must_fail git tag -d $option HEAD some-tag &&\n+\t\ttest_must_fail git tag -v $option HEAD\n+\t\"\n+\ttest_expect_success \"Doing 'git tag --list-like $option <commit> <pattern> is permitted\" \"\n+\t\tgit tag -n $option HEAD HEAD &&\n+\t\tgit tag $option HEAD HEAD &&\n+\t\tgit tag $option\n+\t\"\n+done\n+\n+# check points-at\n+\n+test_expect_success '--points-at can be used in non-list mode' '\n+\techo v4.0 >expect &&\n+\tgit tag --points-at=v4.0 \"v*\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--points-at is a synonym for --points-at HEAD' '\n+\techo v4.0 >expect &&\n+\tgit tag --points-at >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--points-at finds lightweight tags' '\n+\techo v4.0 >expect &&\n+\tgit tag --points-at v4.0 >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--points-at finds annotated tags of commits' '\n+\tgit tag -m \"v4.0, annotated\" annotated-v4.0 v4.0 &&\n+\techo annotated-v4.0 >expect &&\n+\tgit tag -l --points-at v4.0 \"annotated*\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--points-at finds annotated tags of tags' '\n+\tgit tag -m \"describing the v4.0 tag object\" \\\n+\t\tannotated-again-v4.0 annotated-v4.0 &&\n+\tcat >expect <<-\\EOF &&\n+\tannotated-again-v4.0\n+\tannotated-v4.0\n+\tEOF\n+\tgit tag --points-at=annotated-v4.0 >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'recursive tagging should give advice' '\n+\tsed -e \"s/|$//\" <<-EOF >expect &&\n+\thint: You have created a nested tag. The object referred to by your new tag is\n+\thint: already a tag. If you meant to tag the object that it points to, use:\n+\thint: |\n+\thint: \tgit tag -f nested annotated-v4.0^{}\n+\tEOF\n+\tgit tag -m nested nested annotated-v4.0 2>actual &&\n+\ttest_i18ncmp expect actual\n+'\n+\n+test_expect_success 'multiple --points-at are OR-ed together' '\n+\tcat >expect <<-\\EOF &&\n+\tv2.0\n+\tv3.0\n+\tEOF\n+\tgit tag --points-at=v2.0 --points-at=v3.0 >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'lexical sort' '\n+\tgit tag foo1.3 &&\n+\tgit tag foo1.6 &&\n+\tgit tag foo1.10 &&\n+\tgit tag -l --sort=refname \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.10\n+\tfoo1.3\n+\tfoo1.6\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'version sort' '\n+\tgit tag -l --sort=version:refname \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.3\n+\tfoo1.6\n+\tfoo1.10\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'reverse version sort' '\n+\tgit tag -l --sort=-version:refname \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.10\n+\tfoo1.6\n+\tfoo1.3\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'reverse lexical sort' '\n+\tgit tag -l --sort=-refname \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.6\n+\tfoo1.3\n+\tfoo1.10\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'configured lexical sort' '\n+\ttest_config tag.sort \"v:refname\" &&\n+\tgit tag -l \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.3\n+\tfoo1.6\n+\tfoo1.10\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'option override configured sort' '\n+\ttest_config tag.sort \"v:refname\" &&\n+\tgit tag -l --sort=-refname \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.6\n+\tfoo1.3\n+\tfoo1.10\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'invalid sort parameter on command line' '\n+\ttest_must_fail git tag -l --sort=notvalid \"foo*\" >actual\n+'\n+\n+test_expect_success 'invalid sort parameter in configuratoin' '\n+\ttest_config tag.sort \"v:notvalid\" &&\n+\ttest_must_fail git tag -l \"foo*\"\n+'\n+\n+test_expect_success 'version sort with prerelease reordering' '\n+\ttest_config versionsort.prereleaseSuffix -rc &&\n+\tgit tag foo1.6-rc1 &&\n+\tgit tag foo1.6-rc2 &&\n+\tgit tag -l --sort=version:refname \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.3\n+\tfoo1.6-rc1\n+\tfoo1.6-rc2\n+\tfoo1.6\n+\tfoo1.10\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'reverse version sort with prerelease reordering' '\n+\ttest_config versionsort.prereleaseSuffix -rc &&\n+\tgit tag -l --sort=-version:refname \"foo*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.10\n+\tfoo1.6\n+\tfoo1.6-rc2\n+\tfoo1.6-rc1\n+\tfoo1.3\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'version sort with prerelease reordering and common leading character' '\n+\ttest_config versionsort.prereleaseSuffix -before &&\n+\tgit tag foo1.7-before1 &&\n+\tgit tag foo1.7 &&\n+\tgit tag foo1.7-after1 &&\n+\tgit tag -l --sort=version:refname \"foo1.7*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.7-before1\n+\tfoo1.7\n+\tfoo1.7-after1\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'version sort with prerelease reordering, multiple suffixes and common leading character' '\n+\ttest_config versionsort.prereleaseSuffix -before &&\n+\tgit config --add versionsort.prereleaseSuffix -after &&\n+\tgit tag -l --sort=version:refname \"foo1.7*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.7-before1\n+\tfoo1.7-after1\n+\tfoo1.7\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'version sort with prerelease reordering, multiple suffixes match the same tag' '\n+\ttest_config versionsort.prereleaseSuffix -bar &&\n+\tgit config --add versionsort.prereleaseSuffix -foo-baz &&\n+\tgit config --add versionsort.prereleaseSuffix -foo-bar &&\n+\tgit tag foo1.8-foo-bar &&\n+\tgit tag foo1.8-foo-baz &&\n+\tgit tag foo1.8 &&\n+\tgit tag -l --sort=version:refname \"foo1.8*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.8-foo-baz\n+\tfoo1.8-foo-bar\n+\tfoo1.8\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'version sort with prerelease reordering, multiple suffixes match starting at the same position' '\n+\ttest_config versionsort.prereleaseSuffix -pre &&\n+\tgit config --add versionsort.prereleaseSuffix -prerelease &&\n+\tgit tag foo1.9-pre1 &&\n+\tgit tag foo1.9-pre2 &&\n+\tgit tag foo1.9-prerelease1 &&\n+\tgit tag -l --sort=version:refname \"foo1.9*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.9-pre1\n+\tfoo1.9-pre2\n+\tfoo1.9-prerelease1\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'version sort with general suffix reordering' '\n+\ttest_config versionsort.suffix -alpha &&\n+\tgit config --add versionsort.suffix -beta &&\n+\tgit config --add versionsort.suffix \"\"  &&\n+\tgit config --add versionsort.suffix -gamma &&\n+\tgit config --add versionsort.suffix -delta &&\n+\tgit tag foo1.10-alpha &&\n+\tgit tag foo1.10-beta &&\n+\tgit tag foo1.10-gamma &&\n+\tgit tag foo1.10-delta &&\n+\tgit tag foo1.10-unlisted-suffix &&\n+\tgit tag -l --sort=version:refname \"foo1.10*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.10-alpha\n+\tfoo1.10-beta\n+\tfoo1.10\n+\tfoo1.10-unlisted-suffix\n+\tfoo1.10-gamma\n+\tfoo1.10-delta\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'versionsort.suffix overrides versionsort.prereleaseSuffix' '\n+\ttest_config versionsort.suffix -before &&\n+\ttest_config versionsort.prereleaseSuffix -after &&\n+\tgit tag -l --sort=version:refname \"foo1.7*\" >actual &&\n+\tcat >expect <<-\\EOF &&\n+\tfoo1.7-before1\n+\tfoo1.7\n+\tfoo1.7-after1\n+\tEOF\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'version sort with very long prerelease suffix' '\n+\ttest_config versionsort.prereleaseSuffix -very-looooooooooooooooooooooooong-prerelease-suffix &&\n+\tgit tag -l --sort=version:refname\n+'\n+\n+test_expect_success ULIMIT_STACK_SIZE '--contains and --no-contains work in a deep repo' '\n+\ti=1 &&\n+\twhile test $i -lt 8000\n+\tdo\n+\t\techo \"commit refs/heads/master\n+committer A U Thor <author@example.com> $((1000000000 + $i * 100)) +0200\n+data <<EOF\n+commit #$i\n+EOF\"\n+\t\ttest $i = 1 && echo \"from refs/heads/master^0\"\n+\t\ti=$(($i + 1))\n+\tdone | git fast-import &&\n+\tgit checkout master &&\n+\tgit tag far-far-away HEAD^ &&\n+\trun_with_limited_stack git tag --contains HEAD >actual &&\n+\ttest_must_be_empty actual &&\n+\trun_with_limited_stack git tag --no-contains HEAD >actual &&\n+\ttest_line_count \"-gt\" 10 actual\n+'\n+\n+test_expect_success '--format should list tags as per format given' '\n+\tcat >expect <<-\\EOF &&\n+\trefname : refs/tags/v1.0\n+\trefname : refs/tags/v1.0.1\n+\trefname : refs/tags/v1.1.3\n+\tEOF\n+\tgit tag -l --format=\"refname : %(refname)\" \"v1*\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success \"set up color tests\" '\n+\techo \"<RED>v1.0<RESET>\" >expect.color &&\n+\techo \"v1.0\" >expect.bare &&\n+\tcolor_args=\"--format=%(color:red)%(refname:short) --list v1.0\"\n+'\n+\n+test_expect_success '%(color) omitted without tty' '\n+\tTERM=vt100 git tag $color_args >actual.raw &&\n+\ttest_decode_color <actual.raw >actual &&\n+\ttest_cmp expect.bare actual\n+'\n+\n+test_expect_success TTY '%(color) present with tty' '\n+\ttest_terminal git tag $color_args >actual.raw &&\n+\ttest_decode_color <actual.raw >actual &&\n+\ttest_cmp expect.color actual\n+'\n+\n+test_expect_success '--color overrides auto-color' '\n+\tgit tag --color $color_args >actual.raw &&\n+\ttest_decode_color <actual.raw >actual &&\n+\ttest_cmp expect.color actual\n+'\n+\n+test_expect_success 'color.ui=always overrides auto-color' '\n+\tgit -c color.ui=always tag $color_args >actual.raw &&\n+\ttest_decode_color <actual.raw >actual &&\n+\ttest_cmp expect.color actual\n+'\n+\n+test_expect_success 'setup --merged test tags' '\n+\tgit tag mergetest-1 HEAD~2 &&\n+\tgit tag mergetest-2 HEAD~1 &&\n+\tgit tag mergetest-3 HEAD\n+'\n+\n+test_expect_success '--merged can be used in non-list mode' '\n+\tcat >expect <<-\\EOF &&\n+\tmergetest-1\n+\tmergetest-2\n+\tEOF\n+\tgit tag --merged=mergetest-2 \"mergetest*\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--merged is incompatible with --no-merged' '\n+\ttest_must_fail git tag --merged HEAD --no-merged HEAD\n+'\n+\n+test_expect_success '--merged shows merged tags' '\n+\tcat >expect <<-\\EOF &&\n+\tmergetest-1\n+\tmergetest-2\n+\tEOF\n+\tgit tag -l --merged=mergetest-2 mergetest-* >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--no-merged show unmerged tags' '\n+\tcat >expect <<-\\EOF &&\n+\tmergetest-3\n+\tEOF\n+\tgit tag -l --no-merged=mergetest-2 mergetest-* >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--no-merged can be used in non-list mode' '\n+\tgit tag --no-merged=mergetest-2 mergetest-* >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success 'ambiguous branch/tags not marked' '\n+\tgit tag ambiguous &&\n+\tgit branch ambiguous &&\n+\techo ambiguous >expect &&\n+\tgit tag -l ambiguous >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success '--contains combined with --no-contains' '\n+\t(\n+\t\tgit init no-contains &&\n+\t\tcd no-contains &&\n+\t\ttest_commit v0.1 &&\n+\t\ttest_commit v0.2 &&\n+\t\ttest_commit v0.3 &&\n+\t\ttest_commit v0.4 &&\n+\t\ttest_commit v0.5 &&\n+\t\tcat >expected <<-\\EOF &&\n+\t\tv0.2\n+\t\tv0.3\n+\t\tv0.4\n+\t\tEOF\n+\t\tgit tag --contains v0.2 --no-contains v0.5 >actual &&\n+\t\ttest_cmp expected actual\n+\t)\n+'\n+\n+# As the docs say, list tags which contain a specified *commit*. We\n+# don't recurse down to tags for trees or blobs pointed to by *those*\n+# commits.\n+test_expect_success 'Does --[no-]contains stop at commits? Yes!' '\n+\tcd no-contains &&\n+\tblob=$(git rev-parse v0.3:v0.3.t) &&\n+\ttree=$(git rev-parse v0.3^{tree}) &&\n+\tgit tag tag-blob $blob &&\n+\tgit tag tag-tree $tree &&\n+\tgit tag --contains v0.3 >actual &&\n+\tcat >expected <<-\\EOF &&\n+\tv0.3\n+\tv0.4\n+\tv0.5\n+\tEOF\n+\ttest_cmp expected actual &&\n+\tgit tag --no-contains v0.3 >actual &&\n+\tcat >expected <<-\\EOF &&\n+\tv0.1\n+\tv0.2\n+\tEOF\n+\ttest_cmp expected actual\n+'\n+\n+test_done\ndiff --git a/t/t7031-verify-tag-signconfig.sh b/t/t7031-verify-tag-signconfig.sh\nnew file mode 100755\nindex 000000000..b5238585a\n--- /dev/null\n+++ b/t/t7031-verify-tag-signconfig.sh\n@@ -0,0 +1,175 @@\n+#!/bin/sh\n+\n+test_description='signed tag tests using new config'\n+. ./test-lib.sh\n+. \"$TEST_DIRECTORY/lib-gpg.sh\"\n+\n+test_expect_success GPG 'create signed tags' '\n+\techo 1 >file && git add file &&\n+\ttest_tick && git commit -m initial &&\n+\tgit tag -s -m initial initial &&\n+\tgit branch side &&\n+\n+\techo 2 >file && test_tick && git commit -a -m second &&\n+\tgit tag -s -m second second &&\n+\n+\tgit checkout side &&\n+\techo 3 >elif && git add elif &&\n+\ttest_tick && git commit -m \"third on side\" &&\n+\n+\tgit checkout master &&\n+\ttest_tick && git merge -S side &&\n+\tgit tag -s -m merge merge &&\n+\n+\techo 4 >file && test_tick && git commit -a -S -m \"fourth unsigned\" &&\n+\tgit tag -a -m fourth-unsigned fourth-unsigned &&\n+\n+\ttest_tick && git commit --amend -S -m \"fourth signed\" &&\n+\tgit tag -s -m fourth fourth-signed &&\n+\n+\techo 5 >file && test_tick && git commit -a -m \"fifth\" &&\n+\tgit tag fifth-unsigned &&\n+\n+\tgit config commit.sign true &&\n+\techo 6 >file && test_tick && git commit -a -m \"sixth\" &&\n+\tgit tag -a -m sixth sixth-unsigned &&\n+\n+\ttest_tick && git rebase -f HEAD^^ && git tag -s -m 6th sixth-signed HEAD^ &&\n+\tgit tag -m seventh -s seventh-signed &&\n+\n+\techo 8 >file && test_tick && git commit -a -m eighth &&\n+\tgit tag -uB7227189 -m eighth eighth-signed-alt\n+'\n+\n+test_expect_success GPGSM 'create signed tags x509 ' '\n+\ttest_config signing.default x509 &&\n+\ttest_config user.signingkey $GIT_COMMITTER_EMAIL &&\n+\techo 9 >file && test_tick && git commit -a -m \"nineth gpgsm-signed\" &&\n+\tgit tag -s -m nineth nineth-signed-x509\n+'\n+\n+test_expect_success GPG 'verify and show signatures' '\n+\t(\n+\t\tfor tag in initial second merge fourth-signed sixth-signed seventh-signed\n+\t\tdo\n+\t\t\tgit verify-tag $tag 2>actual &&\n+\t\t\tgrep \"Good signature from\" actual &&\n+\t\t\t! grep \"BAD signature from\" actual &&\n+\t\t\techo $tag OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor tag in fourth-unsigned fifth-unsigned sixth-unsigned\n+\t\tdo\n+\t\t\ttest_must_fail git verify-tag $tag 2>actual &&\n+\t\t\t! grep \"Good signature from\" actual &&\n+\t\t\t! grep \"BAD signature from\" actual &&\n+\t\t\techo $tag OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor tag in eighth-signed-alt\n+\t\tdo\n+\t\t\tgit verify-tag $tag 2>actual &&\n+\t\t\tgrep \"Good signature from\" actual &&\n+\t\t\t! grep \"BAD signature from\" actual &&\n+\t\t\tgrep \"not certified\" actual &&\n+\t\t\techo $tag OK || exit 1\n+\t\tdone\n+\t)\n+'\n+\n+test_expect_success GPGSM 'verify and show signatures x509' '\n+\tgit verify-tag nineth-signed-x509 2>actual &&\n+\tgrep \"Good signature from\" actual &&\n+\t! grep \"BAD signature from\" actual &&\n+\techo nineth-signed-x509 OK\n+'\n+\n+test_expect_success GPG 'detect fudged signature' '\n+\tgit cat-file tag seventh-signed >raw &&\n+\tsed -e \"/^tag / s/seventh/7th forged/\" raw >forged1 &&\n+\tgit hash-object -w -t tag forged1 >forged1.tag &&\n+\ttest_must_fail git verify-tag $(cat forged1.tag) 2>actual1 &&\n+\tgrep \"BAD signature from\" actual1 &&\n+\t! grep \"Good signature from\" actual1\n+'\n+\n+test_expect_success GPG 'verify signatures with --raw' '\n+\t(\n+\t\tfor tag in initial second merge fourth-signed sixth-signed seventh-signed\n+\t\tdo\n+\t\t\tgit verify-tag --raw $tag 2>actual &&\n+\t\t\tgrep \"GOODSIG\" actual &&\n+\t\t\t! grep \"BADSIG\" actual &&\n+\t\t\techo $tag OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor tag in fourth-unsigned fifth-unsigned sixth-unsigned\n+\t\tdo\n+\t\t\ttest_must_fail git verify-tag --raw $tag 2>actual &&\n+\t\t\t! grep \"GOODSIG\" actual &&\n+\t\t\t! grep \"BADSIG\" actual &&\n+\t\t\techo $tag OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor tag in eighth-signed-alt\n+\t\tdo\n+\t\t\tgit verify-tag --raw $tag 2>actual &&\n+\t\t\tgrep \"GOODSIG\" actual &&\n+\t\t\t! grep \"BADSIG\" actual &&\n+\t\t\tgrep \"TRUST_UNDEFINED\" actual &&\n+\t\t\techo $tag OK || exit 1\n+\t\tdone\n+\t)\n+'\n+\n+test_expect_success GPGSM 'verify signatures with --raw x509' '\n+\tgit verify-tag --raw nineth-signed-x509 2>actual &&\n+\tgrep \"GOODSIG\" actual &&\n+\t! grep \"BADSIG\" actual &&\n+\techo nineth-signed-x509 OK\n+'\n+\n+test_expect_success GPG 'verify multiple tags' '\n+\ttags=\"fourth-signed sixth-signed seventh-signed\" &&\n+\tfor i in $tags\n+\tdo\n+\t\tgit verify-tag -v --raw $i || return 1\n+\tdone >expect.stdout 2>expect.stderr.1 &&\n+\tgrep \"^.GNUPG:.\" <expect.stderr.1 >expect.stderr &&\n+\tgit verify-tag -v --raw $tags >actual.stdout 2>actual.stderr.1 &&\n+\tgrep \"^.GNUPG:.\" <actual.stderr.1 >actual.stderr &&\n+\ttest_cmp expect.stdout actual.stdout &&\n+\ttest_cmp expect.stderr actual.stderr\n+'\n+\n+test_expect_success GPGSM 'verify multiple tags x509' '\n+\ttags=\"seventh-signed nineth-signed-x509\" &&\n+\tfor i in $tags\n+\tdo\n+\t\tgit verify-tag -v --raw $i || return 1\n+\tdone >expect.stdout 2>expect.stderr.1 &&\n+\tgrep \"^.GNUPG:.\" <expect.stderr.1 >expect.stderr &&\n+\tgit verify-tag -v --raw $tags >actual.stdout 2>actual.stderr.1 &&\n+\tgrep \"^.GNUPG:.\" <actual.stderr.1 >actual.stderr &&\n+\ttest_cmp expect.stdout actual.stdout &&\n+\ttest_cmp expect.stderr actual.stderr\n+'\n+\n+test_expect_success GPG 'verifying tag with --format' '\n+\tcat >expect <<-\\EOF &&\n+\ttagname : fourth-signed\n+\tEOF\n+\tgit verify-tag --format=\"tagname : %(tag)\" \"fourth-signed\" >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'verifying a forged tag with --format should fail silently' '\n+\ttest_must_fail git verify-tag --format=\"tagname : %(tag)\" $(cat forged1.tag) >actual-forged &&\n+\ttest_must_be_empty actual-forged\n+'\n+\n+test_done\ndiff --git a/t/t7522-signed-commit-signconfig.sh b/t/t7522-signed-commit-signconfig.sh\nnew file mode 100755\nindex 000000000..682b23a06\n--- /dev/null\n+++ b/t/t7522-signed-commit-signconfig.sh\n@@ -0,0 +1,288 @@\n+#!/bin/sh\n+\n+test_description='signed commit tests'\n+. ./test-lib.sh\n+GNUPGHOME_NOT_USED=$GNUPGHOME\n+. \"$TEST_DIRECTORY/lib-gpg.sh\"\n+\n+test_expect_success GPG 'create signed commits' '\n+\ttest_when_finished \"test_unconfig commit.gpgsign\" &&\n+\n+\techo 1 >file && git add file &&\n+\ttest_tick && git commit -S -m initial &&\n+\tgit tag initial &&\n+\tgit branch side &&\n+\n+\techo 2 >file && test_tick && git commit -a -S -m second &&\n+\tgit tag second &&\n+\n+\tgit checkout side &&\n+\techo 3 >elif && git add elif &&\n+\ttest_tick && git commit -m \"third on side\" &&\n+\n+\tgit checkout master &&\n+\ttest_tick && git merge -S side &&\n+\tgit tag merge &&\n+\n+\techo 4 >file && test_tick && git commit -a -m \"fourth unsigned\" &&\n+\tgit tag fourth-unsigned &&\n+\n+\ttest_tick && git commit --amend -S -m \"fourth signed\" &&\n+\tgit tag fourth-signed &&\n+\n+\tgit config commit.gpgsign true &&\n+\techo 5 >file && test_tick && git commit -a -m \"fifth signed\" &&\n+\tgit tag fifth-signed &&\n+\n+\tgit config commit.gpgsign false &&\n+\techo 6 >file && test_tick && git commit -a -m \"sixth\" &&\n+\tgit tag sixth-unsigned &&\n+\n+\tgit config commit.gpgsign true &&\n+\techo 7 >file && test_tick && git commit -a -m \"seventh\" --no-gpg-sign &&\n+\tgit tag seventh-unsigned &&\n+\n+\ttest_tick && git rebase -f HEAD^^ && git tag sixth-signed HEAD^ &&\n+\tgit tag seventh-signed &&\n+\n+\techo 8 >file && test_tick && git commit -a -m eighth -SB7227189 &&\n+\tgit tag eighth-signed-alt &&\n+\n+\t# commit.gpgsign is still on but this must not be signed\n+\techo 9 | git commit-tree HEAD^{tree} >oid &&\n+\ttest_line_count = 1 oid &&\n+\tgit tag ninth-unsigned $(cat oid) &&\n+\t# explicit -S of course must sign.\n+\techo 10 | git commit-tree -S HEAD^{tree} >oid &&\n+\ttest_line_count = 1 oid &&\n+\tgit tag tenth-signed $(cat oid) &&\n+\n+\t# --gpg-sign[=<key-id>] must sign.\n+\techo 11 | git commit-tree --gpg-sign HEAD^{tree} >oid &&\n+\ttest_line_count = 1 oid &&\n+\tgit tag eleventh-signed $(cat oid) &&\n+\techo 12 | git commit-tree --gpg-sign=B7227189 HEAD^{tree} >oid &&\n+\ttest_line_count = 1 oid &&\n+\tgit tag twelfth-signed-alt $(cat oid)\n+'\n+\n+test_expect_success GPG 'verify and show signatures' '\n+\t(\n+\t\tfor commit in initial second merge fourth-signed \\\n+\t\t\tfifth-signed sixth-signed seventh-signed tenth-signed \\\n+\t\t\televenth-signed\n+\t\tdo\n+\t\t\tgit verify-commit $commit &&\n+\t\t\tgit show --pretty=short --show-signature $commit >actual &&\n+\t\t\tgrep \"Good signature from\" actual &&\n+\t\t\t! grep \"BAD signature from\" actual &&\n+\t\t\techo $commit OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor commit in merge^2 fourth-unsigned sixth-unsigned \\\n+\t\t\tseventh-unsigned ninth-unsigned\n+\t\tdo\n+\t\t\ttest_must_fail git verify-commit $commit &&\n+\t\t\tgit show --pretty=short --show-signature $commit >actual &&\n+\t\t\t! grep \"Good signature from\" actual &&\n+\t\t\t! grep \"BAD signature from\" actual &&\n+\t\t\techo $commit OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor commit in eighth-signed-alt twelfth-signed-alt\n+\t\tdo\n+\t\t\tgit show --pretty=short --show-signature $commit >actual &&\n+\t\t\tgrep \"Good signature from\" actual &&\n+\t\t\t! grep \"BAD signature from\" actual &&\n+\t\t\tgrep \"not certified\" actual &&\n+\t\t\techo $commit OK || exit 1\n+\t\tdone\n+\t)\n+'\n+\n+test_expect_success GPG 'verify-commit exits success on untrusted signature' '\n+\tgit verify-commit eighth-signed-alt 2>actual &&\n+\tgrep \"Good signature from\" actual &&\n+\t! grep \"BAD signature from\" actual &&\n+\tgrep \"not certified\" actual\n+'\n+\n+test_expect_success GPG 'verify signatures with --raw' '\n+\t(\n+\t\tfor commit in initial second merge fourth-signed fifth-signed sixth-signed seventh-signed\n+\t\tdo\n+\t\t\tgit verify-commit --raw $commit 2>actual &&\n+\t\t\tgrep \"GOODSIG\" actual &&\n+\t\t\t! grep \"BADSIG\" actual &&\n+\t\t\techo $commit OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor commit in merge^2 fourth-unsigned sixth-unsigned seventh-unsigned\n+\t\tdo\n+\t\t\ttest_must_fail git verify-commit --raw $commit 2>actual &&\n+\t\t\t! grep \"GOODSIG\" actual &&\n+\t\t\t! grep \"BADSIG\" actual &&\n+\t\t\techo $commit OK || exit 1\n+\t\tdone\n+\t) &&\n+\t(\n+\t\tfor commit in eighth-signed-alt\n+\t\tdo\n+\t\t\tgit verify-commit --raw $commit 2>actual &&\n+\t\t\tgrep \"GOODSIG\" actual &&\n+\t\t\t! grep \"BADSIG\" actual &&\n+\t\t\tgrep \"TRUST_UNDEFINED\" actual &&\n+\t\t\techo $commit OK || exit 1\n+\t\tdone\n+\t)\n+'\n+\n+test_expect_success GPG 'show signed commit with signature' '\n+\tgit show -s initial >commit &&\n+\tgit show -s --show-signature initial >show &&\n+\tgit verify-commit -v initial >verify.1 2>verify.2 &&\n+\tgit cat-file commit initial >cat &&\n+\tgrep -v -e \"gpg: \" -e \"Warning: \" show >show.commit &&\n+\tgrep -e \"gpg: \" -e \"Warning: \" show >show.gpg &&\n+\tgrep -v \"^ \" cat | grep -v \"^gpgsig \" >cat.commit &&\n+\ttest_cmp show.commit commit &&\n+\ttest_cmp show.gpg verify.2 &&\n+\ttest_cmp cat.commit verify.1\n+'\n+\n+test_expect_success GPG 'detect fudged signature' '\n+\tgit cat-file commit seventh-signed >raw &&\n+\tsed -e \"s/^seventh/7th forged/\" raw >forged1 &&\n+\tgit hash-object -w -t commit forged1 >forged1.commit &&\n+\ttest_must_fail git verify-commit $(cat forged1.commit) &&\n+\tgit show --pretty=short --show-signature $(cat forged1.commit) >actual1 &&\n+\tgrep \"BAD signature from\" actual1 &&\n+\t! grep \"Good signature from\" actual1\n+'\n+\n+test_expect_success GPG 'detect fudged signature with NUL' '\n+\tgit cat-file commit seventh-signed >raw &&\n+\tcat raw >forged2 &&\n+\techo Qwik | tr \"Q\" \"\\000\" >>forged2 &&\n+\tgit hash-object -w -t commit forged2 >forged2.commit &&\n+\ttest_must_fail git verify-commit $(cat forged2.commit) &&\n+\tgit show --pretty=short --show-signature $(cat forged2.commit) >actual2 &&\n+\tgrep \"BAD signature from\" actual2 &&\n+\t! grep \"Good signature from\" actual2\n+'\n+\n+test_expect_success GPG 'amending already signed commit' '\n+\tgit checkout fourth-signed^0 &&\n+\tgit commit --amend -S --no-edit &&\n+\tgit verify-commit HEAD &&\n+\tgit show -s --show-signature HEAD >actual &&\n+\tgrep \"Good signature from\" actual &&\n+\t! grep \"BAD signature from\" actual\n+'\n+\n+test_expect_success GPG 'show good signature with custom format' '\n+\tcat >expect <<-\\EOF &&\n+\tG\n+\t13B6F51ECDDE430D\n+\tC O Mitter <committer@example.com>\n+\t73D758744BE721698EC54E8713B6F51ECDDE430D\n+\t73D758744BE721698EC54E8713B6F51ECDDE430D\n+\tEOF\n+\tgit log -1 --format=\"%G?%n%GK%n%GS%n%GF%n%GP\" sixth-signed >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'show bad signature with custom format' '\n+\tcat >expect <<-\\EOF &&\n+\tB\n+\t13B6F51ECDDE430D\n+\tC O Mitter <committer@example.com>\n+\n+\n+\tEOF\n+\tgit log -1 --format=\"%G?%n%GK%n%GS%n%GF%n%GP\" $(cat forged1.commit) >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'show untrusted signature with custom format' '\n+\tcat >expect <<-\\EOF &&\n+\tU\n+\t65A0EEA02E30CAD7\n+\tEris Discordia <discord@example.net>\n+\tF8364A59E07FFE9F4D63005A65A0EEA02E30CAD7\n+\tD4BE22311AD3131E5EDA29A461092E85B7227189\n+\tEOF\n+\tgit log -1 --format=\"%G?%n%GK%n%GS%n%GF%n%GP\" eighth-signed-alt >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'show unknown signature with custom format' '\n+\tcat >expect <<-\\EOF &&\n+\tE\n+\t65A0EEA02E30CAD7\n+\n+\n+\n+\tEOF\n+\tGNUPGHOME=\"$GNUPGHOME_NOT_USED\" git log -1 --format=\"%G?%n%GK%n%GS%n%GF%n%GP\" eighth-signed-alt >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'show lack of signature with custom format' '\n+\tcat >expect <<-\\EOF &&\n+\tN\n+\n+\n+\n+\n+\tEOF\n+\tgit log -1 --format=\"%G?%n%GK%n%GS%n%GF%n%GP\" seventh-unsigned >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_expect_success GPG 'log.showsignature behaves like --show-signature' '\n+\ttest_config log.showsignature true &&\n+\tgit show initial >actual &&\n+\tgrep \"gpg: Signature made\" actual &&\n+\tgrep \"gpg: Good signature\" actual\n+'\n+\n+test_expect_success GPG 'check config gpg.format values' '\n+\ttest_config gpg.format openpgp &&\n+\tgit commit -S --amend -m \"success\" &&\n+\ttest_config gpg.format OpEnPgP &&\n+\ttest_must_fail git commit -S --amend -m \"fail\"\n+'\n+\n+test_expect_success GPG 'detect fudged commit with double signature' '\n+\tsed -e \"/gpgsig/,/END PGP/d\" forged1 >double-base &&\n+\tsed -n -e \"/gpgsig/,/END PGP/p\" forged1 | \\\n+\t\tsed -e \"s/^gpgsig//;s/^ //\" | gpg --dearmor >double-sig1.sig &&\n+\tgpg -o double-sig2.sig -u 29472784 --detach-sign double-base &&\n+\tcat double-sig1.sig double-sig2.sig | gpg --enarmor >double-combined.asc &&\n+\tsed -e \"s/^\\(-.*\\)ARMORED FILE/\\1SIGNATURE/;1s/^/gpgsig /;2,\\$s/^/ /\" \\\n+\t\tdouble-combined.asc > double-gpgsig &&\n+\tsed -e \"/committer/r double-gpgsig\" double-base >double-commit &&\n+\tgit hash-object -w -t commit double-commit >double-commit.commit &&\n+\ttest_must_fail git verify-commit $(cat double-commit.commit) &&\n+\tgit show --pretty=short --show-signature $(cat double-commit.commit) >double-actual &&\n+\tgrep \"BAD signature from\" double-actual &&\n+\tgrep \"Good signature from\" double-actual\n+'\n+\n+test_expect_success GPG 'show double signature with custom format' '\n+\tcat >expect <<-\\EOF &&\n+\tE\n+\n+\n+\n+\n+\tEOF\n+\tgit log -1 --format=\"%G?%n%GK%n%GS%n%GF%n%GP\" $(cat double-commit.commit) >actual &&\n+\ttest_cmp expect actual\n+'\n+\n+test_done\n-- \n2.11.0\n\n\n"}]}