X-Git-Url: https://git.tokkee.org/?a=blobdiff_plain;f=builtin-log.c;h=d5bbc1cc06931974de46078b5cac17e315177e40;hb=e686eb9870d6b382f0760e3e859e93c8c2dfb31b;hp=1649f4943e03f379f69716ecea2074b0d92c41f3;hpb=81f3a188a3781fa4a818ed27ee83430682a98ec4;p=git.git diff --git a/builtin-log.c b/builtin-log.c index 1649f4943..d5bbc1cc0 100644 --- a/builtin-log.c +++ b/builtin-log.c @@ -11,6 +11,9 @@ #include "log-tree.h" #include "builtin.h" +/* this is in builtin-diff.c */ +void add_head(struct rev_info *revs); + static int cmd_log_wc(int argc, const char **argv, char **envp, struct rev_info *rev) { @@ -76,15 +79,22 @@ static int istitlechar(char c) } static FILE *realstdout = NULL; +static char *output_directory = NULL; -static void reopen_stdout(struct commit *commit, int nr) +static void reopen_stdout(struct commit *commit, int nr, int keep_subject) { char filename[1024]; char *sol; - int len; + int len = 0; + if (output_directory) { + strncpy(filename, output_directory, 1010); + len = strlen(filename); + if (filename[len - 1] != '/') + filename[len++] = '/'; + } - sprintf(filename, "%04d", nr); + sprintf(filename + len, "%04d", nr); len = strlen(filename); sol = strstr(commit->buffer, "\n\n"); @@ -93,7 +103,7 @@ static void reopen_stdout(struct commit *commit, int nr) sol += 2; /* strip [PATCH] or [PATCH blabla] */ - if (!strncmp(sol, "[PATCH", 6)) { + if (!keep_subject && !strncmp(sol, "[PATCH", 6)) { char *eos = strchr(sol + 6, ']'); if (eos) { while (isspace(*eos)) @@ -128,8 +138,10 @@ int cmd_format_patch(int argc, const char **argv, char **envp) struct commit *commit; struct commit **list = NULL; struct rev_info rev; - int nr = 0, total; + int nr = 0, total, i, j; int use_stdout = 0; + int numbered = 0; + int keep_subject = 0; init_revisions(&rev); rev.commit_format = CMIT_FMT_EMAIL; @@ -140,15 +152,45 @@ int cmd_format_patch(int argc, const char **argv, char **envp) rev.combine_merges = 0; rev.ignore_merges = 1; rev.diffopt.output_format = DIFF_FORMAT_PATCH; - argc = setup_revisions(argc, argv, &rev, "HEAD"); - while (argc > 1) { - if (!strcmp(argv[1], "--stdout")) + /* + * Parse the arguments before setup_revisions(), or something + * like "git fmt-patch -o a123 HEAD^.." may fail; a123 is + * possibly a valid SHA1. + */ + for (i = 1, j = 1; i < argc; i++) { + if (!strcmp(argv[i], "--stdout")) use_stdout = 1; - else - die ("unrecognized argument: %s", argv[1]); - argc--; - argv++; + else if (!strcmp(argv[i], "-n") || + !strcmp(argv[i], "--numbered")) + numbered = 1; + else if (!strcmp(argv[i], "-k") || + !strcmp(argv[i], "--keep-subject")) { + keep_subject = 1; + rev.total = -1; + } else if (!strcmp(argv[i], "-o")) { + if (argc < 3) + die ("Which directory?"); + if (mkdir(argv[i + 1], 0777) < 0 && errno != EEXIST) + die("Could not create directory %s", + argv[i + 1]); + output_directory = strdup(argv[i + 1]); + i++; + } else + argv[j++] = argv[i]; + } + argc = j; + + if (numbered && keep_subject < 0) + die ("-n and -k are mutually exclusive."); + + argc = setup_revisions(argc, argv, &rev, "HEAD"); + if (argc > 1) + die ("unrecognized argument: %s", argv[1]); + + if (rev.pending_objects && rev.pending_objects->next == NULL) { + rev.pending_objects->item->flags |= UNINTERESTING; + add_head(&rev); } if (!use_stdout) @@ -164,11 +206,14 @@ int cmd_format_patch(int argc, const char **argv, char **envp) list[nr - 1] = commit; } total = nr; + if (numbered) + rev.total = total; while (0 <= --nr) { int shown; commit = list[nr]; + rev.nr = total - nr; if (!use_stdout) - reopen_stdout(commit, total - nr); + reopen_stdout(commit, rev.nr, keep_subject); shown = log_tree_commit(&rev, commit); free(commit->buffer); commit->buffer = NULL; @@ -177,6 +222,8 @@ int cmd_format_patch(int argc, const char **argv, char **envp) if (!use_stdout) fclose(stdout); } + if (output_directory) + free(output_directory); free(list); return 0; }