From: Eric Blake Date: Mon, 15 Oct 2007 18:18:24 +0000 (-0600) Subject: Enhance AS_HELP_STRING. X-Git-Tag: v2.62~212^2~5 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=10a850e84a0b7c20a59692a19c47e1048f2d086f;p=thirdparty%2Fautoconf.git Enhance AS_HELP_STRING. * lib/m4sugar/m4sugar.m4 (m4_text_wrap): Don't expand arguments, and reduce number of expansions. * lib/m4sugar/m4sh.m4 (AS_HELP_STRING): Rework to use m4_expand, and to take indent and wrap column numbers. * tests/m4sh.at (AS@&t@_HELP_STRING): Update the test. * doc/autoconf.texi (Pretty Help Strings): Document details about arguments. (Text processing Macros): Minor tweaks. * NEWS: Document this change. Signed-off-by: Eric Blake --- diff --git a/ChangeLog b/ChangeLog index 3d25d0dd..c6654850 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,16 @@ 2007-10-15 Eric Blake + Enhance AS_HELP_STRING. + * lib/m4sugar/m4sugar.m4 (m4_text_wrap): Don't expand arguments, + and reduce number of expansions. + * lib/m4sugar/m4sh.m4 (AS_HELP_STRING): Rework to use m4_expand, + and to take indent and wrap column numbers. + * tests/m4sh.at (AS@&t@_HELP_STRING): Update the test. + * doc/autoconf.texi (Pretty Help Strings): Document details about + arguments. + (Text processing Macros): Minor tweaks. + * NEWS: Document this change. + Fix 2007-10-03 regression with AT_SETUP([a, b]). * lib/m4sugar/m4sugar.m4 (m4_expand): New macro. (m4_text_box): Use it. diff --git a/NEWS b/NEWS index 8804f939..e4239065 100644 --- a/NEWS +++ b/NEWS @@ -50,7 +50,13 @@ GNU Autoconf NEWS - User visible changes. ** AC_USE_SYSTEM_EXTENSIONS now defines _ALL_SOURCE for Interix platforms. -** AS_HELP_STRING no longer underquotes its first argument. +** AS_HELP_STRING no longer underquotes its first argument; it also handles + the case where the first argument contains single-quoted commas. + For example, "AS_HELP_STRING([-a, [--arg[=foo]]], [bar])" produces: + " -a, --arg=[foo] bar" + Additionally, the macro now takes two additional arguments, + indent-column and wrap-column; these should not normally be needed, + but can be used to fine-tune how the output text is wrapped. ** The command 'autoconf -' now correctly processes a file from stdin. diff --git a/doc/autoconf.texi b/doc/autoconf.texi index fb7a3ad9..addb7b1a 100644 --- a/doc/autoconf.texi +++ b/doc/autoconf.texi @@ -10821,9 +10821,9 @@ are expanded during this macro; instead, they are expanded when @code{m4_append} can be used to grow strings, and @code{m4_append_uniq} to grow strings without duplicating substrings. Additionally, -@code{m4_append_uniq} takes two optional parameters; @var{if-uniq} is -expanded if @var{string} was appended, and @var{if-duplicate} is -expanded if @var{string} was already present. +@code{m4_append_uniq} takes two optional parameters as of Autoconf 2.62; +@var{if-uniq} is expanded if @var{string} was appended, and +@var{if-duplicate} is expanded if @var{string} was already present. @example m4_define([active], [ACTIVE])dnl @@ -10935,25 +10935,27 @@ format those words to wrap within @var{width} columns, and without trailing whitespace. If given, @var{prefix1} is prepended to the first line, and @var{prefix} is prepended to each continuation line. As a special case, if @var{prefix1} is longer than @var{prefix}, the first -line will consist solely of @var{prefix1}. +line will consist solely of @var{prefix1}. No expansions occur on +@var{prefix}, @var{prefix1}, or the words of @var{string}, although +quadrigraphs are recognized. For some examples: @example -m4_text_wrap([Short string */], [@ @ @ ], [/* ], [20]) +m4_text_wrap([Short string */], [ ], [/* ], [20]) @result{}/* Short string */ -m4_text_wrap([Much longer string */], [@ @ @ ], [/* ], [20]) +m4_text_wrap([Much longer string */], [ ], [/* ], [20]) @result{}/* Much longer -@result{}@ @ @ string */ -m4_text_wrap([Short doc.], [@ @ @ @ @ @ @ @ @ @ ], [@ @ --short ], [30]) -@result{}@ @ --short Short doc. -m4_text_wrap([Short doc.], [@ @ @ @ @ @ @ @ @ @ ], [@ @ --too-wide ], [30]) -@result{}@ @ --too-wide -@result{}@ @ @ @ @ @ @ @ @ @ Short doc. -m4_text_wrap([Super long documentation.], [@ @ @ @ @ ], - [@ @ --too-wide ], 30) -@result{}@ @ --too-wide -@result{}@ @ @ @ @ Super long -@result{}@ @ @ @ @ documentation. +@result{} string */ +m4_text_wrap([Short doc.], [ ], [ --short ], [30]) +@result{} --short Short doc. +m4_text_wrap([Short doc.], [ ], [ --too-wide ], [30]) +@result{} --too-wide +@result{} Short doc. +m4_text_wrap([Super long documentation.], [ ], + [ --too-wide ], 30) +@result{} --too-wide +@result{} Super long +@result{} documentation. @end example @end defmac @@ -17199,7 +17201,8 @@ your own @samp{help strings} to line up in the appropriate columns of strings} do. This is the purpose of the @code{AS_HELP_STRING} macro. @anchor{AS_HELP_STRING} -@defmac AS_HELP_STRING (@var{left-hand-side}, @var{right-hand-side}) +@defmac AS_HELP_STRING (@var{left-hand-side}, @var{right-hand-side} @ + @dvar{indent-column, 26}, @dvar{wrap-column, 79}) @asindex{HELP_STRING} Expands into an help string that looks pretty when the user executes @@ -17215,9 +17218,6 @@ AC_ARG_WITH([foo], [use_foo=no]) @end example -The second argument of @code{AS_HELP_STRING} is -not a literal, and should not be double quoted. -@xref{Autoconf Language}, for a more detailed explanation. Then the last few lines of @samp{configure --help} appear like this: @@ -17226,16 +17226,42 @@ this: --with-foo use foo (default is no) @end example +Macro expansion is performed on the first argument. However, the second +argument of @code{AS_HELP_STRING} is treated as a whitespace separated +list of text to be reformatted, and is not subject to macro expansion. +Since it is not expanded, it should not be double quoted. +@xref{Autoconf Language}, for a more detailed explanation. + The @code{AS_HELP_STRING} macro is particularly helpful when the @var{left-hand-side} and/or @var{right-hand-side} are composed of macro arguments, as shown in the following example. @example AC_DEFUN([MY_ARG_WITH], - [AC_ARG_WITH([$1], - [AS_HELP_STRING([--with-$1], [use $1 (default is $2)])], + [AC_ARG_WITH(m4_translit([[$1]], [_], [-]), + [AS_HELP_STRING([--with-m4_translit([$1], [_], [-])], + [use $1 (default is $2)])], [use_[]$1=$withval], [use_[]$1=$2])]) +MY_ARG_WITH([a_b], [no]) +@end example +@noindent +Here, the last few lines of @samp{configure --help} will include: + +@example +--enable and --with options recognized: + --with-a-b use a_b (default is no) +@end example + +The parameters @var{indent-column} and @var{wrap-column} were introduced +in Autoconf 2.62. Generally, they should not be specified; they exist +for fine-tuning of the wrapping. +@example +AS_HELP_STRING([--option], [description of option]) +@result{} --option description of option +AS_HELP_STRING([--option], [description of option], [15], [30]) +@result{} --option description of +@result{} option @end example @end defmac diff --git a/lib/m4sugar/m4sh.m4 b/lib/m4sugar/m4sh.m4 index 31fecbcc..debf2084 100644 --- a/lib/m4sugar/m4sh.m4 +++ b/lib/m4sugar/m4sh.m4 @@ -1158,14 +1158,21 @@ m4_define([_AS_BOX_INDIR], _ASBOX]) -# AS_HELP_STRING(LHS, RHS, [COLUMN]) -# ---------------------------------- +# AS_HELP_STRING(LHS, RHS, [INDENT-COLUMN = 26], [WRAP-COLUMN = 79]) +# ------------------------------------------------------------------ +# +# Format a help string so that it looks pretty when the user executes +# "script --help". This macro takes up to four arguments, a +# "left hand side" (LHS), a "right hand side" (RHS), a decimal +# INDENT-COLUMN which is the column where wrapped lines should begin +# (the default of 26 is recommended), and a decimal WRAP-COLUMN which is +# the column where lines should wrap (the default of 79 is recommended). +# LHS is expanded, RHS is not. # -# Format a help string so that it looks pretty when -# the user executes "script --help". This macro takes three -# arguments, a "left hand side" (LHS), a "right hand side" (RHS), and -# the COLUMN which is a string of white spaces which leads to the -# the RHS column (default: 26 white spaces). +# For backwards compatibility not documented in the manual, INDENT-COLUMN +# can also be specified as a string of white spaces, whose width +# determines the indentation column. Using TABs in INDENT-COLUMN is not +# recommended, since screen width of TAB is not computed. # # The resulting string is suitable for use in other macros that require # a help string (e.g. AC_ARG_WITH). @@ -1185,9 +1192,9 @@ _ASBOX]) # "--with-readline", while the RHS is "support fancy command line # editing". # -# If the LHS contains more than (COLUMN - 3) characters, then the LHS is -# terminated with a newline so that the RHS starts on a line of its own -# beginning with COLUMN. In the default case, this corresponds to an +# If the LHS contains more than (INDENT-COLUMN - 3) characters, then the +# LHS is terminated with a newline so that the RHS starts on a line of its +# own beginning at INDENT-COLUMN. In the default case, this corresponds to an # LHS with more than 23 characters. # # Therefore, in the example, if the LHS were instead @@ -1206,12 +1213,10 @@ _ASBOX]) # know quadrigraphs. # m4_define([AS_HELP_STRING], -[m4_pushdef([AS_Prefix], m4_default([$3], [ ]))dnl -m4_pushdef([AS_Prefix_Format], - [ %-]m4_eval(m4_len(AS_Prefix) - 3)[s ])dnl [ %-23s ] -m4_text_wrap([$2], AS_Prefix, m4_format(AS_Prefix_Format, [[$1]]))dnl -m4_popdef([AS_Prefix_Format])dnl -m4_popdef([AS_Prefix])dnl +[m4_text_wrap([$2], m4_cond([[$3]], [], [ ], + [m4_eval([$3]+0)], [0], [[$3]], + [m4_format([[%*s]], [$3], [])]), + m4_expand([ $1 ]), [$4])dnl ])# AS_HELP_STRING diff --git a/lib/m4sugar/m4sugar.m4 b/lib/m4sugar/m4sugar.m4 index dc9f1da1..9b3a615b 100644 --- a/lib/m4sugar/m4sugar.m4 +++ b/lib/m4sugar/m4sugar.m4 @@ -1785,6 +1785,9 @@ m4_define([m4_append_uniq], # if the length of FIRST-PREFIX is greater than that of PREFIX, then # FIRST-PREFIX will be left alone on the first line. # +# No expansion occurs on the contents STRING, PREFIX, or FIRST-PREFIX, +# although quadrigraphs are correctly recognized. +# # Typical outputs are: # # m4_text_wrap([Short string */], [ ], [/* ], 20) @@ -1815,44 +1818,49 @@ m4_define([m4_append_uniq], # all the words are preceded by m4_Separator which is defined to empty for # the first word, and then ` ' (single space) for all the others. # -# The algorithm overquotes m4_Prefix1 to avoid m4_defn overhead, and bypasses -# m4_popdef overhead with m4_builtin since no user macro expansion occurs in -# the meantime. +# The algorithm overquotes m4_Prefix and m4_Prefix1 to avoid m4_defn +# overhead, and bypasses m4_popdef overhead with m4_builtin since no user +# macro expansion occurs in the meantime. Also, the definition is written +# with m4_do, to avoid time wasted on dnl during expansion (since this is +# already a time-consuming macro). m4_define([m4_text_wrap], -[m4_pushdef([m4_Prefix], [$2])dnl -m4_pushdef([m4_Prefix1], m4_dquote(m4_default([$3], [m4_Prefix])))dnl -m4_pushdef([m4_Width], m4_default([$4], 79))dnl -m4_pushdef([m4_Cursor], m4_qlen(m4_Prefix1))dnl -m4_pushdef([m4_Separator], [])dnl -m4_Prefix1[]dnl -m4_cond([m4_eval(m4_qlen(m4_Prefix1) > m4_len(m4_Prefix))], - [1], [m4_define([m4_Cursor], m4_len(m4_Prefix)) -m4_Prefix], - [m4_eval(m4_qlen(m4_Prefix1) < m4_len(m4_Prefix))], - [0], [], - [m4_define([m4_Cursor], m4_len(m4_Prefix))[]dnl -m4_format([%*s], - m4_max([0], m4_eval(m4_len(m4_Prefix) - m4_qlen(m4_Prefix1))), - [])])[]dnl -m4_foreach_w([m4_Word], [$1], -[m4_define([m4_Cursor], - m4_eval(m4_Cursor + m4_qlen(m4_builtin([defn], [m4_Word])) + 1))dnl -dnl New line if too long, else insert a space unless it is the first -dnl of the words. -m4_if(m4_eval(m4_Cursor > m4_Width), - 1, [m4_define([m4_Cursor], - m4_eval(m4_len(m4_Prefix) - + m4_qlen(m4_builtin([defn], [m4_Word])) + 1))] -m4_Prefix, - [m4_Separator])[]dnl -m4_builtin([defn], [m4_Word])[]dnl -m4_define([m4_Separator], [ ])])dnl -m4_builtin([popdef], [m4_Separator])dnl -m4_builtin([popdef], [m4_Cursor])dnl -m4_builtin([popdef], [m4_Width])dnl -m4_builtin([popdef], [m4_Prefix1])dnl -m4_builtin([popdef], [m4_Prefix])dnl -]) +m4_do(dnl set up local variables, to avoid repeated calculations +[[m4_pushdef([m4_Prefix], [[$2]])]], +[[m4_pushdef([m4_Prefix1], m4_if([$3], [], [m4_Prefix], [[[$3]]]))]], +[[m4_pushdef([m4_Width], m4_default([$4], 79))]], +[[m4_pushdef([m4_Indent], m4_qlen(m4_Prefix))]], +[[m4_pushdef([m4_Cursor], m4_qlen(m4_Prefix1))]], +[[m4_pushdef([m4_Separator], [m4_define([m4_Separator], [ ])])]], +dnl expand the first prefix, then check its length vs. regular prefix +dnl same length: nothing special +dnl prefix1 longer: output on line by itself, and reset cursor +dnl prefix1 shorter: pad to length of prefix, and reset cursor +[[m4_Prefix1[]m4_cond([m4_Cursor], m4_Indent, [], + [m4_eval(m4_Cursor > m4_Indent)], [1], [ +m4_Prefix[]m4_define([m4_Cursor], m4_Indent)], + [m4_format([%*s], m4_max([0], + m4_eval(m4_Indent - m4_Cursor)), [])m4_define([m4_Cursor], m4_Indent)])]], +dnl now, for each word, compute the curser after the word is output, then +dnl check if the cursor would exceed the wrap column +dnl if so, reset cursor, and insert newline and prefix +dnl if not, insert the separator (usually a space) +dnl either way, insert the word +[[m4_foreach_w([m4_Word], [$1], + [m4_define([m4_Cursor], + m4_eval(m4_Cursor + m4_qlen(m4_builtin([defn], [m4_Word])) + + 1))m4_if(m4_eval(m4_Cursor > m4_Width), + [1], [m4_define([m4_Cursor], + m4_eval(m4_Indent + + m4_qlen(m4_builtin([defn], [m4_Word])) + 1)) +m4_Prefix[]], + [m4_Separator[]])m4_builtin([defn], [m4_Word])])]], +dnl finally, clean up the local variabls +[[m4_builtin([popdef], [m4_Separator])]], +[[m4_builtin([popdef], [m4_Cursor])]], +[[m4_builtin([popdef], [m4_Indent])]], +[[m4_builtin([popdef], [m4_Width])]], +[[m4_builtin([popdef], [m4_Prefix1])]], +[[m4_builtin([popdef], [m4_Prefix])]])) # m4_text_box(MESSAGE, [FRAME-CHARACTER = `-']) diff --git a/tests/m4sh.at b/tests/m4sh.at index a523785b..9c6624cd 100644 --- a/tests/m4sh.at +++ b/tests/m4sh.at @@ -490,10 +490,8 @@ AT_CLEANUP ## AS_HELP_STRING ## ## -------------- ## -# I'm not totally certain that we want to enforce the defaults here, -# but at least it is being tested. - AT_SETUP([AS@&t@_HELP_STRING]) +AT_KEYWORDS([m4@&t@_text_wrap]) AT_DATA_M4SH([script.as], [[AS_INIT @@ -545,6 +543,18 @@ echo "AS_HELP_STRING([[--foo[=bar]123456789012]], [some other t[]t which should wrap at our default of 80 characters.])" echo "AS_HELP_STRING([[--foo[=bar]1234567890123]], [some other t[]t which should wrap at our default of 80 characters.])" +m4_define([mac], [MACRO])dnl +echo "AS_HELP_STRING([--mac], [mac])" +echo "AS_HELP_STRING([--o1, --o2], [two +options, one description])" +echo "AS_HELP_STRING([--tune1], [check out the tuned formatting], +[ ])" +echo "AS_HELP_STRING([--tune2], [check out the tuned formatting], +[12])" +echo "AS_HELP_STRING([--tune3], [check out the tuned formatting], +[], [40])" +echo "AS_HELP_STRING([--tune4], [check out the tuned formatting], +[12], [40])" ]]) AT_CHECK_M4SH @@ -600,6 +610,15 @@ AT_CHECK([./script], [0], --foo[=bar]1234567890123 some other t[]t which should wrap at our default of 80 characters. + --MACRO mac + --o1, --o2 two options, one description + --tune1 check out the tuned formatting + --tune2 check out the tuned formatting + --tune3 check out the + tuned + formatting + --tune4 check out the tuned + formatting ]]) AT_CLEANUP