]> git.ipfire.org Git - thirdparty/git.git/commitdiff
config: add kvi.path, use it to evaluate includes
authorGlen Choo <chooglen@google.com>
Wed, 28 Jun 2023 19:26:29 +0000 (19:26 +0000)
committerJunio C Hamano <gitster@pobox.com>
Wed, 28 Jun 2023 21:06:40 +0000 (14:06 -0700)
Include directives are evaluated using the path of the config file. To
reduce the dependence on "config_reader.source", add a new
"key_value_info.path" member and use that instead of
"config_source.path". This allows us to remove a "struct config_reader
*" field from "struct config_include_data", which will subsequently
allow us to remove "struct config_reader" entirely.

Signed-off-by: Glen Choo <chooglen@google.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
config.c
config.h

index 50dbd89a6d6b13ea7e684247aeb57cbbf7327ae1..8d342d8425501269023db0460f347967470f8c43 100644 (file)
--- a/config.c
+++ b/config.c
@@ -162,7 +162,6 @@ struct config_include_data {
        const struct config_options *opts;
        struct git_config_source *config_source;
        struct repository *repo;
-       struct config_reader *config_reader;
 
        /*
         * All remote URLs discovered when reading all config files.
@@ -181,8 +180,7 @@ static const char include_depth_advice[] = N_(
 "from\n"
 "      %s\n"
 "This might be due to circular includes.");
-static int handle_path_include(struct config_source *cs,
-                              const struct key_value_info *kvi,
+static int handle_path_include(const struct key_value_info *kvi,
                               const char *path,
                               struct config_include_data *inc)
 {
@@ -205,14 +203,14 @@ static int handle_path_include(struct config_source *cs,
        if (!is_absolute_path(path)) {
                char *slash;
 
-               if (!cs || !cs->path) {
+               if (!kvi || !kvi->path) {
                        ret = error(_("relative config includes must come from files"));
                        goto cleanup;
                }
 
-               slash = find_last_dir_sep(cs->path);
+               slash = find_last_dir_sep(kvi->path);
                if (slash)
-                       strbuf_add(&buf, cs->path, slash - cs->path + 1);
+                       strbuf_add(&buf, kvi->path, slash - kvi->path + 1);
                strbuf_addstr(&buf, path);
                path = buf.buf;
        }
@@ -220,8 +218,8 @@ static int handle_path_include(struct config_source *cs,
        if (!access_or_die(path, R_OK, 0)) {
                if (++inc->depth > MAX_INCLUDE_DEPTH)
                        die(_(include_depth_advice), MAX_INCLUDE_DEPTH, path,
-                           !cs ? "<unknown>" :
-                           cs->name ? cs->name :
+                           !kvi ? "<unknown>" :
+                           kvi->filename ? kvi->filename :
                            "the command line");
                ret = git_config_from_file_with_options(git_config_include, path, inc,
                                                        kvi->scope, NULL);
@@ -239,7 +237,7 @@ static void add_trailing_starstar_for_dir(struct strbuf *pat)
                strbuf_addstr(pat, "**");
 }
 
-static int prepare_include_condition_pattern(struct config_source *cs,
+static int prepare_include_condition_pattern(const struct key_value_info *kvi,
                                             struct strbuf *pat)
 {
        struct strbuf path = STRBUF_INIT;
@@ -256,11 +254,11 @@ static int prepare_include_condition_pattern(struct config_source *cs,
        if (pat->buf[0] == '.' && is_dir_sep(pat->buf[1])) {
                const char *slash;
 
-               if (!cs || !cs->path)
+               if (!kvi || !kvi->path)
                        return error(_("relative config include "
                                       "conditionals must come from files"));
 
-               strbuf_realpath(&path, cs->path, 1);
+               strbuf_realpath(&path, kvi->path, 1);
                slash = find_last_dir_sep(path.buf);
                if (!slash)
                        BUG("how is this possible?");
@@ -275,7 +273,7 @@ static int prepare_include_condition_pattern(struct config_source *cs,
        return prefix;
 }
 
-static int include_by_gitdir(struct config_source *cs,
+static int include_by_gitdir(const struct key_value_info *kvi,
                             const struct config_options *opts,
                             const char *cond, size_t cond_len, int icase)
 {
@@ -292,7 +290,7 @@ static int include_by_gitdir(struct config_source *cs,
 
        strbuf_realpath(&text, git_dir, 1);
        strbuf_add(&pattern, cond, cond_len);
-       prefix = prepare_include_condition_pattern(cs, &pattern);
+       prefix = prepare_include_condition_pattern(kvi, &pattern);
 
 again:
        if (prefix < 0)
@@ -428,16 +426,16 @@ static int include_by_remote_url(struct config_include_data *inc,
                                             inc->remote_urls);
 }
 
-static int include_condition_is_true(struct config_source *cs,
+static int include_condition_is_true(const struct key_value_info *kvi,
                                     struct config_include_data *inc,
                                     const char *cond, size_t cond_len)
 {
        const struct config_options *opts = inc->opts;
 
        if (skip_prefix_mem(cond, cond_len, "gitdir:", &cond, &cond_len))
-               return include_by_gitdir(cs, opts, cond, cond_len, 0);
+               return include_by_gitdir(kvi, opts, cond, cond_len, 0);
        else if (skip_prefix_mem(cond, cond_len, "gitdir/i:", &cond, &cond_len))
-               return include_by_gitdir(cs, opts, cond, cond_len, 1);
+               return include_by_gitdir(kvi, opts, cond, cond_len, 1);
        else if (skip_prefix_mem(cond, cond_len, "onbranch:", &cond, &cond_len))
                return include_by_branch(cond, cond_len);
        else if (skip_prefix_mem(cond, cond_len, "hasconfig:remote.*.url:", &cond,
@@ -453,7 +451,6 @@ static int git_config_include(const char *var, const char *value,
                              void *data)
 {
        struct config_include_data *inc = data;
-       struct config_source *cs = inc->config_reader->source;
        const char *cond, *key;
        size_t cond_len;
        int ret;
@@ -467,16 +464,16 @@ static int git_config_include(const char *var, const char *value,
                return ret;
 
        if (!strcmp(var, "include.path"))
-               ret = handle_path_include(cs, ctx->kvi, value, inc);
+               ret = handle_path_include(ctx->kvi, value, inc);
 
        if (!parse_config_key(var, "includeif", &cond, &cond_len, &key) &&
-           cond && include_condition_is_true(cs, inc, cond, cond_len) &&
+           cond && include_condition_is_true(ctx->kvi, inc, cond, cond_len) &&
            !strcmp(key, "path")) {
                config_fn_t old_fn = inc->fn;
 
                if (inc->opts->unconditional_remote_url)
                        inc->fn = forbid_remote_url;
-               ret = handle_path_include(cs, ctx->kvi, value, inc);
+               ret = handle_path_include(ctx->kvi, value, inc);
                inc->fn = old_fn;
        }
 
@@ -661,6 +658,7 @@ void kvi_from_param(struct key_value_info *out)
        out->linenr = -1;
        out->origin_type = CONFIG_ORIGIN_CMDLINE;
        out->scope = CONFIG_SCOPE_COMMAND;
+       out->path = NULL;
 }
 
 int git_config_parse_parameter(const char *text,
@@ -1064,6 +1062,7 @@ static void kvi_from_source(struct config_source *cs,
        out->origin_type = cs->origin_type;
        out->linenr = cs->linenr;
        out->scope = scope;
+       out->path = cs->path;
 }
 
 static int git_parse_source(struct config_source *cs, config_fn_t fn,
@@ -2282,7 +2281,6 @@ int config_with_options(config_fn_t fn, void *data,
                inc.opts = opts;
                inc.repo = repo;
                inc.config_source = config_source;
-               inc.config_reader = &the_reader;
                fn = git_config_include;
                data = &inc;
        }
index bd366ddb5ef0bc311b91f4ae4fd26414683d4a93..b5573e67a00440e2eb0ba0e737087ef6db14d2e3 100644 (file)
--- a/config.h
+++ b/config.h
@@ -116,12 +116,14 @@ struct key_value_info {
        int linenr;
        enum config_origin_type origin_type;
        enum config_scope scope;
+       const char *path;
 };
 #define KVI_INIT { \
        .filename = NULL, \
        .linenr = -1, \
        .origin_type = CONFIG_ORIGIN_UNKNOWN, \
        .scope = CONFIG_SCOPE_UNKNOWN, \
+       .path = NULL, \
 }
 
 /* Captures additional information that a config callback can use. */