@@ -16,6 +16,7 @@ static struct cmt_fmt_map {
1616 const char * name ;
1717 enum cmit_fmt format ;
1818 int is_tformat ;
19+ int expand_tabs_in_log ;
1920 int is_alias ;
2021 const char * user_format ;
2122} * commit_formats ;
@@ -87,13 +88,13 @@ static int git_pretty_formats_config(const char *var, const char *value, void *c
8788static void setup_commit_formats (void )
8889{
8990 struct cmt_fmt_map builtin_formats [] = {
90- { "raw" , CMIT_FMT_RAW , 0 },
91- { "medium" , CMIT_FMT_MEDIUM , 0 },
92- { "short" , CMIT_FMT_SHORT , 0 },
93- { "email" , CMIT_FMT_EMAIL , 0 },
94- { "fuller" , CMIT_FMT_FULLER , 0 },
95- { "full" , CMIT_FMT_FULL , 0 },
96- { "oneline" , CMIT_FMT_ONELINE , 1 }
91+ { "raw" , CMIT_FMT_RAW , 0 , 0 },
92+ { "medium" , CMIT_FMT_MEDIUM , 0 , 8 },
93+ { "short" , CMIT_FMT_SHORT , 0 , 0 },
94+ { "email" , CMIT_FMT_EMAIL , 0 , 0 },
95+ { "fuller" , CMIT_FMT_FULLER , 0 , 8 },
96+ { "full" , CMIT_FMT_FULL , 0 , 8 },
97+ { "oneline" , CMIT_FMT_ONELINE , 1 , 0 }
9798 };
9899 commit_formats_len = ARRAY_SIZE (builtin_formats );
99100 builtin_formats_len = commit_formats_len ;
@@ -172,6 +173,7 @@ void get_commit_format(const char *arg, struct rev_info *rev)
172173
173174 rev -> commit_format = commit_format -> format ;
174175 rev -> use_terminator = commit_format -> is_tformat ;
176+ rev -> expand_tabs_in_log_default = commit_format -> expand_tabs_in_log ;
175177 if (commit_format -> format == CMIT_FMT_USERFORMAT ) {
176178 save_user_format (rev , commit_format -> user_format ,
177179 commit_format -> is_tformat );
@@ -1629,6 +1631,72 @@ void pp_title_line(struct pretty_print_context *pp,
16291631 strbuf_release (& title );
16301632}
16311633
1634+ static int pp_utf8_width (const char * start , const char * end )
1635+ {
1636+ int width = 0 ;
1637+ size_t remain = end - start ;
1638+
1639+ while (remain ) {
1640+ int n = utf8_width (& start , & remain );
1641+ if (n < 0 || !start )
1642+ return -1 ;
1643+ width += n ;
1644+ }
1645+ return width ;
1646+ }
1647+
1648+ static void strbuf_add_tabexpand (struct strbuf * sb , int tabwidth ,
1649+ const char * line , int linelen )
1650+ {
1651+ const char * tab ;
1652+
1653+ while ((tab = memchr (line , '\t' , linelen )) != NULL ) {
1654+ int width = pp_utf8_width (line , tab );
1655+
1656+ /*
1657+ * If it wasn't well-formed utf8, or it
1658+ * had characters with badly defined
1659+ * width (control characters etc), just
1660+ * give up on trying to align things.
1661+ */
1662+ if (width < 0 )
1663+ break ;
1664+
1665+ /* Output the data .. */
1666+ strbuf_add (sb , line , tab - line );
1667+
1668+ /* .. and the de-tabified tab */
1669+ strbuf_addchars (sb , ' ' , tabwidth - (width % tabwidth ));
1670+
1671+ /* Skip over the printed part .. */
1672+ linelen -= tab + 1 - line ;
1673+ line = tab + 1 ;
1674+ }
1675+
1676+ /*
1677+ * Print out everything after the last tab without
1678+ * worrying about width - there's nothing more to
1679+ * align.
1680+ */
1681+ strbuf_add (sb , line , linelen );
1682+ }
1683+
1684+ /*
1685+ * pp_handle_indent() prints out the intendation, and
1686+ * the whole line (without the final newline), after
1687+ * de-tabifying.
1688+ */
1689+ static void pp_handle_indent (struct pretty_print_context * pp ,
1690+ struct strbuf * sb , int indent ,
1691+ const char * line , int linelen )
1692+ {
1693+ strbuf_addchars (sb , ' ' , indent );
1694+ if (pp -> expand_tabs_in_log )
1695+ strbuf_add_tabexpand (sb , pp -> expand_tabs_in_log , line , linelen );
1696+ else
1697+ strbuf_add (sb , line , linelen );
1698+ }
1699+
16321700void pp_remainder (struct pretty_print_context * pp ,
16331701 const char * * msg_p ,
16341702 struct strbuf * sb ,
@@ -1653,8 +1721,12 @@ void pp_remainder(struct pretty_print_context *pp,
16531721
16541722 strbuf_grow (sb , linelen + indent + 20 );
16551723 if (indent )
1656- strbuf_addchars (sb , ' ' , indent );
1657- strbuf_add (sb , line , linelen );
1724+ pp_handle_indent (pp , sb , indent , line , linelen );
1725+ else if (pp -> expand_tabs_in_log )
1726+ strbuf_add_tabexpand (sb , pp -> expand_tabs_in_log ,
1727+ line , linelen );
1728+ else
1729+ strbuf_add (sb , line , linelen );
16581730 strbuf_addch (sb , '\n' );
16591731 }
16601732}
0 commit comments