From 6c71c5ec4fe8d4adf56f679ef350e33e8454590b Mon Sep 17 00:00:00 2001 From: Martijn Dekker Date: Sat, 16 Jul 2022 05:20:13 +0200 Subject: [PATCH] Properly block .sh.level and .sh.value discipline functions These now give an "invalid discipline function" error instead of being silently ignored or crashing the shell. --- src/cmd/ksh93/sh/nvdisc.c | 4 +++- src/cmd/ksh93/tests/variables.sh | 14 ++++++++++++++ 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/src/cmd/ksh93/sh/nvdisc.c b/src/cmd/ksh93/sh/nvdisc.c index 6fce69bd5..e543853d9 100644 --- a/src/cmd/ksh93/sh/nvdisc.c +++ b/src/cmd/ksh93/sh/nvdisc.c @@ -507,6 +507,8 @@ char *nv_setdisc(register Namval_t* np,register const char *event,Namval_t *acti if (type < 0) return(NIL(char*)); /* Handle GET/SET/APPEND/UNSET disc */ + if(np==SH_VALNOD || np==SH_LEVELNOD) + return(0); if(vp && vp->fun.disc->putval!=assign) vp = 0; if(!vp) @@ -529,7 +531,7 @@ char *nv_setdisc(register Namval_t* np,register const char *event,Namval_t *acti action = vp->disc[type]; empty = 0; } - else if(action && np!=SH_LEVELNOD) + else if(action) { Namdisc_t *dp = (Namdisc_t*)vp->fun.disc; dp->getval = lookup; diff --git a/src/cmd/ksh93/tests/variables.sh b/src/cmd/ksh93/tests/variables.sh index f3414e282..1c72af658 100755 --- a/src/cmd/ksh93/tests/variables.sh +++ b/src/cmd/ksh93/tests/variables.sh @@ -1401,5 +1401,19 @@ exp=$'0\n1\n1' [[ $got == "$exp" ]] || err_exit '${.sh.level} in dot script not correct' \ "(expected $(printf %q "$exp"), got $(printf %q "$got"))" +# ====== +# setting a .sh.value or .sh.level discipline makes no sense, but should be an error, not crash the shell +for v in .sh.value .sh.level +do + for d in get set append + do + exp=": $v.$d: invalid discipline function" + got=$(set +x; { "$SHELL" -c "$v.$d() { .sh.value=foo; }; $v=13; $v+=13; : \${$v}"; } 2>&1) + (((e = $?)==1)) && [[ $got == *"$exp" ]] || err_exit "attempt to set $v.get discipline does not fail gracefully" \ + "(expected status 1 and match of *$(printf %q "$exp")," \ + "got status $e$( ((e>128)) && print -n /SIG && kill -l "$e") and $(printf %q "$got"))" + done +done + # ====== exit $((Errors<125?Errors:125))