From 577b4d35ca96ca6c39b365cab797ca3c1d83b4bb Mon Sep 17 00:00:00 2001 From: Rob Landley Date: Fri, 16 Jun 2023 23:54:05 -0500 Subject: [PATCH] Fix ${X::} with no args, and add various tests. --- tests/sh.test | 12 ++++++++++++ toys/pending/sh.c | 7 +++++-- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/tests/sh.test b/tests/sh.test index 5dd4d4f4..9f7a762c 100644 --- a/tests/sh.test +++ b/tests/sh.test @@ -108,6 +108,10 @@ testing 'trailing $ is literal' 'echo $' '$\n' '' '' testing 'work after HERE' $'cat<<0;echo hello\npotato\n0' 'potato\nhello\n' '' '' testing '<<""' $'cat<<"";echo hello\npotato\n\necho huh' 'potato\nhello\nhuh\n'\ '' '' +testing '<< trailing \' $'cat</dev/null\nabcde\nnext\\\nEOF\nEOF' \ + 'abcde\nnextEOF\n' '' '' +testing '<< trailing \ 2' $'cat<&1 | grep -o bad' 'bad\n' '' '' +shxpect '${:} empty len is err' I$'ABC=def; echo ${ABC:}\n' RE'ABC' X +testing '${::} both empty=0' 'ABC=def; echo ${ABC::}' '\n' '' '' +testing '${::} first empty' 'ABC=def; echo ${ABC: : 2 }' 'de\n' '' '' +testing '${::} second empty' 'ABC=def; echo ${ABC: 2 : }' '\n' '' '' testing '${:}' 'ABC=def; echo ${ABC:1}' 'ef\n' '' '' testing '${a: }' 'ABC=def; echo ${ABC: 1}' 'ef\n' '' '' testing '${a :}' 'ABC=def; { echo ${ABC :1};} 2>&1 | grep -o bad' 'bad\n' '' '' @@ -683,6 +691,10 @@ testing '[[1<2]] is alphabetical, not numeric' '[[ 123 < 19 ]] && echo yes' \ 'yes\n' '' '' testing '[[~]]' '[[ ~ == $HOME ]] && echo yes' 'yes\n' '' '' +testing 'quoting contexts nest' \ + $'echo -n "$(echo "hello $(eval $\'echo -\\\\\\ne \\\'world\\n \\\'\')")"' \ + 'hello world\n ' '' '' + # TODO finish variable list from shell init # $# $? $- $! $0 # $$ diff --git a/toys/pending/sh.c b/toys/pending/sh.c index 1b53acc3..78773b0a 100644 --- a/toys/pending/sh.c +++ b/toys/pending/sh.c @@ -31,6 +31,7 @@ * TODO: test that $PS1 color changes work without stupid \[ \] hack * TODO: Handle embedded NUL bytes in the command line? (When/how?) * TODO: set -e -o pipefail, shopt -s nullglob + * TODO: utf8 isspace * * bash man page: * control operators || & && ; ;; ;& ;;& ( ) | |& @@ -2058,9 +2059,11 @@ barf: long long la = 0, lb = LLONG_MAX, lc = 1; ss = ++slice; - if ((lc = recalculate(&la, &ss, 0)) && *ss == ':') { + nospace(&ss); + if ((*ss==':' ? 1 : (lc = recalculate(&la, &ss, 0))) && *ss == ':') { ss++; - lc = recalculate(&lb, &ss, 0); + if (**nospace(&ss)=='}') lb = 0; + else lc = recalculate(&lb, &ss, 0); } if (!lc || *ss != '}') { for (s = ss; *s != '}' && *s != ':'; s++); -- 2.39.2