2
0
Эх сурвалжийг харах

Handle invalid object literal keys. Fixes #352.

Dmitry Panov 3 жил өмнө
parent
commit
fb27c91c26

+ 7 - 0
compiler_test.go

@@ -4515,6 +4515,13 @@ func TestSrcLocations(t *testing.T) {
 	testScriptWithTestLib(SCRIPT, _undefined, t)
 }
 
+func TestBadObjectKey(t *testing.T) {
+	_, err := Compile("", "({!:0})", false)
+	if err == nil {
+		t.Fatal("expected error")
+	}
+}
+
 /*
 func TestBabel(t *testing.T) {
 	src, err := ioutil.ReadFile("babel7.js")

+ 15 - 9
parser/expression.go

@@ -310,13 +310,15 @@ func (self *_parser) parseObjectPropertyKey() (string, unistring.String, ast.Exp
 		}
 	default:
 		// null, false, class, etc.
-		if isId(tkn) {
+		if token.IsId(tkn) {
 			value = &ast.StringLiteral{
 				Idx:     idx,
 				Literal: literal,
 				Value:   unistring.String(literal),
 			}
 			tkn = token.KEYWORD
+		} else {
+			self.errorUnexpectedToken(tkn)
 		}
 	}
 	return literal, parsedLiteral, value, tkn
@@ -404,13 +406,15 @@ func (self *_parser) parseObjectProperty() ast.Property {
 	}
 
 	self.expect(token.COLON)
-
-	return &ast.PropertyKeyed{
-		Key:      value,
-		Kind:     ast.PropertyKindValue,
-		Value:    self.parseAssignmentExpression(),
-		Computed: tkn == token.ILLEGAL,
+	if value != nil {
+		return &ast.PropertyKeyed{
+			Key:      value,
+			Kind:     ast.PropertyKindValue,
+			Value:    self.parseAssignmentExpression(),
+			Computed: tkn == token.ILLEGAL,
+		}
 	}
+	return nil
 }
 
 func (self *_parser) parseObjectLiteral() *ast.ObjectLiteral {
@@ -418,7 +422,9 @@ func (self *_parser) parseObjectLiteral() *ast.ObjectLiteral {
 	idx0 := self.expect(token.LEFT_BRACE)
 	for self.token != token.RIGHT_BRACE && self.token != token.EOF {
 		property := self.parseObjectProperty()
-		value = append(value, property)
+		if property != nil {
+			value = append(value, property)
+		}
 		if self.token != token.RIGHT_BRACE {
 			self.expect(token.COMMA)
 		} else {
@@ -543,7 +549,7 @@ func (self *_parser) parseDotMember(left ast.Expression) ast.Expression {
 	literal := self.parsedLiteral
 	idx := self.idx
 
-	if self.token != token.IDENTIFIER && !isId(self.token) {
+	if !token.IsId(self.token) {
 		self.expect(token.IDENTIFIER)
 		self.nextStatement()
 		return &ast.BadExpression{From: period, To: self.idx}

+ 0 - 47
parser/lexer.go

@@ -186,53 +186,6 @@ func isLineTerminator(chr rune) bool {
 	return false
 }
 
-func isId(tkn token.Token) bool {
-	switch tkn {
-	case token.KEYWORD,
-		token.BOOLEAN,
-		token.NULL,
-		token.THIS,
-		token.IF,
-		token.IN,
-		token.OF,
-		token.DO,
-
-		token.VAR,
-		token.LET,
-		token.FOR,
-		token.NEW,
-		token.TRY,
-
-		token.ELSE,
-		token.CASE,
-		token.VOID,
-		token.WITH,
-
-		token.CONST,
-		token.WHILE,
-		token.BREAK,
-		token.CATCH,
-		token.THROW,
-
-		token.RETURN,
-		token.TYPEOF,
-		token.DELETE,
-		token.SWITCH,
-
-		token.DEFAULT,
-		token.FINALLY,
-
-		token.FUNCTION,
-		token.CONTINUE,
-		token.DEBUGGER,
-
-		token.INSTANCEOF:
-
-		return true
-	}
-	return false
-}
-
 type parserState struct {
 	tok                                token.Token
 	literal                            string

+ 4 - 0
token/token.go

@@ -114,3 +114,7 @@ func IsKeyword(literal string) (Token, bool) {
 	}
 	return 0, false
 }
+
+func IsId(tkn Token) bool {
+	return tkn >= IDENTIFIER
+}

+ 7 - 6
token/token_const.go

@@ -6,13 +6,9 @@ const (
 	ILLEGAL
 	EOF
 	COMMENT
-	KEYWORD
 
 	STRING
-	BOOLEAN
-	NULL
 	NUMBER
-	IDENTIFIER
 
 	PLUS      // +
 	MINUS     // -
@@ -75,7 +71,13 @@ const (
 	ELLIPSIS          // ...
 	BACKTICK          // `
 
-	firstKeyword
+	// tokens below (and only them) are syntactically valid identifiers
+
+	IDENTIFIER
+	KEYWORD
+	BOOLEAN
+	NULL
+
 	IF
 	IN
 	OF
@@ -112,7 +114,6 @@ const (
 	DEBUGGER
 
 	INSTANCEOF
-	lastKeyword
 )
 
 var token2string = [...]string{