32
32
#include "advice.h"
33
33
#include "branch.h"
34
34
#include "list-objects-filter-options.h"
35
+ #include "wildmatch.h"
36
+ #include "strbuf.h"
35
37
36
38
#define OPT_QUIET (1 << 0)
37
39
#define OPT_CACHED (1 << 1)
@@ -3329,6 +3331,9 @@ static void configure_added_submodule(struct add_data *add_data)
3329
3331
char * key ;
3330
3332
struct child_process add_submod = CHILD_PROCESS_INIT ;
3331
3333
struct child_process add_gitmodules = CHILD_PROCESS_INIT ;
3334
+ const struct string_list * values ;
3335
+ size_t i ;
3336
+ int matched = 0 ;
3332
3337
3333
3338
key = xstrfmt ("submodule.%s.url" , add_data -> sm_name );
3334
3339
git_config_set_gently (key , add_data -> realrepo );
@@ -3371,20 +3376,25 @@ static void configure_added_submodule(struct add_data *add_data)
3371
3376
* is_submodule_active(), since that function needs to find
3372
3377
* out the value of "submodule.active" again anyway.
3373
3378
*/
3374
- if (!git_config_get ("submodule.active" )) {
3375
- /*
3376
- * If the submodule being added isn't already covered by the
3377
- * current configured pathspec, set the submodule's active flag
3378
- */
3379
- if (!is_submodule_active (the_repository , add_data -> sm_path )) {
3380
- key = xstrfmt ("submodule.%s.active" , add_data -> sm_name );
3381
- git_config_set_gently (key , "true" );
3382
- free (key );
3383
- }
3384
- } else {
3379
+ if (git_config_get ("submodule.active" ) || /* key absent */
3380
+ git_config_get_string_multi ("submodule.active" , & values )) {
3381
+ /* submodule.active is missing -> force-enable */
3385
3382
key = xstrfmt ("submodule.%s.active" , add_data -> sm_name );
3386
3383
git_config_set_gently (key , "true" );
3387
3384
free (key );
3385
+ } else {
3386
+ for (i = 0 ; i < values -> nr ; i ++ ) {
3387
+ const char * pat = values -> items [i ].string ;
3388
+ if (!wildmatch (pat , add_data -> sm_path , 0 )) { /* match found */
3389
+ matched = 1 ;
3390
+ break ;
3391
+ }
3392
+ }
3393
+ if (!matched ) { /* no pattern matched -> force-enable */
3394
+ key = xstrfmt ("submodule.%s.active" , add_data -> sm_name );
3395
+ git_config_set_gently (key , "true" );
3396
+ free (key );
3397
+ }
3388
3398
}
3389
3399
}
3390
3400
@@ -3445,6 +3455,10 @@ static int module_add(int argc, const char **argv, const char *prefix,
3445
3455
struct add_data add_data = ADD_DATA_INIT ;
3446
3456
const char * ref_storage_format = NULL ;
3447
3457
char * to_free = NULL ;
3458
+ const struct submodule * existing ;
3459
+ struct strbuf buf = STRBUF_INIT ;
3460
+ int i ;
3461
+ char * sm_name_to_free = NULL ;
3448
3462
struct option options [] = {
3449
3463
OPT_STRING ('b' , "branch" , & add_data .branch , N_ ("branch" ),
3450
3464
N_ ("branch of repository to add as submodule" )),
@@ -3547,6 +3561,29 @@ static int module_add(int argc, const char **argv, const char *prefix,
3547
3561
if (!add_data .sm_name )
3548
3562
add_data .sm_name = add_data .sm_path ;
3549
3563
3564
+ existing = submodule_from_name (the_repository ,
3565
+ null_oid (the_hash_algo ),
3566
+ add_data .sm_name );
3567
+
3568
+ if (existing && strcmp (existing -> path , add_data .sm_path )) {
3569
+ if (!force ) {
3570
+ die (_ ("submodule name '%s' already used for path '%s'" ),
3571
+ add_data .sm_name , existing -> path );
3572
+ }
3573
+
3574
+ /* --force: build <name><n> until unique */
3575
+ for (i = 1 ; ; i ++ ) {
3576
+ strbuf_reset (& buf );
3577
+ strbuf_addf (& buf , "%s%d" , add_data .sm_name , i );
3578
+ if (!submodule_from_name (the_repository ,
3579
+ null_oid (the_hash_algo ),
3580
+ buf .buf )) {
3581
+ break ;
3582
+ }
3583
+ }
3584
+
3585
+ add_data .sm_name = sm_name_to_free = strbuf_detach (& buf , NULL );
3586
+ }
3550
3587
if (check_submodule_name (add_data .sm_name ))
3551
3588
die (_ ("'%s' is not a valid submodule name" ), add_data .sm_name );
3552
3589
@@ -3562,6 +3599,7 @@ static int module_add(int argc, const char **argv, const char *prefix,
3562
3599
3563
3600
ret = 0 ;
3564
3601
cleanup :
3602
+ free (sm_name_to_free );
3565
3603
free (add_data .sm_path );
3566
3604
free (to_free );
3567
3605
strbuf_release (& sb );
0 commit comments