diff options
-rw-r--r-- | bin/sh/input.c | 27 | ||||
-rw-r--r-- | bin/sh/input.h | 1 | ||||
-rw-r--r-- | bin/sh/parser.c | 38 | ||||
-rw-r--r-- | bin/sh/tests/parser/Makefile | 1 | ||||
-rw-r--r-- | bin/sh/tests/parser/heredoc12.0 | 47 |
5 files changed, 65 insertions, 49 deletions
diff --git a/bin/sh/input.c b/bin/sh/input.c index 7da8957..412f144 100644 --- a/bin/sh/input.c +++ b/bin/sh/input.c @@ -116,33 +116,6 @@ resetinput(void) } -/* - * Read a line from the script. - */ - -char * -pfgets(char *line, int len) -{ - char *p = line; - int nleft = len; - int c; - - while (--nleft > 0) { - c = pgetc_macro(); - if (c == PEOF) { - if (p == line) - return NULL; - break; - } - *p++ = c; - if (c == '\n') - break; - } - *p = '\0'; - return line; -} - - /* * Read a character from the script, returning PEOF on end of file. diff --git a/bin/sh/input.h b/bin/sh/input.h index 7de9435..cb0af77 100644 --- a/bin/sh/input.h +++ b/bin/sh/input.h @@ -48,7 +48,6 @@ struct alias; struct parsefile; void resetinput(void); -char *pfgets(char *, int); int pgetc(void); int preadbuffer(void); int preadateof(void); diff --git a/bin/sh/parser.c b/bin/sh/parser.c index 2b36f50..8e98768 100644 --- a/bin/sh/parser.c +++ b/bin/sh/parser.c @@ -66,7 +66,6 @@ __FBSDID("$FreeBSD$"); * Shell command parser. */ -#define EOFMARKLEN 79 #define PROMPTLEN 128 /* values of checkkwd variable */ @@ -718,7 +717,6 @@ parsefname(void) if (n->type == NHERE) { struct heredoc *here = heredoc; struct heredoc *p; - int i; if (quoteflag == 0) n->type = NXHERE; @@ -727,7 +725,7 @@ parsefname(void) while (*wordtext == '\t') wordtext++; } - if (! noexpand(wordtext) || (i = strlen(wordtext)) == 0 || i > EOFMARKLEN) + if (! noexpand(wordtext)) synerror("Illegal eof marker for << redirection"); rmescapes(wordtext); here->eofmark = wordtext; @@ -953,28 +951,27 @@ struct tokenstate */ static int -checkend(int c, const char *eofmark, char *line, size_t sizeof_line, - int striptabs) +checkend(int c, const char *eofmark, int striptabs) { if (striptabs) { while (c == '\t') c = pgetc(); } if (c == *eofmark) { - if (pfgets(line, sizeof_line) != NULL) { - const char *p, *q; - - p = line; - for (q = eofmark + 1 ; *q && *p == *q ; p++, q++); - if ((*p == '\0' || *p == '\n') && *q == '\0') { - c = PEOF; - if (*p == '\n') { - plinno++; - needprompt = doprompt; - } - } else { - pushstring(line, strlen(line), NULL); + int c2; + const char *q; + + for (q = eofmark + 1; c2 = pgetc(), *q != '\0' && c2 == *q; q++) + ; + if ((c2 == PEOF || c2 == '\n') && *q == '\0') { + c = PEOF; + if (c2 == '\n') { + plinno++; + needprompt = doprompt; } + } else { + pungetc(); + pushstring(eofmark + 1, q - (eofmark + 1), NULL); } } return (c); @@ -1316,7 +1313,6 @@ readtoken1(int firstc, char const *initialsyntax, const char *eofmark, int c = firstc; char *out; int len; - char line[EOFMARKLEN + 1]; struct nodelist *bqlist; int quotef; int newvarnest; @@ -1340,7 +1336,7 @@ readtoken1(int firstc, char const *initialsyntax, const char *eofmark, loop: { /* for each line, until end of word */ if (eofmark) /* set c to PEOF if at end of here document */ - c = checkend(c, eofmark, line, sizeof(line), striptabs); + c = checkend(c, eofmark, striptabs); for (;;) { /* until end of line or end of word */ CHECKSTRSPACE(4, out); /* permit 4 calls to USTPUTC */ @@ -2032,7 +2028,7 @@ expandstr(const char *ps) parser_temp = NULL; setinputstring(ps, 1); doprompt = 0; - readtoken1(pgetc(), DQSYNTAX, "\n\n", 0); + readtoken1(pgetc(), DQSYNTAX, "", 0); if (backquotelist != NULL) error("Command substitution not allowed here"); diff --git a/bin/sh/tests/parser/Makefile b/bin/sh/tests/parser/Makefile index 4b2e76d..7b77cb8 100644 --- a/bin/sh/tests/parser/Makefile +++ b/bin/sh/tests/parser/Makefile @@ -54,6 +54,7 @@ FILES+= heredoc8.0 FILES+= heredoc9.0 FILES+= heredoc10.0 FILES+= heredoc11.0 +FILES+= heredoc12.0 FILES+= no-space1.0 FILES+= no-space2.0 FILES+= only-redir1.0 diff --git a/bin/sh/tests/parser/heredoc12.0 b/bin/sh/tests/parser/heredoc12.0 new file mode 100644 index 0000000..9648384 --- /dev/null +++ b/bin/sh/tests/parser/heredoc12.0 @@ -0,0 +1,47 @@ +# $FreeBSD$ + +failures=0 + +check() { + if ! eval "[ $* ]"; then + echo "Failed: $*" + : $((failures += 1)) + fi +} + +longmark=`printf %01000d 4` +longmarkstripped=`printf %0999d 0` + +check '"$(cat <<'"$longmark +$longmark"' +echo yes)" = "yes"' + +check '"$(cat <<\'"$longmark +$longmark"' +echo yes)" = "yes"' + +check '"$(cat <<'"$longmark +yes +$longmark"' +)" = "yes"' + +check '"$(cat <<\'"$longmark +yes +$longmark"' +)" = "yes"' + +check '"$(cat <<'"$longmark +$longmarkstripped +$longmark. +$longmark"' +)" = "'"$longmarkstripped +$longmark."'"' + +check '"$(cat <<\'"$longmark +$longmarkstripped +$longmark. +$longmark"' +)" = "'"$longmarkstripped +$longmark."'"' + +exit $((failures != 0)) |