aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDenys Vlasenko <vda.linux@googlemail.com>2018-03-31 19:21:31 +0200
committerDenys Vlasenko <vda.linux@googlemail.com>2018-03-31 19:40:56 +0200
commit220be537a03f029e1e619003d6f7def10103a156 (patch)
tree73a8c8d1a19796c15db0dc7b238cf8bc644a4e46
parentad4e961352f04ba88019c4c2bb36c652ce9c51fa (diff)
downloadbusybox-w32-220be537a03f029e1e619003d6f7def10103a156.tar.gz
busybox-w32-220be537a03f029e1e619003d6f7def10103a156.tar.bz2
busybox-w32-220be537a03f029e1e619003d6f7def10103a156.zip
ash: use pgetc_eatbnl() in more places
Part of upstream commit: Date: Thu Mar 8 08:37:11 2018 +0100 Author: Harald van Dijk <harald@gigawatt.nl> parser: use pgetc_eatbnl() in more places dash has a pgetc_eatbnl function in parser.c which skips any backslash-newline combinations. It's not used everywhere it could be. There is also some duplicated backslash-newline handling elsewhere in parser.c. Replace most of the calls to pgetc() with calls to pgetc_eatbnl() and remove the duplicated backslash-newline handling. Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au> Not adding "readtoken1(pgetc_eatbnl(), DQSYNTAX..." changes, since readtoken1() handles the "starts with backslash + newline" case itself. Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r--shell/ash.c47
-rw-r--r--shell/ash_test/ash-heredoc/heredoc_backslash1.right43
-rwxr-xr-xshell/ash_test/ash-heredoc/heredoc_backslash1.tests70
-rw-r--r--shell/ash_test/ash-heredoc/heredoc_bkslash_newline1.right8
-rwxr-xr-xshell/ash_test/ash-heredoc/heredoc_bkslash_newline1.tests25
-rw-r--r--shell/hush_test/hush-heredoc/heredoc_bkslash_newline1.right8
-rwxr-xr-xshell/hush_test/hush-heredoc/heredoc_bkslash_newline1.tests25
7 files changed, 191 insertions, 35 deletions
diff --git a/shell/ash.c b/shell/ash.c
index 2ed802d2e..a7767b4f8 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -12225,7 +12225,7 @@ parseredir: {
12225 np = stzalloc(sizeof(struct nfile)); 12225 np = stzalloc(sizeof(struct nfile));
12226 if (c == '>') { 12226 if (c == '>') {
12227 np->nfile.fd = 1; 12227 np->nfile.fd = 1;
12228 c = pgetc(); 12228 c = pgetc_eatbnl();
12229 if (c == '>') 12229 if (c == '>')
12230 np->type = NAPPEND; 12230 np->type = NAPPEND;
12231 else if (c == '|') 12231 else if (c == '|')
@@ -12247,7 +12247,7 @@ parseredir: {
12247#endif 12247#endif
12248 else { /* c == '<' */ 12248 else { /* c == '<' */
12249 /*np->nfile.fd = 0; - stzalloc did it */ 12249 /*np->nfile.fd = 0; - stzalloc did it */
12250 c = pgetc(); 12250 c = pgetc_eatbnl();
12251 switch (c) { 12251 switch (c) {
12252 case '<': 12252 case '<':
12253 if (sizeof(struct nfile) != sizeof(struct nhere)) { 12253 if (sizeof(struct nfile) != sizeof(struct nhere)) {
@@ -12257,7 +12257,7 @@ parseredir: {
12257 np->type = NHERE; 12257 np->type = NHERE;
12258 heredoc = stzalloc(sizeof(struct heredoc)); 12258 heredoc = stzalloc(sizeof(struct heredoc));
12259 heredoc->here = np; 12259 heredoc->here = np;
12260 c = pgetc(); 12260 c = pgetc_eatbnl();
12261 if (c == '-') { 12261 if (c == '-') {
12262 heredoc->striptabs = 1; 12262 heredoc->striptabs = 1;
12263 } else { 12263 } else {
@@ -12487,23 +12487,13 @@ parsebackq: {
12487 int pc; 12487 int pc;
12488 12488
12489 setprompt_if(needprompt, 2); 12489 setprompt_if(needprompt, 2);
12490 pc = pgetc(); 12490 pc = pgetc_eatbnl();
12491 switch (pc) { 12491 switch (pc) {
12492 case '`': 12492 case '`':
12493 goto done; 12493 goto done;
12494 12494
12495 case '\\': 12495 case '\\':
12496 pc = pgetc(); 12496 pc = pgetc(); /* or pgetc_eatbnl()? why (example)? */
12497 if (pc == '\n') {
12498 nlprompt();
12499 /*
12500 * If eating a newline, avoid putting
12501 * the newline into the new character
12502 * stream (via the STPUTC after the
12503 * switch).
12504 */
12505 continue;
12506 }
12507 if (pc != '\\' && pc != '`' && pc != '$' 12497 if (pc != '\\' && pc != '`' && pc != '$'
12508 && (!dblquote || pc != '"') 12498 && (!dblquote || pc != '"')
12509 ) { 12499 ) {
@@ -12635,7 +12625,7 @@ xxreadtoken(void)
12635 } 12625 }
12636 setprompt_if(needprompt, 2); 12626 setprompt_if(needprompt, 2);
12637 for (;;) { /* until token or start of word found */ 12627 for (;;) { /* until token or start of word found */
12638 c = pgetc(); 12628 c = pgetc_eatbnl();
12639 if (c == ' ' || c == '\t' IF_ASH_ALIAS( || c == PEOA)) 12629 if (c == ' ' || c == '\t' IF_ASH_ALIAS( || c == PEOA))
12640 continue; 12630 continue;
12641 12631
@@ -12644,11 +12634,7 @@ xxreadtoken(void)
12644 continue; 12634 continue;
12645 pungetc(); 12635 pungetc();
12646 } else if (c == '\\') { 12636 } else if (c == '\\') {
12647 if (pgetc() != '\n') { 12637 break; /* return readtoken1(...) */
12648 pungetc();
12649 break; /* return readtoken1(...) */
12650 }
12651 nlprompt();
12652 } else { 12638 } else {
12653 const char *p; 12639 const char *p;
12654 12640
@@ -12695,7 +12681,7 @@ xxreadtoken(void)
12695 } 12681 }
12696 setprompt_if(needprompt, 2); 12682 setprompt_if(needprompt, 2);
12697 for (;;) { /* until token or start of word found */ 12683 for (;;) { /* until token or start of word found */
12698 c = pgetc(); 12684 c = pgetc_eatbnl();
12699 switch (c) { 12685 switch (c) {
12700 case ' ': case '\t': 12686 case ' ': case '\t':
12701 IF_ASH_ALIAS(case PEOA:) 12687 IF_ASH_ALIAS(case PEOA:)
@@ -12705,30 +12691,23 @@ xxreadtoken(void)
12705 continue; 12691 continue;
12706 pungetc(); 12692 pungetc();
12707 continue; 12693 continue;
12708 case '\\':
12709 if (pgetc() == '\n') {
12710 nlprompt();
12711 continue;
12712 }
12713 pungetc();
12714 goto breakloop;
12715 case '\n': 12694 case '\n':
12716 nlnoprompt(); 12695 nlnoprompt();
12717 RETURN(TNL); 12696 RETURN(TNL);
12718 case PEOF: 12697 case PEOF:
12719 RETURN(TEOF); 12698 RETURN(TEOF);
12720 case '&': 12699 case '&':
12721 if (pgetc() == '&') 12700 if (pgetc_eatbnl() == '&')
12722 RETURN(TAND); 12701 RETURN(TAND);
12723 pungetc(); 12702 pungetc();
12724 RETURN(TBACKGND); 12703 RETURN(TBACKGND);
12725 case '|': 12704 case '|':
12726 if (pgetc() == '|') 12705 if (pgetc_eatbnl() == '|')
12727 RETURN(TOR); 12706 RETURN(TOR);
12728 pungetc(); 12707 pungetc();
12729 RETURN(TPIPE); 12708 RETURN(TPIPE);
12730 case ';': 12709 case ';':
12731 if (pgetc() == ';') 12710 if (pgetc_eatbnl() == ';')
12732 RETURN(TENDCASE); 12711 RETURN(TENDCASE);
12733 pungetc(); 12712 pungetc();
12734 RETURN(TSEMI); 12713 RETURN(TSEMI);
@@ -12736,11 +12715,9 @@ xxreadtoken(void)
12736 RETURN(TLP); 12715 RETURN(TLP);
12737 case ')': 12716 case ')':
12738 RETURN(TRP); 12717 RETURN(TRP);
12739 default:
12740 goto breakloop;
12741 } 12718 }
12719 break;
12742 } 12720 }
12743 breakloop:
12744 return readtoken1(c, BASESYNTAX, (char *)NULL, 0); 12721 return readtoken1(c, BASESYNTAX, (char *)NULL, 0);
12745#undef RETURN 12722#undef RETURN
12746} 12723}
diff --git a/shell/ash_test/ash-heredoc/heredoc_backslash1.right b/shell/ash_test/ash-heredoc/heredoc_backslash1.right
new file mode 100644
index 000000000..6a6114821
--- /dev/null
+++ b/shell/ash_test/ash-heredoc/heredoc_backslash1.right
@@ -0,0 +1,43 @@
1Quoted heredoc:
2a\
3 b
4a\\
5 b
6 123456 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
7 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
8 123456 `echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-'`
9 123456 $(echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-')
10c\
11
12Unquoted heredoc:
13a b
14a\
15 b
16 123456 -qwerty-\t-\-\"-\'-`-\--\z-\*-\?-
17 -qwerty-\t-\-\"-\'-`-\--\z-\*-\?-
18 123456 v-$a-\t-\-\"-\x-`-\--\z-\*-\?-
19 123456 v-$a-\t-\\-\"-\x-\`-\--\z-\*-\?-
20cEOF2
21
22Quoted -heredoc:
23a\
24b
25a\\
26b
27 123456 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
28-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
29 123456 `echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-'`
30 123456 $(echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-')
31c\
32
33Unquoted -heredoc:
34a b
35a\
36b
37 123456 -qwerty-\t-\-\"-\'-`-\--\z-\*-\?-
38-qwerty-\t-\-\"-\'-`-\--\z-\*-\?-
39 123456 v-$a-\t-\-\"-\x-`-\--\z-\*-\?-
40 123456 v-$a-\t-\\-\"-\x-\`-\--\z-\*-\?-
41cEOF4
42
43Done: 0
diff --git a/shell/ash_test/ash-heredoc/heredoc_backslash1.tests b/shell/ash_test/ash-heredoc/heredoc_backslash1.tests
new file mode 100755
index 000000000..501af5490
--- /dev/null
+++ b/shell/ash_test/ash-heredoc/heredoc_backslash1.tests
@@ -0,0 +1,70 @@
1# Test for correct handling of backslashes.
2# Note that some lines in each heredoc start with a tab.
3
4a=qwerty
5
6echo Quoted heredoc:
7cat <<"EOF1"
8a\
9 b
10a\\
11 b
12 123456 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
13 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
14 123456 `echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-'`
15 123456 $(echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-')
16c\
17EOF1
18echo
19
20echo Unquoted heredoc:
21cat <<EOF2
22a\
23 b
24a\\
25 b
26 123456 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
27 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
28 123456 `echo v'-$a-\t-\\-\"-\x-\`-\--\z-\*-\?-'`
29 123456 $(echo v'-$a-\t-\\-\"-\x-\`-\--\z-\*-\?-')
30c\
31EOF2
32EOF2
33echo
34
35echo Quoted -heredoc:
36cat <<-"EOF3"
37a\
38 b
39a\\
40 b
41 123456 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
42 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
43 123456 `echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-'`
44 123456 $(echo v'-$a-\t-\\-\"-\'-\`-\--\z-\*-\?-')
45c\
46 EOF3
47# In -heredoc case the marker is detected even if it is indented.
48echo
49
50echo Unquoted -heredoc:
51cat <<-EOF4
52a\
53 b
54a\\
55 b
56 123456 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
57 -$a-\t-\\-\"-\'-\`-\--\z-\*-\?-
58 123456 `echo v'-$a-\t-\\-\"-\x-\`-\--\z-\*-\?-'`
59 123456 $(echo v'-$a-\t-\\-\"-\x-\`-\--\z-\*-\?-')
60c\
61EOF4
62 EOF4
63# The marker is not detected if preceding line ends in backslash.
64# TODO: marker should be detected even if it is split by line continuation:
65# EOF\
66# 4
67# but currently hush doesn't do it. (Tab before "4" is not allowed, though.)
68echo
69
70echo "Done: $?"
diff --git a/shell/ash_test/ash-heredoc/heredoc_bkslash_newline1.right b/shell/ash_test/ash-heredoc/heredoc_bkslash_newline1.right
new file mode 100644
index 000000000..fdb7ebd03
--- /dev/null
+++ b/shell/ash_test/ash-heredoc/heredoc_bkslash_newline1.right
@@ -0,0 +1,8 @@
1heredoc0
2Ok0:0
3heredoc1
4Ok1:0
5heredoc2
6Ok2:0
7heredoc3
8Ok4:0
diff --git a/shell/ash_test/ash-heredoc/heredoc_bkslash_newline1.tests b/shell/ash_test/ash-heredoc/heredoc_bkslash_newline1.tests
new file mode 100755
index 000000000..584edd0e4
--- /dev/null
+++ b/shell/ash_test/ash-heredoc/heredoc_bkslash_newline1.tests
@@ -0,0 +1,25 @@
1cat <\
2<\
3EOF
4heredoc0
5EOF
6echo Ok0:$?
7
8cat <<\
9 EOF
10heredoc1
11EOF
12echo Ok1:$?
13
14cat <<\
15- EOF
16heredoc2
17 EOF
18echo Ok2:$?
19
20cat <\
21<\
22- EOF
23heredoc3
24 EOF
25echo Ok4:$?
diff --git a/shell/hush_test/hush-heredoc/heredoc_bkslash_newline1.right b/shell/hush_test/hush-heredoc/heredoc_bkslash_newline1.right
new file mode 100644
index 000000000..fdb7ebd03
--- /dev/null
+++ b/shell/hush_test/hush-heredoc/heredoc_bkslash_newline1.right
@@ -0,0 +1,8 @@
1heredoc0
2Ok0:0
3heredoc1
4Ok1:0
5heredoc2
6Ok2:0
7heredoc3
8Ok4:0
diff --git a/shell/hush_test/hush-heredoc/heredoc_bkslash_newline1.tests b/shell/hush_test/hush-heredoc/heredoc_bkslash_newline1.tests
new file mode 100755
index 000000000..584edd0e4
--- /dev/null
+++ b/shell/hush_test/hush-heredoc/heredoc_bkslash_newline1.tests
@@ -0,0 +1,25 @@
1cat <\
2<\
3EOF
4heredoc0
5EOF
6echo Ok0:$?
7
8cat <<\
9 EOF
10heredoc1
11EOF
12echo Ok1:$?
13
14cat <<\
15- EOF
16heredoc2
17 EOF
18echo Ok2:$?
19
20cat <\
21<\
22- EOF
23heredoc3
24 EOF
25echo Ok4:$?