Skip to content

Commit 36da314

Browse files
committed
POSIX compliance fix: apply 'set -u' to $1, $2, ...
POSIX requires[*] that expanding any unset parameter other than $@ and $* is an error when 'set -u'/'set -o nounset' is active. However, on ksh93, $1, $2, ... were exempt as well. That is a bug. [*] https://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_25 src/cmd/ksh93/sh/macro.c: - varsub(): Backport code for handling 'set -u' for positional parameters from the ast 2016-10-01-beta branch. src/cmd/ksh93/tests/options.sh: - Add relevant regression tests. src/cmd/ksh93/sh.1: - Document that $@ and $* are exempt from 'set -u'. (cherry picked from commit f954c6be0748c4c38a680a75f27564965fbd328e)
1 parent e2a648b commit 36da314

File tree

5 files changed

+22
-1
lines changed

5 files changed

+22
-1
lines changed

NEWS

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,12 @@ For full details, see the git log at:
44

55
Any uppercase BUG_* names are modernish shell bug IDs.
66

7+
2020-06-08:
8+
9+
- If 'set -u'/'set -o nounset' is active, then the shell now errors out if a
10+
nonexistent positional parameter such as $1, $2, ... is accessed, as other
11+
shells do and POSIX requires. (This does *not* apply to "$@" and "$*".)
12+
713
2020-06-06:
814

915
- The 'times' command is now a builtin command that conforms to POSIX

src/cmd/ksh93/include/version.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,4 +17,4 @@
1717
* David Korn <dgk@research.att.com> *
1818
* *
1919
***********************************************************************/
20-
#define SH_RELEASE "93u+m 2020-06-06"
20+
#define SH_RELEASE "93u+m 2020-06-08"

src/cmd/ksh93/sh.1

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7041,6 +7041,10 @@ Sort the positional parameters lexicographically.
70417041
.TP 8
70427042
.B \-u
70437043
Treat unset parameters as an error when substituting.
7044+
.B "$@"
7045+
and
7046+
.B "$\(**"
7047+
are exempt.
70447048
.TP 8
70457049
.B \-v
70467050
Print shell input lines as they are read.

src/cmd/ksh93/sh/macro.c

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1195,6 +1195,14 @@ static int varsub(Mac_t *mp)
11951195
}
11961196
else
11971197
v = 0;
1198+
/* Handle 'set -u'/'set -o nounset' for positional parameters */
1199+
if(!v && sh_isoption(SH_NOUNSET))
1200+
{
1201+
d=fcget();
1202+
fcseek(-1);
1203+
if(!(d && strchr(":+-?=",d)))
1204+
errormsg(SH_DICT,ERROR_exit(1),e_notset,ltos(c));
1205+
}
11981206
break;
11991207
case S_ALP:
12001208
if(c=='.' && type==0)

src/cmd/ksh93/tests/options.sh

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -512,6 +512,9 @@ $SHELL -uc 'var=foo;unset var;: ${!var}' >/dev/null 2>&1 && err_exit '${!var} sh
512512
$SHELL -uc 'var=foo;unset var;: ${#var}' >/dev/null 2>&1 && err_exit '${#var} should fail with set -u'
513513
$SHELL -uc 'var=foo;unset var;: ${var-OK}' >/dev/null 2>&1 || err_exit '${var-OK} should not fail with set -u'
514514
$SHELL -uc 'var=foo;nset var;: ${var:-OK}' >/dev/null 2>&1 || err_exit '${var:-OK} should not fail with set -u'
515+
(set -u -- one two; : $2) 2>/dev/null || err_exit "an unset PP failed with set -u"
516+
(set -u -- one two; : $3) 2>/dev/null && err_exit "a set PP failed to fail with set -u"
517+
(set -u --; : $@ $*) 2>/dev/null || err_exit '$@ and/or $* fail to be exempt from set -u'
515518

516519
z=$($SHELL 2>&1 -uc 'print ${X23456789012345}')
517520
[[ $z == *X23456789012345:* ]] || err_exit "error message garbled with set -u got $z"

0 commit comments

Comments
 (0)