summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLibravatar Brandon Williams <bmwill@google.com>2017-06-14 11:07:38 -0700
committerLibravatar Junio C Hamano <gitster@pobox.com>2017-06-15 12:56:22 -0700
commita577fb5fdc53a4729eeedc2922d1461350b92f73 (patch)
tree15197dd21a7820432815f55a2e88a38766dd99a3
parentsetup: teach discover_git_directory to respect the commondir (diff)
downloadtgif-a577fb5fdc53a4729eeedc2922d1461350b92f73.tar.xz
config: respect commondir
Worktrees present an interesting problem when it comes to the config. Historically we could assume that the per-repository config lives at 'gitdir/config', but since worktrees were introduced this isn't the case anymore. There is currently no way to specify per-worktree configuration, and as such the repository config is shared with all worktrees and is located at 'commondir/config'. Many users of the config machinery correctly set 'config_options.git_dir' with the repository's commondir, allowing the config to be properly loaded when operating in a worktree. But other's, like 'read_early_config()', set 'config_options.git_dir' with the repository's gitdir which can be incorrect when using worktrees. To fix this issue, and to make things less ambiguous, lets add a 'commondir' field to the 'config_options' struct and have all callers properly set both the 'git_dir' and 'commondir' fields so that the config machinery is able to properly find the repository's config. Signed-off-by: Brandon Williams <bmwill@google.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
-rw-r--r--config.c11
-rw-r--r--config.h1
2 files changed, 8 insertions, 4 deletions
diff --git a/config.c b/config.c
index e8dbf9e64a..edc0d17708 100644
--- a/config.c
+++ b/config.c
@@ -1531,8 +1531,8 @@ static int do_git_config_sequence(const struct config_options *opts,
char *user_config = expand_user_path("~/.gitconfig", 0);
char *repo_config;
- if (opts->git_dir)
- repo_config = mkpathdup("%s/config", opts->git_dir);
+ if (opts->commondir)
+ repo_config = mkpathdup("%s/config", opts->commondir);
else if (have_git_dir())
repo_config = git_pathdup("config");
else
@@ -1644,7 +1644,8 @@ void read_early_config(config_fn_t cb, void *data)
opts.respect_includes = 1;
- if (have_git_dir())
+ if (have_git_dir()) {
+ opts.commondir = get_git_common_dir();
opts.git_dir = get_git_dir();
/*
* When setup_git_directory() was not yet asked to discover the
@@ -1654,8 +1655,10 @@ void read_early_config(config_fn_t cb, void *data)
* notably, the current working directory is still the same after the
* call).
*/
- else if (!discover_git_directory(&commondir, &gitdir))
+ } else if (!discover_git_directory(&commondir, &gitdir)) {
+ opts.commondir = commondir.buf;
opts.git_dir = gitdir.buf;
+ }
git_config_with_options(cb, data, NULL, &opts);
diff --git a/config.h b/config.h
index c70599bd5f..63b92784cd 100644
--- a/config.h
+++ b/config.h
@@ -30,6 +30,7 @@ enum config_origin_type {
struct config_options {
unsigned int respect_includes : 1;
+ const char *commondir;
const char *git_dir;
};