From 6b78d72f0dc35e0cf06798beef71519a37350fdd Mon Sep 17 00:00:00 2001 From: furkanocalan Date: Wed, 23 Jul 2025 12:32:20 +0300 Subject: [PATCH] Fix interface mixed literals Issue: #ICOC2X Description: Fix on parser to guard not to produce duplicate index signature Signed-off-by: furkanocalan --- ets2panda/parser/ETSparser.cpp | 2 ++ ets2panda/parser/ETSparser.h | 2 ++ ets2panda/parser/ETSparserClasses.cpp | 13 +++++++ .../parser/ets/interface_mixed_literals.ets | 35 +++++++++++++++++++ ets2panda/util/diagnostic/semantic.yaml | 5 ++- 5 files changed, 56 insertions(+), 1 deletion(-) create mode 100644 ets2panda/test/parser/ets/interface_mixed_literals.ets diff --git a/ets2panda/parser/ETSparser.cpp b/ets2panda/parser/ETSparser.cpp index 7847a5b899..f08fe9a042 100644 --- a/ets2panda/parser/ETSparser.cpp +++ b/ets2panda/parser/ETSparser.cpp @@ -2132,6 +2132,8 @@ ir::AstNode *ETSParser::ParseAmbientSignature(const lexer::SourcePosition &start ir::DummyNodeFlag::INDEXER, typeAnno); ES2PANDA_ASSERT(dummyNode != nullptr); dummyNode->SetRange({startPos, Lexer()->GetToken().End()}); + Lexer()->NextToken(); // eat return type + ambientIndexerSeen_ = true; return dummyNode; } diff --git a/ets2panda/parser/ETSparser.h b/ets2panda/parser/ETSparser.h index bd8fcb7b1c..c2db7ca3cf 100644 --- a/ets2panda/parser/ETSparser.h +++ b/ets2panda/parser/ETSparser.h @@ -180,6 +180,7 @@ private: ArenaVector ParseTopLevelStatements(); ir::AstNode *HandleAmbientDeclaration(ir::ModifierFlags &memberModifiers, const std::function &parseClassMethod); + ir::Statement *CheckDuplicateAmbientIndex(bool ambientIndexerSeen, const lexer::SourcePosition &startPos); static bool IsClassMethodModifier(lexer::TokenType type) noexcept; #ifdef USE_FTW @@ -458,6 +459,7 @@ private: parser::Program *globalProgram_; std::vector insertingNodes_ {}; std::unique_ptr importPathManager_ {nullptr}; + bool ambientIndexerSeen_ {false}; }; class ExternalSourceParser { diff --git a/ets2panda/parser/ETSparserClasses.cpp b/ets2panda/parser/ETSparserClasses.cpp index 6341e82096..03d4779e7b 100644 --- a/ets2panda/parser/ETSparserClasses.cpp +++ b/ets2panda/parser/ETSparserClasses.cpp @@ -332,12 +332,24 @@ ir::AstNode *ETSParser::HandleAmbientDeclaration(ir::ModifierFlags &memberModifi return parseClassMethod(memberName); } } else { + if (auto *dup = CheckDuplicateAmbientIndex(ambientIndexerSeen_, startPosAmbient)) { + return dup; + } return ParseAmbientSignature(startPosAmbient); } } return nullptr; } +ir::Statement *ETSParser::CheckDuplicateAmbientIndex(bool ambientIndexerSeen, const lexer::SourcePosition &startPos) +{ + if (!ambientIndexerSeen) { + return nullptr; + } + LogError(diagnostic::DUPLICATE_INDEX_SIGNATURE, {}, startPos); + return AllocBrokenStatement(startPos); +} + // Helper method for ir::ModifierFlags ETSParser::ParseClassMethodModifiers(bool seenStatic) ir::ModifierFlags ETSParser::ParseClassMethodModifierFlag() { @@ -1056,6 +1068,7 @@ ir::AstNode *ETSParser::ParseInterfaceField() fieldModifiers |= ir::ModifierFlags::DECLARE; auto property = HandleAmbientDeclaration(fieldModifiers, parseClassMethod); if (property != nullptr) { + ambientIndexerSeen_ = true; return property; } } diff --git a/ets2panda/test/parser/ets/interface_mixed_literals.ets b/ets2panda/test/parser/ets/interface_mixed_literals.ets new file mode 100644 index 0000000000..675c6ab62b --- /dev/null +++ b/ets2panda/test/parser/ets/interface_mixed_literals.ets @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2024-2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + declare interface Z { + [name: string]: string; + [456: number]: boolean; +} + +/* @@? 17:12 Error SyntaxError: Index type must be number in index signature. */ +/* @@? 18:5 Error TypeError: Duplicate index signature in interface */ +/* @@? 18:6 Error SyntaxError: Unexpected token, expected ','. */ +/* @@? 18:6 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ +/* @@? 18:9 Error SyntaxError: Identifier expected. */ +/* @@? 18:9 Error SyntaxError: Unexpected token, expected ','. */ +/* @@? 18:9 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ +/* @@? 18:17 Error SyntaxError: Interface fields must have type annotation. */ +/* @@? 18:18 Error SyntaxError: Invalid Type. */ +/* @@? 18:18 Error SyntaxError: Unexpected token, expected ','. */ +/* @@? 18:18 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ +/* @@? 18:20 Error SyntaxError: Identifier expected. */ +/* @@? 18:20 Error SyntaxError: Unexpected token, expected ','. */ +/* @@? 18:20 Error SyntaxError: Unexpected token, expected 'private' or identifier. */ +/* @@? 18:27 Error SyntaxError: Identifier expected. */ \ No newline at end of file diff --git a/ets2panda/util/diagnostic/semantic.yaml b/ets2panda/util/diagnostic/semantic.yaml index cd59e9ec84..3be121909b 100644 --- a/ets2panda/util/diagnostic/semantic.yaml +++ b/ets2panda/util/diagnostic/semantic.yaml @@ -395,6 +395,10 @@ semantic: id: 219 message: "Duplicate accessor definition" +- name: DUPLICATE_INDEX_SIGNATURE + id: 392 + message: "Duplicate index signature in interface" + - name: DUPLICATE_OVERLOADED_NAME id: 385 message: "Duplicate overloaded method." @@ -1601,7 +1605,6 @@ semantic: id: 347 message: "Wrong operand type for unary expression" - graveyard: - 8 - 29 -- Gitee