/* * If we are cherry-pick, and if the merge did not result in * hand-editing, we will hit this commit and inherit the original * author date and name. * * If we are revert, or if our cherry-pick results in a hand merge, * we had better say that the current user is responsible for that. * * An exception is when run_git_commit() is called during an * interactive rebase: in that case, we will want to retain the * author metadata. */ static int run_git_commit(const char *defmsg, struct replay_opts *opts, int allow_empty, int edit, int amend, int cleanup_commit_message) { char **env = NULL; struct argv_array array; int rc; const char *value; if (is_rebase_i(opts)) { env = read_author_script(); if (!env) { const char *gpg_opt = gpg_sign_opt_quoted(opts); return error(_(staged_changes_advice), gpg_opt, gpg_opt); } } argv_array_init(&array); argv_array_push(&array, "commit"); argv_array_push(&array, "-n"); if (amend) argv_array_push(&array, "--amend"); if (opts->gpg_sign) argv_array_pushf(&array, "-S%s", opts->gpg_sign); if (opts->signoff) argv_array_push(&array, "-s"); if (defmsg) argv_array_pushl(&array, "-F", defmsg, NULL); if (cleanup_commit_message) argv_array_push(&array, "--cleanup=strip"); if (edit) argv_array_push(&array, "-e"); else if (!cleanup_commit_message && !opts->signoff && !opts->record_origin && git_config_get_value("commit.cleanup", &value)) argv_array_push(&array, "--cleanup=verbatim"); if (allow_empty) argv_array_push(&array, "--allow-empty"); if (opts->allow_empty_message) argv_array_push(&array, "--allow-empty-message"); rc = run_command_v_opt_cd_env(array.argv, RUN_GIT_CMD, NULL, (const char *const *)env); argv_array_clear(&array); free(env); return rc; }
static int run_file_diff(int prompt, const char *prefix, int argc, const char **argv) { struct argv_array args = ARGV_ARRAY_INIT; const char *env[] = { "GIT_PAGER=", "GIT_EXTERNAL_DIFF=git-difftool--helper", NULL, NULL }; int ret = 0, i; if (prompt > 0) env[2] = "GIT_DIFFTOOL_PROMPT=true"; else if (!prompt) env[2] = "GIT_DIFFTOOL_NO_PROMPT=true"; argv_array_push(&args, "diff"); for (i = 0; i < argc; i++) argv_array_push(&args, argv[i]); ret = run_command_v_opt_cd_env(args.argv, RUN_GIT_CMD, prefix, env); exit(ret); }
int run_command_v_opt(const char **argv, int opt) { return run_command_v_opt_cd_env(argv, opt, NULL, NULL); }
static int handle_alias(int *argcp, const char ***argv) { int envchanged = 0, ret = 0, saved_errno = errno; const char *subdir; int count, option_count; const char **new_argv; const char *alias_command; char *alias_string; int unused_nongit; subdir = setup_git_directory_gently(&unused_nongit); alias_command = (*argv)[0]; alias_string = alias_lookup(alias_command); if (alias_string) { if (alias_string[0] == '!') { const char **alias_argv; int argc = *argcp, i; struct strbuf sb = STRBUF_INIT; const char *env[2]; commit_pager_choice(); /* build alias_argv */ alias_argv = xmalloc(sizeof(*alias_argv) * (argc + 1)); alias_argv[0] = alias_string + 1; for (i = 1; i < argc; ++i) alias_argv[i] = (*argv)[i]; alias_argv[argc] = NULL; strbuf_addstr(&sb, "GIT_PREFIX="); if (subdir) strbuf_addstr(&sb, subdir); env[0] = sb.buf; env[1] = NULL; ret = run_command_v_opt_cd_env(alias_argv, RUN_USING_SHELL, NULL, env); strbuf_release(&sb); if (ret >= 0) /* normal exit */ exit(ret); die_errno("While expanding alias '%s': '%s'", alias_command, alias_string + 1); } count = split_cmdline(alias_string, &new_argv); if (count < 0) die("Bad alias.%s string: %s", alias_command, split_cmdline_strerror(count)); option_count = handle_options(&new_argv, &count, &envchanged); if (envchanged) die("alias '%s' changes environment variables\n" "You can use '!git' in the alias to do this.", alias_command); memmove(new_argv - option_count, new_argv, count * sizeof(char *)); new_argv -= option_count; if (count < 1) die("empty alias for %s", alias_command); if (!strcmp(alias_command, new_argv[0])) die("recursive alias: %s", alias_command); trace_argv_printf(new_argv, "trace: alias expansion: %s =>", alias_command); new_argv = xrealloc(new_argv, sizeof(char *) * (count + *argcp)); /* insert after command name */ memcpy(new_argv + count, *argv + 1, sizeof(char *) * *argcp); *argv = new_argv; *argcp += count - 1; ret = 1; } if (subdir && chdir(subdir)) die_errno("Cannot change to '%s'", subdir); errno = saved_errno; return ret; }