summaryrefslogtreecommitdiff
path: root/setup.c
diff options
context:
space:
mode:
authorPatrick Steinhardt <ps@pks.im>2024-08-16 10:57:03 +0200
committerJunio C Hamano <gitster@pobox.com>2024-08-16 09:55:21 -0700
commit0c22e09b7376ce9c010e5901108bab08e5ec2b2c (patch)
treedb58d932fd86879b9d5c3623c84a6983983200f4 /setup.c
parent39e15b789ad3c3a192f4c8abde3daff83a053aaa (diff)
setup: make object format configurable via config
The object format for repositories can either be configured explicitly by passing the `--object-format=` option to git-init(1) or git-clone(1), or globally by setting the `GIT_DEFAULT_HASH` environment variable. While the former makes sense, setting random environment variables is not really a good user experience in case someone decides to only use SHA256 repositories. It is only natural to expect for a user that things like this can also be configured via their config. As such, introduce a new config "init.defaultObjectFormat", similar to "init.defaultBranch", that allows the user to configure the default object format when creating new repos. The precedence order now is the following, where the first one wins: 1. The `--object-format=` switch. 2. The `GIT_DEFAULT_HASH` environment variable. 3. The `init.defaultObjectFormat` config variable. This matches the typical precedence order we use in Git. We typically let the environment override the config such that the latter can easily be overridden on an ephemeral basis, for example by scripts. Signed-off-by: Patrick Steinhardt <ps@pks.im> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Diffstat (limited to 'setup.c')
-rw-r--r--setup.c40
1 files changed, 40 insertions, 0 deletions
diff --git a/setup.c b/setup.c
index 5dfcdc99dd..770ad1393f 100644
--- a/setup.c
+++ b/setup.c
@@ -2284,11 +2284,49 @@ static void separate_git_dir(const char *git_dir, const char *git_link)
write_file(git_link, "gitdir: %s", git_dir);
}
+struct default_format_config {
+ int hash;
+};
+
+static int read_default_format_config(const char *key, const char *value,
+ const struct config_context *ctx UNUSED,
+ void *payload)
+{
+ struct default_format_config *cfg = payload;
+ char *str = NULL;
+ int ret;
+
+ if (!strcmp(key, "init.defaultobjectformat")) {
+ ret = git_config_string(&str, key, value);
+ if (ret)
+ goto out;
+ cfg->hash = hash_algo_by_name(str);
+ if (cfg->hash == GIT_HASH_UNKNOWN)
+ warning(_("unknown hash algorithm '%s'"), str);
+ goto out;
+ }
+
+ ret = 0;
+out:
+ free(str);
+ return ret;
+}
+
static void repository_format_configure(struct repository_format *repo_fmt,
int hash, enum ref_storage_format ref_format)
{
+ struct default_format_config cfg = {
+ .hash = GIT_HASH_UNKNOWN,
+ };
+ struct config_options opts = {
+ .respect_includes = 1,
+ .ignore_repo = 1,
+ .ignore_worktree = 1,
+ };
const char *env;
+ config_with_options(read_default_format_config, &cfg, NULL, NULL, &opts);
+
/*
* If we already have an initialized repo, don't allow the user to
* specify a different algorithm, as that could cause corruption.
@@ -2304,6 +2342,8 @@ static void repository_format_configure(struct repository_format *repo_fmt,
if (env_algo == GIT_HASH_UNKNOWN)
die(_("unknown hash algorithm '%s'"), env);
repo_fmt->hash_algo = env_algo;
+ } else if (cfg.hash != GIT_HASH_UNKNOWN) {
+ repo_fmt->hash_algo = cfg.hash;
}
repo_set_hash_algo(the_repository, repo_fmt->hash_algo);