1
0
mirror of https://github.com/lua/lua.git synced 2025-01-28 06:03:00 +08:00

new form of long strings: `[***[...]***]'

This commit is contained in:
Roberto Ierusalimschy 2003-08-29 13:48:14 -03:00
parent b27664e0db
commit 0ff1596476

63
llex.c
View File

@ -1,5 +1,5 @@
/* /*
** $Id: llex.c,v 1.122 2003/08/27 21:01:44 roberto Exp roberto $ ** $Id: llex.c,v 1.123 2003/08/28 14:38:46 roberto Exp roberto $
** Lexical Analyzer ** Lexical Analyzer
** See Copyright Notice in lua.h ** See Copyright Notice in lua.h
*/ */
@ -196,9 +196,22 @@ static void read_numeral (LexState *ls, SemInfo *seminfo) {
} }
static void read_long_string (LexState *ls, SemInfo *seminfo) { static int skip_ast (LexState *ls) {
int count = 0;
int s = ls->current;
lua_assert(s == '[' || s == ']');
save_and_next(ls);
while (ls->current == '*') {
save_and_next(ls);
count++;
}
return (ls->current == s) ? count : (-count) - 1;
}
static void read_long_string (LexState *ls, SemInfo *seminfo, int ast) {
int cont = 0; int cont = 0;
save_and_next(ls); /* pass the second `[' */ save_and_next(ls); /* skip 2nd `[' */
if (currIsNewline(ls)) /* string starts with a newline? */ if (currIsNewline(ls)) /* string starts with a newline? */
inclinenumber(ls); /* skip it */ inclinenumber(ls); /* skip it */
for (;;) { for (;;) {
@ -208,18 +221,15 @@ static void read_long_string (LexState *ls, SemInfo *seminfo) {
"unfinished long comment", TK_EOS); "unfinished long comment", TK_EOS);
break; /* to avoid warnings */ break; /* to avoid warnings */
case '[': case '[':
save_and_next(ls); if (skip_ast(ls) == ast) {
if (ls->current == '[') { save_and_next(ls); /* skip 2nd `[' */
cont++; cont++;
save_and_next(ls);
} }
continue; continue;
case ']': case ']':
save_and_next(ls); if (skip_ast(ls) == ast) {
if (ls->current == ']') { save_and_next(ls); /* skip 2nd `]' */
if (cont == 0) goto endloop; if (cont-- == 0) goto endloop;
cont--;
save_and_next(ls);
} }
continue; continue;
case '\n': case '\n':
@ -233,10 +243,9 @@ static void read_long_string (LexState *ls, SemInfo *seminfo) {
else next(ls); else next(ls);
} }
} endloop: } endloop:
save_and_next(ls); /* skip the second `]' */
if (seminfo) if (seminfo)
seminfo->ts = luaX_newstring(ls, luaZ_buffer(ls->buff) + 2, seminfo->ts = luaX_newstring(ls, luaZ_buffer(ls->buff) + (2 + ast),
luaZ_bufflen(ls->buff) - 4); luaZ_bufflen(ls->buff) - 2*(2 + ast));
} }
@ -310,22 +319,28 @@ int luaX_lex (LexState *ls, SemInfo *seminfo) {
if (ls->current != '-') return '-'; if (ls->current != '-') return '-';
/* else is a comment */ /* else is a comment */
next(ls); next(ls);
if (ls->current == '[' && (next(ls), ls->current == '[')) { if (ls->current == '[') {
read_long_string(ls, NULL); /* long comment */ int ast = skip_ast(ls);
luaZ_resetbuffer(ls->buff); luaZ_resetbuffer(ls->buff); /* `skip_ast' may dirty the buffer */
if (ast >= 0) {
read_long_string(ls, NULL, ast); /* long comment */
luaZ_resetbuffer(ls->buff);
continue;
}
} }
else /* short comment */ /* else short comment */
while (!currIsNewline(ls) && ls->current != EOZ) while (!currIsNewline(ls) && ls->current != EOZ)
next(ls); next(ls);
continue; continue;
} }
case '[': { case '[': {
save_and_next(ls); int ast = skip_ast(ls);
if (ls->current != '[') return '['; if (ast >= 0) {
else { read_long_string(ls, seminfo, ast);
read_long_string(ls, seminfo);
return TK_STRING; return TK_STRING;
} }
else if (ast == -1) return '[';
else luaX_lexerror(ls, "invalid long string delimiter", TK_STRING);
} }
case '=': { case '=': {
next(ls); next(ls);