git@vger.kernel.org mailing list mirror (one of many)
 help / color / mirror / code / Atom feed
From: Jeff King <peff@peff.net>
To: Junio C Hamano <gitster@pobox.com>
Cc: git@vger.kernel.org, Alex Riesen <raa.lkml@gmail.com>,
	Christian Couder <chriscool@tuxfamily.org>,
	Jonathan Nieder <jrnieder@gmail.com>
Subject: Re: "git -c web.browser=w3m help -w help" still kicks firefox
Date: Mon, 23 Aug 2010 15:16:00 -0400	[thread overview]
Message-ID: <20100823191600.GA2523@coredump.intra.peff.net> (raw)
In-Reply-To: <20100823183857.GA22386@coredump.intra.peff.net>

On Mon, Aug 23, 2010 at 02:38:57PM -0400, Jeff King wrote:

> The environment is the only sensible way to pass this down, because we
> need to hit not just externals, but things like "git config" invocations
> from shell scripts. IOW, "git -c" really is about executing in a
> sub-environment that pretends that config is set. Obviously we would
> need to quote and unquote when using the environment as a transport (or
> do something horrible like making a temporary config file and pointing
> at it through the environment).

Here's a first attempt. No idea if it has any bad side effects. :)

-- >8 --
Subject: [PATCH] pass "git -c foo=bar" params through environment

Git uses the "-c foo=bar" parameters to set a config
variable for a single git invocation. We currently do this
by making a list in the current process and consulting that
list in git_config.

This works fine for built-ins, but the config changes are
silently ignored by subprocesses, including dashed externals
and invocations to "git config" from shell scripts.

This patch instead puts them in an environment variable
which we consult when looking at config (both internally and
via calls "git config").

Signed-off-by: Jeff King <peff@peff.net>
---
 cache.h  |    2 ++
 config.c |   57 ++++++++++++++++++++++++++++++++++++++++++++++++++++++---
 git.c    |    2 +-
 3 files changed, 57 insertions(+), 4 deletions(-)

diff --git a/cache.h b/cache.h
index d8c0a98..b76d7b3 100644
--- a/cache.h
+++ b/cache.h
@@ -974,7 +974,9 @@ extern int update_server_info(int);
 typedef int (*config_fn_t)(const char *, const char *, void *);
 extern int git_default_config(const char *, const char *, void *);
 extern int git_config_from_file(config_fn_t fn, const char *, void *);
+extern void git_config_push_parameter(const char *text);
 extern int git_config_parse_parameter(const char *text);
+extern int git_config_parse_environment(void);
 extern int git_config_from_parameters(config_fn_t fn, void *data);
 extern int git_config(config_fn_t fn, void *);
 extern int git_parse_ulong(const char *, unsigned long *);
diff --git a/config.c b/config.c
index 7a18bc9..15eabaf 100644
--- a/config.c
+++ b/config.c
@@ -8,6 +8,7 @@
 #include "cache.h"
 #include "exec_cmd.h"
 #include "strbuf.h"
+#include "quote.h"
 
 #define MAXNAME (256)
 
@@ -34,6 +35,19 @@ static void lowercase(char *p)
 		*p = tolower(*p);
 }
 
+void git_config_push_parameter(const char *text)
+{
+	struct strbuf env = STRBUF_INIT;
+	const char *old = getenv("GIT_CONFIG_PARAMETERS");
+	if (old) {
+		strbuf_addstr(&env, old);
+		strbuf_addch(&env, ' ');
+	}
+	sq_quote_buf(&env, text);
+	setenv("GIT_CONFIG_PARAMETERS", env.buf, 1);
+	strbuf_release(&env);
+}
+
 int git_config_parse_parameter(const char *text)
 {
 	struct config_item *ct;
@@ -61,6 +75,37 @@ int git_config_parse_parameter(const char *text)
 	return 0;
 }
 
+int git_config_parse_environment(void) {
+	const char *env = getenv("GIT_CONFIG_PARAMETERS");
+	char *envw;
+	const char **argv = NULL;
+	int nr = 0, alloc = 0;
+	int i;
+
+	if (!env)
+		return 0;
+	/* sq_dequote will write over it */
+	envw = xstrdup(env);
+
+	if (sq_dequote_to_argv(envw, &argv, &nr, &alloc) < 0) {
+		free(envw);
+		return error("bogus format in GIT_CONFIG_PARAMETERS");
+	}
+
+	for (i = 0; i < nr; i++) {
+		if (git_config_parse_parameter(argv[i]) < 0) {
+			error("bogus config parameter: %s", argv[i]);
+			free(argv);
+			free(envw);
+			return -1;
+		}
+	}
+
+	free(argv);
+	free(envw);
+	return 0;
+}
+
 static int get_next_char(void)
 {
 	int c;
@@ -781,7 +826,14 @@ int git_config_global(void)
 
 int git_config_from_parameters(config_fn_t fn, void *data)
 {
+	static int loaded_environment;
 	const struct config_item *ct;
+
+	if (!loaded_environment) {
+		if (git_config_parse_environment() < 0)
+			return -1;
+		loaded_environment = 1;
+	}
 	for (ct = config_parameters; ct; ct = ct->next)
 		if (fn(ct->name, ct->value, data) < 0)
 			return -1;
@@ -820,10 +872,9 @@ int git_config(config_fn_t fn, void *data)
 	}
 	free(repo_config);
 
-	if (config_parameters) {
-		ret += git_config_from_parameters(fn, data);
+	ret += git_config_from_parameters(fn, data);
+	if (config_parameters)
 		found += 1;
-	}
 
 	if (found == 0)
 		return -1;
diff --git a/git.c b/git.c
index 8dda939..681f96c 100644
--- a/git.c
+++ b/git.c
@@ -137,7 +137,7 @@ static int handle_options(const char ***argv, int *argc, int *envchanged)
 				fprintf(stderr, "-c expects a configuration string\n" );
 				usage(git_usage_string);
 			}
-			git_config_parse_parameter((*argv)[1]);
+			git_config_push_parameter((*argv)[1]);
 			(*argv)++;
 			(*argc)--;
 		} else {
-- 
1.7.2.2.418.g55566.dirty

  reply	other threads:[~2010-08-23 19:16 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2010-08-23 18:05 "git -c web.browser=w3m help -w help" still kicks firefox Junio C Hamano
2010-08-23 18:38 ` Jeff King
2010-08-23 19:16   ` Jeff King [this message]
2010-08-24  6:41     ` [PATCH 2/1] do not pass "git -c foo=bar" params to transport helpers Jonathan Nieder
2010-08-24 14:14       ` Jeff King
2010-08-24 19:07       ` [PATCH 2/1] do not pass &quot;git -c foo=bar&quot; " Eric Raible
2010-08-23 19:02 ` "git -c web.browser=w3m help -w help" still kicks firefox Alex Riesen
2010-08-23 20:33   ` Jeff King
2010-08-24  5:01     ` Jonathan Nieder
2010-08-24 14:12       ` Jeff King

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: http://vger.kernel.org/majordomo-info.html

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20100823191600.GA2523@coredump.intra.peff.net \
    --to=peff@peff.net \
    --cc=chriscool@tuxfamily.org \
    --cc=git@vger.kernel.org \
    --cc=gitster@pobox.com \
    --cc=jrnieder@gmail.com \
    --cc=raa.lkml@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://80x24.org/mirrors/git.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).