Merge branch 'master' into dev
This commit is contained in:
commit
0138749c6d
1024
php5/php5.go
1024
php5/php5.go
File diff suppressed because it is too large
Load Diff
@ -377,6 +377,8 @@ top_statement:
|
|||||||
addMeta($$, $4.Meta, meta.SemiColonToken)
|
addMeta($$, $4.Meta, meta.SemiColonToken)
|
||||||
|
|
||||||
yylex.(*Parser).returnTokenToPool(yyDollar, &yyVAL)
|
yylex.(*Parser).returnTokenToPool(yyDollar, &yyVAL)
|
||||||
|
|
||||||
|
yylex.(*Parser).Begin(scanner.HALT_COMPILER)
|
||||||
}
|
}
|
||||||
| T_NAMESPACE namespace_name ';'
|
| T_NAMESPACE namespace_name ';'
|
||||||
{
|
{
|
||||||
|
13404
php5/php5_test.go
13404
php5/php5_test.go
File diff suppressed because it is too large
Load Diff
800
php7/php7.go
800
php7/php7.go
File diff suppressed because it is too large
Load Diff
@ -476,6 +476,8 @@ top_statement:
|
|||||||
addMeta($$, $4.Meta, meta.SemiColonToken)
|
addMeta($$, $4.Meta, meta.SemiColonToken)
|
||||||
|
|
||||||
yylex.(*Parser).returnTokenToPool(yyDollar, &yyVAL)
|
yylex.(*Parser).returnTokenToPool(yyDollar, &yyVAL)
|
||||||
|
|
||||||
|
yylex.(*Parser).Begin(scanner.HALT_COMPILER)
|
||||||
}
|
}
|
||||||
| T_NAMESPACE namespace_name ';'
|
| T_NAMESPACE namespace_name ';'
|
||||||
{
|
{
|
||||||
|
10371
php7/php7_test.go
10371
php7/php7_test.go
File diff suppressed because it is too large
Load Diff
@ -108,7 +108,7 @@ func (l *Lexer) popState() {
|
|||||||
l.StateStack = l.StateStack[:len-1]
|
l.StateStack = l.StateStack[:len-1]
|
||||||
}
|
}
|
||||||
|
|
||||||
func (l *Lexer) begin(state int) {
|
func (l *Lexer) Begin(state int) {
|
||||||
len := len(l.StateStack)
|
len := len(l.StateStack)
|
||||||
l.StateStack = l.StateStack[:len-1]
|
l.StateStack = l.StateStack[:len-1]
|
||||||
l.StateStack = append(l.StateStack, state)
|
l.StateStack = append(l.StateStack, state)
|
||||||
|
5941
scanner/scanner.go
5941
scanner/scanner.go
File diff suppressed because it is too large
Load Diff
@ -24,6 +24,7 @@ const (
|
|||||||
NOWDOC
|
NOWDOC
|
||||||
HEREDOC
|
HEREDOC
|
||||||
BACKQUOTE
|
BACKQUOTE
|
||||||
|
HALT_COMPILER
|
||||||
)
|
)
|
||||||
|
|
||||||
func isValidFirstVarNameRune(r rune) bool {
|
func isValidFirstVarNameRune(r rune) bool {
|
||||||
@ -36,7 +37,7 @@ func (l *Lexer) Lex(lval Lval) int {
|
|||||||
|
|
||||||
%}
|
%}
|
||||||
|
|
||||||
%s PHP STRING STRING_VAR STRING_VAR_INDEX STRING_VAR_NAME PROPERTY HEREDOC_END NOWDOC HEREDOC BACKQUOTE
|
%s PHP STRING STRING_VAR STRING_VAR_INDEX STRING_VAR_NAME PROPERTY HEREDOC_END NOWDOC HEREDOC BACKQUOTE HALT_COMPILER
|
||||||
|
|
||||||
%yyb last == '\n' || last = '\0'
|
%yyb last == '\n' || last = '\0'
|
||||||
%yyt l.getCurrentState()
|
%yyt l.getCurrentState()
|
||||||
@ -84,13 +85,13 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
lval.Token(l.createToken(tb))
|
lval.Token(l.createToken(tb))
|
||||||
return int(T_INLINE_HTML)
|
return int(T_INLINE_HTML)
|
||||||
|
|
||||||
<INITIAL>\<\?php([ \t]|{NEW_LINE}) l.begin(PHP);l.ungetChars(len(l.Token())-5)
|
<INITIAL>\<\?php([ \t]|{NEW_LINE}) l.Begin(PHP);l.ungetChars(len(l.Token())-5)
|
||||||
<INITIAL>\<\? l.begin(PHP);
|
<INITIAL>\<\? l.Begin(PHP);
|
||||||
<INITIAL>\<\?= l.begin(PHP);lval.Token(l.createToken(l.Token())); return int(T_ECHO);
|
<INITIAL>\<\?= l.Begin(PHP);lval.Token(l.createToken(l.Token())); return int(T_ECHO);
|
||||||
|
|
||||||
<PHP>[ \t\n\r]+ l.addWhiteSpace(l.Token())
|
<PHP>[ \t\n\r]+ l.addWhiteSpace(l.Token())
|
||||||
<PHP>[;][ \t\n\r]*\?\>{NEW_LINE}? l.begin(INITIAL);lval.Token(l.createToken(l.Token())); return Rune2Class(';');
|
<PHP>[;][ \t\n\r]*\?\>{NEW_LINE}? l.Begin(INITIAL);lval.Token(l.createToken(l.Token())); return Rune2Class(';');
|
||||||
<PHP>\?\>{NEW_LINE}? l.begin(INITIAL);lval.Token(l.createToken(l.Token())); return Rune2Class(';');
|
<PHP>\?\>{NEW_LINE}? l.Begin(INITIAL);lval.Token(l.createToken(l.Token())); return Rune2Class(';');
|
||||||
|
|
||||||
<PHP>{DNUM}|{EXPONENT_DNUM} lval.Token(l.createToken(l.Token())); return int(T_DNUMBER)
|
<PHP>{DNUM}|{EXPONENT_DNUM} lval.Token(l.createToken(l.Token())); return int(T_DNUMBER)
|
||||||
<PHP>{BNUM}
|
<PHP>{BNUM}
|
||||||
@ -287,6 +288,8 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
|
|
||||||
l.addComments(tb)
|
l.addComments(tb)
|
||||||
|
|
||||||
|
<PHP>[/][*][*][/]
|
||||||
|
l.addComments(l.Token())
|
||||||
<PHP>([/][*])|([/][*][*])
|
<PHP>([/][*])|([/][*][*])
|
||||||
tb := l.Token()
|
tb := l.Token()
|
||||||
is_doc_comment := false
|
is_doc_comment := false
|
||||||
@ -295,6 +298,7 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
l.PhpDocComment = ""
|
l.PhpDocComment = ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
c = l.Next()
|
||||||
for {
|
for {
|
||||||
if c == -1 {
|
if c == -1 {
|
||||||
break; // TODO: Unterminated comment starting line %d
|
break; // TODO: Unterminated comment starting line %d
|
||||||
@ -322,16 +326,16 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
<PHP>\${VAR_NAME} lval.Token(l.createToken(l.Token())); return int(T_VARIABLE)
|
<PHP>\${VAR_NAME} lval.Token(l.createToken(l.Token())); return int(T_VARIABLE)
|
||||||
<PHP>{VAR_NAME} lval.Token(l.createToken(l.Token())); return int(T_STRING)
|
<PHP>{VAR_NAME} lval.Token(l.createToken(l.Token())); return int(T_STRING)
|
||||||
|
|
||||||
<PHP>-> l.begin(PROPERTY);lval.Token(l.createToken(l.Token())); return int(T_OBJECT_OPERATOR);
|
<PHP>-> l.Begin(PROPERTY);lval.Token(l.createToken(l.Token())); return int(T_OBJECT_OPERATOR);
|
||||||
<PROPERTY>[ \t\n\r]+ l.addWhiteSpace(l.Token())
|
<PROPERTY>[ \t\n\r]+ l.addWhiteSpace(l.Token())
|
||||||
<PROPERTY>-> lval.Token(l.createToken(l.Token())); return int(T_OBJECT_OPERATOR);
|
<PROPERTY>-> lval.Token(l.createToken(l.Token())); return int(T_OBJECT_OPERATOR);
|
||||||
<PROPERTY>{VAR_NAME} l.begin(PHP);lval.Token(l.createToken(l.Token())); return int(T_STRING);
|
<PROPERTY>{VAR_NAME} l.Begin(PHP);lval.Token(l.createToken(l.Token())); return int(T_STRING);
|
||||||
<PROPERTY>. l.ungetChars(1);l.begin(PHP)
|
<PROPERTY>. l.ungetChars(1);l.Begin(PHP)
|
||||||
|
|
||||||
<PHP>[\']([^\\\']*([\\].)*)*[\'] lval.Token(l.createToken(l.Token())); return int(T_CONSTANT_ENCAPSED_STRING);
|
<PHP>[\']([^\\\']*(\\(.|\n))*)*[\'] lval.Token(l.createToken(l.Token())); return int(T_CONSTANT_ENCAPSED_STRING);
|
||||||
|
|
||||||
<PHP>` l.begin(BACKQUOTE); lval.Token(l.createToken(l.Token())); return Rune2Class(rune(l.TokenBytes(nil)[0]))
|
<PHP>` l.Begin(BACKQUOTE); lval.Token(l.createToken(l.Token())); return Rune2Class(rune(l.TokenBytes(nil)[0]))
|
||||||
<BACKQUOTE>` l.begin(PHP); lval.Token(l.createToken(l.Token())); return Rune2Class(rune(l.TokenBytes(nil)[0]))
|
<BACKQUOTE>` l.Begin(PHP); lval.Token(l.createToken(l.Token())); return Rune2Class(rune(l.TokenBytes(nil)[0]))
|
||||||
|
|
||||||
<PHP>[b]?\<\<\<[ \t]*({VAR_NAME}|([']{VAR_NAME}['])|(["]{VAR_NAME}["])){NEW_LINE}
|
<PHP>[b]?\<\<\<[ \t]*({VAR_NAME}|([']{VAR_NAME}['])|(["]{VAR_NAME}["])){NEW_LINE}
|
||||||
tb := l.Token()
|
tb := l.Token()
|
||||||
@ -362,13 +366,13 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
case '\'' :
|
case '\'' :
|
||||||
lblFirst++
|
lblFirst++
|
||||||
lblLast--
|
lblLast--
|
||||||
l.begin(NOWDOC)
|
l.Begin(NOWDOC)
|
||||||
case '"' :
|
case '"' :
|
||||||
lblFirst++
|
lblFirst++
|
||||||
lblLast--
|
lblLast--
|
||||||
l.begin(HEREDOC)
|
l.Begin(HEREDOC)
|
||||||
default:
|
default:
|
||||||
l.begin(HEREDOC)
|
l.Begin(HEREDOC)
|
||||||
}
|
}
|
||||||
|
|
||||||
l.heredocLabel = l.tokenString(tb[lblFirst:lblLast+1])
|
l.heredocLabel = l.tokenString(tb[lblFirst:lblLast+1])
|
||||||
@ -387,7 +391,7 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
ungetCnt++
|
ungetCnt++
|
||||||
c = l.Next()
|
c = l.Next()
|
||||||
if '\n' == rune(c) || '\r' == rune(c) {
|
if '\n' == rune(c) || '\r' == rune(c) {
|
||||||
l.begin(HEREDOC_END)
|
l.Begin(HEREDOC_END)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -407,14 +411,14 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
|
|
||||||
if '\n' == rune(c) || '\r' == rune(c) {
|
if '\n' == rune(c) || '\r' == rune(c) {
|
||||||
if l.heredocLabel + ";" == string(searchLabel) {
|
if l.heredocLabel + ";" == string(searchLabel) {
|
||||||
l.begin(HEREDOC_END)
|
l.Begin(HEREDOC_END)
|
||||||
tb = l.ungetChars(len(l.heredocLabel)+1)
|
tb = l.ungetChars(len(l.heredocLabel)+1)
|
||||||
tb = tb[:len(tb)-1]
|
tb = tb[:len(tb)-1]
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if l.heredocLabel == string(searchLabel) {
|
if l.heredocLabel == string(searchLabel) {
|
||||||
l.begin(HEREDOC_END)
|
l.Begin(HEREDOC_END)
|
||||||
tb = l.ungetChars(len(l.heredocLabel))
|
tb = l.ungetChars(len(l.heredocLabel))
|
||||||
tb = tb[:len(tb)-1]
|
tb = tb[:len(tb)-1]
|
||||||
break;
|
break;
|
||||||
@ -431,8 +435,8 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
lval.Token(l.createToken(tb) )
|
lval.Token(l.createToken(tb) )
|
||||||
return int(T_ENCAPSED_AND_WHITESPACE)
|
return int(T_ENCAPSED_AND_WHITESPACE)
|
||||||
|
|
||||||
<HEREDOC_END>{VAR_NAME}\; l.begin(PHP);lval.Token(l.createToken(l.ungetChars(1))); return int(T_END_HEREDOC)
|
<HEREDOC_END>{VAR_NAME}\; l.Begin(PHP);lval.Token(l.createToken(l.ungetChars(1))); return int(T_END_HEREDOC)
|
||||||
<HEREDOC_END>{VAR_NAME} l.begin(PHP);lval.Token(l.createToken(l.Token())); return int(T_END_HEREDOC)
|
<HEREDOC_END>{VAR_NAME} l.Begin(PHP);lval.Token(l.createToken(l.Token())); return int(T_END_HEREDOC)
|
||||||
|
|
||||||
<PHP>[b]?[\"]
|
<PHP>[b]?[\"]
|
||||||
binPrefix := l.Token()[0].Rune == 'b'
|
binPrefix := l.Token()[0].Rune == 'b'
|
||||||
@ -586,7 +590,7 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
|
|
||||||
case '\n':
|
case '\n':
|
||||||
if l.heredocLabel + ";" == string(searchLabel) {
|
if l.heredocLabel + ";" == string(searchLabel) {
|
||||||
l.begin(HEREDOC_END)
|
l.Begin(HEREDOC_END)
|
||||||
l.ungetChars(len(l.heredocLabel)+1+nls)
|
l.ungetChars(len(l.heredocLabel)+1+nls)
|
||||||
|
|
||||||
i := len(tb) - len(l.heredocLabel) - 3 - nls
|
i := len(tb) - len(l.heredocLabel) - 3 - nls
|
||||||
@ -600,7 +604,7 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if l.heredocLabel == string(searchLabel) {
|
if l.heredocLabel == string(searchLabel) {
|
||||||
l.begin(HEREDOC_END)
|
l.Begin(HEREDOC_END)
|
||||||
l.ungetChars(len(l.heredocLabel)+nls)
|
l.ungetChars(len(l.heredocLabel)+nls)
|
||||||
|
|
||||||
i := len(tb) - len(l.heredocLabel) - 2 - nls
|
i := len(tb) - len(l.heredocLabel) - 2 - nls
|
||||||
@ -667,6 +671,8 @@ NEW_LINE (\r|\n|\r\n)
|
|||||||
<STRING_VAR_NAME>{VAR_NAME}[\[\}] l.popState();l.pushState(PHP);lval.Token(l.createToken(l.ungetChars(1))); return int(T_STRING_VARNAME)
|
<STRING_VAR_NAME>{VAR_NAME}[\[\}] l.popState();l.pushState(PHP);lval.Token(l.createToken(l.ungetChars(1))); return int(T_STRING_VARNAME)
|
||||||
<STRING_VAR_NAME>. l.ungetChars(1);l.popState();l.pushState(PHP)
|
<STRING_VAR_NAME>. l.ungetChars(1);l.popState();l.pushState(PHP)
|
||||||
|
|
||||||
|
<HALT_COMPILER>.|[ \t\n\r] // do nothing
|
||||||
|
|
||||||
%%
|
%%
|
||||||
if _, ok := l.Abort(); ok {
|
if _, ok := l.Abort(); ok {
|
||||||
// always return same $end token
|
// always return same $end token
|
||||||
|
@ -431,6 +431,53 @@ func TestTokens(t *testing.T) {
|
|||||||
assertEqual(t, expected, actual)
|
assertEqual(t, expected, actual)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestSingleQuoteStringTokens(t *testing.T) {
|
||||||
|
src := `<?php
|
||||||
|
'str $var str'
|
||||||
|
|
||||||
|
'\''
|
||||||
|
|
||||||
|
'\'
|
||||||
|
'
|
||||||
|
|
||||||
|
'\
|
||||||
|
\''
|
||||||
|
|
||||||
|
'\\'
|
||||||
|
|
||||||
|
'\\
|
||||||
|
'
|
||||||
|
|
||||||
|
'\
|
||||||
|
\''
|
||||||
|
`
|
||||||
|
|
||||||
|
expected := []string{
|
||||||
|
scanner.T_CONSTANT_ENCAPSED_STRING.String(),
|
||||||
|
scanner.T_CONSTANT_ENCAPSED_STRING.String(),
|
||||||
|
scanner.T_CONSTANT_ENCAPSED_STRING.String(),
|
||||||
|
scanner.T_CONSTANT_ENCAPSED_STRING.String(),
|
||||||
|
scanner.T_CONSTANT_ENCAPSED_STRING.String(),
|
||||||
|
scanner.T_CONSTANT_ENCAPSED_STRING.String(),
|
||||||
|
scanner.T_CONSTANT_ENCAPSED_STRING.String(),
|
||||||
|
}
|
||||||
|
|
||||||
|
lexer := scanner.NewLexer(bytes.NewBufferString(src), "test.php")
|
||||||
|
lv := &lval{}
|
||||||
|
actual := []string{}
|
||||||
|
|
||||||
|
for {
|
||||||
|
token := lexer.Lex(lv)
|
||||||
|
if token < 0 {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
|
||||||
|
actual = append(actual, scanner.LexerToken(token).String())
|
||||||
|
}
|
||||||
|
|
||||||
|
assertEqual(t, expected, actual)
|
||||||
|
}
|
||||||
|
|
||||||
func TestTeplateStringTokens(t *testing.T) {
|
func TestTeplateStringTokens(t *testing.T) {
|
||||||
src := `<?php
|
src := `<?php
|
||||||
"foo $a"
|
"foo $a"
|
||||||
@ -1033,13 +1080,34 @@ func TestInlineComment(t *testing.T) {
|
|||||||
assertEqual(t, expected, actual)
|
assertEqual(t, expected, actual)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestInlineComment2(t *testing.T) {
|
||||||
|
src := `<?php
|
||||||
|
/*/*/`
|
||||||
|
|
||||||
|
expected := []meta.Meta{
|
||||||
|
meta.NewWhiteSpace("\n\t", position.NewPosition(1, 2, 6, 7)),
|
||||||
|
meta.NewComment("/*/*/", position.NewPosition(2, 2, 8, 12)),
|
||||||
|
}
|
||||||
|
|
||||||
|
lexer := scanner.NewLexer(bytes.NewBufferString(src), "test.php")
|
||||||
|
lexer.WithMeta = true
|
||||||
|
lv := &lval{}
|
||||||
|
|
||||||
|
lexer.Lex(lv)
|
||||||
|
|
||||||
|
actual := lexer.Meta
|
||||||
|
|
||||||
|
assertEqual(t, expected, actual)
|
||||||
|
}
|
||||||
|
|
||||||
func TestEmptyInlineComment(t *testing.T) {
|
func TestEmptyInlineComment(t *testing.T) {
|
||||||
src := `<?php
|
src := `<?php
|
||||||
/**/`
|
/**/ `
|
||||||
|
|
||||||
expected := []meta.Meta{
|
expected := []meta.Meta{
|
||||||
meta.NewWhiteSpace("\n\t", position.NewPosition(1, 2, 6, 7)),
|
meta.NewWhiteSpace("\n\t", position.NewPosition(1, 2, 6, 7)),
|
||||||
meta.NewComment("/**/", position.NewPosition(2, 2, 8, 11)),
|
meta.NewComment("/**/", position.NewPosition(2, 2, 8, 11)),
|
||||||
|
meta.NewWhiteSpace(" ", position.NewPosition(2, 2, 12, 12)),
|
||||||
}
|
}
|
||||||
|
|
||||||
lexer := scanner.NewLexer(bytes.NewBufferString(src), "test.php")
|
lexer := scanner.NewLexer(bytes.NewBufferString(src), "test.php")
|
||||||
|
Loading…
Reference in New Issue
Block a user