aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--shell/ash.c23
-rw-r--r--shell/ash_test/ash-quoting/bkslash_case1.right10
-rwxr-xr-xshell/ash_test/ash-quoting/bkslash_case1.tests38
-rw-r--r--shell/hush_test/hush-quoting/bkslash_case1.right10
-rwxr-xr-xshell/hush_test/hush-quoting/bkslash_case1.tests38
5 files changed, 113 insertions, 6 deletions
diff --git a/shell/ash.c b/shell/ash.c
index 4c1b5e409..5e281b5ce 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -6146,12 +6146,12 @@ rmescapes(char *str, int flag, int *slash_position)
6146 if (*p == '*' 6146 if (*p == '*'
6147 || *p == '?' 6147 || *p == '?'
6148 || *p == '[' 6148 || *p == '['
6149 || *p == '\\' /* case '\' in \\ ) echo ok;; *) echo WRONG;; esac */ 6149 || *p == '\\' /* case '\' in \\ ) echo ok;; *) echo WRONG;; esac */
6150 || *p == ']' /* case ']' in [a\]] ) echo ok;; *) echo WRONG;; esac */ 6150 || *p == ']' /* case ']' in [a\]] ) echo ok;; *) echo WRONG;; esac */
6151 || *p == '-' /* case '-' in [a\-c]) echo ok;; *) echo WRONG;; esac */ 6151 || *p == '-' /* case '-' in [a\-c]) echo ok;; *) echo WRONG;; esac */
6152 || *p == '!' /* case '!' in [\!] ) echo ok;; *) echo WRONG;; esac */ 6152 || *p == '!' /* case '!' in [\!] ) echo ok;; *) echo WRONG;; esac */
6153 /* Some libc support [^negate], that's why "^" also needs love */ 6153 /* Some libc support [^negate], that's why "^" also needs love */
6154 || *p == '^' /* case '^' in [\^] ) echo ok;; *) echo WRONG;; esac */ 6154 || *p == '^' /* case '^' in [\^] ) echo ok;; *) echo WRONG;; esac */
6155 ) { 6155 ) {
6156 *q++ = '\\'; 6156 *q++ = '\\';
6157 } 6157 }
@@ -11992,13 +11992,24 @@ readtoken1(int c, int syntax, char *eofmark, int striptabs)
11992 USTPUTC(CTLESC, out); 11992 USTPUTC(CTLESC, out);
11993 USTPUTC('\\', out); 11993 USTPUTC('\\', out);
11994 } 11994 }
11995 /* Backslash is retained if we are in "str" and next char isn't special */ 11995 /* Backslash is retained if we are in "str"
11996 * and next char isn't dquote-special.
11997 */
11996 if (dblquote 11998 if (dblquote
11997 && c != '\\' 11999 && c != '\\'
11998 && c != '`' 12000 && c != '`'
11999 && c != '$' 12001 && c != '$'
12000 && (c != '"' || eofmark != NULL) 12002 && (c != '"' || eofmark != NULL)
12001 ) { 12003 ) {
12004//dash survives not doing USTPUTC(CTLESC), but merely by chance:
12005//Example: "\z" gets encoded as "\<CTLESC>z".
12006//rmescapes() then emits "\", "\z", protecting z from globbing.
12007//But it's wrong, should protect _both_ from globbing:
12008//everything in double quotes is not globbed.
12009//Unlike dash, we have a fix in rmescapes() which emits bare "z"
12010//for "<CTLESC>z" since "z" is not glob-special (else unicode may break),
12011//and glob would see "\z" and eat "\". Thus:
12012 USTPUTC(CTLESC, out); /* protect '\' from glob */
12002 USTPUTC('\\', out); 12013 USTPUTC('\\', out);
12003 } 12014 }
12004 USTPUTC(CTLESC, out); 12015 USTPUTC(CTLESC, out);
diff --git a/shell/ash_test/ash-quoting/bkslash_case1.right b/shell/ash_test/ash-quoting/bkslash_case1.right
new file mode 100644
index 000000000..1b52491f7
--- /dev/null
+++ b/shell/ash_test/ash-quoting/bkslash_case1.right
@@ -0,0 +1,10 @@
1ok1
2ok2
3ok3
4ok4
5ok5
6Ok:0
7ok6
8ok7
9ok8
10Ok:0
diff --git a/shell/ash_test/ash-quoting/bkslash_case1.tests b/shell/ash_test/ash-quoting/bkslash_case1.tests
new file mode 100755
index 000000000..d0c359927
--- /dev/null
+++ b/shell/ash_test/ash-quoting/bkslash_case1.tests
@@ -0,0 +1,38 @@
1# Case argument is globbed, match patterns are not.
2# This caught some bugs in the past.
3
4case z in
5\z ) echo ok1 ;;
6* ) echo BUG ;;
7esac
8case \z in
9z ) echo ok2 ;;
10* ) echo BUG ;;
11esac
12case \z in
13\z ) echo ok3 ;;
14* ) echo BUG ;;
15esac
16case z in
17\z ) echo ok4 ;;
18* ) echo BUG ;;
19esac
20case \\z in
21\\z ) echo ok5 ;;
22* ) echo BUG ;;
23esac
24echo Ok:$?
25
26case "\z" in
27"\z" ) echo ok6 ;;
28* ) echo BUG ;;
29esac
30case "\\z" in
31"\\z" ) echo ok7 ;;
32* ) echo BUG ;;
33esac
34case "\\\z" in
35"\\\z") echo ok8 ;;
36* ) echo BUG ;;
37esac
38echo Ok:$?
diff --git a/shell/hush_test/hush-quoting/bkslash_case1.right b/shell/hush_test/hush-quoting/bkslash_case1.right
new file mode 100644
index 000000000..1b52491f7
--- /dev/null
+++ b/shell/hush_test/hush-quoting/bkslash_case1.right
@@ -0,0 +1,10 @@
1ok1
2ok2
3ok3
4ok4
5ok5
6Ok:0
7ok6
8ok7
9ok8
10Ok:0
diff --git a/shell/hush_test/hush-quoting/bkslash_case1.tests b/shell/hush_test/hush-quoting/bkslash_case1.tests
new file mode 100755
index 000000000..d0c359927
--- /dev/null
+++ b/shell/hush_test/hush-quoting/bkslash_case1.tests
@@ -0,0 +1,38 @@
1# Case argument is globbed, match patterns are not.
2# This caught some bugs in the past.
3
4case z in
5\z ) echo ok1 ;;
6* ) echo BUG ;;
7esac
8case \z in
9z ) echo ok2 ;;
10* ) echo BUG ;;
11esac
12case \z in
13\z ) echo ok3 ;;
14* ) echo BUG ;;
15esac
16case z in
17\z ) echo ok4 ;;
18* ) echo BUG ;;
19esac
20case \\z in
21\\z ) echo ok5 ;;
22* ) echo BUG ;;
23esac
24echo Ok:$?
25
26case "\z" in
27"\z" ) echo ok6 ;;
28* ) echo BUG ;;
29esac
30case "\\z" in
31"\\z" ) echo ok7 ;;
32* ) echo BUG ;;
33esac
34case "\\\z" in
35"\\\z") echo ok8 ;;
36* ) echo BUG ;;
37esac
38echo Ok:$?