From 83b0fd36740bd78d6058be58115ff688796a922a Mon Sep 17 00:00:00 2001 From: Peter Stephenson Date: Thu, 25 Mar 2004 10:07:12 +0000 Subject: [PATCH] 19682: Don't run ZERR, DEBUG or EXIT traps inside other traps. --- ChangeLog | 6 ++++++ Doc/Zsh/builtins.yo | 2 ++ Etc/NEWS | 13 +++++++++---- Src/signals.c | 24 +++++++++++++++++++++++- 4 files changed, 40 insertions(+), 5 deletions(-) diff --git a/ChangeLog b/ChangeLog index f83836078..64d5ea989 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2004-03-25 Peter Stephenson + + * 19682: Doc/Zsh/builtins.yo, Etc/NEWS, Src/signals.c: Don't + run ZERR, DEBUG or EXIT traps inside other traps; caused confusion + and incompatibility. + 2004-03-24 Peter Stephenson * 19674 plus unposted changes suggested in 19676: diff --git a/Doc/Zsh/builtins.yo b/Doc/Zsh/builtins.yo index 3f6f3c450..363115297 100644 --- a/Doc/Zsh/builtins.yo +++ b/Doc/Zsh/builtins.yo @@ -1116,6 +1116,8 @@ If var(sig) is tt(0) or tt(EXIT) and the tt(trap) statement is not executed inside the body of a function, then the command var(arg) is executed when the shell terminates. +tt(ZERR), tt(DEBUG) and tt(EXIT) traps are not executed inside other traps. + The tt(trap) command with no arguments prints a list of commands associated with each signal. diff --git a/Etc/NEWS b/Etc/NEWS index 654857457..d2e53ee1c 100644 --- a/Etc/NEWS +++ b/Etc/NEWS @@ -5,14 +5,19 @@ CHANGES FROM PREVIOUS VERSIONS OF ZSH Changes since zsh version 4.2.0 ------------------------------- -The zftp module supports ports following the hostname in the normal suffix -notation, `host:port'. This requires IPv6 colon-style addresses to be -specified in suitably quoted square brackets, for example: +- The zftp module supports ports following the hostname in the normal suffix + notation, `host:port'. This requires IPv6 colon-style addresses to be + specified in suitably quoted square brackets, for example: zftp open '[f000::baaa]' zftp open '[f000::baaa]:ftp' -(the two are equivalent). + (the two are equivalent). + +- Special traps, those that don't correspond to signals, i.e. ZERR, DEBUG + and EXIT are no longer executed inside other traps. This caused + unnecessary confusion if, for example, both DEBUG and EXIT traps + were set. The new behaviour is more compatible with other shells. New features between zsh versions 4.0 and 4.2 diff --git a/Src/signals.c b/Src/signals.c index affb5379b..dbecdf20c 100644 --- a/Src/signals.c +++ b/Src/signals.c @@ -932,7 +932,10 @@ dotrapargs(int sig, int *sigtr, void *sigfn) int trapret = 0; int obreaks = breaks; int isfunc; - + + /* Are we already executing a trap? */ + static int intrap; + /* if signal is being ignored or the trap function * * is NULL, then return * * * @@ -946,6 +949,24 @@ dotrapargs(int sig, int *sigtr, void *sigfn) if ((*sigtr & ZSIG_IGNORED) || !sigfn || errflag) return; + /* + * Never execute special (synchronous) traps inside other traps. + * This can cause unexpected code execution when more than one + * of these is set. + * + * The down side is that it's harder to debug traps. I don't think + * that's a big issue. + */ + if (intrap) { + switch (sig) { + case SIGEXIT: + case SIGDEBUG: + case SIGZERR: + return; + } + } + + intrap++; *sigtr |= ZSIG_IGNORED; lexsave(); @@ -1023,6 +1044,7 @@ dotrapargs(int sig, int *sigtr, void *sigfn) if (*sigtr != ZSIG_IGNORED) *sigtr &= ~ZSIG_IGNORED; + intrap--; } /* Standard call to execute a trap for a given signal. */