%{ // Copyright (c) 2011 CZ.NIC z.s.p.o. All rights reserved. // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. // blame: jnml, labs.nic.cz package main import ( "fmt" "bytes" ) const ( INITIAL = iota PHP STRING STRING_VAR STRING_VAR_INDEX STRING_VAR_NAME PROPERTY HEREDOC_END NOWDOC HEREDOC BACKQUOTE ) var heredocLabel []byte func (l *lexer) Lex(lval *yySymType) int { // Lex(lval *yySymType) c := l.Enter() %} %s PHP STRING STRING_VAR STRING_VAR_INDEX STRING_VAR_NAME PROPERTY HEREDOC_END NOWDOC HEREDOC BACKQUOTE %yyb last == '\n' || last = '\0' %yyt l.getCurrentState() %yyc c %yyn c = l.Next() %yym l.Mark() LNUM [0-9]+ DNUM ([0-9]*"."[0-9]+)|([0-9]+"."[0-9]*) HNUM 0x[0-9a-fA-F]+ BNUM 0b[01]+ EXPONENT_DNUM (({LNUM}|{DNUM})[eE][+-]?{LNUM}) VAR_NAME [a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]* OPERATORS [;:,.\[\]()|\/\^&\+-*=%!~$<>?@] NEW_LINE (\r|\n|\r\n) %% c = l.Rule0() [ \t\n\r]+ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); . tb := []byte{} for { if c == -1 { tb = l.TokenBytes(nil); break; } if '?' == rune(c) { tb = l.TokenBytes(nil); if (len(tb) < 2 || tb[len(tb)-1] != '<') { c = l.Next() continue; } tb = l.ungetN(1) break; } c = l.Next() } lval.token = newToken(l.handleNewLine(tb)); return T_INLINE_HTML \<\?php([ \t]|{NEW_LINE}) l.begin(PHP);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil)));// return T_OPEN_TAG; \<\? l.begin(PHP);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil)));// return T_OPEN_TAG; \<\?= l.begin(PHP);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ECHO; [ \t\n\r]+ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil)));// return T_WHITESPACE \?\>{NEW_LINE}? l.begin(INITIAL);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(';'); {DNUM}|{EXPONENT_DNUM} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DNUMBER {BNUM} tb := l.TokenBytes(nil) i:=2 BNUMFOR:for { switch tb[i] { case '0': i++; default: break BNUMFOR; } } if len(tb) - i < 64 { lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LNUMBER } else { lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DNUMBER } {LNUM} if len(l.TokenBytes(nil)) < 20 { lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LNUMBER } else { lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DNUMBER } {HNUM} tb := l.TokenBytes(nil) i:=2 HNUMFOR:for { switch tb[i] { case '0': i++; default: break HNUMFOR; } } length := len(tb) - i if length < 16 || (length == 16 && tb[i] <= '7') { lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LNUMBER } else { lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DNUMBER } abstract lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ABSTRACT array lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ARRAY as lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_AS break lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_BREAK callable lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CALLABLE case lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CASE catch lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CATCH class lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CLASS clone lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CLONE const lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CONST; continue lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CONTINUE; declare lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DECLARE; default lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DEFAULT; do lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DO; echo lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ECHO; else lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ELSE; elseif lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ELSEIF; empty lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_EMPTY; enddeclare lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENDDECLARE endfor lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENDFOR endforeach lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENDFOREACH endif lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENDIF endswitch lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENDSWITCH endwhile lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENDWHILE eval lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_EVAL exit|die lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_EXIT extends lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_EXTENDS final lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_FINAL finally lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_FINALLY for lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_FOR foreach lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_FOREACH function|cfunction lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_FUNCTION global lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_GLOBAL goto lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_GOTO if lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IF isset lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ISSET implements lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IMPLEMENTS instanceof lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_INSTANCEOF insteadof lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_INSTEADOF interface lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_INTERFACE list lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LIST namespace lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_NAMESPACE private lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_PRIVATE public lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_PUBLIC print lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_PRINT protected lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_PROTECTED return lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_RETURN static lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_STATIC switch lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_SWITCH throw lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_THROW trait lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_TRAIT try lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_TRY unset lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_UNSET use lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_USE var lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_VAR while lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_WHILE yield[ \t\n\r]+from[^a-zA-Z0-9_\x80-\xff] lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_YIELD_FROM yield lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_YIELD include lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_INCLUDE include_once lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_INCLUDE_ONCE require lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_REQUIRE require_once lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_REQUIRE_ONCE __CLASS__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CLASS_C __DIR__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DIR __FILE__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_FILE __FUNCTION__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_FUNC_C __LINE__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LINE __NAMESPACE__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_NS_C __METHOD__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_METHOD_C __TRAIT__ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_TRAIT_C __halt_compiler lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_HALT_COMPILER \([ \t]*array[ \t]*\) lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ARRAY_CAST \([ \t]*(bool|boolean)[ \t]*\) lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_BOOL_CAST \([ \t]*(real|double|float)[ \t]*\) lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DOUBLE_CAST \([ \t]*(int|integer)[ \t]*\) lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_INT_CAST \([ \t]*object[ \t]*\) lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_OBJECT_CAST \([ \t]*string[ \t]*\) lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_STRING_CAST \([ \t]*unset[ \t]*\) lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_UNSET_CAST new lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_NEW and lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LOGICAL_AND or lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LOGICAL_OR xor lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_LOGICAL_XOR \\ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_NS_SEPARATOR \.\.\. lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ELLIPSIS; :: lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_PAAMAYIM_NEKUDOTAYIM; // T_DOUBLE_COLON && lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_BOOLEAN_AND \|\| lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_BOOLEAN_OR &= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_AND_EQUAL \|= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_OR_EQUAL \.= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CONCAT_EQUAL; \*= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_MUL_EQUAL \*\*= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_POW_EQUAL [/]= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DIV_EQUAL; \+= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_PLUS_EQUAL -= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_MINUS_EQUAL \^= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_XOR_EQUAL %= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_MOD_EQUAL -- lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DEC; \+\+ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_INC => lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DOUBLE_ARROW; \<=\> lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_SPACESHIP \!=|\<\> lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IS_NOT_EQUAL \!== lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IS_NOT_IDENTICAL == lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IS_EQUAL === lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IS_IDENTICAL \<\<= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_SL_EQUAL \>\>= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_SR_EQUAL \>= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IS_GREATER_OR_EQUAL \<= lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_IS_SMALLER_OR_EQUAL \*\* lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_POW \<\< lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_SL \>\> lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_SR \?\? lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_COALESCE (#|[/][/]).*{NEW_LINE} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil)));// return T_COMMENT; // TODO: handle ?> [/][*][^*]*[*]+([^*/][^*]*[*]+)*[/] lval.token = newToken(l.handleNewLine(l.TokenBytes(nil)));// return T_COMMENT; // TODO: handle ?> [/][*][*][^*]*[*]+([^*/][^*]*[*]+)*[/] lval.token = newToken(l.handleNewLine(l.TokenBytes(nil)));// return T_DOC_COMMENT; // TODO: handle ?> '[^']*(\\')*' lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CONSTANT_ENCAPSED_STRING {OPERATORS} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) \{ l.pushState(PHP); lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) \} l.popState(); lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) \${VAR_NAME} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_VARIABLE {VAR_NAME} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_STRING -> l.begin(PROPERTY);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_OBJECT_OPERATOR; [ \t\n\r]+ lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_WHITESPACE; -> lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_OBJECT_OPERATOR; {VAR_NAME} l.begin(PHP);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_STRING; . l.ungetN(1);l.begin(PHP) [\']([^\\\']*([\\][\'])*)*[\'] lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CONSTANT_ENCAPSED_STRING; ` l.begin(BACKQUOTE); lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); rune2Class(rune(l.TokenBytes(nil)[0])) ` l.begin(PHP); lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); rune2Class(rune(l.TokenBytes(nil)[0])) [b]?\<\<\<[ \t]*({VAR_NAME}|([']{VAR_NAME}['])|(["]{VAR_NAME}["])){NEW_LINE} tb := l.TokenBytes(nil) binPrefix := 0 if tb[0] == 'b' { binPrefix = 1 } lblFirst := 3 + binPrefix lblLast := len(tb)-2 if tb[lblLast] == '\r' { lblLast-- } for { if tb[lblFirst] == ' ' || tb[lblFirst] == '\t' { lblFirst++ continue } break } switch tb[lblFirst] { case '\'' : lblFirst++ lblLast-- l.begin(NOWDOC) case '"' : lblFirst++ lblLast-- l.begin(HEREDOC) default: l.begin(HEREDOC) } heredocLabel = make([]byte, lblLast - lblFirst + 1) copy(heredocLabel, tb[lblFirst:lblLast+1]) ungetCnt := len(heredocLabel) searchLabelAhead := []byte{} for i := 0; i < len(heredocLabel); i++ { if c == -1 { break; } searchLabelAhead = append(searchLabelAhead, byte(rune(c))) c = l.Next() } if bytes.Equal(heredocLabel, searchLabelAhead) && ';' == rune(c) { ungetCnt++ c = l.Next() if '\n' == rune(c) || '\r' == rune(c) { l.begin(HEREDOC_END) } } l.ungetN(ungetCnt) lval.token = newToken(l.handleNewLine(tb)); return T_START_HEREDOC . searchLabel := []byte{} tb := []byte{} for { if c == -1 { break; } if '\n' == rune(c) || '\r' == rune(c) { if bytes.Equal(append(heredocLabel, ';'), searchLabel) { l.begin(HEREDOC_END) tb = l.ungetN(len(heredocLabel)+1) break; } searchLabel = []byte{} } else { searchLabel = append(searchLabel, byte(rune(c))) } c = l.Next() } lval.token = newToken(l.handleNewLine(tb)); return T_ENCAPSED_AND_WHITESPACE {VAR_NAME}\; l.begin(PHP);lval.token = newToken(l.handleNewLine(l.ungetN(1))); return T_END_HEREDOC [b]?[\"] binPrefix := l.TokenBytes(nil)[0] == 'b' beginString := func() int { cnt := 1; if (binPrefix) {cnt = 2} l.ungetN(len(l.TokenBytes(nil))-cnt) tokenBytes := l.TokenBytes(nil)[:cnt] l.pushState(STRING) lval.token = newToken(l.handleNewLine(tokenBytes)); return rune2Class('"') } F:for { if c == -1 { break; } switch c { case '"' : c = l.Next(); lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_CONSTANT_ENCAPSED_STRING break F; case '$': c = l.Next(); if rune(c) == '{' || c >= 'A' && c <= 'Z' || c == '_' || c >= 'a' && c <= 'z' || c >= '\u007f' && c <= 'ÿ' { return beginString() break F; } l.ungetN(0) case '{': c = l.Next(); if rune(c) == '$' { return beginString() break F; } l.ungetN(0) case '\\': c = l.Next(); } c = l.Next() } \" l.popState(); lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) \{\$ lval.token = newToken(l.handleNewLine(l.ungetN(1))); l.pushState(PHP); return T_CURLY_OPEN \$\{ l.pushState(STRING_VAR_NAME);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_DOLLAR_OPEN_CURLY_BRACES \$ l.ungetN(1);l.pushState(STRING_VAR) .|[ \t\n\r] F1:for { if c == -1 { break; } switch c { case '"' : lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENCAPSED_AND_WHITESPACE break F1; case '$': c = l.Next(); if rune(c) == '{' || c >= 'A' && c <= 'Z' || c == '_' || c >= 'a' && c <= 'z' || c >= '\u007f' && c <= 'ÿ' { l.ungetN(1) tb := l.TokenBytes(nil) lval.token = newToken(l.handleNewLine(tb[:len(tb)-1])); return T_ENCAPSED_AND_WHITESPACE break F1; } l.ungetN(0) case '{': c = l.Next(); if rune(c) == '$' { l.ungetN(1) tb := l.TokenBytes(nil) lval.token = newToken(l.handleNewLine(tb[:len(tb)-1])); return T_ENCAPSED_AND_WHITESPACE break F1; } l.ungetN(0) case '\\': c = l.Next(); } c = l.Next() } . F2:for { if c == -1 { break; } switch c { case '`' : lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENCAPSED_AND_WHITESPACE break F2; case '$': c = l.Next(); if rune(c) == '{' || c >= 'A' && c <= 'Z' || c == '_' || c >= 'a' && c <= 'z' || c >= '\u007f' && c <= 'ÿ' { l.ungetN(1) tb := l.TokenBytes(nil) lval.token = newToken(l.handleNewLine(tb[:len(tb)-1])); return T_ENCAPSED_AND_WHITESPACE break F2; } l.ungetN(0) case '{': c = l.Next(); if rune(c) == '$' { l.ungetN(1) tb := l.TokenBytes(nil) lval.token = newToken(l.handleNewLine(tb[:len(tb)-1])); return T_ENCAPSED_AND_WHITESPACE break F2; } l.ungetN(0) case '\\': c = l.Next(); } c = l.Next() } .|[ \t\n\r] searchLabel := []byte{} tb := []byte{} HEREDOCFOR:for { if c == -1 { break; } switch c { case '\n': fallthrough case '\r': if bytes.Equal(append(heredocLabel, ';'), searchLabel) { // TODO handle ';' as optional l.begin(HEREDOC_END) tb = l.ungetN(len(heredocLabel)+1) break HEREDOCFOR; } searchLabel = []byte{} case '$': c = l.Next(); if rune(c) == '{' || c >= 'A' && c <= 'Z' || c == '_' || c >= 'a' && c <= 'z' || c >= '\u007f' && c <= 'ÿ' { tb = l.ungetN(1) break HEREDOCFOR; } l.ungetN(0) searchLabel = []byte{} case '{': c = l.Next(); if rune(c) == '$' { tb = l.ungetN(1) break HEREDOCFOR; } l.ungetN(0) searchLabel = []byte{} case '\\': c = l.Next(); searchLabel = []byte{} default: searchLabel = append(searchLabel, byte(rune(c))) } c = l.Next() } lval.token = newToken(l.handleNewLine(tb)); return T_ENCAPSED_AND_WHITESPACE \${VAR_NAME} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_VARIABLE ->{VAR_NAME} lval.token = newToken(l.handleNewLine(l.ungetN(len(l.TokenBytes(nil))-2))); return T_OBJECT_OPERATOR {VAR_NAME} l.popState();lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_STRING \[ l.pushState(STRING_VAR_INDEX);lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) .|[ \t\n\r] l.ungetN(1);l.popState() {LNUM}|{HNUM}|{BNUM} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_NUM_STRING \${VAR_NAME} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_VARIABLE {VAR_NAME} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_STRING \] l.popState(); l.popState();lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) [ \n\r\t\\'#] l.popState(); l.popState();lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return T_ENCAPSED_AND_WHITESPACE {OPERATORS} lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) . lval.token = newToken(l.handleNewLine(l.TokenBytes(nil))); return rune2Class(rune(l.TokenBytes(nil)[0])) {VAR_NAME}[\[\}] l.popState();l.pushState(PHP);lval.token = newToken(l.handleNewLine(l.ungetN(1))); return T_STRING_VARNAME . l.ungetN(1);l.popState();l.pushState(PHP) %% if c, ok := l.Abort(); ok { return int(c) } goto yyAction }