aboutsummaryrefslogtreecommitdiff
path: root/t
diff options
context:
space:
mode:
Diffstat (limited to 't')
-rw-r--r--t/README7
-rw-r--r--t/lib-rebase.sh2
-rwxr-xr-xt/t0003-attributes.sh10
-rwxr-xr-xt/t0080-vcs-svn.sh171
-rwxr-xr-xt/t1011-read-tree-sparse-checkout.sh123
-rwxr-xr-xt/t1501-worktree.sh483
-rwxr-xr-xt/t3030-merge-recursive.sh2
-rwxr-xr-xt/t3302-notes-index-expensive.sh2
-rwxr-xr-xt/t3400-rebase.sh3
-rwxr-xr-xt/t3404-rebase-interactive.sh68
-rwxr-xr-xt/t3407-rebase-abort.sh6
-rwxr-xr-xt/t3415-rebase-autosquash.sh40
-rwxr-xr-xt/t3507-cherry-pick-conflict.sh20
-rwxr-xr-xt/t3508-cherry-pick-many-commits.sh64
-rwxr-xr-xt/t3509-cherry-pick-merge-df.sh35
-rwxr-xr-xt/t4013-diff-various.sh5
-rw-r--r--t/t4013/diff.log_-S_F_master7
-rwxr-xr-xt/t4018-diff-funcname.sh2
-rwxr-xr-xt/t4111-apply-subdir.sh142
-rwxr-xr-xt/t4120-apply-popt.sh35
-rwxr-xr-xt/t4135-apply-weird-filenames.sh75
-rw-r--r--t/t4135/.gitignore3
-rw-r--r--t/t4135/add-plain.diff5
-rw-r--r--t/t4135/add-with backslash.diff5
-rw-r--r--t/t4135/add-with quote.diff5
-rw-r--r--t/t4135/add-with spaces.diff5
-rw-r--r--t/t4135/add-with tab.diff5
-rw-r--r--t/t4135/damaged.diff5
-rw-r--r--t/t4135/diff-plain.diff5
-rw-r--r--t/t4135/diff-with backslash.diff5
-rw-r--r--t/t4135/diff-with quote.diff5
-rw-r--r--t/t4135/diff-with spaces.diff5
-rw-r--r--t/t4135/diff-with tab.diff5
-rw-r--r--t/t4135/git-plain.diff7
-rw-r--r--t/t4135/git-with backslash.diff7
-rw-r--r--t/t4135/git-with quote.diff7
-rw-r--r--t/t4135/git-with spaces.diff7
-rw-r--r--t/t4135/git-with tab.diff7
-rwxr-xr-xt/t4135/make-patches45
-rwxr-xr-xt/t4200-rerere.sh400
-rwxr-xr-xt/t4202-log.sh19
-rwxr-xr-xt/t5520-pull.sh62
-rwxr-xr-xt/t5525-fetch-tagopt.sh41
-rwxr-xr-xt/t5601-clone.sh10
-rwxr-xr-xt/t6010-merge-base.sh340
-rwxr-xr-xt/t6018-rev-list-glob.sh6
-rwxr-xr-xt/t6020-merge-df.sh2
-rwxr-xr-xt/t6031-merge-recursive.sh31
-rwxr-xr-xt/t6035-merge-dir-to-symlink.sh64
-rwxr-xr-xt/t6038-merge-text-auto.sh189
-rwxr-xr-xt/t6200-fmt-merge-msg.sh310
-rwxr-xr-xt/t7006-pager.sh66
-rwxr-xr-xt/t7403-submodule-sync.sh7
-rwxr-xr-xt/t7405-submodule-merge.sh127
-rwxr-xr-xt/t7406-submodule-update.sh2
-rwxr-xr-xt/t7407-submodule-foreach.sh4
-rwxr-xr-xt/t7600-merge.sh391
-rwxr-xr-xt/t7606-merge-custom.sh96
-rwxr-xr-xt/t7609-merge-co-error-msgs.sh125
-rwxr-xr-xt/t7610-mergetool.sh49
-rwxr-xr-xt/t9010-svn-fe.sh32
-rwxr-xr-xt/t9350-fast-export.sh38
-rw-r--r--t/test-lib.sh32
63 files changed, 2911 insertions, 972 deletions
diff --git a/t/README b/t/README
index 0d1183c3e..410499a09 100644
--- a/t/README
+++ b/t/README
@@ -467,6 +467,13 @@ library for your script to use.
<expected> file. This behaves like "cmp" but produces more
helpful output when the test is run with "-v" option.
+ - test_path_is_file <file> [<diagnosis>]
+ test_path_is_dir <dir> [<diagnosis>]
+ test_path_is_missing <path> [<diagnosis>]
+
+ Check whether a file/directory exists or doesn't. <diagnosis> will
+ be displayed if the test fails.
+
- test_when_finished <script>
Prepend <script> to a list of commands to run to clean up
diff --git a/t/lib-rebase.sh b/t/lib-rebase.sh
index 6aefe2759..6ccf79709 100644
--- a/t/lib-rebase.sh
+++ b/t/lib-rebase.sh
@@ -47,6 +47,8 @@ for line in $FAKE_LINES; do
case $line in
squash|fixup|edit|reword)
action="$line";;
+ exec*)
+ echo "$line" | sed 's/_/ /g' >> "$1";;
"#")
echo '# comment' >> "$1";;
">")
diff --git a/t/t0003-attributes.sh b/t/t0003-attributes.sh
index 53bd7fcc4..de38c7f7a 100755
--- a/t/t0003-attributes.sh
+++ b/t/t0003-attributes.sh
@@ -48,11 +48,11 @@ test_expect_success 'attribute test' '
attr_check a/b/g a/b/g &&
attr_check b/g unspecified &&
attr_check a/b/h a/b/h &&
- attr_check a/b/d/g "a/b/d/*"
- attr_check onoff unset
- attr_check offon set
- attr_check no unspecified
- attr_check a/b/d/no "a/b/d/*"
+ attr_check a/b/d/g "a/b/d/*" &&
+ attr_check onoff unset &&
+ attr_check offon set &&
+ attr_check no unspecified &&
+ attr_check a/b/d/no "a/b/d/*" &&
attr_check a/b/d/yes unspecified
'
diff --git a/t/t0080-vcs-svn.sh b/t/t0080-vcs-svn.sh
new file mode 100755
index 000000000..d3225ada6
--- /dev/null
+++ b/t/t0080-vcs-svn.sh
@@ -0,0 +1,171 @@
+#!/bin/sh
+
+test_description='check infrastructure for svn importer'
+
+. ./test-lib.sh
+uint32_max=4294967295
+
+test_expect_success 'obj pool: store data' '
+ cat <<-\EOF >expected &&
+ 0
+ 1
+ EOF
+
+ test-obj-pool <<-\EOF >actual &&
+ alloc one 16
+ set one 13
+ test one 13
+ reset one
+ EOF
+ test_cmp expected actual
+'
+
+test_expect_success 'obj pool: NULL is offset ~0' '
+ echo "$uint32_max" >expected &&
+ echo null one | test-obj-pool >actual &&
+ test_cmp expected actual
+'
+
+test_expect_success 'obj pool: out-of-bounds access' '
+ cat <<-EOF >expected &&
+ 0
+ 0
+ $uint32_max
+ $uint32_max
+ 16
+ 20
+ $uint32_max
+ EOF
+
+ test-obj-pool <<-\EOF >actual &&
+ alloc one 16
+ alloc two 16
+ offset one 20
+ offset two 20
+ alloc one 5
+ offset one 20
+ free one 1
+ offset one 20
+ reset one
+ reset two
+ EOF
+ test_cmp expected actual
+'
+
+test_expect_success 'obj pool: high-water mark' '
+ cat <<-\EOF >expected &&
+ 0
+ 0
+ 10
+ 20
+ 20
+ 20
+ EOF
+
+ test-obj-pool <<-\EOF >actual &&
+ alloc one 10
+ committed one
+ alloc one 10
+ commit one
+ committed one
+ alloc one 10
+ free one 20
+ committed one
+ reset one
+ EOF
+ test_cmp expected actual
+'
+
+test_expect_success 'line buffer' '
+ echo HELLO >expected1 &&
+ printf "%s\n" "" HELLO >expected2 &&
+ echo >expected3 &&
+ printf "%s\n" "" Q | q_to_nul >expected4 &&
+ printf "%s\n" foo "" >expected5 &&
+ printf "%s\n" "" foo >expected6 &&
+
+ test-line-buffer <<-\EOF >actual1 &&
+ 5
+ HELLO
+ EOF
+
+ test-line-buffer <<-\EOF >actual2 &&
+ 0
+
+ 5
+ HELLO
+ EOF
+
+ q_to_nul <<-\EOF |
+ 1
+ Q
+ EOF
+ test-line-buffer >actual3 &&
+
+ q_to_nul <<-\EOF |
+ 0
+
+ 1
+ Q
+ EOF
+ test-line-buffer >actual4 &&
+
+ test-line-buffer <<-\EOF >actual5 &&
+ 5
+ foo
+ EOF
+
+ test-line-buffer <<-\EOF >actual6 &&
+ 0
+
+ 5
+ foo
+ EOF
+
+ test_cmp expected1 actual1 &&
+ test_cmp expected2 actual2 &&
+ test_cmp expected3 actual3 &&
+ test_cmp expected4 actual4 &&
+ test_cmp expected5 actual5 &&
+ test_cmp expected6 actual6
+'
+
+test_expect_success 'string pool' '
+ echo a does not equal b >expected.differ &&
+ echo a equals a >expected.match &&
+ echo equals equals equals >expected.matchmore &&
+
+ test-string-pool "a,--b" >actual.differ &&
+ test-string-pool "a,a" >actual.match &&
+ test-string-pool "equals-equals" >actual.matchmore &&
+ test_must_fail test-string-pool a,a,a &&
+ test_must_fail test-string-pool a &&
+
+ test_cmp expected.differ actual.differ &&
+ test_cmp expected.match actual.match &&
+ test_cmp expected.matchmore actual.matchmore
+'
+
+test_expect_success 'treap sort' '
+ cat <<-\EOF >unsorted &&
+ 68
+ 12
+ 13
+ 13
+ 68
+ 13
+ 13
+ 21
+ 10
+ 11
+ 12
+ 13
+ 13
+ EOF
+ sort unsorted >expected &&
+
+ test-treap <unsorted >actual &&
+ test_cmp expected actual
+'
+
+test_done
diff --git a/t/t1011-read-tree-sparse-checkout.sh b/t/t1011-read-tree-sparse-checkout.sh
index 62246dbf9..9a07de1a5 100755
--- a/t/t1011-read-tree-sparse-checkout.sh
+++ b/t/t1011-read-tree-sparse-checkout.sh
@@ -1,16 +1,30 @@
#!/bin/sh
-test_description='sparse checkout tests'
+test_description='sparse checkout tests
+
+* (tag: removed, master) removed
+| D sub/added
+* (HEAD, tag: top) modified and added
+| M init.t
+| A sub/added
+* (tag: init) init
+ A init.t
+'
. ./test-lib.sh
-cat >expected <<EOF
-100644 77f0ba1734ed79d12881f81b36ee134de6a3327b 0 init.t
-100644 e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 0 sub/added
-EOF
test_expect_success 'setup' '
+ cat >expected <<-\EOF &&
+ 100644 77f0ba1734ed79d12881f81b36ee134de6a3327b 0 init.t
+ 100644 e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 0 sub/added
+ EOF
+ cat >expected.swt <<-\EOF &&
+ H init.t
+ H sub/added
+ EOF
+
test_commit init &&
- echo modified >> init.t &&
+ echo modified >>init.t &&
mkdir sub &&
touch sub/added &&
git add init.t sub/added &&
@@ -20,26 +34,22 @@ test_expect_success 'setup' '
git commit -m removed &&
git tag removed &&
git checkout top &&
- git ls-files --stage > result &&
+ git ls-files --stage >result &&
test_cmp expected result
'
-cat >expected.swt <<EOF
-H init.t
-H sub/added
-EOF
test_expect_success 'read-tree without .git/info/sparse-checkout' '
git read-tree -m -u HEAD &&
- git ls-files --stage > result &&
+ git ls-files --stage >result &&
test_cmp expected result &&
- git ls-files -t > result &&
+ git ls-files -t >result &&
test_cmp expected.swt result
'
test_expect_success 'read-tree with .git/info/sparse-checkout but disabled' '
- echo > .git/info/sparse-checkout
+ echo >.git/info/sparse-checkout
git read-tree -m -u HEAD &&
- git ls-files -t > result &&
+ git ls-files -t >result &&
test_cmp expected.swt result &&
test -f init.t &&
test -f sub/added
@@ -47,9 +57,9 @@ test_expect_success 'read-tree with .git/info/sparse-checkout but disabled' '
test_expect_success 'read-tree --no-sparse-checkout with empty .git/info/sparse-checkout and enabled' '
git config core.sparsecheckout true &&
- echo > .git/info/sparse-checkout &&
+ echo >.git/info/sparse-checkout &&
git read-tree --no-sparse-checkout -m -u HEAD &&
- git ls-files -t > result &&
+ git ls-files -t >result &&
test_cmp expected.swt result &&
test -f init.t &&
test -f sub/added
@@ -57,94 +67,113 @@ test_expect_success 'read-tree --no-sparse-checkout with empty .git/info/sparse-
test_expect_success 'read-tree with empty .git/info/sparse-checkout' '
git config core.sparsecheckout true &&
- echo > .git/info/sparse-checkout &&
+ echo >.git/info/sparse-checkout &&
test_must_fail git read-tree -m -u HEAD &&
- git ls-files --stage > result &&
+ git ls-files --stage >result &&
test_cmp expected result &&
- git ls-files -t > result &&
+ git ls-files -t >result &&
test_cmp expected.swt result &&
test -f init.t &&
test -f sub/added
'
-cat >expected.swt <<EOF
-S init.t
-H sub/added
-EOF
test_expect_success 'match directories with trailing slash' '
+ cat >expected.swt-noinit <<-\EOF &&
+ S init.t
+ H sub/added
+ EOF
+
echo sub/ > .git/info/sparse-checkout &&
git read-tree -m -u HEAD &&
git ls-files -t > result &&
- test_cmp expected.swt result &&
+ test_cmp expected.swt-noinit result &&
test ! -f init.t &&
test -f sub/added
'
-cat >expected.swt <<EOF
-H init.t
-H sub/added
-EOF
test_expect_failure 'match directories without trailing slash' '
- echo init.t > .git/info/sparse-checkout &&
- echo sub >> .git/info/sparse-checkout &&
+ echo init.t >.git/info/sparse-checkout &&
+ echo sub >>.git/info/sparse-checkout &&
git read-tree -m -u HEAD &&
- git ls-files -t > result &&
+ git ls-files -t >result &&
test_cmp expected.swt result &&
test ! -f init.t &&
test -f sub/added
'
-cat >expected.swt <<EOF
-H init.t
-S sub/added
-EOF
test_expect_success 'checkout area changes' '
- echo init.t > .git/info/sparse-checkout &&
+ cat >expected.swt-nosub <<-\EOF &&
+ H init.t
+ S sub/added
+ EOF
+
+ echo init.t >.git/info/sparse-checkout &&
git read-tree -m -u HEAD &&
- git ls-files -t > result &&
- test_cmp expected.swt result &&
+ git ls-files -t >result &&
+ test_cmp expected.swt-nosub result &&
test -f init.t &&
test ! -f sub/added
'
test_expect_success 'read-tree updates worktree, absent case' '
- echo sub/added > .git/info/sparse-checkout &&
+ echo sub/added >.git/info/sparse-checkout &&
git checkout -f top &&
git read-tree -m -u HEAD^ &&
test ! -f init.t
'
test_expect_success 'read-tree updates worktree, dirty case' '
- echo sub/added > .git/info/sparse-checkout &&
+ echo sub/added >.git/info/sparse-checkout &&
git checkout -f top &&
- echo dirty > init.t &&
+ echo dirty >init.t &&
git read-tree -m -u HEAD^ &&
grep -q dirty init.t &&
rm init.t
'
test_expect_success 'read-tree removes worktree, dirty case' '
- echo init.t > .git/info/sparse-checkout &&
+ echo init.t >.git/info/sparse-checkout &&
git checkout -f top &&
- echo dirty > added &&
+ echo dirty >added &&
git read-tree -m -u HEAD^ &&
grep -q dirty added
'
test_expect_success 'read-tree adds to worktree, absent case' '
- echo init.t > .git/info/sparse-checkout &&
+ echo init.t >.git/info/sparse-checkout &&
git checkout -f removed &&
git read-tree -u -m HEAD^ &&
test ! -f sub/added
'
test_expect_success 'read-tree adds to worktree, dirty case' '
- echo init.t > .git/info/sparse-checkout &&
+ echo init.t >.git/info/sparse-checkout &&
git checkout -f removed &&
mkdir sub &&
- echo dirty > sub/added &&
+ echo dirty >sub/added &&
git read-tree -u -m HEAD^ &&
grep -q dirty sub/added
'
+test_expect_success 'index removal and worktree narrowing at the same time' '
+ >empty &&
+ echo init.t >.git/info/sparse-checkout &&
+ echo sub/added >>.git/info/sparse-checkout &&
+ git checkout -f top &&
+ echo init.t >.git/info/sparse-checkout &&
+ git checkout removed &&
+ git ls-files sub/added >result &&
+ test ! -f sub/added &&
+ test_cmp empty result
+'
+
+test_expect_success 'read-tree --reset removes outside worktree' '
+ >empty &&
+ echo init.t >.git/info/sparse-checkout &&
+ git checkout -f top &&
+ git reset --hard removed &&
+ git ls-files sub/added >result &&
+ test_cmp empty result
+'
+
test_done
diff --git a/t/t1501-worktree.sh b/t/t1501-worktree.sh
index bd8b60732..2c8f01f66 100755
--- a/t/t1501-worktree.sh
+++ b/t/t1501-worktree.sh
@@ -3,183 +3,320 @@
test_description='test separate work tree'
. ./test-lib.sh
-test_rev_parse() {
- name=$1
- shift
-
- test_expect_success "$name: is-bare-repository" \
- "test '$1' = \"\$(git rev-parse --is-bare-repository)\""
- shift
- [ $# -eq 0 ] && return
-
- test_expect_success "$name: is-inside-git-dir" \
- "test '$1' = \"\$(git rev-parse --is-inside-git-dir)\""
- shift
- [ $# -eq 0 ] && return
-
- test_expect_success "$name: is-inside-work-tree" \
- "test '$1' = \"\$(git rev-parse --is-inside-work-tree)\""
- shift
- [ $# -eq 0 ] && return
-
- test_expect_success "$name: prefix" \
- "test '$1' = \"\$(git rev-parse --show-prefix)\""
- shift
- [ $# -eq 0 ] && return
-}
-
-EMPTY_TREE=$(git write-tree)
-mkdir -p work/sub/dir || exit 1
-mkdir -p work2 || exit 1
-mv .git repo.git || exit 1
-
-say "core.worktree = relative path"
-GIT_DIR=repo.git
-GIT_CONFIG="$(pwd)"/$GIT_DIR/config
-export GIT_DIR GIT_CONFIG
-unset GIT_WORK_TREE
-git config core.worktree ../work
-test_rev_parse 'outside' false false false
-cd work || exit 1
-GIT_DIR=../repo.git
-GIT_CONFIG="$(pwd)"/$GIT_DIR/config
-test_rev_parse 'inside' false false true ''
-cd sub/dir || exit 1
-GIT_DIR=../../../repo.git
-GIT_CONFIG="$(pwd)"/$GIT_DIR/config
-test_rev_parse 'subdirectory' false false true sub/dir/
-cd ../../.. || exit 1
-
-say "core.worktree = absolute path"
-GIT_DIR=$(pwd)/repo.git
-GIT_CONFIG=$GIT_DIR/config
-git config core.worktree "$(pwd)/work"
-test_rev_parse 'outside' false false false
-cd work2
-test_rev_parse 'outside2' false false false
-cd ../work || exit 1
-test_rev_parse 'inside' false false true ''
-cd sub/dir || exit 1
-test_rev_parse 'subdirectory' false false true sub/dir/
-cd ../../.. || exit 1
-
-say "GIT_WORK_TREE=relative path (override core.worktree)"
-GIT_DIR=$(pwd)/repo.git
-GIT_CONFIG=$GIT_DIR/config
-git config core.worktree non-existent
-GIT_WORK_TREE=work
-export GIT_WORK_TREE
-test_rev_parse 'outside' false false false
-cd work2
-test_rev_parse 'outside' false false false
-cd ../work || exit 1
-GIT_WORK_TREE=.
-test_rev_parse 'inside' false false true ''
-cd sub/dir || exit 1
-GIT_WORK_TREE=../..
-test_rev_parse 'subdirectory' false false true sub/dir/
-cd ../../.. || exit 1
-
-mv work repo.git/work
-mv work2 repo.git/work2
-
-say "GIT_WORK_TREE=absolute path, work tree below git dir"
-GIT_DIR=$(pwd)/repo.git
-GIT_CONFIG=$GIT_DIR/config
-GIT_WORK_TREE=$(pwd)/repo.git/work
-test_rev_parse 'outside' false false false
-cd repo.git || exit 1
-test_rev_parse 'in repo.git' false true false
-cd objects || exit 1
-test_rev_parse 'in repo.git/objects' false true false
-cd ../work2 || exit 1
-test_rev_parse 'in repo.git/work2' false true false
-cd ../work || exit 1
-test_rev_parse 'in repo.git/work' false true true ''
-cd sub/dir || exit 1
-test_rev_parse 'in repo.git/sub/dir' false true true sub/dir/
-cd ../../../.. || exit 1
-
-test_expect_success 'repo finds its work tree' '
- (cd repo.git &&
- : > work/sub/dir/untracked &&
- test sub/dir/untracked = "$(git ls-files --others)")
-'
-
-test_expect_success 'repo finds its work tree from work tree, too' '
- (cd repo.git/work/sub/dir &&
- : > tracked &&
- git --git-dir=../../.. add tracked &&
- cd ../../.. &&
- test sub/dir/tracked = "$(git ls-files)")
+test_expect_success 'setup' '
+ EMPTY_TREE=$(git write-tree) &&
+ EMPTY_BLOB=$(git hash-object -t blob --stdin </dev/null) &&
+ CHANGED_BLOB=$(echo changed | git hash-object -t blob --stdin) &&
+ ZEROES=0000000000000000000000000000000000000000 &&
+ EMPTY_BLOB7=$(echo $EMPTY_BLOB | sed "s/\(.......\).*/\1/") &&
+ CHANGED_BLOB7=$(echo $CHANGED_BLOB | sed "s/\(.......\).*/\1/") &&
+
+ mkdir -p work/sub/dir &&
+ mkdir -p work2 &&
+ mv .git repo.git
+'
+
+test_expect_success 'setup: helper for testing rev-parse' '
+ test_rev_parse() {
+ echo $1 >expected.bare &&
+ echo $2 >expected.inside-git &&
+ echo $3 >expected.inside-worktree &&
+ if test $# -ge 4
+ then
+ echo $4 >expected.prefix
+ fi &&
+
+ git rev-parse --is-bare-repository >actual.bare &&
+ git rev-parse --is-inside-git-dir >actual.inside-git &&
+ git rev-parse --is-inside-work-tree >actual.inside-worktree &&
+ if test $# -ge 4
+ then
+ git rev-parse --show-prefix >actual.prefix
+ fi &&
+
+ test_cmp expected.bare actual.bare &&
+ test_cmp expected.inside-git actual.inside-git &&
+ test_cmp expected.inside-worktree actual.inside-worktree &&
+ if test $# -ge 4
+ then
+ # rev-parse --show-prefix should output
+ # a single newline when at the top of the work tree,
+ # but we test for that separately.
+ test -z "$4" && ! test -s actual.prefix ||
+ test_cmp expected.prefix actual.prefix
+ fi
+ }
+'
+
+test_expect_success 'setup: core.worktree = relative path' '
+ unset GIT_WORK_TREE;
+ GIT_DIR=repo.git &&
+ GIT_CONFIG="$(pwd)"/$GIT_DIR/config &&
+ export GIT_DIR GIT_CONFIG &&
+ git config core.worktree ../work
+'
+
+test_expect_success 'outside' '
+ test_rev_parse false false false
+'
+
+test_expect_success 'inside work tree' '
+ (
+ cd work &&
+ GIT_DIR=../repo.git &&
+ GIT_CONFIG="$(pwd)"/$GIT_DIR/config &&
+ test_rev_parse false false true ""
+ )
+'
+
+test_expect_failure 'empty prefix is actually written out' '
+ echo >expected &&
+ (
+ cd work &&
+ GIT_DIR=../repo.git &&
+ GIT_CONFIG="$(pwd)"/$GIT_DIR/config &&
+ git rev-parse --show-prefix >../actual
+ ) &&
+ test_cmp expected actual
+'
+
+test_expect_success 'subdir of work tree' '
+ (
+ cd work/sub/dir &&
+ GIT_DIR=../../../repo.git &&
+ GIT_CONFIG="$(pwd)"/$GIT_DIR/config &&
+ test_rev_parse false false true sub/dir/
+ )
+'
+
+test_expect_success 'setup: core.worktree = absolute path' '
+ unset GIT_WORK_TREE;
+ GIT_DIR=$(pwd)/repo.git &&
+ GIT_CONFIG=$GIT_DIR/config &&
+ export GIT_DIR GIT_CONFIG &&
+ git config core.worktree "$(pwd)/work"
+'
+
+test_expect_success 'outside' '
+ test_rev_parse false false false &&
+ (
+ cd work2 &&
+ test_rev_parse false false false
+ )
+'
+
+test_expect_success 'inside work tree' '
+ (
+ cd work &&
+ test_rev_parse false false true ""
+ )
+'
+
+test_expect_success 'subdir of work tree' '
+ (
+ cd work/sub/dir &&
+ test_rev_parse false false true sub/dir/
+ )
+'
+
+test_expect_success 'setup: GIT_WORK_TREE=relative (override core.worktree)' '
+ GIT_DIR=$(pwd)/repo.git &&
+ GIT_CONFIG=$GIT_DIR/config &&
+ git config core.worktree non-existent &&
+ GIT_WORK_TREE=work &&
+ export GIT_DIR GIT_CONFIG GIT_WORK_TREE
+'
+
+test_expect_success 'outside' '
+ test_rev_parse false false false &&
+ (
+ cd work2 &&
+ test_rev_parse false false false
+ )
+'
+
+test_expect_success 'inside work tree' '
+ (
+ cd work &&
+ GIT_WORK_TREE=. &&
+ test_rev_parse false false true ""
+ )
+'
+
+test_expect_success 'subdir of work tree' '
+ (
+ cd work/sub/dir &&
+ GIT_WORK_TREE=../.. &&
+ test_rev_parse false false true sub/dir/
+ )
+'
+
+test_expect_success 'setup: GIT_WORK_TREE=absolute, below git dir' '
+ mv work repo.git/work &&
+ mv work2 repo.git/work2 &&
+ GIT_DIR=$(pwd)/repo.git &&
+ GIT_CONFIG=$GIT_DIR/config &&
+ GIT_WORK_TREE=$(pwd)/repo.git/work &&
+ export GIT_DIR GIT_CONFIG GIT_WORK_TREE
+'
+
+test_expect_success 'outside' '
+ echo outside &&
+ test_rev_parse false false false
+'
+
+test_expect_success 'in repo.git' '
+ (
+ cd repo.git &&
+ test_rev_parse false true false
+ ) &&
+ (
+ cd repo.git/objects &&
+ test_rev_parse false true false
+ ) &&
+ (
+ cd repo.git/work2 &&
+ test_rev_parse false true false
+ )
+'
+
+test_expect_success 'inside work tree' '
+ (
+ cd repo.git/work &&
+ test_rev_parse false true true ""
+ )
+'
+
+test_expect_success 'subdir of work tree' '
+ (
+ cd repo.git/work/sub/dir &&
+ test_rev_parse false true true sub/dir/
+ )
+'
+
+test_expect_success 'find work tree from repo' '
+ echo sub/dir/untracked >expected &&
+ cat <<-\EOF >repo.git/work/.gitignore &&
+ expected.*
+ actual.*
+ .gitignore
+ EOF
+ >repo.git/work/sub/dir/untracked &&
+ (
+ cd repo.git &&
+ git ls-files --others --exclude-standard >../actual
+ ) &&
+ test_cmp expected actual
+'
+
+test_expect_success 'find work tree from work tree' '
+ echo sub/dir/tracked >expected &&
+ >repo.git/work/sub/dir/tracked &&
+ (
+ cd repo.git/work/sub/dir &&
+ git --git-dir=../../.. add tracked
+ ) &&
+ (
+ cd repo.git &&
+ git ls-files >../actual
+ ) &&
+ test_cmp expected actual
'
test_expect_success '_gently() groks relative GIT_DIR & GIT_WORK_TREE' '
- (cd repo.git/work/sub/dir &&
- GIT_DIR=../../.. GIT_WORK_TREE=../.. GIT_PAGER= \
+ (
+ cd repo.git/work/sub/dir &&
+ GIT_DIR=../../.. &&
+ GIT_WORK_TREE=../.. &&
+ GIT_PAGER= &&
+ export GIT_DIR GIT_WORK_TREE GIT_PAGER &&
+
git diff --exit-code tracked &&
- echo changed > tracked &&
- ! GIT_DIR=../../.. GIT_WORK_TREE=../.. GIT_PAGER= \
- git diff --exit-code tracked)
-'
-cat > diff-index-cached.expected <<\EOF
-:000000 100644 0000000000000000000000000000000000000000 e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 A sub/dir/tracked
-EOF
-cat > diff-index.expected <<\EOF
-:000000 100644 0000000000000000000000000000000000000000 0000000000000000000000000000000000000000 A sub/dir/tracked
-EOF
-
-
-test_expect_success 'git diff-index' '
- GIT_DIR=repo.git GIT_WORK_TREE=repo.git/work git diff-index $EMPTY_TREE > result &&
- test_cmp diff-index.expected result &&
- GIT_DIR=repo.git git diff-index --cached $EMPTY_TREE > result &&
- test_cmp diff-index-cached.expected result
-'
-cat >diff-files.expected <<\EOF
-:100644 100644 e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 0000000000000000000000000000000000000000 M sub/dir/tracked
-EOF
-
-test_expect_success 'git diff-files' '
- GIT_DIR=repo.git GIT_WORK_TREE=repo.git/work git diff-files > result &&
- test_cmp diff-files.expected result
-'
-
-cat >diff-TREE.expected <<\EOF
-diff --git a/sub/dir/tracked b/sub/dir/tracked
-new file mode 100644
-index 0000000..5ea2ed4
---- /dev/null
-+++ b/sub/dir/tracked
-@@ -0,0 +1 @@
-+changed
-EOF
-cat >diff-TREE-cached.expected <<\EOF
-diff --git a/sub/dir/tracked b/sub/dir/tracked
-new file mode 100644
-index 0000000..e69de29
-EOF
-cat >diff-FILES.expected <<\EOF
-diff --git a/sub/dir/tracked b/sub/dir/tracked
-index e69de29..5ea2ed4 100644
---- a/sub/dir/tracked
-+++ b/sub/dir/tracked
-@@ -0,0 +1 @@
-+changed
-EOF
-
-test_expect_success 'git diff' '
- GIT_DIR=repo.git GIT_WORK_TREE=repo.git/work git diff $EMPTY_TREE > result &&
- test_cmp diff-TREE.expected result &&
- GIT_DIR=repo.git git diff --cached $EMPTY_TREE > result &&
- test_cmp diff-TREE-cached.expected result &&
- GIT_DIR=repo.git GIT_WORK_TREE=repo.git/work git diff > result &&
- test_cmp diff-FILES.expected result
+ echo changed >tracked &&
+ test_must_fail git diff --exit-code tracked
+ )
+'
+
+test_expect_success 'diff-index respects work tree under .git dir' '
+ cat >diff-index-cached.expected <<-EOF &&
+ :000000 100644 $ZEROES $EMPTY_BLOB A sub/dir/tracked
+ EOF
+ cat >diff-index.expected <<-EOF &&
+ :000000 100644 $ZEROES $ZEROES A sub/dir/tracked
+ EOF
+
+ (
+ GIT_DIR=repo.git &&
+ GIT_WORK_TREE=repo.git/work &&
+ export GIT_DIR GIT_WORK_TREE &&
+ git diff-index $EMPTY_TREE >diff-index.actual &&
+ git diff-index --cached $EMPTY_TREE >diff-index-cached.actual
+ ) &&
+ test_cmp diff-index.expected diff-index.actual &&
+ test_cmp diff-index-cached.expected diff-index-cached.actual
+'
+
+test_expect_success 'diff-files respects work tree under .git dir' '
+ cat >diff-files.expected <<-EOF &&
+ :100644 100644 $EMPTY_BLOB $ZEROES M sub/dir/tracked
+ EOF
+
+ (
+ GIT_DIR=repo.git &&
+ GIT_WORK_TREE=repo.git/work &&
+ export GIT_DIR GIT_WORK_TREE &&
+ git diff-files >diff-files.actual
+ ) &&
+ test_cmp diff-files.expected diff-files.actual
+'
+
+test_expect_success 'git diff respects work tree under .git dir' '
+ cat >diff-TREE.expected <<-EOF &&
+ diff --git a/sub/dir/tracked b/sub/dir/tracked
+ new file mode 100644
+ index 0000000..$CHANGED_BLOB7
+ --- /dev/null
+ +++ b/sub/dir/tracked
+ @@ -0,0 +1 @@
+ +changed
+ EOF
+ cat >diff-TREE-cached.expected <<-EOF &&
+ diff --git a/sub/dir/tracked b/sub/dir/tracked
+ new file mode 100644
+ index 0000000..$EMPTY_BLOB7
+ EOF
+ cat >diff-FILES.expected <<-EOF &&
+ diff --git a/sub/dir/tracked b/sub/dir/tracked
+ index $EMPTY_BLOB7..$CHANGED_BLOB7 100644
+ --- a/sub/dir/tracked
+ +++ b/sub/dir/tracked
+ @@ -0,0 +1 @@
+ +changed
+ EOF
+
+ (
+ GIT_DIR=repo.git &&
+ GIT_WORK_TREE=repo.git/work &&
+ export GIT_DIR GIT_WORK_TREE &&
+ git diff $EMPTY_TREE >diff-TREE.actual &&
+ git diff --cached $EMPTY_TREE >diff-TREE-cached.actual &&
+ git diff >diff-FILES.actual
+ ) &&
+ test_cmp diff-TREE.expected diff-TREE.actual &&
+ test_cmp diff-TREE-cached.expected diff-TREE-cached.actual &&
+ test_cmp diff-FILES.expected diff-FILES.actual
'
test_expect_success 'git grep' '
- (cd repo.git/work/sub &&
- GIT_DIR=../.. GIT_WORK_TREE=.. git grep -l changed | grep dir/tracked)
+ echo dir/tracked >expected.grep &&
+ (
+ cd repo.git/work/sub &&
+ GIT_DIR=../.. &&
+ GIT_WORK_TREE=.. &&
+ export GIT_DIR GIT_WORK_TREE &&
+ git grep -l changed >../../../actual.grep
+ ) &&
+ test_cmp expected.grep actual.grep
'
test_expect_success 'git commit' '
@@ -191,14 +328,14 @@ test_expect_success 'git commit' '
test_expect_success 'absolute pathspec should fail gracefully' '
(
- cd repo.git || exit 1
- git config --unset core.worktree
+ cd repo.git &&
+ test_might_fail git config --unset core.worktree &&
test_must_fail git log HEAD -- /home
)
'
test_expect_success 'make_relative_path handles double slashes in GIT_DIR' '
- : > dummy_file
+ >dummy_file
echo git --git-dir="$(pwd)//repo.git" --work-tree="$(pwd)" add dummy_file &&
git --git-dir="$(pwd)//repo.git" --work-tree="$(pwd)" add dummy_file
'
diff --git a/t/t3030-merge-recursive.sh b/t/t3030-merge-recursive.sh
index d54154453..efe2900a3 100755
--- a/t/t3030-merge-recursive.sh
+++ b/t/t3030-merge-recursive.sh
@@ -294,7 +294,7 @@ test_expect_success 'fail if the index has unresolved entries' '
grep "You have not concluded your merge" out &&
rm -f .git/MERGE_HEAD &&
test_must_fail git merge "$c5" 2> out &&
- grep "Your local changes to .* would be overwritten by merge." out
+ grep "Your local changes to the following files would be overwritten by merge:" out
'
test_expect_success 'merge-recursive remove conflict' '
diff --git a/t/t3302-notes-index-expensive.sh b/t/t3302-notes-index-expensive.sh
index 361a10aeb..8ab333dbd 100755
--- a/t/t3302-notes-index-expensive.sh
+++ b/t/t3302-notes-index-expensive.sh
@@ -98,7 +98,7 @@ time_notes () {
for mode in no-notes notes
do
echo $mode
- /usr/bin/time sh ../time_notes $mode $1
+ /usr/bin/time "$SHELL_PATH" ../time_notes $mode $1
done
}
diff --git a/t/t3400-rebase.sh b/t/t3400-rebase.sh
index a19aeb644..349eebd54 100755
--- a/t/t3400-rebase.sh
+++ b/t/t3400-rebase.sh
@@ -153,7 +153,8 @@ test_expect_success 'setup: recover' '
test_expect_success 'Show verbose error when HEAD could not be detached' '
>B &&
test_must_fail git rebase topic 2>output.err >output.out &&
- grep "Untracked working tree file .B. would be overwritten" output.err
+ grep "The following untracked working tree files would be overwritten by checkout:" output.err &&
+ grep B output.err
'
rm -f B
diff --git a/t/t3404-rebase-interactive.sh b/t/t3404-rebase-interactive.sh
index 9f03ce699..af3b663ae 100755
--- a/t/t3404-rebase-interactive.sh
+++ b/t/t3404-rebase-interactive.sh
@@ -64,6 +64,67 @@ test_expect_success 'setup' '
done
'
+# "exec" commands are ran with the user shell by default, but this may
+# be non-POSIX. For example, if SHELL=zsh then ">file" doesn't work
+# to create a file. Unseting SHELL avoids such non-portable behavior
+# in tests.
+SHELL=
+
+test_expect_success 'rebase -i with the exec command' '
+ git checkout master &&
+ (
+ FAKE_LINES="1 exec_>touch-one
+ 2 exec_>touch-two exec_false exec_>touch-three
+ 3 4 exec_>\"touch-file__name_with_spaces\";_>touch-after-semicolon 5" &&
+ export FAKE_LINES &&
+ test_must_fail git rebase -i A
+ ) &&
+ test_path_is_file touch-one &&
+ test_path_is_file touch-two &&
+ test_path_is_missing touch-three " (should have stopped before)" &&
+ test $(git rev-parse C) = $(git rev-parse HEAD) || {
+ echo "Stopped at wrong revision:"
+ echo "($(git describe --tags HEAD) instead of C)"
+ false
+ } &&
+ git rebase --continue &&
+ test_path_is_file touch-three &&
+ test_path_is_file "touch-file name with spaces" &&
+ test_path_is_file touch-after-semicolon &&
+ test $(git rev-parse master) = $(git rev-parse HEAD) || {
+ echo "Stopped at wrong revision:"
+ echo "($(git describe --tags HEAD) instead of master)"
+ false
+ } &&
+ rm -f touch-*
+'
+
+test_expect_success 'rebase -i with the exec command runs from tree root' '
+ git checkout master &&
+ mkdir subdir && cd subdir &&
+ FAKE_LINES="1 exec_>touch-subdir" \
+ git rebase -i HEAD^ &&
+ cd .. &&
+ test_path_is_file touch-subdir &&
+ rm -fr subdir
+'
+
+test_expect_success 'rebase -i with the exec command checks tree cleanness' '
+ git checkout master &&
+ (
+ FAKE_LINES="exec_echo_foo_>file1 1" &&
+ export FAKE_LINES &&
+ test_must_fail git rebase -i HEAD^
+ ) &&
+ test $(git rev-parse master^) = $(git rev-parse HEAD) || {
+ echo "Stopped at wrong revision:"
+ echo "($(git describe --tags HEAD) instead of master^)"
+ false
+ } &&
+ git reset --hard &&
+ git rebase --continue
+'
+
test_expect_success 'no changes are a nop' '
git checkout branch2 &&
git rebase -i F &&
@@ -143,16 +204,17 @@ test_expect_success 'abort' '
git rebase --abort &&
test $(git rev-parse new-branch1) = $(git rev-parse HEAD) &&
test "$(git symbolic-ref -q HEAD)" = "refs/heads/branch1" &&
- ! test -d .git/rebase-merge
+ test_path_is_missing .git/rebase-merge
'
test_expect_success 'abort with error when new base cannot be checked out' '
git rm --cached file1 &&
git commit -m "remove file in base" &&
test_must_fail git rebase -i master > output 2>&1 &&
- grep "Untracked working tree file .file1. would be overwritten" \
+ grep "The following untracked working tree files would be overwritten by checkout:" \
output &&
- ! test -d .git/rebase-merge &&
+ grep "file1" output &&
+ test_path_is_missing .git/rebase-merge &&
git reset --hard HEAD^
'
diff --git a/t/t3407-rebase-abort.sh b/t/t3407-rebase-abort.sh
index 2999e7893..fbb3f2e0d 100755
--- a/t/t3407-rebase-abort.sh
+++ b/t/t3407-rebase-abort.sh
@@ -38,7 +38,7 @@ testrebase() {
# Clean up the state from the previous one
git reset --hard pre-rebase &&
test_must_fail git rebase$type master &&
- test -d "$dotest" &&
+ test_path_is_dir "$dotest" &&
git rebase --abort &&
test $(git rev-parse to-rebase) = $(git rev-parse pre-rebase) &&
test ! -d "$dotest"
@@ -49,7 +49,7 @@ testrebase() {
# Clean up the state from the previous one
git reset --hard pre-rebase &&
test_must_fail git rebase$type master &&
- test -d "$dotest" &&
+ test_path_is_dir "$dotest" &&
test_must_fail git rebase --skip &&
test $(git rev-parse HEAD) = $(git rev-parse master) &&
git rebase --abort &&
@@ -62,7 +62,7 @@ testrebase() {
# Clean up the state from the previous one
git reset --hard pre-rebase &&
test_must_fail git rebase$type master &&
- test -d "$dotest" &&
+ test_path_is_dir "$dotest" &&
echo c > a &&
echo d >> a &&
git add a &&
diff --git a/t/t3415-rebase-autosquash.sh b/t/t3415-rebase-autosquash.sh
index b63f4e2d6..37cb89ab5 100755
--- a/t/t3415-rebase-autosquash.sh
+++ b/t/t3415-rebase-autosquash.sh
@@ -21,38 +21,62 @@ test_expect_success setup '
git tag base
'
-test_expect_success 'auto fixup' '
+test_auto_fixup() {
git reset --hard base &&
echo 1 >file1 &&
git add -u &&
test_tick &&
git commit -m "fixup! first"
- git tag final-fixup &&
+ git tag $1 &&
test_tick &&
- git rebase --autosquash -i HEAD^^^ &&
+ git rebase $2 -i HEAD^^^ &&
git log --oneline >actual &&
test 3 = $(wc -l <actual) &&
- git diff --exit-code final-fixup &&
+ git diff --exit-code $1 &&
test 1 = "$(git cat-file blob HEAD^:file1)" &&
test 1 = $(git cat-file commit HEAD^ | grep first | wc -l)
+}
+
+test_expect_success 'auto fixup (option)' '
+ test_auto_fixup final-fixup-option --autosquash
+'
+
+test_expect_success 'auto fixup (config)' '
+ git config rebase.autosquash true &&
+ test_auto_fixup final-fixup-config-true &&
+ test_must_fail test_auto_fixup fixup-config-true-no --no-autosquash &&
+ git config rebase.autosquash false &&
+ test_must_fail test_auto_fixup final-fixup-config-false
'
-test_expect_success 'auto squash' '
+test_auto_squash() {
git reset --hard base &&
echo 1 >file1 &&
git add -u &&
test_tick &&
git commit -m "squash! first"
- git tag final-squash &&
+ git tag $1 &&
test_tick &&
- git rebase --autosquash -i HEAD^^^ &&
+ git rebase $2 -i HEAD^^^ &&
git log --oneline >actual &&
test 3 = $(wc -l <actual) &&
- git diff --exit-code final-squash &&
+ git diff --exit-code $1 &&
test 1 = "$(git cat-file blob HEAD^:file1)" &&
test 2 = $(git cat-file commit HEAD^ | grep first | wc -l)
+}
+
+test_expect_success 'auto squash (option)' '
+ test_auto_squash final-squash --autosquash
+'
+
+test_expect_success 'auto squash (config)' '
+ git config rebase.autosquash true &&
+ test_auto_squash final-squash-config-true &&
+ test_must_fail test_auto_squash squash-config-true-no --no-autosquash &&
+ git config rebase.autosquash false &&
+ test_must_fail test_auto_squash final-squash-config-false
'
test_expect_success 'misspelled auto squash' '
diff --git a/t/t3507-cherry-pick-conflict.sh b/t/t3507-cherry-pick-conflict.sh
index e25cf8039..607bf25d8 100755
--- a/t/t3507-cherry-pick-conflict.sh
+++ b/t/t3507-cherry-pick-conflict.sh
@@ -38,6 +38,26 @@ test_expect_success 'failed cherry-pick does not advance HEAD' '
test "$head" = "$newhead"
'
+test_expect_success 'advice from failed cherry-pick' "
+ git checkout -f initial^0 &&
+ git read-tree -u --reset HEAD &&
+ git clean -d -f -f -q -x &&
+
+ git update-index --refresh &&
+ git diff-index --exit-code HEAD &&
+
+ picked=\$(git rev-parse --short picked) &&
+ cat <<-EOF >expected &&
+ error: could not apply \$picked... picked
+ hint: after resolving the conflicts, mark the corrected paths
+ hint: with 'git add <paths>' or 'git rm <paths>'
+ hint: and commit the result with 'git commit -c \$picked'
+ EOF
+ test_must_fail git cherry-pick picked 2>actual &&
+
+ test_cmp expected actual
+"
+
test_expect_success 'failed cherry-pick produces dirty index' '
git checkout -f initial^0 &&
diff --git a/t/t3508-cherry-pick-many-commits.sh b/t/t3508-cherry-pick-many-commits.sh
index f90ed3da3..8e09fd031 100755
--- a/t/t3508-cherry-pick-many-commits.sh
+++ b/t/t3508-cherry-pick-many-commits.sh
@@ -4,6 +4,18 @@ test_description='test cherry-picking many commits'
. ./test-lib.sh
+check_head_differs_from() {
+ head=$(git rev-parse --verify HEAD) &&
+ arg=$(git rev-parse --verify "$1") &&
+ test "$head" != "$arg"
+}
+
+check_head_equals() {
+ head=$(git rev-parse --verify HEAD) &&
+ arg=$(git rev-parse --verify "$1") &&
+ test "$head" = "$arg"
+}
+
test_expect_success setup '
echo first > file1 &&
git add file1 &&
@@ -23,13 +35,55 @@ test_expect_success setup '
'
test_expect_success 'cherry-pick first..fourth works' '
+ cat <<-\EOF >expected &&
+ [master OBJID] second
+ Author: A U Thor <author@example.com>
+ 1 files changed, 1 insertions(+), 0 deletions(-)
+ [master OBJID] third
+ Author: A U Thor <author@example.com>
+ 1 files changed, 1 insertions(+), 0 deletions(-)
+ [master OBJID] fourth
+ Author: A U Thor <author@example.com>
+ 1 files changed, 1 insertions(+), 0 deletions(-)
+ EOF
+
+ git checkout -f master &&
+ git reset --hard first &&
+ test_tick &&
+ git cherry-pick first..fourth >actual &&
+ git diff --quiet other &&
+ git diff --quiet HEAD other &&
+
+ sed -e "s/$_x05[0-9a-f][0-9a-f]/OBJID/" <actual >actual.fuzzy &&
+ test_cmp expected actual.fuzzy &&
+ check_head_differs_from fourth
+'
+
+test_expect_success 'cherry-pick --strategy resolve first..fourth works' '
+ cat <<-\EOF >expected &&
+ Trying simple merge.
+ [master OBJID] second
+ Author: A U Thor <author@example.com>
+ 1 files changed, 1 insertions(+), 0 deletions(-)
+ Trying simple merge.
+ [master OBJID] third
+ Author: A U Thor <author@example.com>
+ 1 files changed, 1 insertions(+), 0 deletions(-)
+ Trying simple merge.
+ [master OBJID] fourth
+ Author: A U Thor <author@example.com>
+ 1 files changed, 1 insertions(+), 0 deletions(-)
+ EOF
+
git checkout -f master &&
git reset --hard first &&
test_tick &&
- git cherry-pick first..fourth &&
+ git cherry-pick --strategy resolve first..fourth >actual &&
git diff --quiet other &&
git diff --quiet HEAD other &&
- test "$(git rev-parse --verify HEAD)" != "$(git rev-parse --verify fourth)"
+ sed -e "s/$_x05[0-9a-f][0-9a-f]/OBJID/" <actual >actual.fuzzy &&
+ test_cmp expected actual.fuzzy &&
+ check_head_differs_from fourth
'
test_expect_success 'cherry-pick --ff first..fourth works' '
@@ -39,7 +93,7 @@ test_expect_success 'cherry-pick --ff first..fourth works' '
git cherry-pick --ff first..fourth &&
git diff --quiet other &&
git diff --quiet HEAD other &&
- test "$(git rev-parse --verify HEAD)" = "$(git rev-parse --verify fourth)"
+ check_head_equals fourth
'
test_expect_success 'cherry-pick -n first..fourth works' '
@@ -89,7 +143,7 @@ test_expect_success 'cherry-pick -3 fourth works' '
git cherry-pick -3 fourth &&
git diff --quiet other &&
git diff --quiet HEAD other &&
- test "$(git rev-parse --verify HEAD)" != "$(git rev-parse --verify fourth)"
+ check_head_differs_from fourth
'
test_expect_success 'cherry-pick --stdin works' '
@@ -99,7 +153,7 @@ test_expect_success 'cherry-pick --stdin works' '
git rev-list --reverse first..fourth | git cherry-pick --stdin &&
git diff --quiet other &&
git diff --quiet HEAD other &&
- test "$(git rev-parse --verify HEAD)" != "$(git rev-parse --verify fourth)"
+ check_head_differs_from fourth
'
test_done
diff --git a/t/t3509-cherry-pick-merge-df.sh b/t/t3509-cherry-pick-merge-df.sh
new file mode 100755
index 000000000..a5ccdbf8f
--- /dev/null
+++ b/t/t3509-cherry-pick-merge-df.sh
@@ -0,0 +1,35 @@
+#!/bin/sh
+
+test_description='Test cherry-pick with directory/file conflicts'
+. ./test-lib.sh
+
+test_expect_success SYMLINKS 'Setup rename across paths each below D/F conflicts' '
+ mkdir a &&
+ >a/f &&
+ git add a &&
+ git commit -m a &&
+
+ mkdir b &&
+ ln -s ../a b/a &&
+ git add b &&
+ git commit -m b &&
+
+ git checkout -b branch &&
+ rm b/a &&
+ mv a b/a &&
+ ln -s b/a a &&
+ git add . &&
+ git commit -m swap &&
+
+ >f1 &&
+ git add f1 &&
+ git commit -m f1
+'
+
+test_expect_success SYMLINKS 'Cherry-pick succeeds with rename across D/F conflicts' '
+ git reset --hard &&
+ git checkout master^0 &&
+ git cherry-pick branch
+'
+
+test_done
diff --git a/t/t4013-diff-various.sh b/t/t4013-diff-various.sh
index dae635851..19857f432 100755
--- a/t/t4013-diff-various.sh
+++ b/t/t4013-diff-various.sh
@@ -208,6 +208,7 @@ log -p --first-parent master
log -m -p --first-parent master
log -m -p master
log -SF master
+log -S F master
log -SF -p master
log --decorate --all
log --decorate=full --all
@@ -282,4 +283,8 @@ diff master master^ side
diff --dirstat master~1 master~2
EOF
+test_expect_success 'log -S requires an argument' '
+ test_must_fail git log -S
+'
+
test_done
diff --git a/t/t4013/diff.log_-S_F_master b/t/t4013/diff.log_-S_F_master
new file mode 100644
index 000000000..978d2b411
--- /dev/null
+++ b/t/t4013/diff.log_-S_F_master
@@ -0,0 +1,7 @@
+$ git log -S F master
+commit 9a6d4949b6b76956d9d5e26f2791ec2ceff5fdc0
+Author: A U Thor <author@example.com>
+Date: Mon Jun 26 00:02:00 2006 +0000
+
+ Third
+$
diff --git a/t/t4018-diff-funcname.sh b/t/t4018-diff-funcname.sh
index 5b10e976a..61de8a271 100755
--- a/t/t4018-diff-funcname.sh
+++ b/t/t4018-diff-funcname.sh
@@ -32,7 +32,7 @@ EOF
sed 's/beer\\/beer,\\/' < Beer.java > Beer-correct.java
-builtin_patterns="bibtex cpp html java objc pascal php python ruby tex"
+builtin_patterns="bibtex cpp csharp html java objc pascal php python ruby tex"
for p in $builtin_patterns
do
test_expect_success "builtin $p pattern compiles" '
diff --git a/t/t4111-apply-subdir.sh b/t/t4111-apply-subdir.sh
new file mode 100755
index 000000000..a52d94ae2
--- /dev/null
+++ b/t/t4111-apply-subdir.sh
@@ -0,0 +1,142 @@
+#!/bin/sh
+
+test_description='patching from inconvenient places'
+
+. ./test-lib.sh
+
+test_expect_success 'setup' '
+ cat >patch <<-\EOF &&
+ diff file.orig file
+ --- a/file.orig
+ +++ b/file
+ @@ -1 +1,2 @@
+ 1
+ +2
+ EOF
+ patch="$(pwd)/patch" &&
+
+ echo 1 >preimage &&
+ printf "%s\n" 1 2 >postimage &&
+ echo 3 >other &&
+
+ test_tick &&
+ git commit --allow-empty -m basis
+'
+
+test_expect_success 'setup: subdir' '
+ reset_subdir() {
+ git reset &&
+ mkdir -p sub/dir/b &&
+ mkdir -p objects &&
+ cp "$1" file &&
+ cp "$1" objects/file &&
+ cp "$1" sub/dir/file &&
+ cp "$1" sub/dir/b/file &&
+ git add file sub/dir/file sub/dir/b/file objects/file &&
+ cp "$2" file &&
+ cp "$2" sub/dir/file &&
+ cp "$2" sub/dir/b/file &&
+ cp "$2" objects/file &&
+ test_might_fail git update-index --refresh -q
+ }
+'
+
+test_expect_success 'apply from subdir of toplevel' '
+ cp postimage expected &&
+ reset_subdir other preimage &&
+ (
+ cd sub/dir &&
+ git apply "$patch"
+ ) &&
+ test_cmp expected sub/dir/file
+'
+
+test_expect_success 'apply --cached from subdir of toplevel' '
+ cp postimage expected &&
+ cp other expected.working &&
+ reset_subdir preimage other &&
+ (
+ cd sub/dir &&
+ git apply --cached "$patch"
+ ) &&
+ git show :sub/dir/file >actual &&
+ test_cmp expected actual &&
+ test_cmp expected.working sub/dir/file
+'
+
+test_expect_success 'apply --index from subdir of toplevel' '
+ cp postimage expected &&
+ reset_subdir preimage other &&
+ (
+ cd sub/dir &&
+ test_must_fail git apply --index "$patch"
+ ) &&
+ reset_subdir other preimage &&
+ (
+ cd sub/dir &&
+ test_must_fail git apply --index "$patch"
+ ) &&
+ reset_subdir preimage preimage &&
+ (
+ cd sub/dir &&
+ git apply --index "$patch"
+ ) &&
+ git show :sub/dir/file >actual &&
+ test_cmp expected actual &&
+ test_cmp expected sub/dir/file
+'
+
+test_expect_success 'apply from .git dir' '
+ cp postimage expected &&
+ cp preimage .git/file &&
+ cp preimage .git/objects/file
+ (
+ cd .git &&
+ git apply "$patch"
+ ) &&
+ test_cmp expected .git/file
+'
+
+test_expect_success 'apply from subdir of .git dir' '
+ cp postimage expected &&
+ cp preimage .git/file &&
+ cp preimage .git/objects/file
+ (
+ cd .git/objects &&
+ git apply "$patch"
+ ) &&
+ test_cmp expected .git/objects/file
+'
+
+test_expect_success 'apply --cached from .git dir' '
+ cp postimage expected &&
+ cp other expected.working &&
+ cp other .git/file &&
+ reset_subdir preimage other &&
+ (
+ cd .git &&
+ git apply --cached "$patch"
+ ) &&
+ git show :file >actual &&
+ test_cmp expected actual &&
+ test_cmp expected.working file &&
+ test_cmp expected.working .git/file
+'
+
+test_expect_success 'apply --cached from subdir of .git dir' '
+ cp postimage expected &&
+ cp preimage expected.subdir &&
+ cp other .git/file &&
+ cp other .git/objects/file &&
+ reset_subdir preimage other &&
+ (
+ cd .git/objects &&
+ git apply --cached "$patch"
+ ) &&
+ git show :file >actual &&
+ git show :objects/file >actual.subdir &&
+ test_cmp expected actual &&
+ test_cmp expected.subdir actual.subdir
+'
+
+test_done
diff --git a/t/t4120-apply-popt.sh b/t/t4120-apply-popt.sh
index b463b4f05..2b2d00b33 100755
--- a/t/t4120-apply-popt.sh
+++ b/t/t4120-apply-popt.sh
@@ -10,21 +10,50 @@ test_description='git apply -p handling.'
test_expect_success setup '
mkdir sub &&
echo A >sub/file1 &&
- cp sub/file1 file1 &&
+ cp sub/file1 file1.saved &&
git add sub/file1 &&
echo B >sub/file1 &&
git diff >patch.file &&
- rm sub/file1 &&
- rmdir sub
+ git checkout -- sub/file1 &&
+ git mv sub süb &&
+ echo B >süb/file1 &&
+ git diff >patch.escaped &&
+ grep "[\]" patch.escaped &&
+ rm süb/file1 &&
+ rmdir süb
'
test_expect_success 'apply git diff with -p2' '
+ cp file1.saved file1 &&
git apply -p2 patch.file
'
test_expect_success 'apply with too large -p' '
+ cp file1.saved file1 &&
test_must_fail git apply --stat -p3 patch.file 2>err &&
grep "removing 3 leading" err
'
+test_expect_success 'apply (-p2) traditional diff with funny filenames' '
+ cat >patch.quotes <<-\EOF &&
+ diff -u "a/"sub/file1 "b/"sub/file1
+ --- "a/"sub/file1
+ +++ "b/"sub/file1
+ @@ -1 +1 @@
+ -A
+ +B
+ EOF
+ echo B >expected &&
+
+ cp file1.saved file1 &&
+ git apply -p2 patch.quotes &&
+ test_cmp expected file1
+'
+
+test_expect_success 'apply with too large -p and fancy filename' '
+ cp file1.saved file1 &&
+ test_must_fail git apply --stat -p3 patch.escaped 2>err &&
+ grep "removing 3 leading" err
+'
+
test_done
diff --git a/t/t4135-apply-weird-filenames.sh b/t/t4135-apply-weird-filenames.sh
new file mode 100755
index 000000000..1e5aad57a
--- /dev/null
+++ b/t/t4135-apply-weird-filenames.sh
@@ -0,0 +1,75 @@
+#!/bin/sh
+
+test_description='git apply with weird postimage filenames'
+
+. ./test-lib.sh
+
+test_expect_success 'setup' '
+ vector=$TEST_DIRECTORY/t4135 &&
+
+ test_tick &&
+ git commit --allow-empty -m preimage &&
+ git tag preimage &&
+
+ reset_preimage() {
+ git checkout -f preimage^0 &&
+ git read-tree -u --reset HEAD &&
+ git update-index --refresh
+ } &&
+
+ test_when_finished "rm -f \"tab embedded.txt\"" &&
+ test_when_finished "rm -f '\''\"quoteembedded\".txt'\''" &&
+ if touch -- "tab embedded.txt" '\''"quoteembedded".txt'\''
+ then
+ test_set_prereq FUNNYNAMES
+ fi
+'
+
+try_filename() {
+ desc=$1
+ postimage=$2
+ prereq=${3:-}
+ exp1=${4:-success}
+ exp2=${5:-success}
+ exp3=${6:-success}
+
+ test_expect_$exp1 $prereq "$desc, git-style file creation patch" "
+ echo postimage >expected &&
+ reset_preimage &&
+ rm -f '$postimage' &&
+ git apply -v \"\$vector\"/'git-$desc.diff' &&
+ test_cmp expected '$postimage'
+ "
+
+ test_expect_$exp2 $prereq "$desc, traditional patch" "
+ echo postimage >expected &&
+ reset_preimage &&
+ echo preimage >'$postimage' &&
+ git apply -v \"\$vector\"/'diff-$desc.diff' &&
+ test_cmp expected '$postimage'
+ "
+
+ test_expect_$exp3 $prereq "$desc, traditional file creation patch" "
+ echo postimage >expected &&
+ reset_preimage &&
+ rm -f '$postimage' &&
+ git apply -v \"\$vector\"/'add-$desc.diff' &&
+ test_cmp expected '$postimage'
+ "
+}
+
+try_filename 'plain' 'postimage.txt'
+try_filename 'with spaces' 'post image.txt'
+try_filename 'with tab' 'post image.txt' FUNNYNAMES
+try_filename 'with backslash' 'post\image.txt' BSLASHPSPEC
+try_filename 'with quote' '"postimage".txt' FUNNYNAMES success failure success
+
+test_expect_success 'whitespace-damaged traditional patch' '
+ echo postimage >expected &&
+ reset_preimage &&
+ rm -f postimage.txt &&
+ git apply -v "$vector/damaged.diff" &&
+ test_cmp expected postimage.txt
+'
+
+test_done
diff --git a/t/t4135/.gitignore b/t/t4135/.gitignore
new file mode 100644
index 000000000..3e58e65f5
--- /dev/null
+++ b/t/t4135/.gitignore
@@ -0,0 +1,3 @@
+/file-creation/
+/trad-creation/
+/trad-modification/
diff --git a/t/t4135/add-plain.diff b/t/t4135/add-plain.diff
new file mode 100644
index 000000000..cf5970a08
--- /dev/null
+++ b/t/t4135/add-plain.diff
@@ -0,0 +1,5 @@
+diff -pruN a/postimage.txt b/postimage.txt
+--- a/postimage.txt 1969-12-31 18:00:00.000000000 -0600
++++ b/postimage.txt 2010-08-18 20:13:31.484002255 -0500
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/add-with backslash.diff b/t/t4135/add-with backslash.diff
new file mode 100644
index 000000000..c6861e196
--- /dev/null
+++ b/t/t4135/add-with backslash.diff
@@ -0,0 +1,5 @@
+diff -pruN a/post\image.txt b/post\image.txt
+--- a/post\image.txt 1969-12-31 18:00:00.000000000 -0600
++++ b/post\image.txt 2010-08-18 20:13:31.692002255 -0500
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/add-with quote.diff b/t/t4135/add-with quote.diff
new file mode 100644
index 000000000..866de78ca
--- /dev/null
+++ b/t/t4135/add-with quote.diff
@@ -0,0 +1,5 @@
+diff -pruN a/"postimage".txt b/"postimage".txt
+--- a/"postimage".txt 1969-12-31 18:00:00.000000000 -0600
++++ b/"postimage".txt 2010-08-18 20:13:31.756002255 -0500
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/add-with spaces.diff b/t/t4135/add-with spaces.diff
new file mode 100644
index 000000000..a9a1212a2
--- /dev/null
+++ b/t/t4135/add-with spaces.diff
@@ -0,0 +1,5 @@
+diff -pruN a/post image.txt b/post image.txt
+--- a/post image.txt 1969-12-31 18:00:00.000000000 -0600
++++ b/post image.txt 2010-08-18 20:13:31.556002255 -0500
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/add-with tab.diff b/t/t4135/add-with tab.diff
new file mode 100644
index 000000000..bb67cb793
--- /dev/null
+++ b/t/t4135/add-with tab.diff
@@ -0,0 +1,5 @@
+diff -pruN a/post image.txt b/post image.txt
+--- a/post image.txt 1969-12-31 18:00:00.000000000 -0600
++++ b/post image.txt 2010-08-18 20:13:31.628002255 -0500
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/damaged.diff b/t/t4135/damaged.diff
new file mode 100644
index 000000000..68f7ededf
--- /dev/null
+++ b/t/t4135/damaged.diff
@@ -0,0 +1,5 @@
+diff -pruN a/postimage.txt b/postimage.txt
+--- a/postimage.txt 1969-12-31 18:00:00.000000000 -0600
++++ b/postimage.txt 2010-08-18 20:13:31.484002255 -0500
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/diff-plain.diff b/t/t4135/diff-plain.diff
new file mode 100644
index 000000000..acedcfa61
--- /dev/null
+++ b/t/t4135/diff-plain.diff
@@ -0,0 +1,5 @@
+--- postimage.txt.orig 2010-08-18 20:13:31.432002255 -0500
++++ postimage.txt 2010-08-18 20:13:31.432002255 -0500
+@@ -1 +1 @@
+-preimage
++postimage
diff --git a/t/t4135/diff-with backslash.diff b/t/t4135/diff-with backslash.diff
new file mode 100644
index 000000000..9068a61bd
--- /dev/null
+++ b/t/t4135/diff-with backslash.diff
@@ -0,0 +1,5 @@
+--- post\image.txt.orig 2010-08-18 20:13:31.680002255 -0500
++++ post\image.txt 2010-08-18 20:13:31.680002255 -0500
+@@ -1 +1 @@
+-preimage
++postimage
diff --git a/t/t4135/diff-with quote.diff b/t/t4135/diff-with quote.diff
new file mode 100644
index 000000000..c8e8cc1a8
--- /dev/null
+++ b/t/t4135/diff-with quote.diff
@@ -0,0 +1,5 @@
+--- "postimage".txt.orig 2010-08-18 20:13:31.744002255 -0500
++++ "postimage".txt 2010-08-18 20:13:31.744002255 -0500
+@@ -1 +1 @@
+-preimage
++postimage
diff --git a/t/t4135/diff-with spaces.diff b/t/t4135/diff-with spaces.diff
new file mode 100644
index 000000000..3512056f2
--- /dev/null
+++ b/t/t4135/diff-with spaces.diff
@@ -0,0 +1,5 @@
+--- post image.txt.orig 2010-08-18 20:13:31.544002255 -0500
++++ post image.txt 2010-08-18 20:13:31.544002255 -0500
+@@ -1 +1 @@
+-preimage
++postimage
diff --git a/t/t4135/diff-with tab.diff b/t/t4135/diff-with tab.diff
new file mode 100644
index 000000000..4e6d9b294
--- /dev/null
+++ b/t/t4135/diff-with tab.diff
@@ -0,0 +1,5 @@
+--- post image.txt.orig 2010-08-18 20:13:31.616002255 -0500
++++ post image.txt 2010-08-18 20:13:31.616002255 -0500
+@@ -1 +1 @@
+-preimage
++postimage
diff --git a/t/t4135/git-plain.diff b/t/t4135/git-plain.diff
new file mode 100644
index 000000000..db47d1a69
--- /dev/null
+++ b/t/t4135/git-plain.diff
@@ -0,0 +1,7 @@
+diff --git a/postimage.txt b/postimage.txt
+new file mode 100644
+index 0000000..eff0c54
+--- /dev/null
++++ b/postimage.txt
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/git-with backslash.diff b/t/t4135/git-with backslash.diff
new file mode 100644
index 000000000..0e84a10e9
--- /dev/null
+++ b/t/t4135/git-with backslash.diff
@@ -0,0 +1,7 @@
+diff --git "a/post\\image.txt" "b/post\\image.txt"
+new file mode 100644
+index 0000000..eff0c54
+--- /dev/null
++++ "b/post\\image.txt"
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/git-with quote.diff b/t/t4135/git-with quote.diff
new file mode 100644
index 000000000..bdbea8af3
--- /dev/null
+++ b/t/t4135/git-with quote.diff
@@ -0,0 +1,7 @@
+diff --git "a/\"postimage\".txt" "b/\"postimage\".txt"
+new file mode 100644
+index 0000000..eff0c54
+--- /dev/null
++++ "b/\"postimage\".txt"
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/git-with spaces.diff b/t/t4135/git-with spaces.diff
new file mode 100644
index 000000000..baaa810de
--- /dev/null
+++ b/t/t4135/git-with spaces.diff
@@ -0,0 +1,7 @@
+diff --git a/post image.txt b/post image.txt
+new file mode 100644
+index 0000000..eff0c54
+--- /dev/null
++++ b/post image.txt
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/git-with tab.diff b/t/t4135/git-with tab.diff
new file mode 100644
index 000000000..cca3c9287
--- /dev/null
+++ b/t/t4135/git-with tab.diff
@@ -0,0 +1,7 @@
+diff --git "a/post\timage.txt" "b/post\timage.txt"
+new file mode 100644
+index 0000000..eff0c54
+--- /dev/null
++++ "b/post\timage.txt"
+@@ -0,0 +1 @@
++postimage
diff --git a/t/t4135/make-patches b/t/t4135/make-patches
new file mode 100755
index 000000000..f5f45ddd0
--- /dev/null
+++ b/t/t4135/make-patches
@@ -0,0 +1,45 @@
+#!/bin/sh
+
+do_filename() {
+ desc=$1
+ postimage=$2
+
+ rm -fr file-creation &&
+ git init file-creation &&
+ (
+ cd file-creation &&
+ git commit --allow-empty -m init &&
+ echo postimage >"$postimage" &&
+ git add -N "$postimage" &&
+ git diff HEAD >"../git-$desc.diff"
+ ) &&
+
+ rm -fr trad-modification &&
+ mkdir trad-modification &&
+ (
+ cd trad-modification &&
+ echo preimage >"$postimage.orig" &&
+ echo postimage >"$postimage" &&
+ ! diff -u "$postimage.orig" "$postimage" >"../diff-$desc.diff"
+ ) &&
+
+ rm -fr trad-creation &&
+ mkdir trad-creation &&
+ (
+ cd trad-creation &&
+ mkdir a b &&
+ echo postimage >"b/$postimage" &&
+ ! diff -pruN a b >"../add-$desc.diff"
+ )
+}
+
+do_filename plain postimage.txt &&
+do_filename 'with spaces' 'post image.txt' &&
+do_filename 'with tab' 'post image.txt' &&
+do_filename 'with backslash' 'post\image.txt' &&
+do_filename 'with quote' '"postimage".txt' &&
+expand add-plain.diff >damaged.diff ||
+{
+ echo >&2 Failed. &&
+ exit 1
+}
diff --git a/t/t4200-rerere.sh b/t/t4200-rerere.sh
index 70856d07e..36255d608 100755
--- a/t/t4200-rerere.sh
+++ b/t/t4200-rerere.sh
@@ -4,237 +4,391 @@
#
test_description='git rerere
+
+! [fifth] version1
+ ! [first] first
+ ! [fourth] version1
+ ! [master] initial
+ ! [second] prefer first over second
+ ! [third] version2
+------
+ + [third] version2
++ [fifth] version1
+ + [fourth] version1
++ + + [third^] third
+ - [second] prefer first over second
+ + + [first] first
+ + [second^] second
+++++++ [master] initial
'
. ./test-lib.sh
-test_expect_success 'setup' "
- cat > a1 <<- EOF &&
+test_expect_success 'setup' '
+ cat >a1 <<-\EOF &&
Some title
==========
- Whether 'tis nobler in the mind to suffer
+ Whether '\''tis nobler in the mind to suffer
The slings and arrows of outrageous fortune,
Or to take arms against a sea of troubles,
And by opposing end them? To die: to sleep;
No more; and by a sleep to say we end
The heart-ache and the thousand natural shocks
- That flesh is heir to, 'tis a consummation
- Devoutly to be wish'd.
+ That flesh is heir to, '\''tis a consummation
+ Devoutly to be wish'\''d.
EOF
git add a1 &&
+ test_tick &&
git commit -q -a -m initial &&
- git checkout -b first &&
- cat >> a1 <<- EOF &&
+ cat >>a1 <<-\EOF &&
Some title
==========
To die, to sleep;
- To sleep: perchance to dream: ay, there's the rub;
+ To sleep: perchance to dream: ay, there'\''s the rub;
For in that sleep of death what dreams may come
When we have shuffled off this mortal coil,
- Must give us pause: there's the respect
+ Must give us pause: there'\''s the respect
That makes calamity of so long life;
EOF
+
+ git checkout -b first &&
+ test_tick &&
git commit -q -a -m first &&
git checkout -b second master &&
git show first:a1 |
- sed -e 's/To die, t/To die! T/' -e 's/Some title/Some Title/' > a1 &&
- echo '* END *' >>a1 &&
+ sed -e "s/To die, t/To die! T/" -e "s/Some title/Some Title/" >a1 &&
+ echo "* END *" >>a1 &&
+ test_tick &&
git commit -q -a -m second
-"
+'
test_expect_success 'nothing recorded without rerere' '
- (rm -rf .git/rr-cache; git config rerere.enabled false) &&
+ rm -rf .git/rr-cache &&
+ git config rerere.enabled false &&
test_must_fail git merge first &&
! test -d .git/rr-cache
'
-# activate rerere, old style
-test_expect_success 'conflicting merge' '
+test_expect_success 'activate rerere, old style (conflicting merge)' '
git reset --hard &&
mkdir .git/rr-cache &&
- git config --unset rerere.enabled &&
- test_must_fail git merge first
-'
+ test_might_fail git config --unset rerere.enabled &&
+ test_must_fail git merge first &&
-sha1=$(perl -pe 's/ .*//' .git/MERGE_RR)
-rr=.git/rr-cache/$sha1
-test_expect_success 'recorded preimage' "grep ^=======$ $rr/preimage"
+ sha1=$(perl -pe "s/ .*//" .git/MERGE_RR) &&
+ rr=.git/rr-cache/$sha1 &&
+ grep "^=======\$" $rr/preimage &&
+ ! test -f $rr/postimage &&
+ ! test -f $rr/thisimage
+'
test_expect_success 'rerere.enabled works, too' '
rm -rf .git/rr-cache &&
git config rerere.enabled true &&
git reset --hard &&
test_must_fail git merge first &&
+
+ sha1=$(perl -pe "s/ .*//" .git/MERGE_RR) &&
+ rr=.git/rr-cache/$sha1 &&
grep ^=======$ $rr/preimage
'
-test_expect_success 'no postimage or thisimage yet' \
- "test ! -f $rr/postimage -a ! -f $rr/thisimage"
+test_expect_success 'set up rr-cache' '
+ rm -rf .git/rr-cache &&
+ git config rerere.enabled true &&
+ git reset --hard &&
+ test_must_fail git merge first &&
+ sha1=$(perl -pe "s/ .*//" .git/MERGE_RR) &&
+ rr=.git/rr-cache/$sha1
+'
-test_expect_success 'preimage has right number of lines' '
+test_expect_success 'rr-cache looks sane' '
+ # no postimage or thisimage yet
+ ! test -f $rr/postimage &&
+ ! test -f $rr/thisimage &&
+ # preimage has right number of lines
cnt=$(sed -ne "/^<<<<<<</,/^>>>>>>>/p" $rr/preimage | wc -l) &&
+ echo $cnt &&
test $cnt = 13
-
'
-git show first:a1 > a1
-
-cat > expect << EOF
---- a/a1
-+++ b/a1
-@@ -1,4 +1,4 @@
--Some Title
-+Some title
- ==========
- Whether 'tis nobler in the mind to suffer
- The slings and arrows of outrageous fortune,
-@@ -8,21 +8,11 @@
- The heart-ache and the thousand natural shocks
- That flesh is heir to, 'tis a consummation
- Devoutly to be wish'd.
--<<<<<<<
--Some Title
--==========
--To die! To sleep;
--=======
- Some title
- ==========
- To die, to sleep;
-->>>>>>>
- To sleep: perchance to dream: ay, there's the rub;
- For in that sleep of death what dreams may come
- When we have shuffled off this mortal coil,
- Must give us pause: there's the respect
- That makes calamity of so long life;
--<<<<<<<
--=======
--* END *
-->>>>>>>
-EOF
-git rerere diff > out
-
-test_expect_success 'rerere diff' 'test_cmp expect out'
-
-cat > expect << EOF
-a1
-EOF
-
-git rerere status > out
-
-test_expect_success 'rerere status' 'test_cmp expect out'
-
-test_expect_success 'commit succeeds' \
- "git commit -q -a -m 'prefer first over second'"
-
-test_expect_success 'recorded postimage' "test -f $rr/postimage"
-
-test_expect_success 'another conflicting merge' '
- git checkout -b third master &&
- git show second^:a1 | sed "s/To die: t/To die! T/" > a1 &&
- git commit -q -a -m third &&
- test_must_fail git pull . first
+test_expect_success 'rerere diff' '
+ git show first:a1 >a1 &&
+ cat >expect <<-\EOF &&
+ --- a/a1
+ +++ b/a1
+ @@ -1,4 +1,4 @@
+ -Some Title
+ +Some title
+ ==========
+ Whether '\''tis nobler in the mind to suffer
+ The slings and arrows of outrageous fortune,
+ @@ -8,21 +8,11 @@
+ The heart-ache and the thousand natural shocks
+ That flesh is heir to, '\''tis a consummation
+ Devoutly to be wish'\''d.
+ -<<<<<<<
+ -Some Title
+ -==========
+ -To die! To sleep;
+ -=======
+ Some title
+ ==========
+ To die, to sleep;
+ ->>>>>>>
+ To sleep: perchance to dream: ay, there'\''s the rub;
+ For in that sleep of death what dreams may come
+ When we have shuffled off this mortal coil,
+ Must give us pause: there'\''s the respect
+ That makes calamity of so long life;
+ -<<<<<<<
+ -=======
+ -* END *
+ ->>>>>>>
+ EOF
+ git rerere diff >out &&
+ test_cmp expect out
'
-git show first:a1 | sed 's/To die: t/To die! T/' > expect
-test_expect_success 'rerere kicked in' "! grep ^=======$ a1"
+test_expect_success 'rerere status' '
+ echo a1 >expect &&
+ git rerere status >out &&
+ test_cmp expect out
+'
-test_expect_success 'rerere prefers first change' 'test_cmp a1 expect'
+test_expect_success 'first postimage wins' '
+ git show first:a1 | sed "s/To die: t/To die! T/" >expect &&
-rm $rr/postimage
-echo "$sha1 a1" | perl -pe 'y/\012/\000/' > .git/MERGE_RR
+ git commit -q -a -m "prefer first over second" &&
+ test -f $rr/postimage &&
-test_expect_success 'rerere clear' 'git rerere clear'
+ oldmtimepost=$(test-chmtime -v -60 $rr/postimage | cut -f 1) &&
-test_expect_success 'clear removed the directory' "test ! -d $rr"
+ git checkout -b third master &&
+ git show second^:a1 | sed "s/To die: t/To die! T/" >a1 &&
+ git commit -q -a -m third &&
-mkdir $rr
-echo Hello > $rr/preimage
-echo World > $rr/postimage
+ test_must_fail git pull . first &&
+ # rerere kicked in
+ ! grep "^=======\$" a1 &&
+ test_cmp expect a1
+'
-sha2=4000000000000000000000000000000000000000
-rr2=.git/rr-cache/$sha2
-mkdir $rr2
-echo Hello > $rr2/preimage
+test_expect_success 'rerere updates postimage timestamp' '
+ newmtimepost=$(test-chmtime -v +0 $rr/postimage | cut -f 1) &&
+ test $oldmtimepost -lt $newmtimepost
+'
-almost_15_days_ago=$((60-15*86400))
-just_over_15_days_ago=$((-1-15*86400))
-almost_60_days_ago=$((60-60*86400))
-just_over_60_days_ago=$((-1-60*86400))
+test_expect_success 'rerere clear' '
+ rm $rr/postimage &&
+ echo "$sha1 a1" | perl -pe "y/\012/\000/" >.git/MERGE_RR &&
+ git rerere clear &&
+ ! test -d $rr
+'
-test-chmtime =$almost_60_days_ago $rr/preimage
-test-chmtime =$almost_15_days_ago $rr2/preimage
+test_expect_success 'set up for garbage collection tests' '
+ mkdir -p $rr &&
+ echo Hello >$rr/preimage &&
+ echo World >$rr/postimage &&
-test_expect_success 'garbage collection (part1)' 'git rerere gc'
+ sha2=4000000000000000000000000000000000000000 &&
+ rr2=.git/rr-cache/$sha2 &&
+ mkdir $rr2 &&
+ echo Hello >$rr2/preimage &&
-test_expect_success 'young records still live' \
- "test -f $rr/preimage && test -f $rr2/preimage"
+ almost_15_days_ago=$((60-15*86400)) &&
+ just_over_15_days_ago=$((-1-15*86400)) &&
+ almost_60_days_ago=$((60-60*86400)) &&
+ just_over_60_days_ago=$((-1-60*86400)) &&
-test-chmtime =$just_over_60_days_ago $rr/preimage
-test-chmtime =$just_over_15_days_ago $rr2/preimage
+ test-chmtime =$just_over_60_days_ago $rr/preimage &&
+ test-chmtime =$almost_60_days_ago $rr/postimage &&
+ test-chmtime =$almost_15_days_ago $rr2/preimage
+'
-test_expect_success 'garbage collection (part2)' 'git rerere gc'
+test_expect_success 'gc preserves young or recently used records' '
+ git rerere gc &&
+ test -f $rr/preimage &&
+ test -f $rr2/preimage
+'
-test_expect_success 'old records rest in peace' \
- "test ! -f $rr/preimage && test ! -f $rr2/preimage"
+test_expect_success 'old records rest in peace' '
+ test-chmtime =$just_over_60_days_ago $rr/postimage &&
+ test-chmtime =$just_over_15_days_ago $rr2/preimage &&
+ git rerere gc &&
+ ! test -f $rr/preimage &&
+ ! test -f $rr2/preimage
+'
-test_expect_success 'file2 added differently in two branches' '
+test_expect_success 'setup: file2 added differently in two branches' '
git reset --hard &&
+
git checkout -b fourth &&
- echo Hallo > file2 &&
+ echo Hallo >file2 &&
git add file2 &&
+ test_tick &&
git commit -m version1 &&
+
git checkout third &&
- echo Bello > file2 &&
+ echo Bello >file2 &&
git add file2 &&
+ test_tick &&
git commit -m version2 &&
+
test_must_fail git merge fourth &&
- echo Cello > file2 &&
+ echo Cello >file2 &&
git add file2 &&
git commit -m resolution
'
test_expect_success 'resolution was recorded properly' '
+ echo Cello >expected &&
+
git reset --hard HEAD~2 &&
git checkout -b fifth &&
- echo Hallo > file3 &&
+
+ echo Hallo >file3 &&
git add file3 &&
+ test_tick &&
git commit -m version1 &&
+
git checkout third &&
- echo Bello > file3 &&
+ echo Bello >file3 &&
git add file3 &&
+ test_tick &&
git commit -m version2 &&
git tag version2 &&
+
test_must_fail git merge fifth &&
- test Cello = "$(cat file3)" &&
- test 0 != $(git ls-files -u | wc -l)
+ test_cmp expected file3 &&
+ test_must_fail git update-index --refresh
'
test_expect_success 'rerere.autoupdate' '
- git config rerere.autoupdate true
+ git config rerere.autoupdate true &&
git reset --hard &&
git checkout version2 &&
test_must_fail git merge fifth &&
- test 0 = $(git ls-files -u | wc -l)
+ git update-index --refresh
'
test_expect_success 'merge --rerere-autoupdate' '
- git config --unset rerere.autoupdate
+ test_might_fail git config --unset rerere.autoupdate &&
git reset --hard &&
git checkout version2 &&
test_must_fail git merge --rerere-autoupdate fifth &&
- test 0 = $(git ls-files -u | wc -l)
+ git update-index --refresh
'
test_expect_success 'merge --no-rerere-autoupdate' '
- git config rerere.autoupdate true
+ headblob=$(git rev-parse version2:file3) &&
+ mergeblob=$(git rev-parse fifth:file3) &&
+ cat >expected <<-EOF &&
+ 100644 $headblob 2 file3
+ 100644 $mergeblob 3 file3
+ EOF
+
+ git config rerere.autoupdate true &&
git reset --hard &&
git checkout version2 &&
test_must_fail git merge --no-rerere-autoupdate fifth &&
- test 2 = $(git ls-files -u | wc -l)
+ git ls-files -u >actual &&
+ test_cmp expected actual
+'
+
+test_expect_success 'set up an unresolved merge' '
+ headblob=$(git rev-parse version2:file3) &&
+ mergeblob=$(git rev-parse fifth:file3) &&
+ cat >expected.unresolved <<-EOF &&
+ 100644 $headblob 2 file3
+ 100644 $mergeblob 3 file3
+ EOF
+
+ test_might_fail git config --unset rerere.autoupdate &&
+ git reset --hard &&
+ git checkout version2 &&
+ fifth=$(git rev-parse fifth) &&
+ echo "$fifth branch 'fifth' of ." |
+ git fmt-merge-msg >msg &&
+ ancestor=$(git merge-base version2 fifth) &&
+ test_must_fail git merge-recursive "$ancestor" -- HEAD fifth &&
+
+ git ls-files --stage >failedmerge &&
+ cp file3 file3.conflict &&
+
+ git ls-files -u >actual &&
+ test_cmp expected.unresolved actual
+'
+
+test_expect_success 'explicit rerere' '
+ test_might_fail git config --unset rerere.autoupdate &&
+ git rm -fr --cached . &&
+ git update-index --index-info <failedmerge &&
+ cp file3.conflict file3 &&
+ test_must_fail git update-index --refresh -q &&
+
+ git rerere &&
+ git ls-files -u >actual &&
+ test_cmp expected.unresolved actual
+'
+
+test_expect_success 'explicit rerere with autoupdate' '
+ git config rerere.autoupdate true &&
+ git rm -fr --cached . &&
+ git update-index --index-info <failedmerge &&
+ cp file3.conflict file3 &&
+ test_must_fail git update-index --refresh -q &&
+
+ git rerere &&
+ git update-index --refresh
+'
+
+test_expect_success 'explicit rerere --rerere-autoupdate overrides' '
+ git config rerere.autoupdate false &&
+ git rm -fr --cached . &&
+ git update-index --index-info <failedmerge &&
+ cp file3.conflict file3 &&
+ git rerere &&
+ git ls-files -u >actual1 &&
+
+ git rm -fr --cached . &&
+ git update-index --index-info <failedmerge &&
+ cp file3.conflict file3 &&
+ git rerere --rerere-autoupdate &&
+ git update-index --refresh &&
+
+ git rm -fr --cached . &&
+ git update-index --index-info <failedmerge &&
+ cp file3.conflict file3 &&
+ git rerere --rerere-autoupdate --no-rerere-autoupdate &&
+ git ls-files -u >actual2 &&
+
+ git rm -fr --cached . &&
+ git update-index --index-info <failedmerge &&
+ cp file3.conflict file3 &&
+ git rerere --rerere-autoupdate --no-rerere-autoupdate --rerere-autoupdate &&
+ git update-index --refresh &&
+
+ test_cmp expected.unresolved actual1 &&
+ test_cmp expected.unresolved actual2
+'
+
+test_expect_success 'rerere --no-no-rerere-autoupdate' '
+ git rm -fr --cached . &&
+ git update-index --index-info <failedmerge &&
+ cp file3.conflict file3 &&
+ test_must_fail git rerere --no-no-rerere-autoupdate 2>err &&
+ grep [Uu]sage err &&
+ test_must_fail git update-index --refresh
+'
+
+test_expect_success 'rerere -h' '
+ test_must_fail git rerere -h >help &&
+ grep [Uu]sage help
'
test_done
diff --git a/t/t4202-log.sh b/t/t4202-log.sh
index ead204e5c..2e5135694 100755
--- a/t/t4202-log.sh
+++ b/t/t4202-log.sh
@@ -100,13 +100,11 @@ test_expect_success 'oneline' '
test_expect_success 'diff-filter=A' '
- actual=$(git log --pretty="format:%s" --diff-filter=A HEAD) &&
- expect=$(echo fifth ; echo fourth ; echo third ; echo initial) &&
- test "$actual" = "$expect" || {
- echo Oops
- echo "Actual: $actual"
- false
- }
+ git log --pretty="format:%s" --diff-filter=A HEAD > actual &&
+ git log --pretty="format:%s" --diff-filter A HEAD > actual-separate &&
+ printf "fifth\nfourth\nthird\ninitial" > expect &&
+ test_cmp expect actual &&
+ test_cmp expect actual-separate
'
@@ -203,6 +201,13 @@ test_expect_success 'log --grep' '
test_cmp expect actual
'
+test_expect_success 'log --grep option parsing' '
+ echo second >expect &&
+ git log -1 --pretty="tformat:%s" --grep sec >actual &&
+ test_cmp expect actual &&
+ test_must_fail git log -1 --pretty="tformat:%s" --grep
+'
+
test_expect_success 'log -i --grep' '
echo Second >expect &&
git log -1 --pretty="tformat:%s" -i --grep=sec >actual &&
diff --git a/t/t5520-pull.sh b/t/t5520-pull.sh
index 319e389ed..0b489f5b1 100755
--- a/t/t5520-pull.sh
+++ b/t/t5520-pull.sh
@@ -4,6 +4,11 @@ test_description='pulling into void'
. ./test-lib.sh
+modify () {
+ sed -e "$1" <"$2" >"$2.x" &&
+ mv "$2.x" "$2"
+}
+
D=`pwd`
test_expect_success setup '
@@ -160,4 +165,61 @@ test_expect_success 'pull --rebase works on branch yet to be born' '
test_cmp expect actual
'
+test_expect_success 'setup for detecting upstreamed changes' '
+ mkdir src &&
+ (cd src &&
+ git init &&
+ printf "1\n2\n3\n4\n5\n6\n7\n8\n9\n10\n" > stuff &&
+ git add stuff &&
+ git commit -m "Initial revision"
+ ) &&
+ git clone src dst &&
+ (cd src &&
+ modify s/5/43/ stuff &&
+ git commit -a -m "5->43" &&
+ modify s/6/42/ stuff &&
+ git commit -a -m "Make it bigger"
+ ) &&
+ (cd dst &&
+ modify s/5/43/ stuff &&
+ git commit -a -m "Independent discovery of 5->43"
+ )
+'
+
+test_expect_success 'git pull --rebase detects upstreamed changes' '
+ (cd dst &&
+ git pull --rebase &&
+ test -z "$(git ls-files -u)"
+ )
+'
+
+test_expect_success 'setup for avoiding reapplying old patches' '
+ (cd dst &&
+ test_might_fail git rebase --abort &&
+ git reset --hard origin/master
+ ) &&
+ git clone --bare src src-replace.git &&
+ rm -rf src &&
+ mv src-replace.git src &&
+ (cd dst &&
+ modify s/2/22/ stuff &&
+ git commit -a -m "Change 2" &&
+ modify s/3/33/ stuff &&
+ git commit -a -m "Change 3" &&
+ modify s/4/44/ stuff &&
+ git commit -a -m "Change 4" &&
+ git push &&
+
+ modify s/44/55/ stuff &&
+ git commit --amend -a -m "Modified Change 4"
+ )
+'
+
+test_expect_success 'git pull --rebase does not reapply old patches' '
+ (cd dst &&
+ test_must_fail git pull --rebase &&
+ test 1 = $(find .git/rebase-apply -name "000*" | wc -l)
+ )
+'
+
test_done
diff --git a/t/t5525-fetch-tagopt.sh b/t/t5525-fetch-tagopt.sh
new file mode 100755
index 000000000..4fbf7a120
--- /dev/null
+++ b/t/t5525-fetch-tagopt.sh
@@ -0,0 +1,41 @@
+#!/bin/sh
+
+test_description='tagopt variable affects "git fetch" and is overridden by commandline.'
+
+. ./test-lib.sh
+
+setup_clone () {
+ git clone --mirror . $1 &&
+ git remote add remote_$1 $1 &&
+ (cd $1 &&
+ git tag tag_$1)
+}
+
+test_expect_success setup '
+ test_commit test &&
+ setup_clone one &&
+ git config remote.remote_one.tagopt --no-tags &&
+ setup_clone two &&
+ git config remote.remote_two.tagopt --tags
+ '
+
+test_expect_success "fetch with tagopt=--no-tags does not get tag" '
+ git fetch remote_one &&
+ test_must_fail git show-ref tag_one
+ '
+
+test_expect_success "fetch --tags with tagopt=--no-tags gets tag" '
+ git fetch --tags remote_one &&
+ git show-ref tag_one
+ '
+
+test_expect_success "fetch --no-tags with tagopt=--tags does not get tag" '
+ git fetch --no-tags remote_two &&
+ test_must_fail git show-ref tag_two
+ '
+
+test_expect_success "fetch with tagopt=--tags gets tag" '
+ git fetch remote_two &&
+ git show-ref tag_two
+ '
+test_done
diff --git a/t/t5601-clone.sh b/t/t5601-clone.sh
index 8abb71afc..4431dfd02 100755
--- a/t/t5601-clone.sh
+++ b/t/t5601-clone.sh
@@ -178,8 +178,14 @@ test_expect_success 'clone respects global branch.autosetuprebase' '
test_expect_success 'respect url-encoding of file://' '
git init x+y &&
- test_must_fail git clone "file://$PWD/x+y" xy-url &&
- git clone "file://$PWD/x%2By" xy-url
+ git clone "file://$PWD/x+y" xy-url-1 &&
+ git clone "file://$PWD/x%2By" xy-url-2
+'
+
+test_expect_success 'do not query-string-decode + in URLs' '
+ rm -rf x+y &&
+ git init "x y" &&
+ test_must_fail git clone "file://$PWD/x+y" xy-no-plus
'
test_expect_success 'do not respect url-encoding of non-url path' '
diff --git a/t/t6010-merge-base.sh b/t/t6010-merge-base.sh
index 0144d9e85..62197a3d3 100755
--- a/t/t6010-merge-base.sh
+++ b/t/t6010-merge-base.sh
@@ -3,175 +3,231 @@
# Copyright (c) 2005 Junio C Hamano
#
-test_description='Merge base computation.
+test_description='Merge base and parent list computation.
'
. ./test-lib.sh
-T=$(git write-tree)
-
-M=1130000000
-Z=+0000
-
-GIT_COMMITTER_EMAIL=git@comm.iter.xz
-GIT_COMMITTER_NAME='C O Mmiter'
-GIT_AUTHOR_NAME='A U Thor'
-GIT_AUTHOR_EMAIL=git@au.thor.xz
-export GIT_COMMITTER_EMAIL GIT_COMMITTER_NAME GIT_AUTHOR_NAME GIT_AUTHOR_EMAIL
-
-doit() {
- OFFSET=$1; shift
- NAME=$1; shift
- PARENTS=
- for P
- do
- PARENTS="${PARENTS}-p $P "
- done
- GIT_COMMITTER_DATE="$(($M + $OFFSET)) $Z"
- GIT_AUTHOR_DATE=$GIT_COMMITTER_DATE
- export GIT_COMMITTER_DATE GIT_AUTHOR_DATE
- commit=$(echo $NAME | git commit-tree $T $PARENTS)
- echo $commit >.git/refs/tags/$NAME
- echo $commit
-}
-
-# E---D---C---B---A
-# \'-_ \ \
-# \ `---------G \
-# \ \
-# F----------------H
-
-# Setup...
-E=$(doit 5 E)
-D=$(doit 4 D $E)
-F=$(doit 6 F $E)
-C=$(doit 3 C $D)
-B=$(doit 2 B $C)
-A=$(doit 1 A $B)
-G=$(doit 7 G $B $E)
-H=$(doit 8 H $A $F)
-
-test_expect_success 'compute merge-base (single)' \
- 'MB=$(git merge-base G H) &&
- expr "$(git name-rev "$MB")" : "[0-9a-f]* tags/B"'
-
-test_expect_success 'compute merge-base (all)' \
- 'MB=$(git merge-base --all G H) &&
- expr "$(git name-rev "$MB")" : "[0-9a-f]* tags/B"'
-
-test_expect_success 'compute merge-base with show-branch' \
- 'MB=$(git show-branch --merge-base G H) &&
- expr "$(git name-rev "$MB")" : "[0-9a-f]* tags/B"'
-
-# Setup for second test to demonstrate that relying on timestamps in a
-# distributed SCM to provide a _consistent_ partial ordering of commits
-# leads to insanity.
-#
-# Relative
-# Structure timestamps
-#
-# PL PR +4 +4
-# / \/ \ / \/ \
-# L2 C2 R2 +3 -1 +3
-# | | | | | |
-# L1 C1 R1 +2 -2 +2
-# | | | | | |
-# L0 C0 R0 +1 -3 +1
-# \ | / \ | /
-# S 0
-#
-# The left and right chains of commits can be of any length and complexity as
-# long as all of the timestamps are greater than that of S.
+test_expect_success 'setup' '
+ T=$(git write-tree) &&
-S=$(doit 0 S)
+ M=1130000000 &&
+ Z=+0000 &&
-C0=$(doit -3 C0 $S)
-C1=$(doit -2 C1 $C0)
-C2=$(doit -1 C2 $C1)
+ GIT_COMMITTER_EMAIL=git@comm.iter.xz &&
+ GIT_COMMITTER_NAME="C O Mmiter" &&
+ GIT_AUTHOR_NAME="A U Thor" &&
+ GIT_AUTHOR_EMAIL=git@au.thor.xz &&
+ export GIT_COMMITTER_EMAIL GIT_COMMITTER_NAME GIT_AUTHOR_NAME GIT_AUTHOR_EMAIL &&
-L0=$(doit 1 L0 $S)
-L1=$(doit 2 L1 $L0)
-L2=$(doit 3 L2 $L1)
+ doit() {
+ OFFSET=$1 &&
+ NAME=$2 &&
+ shift 2 &&
-R0=$(doit 1 R0 $S)
-R1=$(doit 2 R1 $R0)
-R2=$(doit 3 R2 $R1)
+ PARENTS= &&
+ for P
+ do
+ PARENTS="${PARENTS}-p $P "
+ done &&
-PL=$(doit 4 PL $L2 $C2)
-PR=$(doit 4 PR $C2 $R2)
+ GIT_COMMITTER_DATE="$(($M + $OFFSET)) $Z" &&
+ GIT_AUTHOR_DATE=$GIT_COMMITTER_DATE &&
+ export GIT_COMMITTER_DATE GIT_AUTHOR_DATE &&
-test_expect_success 'compute merge-base (single)' \
- 'MB=$(git merge-base PL PR) &&
- expr "$(git name-rev "$MB")" : "[0-9a-f]* tags/C2"'
+ commit=$(echo $NAME | git commit-tree $T $PARENTS) &&
-test_expect_success 'compute merge-base (all)' \
- 'MB=$(git merge-base --all PL PR) &&
- expr "$(git name-rev "$MB")" : "[0-9a-f]* tags/C2"'
+ echo $commit >.git/refs/tags/$NAME &&
+ echo $commit
+ }
+'
-# Another set to demonstrate base between one commit and a merge
-# in the documentation.
-#
-# * C (MMC) * B (MMB) * A (MMA)
-# * o * o * o
-# * o * o * o
-# * o * o * o
-# * o | _______/
-# | |/
-# | * 1 (MM1)
-# | _______/
-# |/
-# * root (MMR)
+test_expect_success 'set up G and H' '
+ # E---D---C---B---A
+ # \"-_ \ \
+ # \ `---------G \
+ # \ \
+ # F----------------H
+ E=$(doit 5 E) &&
+ D=$(doit 4 D $E) &&
+ F=$(doit 6 F $E) &&
+ C=$(doit 3 C $D) &&
+ B=$(doit 2 B $C) &&
+ A=$(doit 1 A $B) &&
+ G=$(doit 7 G $B $E) &&
+ H=$(doit 8 H $A $F)
+'
+
+test_expect_success 'merge-base G H' '
+ git name-rev $B >expected &&
+
+ MB=$(git merge-base G H) &&
+ git name-rev "$MB" >actual.single &&
+
+ MB=$(git merge-base --all G H) &&
+ git name-rev "$MB" >actual.all &&
+
+ MB=$(git show-branch --merge-base G H) &&
+ git name-rev "$MB" >actual.sb &&
+
+ test_cmp expected actual.single &&
+ test_cmp expected actual.all &&
+ test_cmp expected actual.sb
+'
+test_expect_success 'merge-base/show-branch --independent' '
+ git name-rev "$H" >expected1 &&
+ git name-rev "$H" "$G" >expected2 &&
+
+ parents=$(git merge-base --independent H) &&
+ git name-rev $parents >actual1.mb &&
+ parents=$(git merge-base --independent A H G) &&
+ git name-rev $parents >actual2.mb &&
+
+ parents=$(git show-branch --independent H) &&
+ git name-rev $parents >actual1.sb &&
+ parents=$(git show-branch --independent A H G) &&
+ git name-rev $parents >actual2.sb &&
+
+ test_cmp expected1 actual1.mb &&
+ test_cmp expected2 actual2.mb &&
+ test_cmp expected1 actual1.sb &&
+ test_cmp expected2 actual2.sb
+'
+
+test_expect_success 'unsynchronized clocks' '
+ # This test is to demonstrate that relying on timestamps in a distributed
+ # SCM to provide a _consistent_ partial ordering of commits leads to
+ # insanity.
+ #
+ # Relative
+ # Structure timestamps
+ #
+ # PL PR +4 +4
+ # / \/ \ / \/ \
+ # L2 C2 R2 +3 -1 +3
+ # | | | | | |
+ # L1 C1 R1 +2 -2 +2
+ # | | | | | |
+ # L0 C0 R0 +1 -3 +1
+ # \ | / \ | /
+ # S 0
+ #
+ # The left and right chains of commits can be of any length and complexity as
+ # long as all of the timestamps are greater than that of S.
+
+ S=$(doit 0 S) &&
+
+ C0=$(doit -3 C0 $S) &&
+ C1=$(doit -2 C1 $C0) &&
+ C2=$(doit -1 C2 $C1) &&
+
+ L0=$(doit 1 L0 $S) &&
+ L1=$(doit 2 L1 $L0) &&
+ L2=$(doit 3 L2 $L1) &&
+
+ R0=$(doit 1 R0 $S) &&
+ R1=$(doit 2 R1 $R0) &&
+ R2=$(doit 3 R2 $R1) &&
+
+ PL=$(doit 4 PL $L2 $C2) &&
+ PR=$(doit 4 PR $C2 $R2)
+
+ git name-rev $C2 >expected &&
+
+ MB=$(git merge-base PL PR) &&
+ git name-rev "$MB" >actual.single &&
+
+ MB=$(git merge-base --all PL PR) &&
+ git name-rev "$MB" >actual.all &&
+
+ test_cmp expected actual.single &&
+ test_cmp expected actual.all
+'
+
+test_expect_success '--independent with unsynchronized clocks' '
+ IB=$(doit 0 IB) &&
+ I1=$(doit -10 I1 $IB) &&
+ I2=$(doit -9 I2 $I1) &&
+ I3=$(doit -8 I3 $I2) &&
+ I4=$(doit -7 I4 $I3) &&
+ I5=$(doit -6 I5 $I4) &&
+ I6=$(doit -5 I6 $I5) &&
+ I7=$(doit -4 I7 $I6) &&
+ I8=$(doit -3 I8 $I7) &&
+ IH=$(doit -2 IH $I8) &&
+
+ echo $IH >expected &&
+ git merge-base --independent IB IH >actual &&
+ test_cmp expected actual
+'
test_expect_success 'merge-base for octopus-step (setup)' '
- test_tick && git commit --allow-empty -m root && git tag MMR &&
- test_tick && git commit --allow-empty -m 1 && git tag MM1 &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m A && git tag MMA &&
+ # Another set to demonstrate base between one commit and a merge
+ # in the documentation.
+ #
+ # * C (MMC) * B (MMB) * A (MMA)
+ # * o * o * o
+ # * o * o * o
+ # * o * o * o
+ # * o | _______/
+ # | |/
+ # | * 1 (MM1)
+ # | _______/
+ # |/
+ # * root (MMR)
+
+ test_commit MMR &&
+ test_commit MM1 &&
+ test_commit MM-o &&
+ test_commit MM-p &&
+ test_commit MM-q &&
+ test_commit MMA &&
git checkout MM1 &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m B && git tag MMB &&
+ test_commit MM-r &&
+ test_commit MM-s &&
+ test_commit MM-t &&
+ test_commit MMB &&
git checkout MMR &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m C && git tag MMC
+ test_commit MM-u &&
+ test_commit MM-v &&
+ test_commit MM-w &&
+ test_commit MM-x &&
+ test_commit MMC
'
test_expect_success 'merge-base A B C' '
- MB=$(git merge-base --all MMA MMB MMC) &&
- MM1=$(git rev-parse --verify MM1) &&
- test "$MM1" = "$MB"
-'
+ git rev-parse --verify MM1 >expected &&
+ git rev-parse --verify MMR >expected.sb &&
-test_expect_success 'merge-base A B C using show-branch' '
- MB=$(git show-branch --merge-base MMA MMB MMC) &&
- MMR=$(git rev-parse --verify MMR) &&
- test "$MMR" = "$MB"
+ git merge-base --all MMA MMB MMC >actual &&
+ git merge-base --all --octopus MMA MMB MMC >actual.common &&
+ git show-branch --merge-base MMA MMB MMC >actual.sb &&
+
+ test_cmp expected actual &&
+ test_cmp expected.sb actual.common &&
+ test_cmp expected.sb actual.sb
'
-test_expect_success 'criss-cross merge-base for octopus-step (setup)' '
+test_expect_success 'criss-cross merge-base for octopus-step' '
git reset --hard MMR &&
- test_tick && git commit --allow-empty -m 1 && git tag CC1 &&
+ test_commit CC1 &&
git reset --hard E &&
- test_tick && git commit --allow-empty -m 2 && git tag CC2 &&
- test_tick && git merge -s ours CC1 &&
- test_tick && git commit --allow-empty -m o &&
- test_tick && git commit --allow-empty -m B && git tag CCB &&
+ test_commit CC2 &&
+ test_tick &&
+ git merge -s ours CC1 &&
+ test_commit CC-o &&
+ test_commit CCB &&
git reset --hard CC1 &&
- test_tick && git merge -s ours CC2 &&
- test_tick && git commit --allow-empty -m A && git tag CCA
-'
+ git merge -s ours CC2 &&
+ test_commit CCA &&
+
+ git rev-parse CC1 CC2 >expected &&
+ git merge-base --all CCB CCA^^ CCA^^2 >actual &&
-test_expect_success 'merge-base B A^^ A^^2' '
- MB0=$(git merge-base --all CCB CCA^^ CCA^^2 | sort) &&
- MB1=$(git rev-parse CC1 CC2 | sort) &&
- test "$MB0" = "$MB1"
+ sort expected >expected.sorted &&
+ sort actual >actual.sorted &&
+ test_cmp expected.sorted actual.sorted
'
test_done
diff --git a/t/t6018-rev-list-glob.sh b/t/t6018-rev-list-glob.sh
index 58428d9f5..fb8291c81 100755
--- a/t/t6018-rev-list-glob.sh
+++ b/t/t6018-rev-list-glob.sh
@@ -123,6 +123,12 @@ test_expect_success 'rev-list --glob=refs/heads/subspace/*' '
'
+test_expect_success 'rev-list --glob refs/heads/subspace/*' '
+
+ compare rev-list "subspace/one subspace/two" "--glob refs/heads/subspace/*"
+
+'
+
test_expect_success 'rev-list --glob=heads/subspace/*' '
compare rev-list "subspace/one subspace/two" "--glob=heads/subspace/*"
diff --git a/t/t6020-merge-df.sh b/t/t6020-merge-df.sh
index e71c687f2..490d39711 100755
--- a/t/t6020-merge-df.sh
+++ b/t/t6020-merge-df.sh
@@ -22,7 +22,7 @@ git commit -m "File: dir"'
test_expect_code 1 'Merge with d/f conflicts' 'git merge "merge msg" B master'
-test_expect_failure 'F/D conflict' '
+test_expect_success 'F/D conflict' '
git reset --hard &&
git checkout master &&
rm .git/index &&
diff --git a/t/t6031-merge-recursive.sh b/t/t6031-merge-recursive.sh
index 8a3304fb0..bd75e0e64 100755
--- a/t/t6031-merge-recursive.sh
+++ b/t/t6031-merge-recursive.sh
@@ -57,4 +57,35 @@ test_expect_success FILEMODE 'verify executable bit on file' '
test -x file2
'
+test_expect_success 'merging with triple rename across D/F conflict' '
+ git reset --hard HEAD &&
+ git checkout -b main &&
+ git rm -rf . &&
+
+ echo "just a file" >sub1 &&
+ mkdir -p sub2 &&
+ echo content1 >sub2/file1 &&
+ echo content2 >sub2/file2 &&
+ echo content3 >sub2/file3 &&
+ mkdir simple &&
+ echo base >simple/bar &&
+ git add -A &&
+ test_tick &&
+ git commit -m base &&
+
+ git checkout -b other &&
+ echo more >>simple/bar &&
+ test_tick &&
+ git commit -a -m changesimplefile &&
+
+ git checkout main &&
+ git rm sub1 &&
+ git mv sub2 sub1 &&
+ test_tick &&
+ git commit -m changefiletodir &&
+
+ test_tick &&
+ git merge other
+'
+
test_done
diff --git a/t/t6035-merge-dir-to-symlink.sh b/t/t6035-merge-dir-to-symlink.sh
index cd3190c4a..dc09513be 100755
--- a/t/t6035-merge-dir-to-symlink.sh
+++ b/t/t6035-merge-dir-to-symlink.sh
@@ -48,7 +48,7 @@ test_expect_success 'setup for merge test' '
git tag baseline
'
-test_expect_success 'do not lose a/b-2/c/d in merge (resolve)' '
+test_expect_success 'Handle D/F conflict, do not lose a/b-2/c/d in merge (resolve)' '
git reset --hard &&
git checkout baseline^0 &&
git merge -s resolve master &&
@@ -56,7 +56,7 @@ test_expect_success 'do not lose a/b-2/c/d in merge (resolve)' '
test -f a/b-2/c/d
'
-test_expect_failure 'do not lose a/b-2/c/d in merge (recursive)' '
+test_expect_success 'Handle D/F conflict, do not lose a/b-2/c/d in merge (recursive)' '
git reset --hard &&
git checkout baseline^0 &&
git merge -s recursive master &&
@@ -64,6 +64,54 @@ test_expect_failure 'do not lose a/b-2/c/d in merge (recursive)' '
test -f a/b-2/c/d
'
+test_expect_success 'Handle F/D conflict, do not lose a/b-2/c/d in merge (resolve)' '
+ git reset --hard &&
+ git checkout master^0 &&
+ git merge -s resolve baseline^0 &&
+ test -h a/b &&
+ test -f a/b-2/c/d
+'
+
+test_expect_success 'Handle F/D conflict, do not lose a/b-2/c/d in merge (recursive)' '
+ git reset --hard &&
+ git checkout master^0 &&
+ git merge -s recursive baseline^0 &&
+ test -h a/b &&
+ test -f a/b-2/c/d
+'
+
+test_expect_failure 'do not lose untracked in merge (resolve)' '
+ git reset --hard &&
+ git checkout baseline^0 &&
+ >a/b/c/e &&
+ test_must_fail git merge -s resolve master &&
+ test -f a/b/c/e &&
+ test -f a/b-2/c/d
+'
+
+test_expect_success 'do not lose untracked in merge (recursive)' '
+ git reset --hard &&
+ git checkout baseline^0 &&
+ >a/b/c/e &&
+ test_must_fail git merge -s recursive master &&
+ test -f a/b/c/e &&
+ test -f a/b-2/c/d
+'
+
+test_expect_success 'do not lose modifications in merge (resolve)' '
+ git reset --hard &&
+ git checkout baseline^0 &&
+ echo more content >>a/b/c/d &&
+ test_must_fail git merge -s resolve master
+'
+
+test_expect_success 'do not lose modifications in merge (recursive)' '
+ git reset --hard &&
+ git checkout baseline^0 &&
+ echo more content >>a/b/c/d &&
+ test_must_fail git merge -s recursive master
+'
+
test_expect_success 'setup a merge where dir a/b-2 changed to symlink' '
git reset --hard &&
git checkout start^0 &&
@@ -74,7 +122,7 @@ test_expect_success 'setup a merge where dir a/b-2 changed to symlink' '
git tag test2
'
-test_expect_success 'merge should not have conflicts (resolve)' '
+test_expect_success 'merge should not have D/F conflicts (resolve)' '
git reset --hard &&
git checkout baseline^0 &&
git merge -s resolve test2 &&
@@ -82,7 +130,7 @@ test_expect_success 'merge should not have conflicts (resolve)' '
test -f a/b/c/d
'
-test_expect_failure 'merge should not have conflicts (recursive)' '
+test_expect_success 'merge should not have D/F conflicts (recursive)' '
git reset --hard &&
git checkout baseline^0 &&
git merge -s recursive test2 &&
@@ -90,4 +138,12 @@ test_expect_failure 'merge should not have conflicts (recursive)' '
test -f a/b/c/d
'
+test_expect_success 'merge should not have F/D conflicts (recursive)' '
+ git reset --hard &&
+ git checkout -b foo test2 &&
+ git merge -s recursive baseline^0 &&
+ test -h a/b-2 &&
+ test -f a/b/c/d
+'
+
test_done
diff --git a/t/t6038-merge-text-auto.sh b/t/t6038-merge-text-auto.sh
new file mode 100755
index 000000000..52d0dc4bb
--- /dev/null
+++ b/t/t6038-merge-text-auto.sh
@@ -0,0 +1,189 @@
+#!/bin/sh
+
+test_description='CRLF merge conflict across text=auto change
+
+* [master] remove .gitattributes
+ ! [side] add line from b
+--
+ + [side] add line from b
+* [master] remove .gitattributes
+* [master^] add line from a
+* [master~2] normalize file
+*+ [side^] Initial
+'
+
+. ./test-lib.sh
+
+test_expect_success setup '
+ git config core.autocrlf false &&
+
+ echo first line | append_cr >file &&
+ echo first line >control_file &&
+ echo only line >inert_file &&
+
+ git add file control_file inert_file &&
+ test_tick &&
+ git commit -m "Initial" &&
+ git tag initial &&
+ git branch side &&
+
+ echo "* text=auto" >.gitattributes &&
+ touch file &&
+ git add .gitattributes file &&
+ test_tick &&
+ git commit -m "normalize file" &&
+
+ echo same line | append_cr >>file &&
+ echo same line >>control_file &&
+ git add file control_file &&
+ test_tick &&
+ git commit -m "add line from a" &&
+ git tag a &&
+
+ git rm .gitattributes &&
+ rm file &&
+ git checkout file &&
+ test_tick &&
+ git commit -m "remove .gitattributes" &&
+ git tag c &&
+
+ git checkout side &&
+ echo same line | append_cr >>file &&
+ echo same line >>control_file &&
+ git add file control_file &&
+ test_tick &&
+ git commit -m "add line from b" &&
+ git tag b &&
+
+ git checkout master
+'
+
+test_expect_success 'set up fuzz_conflict() helper' '
+ fuzz_conflict() {
+ sed -e "s/^\([<>=]......\) .*/\1/" "$@"
+ }
+'
+
+test_expect_success 'Merge after setting text=auto' '
+ cat <<-\EOF >expected &&
+ first line
+ same line
+ EOF
+
+ git config merge.renormalize true &&
+ git rm -fr . &&
+ rm -f .gitattributes &&
+ git reset --hard a &&
+ git merge b &&
+ test_cmp expected file
+'
+
+test_expect_success 'Merge addition of text=auto' '
+ cat <<-\EOF >expected &&
+ first line
+ same line
+ EOF
+
+ git config merge.renormalize true &&
+ git rm -fr . &&
+ rm -f .gitattributes &&
+ git reset --hard b &&
+ git merge a &&
+ test_cmp expected file
+'
+
+test_expect_success 'Detect CRLF/LF conflict after setting text=auto' '
+ q_to_cr <<-\EOF >expected &&
+ <<<<<<<
+ first line
+ same line
+ =======
+ first lineQ
+ same lineQ
+ >>>>>>>
+ EOF
+
+ git config merge.renormalize false &&
+ rm -f .gitattributes &&
+ git reset --hard a &&
+ test_must_fail git merge b &&
+ fuzz_conflict file >file.fuzzy &&
+ test_cmp expected file.fuzzy
+'
+
+test_expect_success 'Detect LF/CRLF conflict from addition of text=auto' '
+ q_to_cr <<-\EOF >expected &&
+ <<<<<<<
+ first lineQ
+ same lineQ
+ =======
+ first line
+ same line
+ >>>>>>>
+ EOF
+
+ git config merge.renormalize false &&
+ rm -f .gitattributes &&
+ git reset --hard b &&
+ test_must_fail git merge a &&
+ fuzz_conflict file >file.fuzzy &&
+ test_cmp expected file.fuzzy
+'
+
+test_expect_failure 'checkout -m after setting text=auto' '
+ cat <<-\EOF >expected &&
+ first line
+ same line
+ EOF
+
+ git config merge.renormalize true &&
+ git rm -fr . &&
+ rm -f .gitattributes &&
+ git reset --hard initial &&
+ git checkout a -- . &&
+ git checkout -m b &&
+ test_cmp expected file
+'
+
+test_expect_failure 'checkout -m addition of text=auto' '
+ cat <<-\EOF >expected &&
+ first line
+ same line
+ EOF
+
+ git config merge.renormalize true &&
+ git rm -fr . &&
+ rm -f .gitattributes file &&
+ git reset --hard initial &&
+ git checkout b -- . &&
+ git checkout -m a &&
+ test_cmp expected file
+'
+
+test_expect_failure 'cherry-pick patch from after text=auto was added' '
+ append_cr <<-\EOF >expected &&
+ first line
+ same line
+ EOF
+
+ git config merge.renormalize true &&
+ git rm -fr . &&
+ git reset --hard b &&
+ test_must_fail git cherry-pick a >err 2>&1 &&
+ grep "[Nn]othing added" err &&
+ test_cmp expected file
+'
+
+test_expect_success 'Test delete/normalize conflict' '
+ git checkout -f side &&
+ git rm -fr . &&
+ rm -f .gitattributes &&
+ git reset --hard initial &&
+ git rm file &&
+ git commit -m "remove file" &&
+ git checkout master &&
+ git reset --hard a^ &&
+ git merge side
+'
+
+test_done
diff --git a/t/t6200-fmt-merge-msg.sh b/t/t6200-fmt-merge-msg.sh
index 42f8ece09..71f6cad3c 100755
--- a/t/t6200-fmt-merge-msg.sh
+++ b/t/t6200-fmt-merge-msg.sh
@@ -70,14 +70,13 @@ test_expect_success setup '
i=$(($i+1))
done &&
- git show-branch
-'
+ git show-branch &&
-cat >expected <<\EOF
-Merge branch 'left'
-EOF
+ apos="'\''"
+'
-test_expect_success 'merge-msg test #1' '
+test_expect_success 'message for merging local branch' '
+ echo "Merge branch ${apos}left${apos}" >expected &&
git checkout master &&
git fetch . left &&
@@ -86,11 +85,8 @@ test_expect_success 'merge-msg test #1' '
test_cmp expected actual
'
-cat >expected <<EOF
-Merge branch 'left' of $(pwd)
-EOF
-
-test_expect_success 'merge-msg test #2' '
+test_expect_success 'message for merging external branch' '
+ echo "Merge branch ${apos}left${apos} of $(pwd)" >expected &&
git checkout master &&
git fetch "$(pwd)" left &&
@@ -99,139 +95,140 @@ test_expect_success 'merge-msg test #2' '
test_cmp expected actual
'
-cat >expected <<\EOF
-Merge branch 'left'
-
-* left:
- Left #5
- Left #4
- Left #3
- Common #2
- Common #1
-EOF
+test_expect_success '[merge] summary/log configuration' '
+ cat >expected <<-EOF &&
+ Merge branch ${apos}left${apos}
-test_expect_success 'merge-msg test #3-1' '
+ * left:
+ Left #5
+ Left #4
+ Left #3
+ Common #2
+ Common #1
+ EOF
- git config --unset-all merge.log
- git config --unset-all merge.summary
git config merge.log true &&
+ test_might_fail git config --unset-all merge.summary &&
git checkout master &&
test_tick &&
git fetch . left &&
- git fmt-merge-msg <.git/FETCH_HEAD >actual &&
- test_cmp expected actual
-'
-
-test_expect_success 'merge-msg test #3-2' '
+ git fmt-merge-msg <.git/FETCH_HEAD >actual1 &&
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary true &&
git checkout master &&
test_tick &&
git fetch . left &&
- git fmt-merge-msg <.git/FETCH_HEAD >actual &&
- test_cmp expected actual
-'
-
-cat >expected <<\EOF
-Merge branches 'left' and 'right'
+ git fmt-merge-msg <.git/FETCH_HEAD >actual2 &&
-* left:
- Left #5
- Left #4
- Left #3
- Common #2
- Common #1
+ test_cmp expected actual1 &&
+ test_cmp expected actual2
+'
-* right:
- Right #5
- Right #4
- Right #3
- Common #2
- Common #1
-EOF
+test_expect_success 'fmt-merge-msg -m' '
+ echo "Sync with left" >expected &&
+ cat >expected.log <<-EOF &&
+ Sync with left
+
+ * ${apos}left${apos} of $(pwd):
+ Left #5
+ Left #4
+ Left #3
+ Common #2
+ Common #1
+ EOF
+
+ test_might_fail git config --unset merge.log &&
+ test_might_fail git config --unset merge.summary &&
+ git checkout master &&
+ git fetch "$(pwd)" left &&
+ git fmt-merge-msg -m "Sync with left" <.git/FETCH_HEAD >actual &&
+ git fmt-merge-msg --log -m "Sync with left" \
+ <.git/FETCH_HEAD >actual.log &&
+ git config merge.log true &&
+ git fmt-merge-msg -m "Sync with left" \
+ <.git/FETCH_HEAD >actual.log-config &&
+ git fmt-merge-msg --no-log -m "Sync with left" \
+ <.git/FETCH_HEAD >actual.nolog &&
+
+ test_cmp expected actual &&
+ test_cmp expected.log actual.log &&
+ test_cmp expected.log actual.log-config &&
+ test_cmp expected actual.nolog
+'
-test_expect_success 'merge-msg test #4-1' '
+test_expect_success 'setup: expected shortlog for two branches' '
+ cat >expected <<-EOF
+ Merge branches ${apos}left${apos} and ${apos}right${apos}
+
+ * left:
+ Left #5
+ Left #4
+ Left #3
+ Common #2
+ Common #1
+
+ * right:
+ Right #5
+ Right #4
+ Right #3
+ Common #2
+ Common #1
+ EOF
+'
- git config --unset-all merge.log
- git config --unset-all merge.summary
+test_expect_success 'shortlog for two branches' '
git config merge.log true &&
-
+ test_might_fail git config --unset-all merge.summary &&
git checkout master &&
test_tick &&
git fetch . left right &&
+ git fmt-merge-msg <.git/FETCH_HEAD >actual1 &&
- git fmt-merge-msg <.git/FETCH_HEAD >actual &&
- test_cmp expected actual
-'
-
-test_expect_success 'merge-msg test #4-2' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary true &&
-
git checkout master &&
test_tick &&
git fetch . left right &&
+ git fmt-merge-msg <.git/FETCH_HEAD >actual2 &&
- git fmt-merge-msg <.git/FETCH_HEAD >actual &&
- test_cmp expected actual
-'
-
-test_expect_success 'merge-msg test #5-1' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
git config merge.log yes &&
-
+ test_might_fail git config --unset-all merge.summary &&
git checkout master &&
test_tick &&
git fetch . left right &&
+ git fmt-merge-msg <.git/FETCH_HEAD >actual3 &&
- git fmt-merge-msg <.git/FETCH_HEAD >actual &&
- test_cmp expected actual
-'
-
-test_expect_success 'merge-msg test #5-2' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary yes &&
-
git checkout master &&
test_tick &&
git fetch . left right &&
+ git fmt-merge-msg <.git/FETCH_HEAD >actual4 &&
- git fmt-merge-msg <.git/FETCH_HEAD >actual &&
- test_cmp expected actual
+ test_cmp expected actual1 &&
+ test_cmp expected actual2 &&
+ test_cmp expected actual3 &&
+ test_cmp expected actual4
'
test_expect_success 'merge-msg -F' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary yes &&
-
git checkout master &&
test_tick &&
git fetch . left right &&
-
git fmt-merge-msg -F .git/FETCH_HEAD >actual &&
test_cmp expected actual
'
test_expect_success 'merge-msg -F in subdirectory' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary yes &&
-
git checkout master &&
test_tick &&
git fetch . left right &&
@@ -245,11 +242,11 @@ test_expect_success 'merge-msg -F in subdirectory' '
'
test_expect_success 'merge-msg with nothing to merge' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary yes &&
+ >empty &&
+
(
cd remote &&
git checkout -b unrelated &&
@@ -258,22 +255,20 @@ test_expect_success 'merge-msg with nothing to merge' '
git fmt-merge-msg <.git/FETCH_HEAD >../actual
) &&
- test_cmp /dev/null actual
+ test_cmp empty actual
'
-cat >expected <<\EOF
-Merge tag 'tag-r3'
-
-* tag 'tag-r3':
- Right #3
- Common #2
- Common #1
-EOF
-
test_expect_success 'merge-msg tag' '
+ cat >expected <<-EOF &&
+ Merge tag ${apos}tag-r3${apos}
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ * tag ${apos}tag-r3${apos}:
+ Right #3
+ Common #2
+ Common #1
+ EOF
+
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary yes &&
git checkout master &&
@@ -284,26 +279,24 @@ test_expect_success 'merge-msg tag' '
test_cmp expected actual
'
-cat >expected <<\EOF
-Merge tags 'tag-r3' and 'tag-l5'
-
-* tag 'tag-r3':
- Right #3
- Common #2
- Common #1
-
-* tag 'tag-l5':
- Left #5
- Left #4
- Left #3
- Common #2
- Common #1
-EOF
-
test_expect_success 'merge-msg two tags' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ cat >expected <<-EOF &&
+ Merge tags ${apos}tag-r3${apos} and ${apos}tag-l5${apos}
+
+ * tag ${apos}tag-r3${apos}:
+ Right #3
+ Common #2
+ Common #1
+
+ * tag ${apos}tag-l5${apos}:
+ Left #5
+ Left #4
+ Left #3
+ Common #2
+ Common #1
+ EOF
+
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary yes &&
git checkout master &&
@@ -314,26 +307,24 @@ test_expect_success 'merge-msg two tags' '
test_cmp expected actual
'
-cat >expected <<\EOF
-Merge branch 'left', tag 'tag-r3'
-
-* tag 'tag-r3':
- Right #3
- Common #2
- Common #1
-
-* left:
- Left #5
- Left #4
- Left #3
- Common #2
- Common #1
-EOF
-
test_expect_success 'merge-msg tag and branch' '
-
- git config --unset-all merge.log
- git config --unset-all merge.summary
+ cat >expected <<-EOF &&
+ Merge branch ${apos}left${apos}, tag ${apos}tag-r3${apos}
+
+ * tag ${apos}tag-r3${apos}:
+ Right #3
+ Common #2
+ Common #1
+
+ * left:
+ Left #5
+ Left #4
+ Left #3
+ Common #2
+ Common #1
+ EOF
+
+ test_might_fail git config --unset-all merge.log &&
git config merge.summary yes &&
git checkout master &&
@@ -344,26 +335,27 @@ test_expect_success 'merge-msg tag and branch' '
test_cmp expected actual
'
-cat >expected <<\EOF
-Merge branch 'long'
-
-* long: (35 commits)
-EOF
-
test_expect_success 'merge-msg lots of commits' '
+ {
+ cat <<-EOF &&
+ Merge branch ${apos}long${apos}
+
+ * long: (35 commits)
+ EOF
+
+ i=29 &&
+ while test $i -gt 9
+ do
+ echo " $i" &&
+ i=$(($i-1))
+ done &&
+ echo " ..."
+ } >expected &&
git checkout master &&
test_tick &&
git fetch . long &&
- i=29 &&
- while test $i -gt 9
- do
- echo " $i" &&
- i=$(($i-1))
- done >>expected &&
- echo " ..." >>expected
-
git fmt-merge-msg <.git/FETCH_HEAD >actual &&
test_cmp expected actual
'
diff --git a/t/t7006-pager.sh b/t/t7006-pager.sh
index 71d3ceff8..fb744e3c4 100755
--- a/t/t7006-pager.sh
+++ b/t/t7006-pager.sh
@@ -58,6 +58,21 @@ test_expect_success TTY 'some commands use a pager' '
test -e paginated.out
'
+test_expect_failure TTY 'pager runs from subdir' '
+ echo subdir/paginated.out >expected &&
+ mkdir -p subdir &&
+ rm -f paginated.out subdir/paginated.out &&
+ (
+ cd subdir &&
+ test_terminal git log
+ ) &&
+ {
+ ls paginated.out subdir/paginated.out ||
+ :
+ } >actual &&
+ test_cmp expected actual
+'
+
test_expect_success TTY 'some commands do not use a pager' '
rm -f paginated.out ||
cleanup_fail &&
@@ -106,6 +121,45 @@ test_expect_success TTY 'no pager with --no-pager' '
! test -e paginated.out
'
+test_expect_success TTY 'configuration can disable pager' '
+ rm -f paginated.out &&
+ test_might_fail git config --unset pager.grep &&
+ test_terminal git grep initial &&
+ test -e paginated.out &&
+
+ rm -f paginated.out &&
+ git config pager.grep false &&
+ test_when_finished "git config --unset pager.grep" &&
+ test_terminal git grep initial &&
+ ! test -e paginated.out
+'
+
+test_expect_success TTY 'git config uses a pager if configured to' '
+ rm -f paginated.out &&
+ git config pager.config true &&
+ test_when_finished "git config --unset pager.config" &&
+ test_terminal git config --list &&
+ test -e paginated.out
+'
+
+test_expect_success TTY 'configuration can enable pager (from subdir)' '
+ rm -f paginated.out &&
+ mkdir -p subdir &&
+ git config pager.bundle true &&
+ test_when_finished "git config --unset pager.bundle" &&
+
+ git bundle create test.bundle --all &&
+ rm -f paginated.out subdir/paginated.out &&
+ (
+ cd subdir &&
+ test_terminal git bundle unbundle ../test.bundle
+ ) &&
+ {
+ test -e paginated.out ||
+ test -e subdir/paginated.out
+ }
+'
+
# A colored commit log will begin with an appropriate ANSI escape
# for the first color; the text "commit" comes later.
colorful() {
@@ -369,4 +423,16 @@ test_GIT_PAGER_overrides expect_success test_must_fail 'git -p'
test_doesnt_paginate expect_failure test_must_fail 'git -p nonsense'
+test_pager_choices 'git shortlog'
+test_expect_success 'setup: configure shortlog not to paginate' '
+ git config pager.shortlog false
+'
+test_doesnt_paginate expect_success 'git shortlog'
+test_no_local_config_subdir expect_success 'git shortlog'
+test_default_pager expect_success 'git -p shortlog'
+test_core_pager_subdir expect_success 'git -p shortlog'
+
+test_core_pager_subdir expect_success test_must_fail \
+ 'git -p apply </dev/null'
+
test_done
diff --git a/t/t7403-submodule-sync.sh b/t/t7403-submodule-sync.sh
index 753875648..02522f962 100755
--- a/t/t7403-submodule-sync.sh
+++ b/t/t7403-submodule-sync.sh
@@ -14,7 +14,7 @@ test_expect_success setup '
echo file > file &&
git add file &&
test_tick &&
- git commit -m upstream
+ git commit -m upstream &&
git clone . super &&
git clone super submodule &&
(cd super &&
@@ -42,7 +42,7 @@ test_expect_success 'change submodule url' '
) &&
mv submodule moved-submodule &&
(cd super &&
- git config -f .gitmodules submodule.submodule.url ../moved-submodule
+ git config -f .gitmodules submodule.submodule.url ../moved-submodule &&
test_tick &&
git commit -a -m moved-submodule
)
@@ -58,6 +58,9 @@ test_expect_success '"git submodule sync" should update submodule URLs' '
(cd super-clone/submodule &&
git checkout master &&
git pull
+ ) &&
+ (cd super-clone &&
+ test -d "$(git config submodule.submodule.url)"
)
'
diff --git a/t/t7405-submodule-merge.sh b/t/t7405-submodule-merge.sh
index 4a7b8933f..7e2e25895 100755
--- a/t/t7405-submodule-merge.sh
+++ b/t/t7405-submodule-merge.sh
@@ -54,21 +54,132 @@ test_expect_success setup '
git merge -s ours a
'
-test_expect_success 'merging with modify/modify conflict' '
+# History setup
+#
+# b
+# / \
+# a d
+# \ /
+# c
+#
+# a in the main repository records to sub-a in the submodule and
+# analogous b and c. d should be automatically found by merging c into
+# b in the main repository.
+test_expect_success 'setup for merge search' '
+ mkdir merge-search &&
+ (cd merge-search &&
+ git init &&
+ mkdir sub &&
+ (cd sub &&
+ git init &&
+ echo "file-a" > file-a &&
+ git add file-a &&
+ git commit -m "sub-a" &&
+ git branch sub-a) &&
+ git add sub &&
+ git commit -m "a" &&
+ git branch a &&
+
+ git checkout -b b &&
+ (cd sub &&
+ git checkout -b sub-b &&
+ echo "file-b" > file-b &&
+ git add file-b &&
+ git commit -m "sub-b") &&
+ git commit -a -m "b" &&
+
+ git checkout -b c a &&
+ (cd sub &&
+ git checkout -b sub-c sub-a &&
+ echo "file-c" > file-c &&
+ git add file-c &&
+ git commit -m "sub-c") &&
+ git commit -a -m "c" &&
- git checkout -b test1 a &&
- test_must_fail git merge b &&
- test -f .git/MERGE_MSG &&
- git diff &&
- test -n "$(git ls-files -u)"
+ git checkout -b d a &&
+ (cd sub &&
+ git checkout -b sub-d sub-b &&
+ git merge sub-c) &&
+ git commit -a -m "d" &&
+ git branch test b)
'
-test_expect_success 'merging with a modify/modify conflict between merge bases' '
+test_expect_success 'merge with one side as a fast-forward of the other' '
+ (cd merge-search &&
+ git checkout -b test-forward b &&
+ git merge d &&
+ git ls-tree test-forward sub | cut -f1 | cut -f3 -d" " > actual &&
+ (cd sub &&
+ git rev-parse sub-d > ../expect) &&
+ test_cmp actual expect)
+'
+test_expect_success 'merging should conflict for non fast-forward' '
+ (cd merge-search &&
+ git checkout -b test-nonforward b &&
+ (cd sub &&
+ git rev-parse sub-d > ../expect) &&
+ test_must_fail git merge c 2> actual &&
+ grep $(cat expect) actual > /dev/null &&
+ git reset --hard)
+'
+
+test_expect_success 'merging should fail for ambiguous common parent' '
+ (cd merge-search &&
+ git checkout -b test-ambiguous b &&
+ (cd sub &&
+ git checkout -b ambiguous sub-b &&
+ git merge sub-c &&
+ git rev-parse sub-d > ../expect1 &&
+ git rev-parse ambiguous > ../expect2) &&
+ test_must_fail git merge c 2> actual &&
+ grep $(cat expect1) actual > /dev/null &&
+ grep $(cat expect2) actual > /dev/null &&
+ git reset --hard)
+'
+
+# in a situation like this
+#
+# submodule tree:
+#
+# sub-a --- sub-b --- sub-d
+#
+# main tree:
+#
+# e (sub-a)
+# /
+# bb (sub-b)
+# \
+# f (sub-d)
+#
+# A merge between e and f should fail because one of the submodule
+# commits (sub-a) does not descend from the submodule merge-base (sub-b).
+#
+test_expect_success 'merging should fail for changes that are backwards' '
+ (cd merge-search &&
+ git checkout -b bb a &&
+ (cd sub &&
+ git checkout sub-b) &&
+ git commit -a -m "bb" &&
+
+ git checkout -b e bb &&
+ (cd sub &&
+ git checkout sub-a) &&
+ git commit -a -m "e" &&
+
+ git checkout -b f bb &&
+ (cd sub &&
+ git checkout sub-d) &&
+ git commit -a -m "f" &&
+
+ git checkout -b test-backward e &&
+ test_must_fail git merge f)
+'
+
+test_expect_success 'merging with a modify/modify conflict between merge bases' '
git reset --hard HEAD &&
git checkout -b test2 c &&
git merge d
-
'
test_done
diff --git a/t/t7406-submodule-update.sh b/t/t7406-submodule-update.sh
index 1382a8e58..bfb4975e9 100755
--- a/t/t7406-submodule-update.sh
+++ b/t/t7406-submodule-update.sh
@@ -25,7 +25,7 @@ test_expect_success 'setup a submodule tree' '
echo file > file &&
git add file &&
test_tick &&
- git commit -m upstream
+ git commit -m upstream &&
git clone . super &&
git clone super submodule &&
git clone super rebasing &&
diff --git a/t/t7407-submodule-foreach.sh b/t/t7407-submodule-foreach.sh
index db9365b64..905a8baae 100755
--- a/t/t7407-submodule-foreach.sh
+++ b/t/t7407-submodule-foreach.sh
@@ -16,7 +16,7 @@ test_expect_success 'setup a submodule tree' '
echo file > file &&
git add file &&
test_tick &&
- git commit -m upstream
+ git commit -m upstream &&
git clone . super &&
git clone super submodule &&
(
@@ -30,7 +30,7 @@ test_expect_success 'setup a submodule tree' '
submodule.sub2 submodule.foo2 &&
git config -f .gitmodules --rename-section \
submodule.sub3 submodule.foo3 &&
- git add .gitmodules
+ git add .gitmodules &&
test_tick &&
git commit -m "submodules" &&
git submodule init sub1 &&
diff --git a/t/t7600-merge.sh b/t/t7600-merge.sh
index cde8390c1..b4f40e4c3 100755
--- a/t/t7600-merge.sh
+++ b/t/t7600-merge.sh
@@ -5,189 +5,103 @@
test_description='git merge
-Testing basic merge operations/option parsing.'
+Testing basic merge operations/option parsing.
+
+! [c0] commit 0
+ ! [c1] commit 1
+ ! [c2] commit 2
+ ! [c3] commit 3
+ ! [c4] c4
+ ! [c5] c5
+ ! [c6] c6
+ * [master] Merge commit 'c1'
+--------
+ - [master] Merge commit 'c1'
+ + * [c1] commit 1
+ + [c6] c6
+ + [c5] c5
+ ++ [c4] c4
+ ++++ [c3] commit 3
+ + [c2] commit 2
++++++++* [c0] commit 0
+'
. ./test-lib.sh
-cat >file <<EOF
-1
-2
-3
-4
-5
-6
-7
-8
-9
-EOF
-
-cat >file.1 <<EOF
-1 X
-2
-3
-4
-5
-6
-7
-8
-9
-EOF
-
-cat >file.5 <<EOF
-1
-2
-3
-4
-5 X
-6
-7
-8
-9
-EOF
-
-cat >file.9 <<EOF
-1
-2
-3
-4
-5
-6
-7
-8
-9 X
-EOF
-
-cat >result.1 <<EOF
-1 X
-2
-3
-4
-5
-6
-7
-8
-9
-EOF
-
-cat >result.1-5 <<EOF
-1 X
-2
-3
-4
-5 X
-6
-7
-8
-9
-EOF
-
-cat >result.1-5-9 <<EOF
-1 X
-2
-3
-4
-5 X
-6
-7
-8
-9 X
-EOF
-
-create_merge_msgs() {
- echo "Merge commit 'c2'" >msg.1-5 &&
- echo "Merge commit 'c2'; commit 'c3'" >msg.1-5-9 &&
- echo "Squashed commit of the following:" >squash.1 &&
- echo >>squash.1 &&
- git log --no-merges ^HEAD c1 >>squash.1 &&
- echo "Squashed commit of the following:" >squash.1-5 &&
- echo >>squash.1-5 &&
- git log --no-merges ^HEAD c2 >>squash.1-5 &&
- echo "Squashed commit of the following:" >squash.1-5-9 &&
- echo >>squash.1-5-9 &&
- git log --no-merges ^HEAD c2 c3 >>squash.1-5-9 &&
- echo > msg.nolog &&
- echo "* commit 'c3':" >msg.log &&
- echo " commit 3" >>msg.log &&
- echo >>msg.log
-}
-
-verify_diff() {
- if ! test_cmp "$1" "$2"
- then
- echo "$3"
- false
- fi
-}
-
-verify_merge() {
- verify_diff "$2" "$1" "[OOPS] bad merge result" &&
- if test $(git ls-files -u | wc -l) -gt 0
- then
- echo "[OOPS] unmerged files"
- false
- fi &&
- if test_must_fail git diff --exit-code
- then
- echo "[OOPS] working tree != index"
- false
- fi &&
- if test -n "$3"
- then
- git show -s --pretty=format:%s HEAD >msg.act &&
- verify_diff "$3" msg.act "[OOPS] bad merge message"
- fi
-}
-
-verify_head() {
- if test "$1" != "$(git rev-parse HEAD)"
- then
- echo "[OOPS] HEAD != $1"
- false
- fi
-}
-
-verify_parents() {
- i=1
- while test $# -gt 0
- do
- if test "$1" != "$(git rev-parse HEAD^$i)"
+test_expect_success 'set up test data and helpers' '
+ printf "%s\n" 1 2 3 4 5 6 7 8 9 >file &&
+ printf "%s\n" "1 X" 2 3 4 5 6 7 8 9 >file.1 &&
+ printf "%s\n" 1 2 3 4 "5 X" 6 7 8 9 >file.5 &&
+ printf "%s\n" 1 2 3 4 5 6 7 8 "9 X" >file.9 &&
+ printf "%s\n" "1 X" 2 3 4 5 6 7 8 9 >result.1 &&
+ printf "%s\n" "1 X" 2 3 4 "5 X" 6 7 8 9 >result.1-5 &&
+ printf "%s\n" "1 X" 2 3 4 "5 X" 6 7 8 "9 X" >result.1-5-9 &&
+
+ create_merge_msgs() {
+ echo "Merge commit '\''c2'\''" >msg.1-5 &&
+ echo "Merge commit '\''c2'\''; commit '\''c3'\''" >msg.1-5-9 &&
+ {
+ echo "Squashed commit of the following:" &&
+ echo &&
+ git log --no-merges ^HEAD c1
+ } >squash.1 &&
+ {
+ echo "Squashed commit of the following:" &&
+ echo &&
+ git log --no-merges ^HEAD c2
+ } >squash.1-5 &&
+ {
+ echo "Squashed commit of the following:" &&
+ echo &&
+ git log --no-merges ^HEAD c2 c3
+ } >squash.1-5-9 &&
+ echo >msg.nolog &&
+ {
+ echo "* commit '\''c3'\'':" &&
+ echo " commit 3" &&
+ echo
+ } >msg.log
+ } &&
+
+ verify_merge() {
+ test_cmp "$2" "$1" &&
+ git update-index --refresh &&
+ git diff --exit-code &&
+ if test -n "$3"
then
- echo "[OOPS] HEAD^$i != $1"
- return 1
+ git show -s --pretty=format:%s HEAD >msg.act &&
+ test_cmp "$3" msg.act
fi
- i=$(expr $i + 1)
- shift
- done
-}
-
-verify_mergeheads() {
- i=1
- if ! test -f .git/MERGE_HEAD
- then
- echo "[OOPS] MERGE_HEAD is missing"
- false
- fi &&
- while test $# -gt 0
- do
- head=$(head -n $i .git/MERGE_HEAD | sed -ne \$p)
- if test "$1" != "$head"
- then
- echo "[OOPS] MERGE_HEAD $i != $1"
+ } &&
+
+ verify_head() {
+ echo "$1" >head.expected &&
+ git rev-parse HEAD >head.actual &&
+ test_cmp head.expected head.actual
+ } &&
+
+ verify_parents() {
+ printf "%s\n" "$@" >parents.expected &&
+ >parents.actual &&
+ i=1 &&
+ while test $i -le $#
+ do
+ git rev-parse HEAD^$i >>parents.actual &&
+ i=$(expr $i + 1) ||
return 1
- fi
- i=$(expr $i + 1)
- shift
- done
-}
+ done &&
+ test_cmp parents.expected parents.actual
+ } &&
-verify_no_mergehead() {
- if test -f .git/MERGE_HEAD
- then
- echo "[OOPS] MERGE_HEAD exists"
- false
- fi
-}
+ verify_mergeheads() {
+ printf "%s\n" "$@" >mergehead.expected &&
+ test_cmp mergehead.expected .git/MERGE_HEAD
+ } &&
+ verify_no_mergehead() {
+ ! test -e .git/MERGE_HEAD
+ }
+'
test_expect_success 'setup' '
git add file &&
@@ -219,7 +133,7 @@ test_expect_success 'setup' '
create_merge_msgs
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'test option parsing' '
test_must_fail git merge -$ c1 &&
@@ -235,13 +149,19 @@ test_expect_success 'reject non-strategy with a git-merge-foo name' '
'
test_expect_success 'merge c0 with c1' '
+ echo "OBJID HEAD@{0}: merge c1: Fast-forward" >reflog.expected &&
+
git reset --hard c0 &&
git merge c1 &&
verify_merge file result.1 &&
- verify_head "$c1"
+ verify_head "$c1" &&
+
+ git reflog -1 >reflog.actual &&
+ sed "s/$_x05[0-9a-f]*/OBJID/g" reflog.actual >reflog.fuzzy &&
+ test_cmp reflog.expected reflog.fuzzy
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c0 with c1 with --ff-only' '
git reset --hard c0 &&
@@ -251,7 +171,28 @@ test_expect_success 'merge c0 with c1 with --ff-only' '
verify_head "$c1"
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
+
+test_expect_success 'merge from unborn branch' '
+ git checkout -f master &&
+ test_might_fail git branch -D kid &&
+
+ echo "OBJID HEAD@{0}: initial pull" >reflog.expected &&
+
+ git checkout --orphan kid &&
+ test_when_finished "git checkout -f master" &&
+ git rm -fr . &&
+ test_tick &&
+ git merge --ff-only c1 &&
+ verify_merge file result.1 &&
+ verify_head "$c1" &&
+
+ git reflog -1 >reflog.actual &&
+ sed "s/$_x05[0-9a-f][0-9a-f]/OBJID/g" reflog.actual >reflog.fuzzy &&
+ test_cmp reflog.expected reflog.fuzzy
+'
+
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2' '
git reset --hard c1 &&
@@ -261,7 +202,7 @@ test_expect_success 'merge c1 with c2' '
verify_parents $c1 $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 and c3' '
git reset --hard c1 &&
@@ -271,7 +212,7 @@ test_expect_success 'merge c1 with c2 and c3' '
verify_parents $c1 $c2 $c3
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'failing merges with --ff-only' '
git reset --hard c1 &&
@@ -288,7 +229,7 @@ test_expect_success 'merge c0 with c1 (no-commit)' '
verify_head $c1
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 (no-commit)' '
git reset --hard c1 &&
@@ -298,7 +239,7 @@ test_expect_success 'merge c1 with c2 (no-commit)' '
verify_mergeheads $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 and c3 (no-commit)' '
git reset --hard c1 &&
@@ -308,7 +249,7 @@ test_expect_success 'merge c1 with c2 and c3 (no-commit)' '
verify_mergeheads $c2 $c3
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c0 with c1 (squash)' '
git reset --hard c0 &&
@@ -316,10 +257,10 @@ test_expect_success 'merge c0 with c1 (squash)' '
verify_merge file result.1 &&
verify_head $c0 &&
verify_no_mergehead &&
- verify_diff squash.1 .git/SQUASH_MSG "[OOPS] bad squash message"
+ test_cmp squash.1 .git/SQUASH_MSG
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c0 with c1 (squash, ff-only)' '
git reset --hard c0 &&
@@ -327,10 +268,10 @@ test_expect_success 'merge c0 with c1 (squash, ff-only)' '
verify_merge file result.1 &&
verify_head $c0 &&
verify_no_mergehead &&
- verify_diff squash.1 .git/SQUASH_MSG "[OOPS] bad squash message"
+ test_cmp squash.1 .git/SQUASH_MSG
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 (squash)' '
git reset --hard c1 &&
@@ -338,17 +279,17 @@ test_expect_success 'merge c1 with c2 (squash)' '
verify_merge file result.1-5 &&
verify_head $c1 &&
verify_no_mergehead &&
- verify_diff squash.1-5 .git/SQUASH_MSG "[OOPS] bad squash message"
+ test_cmp squash.1-5 .git/SQUASH_MSG
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'unsuccesful merge of c1 with c2 (squash, ff-only)' '
git reset --hard c1 &&
test_must_fail git merge --squash --ff-only c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 and c3 (squash)' '
git reset --hard c1 &&
@@ -356,10 +297,10 @@ test_expect_success 'merge c1 with c2 and c3 (squash)' '
verify_merge file result.1-5-9 &&
verify_head $c1 &&
verify_no_mergehead &&
- verify_diff squash.1-5-9 .git/SQUASH_MSG "[OOPS] bad squash message"
+ test_cmp squash.1-5-9 .git/SQUASH_MSG
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 (no-commit in config)' '
git reset --hard c1 &&
@@ -370,7 +311,7 @@ test_expect_success 'merge c1 with c2 (no-commit in config)' '
verify_mergeheads $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 (squash in config)' '
git reset --hard c1 &&
@@ -379,10 +320,10 @@ test_expect_success 'merge c1 with c2 (squash in config)' '
verify_merge file result.1-5 &&
verify_head $c1 &&
verify_no_mergehead &&
- verify_diff squash.1-5 .git/SQUASH_MSG "[OOPS] bad squash message"
+ test_cmp squash.1-5 .git/SQUASH_MSG
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'override config option -n with --summary' '
git reset --hard c1 &&
@@ -412,7 +353,7 @@ test_expect_success 'override config option -n with --stat' '
fi
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'override config option --stat' '
git reset --hard c1 &&
@@ -428,7 +369,7 @@ test_expect_success 'override config option --stat' '
fi
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 (override --no-commit)' '
git reset --hard c1 &&
@@ -439,7 +380,7 @@ test_expect_success 'merge c1 with c2 (override --no-commit)' '
verify_parents $c1 $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c2 (override --squash)' '
git reset --hard c1 &&
@@ -450,7 +391,7 @@ test_expect_success 'merge c1 with c2 (override --squash)' '
verify_parents $c1 $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c0 with c1 (no-ff)' '
git reset --hard c0 &&
@@ -461,7 +402,7 @@ test_expect_success 'merge c0 with c1 (no-ff)' '
verify_parents $c0 $c1
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'combining --squash and --no-ff is refused' '
test_must_fail git merge --squash --no-ff c1 &&
@@ -485,20 +426,20 @@ test_expect_success 'merge log message' '
git reset --hard c0 &&
git merge --no-log c2 &&
git show -s --pretty=format:%b HEAD >msg.act &&
- verify_diff msg.nolog msg.act "[OOPS] bad merge log message" &&
+ test_cmp msg.nolog msg.act &&
git merge --log c3 &&
git show -s --pretty=format:%b HEAD >msg.act &&
- verify_diff msg.log msg.act "[OOPS] bad merge log message" &&
+ test_cmp msg.log msg.act &&
git reset --hard HEAD^ &&
git config merge.log yes &&
git merge c3 &&
git show -s --pretty=format:%b HEAD >msg.act &&
- verify_diff msg.log msg.act "[OOPS] bad merge log message"
+ test_cmp msg.log msg.act
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c0, c2, c0, and c1' '
git reset --hard c1 &&
@@ -509,7 +450,7 @@ test_expect_success 'merge c1 with c0, c2, c0, and c1' '
verify_parents $c1 $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c0, c2, c0, and c1' '
git reset --hard c1 &&
@@ -520,7 +461,7 @@ test_expect_success 'merge c1 with c0, c2, c0, and c1' '
verify_parents $c1 $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge c1 with c1 and c2' '
git reset --hard c1 &&
@@ -531,7 +472,7 @@ test_expect_success 'merge c1 with c1 and c2' '
verify_parents $c1 $c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge fast-forward in a dirty tree' '
git reset --hard c0 &&
@@ -541,16 +482,16 @@ test_expect_success 'merge fast-forward in a dirty tree' '
git merge c2
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'in-index merge' '
git reset --hard c0 &&
- git merge --no-ff -s resolve c1 > out &&
+ git merge --no-ff -s resolve c1 >out &&
grep "Wonderful." out &&
verify_parents $c0 $c1
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'refresh the index before merging' '
git reset --hard c1 &&
@@ -558,31 +499,39 @@ test_expect_success 'refresh the index before merging' '
git merge c3
'
-cat >expected <<EOF
-Merge branch 'c5' (early part)
+cat >expected.branch <<\EOF
+Merge branch 'c5-branch' (early part)
+EOF
+cat >expected.tag <<\EOF
+Merge commit 'c5~1'
EOF
test_expect_success 'merge early part of c2' '
git reset --hard c3 &&
- echo c4 > c4.c &&
+ echo c4 >c4.c &&
git add c4.c &&
git commit -m c4 &&
git tag c4 &&
- echo c5 > c5.c &&
+ echo c5 >c5.c &&
git add c5.c &&
git commit -m c5 &&
git tag c5 &&
git reset --hard c3 &&
- echo c6 > c6.c &&
+ echo c6 >c6.c &&
git add c6.c &&
git commit -m c6 &&
git tag c6 &&
+ git branch -f c5-branch c5 &&
+ git merge c5-branch~1 &&
+ git show -s --pretty=format:%s HEAD >actual.branch &&
+ git reset --keep HEAD^ &&
git merge c5~1 &&
- git show -s --pretty=format:%s HEAD > actual &&
- test_cmp actual expected
+ git show -s --pretty=format:%s HEAD >actual.tag &&
+ test_cmp expected.branch actual.branch &&
+ test_cmp expected.tag actual.tag
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'merge --no-ff --no-commit && commit' '
git reset --hard c0 &&
@@ -591,13 +540,13 @@ test_expect_success 'merge --no-ff --no-commit && commit' '
verify_parents $c0 $c1
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_expect_success 'amending no-ff merge commit' '
EDITOR=: git commit --amend &&
verify_parents $c0 $c1
'
-test_debug 'gitk --all'
+test_debug 'git log --graph --decorate --oneline --all'
test_done
diff --git a/t/t7606-merge-custom.sh b/t/t7606-merge-custom.sh
index 52a451dd5..8e8c4d724 100755
--- a/t/t7606-merge-custom.sh
+++ b/t/t7606-merge-custom.sh
@@ -1,49 +1,93 @@
#!/bin/sh
-test_description='git merge
+test_description="git merge
-Testing a custom strategy.'
+Testing a custom strategy.
+
+* (HEAD, master) Merge commit 'c3'
+|\
+| * (tag: c3) c3
+* | (tag: c1) c1
+|/
+| * tag: c2) c2
+|/
+* (tag: c0) c0
+"
. ./test-lib.sh
-cat >git-merge-theirs <<EOF
-#!$SHELL_PATH
-eval git read-tree --reset -u \\\$\$#
-EOF
-chmod +x git-merge-theirs
-PATH=.:$PATH
-export PATH
+test_expect_success 'set up custom strategy' '
+ cat >git-merge-theirs <<-EOF &&
+ #!$SHELL_PATH
+ eval git read-tree --reset -u \\\$\$#
+ EOF
+
+ chmod +x git-merge-theirs &&
+ PATH=.:$PATH &&
+ export PATH
+'
test_expect_success 'setup' '
- echo c0 >c0.c &&
- git add c0.c &&
- git commit -m c0 &&
- git tag c0 &&
- echo c1 >c1.c &&
- git add c1.c &&
- git commit -m c1 &&
- git tag c1 &&
- git reset --hard c0 &&
+ test_commit c0 c0.c &&
+ test_commit c1 c1.c &&
+ git reset --keep c0 &&
echo c1c1 >c1.c &&
- echo c2 >c2.c &&
- git add c1.c c2.c &&
- git commit -m c2 &&
- git tag c2
+ git add c1.c &&
+ test_commit c2 c2.c &&
+ git reset --keep c0 &&
+ test_commit c3 c3.c
'
test_expect_success 'merge c2 with a custom strategy' '
git reset --hard c1 &&
+
+ git rev-parse c1 >head.old &&
+ git rev-parse c2 >second-parent.expected &&
+ git rev-parse c2^{tree} >tree.expected &&
git merge -s theirs c2 &&
- test "$(git rev-parse c1)" != "$(git rev-parse HEAD)" &&
- test "$(git rev-parse c1)" = "$(git rev-parse HEAD^1)" &&
- test "$(git rev-parse c2)" = "$(git rev-parse HEAD^2)" &&
- test "$(git rev-parse c2^{tree})" = "$(git rev-parse HEAD^{tree})" &&
+
+ git rev-parse HEAD >head.new &&
+ git rev-parse HEAD^1 >first-parent &&
+ git rev-parse HEAD^2 >second-parent &&
+ git rev-parse HEAD^{tree} >tree &&
+ git update-index --refresh &&
git diff --exit-code &&
git diff --exit-code c2 HEAD &&
git diff --exit-code c2 &&
+
+ ! test_cmp head.old head.new &&
+ test_cmp head.old first-parent &&
+ test_cmp second-parent.expected second-parent &&
+ test_cmp tree.expected tree &&
test -f c0.c &&
grep c1c1 c1.c &&
test -f c2.c
'
+test_expect_success 'trivial merge with custom strategy' '
+ git reset --hard c1 &&
+
+ git rev-parse c1 >head.old &&
+ git rev-parse c3 >second-parent.expected &&
+ git rev-parse c3^{tree} >tree.expected &&
+ git merge -s theirs c3 &&
+
+ git rev-parse HEAD >head.new &&
+ git rev-parse HEAD^1 >first-parent &&
+ git rev-parse HEAD^2 >second-parent &&
+ git rev-parse HEAD^{tree} >tree &&
+ git update-index --refresh &&
+ git diff --exit-code &&
+ git diff --exit-code c3 HEAD &&
+ git diff --exit-code c3 &&
+
+ ! test_cmp head.old head.new &&
+ test_cmp head.old first-parent &&
+ test_cmp second-parent.expected second-parent &&
+ test_cmp tree.expected tree &&
+ test -f c0.c &&
+ ! test -e c1.c &&
+ test -f c3.c
+'
+
test_done
diff --git a/t/t7609-merge-co-error-msgs.sh b/t/t7609-merge-co-error-msgs.sh
new file mode 100755
index 000000000..1a109b41d
--- /dev/null
+++ b/t/t7609-merge-co-error-msgs.sh
@@ -0,0 +1,125 @@
+#!/bin/sh
+
+test_description='unpack-trees error messages'
+
+. ./test-lib.sh
+
+
+test_expect_success 'setup' '
+ echo one >one &&
+ git add one &&
+ git commit -a -m First &&
+
+ git checkout -b branch &&
+ echo two >two &&
+ echo three >three &&
+ echo four >four &&
+ echo five >five &&
+ git add two three four five &&
+ git commit -m Second &&
+
+ git checkout master &&
+ echo other >two &&
+ echo other >three &&
+ echo other >four &&
+ echo other >five
+'
+
+cat >expect <<\EOF
+error: The following untracked working tree files would be overwritten by merge:
+ two
+ three
+ four
+ five
+Please move or remove them before you can merge.
+EOF
+
+test_expect_success 'untracked files overwritten by merge' '
+ test_must_fail git merge branch 2>out &&
+ test_cmp out expect
+'
+
+cat >expect <<\EOF
+error: Your local changes to the following files would be overwritten by merge:
+ two
+ three
+ four
+Please, commit your changes or stash them before you can merge.
+error: The following untracked working tree files would be overwritten by merge:
+ five
+Please move or remove them before you can merge.
+EOF
+
+test_expect_success 'untracked files or local changes ovewritten by merge' '
+ git add two &&
+ git add three &&
+ git add four &&
+ test_must_fail git merge branch 2>out &&
+ test_cmp out expect
+'
+
+cat >expect <<\EOF
+error: Your local changes to the following files would be overwritten by checkout:
+ rep/two
+ rep/one
+Please, commit your changes or stash them before you can switch branches.
+EOF
+
+test_expect_success 'cannot switch branches because of local changes' '
+ git add five &&
+ mkdir rep &&
+ echo one >rep/one &&
+ echo two >rep/two &&
+ git add rep/one rep/two &&
+ git commit -m Fourth &&
+ git checkout master &&
+ echo uno >rep/one &&
+ echo dos >rep/two &&
+ test_must_fail git checkout branch 2>out &&
+ test_cmp out expect
+'
+
+cat >expect <<\EOF
+error: Your local changes to the following files would be overwritten by checkout:
+ rep/two
+ rep/one
+Please, commit your changes or stash them before you can switch branches.
+EOF
+
+test_expect_success 'not uptodate file porcelain checkout error' '
+ git add rep/one rep/two &&
+ test_must_fail git checkout branch 2>out &&
+ test_cmp out expect
+'
+
+cat >expect <<\EOF
+error: Updating the following directories would lose untracked files in it:
+ rep2
+ rep
+
+EOF
+
+test_expect_success 'not_uptodate_dir porcelain checkout error' '
+ git init uptodate &&
+ cd uptodate &&
+ mkdir rep &&
+ mkdir rep2 &&
+ touch rep/foo &&
+ touch rep2/foo &&
+ git add rep/foo rep2/foo &&
+ git commit -m init &&
+ git checkout -b branch &&
+ git rm rep -r &&
+ git rm rep2 -r &&
+ >rep &&
+ >rep2 &&
+ git add rep rep2&&
+ git commit -m "added test as a file" &&
+ git checkout master &&
+ >rep/untracked-file &&
+ >rep2/untracked-file &&
+ test_must_fail git checkout branch 2>out &&
+ test_cmp out ../expect
+'
+
+test_done
diff --git a/t/t7610-mergetool.sh b/t/t7610-mergetool.sh
index f5a7bf47e..3bd74042e 100755
--- a/t/t7610-mergetool.sh
+++ b/t/t7610-mergetool.sh
@@ -68,22 +68,24 @@ test_expect_success 'mergetool crlf' '
'
test_expect_success 'mergetool in subdir' '
- git checkout -b test3 branch1
- cd subdir && (
- test_must_fail git merge master >/dev/null 2>&1 &&
- ( yes "" | git mergetool file3 >/dev/null 2>&1 ) &&
- test "$(cat file3)" = "master new sub") &&
- cd ..
+ git checkout -b test3 branch1 &&
+ (
+ cd subdir &&
+ test_must_fail git merge master >/dev/null 2>&1 &&
+ ( yes "" | git mergetool file3 >/dev/null 2>&1 ) &&
+ test "$(cat file3)" = "master new sub"
+ )
'
test_expect_success 'mergetool on file in parent dir' '
- cd subdir && (
- ( yes "" | git mergetool ../file1 >/dev/null 2>&1 ) &&
- ( yes "" | git mergetool ../file2 >/dev/null 2>&1 ) &&
- test "$(cat ../file1)" = "master updated" &&
- test "$(cat ../file2)" = "master new" &&
- git commit -m "branch1 resolved with mergetool - subdir") &&
- cd ..
+ (
+ cd subdir &&
+ ( yes "" | git mergetool ../file1 >/dev/null 2>&1 ) &&
+ ( yes "" | git mergetool ../file2 >/dev/null 2>&1 ) &&
+ test "$(cat ../file1)" = "master updated" &&
+ test "$(cat ../file2)" = "master new" &&
+ git commit -m "branch1 resolved with mergetool - subdir"
+ )
'
test_expect_success 'mergetool skips autoresolved' '
@@ -96,16 +98,17 @@ test_expect_success 'mergetool skips autoresolved' '
'
test_expect_success 'mergetool merges all from subdir' '
- cd subdir && (
- git config rerere.enabled false &&
- test_must_fail git merge master &&
- git mergetool --no-prompt &&
- test "$(cat ../file1)" = "master updated" &&
- test "$(cat ../file2)" = "master new" &&
- test "$(cat file3)" = "master new sub" &&
- git add ../file1 ../file2 file3 &&
- git commit -m "branch2 resolved by mergetool from subdir") &&
- cd ..
+ (
+ cd subdir &&
+ git config rerere.enabled false &&
+ test_must_fail git merge master &&
+ git mergetool --no-prompt &&
+ test "$(cat ../file1)" = "master updated" &&
+ test "$(cat ../file2)" = "master new" &&
+ test "$(cat file3)" = "master new sub" &&
+ git add ../file1 ../file2 file3 &&
+ git commit -m "branch2 resolved by mergetool from subdir"
+ )
'
test_done
diff --git a/t/t9010-svn-fe.sh b/t/t9010-svn-fe.sh
new file mode 100755
index 000000000..a713dfc50
--- /dev/null
+++ b/t/t9010-svn-fe.sh
@@ -0,0 +1,32 @@
+#!/bin/sh
+
+test_description='check svn dumpfile importer'
+
+. ./lib-git-svn.sh
+
+test_dump() {
+ label=$1
+ dump=$2
+ test_expect_success "$dump" '
+ svnadmin create "$label-svn" &&
+ svnadmin load "$label-svn" < "$TEST_DIRECTORY/$dump" &&
+ svn_cmd export "file://$PWD/$label-svn" "$label-svnco" &&
+ git init "$label-git" &&
+ test-svn-fe "$TEST_DIRECTORY/$dump" >"$label.fe" &&
+ (
+ cd "$label-git" &&
+ git fast-import < ../"$label.fe"
+ ) &&
+ (
+ cd "$label-svnco" &&
+ git init &&
+ git add . &&
+ git fetch "../$label-git" master &&
+ git diff --exit-code FETCH_HEAD
+ )
+ '
+}
+
+test_dump simple t9135/svn.dump
+
+test_done
diff --git a/t/t9350-fast-export.sh b/t/t9350-fast-export.sh
index d43f37cca..8c8e67946 100755
--- a/t/t9350-fast-export.sh
+++ b/t/t9350-fast-export.sh
@@ -355,6 +355,20 @@ test_expect_failure 'no exact-ref revisions included' '
)
'
+test_expect_success 'path limiting with import-marks does not lose unmodified files' '
+ git checkout -b simple marks~2 &&
+ git fast-export --export-marks=marks simple -- file > /dev/null &&
+ echo more content >> file &&
+ test_tick &&
+ git commit -mnext file &&
+ git fast-export --import-marks=marks simple -- file file0 | grep file0
+'
+
+test_expect_success 'full-tree re-shows unmodified files' '
+ git checkout -f simple &&
+ test $(git fast-export --full-tree simple | grep -c file0) -eq 3
+'
+
test_expect_success 'set-up a few more tags for tag export tests' '
git checkout -f master &&
HEAD_TREE=`git show -s --pretty=raw HEAD | grep tree | sed "s/tree //"` &&
@@ -376,4 +390,28 @@ test_expect_success 'tree_tag-obj' 'git fast-export tree_tag-obj'
test_expect_success 'tag-obj_tag' 'git fast-export tag-obj_tag'
test_expect_success 'tag-obj_tag-obj' 'git fast-export tag-obj_tag-obj'
+test_expect_success SYMLINKS 'directory becomes symlink' '
+ git init dirtosymlink &&
+ git init result &&
+ (
+ cd dirtosymlink &&
+ mkdir foo &&
+ mkdir bar &&
+ echo hello > foo/world &&
+ echo hello > bar/world &&
+ git add foo/world bar/world &&
+ git commit -q -mone &&
+ git rm -r foo &&
+ ln -s bar foo &&
+ git add foo &&
+ git commit -q -mtwo
+ ) &&
+ (
+ cd dirtosymlink &&
+ git fast-export master -- foo |
+ (cd ../result && git fast-import --quiet)
+ ) &&
+ (cd result && git show master:foo)
+'
+
test_done
diff --git a/t/test-lib.sh b/t/test-lib.sh
index 29fd7209c..3a3d4c472 100644
--- a/t/test-lib.sh
+++ b/t/test-lib.sh
@@ -545,6 +545,38 @@ test_external_without_stderr () {
fi
}
+# debugging-friendly alternatives to "test [-f|-d|-e]"
+# The commands test the existence or non-existence of $1. $2 can be
+# given to provide a more precise diagnosis.
+test_path_is_file () {
+ if ! [ -f "$1" ]
+ then
+ echo "File $1 doesn't exist. $*"
+ false
+ fi
+}
+
+test_path_is_dir () {
+ if ! [ -d "$1" ]
+ then
+ echo "Directory $1 doesn't exist. $*"
+ false
+ fi
+}
+
+test_path_is_missing () {
+ if [ -e "$1" ]
+ then
+ echo "Path exists:"
+ ls -ld "$1"
+ if [ $# -ge 1 ]; then
+ echo "$*"
+ fi
+ false
+ fi
+}
+
+
# This is not among top-level (test_expect_success | test_expect_failure)
# but is a prefix that can be used in the test script, like:
#