@@ -1166,14 +1166,32 @@ static int git_config_from_blob_ref(config_fn_t fn,
1166
1166
return git_config_from_blob_sha1 (fn , name , sha1 , data );
1167
1167
}
1168
1168
1169
+ static const char * etc_gitconfig = ETC_GITCONFIG ;
1170
+
1169
1171
const char * git_etc_gitconfig (void )
1170
1172
{
1171
1173
static const char * system_wide ;
1172
1174
if (!system_wide )
1173
- system_wide = system_path (ETC_GITCONFIG );
1175
+ system_wide = system_path (etc_gitconfig );
1174
1176
return system_wide ;
1175
1177
}
1176
1178
1179
+ static const char * git_inst_gitconfig (void )
1180
+ {
1181
+ static const char * installation_defaults ;
1182
+ if (!installation_defaults ) {
1183
+ /*
1184
+ * if ETC_GITCONFIG as configured in the Makefile is an absolute path,
1185
+ * also load installation-specific defaults (relative to $(prefix))
1186
+ */
1187
+ if (is_dir_sep (* etc_gitconfig ))
1188
+ installation_defaults = system_path (etc_gitconfig + 1 );
1189
+ else
1190
+ installation_defaults = "" ;
1191
+ }
1192
+ return * installation_defaults ? installation_defaults : NULL ;
1193
+ }
1194
+
1177
1195
/*
1178
1196
* Parse environment variable 'k' as a boolean (in various
1179
1197
* possible spellings); if missing, use the default value 'def'.
@@ -1201,41 +1219,38 @@ int git_config_system(void)
1201
1219
return !git_env_bool ("GIT_CONFIG_NOSYSTEM" , 0 );
1202
1220
}
1203
1221
1222
+ static inline int config_early_helper (config_fn_t fn , const char * filename ,
1223
+ void * data , unsigned access_flags , int count ) {
1224
+ if (!filename || access_or_die (filename , R_OK , access_flags ))
1225
+ /* no file: return unchanged */
1226
+ return count ;
1227
+
1228
+ if (git_config_from_file (fn , filename , data ))
1229
+ /* error: decrement or start counting errors at -1 */
1230
+ return count < 0 ? count - 1 : -1 ;
1231
+ else
1232
+ /* ok: increment unless we had errors before */
1233
+ return count < 0 ? count : count + 1 ;
1234
+ }
1235
+
1204
1236
int git_config_early (config_fn_t fn , void * data , const char * repo_config )
1205
1237
{
1206
- int ret = 0 , found = 0 ;
1207
- const char * super_config = git_super_config () ;
1238
+ /* count loaded files (> 0) or errors (< 0) */
1239
+ int cnt = 0 ;
1208
1240
char * xdg_config = NULL ;
1209
1241
char * user_config = NULL ;
1210
1242
1211
1243
home_config_paths (& user_config , & xdg_config , "config" );
1212
1244
1213
- if (super_config && git_config_system () &&
1214
- !access (super_config , R_OK )) {
1215
- ret += git_config_from_file (fn , super_config , data );
1216
- found += 1 ;
1245
+ if (git_config_system ()) {
1246
+ cnt = config_early_helper (fn , git_inst_gitconfig (), data , 0 , cnt );
1247
+ cnt = config_early_helper (fn , git_etc_gitconfig (), data , 0 , cnt );
1217
1248
}
1218
1249
1219
- if (git_config_system () && !access_or_die (git_etc_gitconfig (), R_OK , 0 )) {
1220
- ret += git_config_from_file (fn , git_etc_gitconfig (),
1221
- data );
1222
- found += 1 ;
1223
- }
1250
+ cnt = config_early_helper (fn , xdg_config , data , ACCESS_EACCES_OK , cnt );
1251
+ cnt = config_early_helper (fn , user_config , data , ACCESS_EACCES_OK , cnt );
1224
1252
1225
- if (xdg_config && !access_or_die (xdg_config , R_OK , ACCESS_EACCES_OK )) {
1226
- ret += git_config_from_file (fn , xdg_config , data );
1227
- found += 1 ;
1228
- }
1229
-
1230
- if (user_config && !access_or_die (user_config , R_OK , ACCESS_EACCES_OK )) {
1231
- ret += git_config_from_file (fn , user_config , data );
1232
- found += 1 ;
1233
- }
1234
-
1235
- if (repo_config && !access_or_die (repo_config , R_OK , 0 )) {
1236
- ret += git_config_from_file (fn , repo_config , data );
1237
- found += 1 ;
1238
- }
1253
+ cnt = config_early_helper (fn , repo_config , data , 0 , cnt );
1239
1254
1240
1255
switch (git_config_from_parameters (fn , data )) {
1241
1256
case -1 : /* error */
@@ -1244,13 +1259,14 @@ int git_config_early(config_fn_t fn, void *data, const char *repo_config)
1244
1259
case 0 : /* found nothing */
1245
1260
break ;
1246
1261
default : /* found at least one item */
1247
- found ++ ;
1262
+ if (cnt >= 0 )
1263
+ cnt ++ ;
1248
1264
break ;
1249
1265
}
1250
1266
1251
1267
free (xdg_config );
1252
1268
free (user_config );
1253
- return ret == 0 ? found : ret ;
1269
+ return cnt ;
1254
1270
}
1255
1271
1256
1272
int git_config_with_options (config_fn_t fn , void * data ,
@@ -1932,6 +1948,24 @@ int git_config_parse_key(const char *key, char **store_key, int *baselen_)
1932
1948
return - CONFIG_INVALID_KEY ;
1933
1949
}
1934
1950
1951
+
1952
+ static int lock_config_file (const char * config_filename ,
1953
+ struct lock_file * * result )
1954
+ {
1955
+ int fd ;
1956
+ /* make sure the parent directory exists */
1957
+ if (safe_create_leading_directories_const (config_filename )) {
1958
+ error ("could not create parent directory of %s" , config_filename );
1959
+ return -1 ;
1960
+ }
1961
+ * result = xcalloc (1 , sizeof (struct lock_file ));
1962
+ fd = hold_lock_file_for_update (* result , config_filename , 0 );
1963
+ if (fd < 0 )
1964
+ error ("could not lock config file %s: %s" , config_filename ,
1965
+ strerror (errno ));
1966
+ return fd ;
1967
+ }
1968
+
1935
1969
/*
1936
1970
* If value==NULL, unset in (remove from) config,
1937
1971
* if value_regex!=NULL, disregard key/value pairs where value does not match.
@@ -1980,10 +2014,8 @@ int git_config_set_multivar_in_file(const char *config_filename,
1980
2014
* The lock serves a purpose in addition to locking: the new
1981
2015
* contents of .git/config will be written into it.
1982
2016
*/
1983
- lock = xcalloc (1 , sizeof (struct lock_file ));
1984
- fd = hold_lock_file_for_update (lock , config_filename , 0 );
2017
+ fd = lock_config_file (config_filename , & lock );
1985
2018
if (fd < 0 ) {
1986
- error ("could not lock config file %s: %s" , config_filename , strerror (errno ));
1987
2019
free (store .key );
1988
2020
ret = CONFIG_NO_LOCK ;
1989
2021
goto out_free ;
@@ -2251,12 +2283,9 @@ int git_config_rename_section_in_file(const char *config_filename,
2251
2283
if (!config_filename )
2252
2284
config_filename = filename_buf = git_pathdup ("config" );
2253
2285
2254
- lock = xcalloc (1 , sizeof (struct lock_file ));
2255
- out_fd = hold_lock_file_for_update (lock , config_filename , 0 );
2256
- if (out_fd < 0 ) {
2257
- ret = error ("could not lock config file %s" , config_filename );
2286
+ out_fd = lock_config_file (config_filename , & lock );
2287
+ if (out_fd < 0 )
2258
2288
goto out ;
2259
- }
2260
2289
2261
2290
if (!(config_file = fopen (config_filename , "rb" ))) {
2262
2291
/* no config file means nothing to rename, no error */
0 commit comments