diff options
-rw-r--r-- | builtin/am.c | 1 | ||||
-rw-r--r-- | merge-recursive.c | 18 | ||||
-rw-r--r-- | merge-recursive.h | 1 | ||||
-rwxr-xr-x | t/t3401-rebase-and-am-rename.sh | 110 |
4 files changed, 124 insertions, 6 deletions
diff --git a/builtin/am.c b/builtin/am.c index 9f7ecf6ecb..5e866d17c7 100644 --- a/builtin/am.c +++ b/builtin/am.c @@ -1598,6 +1598,7 @@ static int fall_back_threeway(const struct am_state *state, const char *index_pa o.branch1 = "HEAD"; their_tree_name = xstrfmt("%.*s", linelen(state->msg), state->msg); o.branch2 = their_tree_name; + o.detect_directory_renames = 0; if (state->quiet) o.verbosity = 0; diff --git a/merge-recursive.c b/merge-recursive.c index dcdc93019c..e5243dbc54 100644 --- a/merge-recursive.c +++ b/merge-recursive.c @@ -2869,12 +2869,19 @@ static int detect_and_process_renames(struct merge_options *o, head_pairs = get_diffpairs(o, common, head); merge_pairs = get_diffpairs(o, common, merge); - dir_re_head = get_directory_renames(head_pairs, head); - dir_re_merge = get_directory_renames(merge_pairs, merge); + if (o->detect_directory_renames) { + dir_re_head = get_directory_renames(head_pairs, head); + dir_re_merge = get_directory_renames(merge_pairs, merge); - handle_directory_level_conflicts(o, - dir_re_head, head, - dir_re_merge, merge); + handle_directory_level_conflicts(o, + dir_re_head, head, + dir_re_merge, merge); + } else { + dir_re_head = xmalloc(sizeof(*dir_re_head)); + dir_re_merge = xmalloc(sizeof(*dir_re_merge)); + dir_rename_init(dir_re_head); + dir_rename_init(dir_re_merge); + } ri->head_renames = get_renames(o, head_pairs, dir_re_merge, dir_re_head, head, @@ -3586,6 +3593,7 @@ void init_merge_options(struct merge_options *o) o->renormalize = 0; o->diff_detect_rename = -1; o->merge_detect_rename = -1; + o->detect_directory_renames = 1; merge_recursive_config(o); merge_verbosity = getenv("GIT_MERGE_VERBOSITY"); if (merge_verbosity) diff --git a/merge-recursive.h b/merge-recursive.h index 0c46a5a4ff..e6a0828eca 100644 --- a/merge-recursive.h +++ b/merge-recursive.h @@ -20,6 +20,7 @@ struct merge_options { unsigned renormalize : 1; long xdl_opts; int verbosity; + int detect_directory_renames; int diff_detect_rename; int merge_detect_rename; int diff_rename_limit; diff --git a/t/t3401-rebase-and-am-rename.sh b/t/t3401-rebase-and-am-rename.sh index 8f832957fc..e0b5111993 100755 --- a/t/t3401-rebase-and-am-rename.sh +++ b/t/t3401-rebase-and-am-rename.sh @@ -5,7 +5,7 @@ test_description='git rebase + directory rename tests' . ./test-lib.sh . "$TEST_DIRECTORY"/lib-rebase.sh -test_expect_success 'setup testcase' ' +test_expect_success 'setup testcase where directory rename should be detected' ' test_create_repo dir-rename && ( cd dir-rename && @@ -102,4 +102,112 @@ test_expect_failure 'am: directory rename detected' ' ) ' +test_expect_success 'setup testcase where directory rename should NOT be detected' ' + test_create_repo no-dir-rename && + ( + cd no-dir-rename && + + mkdir x && + test_seq 1 10 >x/a && + test_seq 11 20 >x/b && + test_seq 21 30 >x/c && + echo original >project_info && + git add x project_info && + git commit -m "Initial" && + + git branch O && + git branch A && + git branch B && + + git checkout A && + echo v2 >project_info && + git add project_info && + git commit -m "Modify project_info" && + + git checkout B && + mkdir y && + git mv x/c y/c && + echo v1 >project_info && + git add project_info && + git commit -m "Rename x/c to y/c, modify project_info" + ) +' + +test_expect_success 'rebase --interactive: NO directory rename' ' + test_when_finished "git -C no-dir-rename rebase --abort" && + ( + cd no-dir-rename && + + git checkout B^0 && + + set_fake_editor && + test_must_fail env FAKE_LINES="1" git rebase --interactive A && + + git ls-files -s >out && + test_line_count = 6 out && + + test_path_is_file x/a && + test_path_is_file x/b && + test_path_is_missing x/c + ) +' + +test_expect_success 'rebase (am): NO directory rename' ' + test_when_finished "git -C no-dir-rename rebase --abort" && + ( + cd no-dir-rename && + + git checkout B^0 && + + set_fake_editor && + test_must_fail git rebase A && + + git ls-files -s >out && + test_line_count = 6 out && + + test_path_is_file x/a && + test_path_is_file x/b && + test_path_is_missing x/c + ) +' + +test_expect_success 'rebase --merge: NO directory rename' ' + test_when_finished "git -C no-dir-rename rebase --abort" && + ( + cd no-dir-rename && + + git checkout B^0 && + + set_fake_editor && + test_must_fail git rebase --merge A && + + git ls-files -s >out && + test_line_count = 6 out && + + test_path_is_file x/a && + test_path_is_file x/b && + test_path_is_missing x/c + ) +' + +test_expect_success 'am: NO directory rename' ' + test_when_finished "git -C no-dir-rename am --abort" && + ( + cd no-dir-rename && + + git checkout A^0 && + + git format-patch -1 B && + + test_must_fail git am --3way 0001*.patch && + + git ls-files -s >out && + test_line_count = 6 out && + + test_path_is_file x/a && + test_path_is_file x/b && + test_path_is_missing x/c + ) +' + test_done |