summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Documentation/config/checkout.txt7
-rw-r--r--builtin/checkout.c8
-rwxr-xr-xt/t2025-checkout-no-overlay.sh10
3 files changed, 24 insertions, 1 deletions
diff --git a/Documentation/config/checkout.txt b/Documentation/config/checkout.txt
index c4118fa196..73380a8d86 100644
--- a/Documentation/config/checkout.txt
+++ b/Documentation/config/checkout.txt
@@ -21,3 +21,10 @@ checkout.optimizeNewBranch::
will not update the skip-worktree bit in the index nor add/remove
files in the working directory to reflect the current sparse checkout
settings nor will it show the local changes.
+
+checkout.overlayMode::
+ In the default overlay mode, `git checkout` never
+ removes files from the index or the working tree. When
+ setting `checkout.overlayMode` to false, files that appear in
+ the index and working tree, but not in <tree-ish> are removed,
+ to make them match <tree-ish> exactly.
diff --git a/builtin/checkout.c b/builtin/checkout.c
index 0c5fe948ef..b5dfc45736 100644
--- a/builtin/checkout.c
+++ b/builtin/checkout.c
@@ -1019,13 +1019,19 @@ static int switch_branches(const struct checkout_opts *opts,
static int git_checkout_config(const char *var, const char *value, void *cb)
{
+ struct checkout_opts *opts = cb;
+
if (!strcmp(var, "checkout.optimizenewbranch")) {
checkout_optimize_new_branch = git_config_bool(var, value);
return 0;
}
+ if (!strcmp(var, "checkout.overlaymode")) {
+ opts->overlay_mode = git_config_bool(var, value);
+ return 0;
+ }
+
if (!strcmp(var, "diff.ignoresubmodules")) {
- struct checkout_opts *opts = cb;
handle_ignore_submodules_arg(&opts->diff_options, value);
return 0;
}
diff --git a/t/t2025-checkout-no-overlay.sh b/t/t2025-checkout-no-overlay.sh
index 76330cb5ab..a4912e35cb 100755
--- a/t/t2025-checkout-no-overlay.sh
+++ b/t/t2025-checkout-no-overlay.sh
@@ -44,4 +44,14 @@ test_expect_success '--no-overlay --theirs with D/F conflict deletes file' '
test_path_is_missing file1
'
+test_expect_success 'checkout with checkout.overlayMode=false deletes files not in <tree-ish>' '
+ >file &&
+ mkdir dir &&
+ >dir/file1 &&
+ git add file dir/file1 &&
+ git -c checkout.overlayMode=false checkout HEAD -- file &&
+ test_path_is_missing file &&
+ test_path_is_file dir/file1
+'
+
test_done