Skip to content

Commit

Permalink
Merge pull request #62 from matejak/double_quotes
Browse files Browse the repository at this point in the history
Escape double quotes for help messages iff the provided string is unquoted
  • Loading branch information
matejak authored Jan 16, 2019
2 parents 49c80e5 + 71ba74f commit 3c80fc3
Show file tree
Hide file tree
Showing 8 changed files with 29 additions and 14 deletions.
1 change: 1 addition & 0 deletions ChangeLog
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ New features:

* Allow argbash and argbash-init to be run from symbolic links.
* Allow scripts generated by argbash-init with complete separation (`-s -s`) to be run from a symbolic link.
* Double quotes in help messages are escaped (fixes #61).


2.7.1 (2018-08-15)
Expand Down
7 changes: 4 additions & 3 deletions src/stuff.m4
Original file line number Diff line number Diff line change
Expand Up @@ -229,7 +229,7 @@ m4_define([_MAKE_HELP_FUNCTION_POSITIONAL_PART], [m4_lists_foreach_positional(
],
[m4_pushdef([argname1], <m4_dquote(argname0)[[]m4_ifnblank(m4_quote($][1), m4_quote(-$][1))]>)],
[m4_pushdef([argname], m4_if(_arg_type, [inf], [m4_default(_INF_REPR, argname1)], [[argname1($][@)]]))],
[_INDENT_()[printf '\t%s\n' "]argname[: ]_SUBSTITUTE_LF_FOR_NEWLINE_AND_INDENT(_msg)],
[_INDENT_()[printf '\t%s\n' "]argname[: ]_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES(_msg)],
[_POS_ARG_HELP_DEFAULTS([argname], _arg_type, _min_argn, _defaults)],
[m4_popdef([argname])],
[m4_popdef([argname1])],
Expand All @@ -252,7 +252,7 @@ m4_define([_MAKE_PRINTF_OPTARG_HELP_STATEMENTS], [m4_do(
[string], [],
[_GET_VALUE_DESC([$1])])])])],
[m4_pushdef([_options], [$6([$1], [$2], [$3])])],
[m4_pushdef([_help_msg], [_SUBSTITUTE_LF_FOR_NEWLINE_AND_INDENT([$5])])],
[m4_pushdef([_help_msg], [_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES([$5])])],
[m4_case([$3],
[action],
[_INDENT_()[printf '\t%s\n'] "_options: _help_msg"],
Expand Down Expand Up @@ -343,7 +343,7 @@ m4_define([_MAKE_HELP], [MAKE_FUNCTION(
[and it makes sense to remind the user how the script is supposed to be called.]],
[print_help], [m4_do(
[m4_ifnblank(m4_expand([_HELP_MSG]),
m4_dquote(_INDENT_()[printf] '%s\n' "_SUBSTITUTE_LF_FOR_NEWLINE_AND_INDENT(_HELP_MSG)"_ENDL_()))],
m4_dquote(_INDENT_()[printf] '%s\n' "_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES(_HELP_MSG)"_ENDL_()))],
[_INDENT_()[]printf 'Usage: %s],
[dnl If we have optionals, display them like [--opt1 arg] [--(no-)opt2] ... according to their type. @<:@ becomes square bracket at the end of processing
],
Expand Down Expand Up @@ -1079,6 +1079,7 @@ dnl $1: argname macro
dnl $2: _arg_type
dnl $3: _min_argn
dnl $4: _defaults
dnl TODO: The changed doublequote-escape behavior may have ugly side-effects.
dnl
m4_define([_MAKE_DEFAULTS_FOR_MULTIVALUED_ARGUMENTS], [m4_do(
[@{:@],
Expand Down
17 changes: 10 additions & 7 deletions src/utilities.m4
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,9 @@ m4_define([_CHECK_INTEGER_TYPE],
dnl
dnl Encloses string into "" if its first char is not ' or "
dnl If first char of string is not ' or " enclose it into ""
dnl and escape " with \".
dnl
dnl The string is also []-quoted
dnl Property: Quoting a blank input results in blank result
dnl to AVOID it, pass string like ""ls -l or "ls" -l
Expand All @@ -58,9 +60,7 @@ dnl $1: String to quote
m4_define([_sh_quote], [m4_do(
[m4_if(
[$1], , ,
m4_index([$1], [']), 0, [[$1]],
m4_index([$1], ["]), 0, [[$1]],
[["$1"]])],
m4_dquote(_sh_quote_also_blanks([$1])))],
)])
Expand All @@ -74,7 +74,6 @@ m4_define([_sh_quote_also_blanks], [m4_do(
[["$1"]])],
)])
dnl
dnl Define a macro that is part of the public API
dnl Ensure the replication and also add the macro name to a list of allowed macros
Expand Down Expand Up @@ -120,13 +119,17 @@ m4_define([_COMMENT], [m4_ifdef([COMMENT_OUTPUT], [$1])])
dnl
dnl $1: The text to substitute
dnl Regexp: Find beginning of backslashes, match for pairs, and if \\n is left, then substitute it for literal newline.
m4_define([_SUBSTITUTE_LF_FOR_NEWLINE_AND_INDENT], [m4_bpatsubst([[$1]], [\([^\\]\)\(\\\\\)*\\n], [\1\2
])])
dnl The indentation is a display indentation - not source code one.
m4_define([_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES],
[m4_bpatsubsts([[$1]],
[\([^\\]\)\(\\\\\)*\\n], m4_expand([[\1\2]_ENDL_() ]),
[\([^\]\)"], [\1\\"])])
m4_define([_CHECK_PASSED_ARGS_COUNT_TOO_FEW],
[m4_fatal([You have passed $2 arguments to macro $1, while it requires at least $3.]m4_ifnblank([$4], [ Call it like: $4]))])
m4_define([_CHECK_PASSED_ARGS_COUNT_TOO_MANY],
[m4_fatal([You have passed $2 arguments to macro $1, while it accepts at most $3.]m4_ifnblank([$4], [ Call it like: $4]))])
Expand Down
2 changes: 2 additions & 0 deletions tests/regressiontests/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -357,6 +357,7 @@ test-simple: $(TESTDIR)/test-simple.sh
$< -h | grep -q '^ -BEGIN'
$< -h | grep -q -v '^\s*-BEGIN2'
$< -h | grep -q -v 'END2-$$'
$< -h | grep -q '"line 2" END-\\n'
$< -h | grep -q '^ -PBEGIN'
$< -h | grep -q 'PEND-$$'
grep -q '^ esac' $<
Expand All @@ -376,6 +377,7 @@ test-simple-dash: $(TESTDIR)/test-simple-dash.sh
$< -h | grep -q '^ -BEGIN'
$< -h | grep -q -v '^\s*-BEGIN2'
$< -h | grep -q -v 'END2-$$'
$< -h | grep -q '"line 2" END-\\n'
$< -h | grep -q '^ -PBEGIN'
$< -h | grep -q 'PEND-$$'
grep -q '^ esac' $<
Expand Down
1 change: 1 addition & 0 deletions tests/regressiontests/make/tests/tests-base.m4
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,7 @@ m4_define([test_simple_body], [[
$< -h | grep -q '^ -BEGIN'
$< -h | grep -q -v '^\s*-BEGIN2'
$< -h | grep -q -v 'END2-$$'
$< -h | grep -q '"line 2" END-\\n'
$< -h | grep -q '^ -PBEGIN'
$< -h | grep -q 'PEND-$$'
grep -q '^ esac' $<
Expand Down
2 changes: 1 addition & 1 deletion tests/regressiontests/test-simple.m4
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#!/bin/bash -e

# ARG_POSITIONAL_SINGLE([pos-arg], [help line PEND-\n-PBEGIN])
# ARG_OPTIONAL_SINGLE([prefix],[o],[help line END-\n-BEGIN line 2END-\\n-2BEGIN],[x])
# ARG_OPTIONAL_SINGLE([prefix],[o],[help line END-\n-BEGIN "line 2" END-\\n-2BEGIN],[x])
# ARG_VERSION([echo "$0 FOO"])
# ARG_HELP([Testing program m4_fatal(BOOM!)], [m4_fatal([CRASH!])])
# ARG_DEFAULTS_POS()
Expand Down
10 changes: 7 additions & 3 deletions tests/unittests/check-indentation.m4
Original file line number Diff line number Diff line change
Expand Up @@ -57,10 +57,14 @@ assert_equals(_POSSIBLY_REPEATED_COMMENT_BLOCK([comment-topic], [comment at ther
assert_equals(_POSSIBLY_REPEATED_COMMENT_BLOCK([comment-topic], [here], 1, x, [BOMB]), [ # comment at there BOMB
])

assert_equals(_SUBSTITUTE_LF_FOR_NEWLINE_AND_INDENT([first\nsecond]), [first
assert_equals(_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES([first\nsecond]), [first
second])

assert_equals(_SUBSTITUTE_LF_FOR_NEWLINE_AND_INDENT([first\\nsecond]), [first\\nsecond])
assert_equals(_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES([first\nsecond\nthird]), [first
second
third])
assert_equals(_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES([first\\nsecond]), [first\\nsecond])
assert_equals(_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES(x "y z"), [x \"y z\"])
assert_equals(_SUBSTITUTE_LF_FOR_NEWLINE_WITH_DISPLAY_INDENT_AND_ESCAPE_DOUBLEQUOTES([x \"m4_ignore() z"]), [x \"m4_ignore() z\"])

assert_equals(m4_quote(_COMMENT_CHAIN([BOMB], [two])), [BOMB,two])

Expand Down
3 changes: 3 additions & 0 deletions tests/unittests/check-utils.m4
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,11 @@ assert_equals(m4_lists_foreach([FOO,BAR,BAZ],[fu,ba,za],[fu: ba-za@]),

assert_equals(_sh_quote(), [])
assert_equals(_sh_quote(x), ["x"])
assert_equals(_sh_quote([m4_ignore()]), ["m4_ignore()"])
assert_equals(_sh_quote("x"), ["x"])
assert_equals(_sh_quote("x "f f""), ["x "f f""])
assert_equals(_sh_quote('x'), ['x'])
assert_equals(_sh_quote(['x "m4_ignore()\"']), ['x "m4_ignore()\"'])

assert_equals(_sh_quote_also_blanks(), [""])
assert_equals(_sh_quote_also_blanks(x), ["x"])
Expand Down

0 comments on commit 3c80fc3

Please sign in to comment.