[git commit] ash: parser: Fix alias expansion after heredoc or newlines

Denys Vlasenko vda.linux at googlemail.com
Tue Sep 7 23:43:12 UTC 2021


commit: https://git.busybox.net/busybox/commit/?id=8c68ae8416c8b54222eb3cd1d4908a570147e134
branch: https://git.busybox.net/busybox/commit/?id=refs/heads/master

Upstream commit:

    Date: Wed, 29 Apr 2020 00:19:59 +1000
    parser: Fix alias expansion after heredoc or newlines

    This script should print OK:

        alias a="case x in " b=x
        a
        b) echo BAD;; esac

        alias BEGIN={ END=}
        BEGIN
    	cat <<- EOF > /dev/null
    		$(:)
    	EOF
        END
        : <<- EOF &&
    		$(:)
        EOF
        BEGIN
    	echo OK
        END

    However, because the value of checkkwd is either zeroed when it
    shouldn't, or isn't zeroed when it should, dash currently gets
    it wrong in every case.

    This patch fixes it by saving checkkwd and zeroing it where needed.

function                                             old     new   delta
readtoken                                            157     176     +19

Signed-off-by: Denys Vlasenko <vda.linux at googlemail.com>
---
 shell/ash.c                                |  7 +++++--
 shell/ash_test/ash-alias/alias_brace.right |  1 +
 shell/ash_test/ash-alias/alias_brace.tests | 16 ++++++++++++++++
 shell/ash_test/ash-alias/alias_case.right  |  1 +
 shell/ash_test/ash-alias/alias_case.tests  |  8 ++++++++
 5 files changed, 31 insertions(+), 2 deletions(-)

diff --git a/shell/ash.c b/shell/ash.c
index f1c21188e..5a001b004 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -13265,10 +13265,14 @@ readtoken(void)
 	if (kwd & CHKNL) {
 		while (t == TNL) {
 			parseheredoc();
+			checkkwd = 0;
 			t = xxreadtoken();
 		}
 	}
 
+	kwd |= checkkwd;
+	checkkwd = 0;
+
 	if (t != TWORD || quoteflag) {
 		goto out;
 	}
@@ -13287,7 +13291,7 @@ readtoken(void)
 		}
 	}
 
-	if (checkkwd & CHKALIAS) {
+	if (kwd & CHKALIAS) {
 #if ENABLE_ASH_ALIAS
 		struct alias *ap;
 		ap = lookupalias(wordtext, 1);
@@ -13300,7 +13304,6 @@ readtoken(void)
 #endif
 	}
  out:
-	checkkwd = 0;
 #if DEBUG
 	if (!alreadyseen)
 		TRACE(("token '%s' %s\n", tokname_array[t], t == TWORD ? wordtext : ""));
diff --git a/shell/ash_test/ash-alias/alias_brace.right b/shell/ash_test/ash-alias/alias_brace.right
new file mode 100644
index 000000000..7326d9603
--- /dev/null
+++ b/shell/ash_test/ash-alias/alias_brace.right
@@ -0,0 +1 @@
+Ok
diff --git a/shell/ash_test/ash-alias/alias_brace.tests b/shell/ash_test/ash-alias/alias_brace.tests
new file mode 100755
index 000000000..7571b64ac
--- /dev/null
+++ b/shell/ash_test/ash-alias/alias_brace.tests
@@ -0,0 +1,16 @@
+# Note: bash would need:
+#shopt -s expand_aliases
+# to enable aliases in non-interactive mode
+alias BEGIN={ END=}
+BEGIN
+	cat <<- EOF > /dev/null
+		$(:)
+	EOF
+END
+
+: <<- EOF &&
+	$(:)
+EOF
+BEGIN
+	echo Ok
+END
diff --git a/shell/ash_test/ash-alias/alias_case.right b/shell/ash_test/ash-alias/alias_case.right
new file mode 100644
index 000000000..7326d9603
--- /dev/null
+++ b/shell/ash_test/ash-alias/alias_case.right
@@ -0,0 +1 @@
+Ok
diff --git a/shell/ash_test/ash-alias/alias_case.tests b/shell/ash_test/ash-alias/alias_case.tests
new file mode 100755
index 000000000..ed8275875
--- /dev/null
+++ b/shell/ash_test/ash-alias/alias_case.tests
@@ -0,0 +1,8 @@
+# Note: bash would need:
+#shopt -s expand_aliases
+# to enable aliases in non-interactive mode
+alias a="case x in " b=x
+a
+b) echo BAD;;
+*) echo Ok;;
+esac


More information about the busybox-cvs mailing list