From: Junio C Hamano Date: Tue, 25 Mar 2014 18:07:47 +0000 (-0700) Subject: Merge branch 'nd/commit-editor-cleanup' X-Git-Tag: v2.0.0-rc0~67 X-Git-Url: https://git.lorimer.id.au/gitweb.git/diff_plain/46c0f913a49218a8a94d30c5a2df792a16aab827?ds=inline;hp=-c Merge branch 'nd/commit-editor-cleanup' "git commit --cleanup=" learned a new mode, scissors. * nd/commit-editor-cleanup: commit: add --cleanup=scissors wt-status.c: move cut-line print code out to wt_status_add_cut_line wt-status.c: make cut_line[] const to shrink .data section a bit --- 46c0f913a49218a8a94d30c5a2df792a16aab827 diff --combined Documentation/git-commit.txt index 7c42e9cabc,7948233035..429267abf6 --- a/Documentation/git-commit.txt +++ b/Documentation/git-commit.txt @@@ -176,7 -176,7 +176,7 @@@ OPTION --cleanup=:: This option determines how the supplied commit message should be cleaned up before committing. The '' can be `strip`, - `whitespace`, `verbatim`, or `default`. + `whitespace`, `verbatim`, `scissors` or `default`. + -- strip:: @@@ -186,6 -186,12 +186,12 @@@ whitespace: Same as `strip` except #commentary is not removed. verbatim:: Do not change the message at all. + scissors:: + Same as `whitespace`, except that everything from (and + including) the line + "`# ------------------------ >8 ------------------------`" + is truncated if the message is to be edited. "`#`" can be + customized with core.commentChar. default:: Same as `strip` if the message is to be edited. Otherwise `whitespace`. @@@ -302,10 -308,6 +308,10 @@@ configuration variable documented in li --gpg-sign[=]:: GPG-sign commit. +--no-gpg-sign:: + Countermand `commit.gpgsign` configuration variable that is + set to force each and every commit to be signed. + \--:: Do not interpret any more arguments as options. diff --combined builtin/commit.c index 3783bcadcd,1033c500d2..38f34e7cd3 --- a/builtin/commit.c +++ b/builtin/commit.c @@@ -113,6 -113,7 +113,7 @@@ static char *sign_commit static enum { CLEANUP_SPACE, CLEANUP_NONE, + CLEANUP_SCISSORS, CLEANUP_ALL } cleanup_mode; static const char *cleanup_arg; @@@ -234,7 -235,7 +235,7 @@@ static int list_paths(struct string_lis if (ce->ce_flags & CE_UPDATE) continue; - if (!match_pathspec_depth(pattern, ce->name, ce_namelen(ce), 0, m)) + if (!ce_path_match(ce, pattern, m)) continue; item = string_list_insert(list, ce->name); if (ce_skip_worktree(ce)) @@@ -307,6 -308,7 +308,6 @@@ static char *prepare_index(int argc, co int fd; struct string_list partial; struct pathspec pathspec; - char *old_index_env = NULL; int refresh_flags = REFRESH_QUIET; if (is_status) @@@ -319,7 -321,6 +320,7 @@@ die(_("index file corrupt")); if (interactive) { + char *old_index_env = NULL; fd = hold_locked_index(&index_lock, 1); refresh_cache_or_die(refresh_flags); @@@ -600,10 -601,12 +601,10 @@@ static int prepare_to_commit(const cha { struct stat statbuf; struct strbuf committer_ident = STRBUF_INIT; - int commitable, saved_color_setting; + int commitable; struct strbuf sb = STRBUF_INIT; - char *buffer; const char *hook_arg1 = NULL; const char *hook_arg2 = NULL; - int ident_shown = 0; int clean_message_contents = (cleanup_mode != CLEANUP_NONE); int old_display_comment_prefix; @@@ -647,7 -650,6 +648,7 @@@ logfile); hook_arg1 = "message"; } else if (use_message) { + char *buffer; buffer = strstr(use_message_buffer, "\n\n"); if (!use_editor && (!buffer || buffer[2] == '\0')) die(_("commit has empty message")); @@@ -752,10 -754,10 +753,12 @@@ /* This checks if committer ident is explicitly given */ strbuf_addstr(&committer_ident, git_committer_info(IDENT_STRICT)); if (use_editor && include_status) { + int ident_shown = 0; + int saved_color_setting; char *ai_tmp, *ci_tmp; - if (whence != FROM_COMMIT) + if (whence != FROM_COMMIT) { + if (cleanup_mode == CLEANUP_SCISSORS) + wt_status_add_cut_line(s->fp); status_printf_ln(s, GIT_COLOR_NORMAL, whence == FROM_MERGE ? _("\n" @@@ -771,6 -773,7 +774,7 @@@ git_path(whence == FROM_MERGE ? "MERGE_HEAD" : "CHERRY_PICK_HEAD")); + } fprintf(s->fp, "\n"); if (cleanup_mode == CLEANUP_ALL) @@@ -778,6 -781,8 +782,8 @@@ _("Please enter the commit message for your changes." " Lines starting\nwith '%c' will be ignored, and an empty" " message aborts the commit.\n"), comment_line_char); + else if (cleanup_mode == CLEANUP_SCISSORS && whence == FROM_COMMIT) + wt_status_add_cut_line(s->fp); else /* CLEANUP_SPACE, that is. */ status_printf(s, GIT_COLOR_NORMAL, _("Please enter the commit message for your changes." @@@ -1133,6 -1138,8 +1139,8 @@@ static int parse_and_validate_options(i cleanup_mode = CLEANUP_SPACE; else if (!strcmp(cleanup_arg, "strip")) cleanup_mode = CLEANUP_ALL; + else if (!strcmp(cleanup_arg, "scissors")) + cleanup_mode = use_editor ? CLEANUP_SCISSORS : CLEANUP_SPACE; else die(_("Invalid cleanup mode %s"), cleanup_arg); @@@ -1407,10 -1414,6 +1415,10 @@@ static int git_commit_config(const cha } if (!strcmp(k, "commit.cleanup")) return git_config_string(&cleanup_arg, k, v); + if (!strcmp(k, "commit.gpgsign")) { + sign_commit = git_config_bool(k, v) ? "" : NULL; + return 0; + } status = git_gpg_config(k, v, NULL); if (status) @@@ -1515,6 -1518,7 +1523,6 @@@ int cmd_commit(int argc, const char **a struct ref_lock *ref_lock; struct commit_list *parents = NULL, **pptr = &parents; struct stat statbuf; - int allow_fast_forward = 1; struct commit *current_head = NULL; struct commit_extra_header *extra = NULL; @@@ -1562,7 -1566,6 +1570,7 @@@ } else if (whence == FROM_MERGE) { struct strbuf m = STRBUF_INIT; FILE *fp; + int allow_fast_forward = 1; if (!reflog_msg) reflog_msg = "commit (merge)"; @@@ -1605,8 -1608,8 +1613,8 @@@ die(_("could not read commit message: %s"), strerror(saved_errno)); } - /* Truncate the message just before the diff, if any. */ - if (verbose) + if (verbose || /* Truncate the message just before the diff, if any. */ + cleanup_mode == CLEANUP_SCISSORS) wt_status_truncate_message_at_cut_line(&sb); if (cleanup_mode != CLEANUP_NONE) diff --combined wt-status.c index c89c3bb537,ed31b6afbe..e1827faf07 --- a/wt-status.c +++ b/wt-status.c @@@ -17,7 -17,7 +17,7 @@@ #include "strbuf.h" #include "utf8.h" - static char cut_line[] = + static const char cut_line[] = "------------------------ >8 ------------------------\n"; static char default_wt_status_colors[][COLOR_MAXLEN] = { @@@ -245,92 -245,53 +245,92 @@@ static void wt_status_print_trailer(str #define quote_path quote_path_relative -static void wt_status_print_unmerged_data(struct wt_status *s, - struct string_list_item *it) +static const char *wt_status_unmerged_status_string(int stagemask) { - const char *c = color(WT_STATUS_UNMERGED, s); - struct wt_status_change_data *d = it->util; - struct strbuf onebuf = STRBUF_INIT; - const char *one, *how = _("bug"); - - one = quote_path(it->string, s->prefix, &onebuf); - status_printf(s, color(WT_STATUS_HEADER, s), "\t"); - switch (d->stagemask) { - case 1: how = _("both deleted:"); break; - case 2: how = _("added by us:"); break; - case 3: how = _("deleted by them:"); break; - case 4: how = _("added by them:"); break; - case 5: how = _("deleted by us:"); break; - case 6: how = _("both added:"); break; - case 7: how = _("both modified:"); break; + switch (stagemask) { + case 1: + return _("both deleted:"); + case 2: + return _("added by us:"); + case 3: + return _("deleted by them:"); + case 4: + return _("added by them:"); + case 5: + return _("deleted by us:"); + case 6: + return _("both added:"); + case 7: + return _("both modified:"); + default: + die(_("bug: unhandled unmerged status %x"), stagemask); } - status_printf_more(s, c, "%-20s%s\n", how, one); - strbuf_release(&onebuf); } static const char *wt_status_diff_status_string(int status) { switch (status) { case DIFF_STATUS_ADDED: - return _("new file"); + return _("new file:"); case DIFF_STATUS_COPIED: - return _("copied"); + return _("copied:"); case DIFF_STATUS_DELETED: - return _("deleted"); + return _("deleted:"); case DIFF_STATUS_MODIFIED: - return _("modified"); + return _("modified:"); case DIFF_STATUS_RENAMED: - return _("renamed"); + return _("renamed:"); case DIFF_STATUS_TYPE_CHANGED: - return _("typechange"); + return _("typechange:"); case DIFF_STATUS_UNKNOWN: - return _("unknown"); + return _("unknown:"); case DIFF_STATUS_UNMERGED: - return _("unmerged"); + return _("unmerged:"); default: return NULL; } } +static int maxwidth(const char *(*label)(int), int minval, int maxval) +{ + int result = 0, i; + + for (i = minval; i <= maxval; i++) { + const char *s = label(i); + int len = s ? utf8_strwidth(s) : 0; + if (len > result) + result = len; + } + return result; +} + +static void wt_status_print_unmerged_data(struct wt_status *s, + struct string_list_item *it) +{ + const char *c = color(WT_STATUS_UNMERGED, s); + struct wt_status_change_data *d = it->util; + struct strbuf onebuf = STRBUF_INIT; + static char *padding; + static int label_width; + const char *one, *how; + int len; + + if (!padding) { + label_width = maxwidth(wt_status_unmerged_status_string, 1, 7); + label_width += strlen(" "); + padding = xmallocz(label_width); + memset(padding, ' ', label_width); + } + + one = quote_path(it->string, s->prefix, &onebuf); + status_printf(s, color(WT_STATUS_HEADER, s), "\t"); + + how = wt_status_unmerged_status_string(d->stagemask); + len = label_width - utf8_strwidth(how); + status_printf_more(s, c, "%s%.*s%s\n", how, len, padding, one); + strbuf_release(&onebuf); +} + static void wt_status_print_change_data(struct wt_status *s, int change_type, struct string_list_item *it) @@@ -344,16 -305,21 +344,16 @@@ struct strbuf onebuf = STRBUF_INIT, twobuf = STRBUF_INIT; struct strbuf extra = STRBUF_INIT; static char *padding; + static int label_width; const char *what; int len; if (!padding) { - int width = 0; - /* If DIFF_STATUS_* uses outside this range, we're in trouble */ - for (status = 'A'; status <= 'Z'; status++) { - what = wt_status_diff_status_string(status); - len = what ? strlen(what) : 0; - if (len > width) - width = len; - } - width += 2; /* colon and a space */ - padding = xmallocz(width); - memset(padding, ' ', width); + /* If DIFF_STATUS_* uses outside the range [A..Z], we're in trouble */ + label_width = maxwidth(wt_status_diff_status_string, 'A', 'Z'); + label_width += strlen(" "); + padding = xmallocz(label_width); + memset(padding, ' ', label_width); } one_name = two_name = it->string; @@@ -389,13 -355,14 +389,13 @@@ what = wt_status_diff_status_string(status); if (!what) die(_("bug: unhandled diff status %c"), status); - /* 1 for colon, which is not part of "what" */ - len = strlen(padding) - (utf8_strwidth(what) + 1); + len = label_width - utf8_strwidth(what); assert(len >= 0); if (status == DIFF_STATUS_COPIED || status == DIFF_STATUS_RENAMED) - status_printf_more(s, c, "%s:%.*s%s -> %s", + status_printf_more(s, c, "%s%.*s%s -> %s", what, len, padding, one, two); else - status_printf_more(s, c, "%s:%.*s%s", + status_printf_more(s, c, "%s%.*s%s", what, len, padding, one); if (extra.len) { status_printf_more(s, color(WT_STATUS_HEADER, s), "%s", extra.buf); @@@ -543,7 -510,7 +543,7 @@@ static void wt_status_collect_changes_i struct wt_status_change_data *d; const struct cache_entry *ce = active_cache[i]; - if (!ce_path_match(ce, &s->pathspec)) + if (!ce_path_match(ce, &s->pathspec, NULL)) continue; it = string_list_insert(&s->change, ce->name); d = it->util; @@@ -585,7 -552,7 +585,7 @@@ static void wt_status_collect_untracked for (i = 0; i < dir.nr; i++) { struct dir_entry *ent = dir.entries[i]; if (cache_name_is_other(ent->name, ent->len) && - match_pathspec_depth(&s->pathspec, ent->name, ent->len, 0, NULL)) + dir_path_match(ent, &s->pathspec, 0, NULL)) string_list_insert(&s->untracked, ent->name); free(ent); } @@@ -593,7 -560,7 +593,7 @@@ for (i = 0; i < dir.ignored_nr; i++) { struct dir_entry *ent = dir.ignored[i]; if (cache_name_is_other(ent->name, ent->len) && - match_pathspec_depth(&s->pathspec, ent->name, ent->len, 0, NULL)) + dir_path_match(ent, &s->pathspec, 0, NULL)) string_list_insert(&s->ignored, ent->name); free(ent); } @@@ -841,6 -808,17 +841,17 @@@ void wt_status_truncate_message_at_cut_ strbuf_release(&pattern); } + void wt_status_add_cut_line(FILE *fp) + { + const char *explanation = _("Do not touch the line above.\nEverything below will be removed."); + struct strbuf buf = STRBUF_INIT; + + fprintf(fp, "%c %s", comment_line_char, cut_line); + strbuf_add_commented_lines(&buf, explanation, strlen(explanation)); + fputs(buf.buf, fp); + strbuf_release(&buf); + } + static void wt_status_print_verbose(struct wt_status *s) { struct rev_info rev; @@@ -866,14 -844,8 +877,8 @@@ * diff before committing. */ if (s->fp != stdout) { - const char *explanation = _("Do not touch the line above.\nEverything below will be removed."); - struct strbuf buf = STRBUF_INIT; - rev.diffopt.use_color = 0; - fprintf(s->fp, "%c %s", comment_line_char, cut_line); - strbuf_add_commented_lines(&buf, explanation, strlen(explanation)); - fputs(buf.buf, s->fp); - strbuf_release(&buf); + wt_status_add_cut_line(s->fp); } run_diff_index(&rev, 1); }