diff --git a/ets2panda/parser/ETSparser.h b/ets2panda/parser/ETSparser.h index 37b3d195b34dc1aafde24a93536b5f3f7636c8c9..af11e5ec649379b6f76a7a7047be5ba70606dd50 100644 --- a/ets2panda/parser/ETSparser.h +++ b/ets2panda/parser/ETSparser.h @@ -338,6 +338,8 @@ private: // NOLINTNEXTLINE(google-default-arguments) ir::Statement *ParseStructStatement(StatementParsingFlags flags, ir::ClassDefinitionModifiers modifiers, ir::ModifierFlags modFlags = ir::ModifierFlags::NONE) override; + // NOLINTNEXTLINE(google-default-arguments) + ir::Statement *ParseInterfaceStatement(StatementParsingFlags flags) override; ir::AstNode *ParseClassElementHelper( const ArenaVector &properties, std::tuple modifierInfo, diff --git a/ets2panda/parser/ETSparserStatements.cpp b/ets2panda/parser/ETSparserStatements.cpp index c38ad1ef3a16019cfa945f615ecdceec7eab4408..d466aa3aafdf32fcbe2ce02fcb7701c93d448b59 100644 --- a/ets2panda/parser/ETSparserStatements.cpp +++ b/ets2panda/parser/ETSparserStatements.cpp @@ -374,4 +374,13 @@ ir::Statement *ETSParser::ParseStructStatement([[maybe_unused]] StatementParsing return AllocBrokenStatement(rangeStruct); } +// NOLINTNEXTLINE(google-default-arguments) +ir::Statement *ETSParser::ParseInterfaceStatement([[maybe_unused]] StatementParsingFlags flags) +{ + auto &rangeClass = Lexer()->GetToken().Loc(); + LogError(diagnostic::ILLEGAL_START_STRUCT_CLASS, {"INTERFACE"}, Lexer()->GetToken().Start()); + ParseInterfaceDeclaration(false); + return AllocBrokenStatement(rangeClass); +} + } // namespace ark::es2panda::parser diff --git a/ets2panda/parser/parserImpl.h b/ets2panda/parser/parserImpl.h index c71ad06628d3c17756b408eace5e79973cf7e316..dedba93cebdb61ee7736e404a4ee37cd17ccac28 100644 --- a/ets2panda/parser/parserImpl.h +++ b/ets2panda/parser/parserImpl.h @@ -305,6 +305,8 @@ protected: // NOLINTNEXTLINE(google-default-arguments) virtual ir::Statement *ParseStructStatement(StatementParsingFlags flags, ir::ClassDefinitionModifiers modifiers, ir::ModifierFlags modFlags = ir::ModifierFlags::NONE); + // NOLINTNEXTLINE(google-default-arguments) + virtual ir::Statement *ParseInterfaceStatement(StatementParsingFlags flags); ir::Statement *ParseStatementBasedOnTokenType(StatementParsingFlags flags); ir::Statement *ParseVarStatement(); ir::Statement *ParseLetStatement(StatementParsingFlags flags); diff --git a/ets2panda/parser/statementParser.cpp b/ets2panda/parser/statementParser.cpp index a866581e20c49c3d4837afb112887aaf46c2a8c1..8cbab67f45a342dc6d076b6e604d1a637a2f1120 100644 --- a/ets2panda/parser/statementParser.cpp +++ b/ets2panda/parser/statementParser.cpp @@ -195,7 +195,7 @@ ir::Statement *ParserImpl::ParseStatementBasedOnTokenType(StatementParsingFlags case lexer::TokenType::KEYW_ENUM: return ParseEnumDeclaration(); case lexer::TokenType::KEYW_INTERFACE: - return ParseInterfaceDeclaration(false); + return ParseInterfaceStatement(flags); case lexer::TokenType::PUNCTUATOR_AT: if (IsETSParser()) { return ParseAnnotationsInStatement(flags); @@ -317,6 +317,15 @@ ir::Statement *ParserImpl::ParseClassStatement(StatementParsingFlags flags, ir:: return ParseClassDeclaration(modifiers, modFlags); } +ir::Statement *ParserImpl::ParseInterfaceStatement(StatementParsingFlags flags) +{ + if ((flags & StatementParsingFlags::ALLOW_LEXICAL) == 0) { + LogError(diagnostic::LEXICAL_DEC_NOT_ALLOWED_IN_SINGLE_STATEMENT_CONTEXT); + } + + return ParseInterfaceDeclaration(false); +} + ir::Statement *ParserImpl::ParseStructDeclaration(ir::ClassDefinitionModifiers modifiers, ir::ModifierFlags flags) { const lexer::SourcePosition startLoc = lexer_->GetToken().Start(); diff --git a/ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets b/ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets index 891e84f1a8062aaaed089fba65075575d49c121f..89ab183d9fbceec4894288ae00fbbcb900d9b796 100644 --- a/ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets +++ b/ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets @@ -19,4 +19,7 @@ export function foo() { } let a:A = {s:""} -} \ No newline at end of file +} + +/* @@? 17:5 Error SyntaxError: Illegal start of INTERFACE expression. */ +/* @@? 21:11 Error TypeError: Cannot find type 'A'. */ diff --git a/ets2panda/test/ast/parser/ets/InvalidClasses.ets b/ets2panda/test/ast/parser/ets/InvalidClasses.ets index b73dc9af4c14bebae42fa2cc529e95e6ee810222..44236605f8b537db60d09db885cf76b9519e228b 100644 --- a/ets2panda/test/ast/parser/ets/InvalidClasses.ets +++ b/ets2panda/test/ast/parser/ets/InvalidClasses.ets @@ -114,11 +114,12 @@ interface I1 { /* @@? 58:25 Error SyntaxError: Unexpected token '}'. */ /* @@? 61:5 Error SyntaxError: Illegal start of CLASS expression. */ /* @@? 62:9 Error SyntaxError: Local class or interface declaration members can not have access modifies. */ +/* @@? 65:5 Error SyntaxError: Illegal start of INTERFACE expression. */ /* @@? 66:9 Error SyntaxError: Local class or interface declaration members can not have access modifies. */ /* @@? 66:18 Error SyntaxError: Private interface methods must have body. */ /* @@? 67:9 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ -/* @@? 67:16 Error SyntaxError: Unexpected token, expected ','. */ /* @@? 67:16 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ +/* @@? 67:16 Error SyntaxError: Unexpected token, expected ','. */ /* @@? 67:16 Error SyntaxError: Identifier expected. */ /* @@? 67:24 Error SyntaxError: Private interface methods must have body. */ /* @@? 72:5 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ diff --git a/ets2panda/test/ast/parser/ets/annotations_tests/annotationDecl_with_access_modifier03.ets b/ets2panda/test/ast/parser/ets/annotations_tests/annotationDecl_with_access_modifier03.ets index c6d1285bf8ac75f6673ba770e7e0c0105e76c263..5d02e269821f8baa9efce346ee33ae994d51afa2 100644 --- a/ets2panda/test/ast/parser/ets/annotations_tests/annotationDecl_with_access_modifier03.ets +++ b/ets2panda/test/ast/parser/ets/annotations_tests/annotationDecl_with_access_modifier03.ets @@ -20,3 +20,4 @@ /* @@@ label Error SyntaxError: Unexpected token 'static'. */ /* @@@ label1 Error SyntaxError: Unexpected token '@'. */ /* @@? 15:38 Error SyntaxError: Annotations can only be declared at the top level. */ +/* @@? 15:38 Error SyntaxError: Illegal start of INTERFACE expression. */ diff --git a/ets2panda/test/ast/parser/ets/interface_parser_error_1.ets b/ets2panda/test/ast/parser/ets/interface_parser_error_1.ets index afa196d8f38516aa48a779213330e93a323eb240..387343669d0359691456327e18121cce54265d17 100644 --- a/ets2panda/test/ast/parser/ets/interface_parser_error_1.ets +++ b/ets2panda/test/ast/parser/ets/interface_parser_error_1.ets @@ -39,6 +39,7 @@ function mdin() { let a = new A(); /* @@? 17:4 Error SyntaxError: Unexpected token '{'. */ /* @@? 17:5 Error TypeError: Unresolved reference name */ /* @@? 17:11 Error SyntaxError: Unexpected token ':'. */ +/* @@? 19:1 Error SyntaxError: Illegal start of INTERFACE expression. */ /* @@? 20:5 Error SyntaxError: Identifier expected. */ /* @@? 20:14 Error SyntaxError: Unexpected token, expected ','. */ /* @@? 20:14 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ @@ -52,11 +53,11 @@ function mdin() { let a = new A(); /* @@? 24:7 Error TypeError: Unresolved reference A */ /* @@? 24:9 Error SyntaxError: Unexpected token 'implements'. */ /* @@? 24:20 Error SyntaxError: Unexpected token 'I'. */ -/* @@? 24:20 Error TypeError: Interface name 'I' used in the wrong context */ +/* @@? 24:20 Error TypeError: Unresolved reference I */ /* @@? 24:22 Error SyntaxError: Unexpected token '{'. */ /* @@? 25:4 Error TypeError: Unresolved reference reanstructor */ -/* @@? 26:19 Error SyntaxError: Unexpected token '�ls'. */ /* @@? 26:19 Error SyntaxError: Unexpected token, expected an identifier. */ +/* @@? 26:19 Error SyntaxError: Unexpected token '�ls'. */ /* @@? 27:5 Error SyntaxError: Unexpected token 'A'. */ /* @@? 27:7 Error SyntaxError: Unexpected token '{'. */ /* @@? 28:5 Error SyntaxError: Identifier expected, got 'constructor'. */ @@ -64,4 +65,4 @@ function mdin() { let a = new A(); /* @@? 29:18 Error SyntaxError: Unexpected token, expected an identifier. */ /* @@? 31:2 Error SyntaxError: Unexpected token '*'. */ /* @@? 32:1 Error SyntaxError: Nested functions are not allowed. */ -/* @@? 68:1 Error SyntaxError: Expected '}', got 'end of stream'. */ +/* @@? 69:1 Error SyntaxError: Expected '}', got 'end of stream'. */ diff --git a/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private1.ets b/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private1.ets index 6a6186266b252947f343039e587b450c7a5fd198..490354a6199008db14aa92835199ca3b07a7e537 100644 --- a/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private1.ets +++ b/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private1.ets @@ -15,10 +15,11 @@ function foo() { - interface LocalInterface + /* @@ label1 */interface LocalInterface { - /* @@ label */private property : int; + /* @@ label2 */private property : int; } } -/* @@@ label Error SyntaxError: Local class or interface declaration members can not have access modifies. */ +/* @@@ label1 Error SyntaxError: Illegal start of INTERFACE expression. */ +/* @@@ label2 Error SyntaxError: Local class or interface declaration members can not have access modifies. */ diff --git a/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private2.ets b/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private2.ets index 1083684e90c401c4f02826620138ba1bdee9c1ad..7f76e7b9909c883eb60e5618fdb2761c6edf2a5b 100644 --- a/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private2.ets +++ b/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-private2.ets @@ -15,10 +15,12 @@ function foo() { - interface LocalInterface + /* @@ label1 */interface LocalInterface { - /* @@ label */private method/* @@ label1 */() : void; + /* @@ label2 */private method/* @@ label3 */() : void; } } -/* @@@ label Error SyntaxError: Local class or interface declaration members can not have access modifies. */ -/* @@@ label1 Error SyntaxError: Private interface methods must have body. */ + +/* @@@ label1 Error SyntaxError: Illegal start of INTERFACE expression. */ +/* @@@ label2 Error SyntaxError: Local class or interface declaration members can not have access modifies. */ +/* @@@ label3 Error SyntaxError: Private interface methods must have body. */ diff --git a/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-protected1.ets b/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-protected1.ets index 915df139ae7012d300941e4659766ef54fc6ec63..af6da8fe3b1d6a352b72da013ebc13ff4dfa389d 100644 --- a/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-protected1.ets +++ b/ets2panda/test/ast/parser/ets/local-interface-member-access-modifier-protected1.ets @@ -15,10 +15,11 @@ function foo() { - interface LocalInterface + /* @@ label1 */interface LocalInterface { - /* @@ label */protected property : int; + /* @@ label2 */protected property : int; } } -/* @@@ label Error SyntaxError: Unexpected token, expected 'private' or identifier. */ +/* @@@ label1 Error SyntaxError: Illegal start of INTERFACE expression. */ +/* @@@ label2 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ diff --git a/ets2panda/test/ast/parser/ets/local_class_already_interface.ets b/ets2panda/test/ast/parser/ets/local_class_already_interface.ets index e9fea16e5276852d2e268c15cb1f2c51075ca1fc..64e86ea35fe8bc56389b747d4ac8285a438e4797 100644 --- a/ets2panda/test/ast/parser/ets/local_class_already_interface.ets +++ b/ets2panda/test/ast/parser/ets/local_class_already_interface.ets @@ -22,4 +22,5 @@ function bar(): void { } } +/* @@? 17:3 Error SyntaxError: Illegal start of INTERFACE expression. */ /* @@? 20:3 Error SyntaxError: Illegal start of CLASS expression. */ diff --git a/ets2panda/test/ast/compiler/ets/external_local_interface.ets b/ets2panda/test/ast/parser/ets/local_interface.ets similarity index 73% rename from ets2panda/test/ast/compiler/ets/external_local_interface.ets rename to ets2panda/test/ast/parser/ets/local_interface.ets index b17d69c20e36db6ce2d8142e5d7484e82ab5deb1..df40da65613d41717e4abda567f03447e1d03aad 100644 --- a/ets2panda/test/ast/compiler/ets/external_local_interface.ets +++ b/ets2panda/test/ast/parser/ets/local_interface.ets @@ -13,6 +13,11 @@ * limitations under the License. */ -import {foo} from "./external_local_interface_decl" - +let myAssertEqual = (actualValue: boolean, expectValue: boolean) => { + /* @@ label */interface R { + pass: boolean, + message: string + } +} +/* @@@ label Error SyntaxError: Illegal start of INTERFACE expression. */ diff --git a/ets2panda/test/ast/parser/ets/local_interface_already_class.ets b/ets2panda/test/ast/parser/ets/local_interface_already_class.ets index a1458dd7714a8573a654f57cb1afe10d621ea107..df8b96452f5280fe3a0fff4b26417033aeac07a9 100644 --- a/ets2panda/test/ast/parser/ets/local_interface_already_class.ets +++ b/ets2panda/test/ast/parser/ets/local_interface_already_class.ets @@ -23,3 +23,4 @@ function bar(): void { } /* @@? 17:3 Error SyntaxError: Illegal start of CLASS expression. */ +/* @@? 20:3 Error SyntaxError: Illegal start of INTERFACE expression. */ \ No newline at end of file diff --git a/ets2panda/test/ast/parser/ets/local_interface_already_interface.ets b/ets2panda/test/ast/parser/ets/local_interface_already_interface.ets index ad3bd01bac821f3845b1be1536d951e67f75518d..67952a2acfbbc7d4cddad6651e69ba25b4ffd959 100644 --- a/ets2panda/test/ast/parser/ets/local_interface_already_interface.ets +++ b/ets2panda/test/ast/parser/ets/local_interface_already_interface.ets @@ -22,5 +22,5 @@ function bar(): void { } } -/* @@? 20:3 Error TypeError: Variable 'BC' has already been declared. */ -/* @@? 20:3 Error TypeError: Merging declarations is not supported, please keep all definitions of classes, interfaces and enums compact in the codebase! */ +/* @@? 17:3 Error SyntaxError: Illegal start of INTERFACE expression. */ +/* @@? 20:3 Error SyntaxError: Illegal start of INTERFACE expression. */ diff --git a/ets2panda/test/ast/parser/ets/local_interface_already_variable..ets b/ets2panda/test/ast/parser/ets/local_interface_already_variable..ets index 0c4c33dce661aa1e9764c957f768cc1f5af07636..0660c505d4bda4e94018cb0e8e5c690c1d5458d8 100644 --- a/ets2panda/test/ast/parser/ets/local_interface_already_variable..ets +++ b/ets2panda/test/ast/parser/ets/local_interface_already_variable..ets @@ -20,5 +20,4 @@ function bar(): void { } } -/* @@? 18:3 Error TypeError: Variable 'BC' has already been declared. */ -/* @@? 18:3 Error TypeError: Merging declarations is not supported, please keep all definitions of classes, interfaces and enums compact in the codebase! */ +/* @@? 18:3 Error SyntaxError: Illegal start of INTERFACE expression. */ diff --git a/ets2panda/test/parser/ets/class_interface_enum_only_top_level_4-expected.txt b/ets2panda/test/parser/ets/class_interface_enum_only_top_level_4-expected.txt index 877b11b3cbdcb1e67bb071b190dba94e75cd4b0e..bb83536a22c4b1622930564982fa849a30014101 100644 --- a/ets2panda/test/parser/ets/class_interface_enum_only_top_level_4-expected.txt +++ b/ets2panda/test/parser/ets/class_interface_enum_only_top_level_4-expected.txt @@ -198,199 +198,11 @@ "type": "BlockStatement", "statements": [ { - "type": "TSInterfaceDeclaration", - "body": { - "type": "TSInterfaceBody", - "body": [ - { - "type": "MethodDefinition", - "key": { - "type": "Identifier", - "name": "foo", - "decorators": [], - "loc": { - "start": { - "line": 19, - "column": 5, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 8, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "kind": "method", - "accessibility": "public", - "static": false, - "optional": false, - "computed": false, - "value": { - "type": "FunctionExpression", - "function": { - "type": "ScriptFunction", - "id": { - "type": "Identifier", - "name": "foo", - "decorators": [], - "loc": { - "start": { - "line": 19, - "column": 5, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 8, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "generator": false, - "async": false, - "expression": false, - "params": [ - { - "type": "ETSParameterExpression", - "name": { - "type": "Identifier", - "name": "a", - "typeAnnotation": { - "type": "ETSPrimitiveType", - "loc": { - "start": { - "line": 19, - "column": 12, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 15, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "decorators": [], - "loc": { - "start": { - "line": 19, - "column": 9, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 15, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "loc": { - "start": { - "line": 19, - "column": 9, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 15, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - } - ], - "returnType": { - "type": "ETSPrimitiveType", - "loc": { - "start": { - "line": 19, - "column": 18, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 21, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "loc": { - "start": { - "line": 19, - "column": 8, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 21, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "loc": { - "start": { - "line": 19, - "column": 8, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 21, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "overloads": [], - "decorators": [], - "loc": { - "start": { - "line": 19, - "column": 5, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 19, - "column": 22, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - } - ], - "loc": { - "start": { - "line": 18, - "column": 15, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 20, - "column": 4, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "id": { - "type": "Identifier", - "name": "C", - "decorators": [], - "loc": { - "start": { - "line": 18, - "column": 13, - "program": "class_interface_enum_only_top_level_4.ets" - }, - "end": { - "line": 18, - "column": 14, - "program": "class_interface_enum_only_top_level_4.ets" - } - } - }, - "extends": [], + "type": "EmptyStatement", "loc": { "start": { - "line": 18, - "column": 3, + "line": 21, + "column": 1, "program": "class_interface_enum_only_top_level_4.ets" }, "end": { @@ -496,3 +308,4 @@ } } } +SyntaxError: Illegal start of INTERFACE expression. [class_interface_enum_only_top_level_4.ets:18:3] diff --git a/ets2panda/test/parser/ets/local-interface-expected.txt b/ets2panda/test/parser/ets/local-interface-expected.txt index 064455264662cae3ec82439cea99991aea405d90..fbabe9545cbfddd12fc129819d2fcc6f1f13ee01 100644 --- a/ets2panda/test/parser/ets/local-interface-expected.txt +++ b/ets2panda/test/parser/ets/local-interface-expected.txt @@ -198,44 +198,10 @@ "type": "BlockStatement", "statements": [ { - "type": "TSInterfaceDeclaration", - "body": { - "type": "TSInterfaceBody", - "body": [], - "loc": { - "start": { - "line": 18, - "column": 30, - "program": "local-interface.ets" - }, - "end": { - "line": 18, - "column": 33, - "program": "local-interface.ets" - } - } - }, - "id": { - "type": "Identifier", - "name": "LocalInterface", - "decorators": [], - "loc": { - "start": { - "line": 18, - "column": 15, - "program": "local-interface.ets" - }, - "end": { - "line": 18, - "column": 29, - "program": "local-interface.ets" - } - } - }, - "extends": [], + "type": "EmptyStatement", "loc": { "start": { - "line": 18, + "line": 19, "column": 5, "program": "local-interface.ets" }, @@ -373,3 +339,4 @@ } } } +SyntaxError: Illegal start of INTERFACE expression. [local-interface.ets:18:5]