diff options
Diffstat (limited to 'builtin-shortlog.c')
-rw-r--r-- | builtin-shortlog.c | 82 |
1 files changed, 45 insertions, 37 deletions
diff --git a/builtin-shortlog.c b/builtin-shortlog.c index d03f14fdad..b3b055f68c 100644 --- a/builtin-shortlog.c +++ b/builtin-shortlog.c @@ -29,6 +29,9 @@ static int compare_by_number(const void *a1, const void *a2) return -1; } +const char *format_subject(struct strbuf *sb, const char *msg, + const char *line_separator); + static void insert_one_record(struct shortlog *log, const char *author, const char *oneline) @@ -36,11 +39,12 @@ static void insert_one_record(struct shortlog *log, const char *dot3 = log->common_repo_prefix; char *buffer, *p; struct string_list_item *item; - struct string_list *onelines; char namebuf[1024]; + char emailbuf[1024]; size_t len; const char *eol; const char *boemail, *eoemail; + struct strbuf subject = STRBUF_INIT; boemail = strchr(author, '<'); if (!boemail) @@ -48,7 +52,19 @@ static void insert_one_record(struct shortlog *log, eoemail = strchr(boemail, '>'); if (!eoemail) return; - if (!map_email(&log->mailmap, boemail+1, namebuf, sizeof(namebuf))) { + + /* copy author name to namebuf, to support matching on both name and email */ + memcpy(namebuf, author, boemail - author); + len = boemail - author; + while (len > 0 && isspace(namebuf[len-1])) + len--; + namebuf[len] = 0; + + /* copy email name to emailbuf, to allow email replacement as well */ + memcpy(emailbuf, boemail+1, eoemail - boemail); + emailbuf[eoemail - boemail - 1] = 0; + + if (!map_user(&log->mailmap, emailbuf, sizeof(emailbuf), namebuf, sizeof(namebuf))) { while (author < boemail && isspace(*author)) author++; for (len = 0; @@ -64,16 +80,13 @@ static void insert_one_record(struct shortlog *log, if (log->email) { size_t room = sizeof(namebuf) - len - 1; - int maillen = eoemail - boemail + 1; - snprintf(namebuf + len, room, " %.*s", maillen, boemail); + int maillen = strlen(emailbuf); + snprintf(namebuf + len, room, " <%.*s>", maillen, emailbuf); } - buffer = xstrdup(namebuf); - item = string_list_insert(buffer, &log->list); + item = string_list_insert(namebuf, &log->list); if (item->util == NULL) item->util = xcalloc(1, sizeof(struct string_list)); - else - free(buffer); /* Skip any leading whitespace, including any blank lines. */ while (*oneline && isspace(*oneline)) @@ -88,10 +101,8 @@ static void insert_one_record(struct shortlog *log, } while (*oneline && isspace(*oneline) && *oneline != '\n') oneline++; - len = eol - oneline; - while (len && isspace(oneline[len-1])) - len--; - buffer = xmemdupz(oneline, len); + format_subject(&subject, oneline, " "); + buffer = strbuf_detach(&subject, NULL); if (dot3) { int dot3len = strlen(dot3); @@ -104,16 +115,7 @@ static void insert_one_record(struct shortlog *log, } } - onelines = item->util; - if (onelines->nr >= onelines->alloc) { - onelines->alloc = alloc_nr(onelines->nr); - onelines->items = xrealloc(onelines->items, - onelines->alloc - * sizeof(struct string_list_item)); - } - - onelines->items[onelines->nr].util = NULL; - onelines->items[onelines->nr++].string = buffer; + string_list_append(buffer, item->util); } static void read_from_stdin(struct shortlog *log) @@ -137,8 +139,12 @@ static void read_from_stdin(struct shortlog *log) void shortlog_add_commit(struct shortlog *log, struct commit *commit) { const char *author = NULL, *buffer; + struct strbuf buf = STRBUF_INIT; + struct strbuf ufbuf = STRBUF_INIT; + struct pretty_print_context ctx = {0}; - buffer = commit->buffer; + pretty_print_commit(CMIT_FMT_RAW, commit, &buf, &ctx); + buffer = buf.buf; while (*buffer && *buffer != '\n') { const char *eol = strchr(buffer, '\n'); @@ -155,17 +161,19 @@ void shortlog_add_commit(struct shortlog *log, struct commit *commit) die("Missing author: %s", sha1_to_hex(commit->object.sha1)); if (log->user_format) { - struct strbuf buf = STRBUF_INIT; - - pretty_print_commit(CMIT_FMT_USERFORMAT, commit, &buf, - DEFAULT_ABBREV, "", "", DATE_NORMAL, 0); - insert_one_record(log, author, buf.buf); - strbuf_release(&buf); - return; - } - if (*buffer) + struct pretty_print_context ctx = {0}; + ctx.abbrev = DEFAULT_ABBREV; + ctx.subject = ""; + ctx.after_subject = ""; + ctx.date_mode = DATE_NORMAL; + pretty_print_commit(CMIT_FMT_USERFORMAT, commit, &ufbuf, &ctx); + buffer = ufbuf.buf; + } else if (*buffer) { buffer++; + } insert_one_record(log, author, !*buffer ? "<none>" : buffer); + strbuf_release(&ufbuf); + strbuf_release(&buf); } static void get_from_rev(struct rev_info *rev, struct shortlog *log) @@ -229,7 +237,7 @@ void shortlog_init(struct shortlog *log) { memset(log, 0, sizeof(*log)); - read_mailmap(&log->mailmap, ".mailmap", &log->common_repo_prefix); + read_mailmap(&log->mailmap, &log->common_repo_prefix); log->list.strdup_strings = 1; log->wrap = DEFAULT_WRAPLEN; @@ -258,9 +266,10 @@ int cmd_shortlog(int argc, const char **argv, const char *prefix) struct parse_opt_ctx_t ctx; prefix = setup_git_directory_gently(&nongit); + git_config(git_default_config, NULL); shortlog_init(&log); init_revisions(&rev, prefix); - parse_options_start(&ctx, argc, argv, PARSE_OPT_KEEP_DASHDASH | + parse_options_start(&ctx, argc, argv, prefix, PARSE_OPT_KEEP_DASHDASH | PARSE_OPT_KEEP_ARGV0); for (;;) { @@ -323,13 +332,12 @@ void shortlog_output(struct shortlog *log) } onelines->strdup_strings = 1; - string_list_clear(onelines, 1); + string_list_clear(onelines, 0); free(onelines); log->list.items[i].util = NULL; } log->list.strdup_strings = 1; string_list_clear(&log->list, 1); - log->mailmap.strdup_strings = 1; - string_list_clear(&log->mailmap, 1); + clear_mailmap(&log->mailmap); } |