int cmd_main(int argc, const char **argv) { const char **arg = argv; int my_argc = argc; int output_url = 0; int lookup_name = 0; arg++; my_argc--; while (starts_with(arg[0], "--")) { if (!strcmp(arg[0], "--url")) output_url = 1; if (!strcmp(arg[0], "--name")) lookup_name = 1; arg++; my_argc--; } if (my_argc % 2 != 0) die_usage(argc, argv, "Wrong number of arguments."); setup_git_directory(); gitmodules_config(); git_config(git_test_config, NULL); while (*arg) { unsigned char commit_sha1[20]; const struct submodule *submodule; const char *commit; const char *path_or_name; commit = arg[0]; path_or_name = arg[1]; if (commit[0] == '\0') hashclr(commit_sha1); else if (get_sha1(commit, commit_sha1) < 0) die_usage(argc, argv, "Commit not found."); if (lookup_name) { submodule = submodule_from_name(commit_sha1, path_or_name); } else submodule = submodule_from_path(commit_sha1, path_or_name); if (!submodule) die_usage(argc, argv, "Submodule not found."); if (output_url) printf("Submodule url: '%s' for path '%s'\n", submodule->url, submodule->path); else printf("Submodule name: '%s' for path '%s'\n", submodule->name, submodule->path); arg += 2; } submodule_free(); return 0; }
int fetch_populated_submodules(const struct argv_array *options, const char *prefix, int command_line_option, int quiet) { int i, result = 0; struct child_process cp = CHILD_PROCESS_INIT; struct argv_array argv = ARGV_ARRAY_INIT; const char *work_tree = get_git_work_tree(); if (!work_tree) goto out; if (read_cache() < 0) die("index file corrupt"); argv_array_push(&argv, "fetch"); for (i = 0; i < options->argc; i++) argv_array_push(&argv, options->argv[i]); argv_array_push(&argv, "--recurse-submodules-default"); /* default value, "--submodule-prefix" and its value are added later */ cp.env = local_repo_env; cp.git_cmd = 1; cp.no_stdin = 1; calculate_changed_submodule_paths(); for (i = 0; i < active_nr; i++) { struct strbuf submodule_path = STRBUF_INIT; struct strbuf submodule_git_dir = STRBUF_INIT; struct strbuf submodule_prefix = STRBUF_INIT; const struct cache_entry *ce = active_cache[i]; const char *git_dir, *default_argv; const struct submodule *submodule; if (!S_ISGITLINK(ce->ce_mode)) continue; submodule = submodule_from_path(null_sha1, ce->name); if (!submodule) submodule = submodule_from_name(null_sha1, ce->name); default_argv = "yes"; if (command_line_option == RECURSE_SUBMODULES_DEFAULT) { if (submodule && submodule->fetch_recurse != RECURSE_SUBMODULES_NONE) { if (submodule->fetch_recurse == RECURSE_SUBMODULES_OFF) continue; if (submodule->fetch_recurse == RECURSE_SUBMODULES_ON_DEMAND) { if (!unsorted_string_list_lookup(&changed_submodule_paths, ce->name)) continue; default_argv = "on-demand"; } } else { if ((config_fetch_recurse_submodules == RECURSE_SUBMODULES_OFF) || gitmodules_is_unmerged) continue; if (config_fetch_recurse_submodules == RECURSE_SUBMODULES_ON_DEMAND) { if (!unsorted_string_list_lookup(&changed_submodule_paths, ce->name)) continue; default_argv = "on-demand"; } } } else if (command_line_option == RECURSE_SUBMODULES_ON_DEMAND) { if (!unsorted_string_list_lookup(&changed_submodule_paths, ce->name)) continue; default_argv = "on-demand"; } strbuf_addf(&submodule_path, "%s/%s", work_tree, ce->name); strbuf_addf(&submodule_git_dir, "%s/.git", submodule_path.buf); strbuf_addf(&submodule_prefix, "%s%s/", prefix, ce->name); git_dir = read_gitfile(submodule_git_dir.buf); if (!git_dir) git_dir = submodule_git_dir.buf; if (is_directory(git_dir)) { if (!quiet) printf("Fetching submodule %s%s\n", prefix, ce->name); cp.dir = submodule_path.buf; argv_array_push(&argv, default_argv); argv_array_push(&argv, "--submodule-prefix"); argv_array_push(&argv, submodule_prefix.buf); cp.argv = argv.argv; if (run_command(&cp)) result = 1; argv_array_pop(&argv); argv_array_pop(&argv); argv_array_pop(&argv); } strbuf_release(&submodule_path); strbuf_release(&submodule_git_dir); strbuf_release(&submodule_prefix); } argv_array_clear(&argv); out: string_list_clear(&changed_submodule_paths, 1); return result; }
static int get_next_submodule(struct child_process *cp, struct strbuf *err, void *data, void **task_cb) { int ret = 0; struct submodule_parallel_fetch *spf = data; for (; spf->count < active_nr; spf->count++) { struct strbuf submodule_path = STRBUF_INIT; struct strbuf submodule_git_dir = STRBUF_INIT; struct strbuf submodule_prefix = STRBUF_INIT; const struct cache_entry *ce = active_cache[spf->count]; const char *git_dir, *default_argv; const struct submodule *submodule; if (!S_ISGITLINK(ce->ce_mode)) continue; submodule = submodule_from_path(null_sha1, ce->name); if (!submodule) submodule = submodule_from_name(null_sha1, ce->name); default_argv = "yes"; if (spf->command_line_option == RECURSE_SUBMODULES_DEFAULT) { if (submodule && submodule->fetch_recurse != RECURSE_SUBMODULES_NONE) { if (submodule->fetch_recurse == RECURSE_SUBMODULES_OFF) continue; if (submodule->fetch_recurse == RECURSE_SUBMODULES_ON_DEMAND) { if (!unsorted_string_list_lookup(&changed_submodule_paths, ce->name)) continue; default_argv = "on-demand"; } } else { if ((config_fetch_recurse_submodules == RECURSE_SUBMODULES_OFF) || gitmodules_is_unmerged) continue; if (config_fetch_recurse_submodules == RECURSE_SUBMODULES_ON_DEMAND) { if (!unsorted_string_list_lookup(&changed_submodule_paths, ce->name)) continue; default_argv = "on-demand"; } } } else if (spf->command_line_option == RECURSE_SUBMODULES_ON_DEMAND) { if (!unsorted_string_list_lookup(&changed_submodule_paths, ce->name)) continue; default_argv = "on-demand"; } strbuf_addf(&submodule_path, "%s/%s", spf->work_tree, ce->name); strbuf_addf(&submodule_git_dir, "%s/.git", submodule_path.buf); strbuf_addf(&submodule_prefix, "%s%s/", spf->prefix, ce->name); git_dir = read_gitfile(submodule_git_dir.buf); if (!git_dir) git_dir = submodule_git_dir.buf; if (is_directory(git_dir)) { child_process_init(cp); cp->dir = strbuf_detach(&submodule_path, NULL); cp->env = local_repo_env; cp->git_cmd = 1; if (!spf->quiet) strbuf_addf(err, "Fetching submodule %s%s\n", spf->prefix, ce->name); argv_array_init(&cp->args); argv_array_pushv(&cp->args, spf->args.argv); argv_array_push(&cp->args, default_argv); argv_array_push(&cp->args, "--submodule-prefix"); argv_array_push(&cp->args, submodule_prefix.buf); ret = 1; } strbuf_release(&submodule_path); strbuf_release(&submodule_git_dir); strbuf_release(&submodule_prefix); if (ret) { spf->count++; return 1; } } return 0; }