[klibc] [klibc:update-dash] dash: [BUILTIN] Return without arguments in a trap should use status outside traps

klibc-bot for Herbert Xu herbert at gondor.apana.org.au
Sat Mar 28 14:48:23 PDT 2020


Commit-ID:  f7b7191322ba416a519761f9d7144b734ca48c87
Gitweb:     http://git.kernel.org/?p=libs/klibc/klibc.git;a=commit;h=f7b7191322ba416a519761f9d7144b734ca48c87
Author:     Herbert Xu <herbert at gondor.apana.org.au>
AuthorDate: Mon, 6 Oct 2014 21:51:26 +0800
Committer:  Ben Hutchings <ben at decadent.org.uk>
CommitDate: Sat, 28 Mar 2020 21:42:54 +0000

[klibc] dash: [BUILTIN] Return without arguments in a trap should use status outside traps

[ dash commit 70c16dd30d4cf824aa895e9f6c095fec741c65a8 ]

POSIX now requires that return without arguments in a trap should
return the last command status prior to executing traps.  This
patch implements this behaviour.

Incidentally this also changes the behaviour of return without
arguments in a loop conditional to use the last exit status in
the body as opposed to the last command in the conditional when
there is one.

Signed-off-by: Herbert Xu <herbert at gondor.apana.org.au>
Signed-off-by: Ben Hutchings <ben at decadent.org.uk>

---
 usr/dash/eval.c | 17 ++++++++++++++---
 usr/dash/eval.h |  1 +
 usr/dash/main.c |  2 +-
 usr/dash/trap.c |  3 ++-
 4 files changed, 18 insertions(+), 5 deletions(-)

diff --git a/usr/dash/eval.c b/usr/dash/eval.c
index bb9fc260..3325cb62 100644
--- a/usr/dash/eval.c
+++ b/usr/dash/eval.c
@@ -967,7 +967,7 @@ funcdone:
 	shellparam = saveparam;
 	handler = savehandler;
 	INTON;
-	evalskip &= ~SKIPFUNC;
+	evalskip &= ~(SKIPFUNC | SKIPFUNCDEF);
 	return e;
 }
 
@@ -1047,12 +1047,23 @@ breakcmd(int argc, char **argv)
 int
 returncmd(int argc, char **argv)
 {
+	int skip;
+	int status;
+
 	/*
 	 * If called outside a function, do what ksh does;
 	 * skip the rest of the file.
 	 */
-	evalskip = SKIPFUNC;
-	return argv[1] ? number(argv[1]) : exitstatus;
+	if (argv[1]) {
+		skip = SKIPFUNC;
+		status = number(argv[1]);
+	} else {
+		skip = SKIPFUNCDEF;
+		status = exitstatus;
+	}
+	evalskip = skip;
+
+	return status;
 }
 
 
diff --git a/usr/dash/eval.h b/usr/dash/eval.h
index 6e62137a..6e8acdaf 100644
--- a/usr/dash/eval.h
+++ b/usr/dash/eval.h
@@ -62,3 +62,4 @@ extern int evalskip;
 #define SKIPBREAK	(1 << 0)
 #define SKIPCONT	(1 << 1)
 #define SKIPFUNC	(1 << 2)
+#define SKIPFUNCDEF	(1 << 3)
diff --git a/usr/dash/main.c b/usr/dash/main.c
index 29a258d3..00c5e00d 100644
--- a/usr/dash/main.c
+++ b/usr/dash/main.c
@@ -242,7 +242,7 @@ cmdloop(int top)
 
 		skip = evalskip;
 		if (skip) {
-			evalskip &= ~SKIPFUNC;
+			evalskip &= ~(SKIPFUNC | SKIPFUNCDEF);
 			break;
 		}
 	}
diff --git a/usr/dash/trap.c b/usr/dash/trap.c
index 7dd8342f..b8470437 100644
--- a/usr/dash/trap.c
+++ b/usr/dash/trap.c
@@ -342,7 +342,8 @@ void dotrap(void)
 		if (!p)
 			continue;
 		evalstring(p, 0);
-		exitstatus = status;
+		if (evalskip != SKIPFUNC)
+			exitstatus = status;
 	}
 
 	savestatus = last_status;


More information about the klibc mailing list