diff --git a/ets2panda/BUILD.gn b/ets2panda/BUILD.gn index 30bba267c94ff308429d0214a574b896b7375555..0e6805a900f5296f3ed4a5a5b2e929b22e72f793 100644 --- a/ets2panda/BUILD.gn +++ b/ets2panda/BUILD.gn @@ -65,6 +65,7 @@ libes2panda_sources = [ "checker/types/ets/doubleType.cpp", "checker/types/ets/etsArrayType.cpp", "checker/types/ets/etsAsyncFuncReturnType.cpp", + "checker/types/ets/etsBigIntType.cpp", "checker/types/ets/etsBooleanType.cpp", "checker/types/ets/etsDynamicType.cpp", "checker/types/ets/etsEnumType.cpp", @@ -162,6 +163,7 @@ libes2panda_sources = [ "compiler/lowering/ets/objectIndexAccess.cpp", "compiler/lowering/ets/opAssignment.cpp", "compiler/lowering/ets/promiseVoid.cpp", + "compiler/lowering/ets/structLowering.cpp", "compiler/lowering/ets/tupleLowering.cpp", "compiler/lowering/ets/unionLowering.cpp", "compiler/lowering/phase.cpp", diff --git a/ets2panda/CMakeLists.txt b/ets2panda/CMakeLists.txt index 2cc33b5480082c1454963bdcaaf8ce060761db2a..646ea4e5d314c6171bc5930ff4234b88b3f89af9 100644 --- a/ets2panda/CMakeLists.txt +++ b/ets2panda/CMakeLists.txt @@ -174,6 +174,7 @@ set(ES2PANDA_LIB_SRC compiler/lowering/ets/unionLowering.cpp compiler/lowering/ets/expandBrackets.cpp compiler/lowering/ets/promiseVoid.cpp + compiler/lowering/ets/structLowering.cpp ir/astDump.cpp ir/srcDump.cpp ir/astNode.cpp @@ -410,6 +411,7 @@ set(ES2PANDA_LIB_SRC checker/types/ets/etsFunctionType.cpp checker/types/ets/etsObjectType.cpp checker/types/ets/etsStringType.cpp + checker/types/ets/etsBigIntType.cpp checker/types/ets/etsTupleType.cpp checker/types/ets/etsTypeParameter.cpp checker/types/ets/etsUnionType.cpp diff --git a/ets2panda/checker/ETSAnalyzer.cpp b/ets2panda/checker/ETSAnalyzer.cpp index 6ce1e33e3fb05564ff3633498088db21f8d6fb91..27894723e2b7d21152fe79a95654ffa99def7cc0 100644 --- a/ets2panda/checker/ETSAnalyzer.cpp +++ b/ets2panda/checker/ETSAnalyzer.cpp @@ -21,6 +21,8 @@ #include "checker/ets/typeRelationContext.h" #include "util/helpers.h" +#include + namespace panda::es2panda::checker { ETSChecker *ETSAnalyzer::GetETSChecker() const @@ -973,9 +975,41 @@ checker::Type *ETSAnalyzer::Check(ir::BlockExpression *st) const UNREACHABLE(); } -ArenaVector &ChooseSignatures(checker::Type *callee_type, bool is_constructor_call, - bool is_functional_interface) +ArenaVector GetUnionTypeSignatures(ETSChecker *checker, checker::ETSUnionType *ets_union_type) +{ + ArenaVector call_signatures(checker->Allocator()->Adapter()); + + for (auto *constituent_type : ets_union_type->ConstituentTypes()) { + if (constituent_type->IsETSObjectType()) { + ArenaVector tmp_call_signatures(checker->Allocator()->Adapter()); + tmp_call_signatures = constituent_type->AsETSObjectType() + ->GetOwnProperty("invoke") + ->TsType() + ->AsETSFunctionType() + ->CallSignatures(); + call_signatures.insert(call_signatures.end(), tmp_call_signatures.begin(), tmp_call_signatures.end()); + } + if (constituent_type->IsETSFunctionType()) { + ArenaVector tmp_call_signatures(checker->Allocator()->Adapter()); + tmp_call_signatures = constituent_type->AsETSFunctionType()->CallSignatures(); + call_signatures.insert(call_signatures.end(), tmp_call_signatures.begin(), tmp_call_signatures.end()); + } + if (constituent_type->IsETSUnionType()) { + ArenaVector tmp_call_signatures(checker->Allocator()->Adapter()); + tmp_call_signatures = GetUnionTypeSignatures(checker, constituent_type->AsETSUnionType()); + call_signatures.insert(call_signatures.end(), tmp_call_signatures.begin(), tmp_call_signatures.end()); + } + } + + return call_signatures; +} + +ArenaVector &ChooseSignatures(ETSChecker *checker, checker::Type *callee_type, + bool is_constructor_call, bool is_functional_interface, + bool is_union_type_with_functional_interface) { + static ArenaVector union_signatures(checker->Allocator()->Adapter()); + union_signatures.clear(); if (is_constructor_call) { return callee_type->AsETSObjectType()->ConstructSignatures(); } @@ -986,6 +1020,10 @@ ArenaVector &ChooseSignatures(checker::Type *callee_type, bool is_c ->AsETSFunctionType() ->CallSignatures(); } + if (is_union_type_with_functional_interface) { + union_signatures = GetUnionTypeSignatures(checker, callee_type->AsETSUnionType()); + return union_signatures; + } return callee_type->AsETSFunctionType()->CallSignatures(); } @@ -1003,7 +1041,8 @@ checker::ETSObjectType *ChooseCalleeObj(ETSChecker *checker, ir::CallExpression } checker::Signature *ResolveSignature(ETSChecker *checker, ir::CallExpression *expr, checker::Type *callee_type, - bool is_constructor_call, bool is_functional_interface) + bool is_constructor_call, bool is_functional_interface, + bool is_union_type_with_functional_interface) { bool extension_function_type = expr->Callee()->IsMemberExpression() && checker->ExtensionETSFunctionType(callee_type); @@ -1014,7 +1053,8 @@ checker::Signature *ResolveSignature(ETSChecker *checker, ir::CallExpression *ex if (extension_function_type) { return ResolveCallExtensionFunction(callee_type->AsETSFunctionType(), checker, expr); } - auto &signatures = ChooseSignatures(callee_type, is_constructor_call, is_functional_interface); + auto &signatures = ChooseSignatures(checker, callee_type, is_constructor_call, is_functional_interface, + is_union_type_with_functional_interface); checker::Signature *signature = checker->ResolveCallExpressionAndTrailingLambda(signatures, expr, expr->Start()); if (signature->Function()->IsExtensionMethod()) { checker->ThrowTypeError({"No matching call signature"}, expr->Start()); @@ -1026,6 +1066,9 @@ checker::Type *ETSAnalyzer::GetReturnType(ir::CallExpression *expr, checker::Typ { ETSChecker *checker = GetETSChecker(); bool is_constructor_call = expr->IsETSConstructorCall(); + bool is_union_type_with_functional_interface = + callee_type->IsETSUnionType() && + callee_type->AsETSUnionType()->HasObjectType(checker::ETSObjectFlags::FUNCTIONAL_INTERFACE); bool is_functional_interface = callee_type->IsETSObjectType() && callee_type->AsETSObjectType()->HasObjectFlag( checker::ETSObjectFlags::FUNCTIONAL_INTERFACE); bool ets_extension_func_helper_type = callee_type->IsETSExtensionFuncHelperType(); @@ -1036,12 +1079,12 @@ checker::Type *ETSAnalyzer::GetReturnType(ir::CallExpression *expr, checker::Typ } if (!is_functional_interface && !callee_type->IsETSFunctionType() && !is_constructor_call && - !ets_extension_func_helper_type) { + !ets_extension_func_helper_type && !is_union_type_with_functional_interface) { checker->ThrowTypeError("This expression is not callable.", expr->Start()); } - checker::Signature *signature = - ResolveSignature(checker, expr, callee_type, is_constructor_call, is_functional_interface); + checker::Signature *signature = ResolveSignature(checker, expr, callee_type, is_constructor_call, + is_functional_interface, is_union_type_with_functional_interface); checker->CheckObjectLiteralArguments(signature, expr->Arguments()); checker->AddUndefinedParamsForDefaultParams(signature, expr->Arguments(), checker); @@ -1113,7 +1156,7 @@ checker::Type *ETSAnalyzer::Check(ir::CallExpression *expr) const // NOTE(vpukhov): #14902 substituted signature is not updated } expr->SetOptionalType(return_type); - if (expr->IsOptional() && callee_type->IsNullishOrNullLike()) { + if (expr->IsOptional() && checker->MayHaveNulllikeValue(expr->Callee()->Check(checker))) { checker->Relation()->SetNode(expr); return_type = checker->CreateOptionalResultType(return_type); checker->Relation()->SetNode(nullptr); @@ -1185,7 +1228,7 @@ checker::Type *ETSAnalyzer::Check(ir::ConditionalExpression *expr) const builtin_alternate_type = alternate_type; } - expr->SetTsType(checker->FindLeastUpperBound(builtin_conseq_type, builtin_alternate_type)); + expr->SetTsType(checker->CreateETSUnionType(builtin_conseq_type, builtin_alternate_type)); } } @@ -1498,6 +1541,38 @@ checker::Type *ETSAnalyzer::Check(ir::UnaryExpression *expr) const auto unboxed_operand_type = is_cond_expr ? checker->ETSBuiltinTypeAsConditionalType(arg_type) : checker->ETSBuiltinTypeAsPrimitiveType(arg_type); + if (arg_type != nullptr && arg_type->IsETSBigIntType() && + arg_type->HasTypeFlag(checker::TypeFlag::BIGINT_LITERAL)) { + switch (expr->OperatorType()) { + case lexer::TokenType::PUNCTUATOR_MINUS: { + checker::Type *type = checker->CreateETSBigIntLiteralType(arg_type->AsETSBigIntType()->GetValue()); + + // We do not need this const anymore as we are negating the bigint object in runtime + type->RemoveTypeFlag(checker::TypeFlag::CONSTANT); + expr->argument_->SetTsType(type); + expr->SetTsType(type); + return expr->TsType(); + } + default: + // Handled below + // NOTE(kkonsw): handle other unary operators for bigint literals + break; + } + } + + if (arg_type != nullptr && arg_type->IsETSBigIntType()) { + switch (expr->OperatorType()) { + case lexer::TokenType::PUNCTUATOR_MINUS: + case lexer::TokenType::PUNCTUATOR_PLUS: + case lexer::TokenType::PUNCTUATOR_TILDE: { + expr->SetTsType(arg_type); + return expr->TsType(); + } + default: + break; + } + } + switch (expr->OperatorType()) { case lexer::TokenType::PUNCTUATOR_MINUS: case lexer::TokenType::PUNCTUATOR_PLUS: { @@ -1516,17 +1591,17 @@ checker::Type *ETSAnalyzer::Check(ir::UnaryExpression *expr) const break; } case lexer::TokenType::PUNCTUATOR_TILDE: { - if (operand_type == nullptr || !operand_type->HasTypeFlag(checker::TypeFlag::ETS_INTEGRAL)) { - checker->ThrowTypeError("Bad operand type, the type of the operand must be integral type.", + if (operand_type == nullptr || !operand_type->HasTypeFlag(checker::TypeFlag::ETS_NUMERIC)) { + checker->ThrowTypeError("Bad operand type, the type of the operand must be numeric type.", expr->Argument()->Start()); } if (operand_type->HasTypeFlag(checker::TypeFlag::CONSTANT)) { - expr->SetTsType(checker->BitwiseNegateIntegralType(operand_type, expr)); + expr->SetTsType(checker->BitwiseNegateNumericType(operand_type, expr)); break; } - expr->SetTsType(operand_type); + expr->SetTsType(checker->SelectGlobalIntegerTypeForNumeric(operand_type)); break; } case lexer::TokenType::PUNCTUATOR_EXCLAMATION_MARK: { @@ -1563,7 +1638,7 @@ checker::Type *ETSAnalyzer::Check(ir::UnaryExpression *expr) const } } - if (arg_type->IsETSObjectType() && (unboxed_operand_type != nullptr) && + if ((arg_type != nullptr) && arg_type->IsETSObjectType() && (unboxed_operand_type != nullptr) && unboxed_operand_type->HasTypeFlag(checker::TypeFlag::ETS_PRIMITIVE)) { expr->Argument()->AddBoxingUnboxingFlags(checker->GetUnboxingFlag(unboxed_operand_type)); } @@ -1593,6 +1668,11 @@ checker::Type *ETSAnalyzer::Check(ir::UpdateExpression *expr) const } } + if (operand_type->IsETSBigIntType()) { + expr->SetTsType(operand_type); + return expr->TsType(); + } + auto unboxed_type = checker->ETSBuiltinTypeAsPrimitiveType(operand_type); if (unboxed_type == nullptr || !unboxed_type->HasTypeFlag(checker::TypeFlag::ETS_NUMERIC)) { checker->ThrowTypeError("Bad operand type, the type of the operand must be numeric type.", @@ -1615,7 +1695,9 @@ checker::Type *ETSAnalyzer::Check([[maybe_unused]] ir::YieldExpression *expr) co // compile methods for LITERAL EXPRESSIONS in alphabetical order checker::Type *ETSAnalyzer::Check([[maybe_unused]] ir::BigIntLiteral *expr) const { - UNREACHABLE(); + ETSChecker *checker = GetETSChecker(); + expr->SetTsType(checker->CreateETSBigIntLiteralType(expr->Str())); + return expr->TsType(); } checker::Type *ETSAnalyzer::Check(ir::BooleanLiteral *expr) const @@ -2671,6 +2753,7 @@ checker::Type *ETSAnalyzer::Check(ir::TSTypeAliasDeclaration *st) const { ETSChecker *checker = GetETSChecker(); if (st->TypeParams() != nullptr) { + st->SetTypeParameterTypes(checker->CreateTypeForTypeParameters(st->TypeParams())); for (auto *const param : st->TypeParams()->Params()) { const auto *const res = st->TypeAnnotation()->FindChild([¶m](const ir::AstNode *const node) { if (!node->IsIdentifier()) { @@ -2685,8 +2768,6 @@ checker::Type *ETSAnalyzer::Check(ir::TSTypeAliasDeclaration *st) const {"Type alias generic parameter '", param->Name()->Name(), "' is not used in type annotation"}, param->Start()); } - - checker->SetUpParameterType(param); } } diff --git a/ets2panda/checker/ETSchecker.cpp b/ets2panda/checker/ETSchecker.cpp index 86acb390afd3a387444ff48c3de13c72fb23780c..08adfd216f44aab57d6ebab7b6120a9b7ae23673 100644 --- a/ets2panda/checker/ETSchecker.cpp +++ b/ets2panda/checker/ETSchecker.cpp @@ -226,6 +226,11 @@ Type *ETSChecker::GlobalETSStringLiteralType() const return GetGlobalTypesHolder()->GlobalETSStringLiteralType(); } +Type *ETSChecker::GlobalETSBigIntType() const +{ + return GetGlobalTypesHolder()->GlobalETSBigIntBuiltinType(); +} + Type *ETSChecker::GlobalWildcardType() const { return GetGlobalTypesHolder()->GlobalWildcardType(); @@ -246,6 +251,11 @@ ETSObjectType *ETSChecker::GlobalBuiltinETSStringType() const return AsETSObjectType(&GlobalTypesHolder::GlobalETSStringBuiltinType); } +ETSObjectType *ETSChecker::GlobalBuiltinETSBigIntType() const +{ + return AsETSObjectType(&GlobalTypesHolder::GlobalETSBigIntBuiltinType); +} + ETSObjectType *ETSChecker::GlobalBuiltinTypeType() const { return AsETSObjectType(&GlobalTypesHolder::GlobalTypeBuiltinType); @@ -344,4 +354,19 @@ void ETSChecker::HandleUpdatedCallExpressionNode(ir::CallExpression *call_expr) VarBinder()->AsETSBinder()->HandleCustomNodes(call_expr); } +Type *ETSChecker::SelectGlobalIntegerTypeForNumeric(Type *type) +{ + switch (ETSType(type)) { + case checker::TypeFlag::FLOAT: { + return GlobalIntType(); + } + case checker::TypeFlag::DOUBLE: { + return GlobalLongType(); + } + default: { + return type; + } + } +} + } // namespace panda::es2panda::checker diff --git a/ets2panda/checker/ETSchecker.h b/ets2panda/checker/ETSchecker.h index 1783bf654dc6e639b2879876286be731ab764e0b..d20eb82595b279a4f3bf77b2c022be7730f77692 100644 --- a/ets2panda/checker/ETSchecker.h +++ b/ets2panda/checker/ETSchecker.h @@ -28,8 +28,10 @@ #include "checker/types/globalTypesHolder.h" #include "ir/ts/tsTypeParameter.h" #include "ir/ts/tsTypeParameterInstantiation.h" +#include "lexer/token/tokenType.h" #include "util/enumbitops.h" #include "util/ustring.h" +#include "utils/bit_utils.h" #include "checker/resolveResult.h" #include "macros.h" @@ -38,6 +40,7 @@ #include #include #include +#include namespace panda::es2panda::varbinder { class VarBinder; @@ -98,11 +101,13 @@ public: Type *GlobalETSNullType() const; Type *GlobalETSUndefinedType() const; Type *GlobalETSStringLiteralType() const; + Type *GlobalETSBigIntType() const; Type *GlobalWildcardType() const; ETSObjectType *GlobalETSObjectType() const; ETSObjectType *GlobalETSNullishObjectType() const; ETSObjectType *GlobalBuiltinETSStringType() const; + ETSObjectType *GlobalBuiltinETSBigIntType() const; ETSObjectType *GlobalBuiltinTypeType() const; ETSObjectType *GlobalBuiltinExceptionType() const; ETSObjectType *GlobalBuiltinErrorType() const; @@ -177,9 +182,11 @@ public: Type *FindLeastUpperBound(Type *source, Type *target); static Type *GetApparentType(Type *type); static Type const *GetApparentType(Type const *type); + Type *MaybePromotedBuiltinType(Type *type) const; Type *GetCommonClass(Type *source, Type *target); ETSObjectType *GetClosestCommonAncestor(ETSObjectType *source, ETSObjectType *target); ETSObjectType *GetTypeargumentedLUB(ETSObjectType *source, ETSObjectType *target); + bool HasETSFunctionType(ir::TypeNode *type_annotation); // Type creation ByteType *CreateByteType(int8_t value); @@ -190,9 +197,17 @@ public: LongType *CreateLongType(int64_t value); ShortType *CreateShortType(int16_t value); CharType *CreateCharType(char16_t value); + ETSBigIntType *CreateETSBigIntLiteralType(util::StringView value); ETSStringType *CreateETSStringLiteralType(util::StringView value); ETSArrayType *CreateETSArrayType(Type *element_type); Type *CreateETSUnionType(ArenaVector &&constituent_types); + template + Type *CreateETSUnionType(Types &&...types) + { + ArenaVector constituent_types(Allocator()->Adapter()); + (constituent_types.push_back(types), ...); + return CreateETSUnionType(std::move(constituent_types)); + } ETSFunctionType *CreateETSFunctionType(Signature *signature); ETSFunctionType *CreateETSFunctionType(Signature *signature, util::StringView name); ETSFunctionType *CreateETSFunctionType(ir::ScriptFunction *func, Signature *signature, util::StringView name); @@ -215,7 +230,8 @@ public: // Arithmetic Type *NegateNumericType(Type *type, ir::Expression *node); - Type *BitwiseNegateIntegralType(Type *type, ir::Expression *node); + Type *BitwiseNegateNumericType(Type *type, ir::Expression *node); + bool CheckBinaryOperatorForBigInt(Type *left, Type *right, ir::Expression *expr, lexer::TokenType op); std::tuple CheckBinaryOperator(ir::Expression *left, ir::Expression *right, ir::Expression *expr, lexer::TokenType operation_type, lexer::SourcePosition pos, bool force_promotion = false); @@ -255,6 +271,7 @@ public: checker::Type *CheckBinaryOperatorNullishCoalescing(ir::Expression *right, lexer::SourcePosition pos, checker::Type *left_type, checker::Type *right_type); Type *HandleArithmeticOperationOnTypes(Type *left, Type *right, lexer::TokenType operation_type); + Type *HandleBitwiseOperationOnTypes(Type *left, Type *right, lexer::TokenType operation_type); void FlagExpressionWithUnboxing(Type *type, Type *unboxed_type, ir::Expression *type_expression); template Type *PerformArithmeticOperationOnTypes(Type *left, Type *right, lexer::TokenType operation_type); @@ -284,6 +301,7 @@ public: { return Allocator()->New>(Allocator()->Adapter()); } + ArenaVector CreateTypeForTypeParameters(ir::TSTypeParameterDeclaration const *type_params); [[nodiscard]] bool EnhanceSubstitutionForType(const ArenaVector &type_params, Type *param_type, Type *argument_type, Substitution *substitution, ArenaUnorderedSet *instantiated_type_params); @@ -525,6 +543,7 @@ public: bool ExtensionETSFunctionType(checker::Type *type); void ValidateTupleMinElementSize(ir::ArrayExpression *array_expr, ETSTupleType *tuple); void ModifyPreferredType(ir::ArrayExpression *array_expr, Type *new_preferred_type); + Type *SelectGlobalIntegerTypeForNumeric(Type *type); // Exception ETSObjectType *CheckExceptionOrErrorType(checker::Type *type, lexer::SourcePosition pos); @@ -642,12 +661,12 @@ private: return is_construct ? &dynamic_new_intrinsics_ : &dynamic_call_intrinsics_; } - ArenaVector CreateTypeForTypeParameters(ir::TSTypeParameterDeclaration *type_params); - using Type2TypeMap = std::unordered_map; void CheckTypeParameterConstraint(ir::TSTypeParameter *param, Type2TypeMap &extends); void SetUpTypeParameterConstraint(ir::TSTypeParameter *param); + ETSObjectType *UpdateGlobalType(ETSObjectType *obj_type, util::StringView name); + ETSObjectType *UpdateBoxedGlobalType(ETSObjectType *obj_type, util::StringView name); ETSObjectType *CreateETSObjectTypeCheckBuiltins(util::StringView name, ir::AstNode *decl_node, ETSObjectFlags flags); void CheckProgram(parser::Program *program, bool run_analysis = false); @@ -655,8 +674,8 @@ private: template UType HandleModulo(UType left_value, UType right_value); - template - UType HandleBitWiseArithmetic(UType left_value, UType right_value, lexer::TokenType operation_type); + template + Type *HandleBitWiseArithmetic(Type *left_value, Type *right_value, lexer::TokenType operation_type); template typename TargetType::UType GetOperand(Type *type); diff --git a/ets2panda/checker/checker.h b/ets2panda/checker/checker.h index d411772aa97bf49a0118b174df0a6989f0b94de0..04d7708dfbf0f645ee49cb110455c41b31a9b1de 100644 --- a/ets2panda/checker/checker.h +++ b/ets2panda/checker/checker.h @@ -134,6 +134,11 @@ public: return unchecked_castable_results_; } + RelationHolder &SupertypeResults() + { + return supertype_results_; + } + std::unordered_set &TypeStack() { return type_stack_; @@ -212,6 +217,7 @@ private: RelationHolder assignable_results_; RelationHolder comparable_results_; RelationHolder unchecked_castable_results_; + RelationHolder supertype_results_; std::unordered_set type_stack_; }; diff --git a/ets2panda/checker/ets/arithmetic.cpp b/ets2panda/checker/ets/arithmetic.cpp index fe8d0cd47345b53fc79081591dd2bac96cd0c6d2..7595d94e775f374dde3fe122ff790fcf63fcd40b 100644 --- a/ets2panda/checker/ets/arithmetic.cpp +++ b/ets2panda/checker/ets/arithmetic.cpp @@ -68,7 +68,7 @@ Type *ETSChecker::NegateNumericType(Type *type, ir::Expression *node) return result; } -Type *ETSChecker::BitwiseNegateIntegralType(Type *type, ir::Expression *node) +Type *ETSChecker::BitwiseNegateNumericType(Type *type, ir::Expression *node) { ASSERT(type->HasTypeFlag(TypeFlag::CONSTANT | TypeFlag::ETS_INTEGRAL)); @@ -97,6 +97,16 @@ Type *ETSChecker::BitwiseNegateIntegralType(Type *type, ir::Expression *node) result = CreateLongType(static_cast(~static_cast(type->AsLongType()->GetValue()))); break; } + case TypeFlag::FLOAT: { + result = CreateIntType( + ~static_cast(CastFloatToInt(type->AsFloatType()->GetValue()))); + break; + } + case TypeFlag::DOUBLE: { + result = CreateLongType( + ~static_cast(CastFloatToInt(type->AsDoubleType()->GetValue()))); + break; + } default: { UNREACHABLE(); } @@ -126,6 +136,44 @@ Type *ETSChecker::HandleRelationOperationOnTypes(Type *left, Type *right, lexer: return PerformRelationOperationOnTypes(left, right, operation_type); } +bool ETSChecker::CheckBinaryOperatorForBigInt(Type *left, Type *right, ir::Expression *expr, lexer::TokenType op) +{ + if ((left == nullptr) || (right == nullptr)) { + return false; + } + + if (!left->IsETSBigIntType()) { + return false; + } + + if (!right->IsETSBigIntType()) { + return false; + } + + if (expr->IsBinaryExpression()) { + ir::BinaryExpression *be = expr->AsBinaryExpression(); + if (be->OperatorType() == lexer::TokenType::PUNCTUATOR_STRICT_EQUAL) { + // Handle strict comparison as normal comparison for bigint objects + be->SetOperator(lexer::TokenType::PUNCTUATOR_EQUAL); + } + } + + switch (op) { + case lexer::TokenType::PUNCTUATOR_EQUAL: + case lexer::TokenType::KEYW_INSTANCEOF: + // This is handled in the main CheckBinaryOperator function + return false; + default: + break; + } + + // Remove const flag - currently there are no compile time operations for bigint + left->RemoveTypeFlag(TypeFlag::CONSTANT); + right->RemoveTypeFlag(TypeFlag::CONSTANT); + + return true; +} + checker::Type *ETSChecker::CheckBinaryOperatorMulDivMod(ir::Expression *left, ir::Expression *right, lexer::TokenType operation_type, lexer::SourcePosition pos, bool is_equal_op, checker::Type *const left_type, @@ -165,6 +213,11 @@ checker::Type *ETSChecker::CheckBinaryOperatorPlus(ir::Expression *left, ir::Exp } if (left_type->IsETSStringType() || right_type->IsETSStringType()) { + if (operation_type == lexer::TokenType::PUNCTUATOR_MINUS || + operation_type == lexer::TokenType::PUNCTUATOR_MINUS_EQUAL) { + ThrowTypeError("Bad operand type, the types of the operands must be numeric type.", pos); + } + return HandleStringConcatenation(left_type, right_type); } @@ -200,13 +253,13 @@ checker::Type *ETSChecker::CheckBinaryOperatorShift(ir::Expression *left, ir::Ex FlagExpressionWithUnboxing(left_type, unboxed_l, left); FlagExpressionWithUnboxing(right_type, unboxed_r, right); - if (promoted_left_type == nullptr || !promoted_left_type->HasTypeFlag(checker::TypeFlag::ETS_INTEGRAL) || - promoted_right_type == nullptr || !promoted_right_type->HasTypeFlag(checker::TypeFlag::ETS_INTEGRAL)) { - ThrowTypeError("Bad operand type, the types of the operands must be integral type.", pos); + if (promoted_left_type == nullptr || !promoted_left_type->HasTypeFlag(checker::TypeFlag::ETS_NUMERIC) || + promoted_right_type == nullptr || !promoted_right_type->HasTypeFlag(checker::TypeFlag::ETS_NUMERIC)) { + ThrowTypeError("Bad operand type, the types of the operands must be numeric type.", pos); } if (promoted_left_type->HasTypeFlag(TypeFlag::CONSTANT) && promoted_right_type->HasTypeFlag(TypeFlag::CONSTANT)) { - return HandleArithmeticOperationOnTypes(promoted_left_type, promoted_right_type, operation_type); + return HandleBitwiseOperationOnTypes(promoted_left_type, promoted_right_type, operation_type); } switch (ETSType(promoted_left_type)) { @@ -219,10 +272,12 @@ checker::Type *ETSChecker::CheckBinaryOperatorShift(ir::Expression *left, ir::Ex case TypeFlag::CHAR: { return GlobalCharType(); } - case TypeFlag::INT: { + case TypeFlag::INT: + case TypeFlag::FLOAT: { return GlobalIntType(); } - case TypeFlag::LONG: { + case TypeFlag::LONG: + case TypeFlag::DOUBLE: { return GlobalLongType(); } default: { @@ -249,20 +304,20 @@ checker::Type *ETSChecker::CheckBinaryOperatorBitwise(ir::Expression *left, ir:: } auto [promotedType, bothConst] = - ApplyBinaryOperatorPromotion(unboxed_l, unboxed_r, TypeFlag::ETS_INTEGRAL, !is_equal_op); + ApplyBinaryOperatorPromotion(unboxed_l, unboxed_r, TypeFlag::ETS_NUMERIC, !is_equal_op); FlagExpressionWithUnboxing(left_type, unboxed_l, left); FlagExpressionWithUnboxing(right_type, unboxed_r, right); if (promotedType == nullptr && !bothConst) { - ThrowTypeError("Bad operand type, the types of the operands must be integral type.", pos); + ThrowTypeError("Bad operand type, the types of the operands must be numeric type.", pos); } if (bothConst) { - return HandleArithmeticOperationOnTypes(left_type, right_type, operation_type); + return HandleBitwiseOperationOnTypes(left_type, right_type, operation_type); } - return promotedType; + return SelectGlobalIntegerTypeForNumeric(promotedType); } checker::Type *ETSChecker::CheckBinaryOperatorLogical(ir::Expression *left, ir::Expression *right, ir::Expression *expr, @@ -477,83 +532,87 @@ Type *ETSChecker::CheckBinaryOperatorNullishCoalescing(ir::Expression *right, le return FindLeastUpperBound(non_nullish_left_type, right_type); } -// NOLINTNEXTLINE(readability-function-size) -std::tuple ETSChecker::CheckBinaryOperator(ir::Expression *left, ir::Expression *right, - ir::Expression *expr, lexer::TokenType operation_type, - lexer::SourcePosition pos, bool force_promotion) +using CheckBinaryFunction = std::function; + +std::map &GetCheckMap() { - checker::Type *const left_type = left->Check(this); - checker::Type *const right_type = right->Check(this); - const bool is_logical_extended_operator = (operation_type == lexer::TokenType::PUNCTUATOR_LOGICAL_AND) || - (operation_type == lexer::TokenType::PUNCTUATOR_LOGICAL_OR); - Type *unboxed_l = is_logical_extended_operator ? ETSBuiltinTypeAsConditionalType(left_type) - : ETSBuiltinTypeAsPrimitiveType(left_type); - Type *unboxed_r = is_logical_extended_operator ? ETSBuiltinTypeAsConditionalType(right_type) - : ETSBuiltinTypeAsPrimitiveType(right_type); + static std::map check_map = { + {lexer::TokenType::PUNCTUATOR_MULTIPLY, &ETSChecker::CheckBinaryOperatorMulDivMod}, + {lexer::TokenType::PUNCTUATOR_MULTIPLY_EQUAL, &ETSChecker::CheckBinaryOperatorMulDivMod}, + {lexer::TokenType::PUNCTUATOR_DIVIDE, &ETSChecker::CheckBinaryOperatorMulDivMod}, + {lexer::TokenType::PUNCTUATOR_DIVIDE_EQUAL, &ETSChecker::CheckBinaryOperatorMulDivMod}, + {lexer::TokenType::PUNCTUATOR_MOD, &ETSChecker::CheckBinaryOperatorMulDivMod}, + {lexer::TokenType::PUNCTUATOR_MOD_EQUAL, &ETSChecker::CheckBinaryOperatorMulDivMod}, + + {lexer::TokenType::PUNCTUATOR_MINUS, &ETSChecker::CheckBinaryOperatorPlus}, + {lexer::TokenType::PUNCTUATOR_MINUS_EQUAL, &ETSChecker::CheckBinaryOperatorPlus}, + {lexer::TokenType::PUNCTUATOR_PLUS, &ETSChecker::CheckBinaryOperatorPlus}, + {lexer::TokenType::PUNCTUATOR_PLUS_EQUAL, &ETSChecker::CheckBinaryOperatorPlus}, + + {lexer::TokenType::PUNCTUATOR_LEFT_SHIFT, &ETSChecker::CheckBinaryOperatorShift}, + {lexer::TokenType::PUNCTUATOR_LEFT_SHIFT_EQUAL, &ETSChecker::CheckBinaryOperatorShift}, + {lexer::TokenType::PUNCTUATOR_RIGHT_SHIFT, &ETSChecker::CheckBinaryOperatorShift}, + {lexer::TokenType::PUNCTUATOR_RIGHT_SHIFT_EQUAL, &ETSChecker::CheckBinaryOperatorShift}, + {lexer::TokenType::PUNCTUATOR_UNSIGNED_RIGHT_SHIFT, &ETSChecker::CheckBinaryOperatorShift}, + {lexer::TokenType::PUNCTUATOR_UNSIGNED_RIGHT_SHIFT_EQUAL, &ETSChecker::CheckBinaryOperatorShift}, + + {lexer::TokenType::PUNCTUATOR_BITWISE_OR, &ETSChecker::CheckBinaryOperatorBitwise}, + {lexer::TokenType::PUNCTUATOR_BITWISE_OR_EQUAL, &ETSChecker::CheckBinaryOperatorBitwise}, + {lexer::TokenType::PUNCTUATOR_BITWISE_AND, &ETSChecker::CheckBinaryOperatorBitwise}, + {lexer::TokenType::PUNCTUATOR_BITWISE_AND_EQUAL, &ETSChecker::CheckBinaryOperatorBitwise}, + {lexer::TokenType::PUNCTUATOR_BITWISE_XOR, &ETSChecker::CheckBinaryOperatorBitwise}, + {lexer::TokenType::PUNCTUATOR_BITWISE_XOR_EQUAL, &ETSChecker::CheckBinaryOperatorBitwise}, + }; + + return check_map; +} +struct BinaryOperatorParams { + ir::Expression *left; + ir::Expression *right; + ir::Expression *expr; + lexer::TokenType operation_type; + lexer::SourcePosition pos; + bool is_equal_op; +}; + +struct TypeParams { + checker::Type *left_type; + checker::Type *right_type; + Type *unboxed_l; + Type *unboxed_r; +}; + +static std::tuple CheckBinaryOperatorHelper(ETSChecker *checker, + const BinaryOperatorParams &binary_params, + const TypeParams &type_params) +{ + ir::Expression *left = binary_params.left; + ir::Expression *right = binary_params.right; + lexer::SourcePosition pos = binary_params.pos; + checker::Type *const left_type = type_params.left_type; + checker::Type *const right_type = type_params.right_type; + Type *unboxed_l = type_params.unboxed_l; + Type *unboxed_r = type_params.unboxed_r; checker::Type *ts_type {}; - bool is_equal_op = (operation_type > lexer::TokenType::PUNCTUATOR_SUBSTITUTION && - operation_type < lexer::TokenType::PUNCTUATOR_ARROW) && - !force_promotion; - - switch (operation_type) { - case lexer::TokenType::PUNCTUATOR_MULTIPLY: - case lexer::TokenType::PUNCTUATOR_MULTIPLY_EQUAL: - case lexer::TokenType::PUNCTUATOR_DIVIDE: - case lexer::TokenType::PUNCTUATOR_DIVIDE_EQUAL: - case lexer::TokenType::PUNCTUATOR_MOD: - case lexer::TokenType::PUNCTUATOR_MOD_EQUAL: { - ts_type = CheckBinaryOperatorMulDivMod(left, right, operation_type, pos, is_equal_op, left_type, right_type, - unboxed_l, unboxed_r); - break; - } - case lexer::TokenType::PUNCTUATOR_MINUS: - case lexer::TokenType::PUNCTUATOR_MINUS_EQUAL: { - if (left_type->IsETSStringType() || right_type->IsETSStringType()) { - ThrowTypeError("Bad operand type, the types of the operands must be numeric type.", pos); - } - - [[fallthrough]]; - } - case lexer::TokenType::PUNCTUATOR_PLUS: - case lexer::TokenType::PUNCTUATOR_PLUS_EQUAL: { - ts_type = CheckBinaryOperatorPlus(left, right, operation_type, pos, is_equal_op, left_type, right_type, - unboxed_l, unboxed_r); - break; - } - case lexer::TokenType::PUNCTUATOR_LEFT_SHIFT: - case lexer::TokenType::PUNCTUATOR_LEFT_SHIFT_EQUAL: - case lexer::TokenType::PUNCTUATOR_RIGHT_SHIFT: - case lexer::TokenType::PUNCTUATOR_RIGHT_SHIFT_EQUAL: - case lexer::TokenType::PUNCTUATOR_UNSIGNED_RIGHT_SHIFT: - case lexer::TokenType::PUNCTUATOR_UNSIGNED_RIGHT_SHIFT_EQUAL: { - ts_type = CheckBinaryOperatorShift(left, right, operation_type, pos, is_equal_op, left_type, right_type, - unboxed_l, unboxed_r); - break; - } - case lexer::TokenType::PUNCTUATOR_BITWISE_OR: - case lexer::TokenType::PUNCTUATOR_BITWISE_OR_EQUAL: - case lexer::TokenType::PUNCTUATOR_BITWISE_AND: - case lexer::TokenType::PUNCTUATOR_BITWISE_AND_EQUAL: - case lexer::TokenType::PUNCTUATOR_BITWISE_XOR_EQUAL: - case lexer::TokenType::PUNCTUATOR_BITWISE_XOR: { - ts_type = CheckBinaryOperatorBitwise(left, right, operation_type, pos, is_equal_op, left_type, right_type, - unboxed_l, unboxed_r); - break; - } + switch (binary_params.operation_type) { case lexer::TokenType::PUNCTUATOR_LOGICAL_AND: case lexer::TokenType::PUNCTUATOR_LOGICAL_OR: { - ts_type = CheckBinaryOperatorLogical(left, right, expr, pos, left_type, right_type, unboxed_l, unboxed_r); + ts_type = checker->CheckBinaryOperatorLogical(left, right, binary_params.expr, pos, left_type, right_type, + unboxed_l, unboxed_r); break; } case lexer::TokenType::PUNCTUATOR_STRICT_EQUAL: case lexer::TokenType::PUNCTUATOR_NOT_STRICT_EQUAL: { - return CheckBinaryOperatorStrictEqual(left, pos, left_type, right_type); + return checker->CheckBinaryOperatorStrictEqual(left, pos, left_type, right_type); } case lexer::TokenType::PUNCTUATOR_EQUAL: case lexer::TokenType::PUNCTUATOR_NOT_EQUAL: { - std::tuple res = - CheckBinaryOperatorEqual(left, right, operation_type, pos, left_type, right_type, unboxed_l, unboxed_r); + std::tuple res = checker->CheckBinaryOperatorEqual( + left, right, binary_params.operation_type, pos, left_type, right_type, unboxed_l, unboxed_r); if (!(std::get<0>(res) == nullptr && std::get<1>(res) == nullptr)) { return res; } @@ -563,18 +622,18 @@ std::tuple ETSChecker::CheckBinaryOperator(ir::Expression *left, case lexer::TokenType::PUNCTUATOR_LESS_THAN_EQUAL: case lexer::TokenType::PUNCTUATOR_GREATER_THAN: case lexer::TokenType::PUNCTUATOR_GREATER_THAN_EQUAL: { - return CheckBinaryOperatorLessGreater(left, right, operation_type, pos, is_equal_op, left_type, right_type, - unboxed_l, unboxed_r); + return checker->CheckBinaryOperatorLessGreater(left, right, binary_params.operation_type, pos, + binary_params.is_equal_op, left_type, right_type, unboxed_l, + unboxed_r); } case lexer::TokenType::KEYW_INSTANCEOF: { - return CheckBinaryOperatorInstanceOf(pos, left_type, right_type); + return checker->CheckBinaryOperatorInstanceOf(pos, left_type, right_type); } case lexer::TokenType::PUNCTUATOR_NULLISH_COALESCING: { - ts_type = CheckBinaryOperatorNullishCoalescing(right, pos, left_type, right_type); + ts_type = checker->CheckBinaryOperatorNullishCoalescing(right, pos, left_type, right_type); break; } default: { - // NOTE UNREACHABLE(); break; } @@ -583,6 +642,51 @@ std::tuple ETSChecker::CheckBinaryOperator(ir::Expression *left, return {ts_type, ts_type}; } +std::tuple ETSChecker::CheckBinaryOperator(ir::Expression *left, ir::Expression *right, + ir::Expression *expr, lexer::TokenType op, + lexer::SourcePosition pos, bool force_promotion) +{ + checker::Type *const left_type = left->Check(this); + checker::Type *const right_type = right->Check(this); + if ((left_type == nullptr) || (right_type == nullptr)) { + ThrowTypeError("Unexpected type error in binary expression", pos); + } + + const bool is_logical_extended_operator = + (op == lexer::TokenType::PUNCTUATOR_LOGICAL_AND) || (op == lexer::TokenType::PUNCTUATOR_LOGICAL_OR); + Type *unboxed_l = is_logical_extended_operator ? ETSBuiltinTypeAsConditionalType(left_type) + : ETSBuiltinTypeAsPrimitiveType(left_type); + Type *unboxed_r = is_logical_extended_operator ? ETSBuiltinTypeAsConditionalType(right_type) + : ETSBuiltinTypeAsPrimitiveType(right_type); + + checker::Type *ts_type {}; + bool is_equal_op = + (op > lexer::TokenType::PUNCTUATOR_SUBSTITUTION && op < lexer::TokenType::PUNCTUATOR_ARROW) && !force_promotion; + + if (CheckBinaryOperatorForBigInt(left_type, right_type, expr, op)) { + switch (op) { + case lexer::TokenType::PUNCTUATOR_GREATER_THAN: + case lexer::TokenType::PUNCTUATOR_LESS_THAN: + case lexer::TokenType::PUNCTUATOR_GREATER_THAN_EQUAL: + case lexer::TokenType::PUNCTUATOR_LESS_THAN_EQUAL: + return {GlobalETSBooleanType(), GlobalETSBooleanType()}; + default: + return {left_type, right_type}; + } + }; + + auto check_map = GetCheckMap(); + if (check_map.find(op) != check_map.end()) { + auto check = check_map[op]; + ts_type = check(this, left, right, op, pos, is_equal_op, left_type, right_type, unboxed_l, unboxed_r); + return {ts_type, ts_type}; + } + + BinaryOperatorParams binary_params {left, right, expr, op, pos, is_equal_op}; + TypeParams type_params {left_type, right_type, unboxed_l, unboxed_r}; + return CheckBinaryOperatorHelper(this, binary_params, type_params); +} + Type *ETSChecker::HandleArithmeticOperationOnTypes(Type *left, Type *right, lexer::TokenType operation_type) { ASSERT(left->HasTypeFlag(TypeFlag::CONSTANT | TypeFlag::ETS_NUMERIC) && @@ -603,6 +707,26 @@ Type *ETSChecker::HandleArithmeticOperationOnTypes(Type *left, Type *right, lexe return PerformArithmeticOperationOnTypes(left, right, operation_type); } +Type *ETSChecker::HandleBitwiseOperationOnTypes(Type *left, Type *right, lexer::TokenType operation_type) +{ + ASSERT(left->HasTypeFlag(TypeFlag::CONSTANT | TypeFlag::ETS_NUMERIC) && + right->HasTypeFlag(TypeFlag::CONSTANT | TypeFlag::ETS_NUMERIC)); + + if (left->IsDoubleType() || right->IsDoubleType()) { + return HandleBitWiseArithmetic(left, right, operation_type); + } + + if (left->IsFloatType() || right->IsFloatType()) { + return HandleBitWiseArithmetic(left, right, operation_type); + } + + if (left->IsLongType() || right->IsLongType()) { + return HandleBitWiseArithmetic(left, right, operation_type); + } + + return HandleBitWiseArithmetic(left, right, operation_type); +} + void ETSChecker::FlagExpressionWithUnboxing(Type *type, Type *unboxed_type, ir::Expression *type_expression) { if (type->IsETSObjectType() && (unboxed_type != nullptr)) { diff --git a/ets2panda/checker/ets/arithmetic.h b/ets2panda/checker/ets/arithmetic.h index 0eb9a9792986862aa336fb6fd436f3af3e9bb80e..c521113a21ddcf682135aab521eeb37ce1408810 100644 --- a/ets2panda/checker/ets/arithmetic.h +++ b/ets2panda/checker/ets/arithmetic.h @@ -17,7 +17,6 @@ #define ES2PANDA_COMPILER_CHECKER_ETS_ARITHMETIC_H #include "checker/ETSchecker.h" -#include "checker/types/ets/etsBooleanType.h" namespace panda::es2panda::checker { @@ -137,7 +136,7 @@ Type *ETSChecker::PerformArithmeticOperationOnTypes(Type *left, Type *right, lex break; } default: { - result = HandleBitWiseArithmetic(left_value, right_value, operation_type); + UNREACHABLE(); } } @@ -172,63 +171,69 @@ inline DoubleType::UType panda::es2panda::checker::ETSChecker::HandleModulo -UType ETSChecker::HandleBitWiseArithmetic(UType left_value, UType right_value, lexer::TokenType operation_type) +template +inline IntegerUType CastIfFloat(FloatOrIntegerUType num) +{ + if constexpr (std::is_floating_point_v) { + return CastFloatToInt(num); + } else { + return num; + } +} + +template +Type *ETSChecker::HandleBitWiseArithmetic(Type *left, Type *right, lexer::TokenType operation_type) { - using UnsignedType = std::make_unsigned_t; - auto unsigned_left_value = static_cast(left_value); - auto unsigned_right_value = static_cast(right_value); - size_t mask = std::numeric_limits::digits - 1U; - size_t shift = static_cast(unsigned_right_value) & mask; + using IntegerUType = typename IntegerType::UType; + using UnsignedUType = std::make_unsigned_t; + + UnsignedUType result = 0; + UnsignedUType unsigned_left_value = CastIfFloat(GetOperand(left)); + UnsignedUType unsigned_right_value = CastIfFloat(GetOperand(right)); + + auto mask = std::numeric_limits::digits - 1U; + auto shift = unsigned_right_value & mask; switch (operation_type) { case lexer::TokenType::PUNCTUATOR_BITWISE_AND: case lexer::TokenType::PUNCTUATOR_BITWISE_AND_EQUAL: { - return unsigned_left_value & unsigned_right_value; + result = unsigned_left_value & unsigned_right_value; + break; } case lexer::TokenType::PUNCTUATOR_BITWISE_OR: case lexer::TokenType::PUNCTUATOR_BITWISE_OR_EQUAL: { - return unsigned_left_value | unsigned_right_value; + result = unsigned_left_value | unsigned_right_value; + break; } case lexer::TokenType::PUNCTUATOR_BITWISE_XOR: case lexer::TokenType::PUNCTUATOR_BITWISE_XOR_EQUAL: { - return unsigned_left_value ^ unsigned_right_value; + result = unsigned_left_value ^ unsigned_right_value; + break; } case lexer::TokenType::PUNCTUATOR_LEFT_SHIFT: case lexer::TokenType::PUNCTUATOR_LEFT_SHIFT_EQUAL: { - static_assert(sizeof(UType) == 4 || sizeof(UType) == 8); - return unsigned_left_value << shift; + static_assert(sizeof(UnsignedUType) == 4 || sizeof(UnsignedUType) == 8); + result = unsigned_left_value << shift; + break; } case lexer::TokenType::PUNCTUATOR_RIGHT_SHIFT: case lexer::TokenType::PUNCTUATOR_RIGHT_SHIFT_EQUAL: { - static_assert(sizeof(UType) == 4 || sizeof(UType) == 8); - return left_value >> shift; // NOLINT(hicpp-signed-bitwise) + static_assert(sizeof(IntegerUType) == 4 || sizeof(IntegerUType) == 8); + result = static_cast(unsigned_left_value) >> shift; // NOLINT(hicpp-signed-bitwise) + break; } case lexer::TokenType::PUNCTUATOR_UNSIGNED_RIGHT_SHIFT: case lexer::TokenType::PUNCTUATOR_UNSIGNED_RIGHT_SHIFT_EQUAL: { - static_assert(sizeof(UType) == 4 || sizeof(UType) == 8); - return unsigned_left_value >> shift; + static_assert(sizeof(UnsignedUType) == 4 || sizeof(UnsignedUType) == 8); + result = unsigned_left_value >> shift; + break; } default: { UNREACHABLE(); } } -} - -template <> -inline FloatType::UType ETSChecker::HandleBitWiseArithmetic( - [[maybe_unused]] FloatType::UType left_value, [[maybe_unused]] FloatType::UType right_value, - [[maybe_unused]] lexer::TokenType operation_type) -{ - return 0.0; -} -template <> -inline DoubleType::UType ETSChecker::HandleBitWiseArithmetic( - [[maybe_unused]] DoubleType::UType left_value, [[maybe_unused]] DoubleType::UType right_value, - [[maybe_unused]] lexer::TokenType operation_type) -{ - return 0.0; + return Allocator()->New(result); } } // namespace panda::es2panda::checker diff --git a/ets2panda/checker/ets/conversion.cpp b/ets2panda/checker/ets/conversion.cpp index 226eb0a57150834eac380649a2e24ebca9c5a00c..4d4833b4af91009029df8cfd97a534ffeb204b12 100644 --- a/ets2panda/checker/ets/conversion.cpp +++ b/ets2panda/checker/ets/conversion.cpp @@ -52,20 +52,17 @@ void WideningNarrowingPrimitive(TypeRelation *const relation, ByteType *const so void WideningReference(TypeRelation *const relation, ETSObjectType *const source, ETSObjectType *const target) { - relation->Result(false); - target->IsSupertypeOf(relation, source); + relation->IsSupertypeOf(target, source); } void WideningReference(TypeRelation *const relation, ETSArrayType *const source, ETSObjectType *const target) { - relation->Result(false); - target->IsSupertypeOf(relation, source); + relation->IsSupertypeOf(target, source); } void WideningReference(TypeRelation *const relation, ETSArrayType *const source, ETSArrayType *const target) { - relation->Result(false); - target->IsSupertypeOf(relation, source); + relation->IsSupertypeOf(target, source); } namespace { @@ -80,7 +77,7 @@ bool IsAllowedNarrowingReferenceConversion(TypeRelation *const relation, Type *c // - S is not a subtype of T relation->Result(false); - if (target->IsSupertypeOf(relation, source), relation->IsTrue()) { + if (relation->IsSupertypeOf(target, source)) { return false; } @@ -97,8 +94,7 @@ bool IsAllowedNarrowingReferenceConversion(TypeRelation *const relation, Type *c // 1. S and T are class types, and either |S| <: |T| or |T| <: |S|. // NOTE: use type erased S and T relation->Result(false); - if ((t->IsSupertypeOf(relation, s), relation->IsTrue()) || - (s->IsSupertypeOf(relation, t), relation->IsTrue())) { + if (relation->IsSupertypeOf(t, s) || relation->IsSupertypeOf(s, t)) { return true; } @@ -116,7 +112,7 @@ bool IsAllowedNarrowingReferenceConversion(TypeRelation *const relation, Type *c // 4. S is a class type, T is an interface type, and S names a class that is marked as final and that // implements the interface named by T. if (s->HasObjectFlag(ETSObjectFlags::CLASS) && t->HasObjectFlag(ETSObjectFlags::INTERFACE) && - s->GetDeclNode()->IsFinal() && (s->IsSupertypeOf(relation, t), relation->IsTrue())) { + s->GetDeclNode()->IsFinal() && relation->IsSupertypeOf(s, t)) { return true; } @@ -130,7 +126,7 @@ bool IsAllowedNarrowingReferenceConversion(TypeRelation *const relation, Type *c // implements the interface named by S. relation->Result(false); if (s->HasObjectFlag(ETSObjectFlags::INTERFACE) && t->HasObjectFlag(ETSObjectFlags::CLASS) && - t->GetDeclNode()->IsFinal() && (t->IsSupertypeOf(relation, s), relation->IsTrue())) { + t->GetDeclNode()->IsFinal() && relation->IsSupertypeOf(t, s)) { return true; } } diff --git a/ets2panda/checker/ets/enum.cpp b/ets2panda/checker/ets/enum.cpp index 30c36a8dc14dc09257873fe6f9638806f702691f..7259535dd04b3978c901decec194940a7c688592 100644 --- a/ets2panda/checker/ets/enum.cpp +++ b/ets2panda/checker/ets/enum.cpp @@ -139,7 +139,7 @@ template varbinder::FunctionParamScope *const param_scope, ArenaVector &¶ms, ArenaVector &&body, - ir::TypeNode *const return_type_annotation) + ir::TypeNode *const return_type_annotation, bool is_declare) { auto *const function_scope = varbinder->Allocator()->New(checker->Allocator(), param_scope); @@ -149,9 +149,15 @@ template auto *const body_block = checker->Allocator()->New(checker->Allocator(), std::move(body)); body_block->SetScope(function_scope); + auto flags = ir::ModifierFlags::PUBLIC; + + if (is_declare) { + flags |= ir::ModifierFlags::DECLARE; + } + auto *const function = checker->Allocator()->New( ir::FunctionSignature(nullptr, std::move(params), return_type_annotation), body_block, - ir::ScriptFunctionFlags::METHOD, ir::ModifierFlags::PUBLIC, false, Language(Language::Id::ETS)); + ir::ScriptFunctionFlags::METHOD, flags, is_declare, Language(Language::Id::ETS)); function->SetScope(function_scope); varbinder->AsETSBinder()->BuildInternalName(function); @@ -335,7 +341,7 @@ ETSEnumType::Method ETSChecker::CreateEnumFromIntMethod(ir::Identifier *const na auto *const enum_type_annotation = MakeTypeReference(Allocator(), enum_type->GetName()); auto *const function = MakeFunction(this, VarBinder()->AsETSBinder(), param_scope, std::move(params), - std::move(body), enum_type_annotation); + std::move(body), enum_type_annotation, enum_type->GetDecl()->IsDeclare()); function->AddFlag(ir::ScriptFunctionFlags::THROWS); auto *const ident = MakeQualifiedIdentifier(Allocator(), enum_type->GetDecl(), ETSEnumType::FROM_INT_METHOD_NAME); @@ -372,7 +378,7 @@ ETSEnumType::Method ETSChecker::CreateEnumToStringMethod(ir::Identifier *const s auto *const string_type_annotation = MakeTypeReference(Allocator(), GlobalBuiltinETSStringType()->Name()); auto *const function = MakeFunction(this, VarBinder()->AsETSBinder(), param_scope, std::move(params), - std::move(body), string_type_annotation); + std::move(body), string_type_annotation, enum_type->GetDecl()->IsDeclare()); auto *const function_ident = MakeQualifiedIdentifier(Allocator(), enum_type->GetDecl(), ETSEnumType::TO_STRING_METHOD_NAME); @@ -410,7 +416,7 @@ ETSEnumType::Method ETSChecker::CreateEnumGetValueMethod(ir::Identifier *const v auto *const int_type_annotation = Allocator()->New(ir::PrimitiveType::INT); auto *const function = MakeFunction(this, VarBinder()->AsETSBinder(), param_scope, std::move(params), - std::move(body), int_type_annotation); + std::move(body), int_type_annotation, enum_type->GetDecl()->IsDeclare()); auto *const function_ident = MakeQualifiedIdentifier(Allocator(), enum_type->GetDecl(), ETSEnumType::GET_VALUE_METHOD_NAME); @@ -449,7 +455,7 @@ ETSEnumType::Method ETSChecker::CreateEnumGetNameMethod(ir::Identifier *const na auto *const string_type_annotation = MakeTypeReference(Allocator(), GlobalBuiltinETSStringType()->Name()); auto *const function = MakeFunction(this, VarBinder()->AsETSBinder(), param_scope, std::move(params), - std::move(body), string_type_annotation); + std::move(body), string_type_annotation, enum_type->GetDecl()->IsDeclare()); auto *const function_ident = MakeQualifiedIdentifier(Allocator(), enum_type->GetDecl(), ETSEnumType::GET_NAME_METHOD_NAME); @@ -573,7 +579,7 @@ ETSEnumType::Method ETSChecker::CreateEnumValueOfMethod(ir::Identifier *const na auto *const enum_type_annotation = MakeTypeReference(Allocator(), enum_type->GetName()); auto *const function = MakeFunction(this, VarBinder()->AsETSBinder(), param_scope, std::move(params), - std::move(body), enum_type_annotation); + std::move(body), enum_type_annotation, enum_type->GetDecl()->IsDeclare()); function->AddFlag(ir::ScriptFunctionFlags::THROWS); auto *const function_ident = @@ -605,7 +611,7 @@ ETSEnumType::Method ETSChecker::CreateEnumValuesMethod(ir::Identifier *const ite Allocator()->New(MakeTypeReference(Allocator(), enum_type->GetName())); auto *const function = MakeFunction(this, VarBinder()->AsETSBinder(), param_scope, std::move(params), - std::move(body), enum_array_type_annotation); + std::move(body), enum_array_type_annotation, enum_type->GetDecl()->IsDeclare()); auto *const function_ident = MakeQualifiedIdentifier(Allocator(), enum_type->GetDecl(), ETSEnumType::VALUES_METHOD_NAME); diff --git a/ets2panda/checker/ets/function.cpp b/ets2panda/checker/ets/function.cpp index 04d093b1f360562c93a25eb156f7465367400da2..54fe77d4108c6e5bd2855f5068a3aa11a6540def 100644 --- a/ets2panda/checker/ets/function.cpp +++ b/ets2panda/checker/ets/function.cpp @@ -67,6 +67,7 @@ namespace panda::es2panda::checker { +// NOTE: #14993 merge with InstantiationContext::ValidateTypeArg bool ETSChecker::IsCompatibleTypeArgument(ETSTypeParameter *type_param, Type *type_argument, const Substitution *substitution) { @@ -76,21 +77,8 @@ bool ETSChecker::IsCompatibleTypeArgument(ETSTypeParameter *type_param, Type *ty if (!type_argument->IsETSTypeParameter() && !IsReferenceType(type_argument)) { return false; } - if (type_argument->IsETSUnionType()) { - auto const &constitutent = type_argument->AsETSUnionType()->ConstituentTypes(); - return std::all_of(constitutent.begin(), constitutent.end(), [this, type_param, substitution](Type *type_arg) { - return IsCompatibleTypeArgument(type_param->AsETSTypeParameter(), type_arg, substitution); - }); - } - - if (auto *constraint = type_param->GetConstraintType(); constraint != nullptr) { - constraint = constraint->Substitute(Relation(), substitution); - constraint->IsSupertypeOf(Relation(), type_argument); - if (!Relation()->IsTrue()) { - return false; - } - } - return true; + auto *constraint = type_param->GetConstraintType()->Substitute(Relation(), substitution); + return Relation()->IsSupertypeOf(constraint, type_argument); } /* A very rough and imprecise partial type inference */ @@ -256,6 +244,11 @@ Signature *ETSChecker::ValidateSignature(Signature *signature, const ir::TSTypeP return nullptr; } + if (argument->IsArrayExpression()) { + argument->AsArrayExpression()->GetPrefferedTypeFromFuncParam( + this, substituted_sig->Function()->Params()[index], flags); + } + auto *const argument_type = argument->Check(this); if (auto const invocation_ctx = checker::InvocationContext( @@ -1051,9 +1044,9 @@ bool ETSChecker::IsOverridableIn(Signature *signature) return false; } - if (signature->HasSignatureFlag(SignatureFlags::PUBLIC)) { - return FindAncestorGivenByType(signature->Function(), ir::AstNodeType::TS_INTERFACE_DECLARATION) == nullptr || - signature->HasSignatureFlag(SignatureFlags::STATIC); + // NOTE: #15095 workaround, separate internal visibility check + if (signature->HasSignatureFlag(SignatureFlags::PUBLIC | SignatureFlags::INTERNAL)) { + return true; } return signature->HasSignatureFlag(SignatureFlags::PROTECTED); @@ -1075,7 +1068,6 @@ bool ETSChecker::IsMethodOverridesOther(Signature *target, Signature *source) if (Relation()->IsTrue()) { CheckThrowMarkers(source, target); - CheckStaticHide(target, source); if (source->HasSignatureFlag(SignatureFlags::STATIC)) { return false; } @@ -1194,7 +1186,8 @@ bool ETSChecker::CheckOverride(Signature *signature, ETSObjectType *site) (it_subst->Function()->IsGetter() && !signature->Function()->IsGetter())) { continue; } - } else if (!IsMethodOverridesOther(it_subst, signature)) { + } + if (!IsMethodOverridesOther(it_subst, signature)) { continue; } @@ -2601,8 +2594,7 @@ bool ETSChecker::IsReturnTypeSubstitutable(Signature *const s1, Signature *const // - If R1 is a reference type then R1, adapted to the type parameters of d2 (link to generic methods), is a // subtype of R2. ASSERT(r1->HasTypeFlag(TypeFlag::ETS_ARRAY_OR_OBJECT) || r1->IsETSTypeParameter()); - r2->IsSupertypeOf(Relation(), r1); - return Relation()->IsTrue(); + return Relation()->IsSupertypeOf(r2, r1); } std::string ETSChecker::GetAsyncImplName(const util::StringView &name) diff --git a/ets2panda/checker/ets/helpers.cpp b/ets2panda/checker/ets/helpers.cpp index d9d2cf1fdde46973941f04947c433cbe6d46b0dc..8b5b137960eac806830e178847873cf457686816 100644 --- a/ets2panda/checker/ets/helpers.cpp +++ b/ets2panda/checker/ets/helpers.cpp @@ -169,37 +169,43 @@ Type *ETSChecker::CreateOptionalResultType(Type *type) return CreateNullishType(type, checker::TypeFlag::UNDEFINED, Allocator(), Relation(), GetGlobalTypesHolder()); } -bool ETSChecker::MayHaveNullValue(const Type *type) const +// NOTE(vpukhov): #14595 could be implemented with relation +template +static bool MatchConstitutentOrConstraint(P const &pred, const Type *type) { - if (type->ContainsNull() || type->IsETSNullType()) { + if (pred(type)) { return true; } + if (type->IsETSUnionType()) { + for (auto const &ctype : type->AsETSUnionType()->ConstituentTypes()) { + if (MatchConstitutentOrConstraint(pred, ctype)) { + return true; + } + } + return false; + } if (type->IsETSTypeParameter()) { - return MayHaveNullValue(type->AsETSTypeParameter()->EffectiveConstraint(this)); + return MatchConstitutentOrConstraint(pred, type->AsETSTypeParameter()->GetConstraintType()); } return false; } +bool ETSChecker::MayHaveNullValue(const Type *type) const +{ + const auto pred = [](const Type *t) { return t->ContainsNull() || t->IsETSNullType(); }; + return MatchConstitutentOrConstraint(pred, type); +} + bool ETSChecker::MayHaveUndefinedValue(const Type *type) const { - if (type->ContainsUndefined() || type->IsETSUndefinedType()) { - return true; - } - if (type->IsETSTypeParameter()) { - return MayHaveUndefinedValue(type->AsETSTypeParameter()->EffectiveConstraint(this)); - } - return false; + const auto pred = [](const Type *t) { return t->ContainsUndefined() || t->IsETSUndefinedType(); }; + return MatchConstitutentOrConstraint(pred, type); } bool ETSChecker::MayHaveNulllikeValue(const Type *type) const { - if (type->IsNullishOrNullLike()) { - return true; - } - if (type->IsETSTypeParameter()) { - return MayHaveNulllikeValue(type->AsETSTypeParameter()->EffectiveConstraint(this)); - } - return false; + const auto pred = [](const Type *t) { return t->IsNullishOrNullLike(); }; + return MatchConstitutentOrConstraint(pred, type); } bool ETSChecker::IsConstantExpression(ir::Expression *expr, Type *type) @@ -354,7 +360,7 @@ Type *ETSChecker::GuaranteedTypeForUncheckedCast(Type *base, Type *substituted) if (!base->IsETSTypeParameter()) { return nullptr; } - auto *constr = base->AsETSTypeParameter()->EffectiveConstraint(this); + auto *constr = base->AsETSTypeParameter()->GetConstraintType(); // Constraint is supertype of TypeArg AND TypeArg is supertype of Constraint return Relation()->IsIdenticalTo(substituted, constr) ? nullptr : constr; } @@ -775,6 +781,10 @@ std::tuple ETSChecker::ApplyBinaryOperatorPromotion(Type *left, Ty return {GlobalLongType(), both_const}; } + if (unboxed_l->IsCharType() && unboxed_r->IsCharType()) { + return {GlobalCharType(), both_const}; + } + return {GlobalIntType(), both_const}; } @@ -1561,7 +1571,7 @@ bool ETSChecker::IsFunctionContainsSignature(ETSFunctionType *func_type, Signatu void ETSChecker::CheckFunctionContainsClashingSignature(const ETSFunctionType *func_type, Signature *signature) { for (auto *it : func_type->CallSignatures()) { - SavedTypeRelationFlagsContext strf_ctx(Relation(), TypeRelationFlag::NO_RETURN_TYPE_CHECK); + SavedTypeRelationFlagsContext strf_ctx(Relation(), TypeRelationFlag::NONE); Relation()->IsIdenticalTo(it, signature); if (Relation()->IsTrue() && it->Function()->Id()->Name() == signature->Function()->Id()->Name()) { std::stringstream ss; @@ -1665,7 +1675,7 @@ bool ETSChecker::IsTypeBuiltinType(const Type *type) const bool ETSChecker::IsReferenceType(const Type *type) { return type->HasTypeFlag(checker::TypeFlag::ETS_ARRAY_OR_OBJECT) || type->IsETSNullLike() || - type->IsETSStringType() || type->IsETSTypeParameter() || type->IsETSUnionType(); + type->IsETSStringType() || type->IsETSTypeParameter() || type->IsETSUnionType() || type->IsETSBigIntType(); } const ir::AstNode *ETSChecker::FindJumpTarget(ir::AstNodeType node_type, const ir::AstNode *node, @@ -2614,6 +2624,19 @@ void ETSChecker::ModifyPreferredType(ir::ArrayExpression *const array_expr, Type } } +std::string GenerateImplicitInstantiateArg(varbinder::LocalVariable *instantiate_method, const std::string &class_name) +{ + auto call_signatures = instantiate_method->TsType()->AsETSFunctionType()->CallSignatures(); + ASSERT(!call_signatures.empty()); + auto method_owner = std::string(call_signatures[0]->Owner()->Name()); + std::string implicit_instantiate_argument = "()=>{return new " + class_name + "()"; + if (method_owner != class_name) { + implicit_instantiate_argument.append(" as " + method_owner); + } + implicit_instantiate_argument.append("}"); + return implicit_instantiate_argument; +} + bool ETSChecker::TryTransformingToStaticInvoke(ir::Identifier *const ident, const Type *resolved_type) { ASSERT(ident->Parent()->IsCallExpression()); @@ -2657,7 +2680,8 @@ bool ETSChecker::TryTransformingToStaticInvoke(ir::Identifier *const ident, cons call_expr->SetCallee(transformed_callee); if (instantiate_method != nullptr) { - std::string implicit_instantiate_argument = "()=>{return new " + std::string(class_name) + "()}"; + std::string implicit_instantiate_argument = + GenerateImplicitInstantiateArg(instantiate_method, std::string(class_name)); parser::Program program(Allocator(), VarBinder()); es2panda::CompilerOptions options; diff --git a/ets2panda/checker/ets/object.cpp b/ets2panda/checker/ets/object.cpp index de5ecff0c97db0f202ebf2267b9c259653f507a4..bcf80ce47039cefaf328ff3967ce74d1fb167df2 100644 --- a/ets2panda/checker/ets/object.cpp +++ b/ets2panda/checker/ets/object.cpp @@ -13,6 +13,7 @@ * limitations under the License. */ +#include "boxingConverter.h" #include "varbinder/variableFlags.h" #include "checker/ets/castingContext.h" #include "checker/types/ets/etsObjectType.h" @@ -55,6 +56,7 @@ #include "checker/types/ets/etsDynamicType.h" #include "checker/types/ets/types.h" #include "checker/ets/typeRelationContext.h" +#include "ir/ets/etsUnionType.h" namespace panda::es2panda::checker { ETSObjectType *ETSChecker::GetSuperType(ETSObjectType *type) @@ -165,7 +167,7 @@ ArenaVector ETSChecker::GetInterfaces(ETSObjectType *type) return type->Interfaces(); } -ArenaVector ETSChecker::CreateTypeForTypeParameters(ir::TSTypeParameterDeclaration *type_params) +ArenaVector ETSChecker::CreateTypeForTypeParameters(ir::TSTypeParameterDeclaration const *type_params) { ArenaVector result {Allocator()->Adapter()}; checker::ScopeContext scope_ctx(this, type_params->Scope()); @@ -247,12 +249,14 @@ void ETSChecker::SetUpTypeParameterConstraint(ir::TSTypeParameter *const param) ThrowTypeError("Extends constraint must be an object", param->Constraint()->Start()); } param_type->SetConstraintType(constraint); + } else { + param_type->SetConstraintType(GlobalETSNullishObjectType()); } + if (param->DefaultType() != nullptr) { traverse_referenced(param->DefaultType()); - auto *const dflt = param->DefaultType()->GetType(this); // NOTE: #14993 ensure default matches constraint - param_type->SetDefaultType(dflt); + param_type->SetDefaultType(MaybePromotedBuiltinType(param->DefaultType()->GetType(this))); } } @@ -263,6 +267,8 @@ ETSTypeParameter *ETSChecker::SetUpParameterType(ir::TSTypeParameter *const para param_type->AddTypeFlag(TypeFlag::GENERIC); param_type->SetDeclNode(param); param_type->SetVariable(param->Variable()); + // NOTE: #15026 recursive type parameter workaround + param_type->SetConstraintType(GlobalETSNullishObjectType()); param->Name()->Variable()->SetTsType(param_type); return param_type; @@ -405,6 +411,12 @@ void ETSChecker::ResolveDeclaredMembersOfObject(ETSObjectType *type) if (class_prop->TypeAnnotation() != nullptr && class_prop->TypeAnnotation()->IsETSFunctionType()) { type->AddProperty(it->AsLocalVariable()); it->AddFlag(varbinder::VariableFlags::METHOD_REFERENCE); + } else if (class_prop->TypeAnnotation() != nullptr && class_prop->TypeAnnotation()->IsETSTypeReference()) { + bool has_function_type = HasETSFunctionType(class_prop->TypeAnnotation()); + if (has_function_type) { + type->AddProperty(it->AsLocalVariable()); + it->AddFlag(varbinder::VariableFlags::METHOD_REFERENCE); + } } } @@ -418,6 +430,12 @@ void ETSChecker::ResolveDeclaredMembersOfObject(ETSObjectType *type) if (class_prop->TypeAnnotation() != nullptr && class_prop->TypeAnnotation()->IsETSFunctionType()) { type->AddProperty(it->AsLocalVariable()); it->AddFlag(varbinder::VariableFlags::METHOD_REFERENCE); + } else if (class_prop->TypeAnnotation() != nullptr && class_prop->TypeAnnotation()->IsETSTypeReference()) { + bool has_function_type = HasETSFunctionType(class_prop->TypeAnnotation()); + if (has_function_type) { + type->AddProperty(it->AsLocalVariable()); + it->AddFlag(varbinder::VariableFlags::METHOD_REFERENCE); + } } } @@ -473,6 +491,39 @@ void ETSChecker::ResolveDeclaredMembersOfObject(ETSObjectType *type) type->AddObjectFlag(ETSObjectFlags::RESOLVED_MEMBERS); } +bool ETSChecker::HasETSFunctionType(ir::TypeNode *type_annotation) +{ + if (type_annotation->IsETSFunctionType()) { + return true; + } + std::unordered_set children_set; + + if (type_annotation->IsETSTypeReference()) { + auto *type_decl = + type_annotation->AsETSTypeReference()->Part()->Name()->AsIdentifier()->Variable()->Declaration(); + if (type_decl != nullptr && type_decl->IsTypeAliasDecl()) { + type_annotation = type_decl->Node()->AsTSTypeAliasDeclaration()->TypeAnnotation(); + if (type_annotation->IsETSUnionType()) { + for (auto *type : type_annotation->AsETSUnionType()->Types()) { + if (type->IsETSTypeReference()) { + children_set.insert(type); + } + } + } else { + children_set.insert(type_annotation); + } + } + + for (auto *child : children_set) { + if (HasETSFunctionType(child)) { + return true; + } + } + } + + return false; +} + std::vector ETSChecker::CollectAbstractSignaturesFromObject(const ETSObjectType *obj_type) { std::vector abstracts; @@ -1481,22 +1532,25 @@ Type *ETSChecker::FindLeastUpperBound(Type *source, Type *target) Type *ETSChecker::GetApparentType(Type *type) { - if (type->IsETSTypeParameter()) { - auto *const param = type->AsETSTypeParameter(); - return param->HasConstraint() ? param->GetConstraintType() : param; + while (type->IsETSTypeParameter()) { + type = type->AsETSTypeParameter()->GetConstraintType(); } return type; } Type const *ETSChecker::GetApparentType(Type const *type) { - if (type->IsETSTypeParameter()) { - auto *const param = type->AsETSTypeParameter(); - return param->HasConstraint() ? param->GetConstraintType() : param; + while (type->IsETSTypeParameter()) { + type = type->AsETSTypeParameter()->GetConstraintType(); } return type; } +Type *ETSChecker::MaybePromotedBuiltinType(Type *type) const +{ + return type->HasTypeFlag(TypeFlag::ETS_PRIMITIVE) ? checker::BoxingConverter::ETSTypeFromSource(this, type) : type; +} + Type *ETSChecker::GetCommonClass(Type *source, Type *target) { SavedTypeRelationFlagsContext checker_ctx(this->Relation(), TypeRelationFlag::IGNORE_TYPE_PARAMETERS); @@ -1505,13 +1559,11 @@ Type *ETSChecker::GetCommonClass(Type *source, Type *target) return source; } - target->IsSupertypeOf(Relation(), source); - if (Relation()->IsTrue()) { + if (Relation()->IsSupertypeOf(target, source)) { return target; } - source->IsSupertypeOf(Relation(), target); - if (Relation()->IsTrue()) { + if (Relation()->IsSupertypeOf(source, target)) { return source; } @@ -1544,8 +1596,7 @@ ETSObjectType *ETSChecker::GetClosestCommonAncestor(ETSObjectType *source, ETSOb auto *source_base = GetOriginalBaseType(source); auto *source_type = source_base == nullptr ? source : source_base; - target_type->IsSupertypeOf(Relation(), source_type); - if (Relation()->IsTrue()) { + if (Relation()->IsSupertypeOf(target_type, source_type)) { // NOTE: TorokG. Extending the search to find intersection types return target_type; } diff --git a/ets2panda/checker/ets/typeCreation.cpp b/ets2panda/checker/ets/typeCreation.cpp index 243fd358958ecfb1f637f142828b32d574ff8354..f673d9c562a953b95925cbaf2e853a87028f5840 100644 --- a/ets2panda/checker/ets/typeCreation.cpp +++ b/ets2panda/checker/ets/typeCreation.cpp @@ -13,6 +13,7 @@ * limitations under the License. */ +#include #include "checker/ETSchecker.h" #include "checker/ets/boxingConverter.h" #include "checker/types/ets/byteType.h" @@ -34,6 +35,7 @@ #include "varbinder/ETSBinder.h" #include "parser/program/program.h" #include "util/helpers.h" +#include "checker/types/ts/bigintType.h" namespace panda::es2panda::checker { ByteType *ETSChecker::CreateByteType(int8_t value) @@ -102,6 +104,11 @@ CharType *ETSChecker::CreateCharType(char16_t value) return Allocator()->New(value); } +ETSBigIntType *ETSChecker::CreateETSBigIntLiteralType(util::StringView value) +{ + return Allocator()->New(Allocator(), GlobalBuiltinETSBigIntType(), value); +} + ETSStringType *ETSChecker::CreateETSStringLiteralType(util::StringView value) { return Allocator()->New(Allocator(), GlobalBuiltinETSStringType(), value); @@ -206,9 +213,126 @@ ETSExtensionFuncHelperType *ETSChecker::CreateETSExtensionFuncHelperType(ETSFunc return Allocator()->New(class_method_type, extension_function_type); } +std::map &GetNameToTypeIdMap() +{ + static std::map name_to_type_id = { + {compiler::Signatures::BUILTIN_BIGINT_CLASS, GlobalTypeId::ETS_BIG_INT_BUILTIN}, + {compiler::Signatures::BUILTIN_STRING_CLASS, GlobalTypeId::ETS_STRING_BUILTIN}, + {compiler::Signatures::BUILTIN_OBJECT_CLASS, GlobalTypeId::ETS_OBJECT_BUILTIN}, + {compiler::Signatures::BUILTIN_EXCEPTION_CLASS, GlobalTypeId::ETS_EXCEPTION_BUILTIN}, + {compiler::Signatures::BUILTIN_ERROR_CLASS, GlobalTypeId::ETS_ERROR_BUILTIN}, + {compiler::Signatures::BUILTIN_TYPE_CLASS, GlobalTypeId::ETS_TYPE_BUILTIN}, + {compiler::Signatures::BUILTIN_PROMISE_CLASS, GlobalTypeId::ETS_PROMISE_BUILTIN}, + {compiler::Signatures::BUILTIN_BOX_CLASS, GlobalTypeId::ETS_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_BOOLEAN_BOX_CLASS, GlobalTypeId::ETS_BOOLEAN_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_BYTE_BOX_CLASS, GlobalTypeId::ETS_BYTE_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_CHAR_BOX_CLASS, GlobalTypeId::ETS_CHAR_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_SHORT_BOX_CLASS, GlobalTypeId::ETS_SHORT_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_INT_BOX_CLASS, GlobalTypeId::ETS_INT_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_LONG_BOX_CLASS, GlobalTypeId::ETS_LONG_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_FLOAT_BOX_CLASS, GlobalTypeId::ETS_FLOAT_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_DOUBLE_BOX_CLASS, GlobalTypeId::ETS_DOUBLE_BOX_BUILTIN}, + {compiler::Signatures::BUILTIN_VOID_CLASS, GlobalTypeId::ETS_VOID_BUILTIN}, + }; + + return name_to_type_id; +} + +std::map> &GetNameToGlobalTypeMap() +{ + static std::map> name_to_global_type = { + {compiler::Signatures::BUILTIN_BIGINT_CLASS, &ETSChecker::GlobalBuiltinETSBigIntType}, + {compiler::Signatures::BUILTIN_STRING_CLASS, &ETSChecker::GlobalBuiltinETSStringType}, + {compiler::Signatures::BUILTIN_OBJECT_CLASS, &ETSChecker::GlobalETSObjectType}, + {compiler::Signatures::BUILTIN_EXCEPTION_CLASS, &ETSChecker::GlobalBuiltinExceptionType}, + {compiler::Signatures::BUILTIN_ERROR_CLASS, &ETSChecker::GlobalBuiltinErrorType}, + {compiler::Signatures::BUILTIN_TYPE_CLASS, &ETSChecker::GlobalBuiltinTypeType}, + {compiler::Signatures::BUILTIN_PROMISE_CLASS, &ETSChecker::GlobalBuiltinPromiseType}, + {compiler::Signatures::BUILTIN_VOID_CLASS, &ETSChecker::GlobalBuiltinVoidType}, + }; + + return name_to_global_type; +} + +std::map> &GetNameToGlobalBoxTypeMap() +{ + static std::map> name_to_global_box_type = { + {compiler::Signatures::BUILTIN_BOX_CLASS, &ETSChecker::GlobalETSObjectType}, + {compiler::Signatures::BUILTIN_BOOLEAN_BOX_CLASS, &ETSChecker::GlobalETSBooleanType}, + {compiler::Signatures::BUILTIN_BYTE_BOX_CLASS, &ETSChecker::GlobalByteType}, + {compiler::Signatures::BUILTIN_CHAR_BOX_CLASS, &ETSChecker::GlobalCharType}, + {compiler::Signatures::BUILTIN_SHORT_BOX_CLASS, &ETSChecker::GlobalShortType}, + {compiler::Signatures::BUILTIN_INT_BOX_CLASS, &ETSChecker::GlobalIntType}, + {compiler::Signatures::BUILTIN_LONG_BOX_CLASS, &ETSChecker::GlobalLongType}, + {compiler::Signatures::BUILTIN_FLOAT_BOX_CLASS, &ETSChecker::GlobalFloatType}, + {compiler::Signatures::BUILTIN_DOUBLE_BOX_CLASS, &ETSChecker::GlobalDoubleType}, + }; + + return name_to_global_box_type; +} + +ETSObjectType *ETSChecker::UpdateBoxedGlobalType(ETSObjectType *obj_type, util::StringView name) +{ + auto name_to_global_box_type = GetNameToGlobalBoxTypeMap(); + auto name_to_type_id = GetNameToTypeIdMap(); + + if (name_to_global_box_type.find(name) != name_to_global_box_type.end()) { + std::function global_type = name_to_global_box_type[name]; + if (GlobalBuiltinBoxType(global_type(this)) != nullptr) { + return GlobalBuiltinBoxType(global_type(this)); + } + + auto id = name_to_type_id.find(name); + if (id != name_to_type_id.end()) { + GetGlobalTypesHolder()->GlobalTypes()[static_cast(id->second)] = obj_type; + } + } + + return obj_type; +} + +ETSObjectType *ETSChecker::UpdateGlobalType(ETSObjectType *obj_type, util::StringView name) +{ + auto name_to_global_type = GetNameToGlobalTypeMap(); + auto name_to_type_id = GetNameToTypeIdMap(); + + if (name_to_global_type.find(name) != name_to_global_type.end()) { + std::function global_type = name_to_global_type[name]; + if (global_type(this) != nullptr) { + return global_type(this); + } + + auto id = name_to_type_id.find(name); + if (id != name_to_type_id.end()) { + GetGlobalTypesHolder()->GlobalTypes()[static_cast(id->second)] = obj_type; + } + + if (name == compiler::Signatures::BUILTIN_OBJECT_CLASS) { + auto *nullish = CreateNullishType(obj_type, checker::TypeFlag::NULLISH, Allocator(), Relation(), + GetGlobalTypesHolder()); + GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_NULLISH_OBJECT)] = nullish; + } + } + + return obj_type; +} + ETSObjectType *ETSChecker::CreateETSObjectTypeCheckBuiltins(util::StringView name, ir::AstNode *decl_node, ETSObjectFlags flags) { + if (name == compiler::Signatures::BUILTIN_BIGINT_CLASS) { + if (GlobalBuiltinETSBigIntType() != nullptr) { + return GlobalBuiltinETSBigIntType(); + } + + GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_BIG_INT_BUILTIN)] = + CreateNewETSObjectType(name, decl_node, flags | ETSObjectFlags::BUILTIN_BIGINT); + GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_BIG_INT)] = + Allocator()->New(Allocator(), GlobalBuiltinETSBigIntType()); + + return GlobalBuiltinETSBigIntType(); + } + if (name == compiler::Signatures::BUILTIN_STRING_CLASS) { if (GlobalBuiltinETSStringType() != nullptr) { return GlobalBuiltinETSStringType(); @@ -222,93 +346,12 @@ ETSObjectType *ETSChecker::CreateETSObjectTypeCheckBuiltins(util::StringView nam } auto *obj_type = CreateNewETSObjectType(name, decl_node, flags); - - if (name == compiler::Signatures::BUILTIN_OBJECT_CLASS) { - if (GlobalETSObjectType() != nullptr) { - return GlobalETSObjectType(); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_OBJECT_BUILTIN)] = obj_type; - auto *nullish = - CreateNullishType(obj_type, checker::TypeFlag::NULLISH, Allocator(), Relation(), GetGlobalTypesHolder()); - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_NULLISH_OBJECT)] = nullish; - } else if (name == compiler::Signatures::BUILTIN_EXCEPTION_CLASS) { - if (GlobalBuiltinExceptionType() != nullptr) { - return GlobalBuiltinExceptionType(); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_EXCEPTION_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_ERROR_CLASS) { - if (GlobalBuiltinErrorType() != nullptr) { - return GlobalBuiltinErrorType(); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_ERROR_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_TYPE_CLASS) { - if (GlobalBuiltinTypeType() != nullptr) { - return GlobalBuiltinTypeType(); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_TYPE_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_PROMISE_CLASS) { - if (GlobalBuiltinPromiseType() != nullptr) { - return GlobalBuiltinPromiseType(); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_PROMISE_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalETSObjectType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalETSObjectType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_BOOLEAN_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalETSBooleanType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalETSBooleanType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_BOOLEAN_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_BYTE_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalByteType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalByteType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_BYTE_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_CHAR_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalCharType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalCharType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_CHAR_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_SHORT_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalShortType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalShortType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_SHORT_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_INT_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalIntType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalIntType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_INT_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_LONG_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalLongType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalLongType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_LONG_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_FLOAT_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalFloatType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalFloatType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_FLOAT_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_FLOAT_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalFloatType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalFloatType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_FLOAT_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_DOUBLE_BOX_CLASS) { - if (GlobalBuiltinBoxType(GlobalDoubleType()) != nullptr) { - return GlobalBuiltinBoxType(GlobalDoubleType()); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_DOUBLE_BOX_BUILTIN)] = obj_type; - } else if (name == compiler::Signatures::BUILTIN_VOID_CLASS) { - if (GlobalBuiltinVoidType() != nullptr) { - return GlobalBuiltinVoidType(); - } - GetGlobalTypesHolder()->GlobalTypes()[static_cast(GlobalTypeId::ETS_VOID_BUILTIN)] = obj_type; + auto name_to_global_box_type = GetNameToGlobalBoxTypeMap(); + if (name_to_global_box_type.find(name) != name_to_global_box_type.end()) { + return UpdateBoxedGlobalType(obj_type, name); } - return obj_type; + return UpdateGlobalType(obj_type, name); } ETSObjectType *ETSChecker::CreateETSObjectType(util::StringView name, ir::AstNode *decl_node, ETSObjectFlags flags) diff --git a/ets2panda/checker/ets/typeRelationContext.cpp b/ets2panda/checker/ets/typeRelationContext.cpp index cbc061f0b9a54cacb5d3f3b0a0221e7b59c411b5..04139740239a859d8384539b91d295a89e84ac9c 100644 --- a/ets2panda/checker/ets/typeRelationContext.cpp +++ b/ets2panda/checker/ets/typeRelationContext.cpp @@ -14,6 +14,7 @@ */ #include "typeRelationContext.h" +#include "boxingConverter.h" #include "varbinder/scope.h" #include "varbinder/variable.h" #include "varbinder/declaration.h" @@ -61,12 +62,15 @@ bool InstantiationContext::ValidateTypeArguments(ETSObjectType *type, ir::TSType extends "Comparable", we will get an error here. */ - auto const get_types = [this, &type_args, type](size_t idx) -> std::pair { + auto const is_defaulted = [type_args](size_t idx) { + return type_args == nullptr || idx >= type_args->Params().size(); + }; + + auto const get_types = [this, &type_args, type, is_defaulted](size_t idx) -> std::pair { auto *type_param = type->TypeArguments().at(idx)->AsETSTypeParameter(); - if (type_args != nullptr && idx < type_args->Params().size()) { - return {type_param, type_args->Params().at(idx)->GetType(checker_)}; - } - return {type_param, type_param->GetDefaultType()}; + return {type_param, is_defaulted(idx) + ? type_param->GetDefaultType() + : checker_->MaybePromotedBuiltinType(type_args->Params().at(idx)->GetType(checker_))}; }; auto *const substitution = checker_->NewSubstitution(); @@ -88,7 +92,7 @@ bool InstantiationContext::ValidateTypeArguments(ETSObjectType *type, ir::TSType if (!ValidateTypeArg(constraint, type_arg) && type_args != nullptr && !checker_->Relation()->NoThrowGenericTypeAlias()) { checker_->ThrowTypeError({"Type '", type_arg, "' is not assignable to constraint type '", constraint, "'."}, - type_args->Params().at(idx)->Start()); + is_defaulted(idx) ? pos : type_args->Params().at(idx)->Start()); } } @@ -97,16 +101,10 @@ bool InstantiationContext::ValidateTypeArguments(ETSObjectType *type, ir::TSType bool InstantiationContext::ValidateTypeArg(Type *constraint_type, Type *type_arg) { - if (!ETSChecker::IsReferenceType(type_arg)) { - return false; - } - - if (type_arg->IsETSUnionType()) { - auto const &constituent_types = type_arg->AsETSUnionType()->ConstituentTypes(); - return std::all_of(constituent_types.begin(), constituent_types.end(), - [this, constraint_type](Type *c_type) { return ValidateTypeArg(constraint_type, c_type); }); + // NOTE: #14993 enforce ETSChecker::IsReferenceType + if (type_arg->IsWildcardType()) { + return true; } - return checker_->Relation()->IsAssignableTo(type_arg, constraint_type); } diff --git a/ets2panda/checker/ets/typeRelationContext.h b/ets2panda/checker/ets/typeRelationContext.h index d0148f37d9f0ab27bf8628c5c8485e69ee83f51e..ca9ebda4a736a29b807952c0fd795713a3f2b16f 100644 --- a/ets2panda/checker/ets/typeRelationContext.h +++ b/ets2panda/checker/ets/typeRelationContext.h @@ -69,7 +69,7 @@ public: relation->SetNode(nullptr); relation->SetFlags(TypeRelationFlag::NONE); - assignable_ = true; + assignable_ = relation->IsTrue(); } bool IsAssignable() const diff --git a/ets2panda/checker/types/ets/etsBigIntType.cpp b/ets2panda/checker/types/ets/etsBigIntType.cpp new file mode 100644 index 0000000000000000000000000000000000000000..883554170c3d8e21af39888af15a8de0368b2ec9 --- /dev/null +++ b/ets2panda/checker/types/ets/etsBigIntType.cpp @@ -0,0 +1,44 @@ +/** + * Copyright (c) 2021-2023 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. + */ + +#include "etsBigIntType.h" + +namespace panda::es2panda::checker { +void ETSBigIntType::Identical(TypeRelation *relation, Type *other) +{ + if (other->IsETSBigIntType()) { + relation->Result(true); + return; + } + + relation->Result(false); +} + +void ETSBigIntType::AssignmentTarget([[maybe_unused]] TypeRelation *relation, [[maybe_unused]] Type *source) +{ + if (source->IsETSBigIntType()) { + relation->Result(true); + return; + } + + relation->Result(false); +} + +Type *ETSBigIntType::Instantiate([[maybe_unused]] ArenaAllocator *allocator, [[maybe_unused]] TypeRelation *relation, + [[maybe_unused]] GlobalTypesHolder *global_types) +{ + return this; +} +} // namespace panda::es2panda::checker diff --git a/ets2panda/checker/types/ets/etsBigIntType.h b/ets2panda/checker/types/ets/etsBigIntType.h new file mode 100644 index 0000000000000000000000000000000000000000..5703107e899a48b7dfb155d200817c21ece45956 --- /dev/null +++ b/ets2panda/checker/types/ets/etsBigIntType.h @@ -0,0 +1,66 @@ +/** + * Copyright (c) 2021-2023 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. + */ + +#ifndef ES2PANDA_COMPILER_CHECKER_TYPES_ETS_BIGINT_TYPE_H +#define ES2PANDA_COMPILER_CHECKER_TYPES_ETS_BIGINT_TYPE_H + +#include "checker/types/ets/etsObjectType.h" + +namespace panda::es2panda::checker { +class ETSBigIntType : public ETSObjectType { +public: + explicit ETSBigIntType(ArenaAllocator *allocator, [[maybe_unused]] ETSObjectType *super) + : ETSObjectType(allocator, + ETSObjectFlags::CLASS | ETSObjectFlags::BUILTIN_BIGINT | ETSObjectFlags::RESOLVED_SUPER) + { + SetSuperType(super); + } + + explicit ETSBigIntType(ArenaAllocator *allocator, ETSObjectType *super, util::StringView value) + : ETSObjectType(allocator, + ETSObjectFlags::CLASS | ETSObjectFlags::BUILTIN_BIGINT | ETSObjectFlags::RESOLVED_SUPER), + value_(value) + { + SetSuperType(super); + AddTypeFlag(TypeFlag::CONSTANT); + AddTypeFlag(TypeFlag::BIGINT_LITERAL); + variable_ = super->Variable(); + } + + void Identical(TypeRelation *relation, Type *other) override; + void AssignmentTarget(TypeRelation *relation, Type *source) override; + Type *Instantiate(ArenaAllocator *allocator, TypeRelation *relation, GlobalTypesHolder *global_types) override; + + void ToString(std::stringstream &ss) const override + { + ss << lexer::TokenToString(lexer::TokenType::KEYW_BIGINT); + } + + void ToAssemblerType([[maybe_unused]] std::stringstream &ss) const override + { + ss << compiler::Signatures::BUILTIN_BIGINT; + } + + util::StringView GetValue() const + { + return value_; + } + +private: + util::StringView value_ {}; +}; +} // namespace panda::es2panda::checker + +#endif diff --git a/ets2panda/checker/types/ets/etsObjectType.cpp b/ets2panda/checker/types/ets/etsObjectType.cpp index 3964d454fab1836252c86262b5392ad60a8bea69..45d0171b1971647d8cee42aedb19f3c507435746 100644 --- a/ets2panda/checker/types/ets/etsObjectType.cpp +++ b/ets2panda/checker/types/ets/etsObjectType.cpp @@ -436,7 +436,7 @@ void ETSObjectType::AssignmentTarget(TypeRelation *const relation, Type *source) return; } - IsSupertypeOf(relation, source); + relation->IsSupertypeOf(this, source); } bool ETSObjectType::CastWideningNarrowing(TypeRelation *const relation, Type *const target, TypeFlag unbox_flags, @@ -609,6 +609,17 @@ void ETSObjectType::IsSupertypeOf(TypeRelation *relation, Type *source) relation->Result(false); auto *const ets_checker = relation->GetChecker()->AsETSChecker(); + if (source->IsETSUnionType()) { + bool res = std::all_of(source->AsETSUnionType()->ConstituentTypes().begin(), + source->AsETSUnionType()->ConstituentTypes().end(), [this, relation](Type *ct) { + relation->Result(false); + IsSupertypeOf(relation, ct); + return relation->IsTrue(); + }); + relation->Result(res); + return; + } + // 3.8.3 Subtyping among Array Types auto const *const base = GetConstOriginalBaseType(); if (base == ets_checker->GlobalETSObjectType() && source->IsETSArrayType()) { @@ -616,11 +627,6 @@ void ETSObjectType::IsSupertypeOf(TypeRelation *relation, Type *source) return; } - if (source->IsETSTypeParameter()) { - source->AsETSTypeParameter()->ConstraintIsSubtypeOf(relation, this); - return; - } - if (!source->IsETSObjectType() || !source->AsETSObjectType()->HasObjectFlag(ETSObjectFlags::CLASS | ETSObjectFlags::INTERFACE | ETSObjectFlags::NULL_TYPE)) { @@ -631,7 +637,7 @@ void ETSObjectType::IsSupertypeOf(TypeRelation *relation, Type *source) return; } // All classes and interfaces are subtypes of Object - if (base == ets_checker->GlobalETSObjectType()) { + if (base == ets_checker->GlobalETSObjectType() || base == ets_checker->GlobalETSNullishObjectType()) { relation->Result(true); return; } @@ -643,16 +649,14 @@ void ETSObjectType::IsSupertypeOf(TypeRelation *relation, Type *source) ETSObjectType *source_obj = source->AsETSObjectType(); if (auto *source_super = source_obj->SuperType(); source_super != nullptr) { - IsSupertypeOf(relation, source_super); - if (relation->IsTrue()) { + if (relation->IsSupertypeOf(this, source_super)) { return; } } if (HasObjectFlag(ETSObjectFlags::INTERFACE)) { for (auto *itf : source_obj->Interfaces()) { - IsSupertypeOf(relation, itf); - if (relation->IsTrue()) { + if (relation->IsSupertypeOf(this, itf)) { return; } } diff --git a/ets2panda/checker/types/ets/etsObjectType.h b/ets2panda/checker/types/ets/etsObjectType.h index b978b6b48a7793ad45113ea33b221f06af15d055..ce2fbc5ffdf98145eaaa72d7c8e0a61f9fdb0f45 100644 --- a/ets2panda/checker/types/ets/etsObjectType.h +++ b/ets2panda/checker/types/ets/etsObjectType.h @@ -48,6 +48,7 @@ enum class ETSObjectFlags : uint32_t { CHECKED_INVOKE_LEGITIMACY = 1U << 18U, UNDEFINED_TYPE = 1U << 19U, + BUILTIN_BIGINT = 1U << 22U, BUILTIN_STRING = 1U << 23U, BUILTIN_BOOLEAN = 1U << 24U, BUILTIN_BYTE = 1U << 25U, @@ -60,7 +61,7 @@ enum class ETSObjectFlags : uint32_t { UNBOXABLE_TYPE = BUILTIN_BOOLEAN | BUILTIN_BYTE | BUILTIN_CHAR | BUILTIN_SHORT | BUILTIN_INT | BUILTIN_LONG | BUILTIN_FLOAT | BUILTIN_DOUBLE, - BUILTIN_TYPE = BUILTIN_STRING | UNBOXABLE_TYPE, + BUILTIN_TYPE = BUILTIN_STRING | BUILTIN_BIGINT | UNBOXABLE_TYPE, VALID_SWITCH_TYPE = BUILTIN_BYTE | BUILTIN_CHAR | BUILTIN_SHORT | BUILTIN_INT | BUILTIN_LONG | BUILTIN_STRING | ENUM, GLOBAL_CLASS = CLASS | GLOBAL, diff --git a/ets2panda/checker/types/ets/etsTypeParameter.cpp b/ets2panda/checker/types/ets/etsTypeParameter.cpp index d19a6ef1162b28ee9fc728d3aad613230c6d612d..f3ea0c6799480959999e96dd74bccb24108cf8dd 100644 --- a/ets2panda/checker/types/ets/etsTypeParameter.cpp +++ b/ets2panda/checker/types/ets/etsTypeParameter.cpp @@ -70,14 +70,13 @@ void ETSTypeParameter::AssignmentTarget([[maybe_unused]] TypeRelation *relation, return; } - IsSupertypeOf(relation, source); + relation->IsSupertypeOf(this, source); } void ETSTypeParameter::Cast(TypeRelation *relation, Type *target) { - if (target->IsSupertypeOf(relation, this), relation->IsTrue()) { + if (relation->IsSupertypeOf(target, this)) { relation->RemoveFlags(TypeRelationFlag::UNCHECKED_CAST); - relation->Result(true); return; } @@ -90,9 +89,8 @@ void ETSTypeParameter::Cast(TypeRelation *relation, Type *target) void ETSTypeParameter::CastTarget(TypeRelation *relation, Type *source) { - if (IsSupertypeOf(relation, source), relation->IsTrue()) { + if (relation->IsSupertypeOf(this, source)) { relation->RemoveFlags(TypeRelationFlag::UNCHECKED_CAST); - relation->Result(true); return; } @@ -101,12 +99,12 @@ void ETSTypeParameter::CastTarget(TypeRelation *relation, Type *source) void ETSTypeParameter::IsSupertypeOf([[maybe_unused]] TypeRelation *relation, [[maybe_unused]] Type *source) { - if (Identical(relation, source), relation->IsTrue()) { - return; - } + relation->Result(false); +} - if (source->IsETSTypeParameter()) { - source->AsETSTypeParameter()->ConstraintIsSubtypeOf(relation, this); +void ETSTypeParameter::IsSubtypeOf([[maybe_unused]] TypeRelation *relation, [[maybe_unused]] Type *target) +{ + if (relation->IsSupertypeOf(target, GetConstraintType())) { return; } @@ -157,27 +155,14 @@ Type *ETSTypeParameter::Substitute(TypeRelation *relation, const Substitution *s return this; } -Type *ETSTypeParameter::EffectiveConstraint(ETSChecker const *checker) const -{ - return HasConstraint() ? GetConstraintType() : checker->GlobalETSNullishObjectType(); -} - void ETSTypeParameter::ToAssemblerType(std::stringstream &ss) const { - if (HasConstraint()) { - GetConstraintType()->ToAssemblerType(ss); - } else { - ss << compiler::Signatures::BUILTIN_OBJECT; - } + GetConstraintType()->ToAssemblerType(ss); } void ETSTypeParameter::ToDebugInfoType(std::stringstream &ss) const { - if (HasConstraint()) { - GetConstraintType()->ToDebugInfoType(ss); - } else { - ETSObjectType::DebugInfoTypeFromName(ss, compiler::Signatures::BUILTIN_OBJECT); - } + GetConstraintType()->ToDebugInfoType(ss); } ETSTypeParameter *ETSTypeParameter::GetOriginal() const diff --git a/ets2panda/checker/types/ets/etsTypeParameter.h b/ets2panda/checker/types/ets/etsTypeParameter.h index d39645a555dfe14069f16b32f5030132dc098b0f..79657fa0b68d5adb86cf0cc03bd66e48bbb43e07 100644 --- a/ets2panda/checker/types/ets/etsTypeParameter.h +++ b/ets2panda/checker/types/ets/etsTypeParameter.h @@ -57,16 +57,10 @@ public: Type *GetConstraintType() const { + ASSERT(constraint_ != nullptr); return constraint_; } - bool HasConstraint() const - { - return GetConstraintType() != nullptr; - } - - Type *EffectiveConstraint(ETSChecker const *checker) const; - void ToString(std::stringstream &ss) const override; void Identical(TypeRelation *relation, Type *other) override; void AssignmentTarget(TypeRelation *relation, Type *source) override; @@ -74,19 +68,10 @@ public: void Cast(TypeRelation *relation, Type *target) override; void CastTarget(TypeRelation *relation, Type *source) override; void IsSupertypeOf(TypeRelation *relation, Type *source) override; + void IsSubtypeOf(TypeRelation *relation, Type *target) override; Type *Instantiate(ArenaAllocator *allocator, TypeRelation *relation, GlobalTypesHolder *global_types) override; Type *Substitute(TypeRelation *relation, const Substitution *substitution) override; - bool ConstraintIsSubtypeOf(TypeRelation *relation, Type *target) - { - if (HasConstraint()) { - target->IsSupertypeOf(relation, GetConstraintType()); - } else { - relation->Result(false); - } - return relation->IsTrue(); - } - void ToAssemblerType(std::stringstream &ss) const override; void ToDebugInfoType(std::stringstream &ss) const override; diff --git a/ets2panda/checker/types/ets/etsUnionType.cpp b/ets2panda/checker/types/ets/etsUnionType.cpp index 18d2fcbde0ba9cf8f44e3bc792424b230b417367..98653a97328cae1341625f6c693e650eba02ff7f 100644 --- a/ets2panda/checker/types/ets/etsUnionType.cpp +++ b/ets2panda/checker/types/ets/etsUnionType.cpp @@ -161,12 +161,24 @@ void ETSUnionType::LinearizeAndEraseIdentical(TypeRelation *relation, ArenaVecto } } constituent_types = copied_constituents; + // Removing subtypes should be in the next iteration, especially needed for proper literals removal + auto check_subtyping = [relation](Type *lhs, Type *rhs) { + if (lhs == rhs) { + return false; + } + relation->Result(false); + lhs->IsSupertypeOf(relation, rhs); + bool inheritance_relation = relation->IsTrue(); + rhs->IsSupertypeOf(relation, lhs); + inheritance_relation = inheritance_relation || relation->IsTrue(); + return inheritance_relation; + }; // Secondly, remove identical types auto cmp_it = constituent_types.begin(); while (cmp_it != constituent_types.end()) { auto it = std::next(cmp_it); while (it != constituent_types.end()) { - if (relation->IsIdenticalTo(*it, *cmp_it)) { + if (relation->IsIdenticalTo(*it, *cmp_it) && !check_subtyping(*it, *cmp_it)) { it = constituent_types.erase(it); } else { ++it; @@ -196,9 +208,9 @@ void ETSUnionType::NormalizeTypes(TypeRelation *relation, ArenaVector &c while (cmp_it != constituent_types.end()) { auto new_end = std::remove_if( constituent_types.begin(), constituent_types.end(), [relation, checker, cmp_it, number_found](Type *ct) { - relation->Result(false); - (*cmp_it)->IsSupertypeOf(relation, ct); - bool remove_subtype = ct != *cmp_it && relation->IsTrue(); + bool both_constants = (*cmp_it)->HasTypeFlag(TypeFlag::CONSTANT) && ct->HasTypeFlag(TypeFlag::CONSTANT); + relation->IsSupertypeOf((*cmp_it), ct); + bool remove_subtype = ct != *cmp_it && !both_constants && relation->IsTrue(); bool remove_numeric = number_found && ct->IsETSObjectType() && ct->AsETSObjectType()->HasObjectFlag(ETSObjectFlags::UNBOXABLE_TYPE) && !ct->AsETSObjectType()->HasObjectFlag(ETSObjectFlags::BUILTIN_DOUBLE) && @@ -285,27 +297,20 @@ void ETSUnionType::Cast(TypeRelation *relation, Type *target) void ETSUnionType::IsSupertypeOf(TypeRelation *relation, Type *source) { - relation->Result(false); - - if (source->IsETSUnionType()) { - for (auto const &source_ctype : source->AsETSUnionType()->ConstituentTypes()) { - if (IsSupertypeOf(relation, source_ctype), !relation->IsTrue()) { - return; - } + for (auto const &ctype : ConstituentTypes()) { + if (relation->IsSupertypeOf(ctype, source)) { + return; } - return; } +} +void ETSUnionType::IsSubtypeOf(TypeRelation *relation, Type *target) +{ for (auto const &ctype : ConstituentTypes()) { - if (ctype->IsSupertypeOf(relation, source), relation->IsTrue()) { + if (!relation->IsSupertypeOf(target, ctype)) { return; } } - - if (source->IsETSTypeParameter()) { - source->AsETSTypeParameter()->ConstraintIsSubtypeOf(relation, this); - return; - } } void ETSUnionType::CastTarget(TypeRelation *relation, Type *source) diff --git a/ets2panda/checker/types/ets/etsUnionType.h b/ets2panda/checker/types/ets/etsUnionType.h index 39dc90ec1f4f6df012d752577675c16c5dbf8fd2..2c6da2652c58e5b81af2172abaf65f6ae4e5836d 100644 --- a/ets2panda/checker/types/ets/etsUnionType.h +++ b/ets2panda/checker/types/ets/etsUnionType.h @@ -43,6 +43,7 @@ public: void Cast(TypeRelation *relation, Type *target) override; void CastTarget(TypeRelation *relation, Type *source) override; void IsSupertypeOf(TypeRelation *relation, Type *source) override; + void IsSubtypeOf(TypeRelation *relation, Type *target) override; Type *FindTypeIsCastableToThis(ir::Expression *node, TypeRelation *relation, Type *source) const; Type *FindTypeIsCastableToSomeType(ir::Expression *node, TypeRelation *relation, Type *target) const; Type *FindUnboxableType() const; diff --git a/ets2panda/checker/types/ets/types.h b/ets2panda/checker/types/ets/types.h index 1f798ee532f0073398218b8c14b9eb951315b8fc..ceb2e87ade93af2b767661af558191fb1f727512 100644 --- a/ets2panda/checker/types/ets/types.h +++ b/ets2panda/checker/types/ets/types.h @@ -30,6 +30,7 @@ #include "etsUnionType.h" #include "etsVoidType.h" #include "etsStringType.h" +#include "etsBigIntType.h" #include "etsObjectType.h" #include "etsDynamicType.h" #include "etsArrayType.h" diff --git a/ets2panda/checker/types/globalTypesHolder.cpp b/ets2panda/checker/types/globalTypesHolder.cpp index 5c6eb9a07bda67acea569de3d9e42d559e285f07..6fcac6fa77a68e5d0ac49c84b52277129286d303 100644 --- a/ets2panda/checker/types/globalTypesHolder.cpp +++ b/ets2panda/checker/types/globalTypesHolder.cpp @@ -42,6 +42,7 @@ #include "checker/types/ets/shortType.h" #include "checker/types/ets/etsBooleanType.h" #include "checker/types/ets/etsStringType.h" +#include "checker/types/ets/etsBigIntType.h" #include "checker/types/ets/etsVoidType.h" #include "checker/types/ets/etsObjectType.h" #include "checker/types/ets/wildcardType.h" @@ -126,6 +127,7 @@ GlobalTypesHolder::GlobalTypesHolder(ArenaAllocator *allocator) : builtin_name_m builtin_name_mappings_.emplace("ClassNotFoundException", GlobalTypeId::ETS_CLASS_NOT_FOUND_EXCEPTION_BUILTIN); builtin_name_mappings_.emplace("ClassCastException", GlobalTypeId::ETS_CLASS_CAST_EXCEPTION_BUILTIN); builtin_name_mappings_.emplace("String", GlobalTypeId::ETS_STRING_BUILTIN); + builtin_name_mappings_.emplace("BigInt", GlobalTypeId::ETS_BIG_INT_BUILTIN); builtin_name_mappings_.emplace("StringBuilder", GlobalTypeId::ETS_STRING_BUILDER_BUILTIN); builtin_name_mappings_.emplace("Type", GlobalTypeId::ETS_TYPE_BUILTIN); builtin_name_mappings_.emplace("Types", GlobalTypeId::ETS_TYPES_BUILTIN); @@ -511,6 +513,16 @@ Type *GlobalTypesHolder::GlobalETSStringBuiltinType() return global_types_.at(static_cast(GlobalTypeId::ETS_STRING_BUILTIN)); } +Type *GlobalTypesHolder::GlobalETSBigIntBuiltinType() +{ + return global_types_.at(static_cast(GlobalTypeId::ETS_BIG_INT_BUILTIN)); +} + +Type *GlobalTypesHolder::GlobalETSBigIntLiteralType() +{ + return global_types_.at(static_cast(GlobalTypeId::ETS_BIG_INT)); +} + Type *GlobalTypesHolder::GlobalStringBuilderBuiltinType() { return global_types_.at(static_cast(GlobalTypeId::ETS_STRING_BUILDER_BUILTIN)); diff --git a/ets2panda/checker/types/globalTypesHolder.h b/ets2panda/checker/types/globalTypesHolder.h index e0e370b4599bf17a0dd767f591e32da91d7d1b7a..8808a17352a19a9ce774a68f46443f9884c18d7f 100644 --- a/ets2panda/checker/types/globalTypesHolder.h +++ b/ets2panda/checker/types/globalTypesHolder.h @@ -109,6 +109,8 @@ enum class GlobalTypeId { ETS_FLOAT_BOX_BUILTIN, ETS_DOUBLE_BOX_BUILTIN, ETS_NEVER_BUILTIN, + ETS_BIG_INT_BUILTIN, + ETS_BIG_INT, COUNT, }; @@ -185,6 +187,8 @@ public: Type *GlobalClassNotFoundExceptionBuiltinType(); [[nodiscard]] Type *GlobalClassCastExceptionBuiltinType() const noexcept; Type *GlobalETSStringBuiltinType(); + Type *GlobalETSBigIntBuiltinType(); + Type *GlobalETSBigIntLiteralType(); Type *GlobalStringBuilderBuiltinType(); Type *GlobalTypeBuiltinType(); Type *GlobalTypesBuiltinType(); diff --git a/ets2panda/checker/types/type.cpp b/ets2panda/checker/types/type.cpp index c28e55dcf5e77f156655442d9a9432f9e5121eb8..239bcf008029f87776bb644796f7cb6c8e05f2c2 100644 --- a/ets2panda/checker/types/type.cpp +++ b/ets2panda/checker/types/type.cpp @@ -61,6 +61,11 @@ bool Type::IsETSStringType() const return IsETSObjectType() && AsETSObjectType()->HasObjectFlag(ETSObjectFlags::STRING); } +bool Type::IsETSBigIntType() const +{ + return IsETSObjectType() && AsETSObjectType()->HasObjectFlag(ETSObjectFlags::BUILTIN_BIGINT); +} + bool Type::IsETSAsyncFuncReturnType() const { return IsETSObjectType() && AsETSObjectType()->HasObjectFlag(ETSObjectFlags::ASYNC_FUNC_RETURN_TYPE); @@ -115,6 +120,11 @@ void Type::IsSupertypeOf(TypeRelation *const relation, [[maybe_unused]] Type *so relation->Result(false); } +void Type::IsSubtypeOf(TypeRelation *const relation, [[maybe_unused]] Type *target) +{ + relation->Result(false); +} + Type *Type::AsSuper([[maybe_unused]] Checker *checker, [[maybe_unused]] varbinder::Variable *source_var) { return nullptr; diff --git a/ets2panda/checker/types/type.h b/ets2panda/checker/types/type.h index 3f5185007d92099a711b83a8c63a20fbb94a2f95..b0bd53e4b0f9dfbe2b4770e89eb15cd3d1c36983 100644 --- a/ets2panda/checker/types/type.h +++ b/ets2panda/checker/types/type.h @@ -43,6 +43,7 @@ class ETSTypeParameter; TYPE_MAPPING(DECLARE_TYPENAMES) #undef DECLARE_TYPENAMES class ETSStringType; +class ETSBigIntType; using Substitution = ArenaMap; @@ -84,6 +85,7 @@ public: #undef TYPE_AS_CASTS bool IsETSStringType() const; + bool IsETSBigIntType() const; bool IsETSNullType() const; bool IsETSUndefinedType() const; bool IsETSNullLike() const; @@ -105,6 +107,12 @@ public: return reinterpret_cast(this); } + const ETSBigIntType *AsETSBigIntType() const + { + ASSERT(IsETSObjectType()); + return reinterpret_cast(this); + } + bool IsETSDynamicType() const { return IsETSObjectType() && HasTypeFlag(TypeFlag::ETS_DYNAMIC_FLAG); @@ -243,6 +251,7 @@ public: virtual void Cast(TypeRelation *relation, Type *target); virtual void CastTarget(TypeRelation *relation, Type *source); virtual void IsSupertypeOf(TypeRelation *relation, Type *source); + virtual void IsSubtypeOf(TypeRelation *relation, Type *target); virtual Type *AsSuper(Checker *checker, varbinder::Variable *source_var); virtual Type *Instantiate(ArenaAllocator *allocator, TypeRelation *relation, GlobalTypesHolder *global_types); diff --git a/ets2panda/checker/types/typeRelation.cpp b/ets2panda/checker/types/typeRelation.cpp index a3453c5190d4467829a12d5a6e89e4c07c168d0a..2e0b44bf40ce81d3906d489369b00a099ddce5b0 100644 --- a/ets2panda/checker/types/typeRelation.cpp +++ b/ets2panda/checker/types/typeRelation.cpp @@ -173,6 +173,29 @@ bool TypeRelation::IsCastableTo(Type *const source, Type *const target) return result_ == RelationResult::TRUE; } +bool TypeRelation::IsSupertypeOf(Type *super, Type *sub) +{ + result_ = CacheLookup(super, sub, checker_->SupertypeResults(), RelationType::SUPERTYPE); + + if (result_ == RelationResult::CACHE_MISS) { + if (IsIdenticalTo(super, sub)) { + return true; + } + + result_ = RelationResult::FALSE; + + if (super->IsSupertypeOf(this, sub), !IsTrue()) { + sub->IsSubtypeOf(this, super); + } + + if (flags_ == TypeRelationFlag::NONE) { + checker_->SupertypeResults().cached.insert({{super->Id(), sub->Id()}, {result_, RelationType::SUPERTYPE}}); + } + } + + return result_ == RelationResult::TRUE; +} + void TypeRelation::RaiseError(const std::string &err_msg, const lexer::SourcePosition &loc) const { checker_->ThrowTypeError(err_msg, loc); diff --git a/ets2panda/checker/types/typeRelation.h b/ets2panda/checker/types/typeRelation.h index 4e7cff3141aac5328cba1a678fd29c4e862c2375..b7f5002b6f01599b1330b9597328a77ca8a3052b 100644 --- a/ets2panda/checker/types/typeRelation.h +++ b/ets2panda/checker/types/typeRelation.h @@ -69,7 +69,7 @@ enum class TypeRelationFlag : uint32_t { enum class RelationResult { TRUE, FALSE, UNKNOWN, MAYBE, CACHE_MISS, ERROR }; -enum class RelationType { COMPARABLE, ASSIGNABLE, IDENTICAL, UNCHECKED_CASTABLE }; +enum class RelationType { COMPARABLE, ASSIGNABLE, IDENTICAL, UNCHECKED_CASTABLE, SUPERTYPE }; DEFINE_BITOPS(TypeRelationFlag) @@ -265,6 +265,7 @@ public: bool IsAssignableTo(Type *source, Type *target); bool IsComparableTo(Type *source, Type *target); bool IsCastableTo(Type *source, Type *target); + bool IsSupertypeOf(Type *super, Type *sub); void RaiseError(const std::string &err_msg, const lexer::SourcePosition &loc) const; void RaiseError(std::initializer_list list, const lexer::SourcePosition &loc) const; diff --git a/ets2panda/compiler/base/condition.cpp b/ets2panda/compiler/base/condition.cpp index d2abcf956930a75c6c9c30f7dae2f79f52208806..73d41b3740c3d47dfb8659fb223382dd8f8226c6 100644 --- a/ets2panda/compiler/base/condition.cpp +++ b/ets2panda/compiler/base/condition.cpp @@ -187,8 +187,60 @@ void Condition::CompileLogicalAndExpr(ETSGen *etsg, const ir::BinaryExpression * etsg->SetLabel(bin_expr, return_right_true_label); } +bool Condition::CompileBinaryExprForBigInt(ETSGen *etsg, const ir::BinaryExpression *expr, Label *false_label) +{ + if ((expr->Left()->TsType() == nullptr) || (expr->Right()->TsType() == nullptr)) { + return false; + } + + if (!expr->Left()->TsType()->IsETSBigIntType()) { + return false; + } + + if (!expr->Right()->TsType()->IsETSBigIntType()) { + return false; + } + + std::string_view signature = compiler::Signatures::ANY; + switch (expr->OperatorType()) { + case lexer::TokenType::PUNCTUATOR_LESS_THAN: + signature = compiler::Signatures::BUILTIN_BIGINT_OPERATOR_LESS_THAN; + break; + case lexer::TokenType::PUNCTUATOR_LESS_THAN_EQUAL: + signature = compiler::Signatures::BUILTIN_BIGINT_OPERATOR_LESS_THAN_EQUAL; + break; + case lexer::TokenType::PUNCTUATOR_GREATER_THAN: + signature = compiler::Signatures::BUILTIN_BIGINT_OPERATOR_GREATER_THAN; + break; + case lexer::TokenType::PUNCTUATOR_GREATER_THAN_EQUAL: + signature = compiler::Signatures::BUILTIN_BIGINT_OPERATOR_GREATER_THAN_EQUAL; + break; + default: + // Other operations are handled in the CompileBinaryExpr function + return false; + } + + auto ttctx = TargetTypeContext(etsg, expr->OperationType()); + RegScope rs(etsg); + VReg lhs = etsg->AllocReg(); + expr->Left()->Compile(etsg); + etsg->ApplyConversionAndStoreAccumulator(expr->Left(), lhs, expr->OperationType()); + expr->Right()->Compile(etsg); + etsg->ApplyConversion(expr->Right(), expr->OperationType()); + compiler::VReg rhs = etsg->AllocReg(); + etsg->StoreAccumulator(expr, rhs); + etsg->CallBigIntBinaryComparison(expr, lhs, rhs, signature); + etsg->BranchIfFalse(expr, false_label); + + return true; +} + bool Condition::CompileBinaryExpr(ETSGen *etsg, const ir::BinaryExpression *bin_expr, Label *false_label) { + if (CompileBinaryExprForBigInt(etsg, bin_expr, false_label)) { + return true; + } + switch (bin_expr->OperatorType()) { case lexer::TokenType::PUNCTUATOR_EQUAL: case lexer::TokenType::PUNCTUATOR_NOT_EQUAL: diff --git a/ets2panda/compiler/base/condition.h b/ets2panda/compiler/base/condition.h index 6380ba538ea054cc711217737c042649cfcc5ba7..30b3b27cadb3b84df4cb6c0682e58034aa31a4a9 100644 --- a/ets2panda/compiler/base/condition.h +++ b/ets2panda/compiler/base/condition.h @@ -42,6 +42,7 @@ private: static bool CompileBinaryExpr(ETSGen *etsg, const ir::BinaryExpression *bin_expr, Label *false_label); static void CompileLogicalAndExpr(ETSGen *etsg, const ir::BinaryExpression *bin_expr, Label *false_label); static void CompileLogicalOrExpr(ETSGen *etsg, const ir::BinaryExpression *bin_expr, Label *false_label); + static bool CompileBinaryExprForBigInt(ETSGen *etsg, const ir::BinaryExpression *bin_expr, Label *false_label); }; } // namespace panda::es2panda::compiler diff --git a/ets2panda/compiler/core/ETSCompiler.cpp b/ets2panda/compiler/core/ETSCompiler.cpp index 2ae78aa60713a4102701bc16d28e454f1cc22049..c19489b0e31997d3876842a76a9faee31675995a 100644 --- a/ets2panda/compiler/core/ETSCompiler.cpp +++ b/ets2panda/compiler/core/ETSCompiler.cpp @@ -290,6 +290,32 @@ static void CreateDynamicObject(const ir::AstNode *node, compiler::ETSGen *etsg, etsg->CallDynamic(node, obj_reg, qname_reg, signature, arguments); } +static void ConvertRestArguments(checker::ETSChecker *const checker, const ir::ETSNewClassInstanceExpression *expr) +{ + if (expr->GetSignature()->RestVar() != nullptr) { + std::size_t const argument_count = expr->GetArguments().size(); + std::size_t const parameter_count = expr->GetSignature()->MinArgCount(); + ASSERT(argument_count >= parameter_count); + + auto &arguments = const_cast &>(expr->GetArguments()); + std::size_t i = parameter_count; + + if (i < argument_count && expr->GetArguments()[i]->IsSpreadElement()) { + arguments[i] = expr->GetArguments()[i]->AsSpreadElement()->Argument(); + } else { + ArenaVector elements(checker->Allocator()->Adapter()); + for (; i < argument_count; ++i) { + elements.emplace_back(expr->GetArguments()[i]); + } + auto *array_expression = checker->AllocNode(std::move(elements), checker->Allocator()); + array_expression->SetParent(const_cast(expr)); + array_expression->SetTsType(expr->GetSignature()->RestVar()->TsType()); + arguments.erase(expr->GetArguments().begin() + parameter_count, expr->GetArguments().end()); + arguments.emplace_back(array_expression); + } + } +} + void ETSCompiler::Compile(const ir::ETSNewClassInstanceExpression *expr) const { ETSGen *etsg = GetETSGen(); @@ -298,6 +324,7 @@ void ETSCompiler::Compile(const ir::ETSNewClassInstanceExpression *expr) const auto *name = expr->GetTypeRef()->AsETSTypeReference()->Part()->Name(); CreateDynamicObject(expr, etsg, obj_reg, name, expr->signature_, expr->GetArguments()); } else { + ConvertRestArguments(const_cast(etsg->Checker()->AsETSChecker()), expr); etsg->InitObject(expr, expr->signature_, expr->GetArguments()); } @@ -523,9 +550,83 @@ static void CompileLogical(compiler::ETSGen *etsg, const ir::BinaryExpression *e etsg->SetAccumulatorType(expr->TsType()); } +std::map &GetBigintSignatures() +{ + static std::map bigint_signatures = { + {lexer::TokenType::PUNCTUATOR_PLUS, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_ADD}, + {lexer::TokenType::PUNCTUATOR_MINUS, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_SUBTRACT}, + {lexer::TokenType::PUNCTUATOR_MULTIPLY, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_MULTIPLY}, + {lexer::TokenType::PUNCTUATOR_DIVIDE, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_DIVIDE}, + {lexer::TokenType::PUNCTUATOR_MOD, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_MODULE}, + {lexer::TokenType::PUNCTUATOR_BITWISE_OR, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_BITWISE_OR}, + {lexer::TokenType::PUNCTUATOR_BITWISE_AND, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_BITWISE_AND}, + {lexer::TokenType::PUNCTUATOR_BITWISE_XOR, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_BITWISE_XOR}, + {lexer::TokenType::PUNCTUATOR_LEFT_SHIFT, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_LEFT_SHIFT}, + {lexer::TokenType::PUNCTUATOR_RIGHT_SHIFT, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_RIGHT_SHIFT}, + {lexer::TokenType::PUNCTUATOR_GREATER_THAN, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_GREATER_THAN}, + {lexer::TokenType::PUNCTUATOR_LESS_THAN, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_LESS_THAN}, + {lexer::TokenType::PUNCTUATOR_GREATER_THAN_EQUAL, + compiler::Signatures::BUILTIN_BIGINT_OPERATOR_GREATER_THAN_EQUAL}, + {lexer::TokenType::PUNCTUATOR_LESS_THAN_EQUAL, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_LESS_THAN_EQUAL}, + }; + + return bigint_signatures; +} + +static bool CompileBigInt(compiler::ETSGen *etsg, const ir::BinaryExpression *expr) +{ + if ((expr->Left()->TsType() == nullptr) || (expr->Right()->TsType() == nullptr)) { + return false; + } + + if (!expr->Left()->TsType()->IsETSBigIntType()) { + return false; + } + + if (!expr->Right()->TsType()->IsETSBigIntType()) { + return false; + } + + auto map = GetBigintSignatures(); + if (map.find(expr->OperatorType()) == map.end()) { + return false; + } + + const checker::Type *operation_type = expr->OperationType(); + auto ttctx = compiler::TargetTypeContext(etsg, operation_type); + compiler::RegScope rs(etsg); + compiler::VReg lhs = etsg->AllocReg(); + expr->Left()->Compile(etsg); + etsg->ApplyConversionAndStoreAccumulator(expr->Left(), lhs, operation_type); + expr->Right()->Compile(etsg); + etsg->ApplyConversion(expr->Right(), operation_type); + compiler::VReg rhs = etsg->AllocReg(); + etsg->StoreAccumulator(expr, rhs); + + std::string_view signature = map.at(expr->OperatorType()); + switch (expr->OperatorType()) { + case lexer::TokenType::PUNCTUATOR_GREATER_THAN: + case lexer::TokenType::PUNCTUATOR_LESS_THAN: + case lexer::TokenType::PUNCTUATOR_GREATER_THAN_EQUAL: + case lexer::TokenType::PUNCTUATOR_LESS_THAN_EQUAL: + etsg->CallBigIntBinaryComparison(expr, lhs, rhs, signature); + break; + default: + etsg->CallBigIntBinaryOperator(expr, lhs, rhs, signature); + break; + } + + return true; +} + void ETSCompiler::Compile(const ir::BinaryExpression *expr) const { ETSGen *etsg = GetETSGen(); + + if (CompileBigInt(etsg, expr)) { + return; + } + if (etsg->TryLoadConstantExpression(expr)) { return; } @@ -551,8 +652,7 @@ void ETSCompiler::Compile(const ir::BinaryExpression *expr) const etsg->ApplyConversionAndStoreAccumulator(expr->Left(), lhs, expr->OperationType()); expr->Right()->Compile(etsg); etsg->ApplyConversion(expr->Right(), expr->OperationType()); - if (expr->OperatorType() >= lexer::TokenType::PUNCTUATOR_LEFT_SHIFT && - expr->OperatorType() <= lexer::TokenType::PUNCTUATOR_UNSIGNED_RIGHT_SHIFT) { + if (expr->OperationType()->IsIntType()) { etsg->ApplyCast(expr->Right(), expr->OperationType()); } @@ -788,7 +888,11 @@ void ETSCompiler::Compile(const ir::ConditionalExpression *expr) const expr->Alternate()->Compile(etsg); etsg->ApplyConversion(expr->Alternate()); etsg->SetLabel(expr, end_label); - etsg->SetAccumulatorType(expr->TsType()); + if (expr->TsType()->IsETSUnionType()) { + etsg->SetAccumulatorType(expr->TsType()->AsETSUnionType()->GetLeastUpperBoundType()); + } else { + etsg->SetAccumulatorType(expr->TsType()); + } } void ETSCompiler::Compile([[maybe_unused]] const ir::DirectEvalExpression *expr) const @@ -1065,7 +1169,13 @@ void ETSCompiler::Compile(const ir::UnaryExpression *expr) const if (!etsg->TryLoadConstantExpression(expr->Argument())) { expr->Argument()->Compile(etsg); } + etsg->ApplyConversion(expr->Argument(), nullptr); + + if (expr->OperatorType() == lexer::TokenType::PUNCTUATOR_TILDE) { + etsg->ApplyCast(expr->Argument(), expr->TsType()); + } + etsg->Unary(expr, expr->OperatorType()); } @@ -1084,7 +1194,16 @@ void ETSCompiler::Compile(const ir::UpdateExpression *expr) const lref.GetValue(); expr->Argument()->SetBoxingUnboxingFlags(argument_unboxing_flags); etsg->ApplyConversion(expr->Argument(), nullptr); - etsg->Update(expr, expr->OperatorType()); + + if (expr->Argument()->TsType()->IsETSBigIntType()) { + compiler::RegScope rs(etsg); + compiler::VReg value_reg = etsg->AllocReg(); + etsg->StoreAccumulator(expr->Argument(), value_reg); + etsg->UpdateBigInt(expr, value_reg, expr->OperatorType()); + } else { + etsg->Update(expr, expr->OperatorType()); + } + expr->Argument()->SetBoxingUnboxingFlags(argument_boxing_flags); etsg->ApplyConversion(expr->Argument(), expr->Argument()->TsType()); lref.SetValue(); @@ -1101,7 +1220,12 @@ void ETSCompiler::Compile(const ir::UpdateExpression *expr) const expr->Argument()->SetBoxingUnboxingFlags(argument_unboxing_flags); etsg->ApplyConversion(expr->Argument(), nullptr); - etsg->Update(expr, expr->OperatorType()); + + if (expr->Argument()->TsType()->IsETSBigIntType()) { + etsg->UpdateBigInt(expr, original_value_reg, expr->OperatorType()); + } else { + etsg->Update(expr, expr->OperatorType()); + } expr->Argument()->SetBoxingUnboxingFlags(argument_boxing_flags); etsg->ApplyConversion(expr->Argument(), expr->Argument()->TsType()); @@ -1117,7 +1241,13 @@ void ETSCompiler::Compile([[maybe_unused]] const ir::YieldExpression *expr) cons // compile methods for LITERAL EXPRESSIONS in alphabetical order void ETSCompiler::Compile([[maybe_unused]] const ir::BigIntLiteral *expr) const { - UNREACHABLE(); + ETSGen *etsg = GetETSGen(); + compiler::TargetTypeContext ttctx = compiler::TargetTypeContext(etsg, expr->TsType()); + compiler::RegScope rs {etsg}; + etsg->LoadAccumulatorBigInt(expr, expr->Str()); + const compiler::VReg value = etsg->AllocReg(); + etsg->StoreAccumulator(expr, value); + etsg->CreateBigIntObject(expr, value); } void ETSCompiler::Compile(const ir::BooleanLiteral *expr) const diff --git a/ets2panda/compiler/core/ETSGen.cpp b/ets2panda/compiler/core/ETSGen.cpp index 7022338e477ee6a5cda369b5144712f197e92dd2..f2cf172a2713729cafb387858dcaf82f655ecc67 100644 --- a/ets2panda/compiler/core/ETSGen.cpp +++ b/ets2panda/compiler/core/ETSGen.cpp @@ -611,6 +611,11 @@ void ETSGen::LoadThis(const ir::AstNode *node) LoadAccumulator(node, GetThisReg()); } +void ETSGen::CreateBigIntObject(const ir::AstNode *node, VReg arg0) +{ + Ra().Emit(node, Signatures::BUILTIN_BIGINT_CTOR, arg0, dummy_reg_); +} + void ETSGen::CreateLambdaObjectFromIdentReference(const ir::AstNode *node, ir::ClassDefinition *lambda_obj) { auto *ctor = lambda_obj->TsType()->AsETSObjectType()->ConstructSignatures()[0]; @@ -836,6 +841,10 @@ void ETSGen::CheckedReferenceNarrowing(const ir::AstNode *node, const checker::T { ASSERT(target->HasTypeFlag(TYPE_FLAG_BYTECODE_REF) && !target->IsETSNullLike()); // NOTE(vpukhov): implement for nulllike and union targets + if (target == Checker()->GlobalETSNullishObjectType()) { + SetAccumulatorType(target); + return; + } Sa().Emit(node, ToAssemblerType(target)); SetAccumulatorType(target); @@ -851,6 +860,19 @@ void ETSGen::GuardUncheckedType(const ir::AstNode *node, const checker::Type *un } } +void ETSGen::LoadConstantObject(const ir::Expression *node, const checker::Type *type) +{ + if (type->HasTypeFlag(checker::TypeFlag::BIGINT_LITERAL)) { + LoadAccumulatorBigInt(node, type->AsETSObjectType()->AsETSBigIntType()->GetValue()); + const VReg value = AllocReg(); + StoreAccumulator(node, value); + CreateBigIntObject(node, value); + } else { + LoadAccumulatorString(node, type->AsETSObjectType()->AsETSStringType()->GetValue()); + SetAccumulatorType(node->TsType()); + } +} + bool ETSGen::TryLoadConstantExpression(const ir::Expression *node) { const auto *type = node->TsType(); @@ -895,8 +917,7 @@ bool ETSGen::TryLoadConstantExpression(const ir::Expression *node) break; } case checker::TypeFlag::ETS_OBJECT: { - LoadAccumulatorString(node, type->AsETSObjectType()->AsETSStringType()->GetValue()); - SetAccumulatorType(node->TsType()); + LoadConstantObject(node, type); break; } default: { @@ -1612,7 +1633,7 @@ void ETSGen::CastToArrayOrObject(const ir::AstNode *const node, const checker::T return; } - if (target_type->IsETSTypeParameter() && target_type->AsETSTypeParameter()->HasConstraint()) { + if (target_type->IsETSTypeParameter()) { CheckedReferenceNarrowing(node, target_type->AsETSTypeParameter()->GetConstraintType()); } else if (target_type->IsETSObjectType()) { CheckedReferenceNarrowing(node, target_type->AsETSObjectType()->GetConstOriginalBaseType()); @@ -2134,7 +2155,10 @@ void ETSGen::BinaryEqualityRef(const ir::AstNode *node, bool test_equal, VReg lh StoreAccumulator(node, rhs); LoadAccumulator(node, lhs); - if (GetVRegType(lhs)->IsETSStringType()) { + + if (GetVRegType(lhs)->IsETSBigIntType()) { + CallThisStatic1(node, lhs, Signatures::BUILTIN_BIGINT_EQUALS, rhs); + } else if (GetVRegType(lhs)->IsETSStringType()) { CallThisStatic1(node, lhs, Signatures::BUILTIN_STRING_EQUALS, rhs); } else { CallThisVirtual1(node, lhs, Signatures::BUILTIN_OBJECT_EQUALS, rhs); @@ -2227,6 +2251,13 @@ void ETSGen::Unary(const ir::AstNode *node, lexer::TokenType op) void ETSGen::UnaryMinus(const ir::AstNode *node) { + if (GetAccumulatorType()->IsETSBigIntType()) { + const VReg value = AllocReg(); + StoreAccumulator(node, value); + CallThisStatic0(node, value, Signatures::BUILTIN_BIGINT_NEGATE); + return; + } + switch (checker::ETSChecker::ETSType(GetAccumulatorType())) { case checker::TypeFlag::LONG: { Sa().Emit(node); @@ -2255,6 +2286,14 @@ void ETSGen::UnaryMinus(const ir::AstNode *node) void ETSGen::UnaryTilde(const ir::AstNode *node) { + if (GetAccumulatorType()->IsETSBigIntType()) { + const VReg value = AllocReg(); + StoreAccumulator(node, value); + CallThisStatic0(node, value, Signatures::BUILTIN_BIGINT_OPERATOR_BITWISE_NOT); + SetAccumulatorType(Checker()->GlobalETSBigIntType()); + return; + } + switch (checker::ETSChecker::ETSType(GetAccumulatorType())) { case checker::TypeFlag::LONG: { Sa().Emit(node); @@ -2299,6 +2338,23 @@ void ETSGen::Update(const ir::AstNode *node, lexer::TokenType op) } } +void ETSGen::UpdateBigInt(const ir::Expression *node, VReg arg, lexer::TokenType op) +{ + switch (op) { + case lexer::TokenType::PUNCTUATOR_PLUS_PLUS: { + CallBigIntUnaryOperator(node, arg, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_INCREMENT); + break; + } + case lexer::TokenType::PUNCTUATOR_MINUS_MINUS: { + CallBigIntUnaryOperator(node, arg, compiler::Signatures::BUILTIN_BIGINT_OPERATOR_DECREMENT); + break; + } + default: { + UNREACHABLE(); + } + } +} + void ETSGen::StringBuilderAppend(const ir::AstNode *node, VReg builder) { RegScope rs(this); @@ -2390,6 +2446,28 @@ void ETSGen::BuildString(const ir::Expression *node) SetAccumulatorType(node->TsType()); } +void ETSGen::CallBigIntUnaryOperator(const ir::Expression *node, VReg arg, const util::StringView signature) +{ + LoadAccumulator(node, arg); + CallThisStatic0(node, arg, signature); + SetAccumulatorType(Checker()->GlobalETSBigIntType()); +} + +void ETSGen::CallBigIntBinaryOperator(const ir::Expression *node, VReg lhs, VReg rhs, const util::StringView signature) +{ + LoadAccumulator(node, lhs); + CallThisStatic1(node, lhs, signature, rhs); + SetAccumulatorType(Checker()->GlobalETSBigIntType()); +} + +void ETSGen::CallBigIntBinaryComparison(const ir::Expression *node, VReg lhs, VReg rhs, + const util::StringView signature) +{ + LoadAccumulator(node, lhs); + CallThisStatic1(node, lhs, signature, rhs); + SetAccumulatorType(Checker()->GlobalETSBooleanType()); +} + void ETSGen::BuildTemplateString(const ir::TemplateLiteral *node) { RegScope rs(this); diff --git a/ets2panda/compiler/core/ETSGen.h b/ets2panda/compiler/core/ETSGen.h index 61c79b6af6bfb2ef6c552f0157ebe43c9351eb03..5aaa0c3d2ccfa9560fce6eb4232782e772aa67a2 100644 --- a/ets2panda/compiler/core/ETSGen.h +++ b/ets2panda/compiler/core/ETSGen.h @@ -98,6 +98,7 @@ public: void Binary(const ir::AstNode *node, lexer::TokenType op, VReg lhs); void Unary(const ir::AstNode *node, lexer::TokenType op); void Update(const ir::AstNode *node, lexer::TokenType op); + void UpdateBigInt(const ir::Expression *node, VReg arg, lexer::TokenType op); bool TryLoadConstantExpression(const ir::Expression *node); void Condition(const ir::AstNode *node, lexer::TokenType op, VReg lhs, Label *if_false); @@ -387,6 +388,12 @@ public: SetAccumulatorType(Checker()->GlobalETSStringLiteralType()); } + void LoadAccumulatorBigInt(const ir::AstNode *node, util::StringView str) + { + Sa().Emit(node, str); + SetAccumulatorType(Checker()->GlobalETSBigIntType()); + } + void LoadAccumulatorNull(const ir::AstNode *node, const checker::Type *type) { Sa().Emit(node); @@ -551,6 +558,9 @@ public: void NewArray(const ir::AstNode *node, VReg arr, VReg dim, const checker::Type *arr_type); void NewObject(const ir::AstNode *node, VReg ctor, util::StringView name); void BuildString(const ir::Expression *node); + void CallBigIntUnaryOperator(const ir::Expression *node, VReg arg, util::StringView signature); + void CallBigIntBinaryOperator(const ir::Expression *node, VReg lhs, VReg rhs, util::StringView signature); + void CallBigIntBinaryComparison(const ir::Expression *node, VReg lhs, VReg rhs, util::StringView signature); void BuildTemplateString(const ir::TemplateLiteral *node); void InitObject(const ir::AstNode *node, checker::Signature *signature, const ArenaVector &arguments) @@ -635,6 +645,7 @@ public: } #endif // PANDA_WITH_ETS + void CreateBigIntObject(const ir::AstNode *node, VReg arg0); void CreateLambdaObjectFromIdentReference(const ir::AstNode *node, ir::ClassDefinition *lambda_obj); void CreateLambdaObjectFromMemberReference(const ir::AstNode *node, ir::Expression *obj, ir::ClassDefinition *lambda_obj); @@ -661,6 +672,7 @@ private: void EmitUnboxedCall(const ir::AstNode *node, std::string_view signature_flag, const checker::Type *target_type, const checker::Type *boxed_type); + void LoadConstantObject(const ir::Expression *node, const checker::Type *type); void StringBuilderAppend(const ir::AstNode *node, VReg builder); void AppendString(const ir::Expression *bin_expr, VReg builder); void StringBuilder(const ir::Expression *left, const ir::Expression *right, VReg builder); @@ -840,6 +852,7 @@ private: case checker::TypeFlag::ETS_BOOLEAN: case checker::TypeFlag::BYTE: case checker::TypeFlag::SHORT: + case checker::TypeFlag::CHAR: case checker::TypeFlag::INT: { Ra().Emit(node, lhs, if_false); break; diff --git a/ets2panda/compiler/core/ETSfunction.cpp b/ets2panda/compiler/core/ETSfunction.cpp index bddfa6ec04982f1dcaafe9b8164d1452034d4a71..75a1cb7e4bcb552611bcec6d4044f9a590445818 100644 --- a/ets2panda/compiler/core/ETSfunction.cpp +++ b/ets2panda/compiler/core/ETSfunction.cpp @@ -146,6 +146,12 @@ void ETSFunction::CompileSourceBlock(ETSGen *etsg, const ir::BlockStatement *blo void ETSFunction::CompileFunction(ETSGen *etsg) { + const auto *decl = etsg->RootNode()->AsScriptFunction(); + + if (decl->IsDeclare()) { + return; + } + CompileSourceBlock(etsg, etsg->RootNode()->AsScriptFunction()->Body()->AsBlockStatement()); } diff --git a/ets2panda/compiler/lowering/ets/structLowering.cpp b/ets2panda/compiler/lowering/ets/structLowering.cpp new file mode 100644 index 0000000000000000000000000000000000000000..e1100319b450136560a44f6f6904bc8d42782bc6 --- /dev/null +++ b/ets2panda/compiler/lowering/ets/structLowering.cpp @@ -0,0 +1,113 @@ +/** + * Copyright (c) 2023 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. + */ + +#include "structLowering.h" +#include "checker/ETSchecker.h" +#include "compiler/core/compilerContext.h" +#include "ir/base/classDefinition.h" +#include "ir/base/classProperty.h" +#include "ir/astNode.h" +#include "ir/expression.h" +#include "ir/opaqueTypeNode.h" +#include "ir/expressions/identifier.h" +#include "ir/statements/classDeclaration.h" +#include "ir/ts/tsAsExpression.h" +#include "type_helper.h" + +namespace panda::es2panda::compiler { + +const char *const STRUCT_CLASS_NAME = "CommonStruct0"; + +std::string_view StructLowering::Name() +{ + static std::string const NAME = "struct-class-extention"; + return NAME; +} + +ir::ETSTypeReference *CreateStructTypeReference(checker::ETSChecker *checker, + ir::ETSStructDeclaration *ets_struc_declaration) +{ + auto *allocator = checker->Allocator(); + + ArenaVector params(allocator->Adapter()); + + ir::TSTypeParameterInstantiation *type_param_self_inst = nullptr; + + if (ets_struc_declaration->Definition()->TypeParams() != nullptr && + !ets_struc_declaration->Definition()->TypeParams()->Params().empty()) { + ArenaVector self_params(allocator->Adapter()); + ir::ETSTypeReferencePart *reference_part = nullptr; + + for (const auto ¶m : ets_struc_declaration->Definition()->TypeParams()->Params()) { + auto *ident_ref = checker->AllocNode(param->AsTSTypeParameter()->Name()->Name(), allocator); + ident_ref->AsIdentifier()->SetReference(); + + reference_part = checker->AllocNode(ident_ref, nullptr, nullptr); + + auto *type_reference = checker->AllocNode(reference_part); + + self_params.push_back(type_reference); + } + + type_param_self_inst = checker->AllocNode(std::move(self_params)); + } + + auto *ident_self_ref = + checker->AllocNode(ets_struc_declaration->Definition()->Ident()->Name(), allocator); + ident_self_ref->AsIdentifier()->SetReference(); + + auto *reference_self_part = + checker->AllocNode(ident_self_ref, type_param_self_inst, nullptr); + + auto *self_type_reference = checker->AllocNode(reference_self_part); + + params.push_back(self_type_reference); + + auto *type_param_inst = checker->AllocNode(std::move(params)); + + auto *ident_ref = checker->AllocNode(util::StringView(STRUCT_CLASS_NAME), allocator); + ident_ref->AsIdentifier()->SetReference(); + auto *reference_part = checker->AllocNode(ident_ref, type_param_inst, nullptr); + + auto *type_reference = checker->AllocNode(reference_part); + + return type_reference; +} + +bool StructLowering::Perform(public_lib::Context *ctx, parser::Program *program) +{ + for (auto &[_, ext_programs] : program->ExternalSources()) { + (void)_; + for (auto *ext_prog : ext_programs) { + Perform(ctx, ext_prog); + } + } + + checker::ETSChecker *checker = ctx->checker->AsETSChecker(); + + program->Ast()->TransformChildrenRecursively([checker](ir::AstNode *ast) -> ir::AstNode * { + if (ast->IsETSStructDeclaration()) { + auto *type_ref = CreateStructTypeReference(checker, ast->AsETSStructDeclaration()); + ast->AsETSStructDeclaration()->Definition()->SetSuper(type_ref); + ast->AsETSStructDeclaration()->Definition()->AddModifier(ir::ModifierFlags::FINAL); + } + + return ast; + }); + + return true; +} + +} // namespace panda::es2panda::compiler diff --git a/ets2panda/compiler/lowering/ets/structLowering.h b/ets2panda/compiler/lowering/ets/structLowering.h new file mode 100644 index 0000000000000000000000000000000000000000..3513322a030ad7a034d5e11b39683667689ad60a --- /dev/null +++ b/ets2panda/compiler/lowering/ets/structLowering.h @@ -0,0 +1,31 @@ +/** + * Copyright (c) 2023 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. + */ + +#ifndef ES2PANDA_COMPILER_LOWERING_STRUCT_LOWERING_H +#define ES2PANDA_COMPILER_LOWERING_STRUCT_LOWERING_H + +#include "compiler/lowering/phase.h" + +namespace panda::es2panda::compiler { + +class StructLowering : public Phase { +public: + std::string_view Name() override; + bool Perform(public_lib::Context *ctx, parser::Program *program) override; +}; + +} // namespace panda::es2panda::compiler + +#endif // ES2PANDA_COMPILER_LOWERING_STRUCT_LOWERING_H diff --git a/ets2panda/compiler/lowering/ets/unionLowering.cpp b/ets2panda/compiler/lowering/ets/unionLowering.cpp index 6460b495063c6895c33863cfd4b23314197fbf04..603c42b6f779f4c830464bb005d50281e198e2f1 100644 --- a/ets2panda/compiler/lowering/ets/unionLowering.cpp +++ b/ets2panda/compiler/lowering/ets/unionLowering.cpp @@ -26,6 +26,8 @@ #include "ir/astNode.h" #include "ir/expression.h" #include "ir/opaqueTypeNode.h" +#include "ir/expressions/literals/nullLiteral.h" +#include "ir/expressions/literals/undefinedLiteral.h" #include "ir/expressions/binaryExpression.h" #include "ir/expressions/identifier.h" #include "ir/expressions/memberExpression.h" @@ -155,9 +157,9 @@ ir::TSAsExpression *HandleUnionCastToPrimitive(checker::ETSChecker *checker, ir: } if (source_type != nullptr && expr->Expr()->GetBoxingUnboxingFlags() != ir::BoxingUnboxingFlags::NONE) { if (expr->TsType()->HasTypeFlag(checker::TypeFlag::ETS_PRIMITIVE)) { - auto *const boxed_expr_type = checker::BoxingConverter::ETSTypeFromSource(checker, expr->TsType()); - auto *const as_expr = GenAsExpression(checker, boxed_expr_type, expr->Expr(), expr); - as_expr->SetBoxingUnboxingFlags(expr->Expr()->GetBoxingUnboxingFlags()); + auto *const as_expr = GenAsExpression(checker, source_type, expr->Expr(), expr); + as_expr->SetBoxingUnboxingFlags( + checker->GetUnboxingFlag(checker->ETSBuiltinTypeAsPrimitiveType(source_type))); expr->Expr()->SetBoxingUnboxingFlags(ir::BoxingUnboxingFlags::NONE); expr->SetExpr(as_expr); } @@ -182,15 +184,24 @@ ir::BinaryExpression *GenInstanceofExpr(checker::ETSChecker *checker, ir::Expres rhs_type = checker::conversion::Boxing(checker->Relation(), constituent_type); checker->Relation()->SetNode(nullptr); } - auto *const rhs_expr = - checker->Allocator()->New(rhs_type->AsETSObjectType()->Name(), checker->Allocator()); + if (constituent_type->IsETSStringType()) { + rhs_type = checker->GlobalBuiltinETSStringType(); + } + ir::Expression *rhs_expr; + if (rhs_type->IsETSUndefinedType()) { + rhs_expr = checker->Allocator()->New(); + } else if (rhs_type->IsETSNullType()) { + rhs_expr = checker->Allocator()->New(); + } else { + rhs_expr = checker->Allocator()->New(rhs_type->AsETSObjectType()->Name(), checker->Allocator()); + auto rhs_var = NearestScope(union_node)->Find(rhs_expr->AsIdentifier()->Name()); + rhs_expr->AsIdentifier()->SetVariable(rhs_var.variable); + } auto *const instanceof_expr = checker->Allocator()->New(lhs_expr, rhs_expr, lexer::TokenType::KEYW_INSTANCEOF); lhs_expr->SetParent(instanceof_expr); rhs_expr->SetParent(instanceof_expr); - auto rhs_var = NearestScope(union_node)->Find(rhs_expr->Name()); - rhs_expr->SetVariable(rhs_var.variable); - rhs_expr->SetTsType(rhs_var.variable->TsType()); + rhs_expr->SetTsType(rhs_type); instanceof_expr->SetOperationType(checker->GlobalETSObjectType()); instanceof_expr->SetTsType(checker->GlobalETSBooleanType()); return instanceof_expr; @@ -272,7 +283,10 @@ ir::Expression *ProcessOperandsInBinaryExpr(checker::ETSChecker *checker, ir::Bi bool is_lhs_union; ir::Expression *union_node = (is_lhs_union = expr->Left()->TsType()->IsETSUnionType()) ? expr->Left() : expr->Right(); - auto *const as_expression = GenAsExpression(checker, constituent_type, union_node, expr); + checker::Type *type_to_cast = constituent_type->IsETSNullLike() + ? union_node->TsType()->AsETSUnionType()->GetLeastUpperBoundType() + : constituent_type; + auto *const as_expression = GenAsExpression(checker, type_to_cast, union_node, expr); if (is_lhs_union) { expr->SetLeft(as_expression); expr->SetRight(SetBoxFlagOrGenAsExpression(checker, constituent_type, expr->Right())); diff --git a/ets2panda/compiler/lowering/phase.cpp b/ets2panda/compiler/lowering/phase.cpp index b64e813bc52d8c4ee33544eddb1a0867ba7e093a..62313396840693ab1a8ed69e1ba217532188ff15 100644 --- a/ets2panda/compiler/lowering/phase.cpp +++ b/ets2panda/compiler/lowering/phase.cpp @@ -29,6 +29,7 @@ #include "compiler/lowering/ets/opAssignment.h" #include "compiler/lowering/ets/tupleLowering.h" #include "compiler/lowering/ets/unionLowering.h" +#include "compiler/lowering/ets/structLowering.h" #include "public/es2panda_lib.h" #include "compiler/lowering/ets/promiseVoid.h" @@ -52,52 +53,74 @@ static TupleLowering TUPLE_LOWERING; // Can be only applied after checking phas static UnionLowering UNION_LOWERING; static ExpandBracketsPhase EXPAND_BRACKETS_PHASE; static PromiseVoidLowering PROMISE_VOID_LOWERING; +static StructLowering STRUCT_LOWERING; static PluginPhase PLUGINS_AFTER_PARSE {"plugins-after-parse", ES2PANDA_STATE_PARSED, &util::Plugin::AfterParse}; static PluginPhase PLUGINS_AFTER_CHECK {"plugins-after-check", ES2PANDA_STATE_CHECKED, &util::Plugin::AfterCheck}; static PluginPhase PLUGINS_AFTER_LOWERINGS {"plugins-after-lowering", ES2PANDA_STATE_LOWERED, &util::Plugin::AfterLowerings}; -std::vector GetPhaseList(ScriptExtension ext) +// clang-format off +std::vector GetETSPhaseList() { static ScopesInitPhaseETS scopes_phase_ets; + return { + &scopes_phase_ets, + &PLUGINS_AFTER_PARSE, + &PROMISE_VOID_LOWERING, + &STRUCT_LOWERING, + &LAMBDA_LOWERING, + &INTERFACE_PROP_DECL_PHASE, + &CHECKER_PHASE, + &PLUGINS_AFTER_CHECK, + &GENERATE_TS_DECLARATIONS_PHASE, + &OP_ASSIGNMENT_LOWERING, + &OBJECT_INDEX_LOWERING, + &TUPLE_LOWERING, + &UNION_LOWERING, + &EXPAND_BRACKETS_PHASE, + &PLUGINS_AFTER_LOWERINGS, + }; +} +// clang-format on + +std::vector GetASPhaseList() +{ static ScopesInitPhaseAS scopes_phase_as; + return { + &scopes_phase_as, + &CHECKER_PHASE, + }; +} + +std::vector GetTSPhaseList() +{ static ScopesInitPhaseTs scopes_phase_ts; + return { + &scopes_phase_ts, + &CHECKER_PHASE, + }; +} + +std::vector GetJSPhaseList() +{ static ScopesInitPhaseJs scopes_phase_js; + return { + &scopes_phase_js, + &CHECKER_PHASE, + }; +} +std::vector GetPhaseList(ScriptExtension ext) +{ switch (ext) { case ScriptExtension::ETS: - return { - &scopes_phase_ets, - &PLUGINS_AFTER_PARSE, - &PROMISE_VOID_LOWERING, - &LAMBDA_LOWERING, - &INTERFACE_PROP_DECL_PHASE, - &CHECKER_PHASE, - &PLUGINS_AFTER_CHECK, - &GENERATE_TS_DECLARATIONS_PHASE, - &OP_ASSIGNMENT_LOWERING, - &OBJECT_INDEX_LOWERING, - &TUPLE_LOWERING, - &UNION_LOWERING, - &EXPAND_BRACKETS_PHASE, - &PLUGINS_AFTER_LOWERINGS, - }; - + return GetETSPhaseList(); case ScriptExtension::AS: - return std::vector { - &scopes_phase_as, - &CHECKER_PHASE, - }; + return GetASPhaseList(); case ScriptExtension::TS: - return std::vector { - &scopes_phase_ts, - &CHECKER_PHASE, - }; + return GetTSPhaseList(); case ScriptExtension::JS: - return std::vector { - &scopes_phase_js, - &CHECKER_PHASE, - }; + return GetJSPhaseList(); default: UNREACHABLE(); } diff --git a/ets2panda/compiler/scripts/signatures.yaml b/ets2panda/compiler/scripts/signatures.yaml index be3639d81fdfb9bc40453f5b77c6097e999ffa44..5c4631985329143d6a748a6db5f006ba4f1c983d 100644 --- a/ets2panda/compiler/scripts/signatures.yaml +++ b/ets2panda/compiler/scripts/signatures.yaml @@ -257,6 +257,9 @@ builtins: - name: Error package: PKG_ESCOMPAT ref: BUILTIN_ERROR + - name: BigInt + package: PKG_ESCOMPAT + ref: BUILTIN_BIGINT - name: AssertionError package: PKG_ESCOMPAT ref: BUILTIN_ASSERTION_ERROR @@ -337,6 +340,132 @@ signatures: return_type: PRIMITIVE_VOID ref: BUILTIN_ASSERTION_ERROR_CTOR + - callee: BUILTIN_BIGINT + method_name: $CTOR + params: [BUILTIN_STRING] + return_type: PRIMITIVE_VOID + ref: BUILTIN_BIGINT_CTOR + + - callee: BUILTIN_BIGINT + method_name: $CTOR + params: [] + return_type: PRIMITIVE_VOID + ref: BUILTIN_BIGINT_CTOR_EMPTY + + - callee: BUILTIN_BIGINT + method_name: equals + params: [BUILTIN_BIGINT] + return_type: PRIMITIVE_BOOLEAN + ref: BUILTIN_BIGINT_EQUALS + + - callee: BUILTIN_BIGINT + method_name: negate + params: [] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_NEGATE + + - callee: BUILTIN_BIGINT + method_name: operatorAdd + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_ADD + + - callee: BUILTIN_BIGINT + method_name: operatorSubtract + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_SUBTRACT + + - callee: BUILTIN_BIGINT + method_name: operatorMultiply + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_MULTIPLY + + - callee: BUILTIN_BIGINT + method_name: operatorDivide + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_DIVIDE + + - callee: BUILTIN_BIGINT + method_name: operatorModule + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_MODULE + + - callee: BUILTIN_BIGINT + method_name: operatorBitwiseOr + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_BITWISE_OR + + - callee: BUILTIN_BIGINT + method_name: operatorBitwiseAnd + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_BITWISE_AND + + - callee: BUILTIN_BIGINT + method_name: operatorBitwiseXor + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_BITWISE_XOR + + - callee: BUILTIN_BIGINT + method_name: operatorGreaterThan + params: [BUILTIN_BIGINT] + return_type: PRIMITIVE_BOOLEAN + ref: BUILTIN_BIGINT_OPERATOR_GREATER_THAN + + - callee: BUILTIN_BIGINT + method_name: operatorLessThan + params: [BUILTIN_BIGINT] + return_type: PRIMITIVE_BOOLEAN + ref: BUILTIN_BIGINT_OPERATOR_LESS_THAN + + - callee: BUILTIN_BIGINT + method_name: operatorGreaterThanEqual + params: [BUILTIN_BIGINT] + return_type: PRIMITIVE_BOOLEAN + ref: BUILTIN_BIGINT_OPERATOR_GREATER_THAN_EQUAL + + - callee: BUILTIN_BIGINT + method_name: operatorLessThanEqual + params: [BUILTIN_BIGINT] + return_type: PRIMITIVE_BOOLEAN + ref: BUILTIN_BIGINT_OPERATOR_LESS_THAN_EQUAL + + - callee: BUILTIN_BIGINT + method_name: operatorLeftShift + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_LEFT_SHIFT + + - callee: BUILTIN_BIGINT + method_name: operatorRightShift + params: [BUILTIN_BIGINT] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_RIGHT_SHIFT + + - callee: BUILTIN_BIGINT + method_name: operatorIncrement + params: [] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_INCREMENT + + - callee: BUILTIN_BIGINT + method_name: operatorDecrement + params: [] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_DECREMENT + + - callee: BUILTIN_BIGINT + method_name: operatorBitwiseNot + params: [] + return_type: BUILTIN_BIGINT + ref: BUILTIN_BIGINT_OPERATOR_BITWISE_NOT + - callee: BUILTIN_THROWABLE method_name: $CTOR params: [] diff --git a/ets2panda/ir/ets/etsNewClassInstanceExpression.h b/ets2panda/ir/ets/etsNewClassInstanceExpression.h index 031531ca7439447d3bcfe41b3ee65cbbdda62ab0..6f4dd092a43abb3cb526868e626208f2f06ef7d5 100644 --- a/ets2panda/ir/ets/etsNewClassInstanceExpression.h +++ b/ets2panda/ir/ets/etsNewClassInstanceExpression.h @@ -70,11 +70,16 @@ public: return type_reference_; } - [[nodiscard]] ArenaVector GetArguments() const noexcept + [[nodiscard]] const ArenaVector &GetArguments() const noexcept { return arguments_; } + [[nodiscard]] checker::Signature *GetSignature() const noexcept + { + return signature_; + } + void SetSignature(checker::Signature *const signature) noexcept { signature_ = signature; diff --git a/ets2panda/ir/expressions/arrayExpression.cpp b/ets2panda/ir/expressions/arrayExpression.cpp index b1b2ef87a7e0a3a03a1d4e129890ab665c9ef780..575c72d4b7e98c28d3a826c062bca9de4a52ee41 100644 --- a/ets2panda/ir/expressions/arrayExpression.cpp +++ b/ets2panda/ir/expressions/arrayExpression.cpp @@ -379,4 +379,26 @@ checker::Type *ArrayExpression::Check(checker::ETSChecker *checker) { return checker->GetAnalyzer()->Check(this); } + +void ArrayExpression::GetPrefferedTypeFromFuncParam(checker::ETSChecker *checker, Expression *param, + checker::TypeRelationFlag flags) +{ + if (preferred_type_ != nullptr) { + return; + } + auto param_type = param->Check(checker); + if (param_type->IsETSArrayType()) { + param_type = param_type->AsETSArrayType()->ElementType(); + } + bool is_assignable = true; + for (auto elem : elements_) { + auto assign_ctx = checker::AssignmentContext(checker->Relation(), elem, elem->Check(checker), param_type, + elem->Start(), {""}, checker::TypeRelationFlag::NO_THROW | flags); + is_assignable &= assign_ctx.IsAssignable(); + } + if (is_assignable) { + preferred_type_ = param->Check(checker); + } +} + } // namespace panda::es2panda::ir diff --git a/ets2panda/ir/expressions/arrayExpression.h b/ets2panda/ir/expressions/arrayExpression.h index cd5f4132d0dc8e5926802fea3e3e1f635875516e..f2699692ac4b351465e1c708a25fbaaf2ba3596e 100644 --- a/ets2panda/ir/expressions/arrayExpression.h +++ b/ets2panda/ir/expressions/arrayExpression.h @@ -18,6 +18,7 @@ #include "ir/expression.h" #include "ir/validationInfo.h" +#include "checker/types/ets/etsArrayType.h" namespace panda::es2panda::checker { class ETSAnalyzer; @@ -140,6 +141,9 @@ public: v->Accept(this); } + void GetPrefferedTypeFromFuncParam(checker::ETSChecker *checker, Expression *param, + checker::TypeRelationFlag flags); + private: ArenaVector decorators_; ArenaVector elements_; diff --git a/ets2panda/ir/expressions/literals/bigIntLiteral.cpp b/ets2panda/ir/expressions/literals/bigIntLiteral.cpp index a12339916cf09c833b73c2bb68976b8dfc8dcdc6..e3fbbd8c8f8f3187b5d30e1b2b765966dd92cf77 100644 --- a/ets2panda/ir/expressions/literals/bigIntLiteral.cpp +++ b/ets2panda/ir/expressions/literals/bigIntLiteral.cpp @@ -19,6 +19,7 @@ #include "compiler/core/ETSGen.h" #include "compiler/core/pandagen.h" #include "ir/astDump.h" +#include "checker/ETSchecker.h" #include "ir/srcDump.h" namespace panda::es2panda::ir { diff --git a/ets2panda/ir/expressions/literals/bigIntLiteral.h b/ets2panda/ir/expressions/literals/bigIntLiteral.h index 0ae06c26404386e01c7bb54e8af482b40257ef71..424c37bcb16d662b6debda9058c93b3c9c871cb2 100644 --- a/ets2panda/ir/expressions/literals/bigIntLiteral.h +++ b/ets2panda/ir/expressions/literals/bigIntLiteral.h @@ -42,10 +42,10 @@ public: void Iterate(const NodeTraverser &cb) const override; void Dump(ir::AstDumper *dumper) const override; void Dump(ir::SrcDumper *dumper) const override; - void Compile(compiler::PandaGen *pg) const override; + void Compile([[maybe_unused]] compiler::PandaGen *pg) const override; void Compile(compiler::ETSGen *etsg) const override; - checker::Type *Check(checker::TSChecker *checker) override; - checker::Type *Check(checker::ETSChecker *checker) override; + checker::Type *Check([[maybe_unused]] checker::TSChecker *checker) override; + checker::Type *Check([[maybe_unused]] checker::ETSChecker *checker) override; void Accept(ASTVisitorT *v) override { diff --git a/ets2panda/ir/expressions/literals/undefinedLiteral.cpp b/ets2panda/ir/expressions/literals/undefinedLiteral.cpp index 27bddb8b4078d63f8edf4676ad83d07621c24b6f..3d28d6c06b465d322edcff248eab416ca5c69398 100644 --- a/ets2panda/ir/expressions/literals/undefinedLiteral.cpp +++ b/ets2panda/ir/expressions/literals/undefinedLiteral.cpp @@ -56,4 +56,17 @@ checker::Type *UndefinedLiteral::Check([[maybe_unused]] checker::ETSChecker *che SetTsType(checker->GlobalETSUndefinedType()); return TsType(); } + +// NOLINTNEXTLINE(google-default-arguments) +UndefinedLiteral *UndefinedLiteral::Clone(ArenaAllocator *allocator, AstNode *parent) +{ + if (auto *const clone = allocator->New(); clone != nullptr) { + if (parent != nullptr) { + clone->SetParent(parent); + } + return clone; + } + + throw Error(ErrorType::GENERIC, "", CLONE_ALLOCATION_ERROR); +} } // namespace panda::es2panda::ir diff --git a/ets2panda/ir/expressions/literals/undefinedLiteral.h b/ets2panda/ir/expressions/literals/undefinedLiteral.h index 818867cde59e9820577967e67411f4bf873a9e30..2de04789a1848e381481fc2d21f6fef1f379bc7e 100644 --- a/ets2panda/ir/expressions/literals/undefinedLiteral.h +++ b/ets2panda/ir/expressions/literals/undefinedLiteral.h @@ -23,6 +23,9 @@ class UndefinedLiteral : public Literal { public: explicit UndefinedLiteral() : Literal(AstNodeType::UNDEFINED_LITERAL) {} + // NOLINTNEXTLINE(google-default-arguments) + [[nodiscard]] UndefinedLiteral *Clone(ArenaAllocator *allocator, AstNode *parent = nullptr) override; + void TransformChildren(const NodeTransformer &cb) override; void Iterate(const NodeTraverser &cb) const override; void Dump(ir::AstDumper *dumper) const override; diff --git a/ets2panda/ir/expressions/memberExpression.cpp b/ets2panda/ir/expressions/memberExpression.cpp index 68cfc53cbbf0fc54e86e521c87f8911b0e073153..1ff530e538cb15e5bc2d771f89f3624d0328a6b3 100644 --- a/ets2panda/ir/expressions/memberExpression.cpp +++ b/ets2panda/ir/expressions/memberExpression.cpp @@ -221,7 +221,7 @@ checker::Type *MemberExpression::AdjustType(checker::ETSChecker *checker, checke if (PropVar() != nullptr) { unchecked_type_ = checker->GuaranteedTypeForUncheckedPropertyAccess(PropVar()); } - if (IsOptional() && Object()->TsType()->IsNullishOrNullLike()) { + if (IsOptional() && checker->MayHaveNulllikeValue(Object()->TsType())) { checker->Relation()->SetNode(this); type = checker->CreateOptionalResultType(type); checker->Relation()->SetNode(nullptr); diff --git a/ets2panda/ir/expressions/unaryExpression.cpp b/ets2panda/ir/expressions/unaryExpression.cpp index 82601c41bfc70b374a26224a45c501f7d357d86a..77160e124d6f40dd57178b94a51aa9d899b61c52 100644 --- a/ets2panda/ir/expressions/unaryExpression.cpp +++ b/ets2panda/ir/expressions/unaryExpression.cpp @@ -16,6 +16,7 @@ #include "unaryExpression.h" #include "varbinder/variable.h" +#include "checker/types/typeFlag.h" #include "compiler/core/pandagen.h" #include "compiler/core/ETSGen.h" #include "checker/TSchecker.h" diff --git a/ets2panda/ir/ts/tsEnumDeclaration.h b/ets2panda/ir/ts/tsEnumDeclaration.h index a0d0c168b6afb63b6b6979801f32fbb9a6aa9d5a..319538c67e659b6ad2f4840782a46629b515e4d2 100644 --- a/ets2panda/ir/ts/tsEnumDeclaration.h +++ b/ets2panda/ir/ts/tsEnumDeclaration.h @@ -31,16 +31,20 @@ class TSEnumMember; class TSEnumDeclaration : public TypedStatement { public: explicit TSEnumDeclaration(ArenaAllocator *allocator, Identifier *key, ArenaVector &&members, - bool is_const, bool is_static = false) + bool is_const, bool is_static = false, bool is_declare = false) : TypedStatement(AstNodeType::TS_ENUM_DECLARATION), decorators_(allocator->Adapter()), key_(key), members_(std::move(members)), - is_const_(is_const) + is_const_(is_const), + is_declare_(is_declare) { if (is_static) { AddModifier(ModifierFlags::STATIC); } + if (is_declare) { + AddModifier(ModifierFlags::DECLARE); + } } bool IsScopeBearer() const override @@ -88,6 +92,11 @@ public: return is_const_; } + bool IsDeclare() const + { + return is_declare_; + } + const ArenaVector &Decorators() const { return decorators_; @@ -131,6 +140,7 @@ private: ArenaVector members_; util::StringView internal_name_; bool is_const_; + bool is_declare_; }; } // namespace panda::es2panda::ir diff --git a/ets2panda/ir/ts/tsTypeAliasDeclaration.h b/ets2panda/ir/ts/tsTypeAliasDeclaration.h index 9c4415dd5a00d0716340b10c786ec83b63ccaa03..ef4ddcb84c6549e4c25164b7e7056720623cbb5b 100644 --- a/ets2panda/ir/ts/tsTypeAliasDeclaration.h +++ b/ets2panda/ir/ts/tsTypeAliasDeclaration.h @@ -34,6 +34,7 @@ public: decorators_(allocator->Adapter()), id_(id), type_params_(type_params), + type_param_types_(allocator->Adapter()), declare_(declare) { } @@ -43,6 +44,7 @@ public: decorators_(allocator->Adapter()), id_(id), type_params_(nullptr), + type_param_types_(allocator->Adapter()), declare_(false) { } @@ -57,7 +59,7 @@ public: return id_; } - const TSTypeParameterDeclaration *TypeParams() const + TSTypeParameterDeclaration *TypeParams() const { return type_params_; } @@ -77,7 +79,7 @@ public: return &Decorators(); } - void AddTypeParameters(ir::TSTypeParameterDeclaration *type_params) + void SetTypeParameters(ir::TSTypeParameterDeclaration *type_params) { type_params_ = type_params; } @@ -92,6 +94,16 @@ public: return !in_ts; } + void SetTypeParameterTypes(ArenaVector &&type_param_types) + { + type_param_types_ = std::move(type_param_types); + } + + ArenaVector const &TypeParameterTypes() const + { + return type_param_types_; + } + void TransformChildren(const NodeTransformer &cb) override; void Iterate(const NodeTraverser &cb) const override; void Dump(ir::AstDumper *dumper) const override; @@ -110,6 +122,7 @@ private: ArenaVector decorators_; Identifier *id_; TSTypeParameterDeclaration *type_params_; + ArenaVector type_param_types_; bool declare_; }; } // namespace panda::es2panda::ir diff --git a/ets2panda/lexer/ETSLexer.h b/ets2panda/lexer/ETSLexer.h index 6c7c7b43e9dbfd0973688763c19f02a692152add..1349e8a8ad188437d4541ea2ebf4bf0fdb2bf980 100644 --- a/ets2panda/lexer/ETSLexer.h +++ b/ets2panda/lexer/ETSLexer.h @@ -17,6 +17,7 @@ #define ES2PANDA_PARSER_CORE_ETS_LEXER_H #include "lexer/lexer.h" +#include "token/letters.h" namespace panda::es2panda::lexer { class ETSLexer final : public Lexer { @@ -40,12 +41,25 @@ public: void ScanNumberLeadingZero() override { const auto saved_lexer_position = Save(); + + bool allow_bigint = false; + if (Iterator().Peek() == LEX_CHAR_LOWERCASE_N) { + // 0n is the only allowed bigint literal with leading 0 + allow_bigint = true; + } + try { ScanNumberLeadingZeroImpl(); } catch (...) { Rewind(saved_lexer_position); ScanNumberLeadingZeroImpl(); } + + if ((GetToken().flags_ & TokenFlags::NUMBER_BIGINT) != 0) { + if (!allow_bigint) { + ThrowError("Invalid BigInt number"); + } + } } void CheckNumberLiteralEnd() override; diff --git a/ets2panda/lexer/scripts/keywords.yaml b/ets2panda/lexer/scripts/keywords.yaml index 690264b0981106674467fef736124b6ffb62a266..287aa8319889050bafc93d9c60036e0dafe33951 100644 --- a/ets2panda/lexer/scripts/keywords.yaml +++ b/ets2panda/lexer/scripts/keywords.yaml @@ -296,6 +296,7 @@ keywords: - name: 'namespace' token: KEYW_NAMESPACE + keyword: [ets] keyword_like: [as, ts] - name: 'native' diff --git a/ets2panda/parser/ASparser.cpp b/ets2panda/parser/ASparser.cpp index b74d7243cfdcd8b053f88e653d2fe4f53ef430c0..e3e06504f702132fb15fe003ac85825555be43e9 100644 --- a/ets2panda/parser/ASparser.cpp +++ b/ets2panda/parser/ASparser.cpp @@ -15,6 +15,7 @@ #include "ASparser.h" +#include "parserFlags.h" #include "util/helpers.h" #include "varbinder/privateBinding.h" #include "varbinder/scope.h" @@ -1350,7 +1351,9 @@ ir::AstNode *ASParser::ParseImportDefaultSpecifier(ArenaVector *s return nullptr; } -ir::Expression *ASParser::ParseCoverParenthesizedExpressionAndArrowParameterList() +// NOLINTNEXTLINE(google-default-arguments) +ir::Expression *ASParser::ParseCoverParenthesizedExpressionAndArrowParameterList( + [[maybe_unused]] ExpressionParseFlags flags) { ASSERT(Lexer()->GetToken().Type() == lexer::TokenType::PUNCTUATOR_LEFT_PARENTHESIS); lexer::SourcePosition start = Lexer()->GetToken().Start(); diff --git a/ets2panda/parser/ASparser.h b/ets2panda/parser/ASparser.h index dbbf869c47b5cd21e5c28977b10a79b1d1a5fea0..fc7cdf98b60312ef2e4aa410d0f3dcc64e0415ed 100644 --- a/ets2panda/parser/ASparser.h +++ b/ets2panda/parser/ASparser.h @@ -17,6 +17,7 @@ #define ES2PANDA_PARSER_CORE_AS_PARSER_H #include "TypedParser.h" +#include "parserFlags.h" namespace panda::es2panda::parser { class ASParser : public TypedParser { @@ -74,7 +75,9 @@ private: const ArenaVector ¶ms, ParserStatus new_status, ParserStatus context_status) override; ir::AstNode *ParseImportDefaultSpecifier(ArenaVector *specifiers) override; std::tuple ParseInterfacePropertyKey() override; - ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList() override; + // NOLINTNEXTLINE(google-default-arguments) + ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList( + ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS) override; ir::Expression *ParsePrefixAssertionExpression() override; ir::Statement *ParseConstStatement(StatementParsingFlags flags) override; ir::AnnotatedExpression *ParseVariableDeclaratorKey(VariableParsingFlags flags) override; diff --git a/ets2panda/parser/ETSparser.cpp b/ets2panda/parser/ETSparser.cpp index a78f3e1ad6e113215d15f1cfc2ece7331dcafdc5..ce756aebcc2e22a9170880f7e92bb593123cb9c3 100644 --- a/ets2panda/parser/ETSparser.cpp +++ b/ets2panda/parser/ETSparser.cpp @@ -187,7 +187,9 @@ void ETSParser::ParseETSGlobalScript(lexer::SourcePosition start_loc, ArenaVecto end(items)); for (const auto &item : items) { - parsed_sources_.push_back(ResolveImportPath(item)); + auto resolved = ResolveImportPath(item); + resolved_parsed_sources_.emplace(item, resolved); + parsed_sources_.push_back(resolved); } }; @@ -778,6 +780,8 @@ ArenaVector ETSParser::ParseTopLevelStatements(ArenaVectorRewind(saved_pos); @@ -1576,6 +1582,9 @@ ir::AstNode *ETSParser::ParseClassElement([[maybe_unused]] const ArenaVectorGetToken().Type(); + if (type == lexer::TokenType::KEYW_FUNCTION || type == lexer::TokenType::KEYW_LET || + type == lexer::TokenType::KEYW_CONST) { + Lexer()->NextToken(); + } + } + + auto *member_name = ExpectIdentifier(); if (Lexer()->GetToken().Type() == lexer::TokenType::PUNCTUATOR_LEFT_PARENTHESIS || Lexer()->GetToken().Type() == lexer::TokenType::PUNCTUATOR_LESS_THAN) { @@ -1726,6 +1743,15 @@ ir::Statement *ETSParser::ParseTypeDeclaration(bool allow_static) case lexer::TokenType::KEYW_INTERFACE: { return ParseInterfaceDeclaration(false); } + case lexer::TokenType::KEYW_NAMESPACE: { + if (!InAmbientContext()) { + ThrowSyntaxError("Namespaces are declare only"); + } + GetContext().Status() |= ParserStatus::IN_NAMESPACE; + auto *ns = ParseClassDeclaration(modifiers, ir::ModifierFlags::STATIC); + GetContext().Status() &= ~ParserStatus::IN_NAMESPACE; + return ns; + } case lexer::TokenType::KEYW_CLASS: { return ParseClassDeclaration(modifiers); } @@ -1800,7 +1826,7 @@ ir::TSTypeAliasDeclaration *ETSParser::ParseTypeAliasDeclaration() auto options = TypeAnnotationParsingOptions::THROW_ERROR | TypeAnnotationParsingOptions::ALLOW_DECLARATION_SITE_VARIANCE; ir::TSTypeParameterDeclaration *params = ParseTypeParameterDeclaration(&options); - type_alias_decl->AddTypeParameters(params); + type_alias_decl->SetTypeParameters(params); params->SetParent(type_alias_decl); } @@ -3806,7 +3832,7 @@ ir::Expression *ETSParser::ParsePrimaryExpression(ExpressionParseFlags flags) return ParseCharLiteral(); } case lexer::TokenType::PUNCTUATOR_LEFT_PARENTHESIS: { - return ParseCoverParenthesizedExpressionAndArrowParameterList(); + return ParseCoverParenthesizedExpressionAndArrowParameterList(flags); } case lexer::TokenType::KEYW_THIS: { return ParseThisExpression(); @@ -3907,7 +3933,8 @@ ir::ArrowFunctionExpression *ETSParser::ParseArrowFunctionExpression() return arrow_func_node; } -ir::Expression *ETSParser::ParseCoverParenthesizedExpressionAndArrowParameterList() +// NOLINTNEXTLINE(google-default-arguments) +ir::Expression *ETSParser::ParseCoverParenthesizedExpressionAndArrowParameterList(ExpressionParseFlags flags) { ASSERT(Lexer()->GetToken().Type() == lexer::TokenType::PUNCTUATOR_LEFT_PARENTHESIS); if (IsArrowFunctionExpressionStart()) { @@ -3917,7 +3944,12 @@ ir::Expression *ETSParser::ParseCoverParenthesizedExpressionAndArrowParameterLis lexer::SourcePosition start = Lexer()->GetToken().Start(); Lexer()->NextToken(); - ir::Expression *expr = ParseExpression(ExpressionParseFlags::ACCEPT_COMMA); + ExpressionParseFlags new_flags = ExpressionParseFlags::ACCEPT_COMMA; + if ((flags & ExpressionParseFlags::INSTANCEOF) != 0) { + new_flags |= ExpressionParseFlags::INSTANCEOF; + }; + + ir::Expression *expr = ParseExpression(new_flags); if (Lexer()->GetToken().Type() != lexer::TokenType::PUNCTUATOR_RIGHT_PARENTHESIS) { ThrowSyntaxError("Unexpected token, expected ')'"); @@ -4289,7 +4321,7 @@ ir::TSEnumDeclaration *ETSParser::ParseEnumMembers(ir::Identifier *const key, co } auto *const enum_declaration = - AllocNode(Allocator(), key, std::move(members), is_const, is_static); + AllocNode(Allocator(), key, std::move(members), is_const, is_static, InAmbientContext()); enum_declaration->SetRange({enum_start, Lexer()->GetToken().End()}); Lexer()->NextToken(); // eat '}' @@ -4595,6 +4627,24 @@ bool ETSParser::IsStructKeyword() const Lexer()->GetToken().KeywordType() == lexer::TokenType::KEYW_STRUCT); } +void ETSParser::ValidateInstanceOfExpression(ir::Expression *expr) +{ + ValidateGroupedExpression(expr); + lexer::TokenType token_type = Lexer()->GetToken().Type(); + if (token_type == lexer::TokenType::PUNCTUATOR_LESS_THAN) { + auto options = TypeAnnotationParsingOptions::NO_OPTS; + + // Run checks to validate type declarations + // Should provide helpful messages with incorrect declarations like the following: + // instanceof A; + ThrowSyntaxError("Invalid right-hand side in 'instanceof' expression"); + } +} + // NOLINTNEXTLINE(google-default-arguments) ir::Expression *ETSParser::ParseExpression(ExpressionParseFlags flags) { @@ -4606,6 +4656,10 @@ ir::Expression *ETSParser::ParseExpression(ExpressionParseFlags flags) } ir::Expression *unary_expression_node = ParseUnaryOrPrefixUpdateExpression(flags); + if ((flags & ExpressionParseFlags::INSTANCEOF) != 0) { + ValidateInstanceOfExpression(unary_expression_node); + } + ir::Expression *assignment_expression = ParseAssignmentExpression(unary_expression_node, flags); if (Lexer()->GetToken().NewLine()) { @@ -4663,6 +4717,7 @@ void ETSParser::CheckDeclare() case lexer::TokenType::KEYW_CLASS: case lexer::TokenType::KEYW_NAMESPACE: case lexer::TokenType::KEYW_ENUM: + case lexer::TokenType::KEYW_TYPE: case lexer::TokenType::KEYW_ABSTRACT: case lexer::TokenType::KEYW_INTERFACE: { return; diff --git a/ets2panda/parser/ETSparser.h b/ets2panda/parser/ETSparser.h index ec1f1667deb052eee62f72a357e7df09efcd3354..ffbbf5b088e87677396e714b9c1b5b8aeed028fd 100644 --- a/ets2panda/parser/ETSparser.h +++ b/ets2panda/parser/ETSparser.h @@ -17,6 +17,7 @@ #define ES2PANDA_PARSER_CORE_ETS_PARSER_H #include +#include "parserFlags.h" #include "util/arktsconfig.h" #include "TypedParser.h" @@ -192,7 +193,9 @@ private: void ValidateForInStatement() override; - ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList() override; + // NOLINTNEXTLINE(google-default-arguments) + ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList( + ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS) override; ir::Statement *ParseTryStatement() override; ir::DebuggerStatement *ParseDebuggerStatement() override; void ParseExport(lexer::SourcePosition start_loc); @@ -264,6 +267,7 @@ private: // NOLINTNEXTLINE(google-default-arguments) ir::Statement *ParseEnumDeclaration(bool is_const = false, bool is_static = false) override; ir::Expression *ParseLaunchExpression(ExpressionParseFlags flags); + void ValidateInstanceOfExpression(ir::Expression *expr); void ValidateRestParameter(ir::Expression *param) override; void CheckIndexAccessMethod(ir::ScriptFunction const *function, const lexer::SourcePosition &position) const; @@ -320,7 +324,6 @@ private: ir::Statement *CreateStatement(std::string_view source_code, std::string_view file_name = DEFAULT_SOURCE_FILE); ir::Statement *CreateFormattedStatement(std::string_view source_code, std::vector &inserting_nodes, std::string_view file_name = DEFAULT_SOURCE_FILE); - // NOLINTEND(google-default-arguments) template ir::Statement *CreateFormattedStatement(std::string_view const source_code, std::string_view const file_name, @@ -338,7 +341,6 @@ private: std::string_view file_name = DEFAULT_SOURCE_FILE); ir::TypeNode *CreateTypeAnnotation(TypeAnnotationParsingOptions *options, std::string_view source_code, std::string_view file_name = DEFAULT_SOURCE_FILE); - // NOLINTEND(google-default-arguments) friend class ExternalSourceParser; friend class InnerSourceParser; diff --git a/ets2panda/parser/TSparser.cpp b/ets2panda/parser/TSparser.cpp index 29781c637d7d2150844d17df54056bc6c62d30b3..3204d0899d76ed71132839279d886c6058a419b4 100644 --- a/ets2panda/parser/TSparser.cpp +++ b/ets2panda/parser/TSparser.cpp @@ -15,6 +15,7 @@ #include "TSparser.h" +#include "parserFlags.h" #include "util/helpers.h" #include "varbinder/privateBinding.h" #include "varbinder/scope.h" @@ -2600,7 +2601,9 @@ ir::Statement *TSParser::ParseExportDeclaration(StatementParsingFlags flags) } } -ir::Expression *TSParser::ParseCoverParenthesizedExpressionAndArrowParameterList() +// NOLINTNEXTLINE(google-default-arguments) +ir::Expression *TSParser::ParseCoverParenthesizedExpressionAndArrowParameterList( + [[maybe_unused]] ExpressionParseFlags flags) { ASSERT(Lexer()->GetToken().Type() == lexer::TokenType::PUNCTUATOR_LEFT_PARENTHESIS); lexer::SourcePosition start = Lexer()->GetToken().Start(); diff --git a/ets2panda/parser/TSparser.h b/ets2panda/parser/TSparser.h index 376f7f0a2e01c7cc97b2351ee61206e29892fc6a..3e660ea9a05fe04b05dc79326fd7eff901e8560d 100644 --- a/ets2panda/parser/TSparser.h +++ b/ets2panda/parser/TSparser.h @@ -17,6 +17,7 @@ #define ES2PANDA_PARSER_CORE_TS_PARSER_H #include "TypedParser.h" +#include "parserFlags.h" namespace panda::es2panda::ir { class Decorator; @@ -123,7 +124,9 @@ private: const ArenaVector ¶ms, ParserStatus new_status, ParserStatus context_status) override; ir::AstNode *ParseImportDefaultSpecifier(ArenaVector *specifiers) override; ir::Statement *ParseExportDeclaration(StatementParsingFlags flags) override; - ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList() override; + // NOLINTNEXTLINE(google-default-arguments) + ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList( + ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS) override; ir::Statement *ParseConstStatement(StatementParsingFlags flags) override; ir::Statement *ParsePotentialConstEnum(VariableParsingFlags flags) override; void ParseCatchParamTypeAnnotation(ir::AnnotatedExpression *param) override; diff --git a/ets2panda/parser/context/parserContext.h b/ets2panda/parser/context/parserContext.h index 2751b480bede62fcf99825648b99619e7c7f01c3..631188ce5dae106f7561cc0ba7d31529c45f9966 100644 --- a/ets2panda/parser/context/parserContext.h +++ b/ets2panda/parser/context/parserContext.h @@ -26,7 +26,7 @@ namespace panda::es2panda::parser { class Program; -enum class ParserStatus : uint32_t { +enum class ParserStatus : uint64_t { NO_OPTS = 0U, DIRECT_EVAL = 1U << 0U, @@ -65,6 +65,7 @@ enum class ParserStatus : uint32_t { IN_DEFAULT_IMPORTS = 1U << 29U, IN_EXTENSION_FUNCTION = 1U << 30U, FUNCTION_HAS_RETURN_STATEMENT = 1U << 31U, + IN_NAMESPACE = 1ULL << 32ULL, }; DEFINE_BITOPS(ParserStatus) diff --git a/ets2panda/parser/expressionParser.cpp b/ets2panda/parser/expressionParser.cpp index 09d10d86420b3643c2eb22ddbd82dfd9f3ae0726..ecfdfd2f8322f71a25530bd8504a1a551483f0e3 100644 --- a/ets2panda/parser/expressionParser.cpp +++ b/ets2panda/parser/expressionParser.cpp @@ -420,7 +420,9 @@ void ParserImpl::ValidateArrowFunctionRestParameter([[maybe_unused]] ir::SpreadE } } -ir::Expression *ParserImpl::ParseCoverParenthesizedExpressionAndArrowParameterList() +// NOLINTNEXTLINE(google-default-arguments) +ir::Expression *ParserImpl::ParseCoverParenthesizedExpressionAndArrowParameterList( + [[maybe_unused]] ExpressionParseFlags flags) { ASSERT(lexer_->GetToken().Type() == lexer::TokenType::PUNCTUATOR_LEFT_PARENTHESIS); lexer::SourcePosition start = lexer_->GetToken().Start(); @@ -492,6 +494,20 @@ void ParserImpl::CheckInvalidDestructuring(const ir::AstNode *object) const }); } +void ParserImpl::ValidateGroupedExpression(ir::Expression *lhs_expression) +{ + lexer::TokenType token_type = lexer_->GetToken().Type(); + if (lhs_expression->IsGrouped() && token_type != lexer::TokenType::PUNCTUATOR_ARROW) { + if (lhs_expression->IsSequenceExpression()) { + for (auto *seq : lhs_expression->AsSequenceExpression()->Sequence()) { + ValidateParenthesizedExpression(seq); + } + } else { + ValidateParenthesizedExpression(lhs_expression); + } + } +} + void ParserImpl::ValidateParenthesizedExpression(ir::Expression *lhs_expression) { switch (lhs_expression->Type()) { @@ -542,17 +558,9 @@ ir::Expression *ParserImpl::ParsePrefixAssertionExpression() ir::Expression *ParserImpl::ParseAssignmentExpression(ir::Expression *lhs_expression, ExpressionParseFlags flags) { - lexer::TokenType token_type = lexer_->GetToken().Type(); - if (lhs_expression->IsGrouped() && token_type != lexer::TokenType::PUNCTUATOR_ARROW) { - if (lhs_expression->IsSequenceExpression()) { - for (auto *seq : lhs_expression->AsSequenceExpression()->Sequence()) { - ValidateParenthesizedExpression(seq); - } - } else { - ValidateParenthesizedExpression(lhs_expression); - } - } + ValidateGroupedExpression(lhs_expression); + lexer::TokenType token_type = lexer_->GetToken().Type(); switch (token_type) { case lexer::TokenType::PUNCTUATOR_QUESTION_MARK: { lexer_->NextToken(); @@ -1191,7 +1199,7 @@ void ParserImpl::CreateAmendedBinaryExpression(ir::Expression *const left, ir::E SetAmendedChildExpression(right, binary_expr); } -ir::Expression *ParserImpl::ParseBinaryExpression(ir::Expression *left) +ir::Expression *ParserImpl::ParseBinaryExpression(ir::Expression *left, ExpressionParseFlags flags) { lexer::TokenType operator_type = lexer_->GetToken().Type(); ASSERT(lexer::Token::IsBinaryToken(operator_type)); @@ -1206,7 +1214,12 @@ ir::Expression *ParserImpl::ParseBinaryExpression(ir::Expression *left) lexer_->NextToken(); - ir::Expression *right_expr = ParseExpression(ExpressionParseFlags::DISALLOW_YIELD); + ExpressionParseFlags new_flags = ExpressionParseFlags::DISALLOW_YIELD; + if ((operator_type == lexer::TokenType::KEYW_INSTANCEOF) || ((flags & ExpressionParseFlags::INSTANCEOF) != 0)) { + new_flags |= ExpressionParseFlags::INSTANCEOF; + } + + ir::Expression *right_expr = ParseExpression(new_flags); ir::ConditionalExpression *conditional_expr = nullptr; if (right_expr->IsConditionalExpression() && !right_expr->IsGrouped()) { diff --git a/ets2panda/parser/parserFlags.h b/ets2panda/parser/parserFlags.h index 792114ad56d706b46972c37cd16270c3df4620e1..6d71e66beb91d4ecb995e92a8deac4f4a3304269 100644 --- a/ets2panda/parser/parserFlags.h +++ b/ets2panda/parser/parserFlags.h @@ -60,6 +60,7 @@ enum class ExpressionParseFlags : uint32_t { IMPORT = 1U << 10U, POTENTIAL_CLASS_LITERAL = 1U << 11U, IN_FOR = 1U << 12U, + INSTANCEOF = 1U << 13U, }; DEFINE_BITOPS(ExpressionParseFlags) diff --git a/ets2panda/parser/parserImpl.h b/ets2panda/parser/parserImpl.h index b6f43c047163d472e6f34e8547e23f66545060de..7d0d74e3d98931fc13b5191690aa639ef5f7b369 100644 --- a/ets2panda/parser/parserImpl.h +++ b/ets2panda/parser/parserImpl.h @@ -229,13 +229,15 @@ protected: // ExpressionParser.Cpp ir::Expression *ParseKeywordExpression(); - ir::Expression *ParseBinaryExpression(ir::Expression *left); + ir::Expression *ParseBinaryExpression(ir::Expression *left, + ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS); void ValidateUpdateExpression(ir::Expression *return_expression, bool is_chain_expression); ir::Expression *ParseMemberExpression(bool ignore_call_expression = false, ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS); ir::MetaProperty *ParsePotentialNewTarget(); void CheckInvalidDestructuring(const ir::AstNode *object) const; void ValidateParenthesizedExpression(ir::Expression *lhs_expression); + void ValidateGroupedExpression(ir::Expression *lhs_expression); ir::Expression *ParseImportExpression(); ir::Expression *ParseOptionalChain(ir::Expression *left_side_expr); ir::Expression *ParsePropertyKey(ExpressionParseFlags flags); @@ -482,7 +484,9 @@ protected: virtual void ThrowIllegalNewLineErrorAfterThrow(); virtual void ThrowIfVarDeclaration(VariableParsingFlags flags); virtual ir::Expression *ParsePrefixAssertionExpression(); - virtual ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList(); + // NOLINTNEXTLINE(google-default-arguments) + virtual ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList( + ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS); virtual void ThrowErrorIfStaticConstructor(ir::ModifierFlags flags); virtual std::tuple ParseComputedClassFieldOrIndexSignature(ir::Expression **prop_name); // NOLINTNEXTLINE(google-default-arguments) diff --git a/ets2panda/test/compiler/ets/StructTest1-expected.txt b/ets2panda/test/compiler/ets/StructTest1-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..50b26e476663ff7fed5b30f4c80a94562f4b5271 --- /dev/null +++ b/ets2panda/test/compiler/ets/StructTest1-expected.txt @@ -0,0 +1,1216 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "CommonStruct0", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 7 + }, + "end": { + "line": 16, + "column": 20 + } + } + }, + "typeParameters": { + "type": "TSTypeParameterDeclaration", + "params": [ + { + "type": "TSTypeParameter", + "name": { + "type": "Identifier", + "name": "K", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 21 + }, + "end": { + "line": 16, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 21 + }, + "end": { + "line": 16, + "column": 23 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 20 + }, + "end": { + "line": 16, + "column": 23 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "f", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 11 + }, + "end": { + "line": 17, + "column": 12 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 5, + "loc": { + "start": { + "line": 17, + "column": 20 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Int", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 14 + }, + "end": { + "line": 17, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 14 + }, + "end": { + "line": 17, + "column": 19 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 14 + }, + "end": { + "line": 17, + "column": 19 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 11 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "GetF", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 11 + }, + "end": { + "line": 18, + "column": 15 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "GetF", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 11 + }, + "end": { + "line": 18, + "column": 15 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Int", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 25 + } + } + }, + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ReturnStatement", + "argument": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "property": { + "type": "Identifier", + "name": "f", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 22 + }, + "end": { + "line": 19, + "column": 23 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 10 + }, + "end": { + "line": 19, + "column": 24 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 24 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 15 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 15 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 4 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 2 + }, + "end": { + "line": 21, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 24 + }, + "end": { + "line": 21, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 21, + "column": 2 + } + } + }, + { + "type": "ETSStructDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 8 + }, + "end": { + "line": 23, + "column": 10 + } + } + }, + "superClass": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CommonStruct0", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "typeParams": { + "type": "TSTypeParameterInstantiation", + "params": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "x", + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 6 + }, + "end": { + "line": 24, + "column": 7 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 24, + "column": 15 + }, + "end": { + "line": 24, + "column": 16 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Int", + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 12 + } + } + }, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 14 + } + } + }, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 14 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 6 + }, + "end": { + "line": 24, + "column": 16 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 25, + "column": 2 + }, + "end": { + "line": 25, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 23, + "column": 11 + }, + "end": { + "line": 25, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 1 + }, + "end": { + "line": 25, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 10 + }, + "end": { + "line": 27, + "column": 14 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 10 + }, + "end": { + "line": 27, + "column": 14 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "void", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 18 + }, + "end": { + "line": 27, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 18 + }, + "end": { + "line": 27, + "column": 24 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 18 + }, + "end": { + "line": 27, + "column": 24 + } + } + }, + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "a", + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 11 + }, + "end": { + "line": 28, + "column": 13 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 11 + }, + "end": { + "line": 28, + "column": 15 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 11 + }, + "end": { + "line": 28, + "column": 15 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 8 + }, + "end": { + "line": 28, + "column": 9 + } + } + }, + "init": { + "type": "ETSNewClassInstanceExpression", + "typeReference": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 20 + }, + "end": { + "line": 28, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 20 + }, + "end": { + "line": 28, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 20 + }, + "end": { + "line": 28, + "column": 23 + } + } + }, + "arguments": [], + "loc": { + "start": { + "line": 28, + "column": 16 + }, + "end": { + "line": 28, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 8 + }, + "end": { + "line": 28, + "column": 23 + } + } + } + ], + "kind": "let", + "loc": { + "start": { + "line": 28, + "column": 4 + }, + "end": { + "line": 28, + "column": 23 + } + } + } + ], + "loc": { + "start": { + "line": 27, + "column": 23 + }, + "end": { + "line": 29, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 14 + }, + "end": { + "line": 29, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 14 + }, + "end": { + "line": 29, + "column": 2 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 1 + }, + "end": { + "line": 29, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 29, + "column": 2 + } + } +} diff --git a/ets2panda/test/compiler/ets/StructTest1.ets b/ets2panda/test/compiler/ets/StructTest1.ets new file mode 100644 index 0000000000000000000000000000000000000000..711e89a2f60e391f9671898148513d59c63b3574 --- /dev/null +++ b/ets2panda/test/compiler/ets/StructTest1.ets @@ -0,0 +1,29 @@ +/* + * Copyright (c) 2021-2023 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. + */ + +class CommonStruct0 { + public f: Int = 5; + public GetF() : Int { + return this.f; + } +} + +struct CE { + x: Int = 1; +} + +function main(): void { + let a: CE = new CE; +} \ No newline at end of file diff --git a/ets2panda/test/compiler/ets/StructTest2-expected.txt b/ets2panda/test/compiler/ets/StructTest2-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..5e9b0511ba87bcf0eed5836f040fb28a52ed588d --- /dev/null +++ b/ets2panda/test/compiler/ets/StructTest2-expected.txt @@ -0,0 +1,1413 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "CommonStruct0", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 7 + }, + "end": { + "line": 16, + "column": 20 + } + } + }, + "typeParameters": { + "type": "TSTypeParameterDeclaration", + "params": [ + { + "type": "TSTypeParameter", + "name": { + "type": "Identifier", + "name": "K", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 21 + }, + "end": { + "line": 16, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 21 + }, + "end": { + "line": 16, + "column": 23 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 20 + }, + "end": { + "line": 16, + "column": 23 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "f", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 11 + }, + "end": { + "line": 17, + "column": 12 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 5, + "loc": { + "start": { + "line": 17, + "column": 20 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Int", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 14 + }, + "end": { + "line": 17, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 14 + }, + "end": { + "line": 17, + "column": 19 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 14 + }, + "end": { + "line": 17, + "column": 19 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 11 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "GetF", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 11 + }, + "end": { + "line": 18, + "column": 15 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "GetF", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 11 + }, + "end": { + "line": 18, + "column": 15 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Int", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 25 + } + } + }, + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ReturnStatement", + "argument": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "property": { + "type": "Identifier", + "name": "f", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 22 + }, + "end": { + "line": 19, + "column": 23 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 10 + }, + "end": { + "line": 19, + "column": 24 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 24 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 15 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 15 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 4 + }, + "end": { + "line": 20, + "column": 5 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 2 + }, + "end": { + "line": 21, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 24 + }, + "end": { + "line": 21, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 21, + "column": 2 + } + } + }, + { + "type": "ETSStructDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 8 + }, + "end": { + "line": 23, + "column": 10 + } + } + }, + "typeParameters": { + "type": "TSTypeParameterDeclaration", + "params": [ + { + "type": "TSTypeParameter", + "name": { + "type": "Identifier", + "name": "K", + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 11 + }, + "end": { + "line": 23, + "column": 12 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 11 + }, + "end": { + "line": 23, + "column": 13 + } + } + } + ], + "loc": { + "start": { + "line": 23, + "column": 10 + }, + "end": { + "line": 23, + "column": 13 + } + } + }, + "superClass": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CommonStruct0", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "typeParams": { + "type": "TSTypeParameterInstantiation", + "params": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "typeParams": { + "type": "TSTypeParameterInstantiation", + "params": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "K", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "x", + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 6 + }, + "end": { + "line": 24, + "column": 7 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "K", + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 10 + } + } + }, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 11 + } + } + }, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 11 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 6 + }, + "end": { + "line": 24, + "column": 11 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 25, + "column": 2 + }, + "end": { + "line": 25, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 23, + "column": 14 + }, + "end": { + "line": 25, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 1 + }, + "end": { + "line": 25, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 10 + }, + "end": { + "line": 27, + "column": 14 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 10 + }, + "end": { + "line": 27, + "column": 14 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "void", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 18 + }, + "end": { + "line": 27, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 18 + }, + "end": { + "line": 27, + "column": 24 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 18 + }, + "end": { + "line": 27, + "column": 24 + } + } + }, + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "a", + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 11 + }, + "end": { + "line": 28, + "column": 13 + } + } + }, + "typeParams": { + "type": "TSTypeParameterInstantiation", + "params": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Int", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 14 + }, + "end": { + "line": 28, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 14 + }, + "end": { + "line": 28, + "column": 18 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 14 + }, + "end": { + "line": 28, + "column": 18 + } + } + } + ], + "loc": { + "start": { + "line": 28, + "column": 13 + }, + "end": { + "line": 28, + "column": 18 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 11 + }, + "end": { + "line": 28, + "column": 20 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 11 + }, + "end": { + "line": 28, + "column": 20 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 8 + }, + "end": { + "line": 28, + "column": 9 + } + } + }, + "init": { + "type": "ETSNewClassInstanceExpression", + "typeReference": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "CE", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 25 + }, + "end": { + "line": 28, + "column": 27 + } + } + }, + "typeParams": { + "type": "TSTypeParameterInstantiation", + "params": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Int", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 28 + }, + "end": { + "line": 28, + "column": 31 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 28 + }, + "end": { + "line": 28, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 28 + }, + "end": { + "line": 28, + "column": 32 + } + } + } + ], + "loc": { + "start": { + "line": 28, + "column": 27 + }, + "end": { + "line": 28, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 25 + }, + "end": { + "line": 28, + "column": 33 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 25 + }, + "end": { + "line": 28, + "column": 33 + } + } + }, + "arguments": [], + "loc": { + "start": { + "line": 28, + "column": 21 + }, + "end": { + "line": 28, + "column": 35 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 8 + }, + "end": { + "line": 28, + "column": 35 + } + } + } + ], + "kind": "let", + "loc": { + "start": { + "line": 28, + "column": 4 + }, + "end": { + "line": 28, + "column": 35 + } + } + } + ], + "loc": { + "start": { + "line": 27, + "column": 23 + }, + "end": { + "line": 29, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 14 + }, + "end": { + "line": 29, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 14 + }, + "end": { + "line": 29, + "column": 2 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 1 + }, + "end": { + "line": 29, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 29, + "column": 2 + } + } +} diff --git a/ets2panda/test/compiler/ets/StructTest2.ets b/ets2panda/test/compiler/ets/StructTest2.ets new file mode 100644 index 0000000000000000000000000000000000000000..88f388511e85094318b35186973240488012fd58 --- /dev/null +++ b/ets2panda/test/compiler/ets/StructTest2.ets @@ -0,0 +1,29 @@ +/* + * Copyright (c) 2021-2023 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. + */ + +class CommonStruct0 { + public f: Int = 5; + public GetF() : Int { + return this.f; + } +} + +struct CE { + x: K; +} + +function main(): void { + let a: CE = new CE(); +} \ No newline at end of file diff --git a/ets2panda/test/compiler/ets/class_def_varargs_1-expected.txt b/ets2panda/test/compiler/ets/class_def_varargs_1-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..a040ec69693735dbc6f57651a4bfecfde3ac5c79 --- /dev/null +++ b/ets2panda/test/compiler/ets/class_def_varargs_1-expected.txt @@ -0,0 +1,916 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "Foo", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 7 + }, + "end": { + "line": 16, + "column": 10 + } + } + }, + "typeParameters": { + "type": "TSTypeParameterDeclaration", + "params": [ + { + "type": "TSTypeParameter", + "name": { + "type": "Identifier", + "name": "T", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 11 + }, + "end": { + "line": 16, + "column": 12 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 11 + }, + "end": { + "line": 16, + "column": 13 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 10 + }, + "end": { + "line": 16, + "column": 13 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [ + { + "type": "ETSParameterExpression", + "rest parameter": { + "type": "RestElement", + "argument": { + "type": "Identifier", + "name": "o", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 20 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "typeAnnotation": { + "type": "TSArrayType", + "elementType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "T", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 23 + }, + "end": { + "line": 17, + "column": 24 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 23 + }, + "end": { + "line": 17, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 23 + }, + "end": { + "line": 17, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 26 + }, + "end": { + "line": 17, + "column": 27 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 17 + }, + "end": { + "line": 17, + "column": 27 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 17 + }, + "end": { + "line": 17, + "column": 27 + } + } + } + ], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 17, + "column": 28 + }, + "end": { + "line": 17, + "column": 30 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 16 + }, + "end": { + "line": 17, + "column": 30 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 16 + }, + "end": { + "line": 17, + "column": 30 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 30 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "of", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 12 + }, + "end": { + "line": 18, + "column": 14 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "of", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 12 + }, + "end": { + "line": 18, + "column": 14 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [ + { + "type": "ETSParameterExpression", + "rest parameter": { + "type": "RestElement", + "argument": { + "type": "Identifier", + "name": "vl", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 21 + }, + "end": { + "line": 18, + "column": 23 + } + } + }, + "typeAnnotation": { + "type": "TSArrayType", + "elementType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 18, + "column": 25 + }, + "end": { + "line": 18, + "column": 28 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 30 + }, + "end": { + "line": 18, + "column": 31 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 18 + }, + "end": { + "line": 18, + "column": 31 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 18 + }, + "end": { + "line": 18, + "column": 31 + } + } + } + ], + "returnType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Foo", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 34 + }, + "end": { + "line": 18, + "column": 37 + } + } + }, + "typeParams": { + "type": "TSTypeParameterInstantiation", + "params": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "T", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 38 + }, + "end": { + "line": 18, + "column": 39 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 38 + }, + "end": { + "line": 18, + "column": 40 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 38 + }, + "end": { + "line": 18, + "column": 40 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 37 + }, + "end": { + "line": 18, + "column": 40 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 34 + }, + "end": { + "line": 18, + "column": 42 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 34 + }, + "end": { + "line": 18, + "column": 42 + } + } + }, + "typeParameters": { + "type": "TSTypeParameterDeclaration", + "params": [ + { + "type": "TSTypeParameter", + "name": { + "type": "Identifier", + "name": "T", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 15 + }, + "end": { + "line": 18, + "column": 16 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 15 + }, + "end": { + "line": 18, + "column": 17 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 18, + "column": 17 + } + } + }, + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "r", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 15 + }, + "end": { + "line": 19, + "column": 16 + } + } + }, + "init": { + "type": "ETSNewClassInstanceExpression", + "typeReference": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Foo", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 23 + }, + "end": { + "line": 19, + "column": 26 + } + } + }, + "typeParams": { + "type": "TSTypeParameterInstantiation", + "params": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "T", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 27 + }, + "end": { + "line": 19, + "column": 28 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 27 + }, + "end": { + "line": 19, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 27 + }, + "end": { + "line": 19, + "column": 29 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 26 + }, + "end": { + "line": 19, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 23 + }, + "end": { + "line": 19, + "column": 30 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 23 + }, + "end": { + "line": 19, + "column": 30 + } + } + }, + "arguments": [], + "loc": { + "start": { + "line": 19, + "column": 19 + }, + "end": { + "line": 20, + "column": 15 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 15 + }, + "end": { + "line": 20, + "column": 15 + } + } + } + ], + "kind": "const", + "loc": { + "start": { + "line": 19, + "column": 9 + }, + "end": { + "line": 20, + "column": 15 + } + } + }, + { + "type": "ReturnStatement", + "argument": { + "type": "Identifier", + "name": "r", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 16 + }, + "end": { + "line": 20, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 17 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 41 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 5 + }, + "end": { + "line": 21, + "column": 6 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 14 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 23, + "column": 1 + } + } +} diff --git a/ets2panda/test/compiler/ets/class_def_varargs_1.ets b/ets2panda/test/compiler/ets/class_def_varargs_1.ets new file mode 100644 index 0000000000000000000000000000000000000000..1bfff1689091f24049947c64dd6c31f370a55ce7 --- /dev/null +++ b/ets2panda/test/compiler/ets/class_def_varargs_1.ets @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2023 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. + */ + +class Foo { + constructor(...o: T[]) {} + static of(...vl: int[]) : Foo { + const r = new Foo() + return r + } +} diff --git a/ets2panda/test/compiler/ets/class_def_varargs_2-expected.txt b/ets2panda/test/compiler/ets/class_def_varargs_2-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..6cdfc1a60f600ee63e897c7bb670488f67b6bad7 --- /dev/null +++ b/ets2panda/test/compiler/ets/class_def_varargs_2-expected.txt @@ -0,0 +1,721 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 7 + }, + "end": { + "line": 16, + "column": 8 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [ + { + "type": "ETSParameterExpression", + "rest parameter": { + "type": "RestElement", + "argument": { + "type": "Identifier", + "name": "items", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 21 + }, + "end": { + "line": 17, + "column": 26 + } + } + }, + "typeAnnotation": { + "type": "TSArrayType", + "elementType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Object", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 28 + }, + "end": { + "line": 17, + "column": 34 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 28 + }, + "end": { + "line": 17, + "column": 35 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 28 + }, + "end": { + "line": 17, + "column": 35 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 36 + }, + "end": { + "line": 17, + "column": 37 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 17 + }, + "end": { + "line": 17, + "column": 37 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 17 + }, + "end": { + "line": 17, + "column": 37 + } + } + } + ], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 17, + "column": 37 + }, + "end": { + "line": 17, + "column": 39 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 16 + }, + "end": { + "line": 17, + "column": 39 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 16 + }, + "end": { + "line": 17, + "column": 39 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 39 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 9 + }, + "end": { + "line": 18, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 18, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 10 + }, + "end": { + "line": 20, + "column": 14 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 10 + }, + "end": { + "line": 20, + "column": 14 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "a", + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 9 + }, + "end": { + "line": 21, + "column": 10 + } + } + }, + "init": { + "type": "ETSNewClassInstanceExpression", + "typeReference": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 17 + }, + "end": { + "line": 21, + "column": 18 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 17 + }, + "end": { + "line": 21, + "column": 19 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 17 + }, + "end": { + "line": 21, + "column": 19 + } + } + }, + "arguments": [], + "loc": { + "start": { + "line": 21, + "column": 13 + }, + "end": { + "line": 21, + "column": 19 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 9 + }, + "end": { + "line": 21, + "column": 19 + } + } + } + ], + "kind": "let", + "loc": { + "start": { + "line": 21, + "column": 5 + }, + "end": { + "line": 21, + "column": 19 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "AssignmentExpression", + "operator": "=", + "left": { + "type": "Identifier", + "name": "a", + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 5 + }, + "end": { + "line": 22, + "column": 6 + } + } + }, + "right": { + "type": "ETSNewClassInstanceExpression", + "typeReference": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 13 + }, + "end": { + "line": 22, + "column": 14 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 13 + }, + "end": { + "line": 22, + "column": 15 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 13 + }, + "end": { + "line": 22, + "column": 15 + } + } + }, + "arguments": [ + { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 22, + "column": 15 + }, + "end": { + "line": 22, + "column": 16 + } + } + }, + { + "type": "NumberLiteral", + "value": 2, + "loc": { + "start": { + "line": 22, + "column": 18 + }, + "end": { + "line": 22, + "column": 19 + } + } + }, + { + "type": "NumberLiteral", + "value": 3, + "loc": { + "start": { + "line": 22, + "column": 21 + }, + "end": { + "line": 22, + "column": 22 + } + } + } + ], + "loc": { + "start": { + "line": 22, + "column": 9 + }, + "end": { + "line": 23, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 5 + }, + "end": { + "line": 23, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 5 + }, + "end": { + "line": 23, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 20, + "column": 17 + }, + "end": { + "line": 23, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 14 + }, + "end": { + "line": 23, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 14 + }, + "end": { + "line": 23, + "column": 2 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 1 + }, + "end": { + "line": 23, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 24, + "column": 1 + } + } +} diff --git a/ets2panda/test/compiler/ets/class_def_varargs_2.ets b/ets2panda/test/compiler/ets/class_def_varargs_2.ets new file mode 100644 index 0000000000000000000000000000000000000000..46f74c9970d3c0abd6b8a1824a0f8fb5c1a598bf --- /dev/null +++ b/ets2panda/test/compiler/ets/class_def_varargs_2.ets @@ -0,0 +1,23 @@ +/* + * Copyright (c) 2023 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. + */ + +class A { + constructor(... items :Object[]){} +} + +function main() { + let a = new A; + a = new A(1, 2, 3) +} diff --git a/ets2panda/test/compiler/ets/override18-expected.txt b/ets2panda/test/compiler/ets/override18-expected.txt index 198ef735ad261d2facf5a02cc7b7419c8013d6ab..a3d01a0fb6531e631db5cadfe0e58d4eefa8f134 100644 --- a/ets2panda/test/compiler/ets/override18-expected.txt +++ b/ets2panda/test/compiler/ets/override18-expected.txt @@ -174,7 +174,7 @@ "type": "MethodDefinition", "key": { "type": "Identifier", - "name": "hashCode", + "name": "$_hashCode", "decorators": [], "loc": { "start": { @@ -183,7 +183,7 @@ }, "end": { "line": 20, - "column": 13 + "column": 15 } } }, @@ -198,7 +198,7 @@ "type": "ScriptFunction", "id": { "type": "Identifier", - "name": "hashCode", + "name": "$_hashCode", "decorators": [], "loc": { "start": { @@ -207,7 +207,7 @@ }, "end": { "line": 20, - "column": 13 + "column": 15 } } }, @@ -220,11 +220,11 @@ "loc": { "start": { "line": 20, - "column": 16 + "column": 18 }, "end": { "line": 20, - "column": 19 + "column": 21 } } }, @@ -263,7 +263,7 @@ "loc": { "start": { "line": 20, - "column": 19 + "column": 21 }, "end": { "line": 22, @@ -274,7 +274,7 @@ "loc": { "start": { "line": 20, - "column": 13 + "column": 15 }, "end": { "line": 22, @@ -285,7 +285,7 @@ "loc": { "start": { "line": 20, - "column": 13 + "column": 15 }, "end": { "line": 22, @@ -907,7 +907,7 @@ }, "property": { "type": "Identifier", - "name": "hashCode", + "name": "$_hashCode", "decorators": [], "loc": { "start": { @@ -916,7 +916,7 @@ }, "end": { "line": 30, - "column": 22 + "column": 24 } } }, @@ -929,7 +929,7 @@ }, "end": { "line": 30, - "column": 22 + "column": 24 } } }, @@ -942,7 +942,7 @@ }, "end": { "line": 30, - "column": 24 + "column": 26 } } }, @@ -952,11 +952,11 @@ "loc": { "start": { "line": 30, - "column": 28 + "column": 30 }, "end": { "line": 30, - "column": 29 + "column": 31 } } }, @@ -967,7 +967,7 @@ }, "end": { "line": 30, - "column": 29 + "column": 31 } } }, @@ -979,7 +979,7 @@ }, "end": { "line": 30, - "column": 29 + "column": 31 } } } diff --git a/ets2panda/test/compiler/ets/override18.ets b/ets2panda/test/compiler/ets/override18.ets index f822161147eaacbe0a090193f48a14175aa6faf3..e6494ec0c68e3b510978b279b4be6af56ef5576d 100644 --- a/ets2panda/test/compiler/ets/override18.ets +++ b/ets2panda/test/compiler/ets/override18.ets @@ -17,7 +17,7 @@ interface J{ toString(): String { return ""; } - hashCode():int{ + $_hashCode():int{ return 4; } } @@ -27,5 +27,5 @@ class JImpl implements J{ function main(): void { let o: JImpl = new JImpl() - assert o.hashCode() == 4 + assert o.$_hashCode() == 4 } diff --git a/ets2panda/test/compiler/ets/override19-expected.txt b/ets2panda/test/compiler/ets/override19-expected.txt index b7d5f654a9fea727af8638d2605d02b2458c2037..c84d6058093bd1380b95849f3d614c84b4a86138 100644 --- a/ets2panda/test/compiler/ets/override19-expected.txt +++ b/ets2panda/test/compiler/ets/override19-expected.txt @@ -189,7 +189,7 @@ "type": "MethodDefinition", "key": { "type": "Identifier", - "name": "hashCode", + "name": "$_hashCode", "decorators": [], "loc": { "start": { @@ -198,7 +198,7 @@ }, "end": { "line": 20, - "column": 22 + "column": 24 } } }, @@ -213,7 +213,7 @@ "type": "ScriptFunction", "id": { "type": "Identifier", - "name": "hashCode", + "name": "$_hashCode", "decorators": [], "loc": { "start": { @@ -222,7 +222,7 @@ }, "end": { "line": 20, - "column": 22 + "column": 24 } } }, @@ -235,11 +235,11 @@ "loc": { "start": { "line": 20, - "column": 26 + "column": 28 }, "end": { "line": 20, - "column": 29 + "column": 31 } } }, @@ -277,7 +277,7 @@ "loc": { "start": { "line": 20, - "column": 30 + "column": 32 }, "end": { "line": 22, @@ -288,7 +288,7 @@ "loc": { "start": { "line": 20, - "column": 22 + "column": 24 }, "end": { "line": 22, @@ -299,7 +299,7 @@ "loc": { "start": { "line": 20, - "column": 22 + "column": 24 }, "end": { "line": 22, @@ -983,7 +983,7 @@ }, "property": { "type": "Identifier", - "name": "hashCode", + "name": "$_hashCode", "decorators": [], "loc": { "start": { @@ -992,7 +992,7 @@ }, "end": { "line": 30, - "column": 22 + "column": 24 } } }, @@ -1005,7 +1005,7 @@ }, "end": { "line": 30, - "column": 22 + "column": 24 } } }, @@ -1018,7 +1018,7 @@ }, "end": { "line": 30, - "column": 24 + "column": 26 } } }, @@ -1028,11 +1028,11 @@ "loc": { "start": { "line": 30, - "column": 28 + "column": 30 }, "end": { "line": 30, - "column": 29 + "column": 31 } } }, @@ -1043,7 +1043,7 @@ }, "end": { "line": 30, - "column": 29 + "column": 31 } } }, @@ -1055,7 +1055,7 @@ }, "end": { "line": 30, - "column": 29 + "column": 31 } } } diff --git a/ets2panda/test/compiler/ets/override19.ets b/ets2panda/test/compiler/ets/override19.ets index 45fb347bb3336291c29c35c81105b83c0a99de23..81a746586769ae009e53238a0f9dac6fbf5c57fb 100644 --- a/ets2panda/test/compiler/ets/override19.ets +++ b/ets2panda/test/compiler/ets/override19.ets @@ -17,7 +17,7 @@ class O{ override toString(): String { return ""; } - override hashCode(): int { + override $_hashCode(): int { return 4; } } @@ -27,5 +27,5 @@ class OExt extends O{ function main(): void { let o: OExt = new OExt() - assert o.hashCode() == 4 + assert o.$_hashCode() == 4 } diff --git a/ets2panda/test/parser/ets/class-instance-field-redeclaration-expected.txt b/ets2panda/test/parser/ets/class-instance-field-redeclaration-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..95028a2c1860cf8bdea912b8cb5f93740a97a585 --- /dev/null +++ b/ets2panda/test/parser/ets/class-instance-field-redeclaration-expected.txt @@ -0,0 +1 @@ +SyntaxError: Variable 'foo' has already been declared. [class-instance-field-redeclaration.ets:18:5] diff --git a/ets2panda/test/parser/ets/class-instance-field-redeclaration.ets b/ets2panda/test/parser/ets/class-instance-field-redeclaration.ets new file mode 100644 index 0000000000000000000000000000000000000000..3f2f82c517b33608f37ac1bd6ad69a7d93e892c0 --- /dev/null +++ b/ets2panda/test/parser/ets/class-instance-field-redeclaration.ets @@ -0,0 +1,19 @@ +/* + * Copyright (c) 2023 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. + */ + +class C { + foo: int = 10; + foo: int = 20; +} diff --git a/ets2panda/test/parser/ets/class-static-field-redeclaration-expected.txt b/ets2panda/test/parser/ets/class-static-field-redeclaration-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..7b1e62f3048c64ed08015624b19a4a938cf5837b --- /dev/null +++ b/ets2panda/test/parser/ets/class-static-field-redeclaration-expected.txt @@ -0,0 +1 @@ +SyntaxError: Variable 'foo' has already been declared. [class-static-field-redeclaration.ets:18:12] diff --git a/ets2panda/test/parser/ets/class-static-field-redeclaration.ets b/ets2panda/test/parser/ets/class-static-field-redeclaration.ets new file mode 100644 index 0000000000000000000000000000000000000000..3c6d509fc05a5bc2e70945eae2c76ca710ec8f68 --- /dev/null +++ b/ets2panda/test/parser/ets/class-static-field-redeclaration.ets @@ -0,0 +1,19 @@ +/* + * Copyright (c) 2023 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. + */ + +class C { + static foo: int = 10; + static foo: int = 20; +} diff --git a/ets2panda/test/parser/ets/declare_enum-expected.txt b/ets2panda/test/parser/ets/declare_enum-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..99104b74758a74b7f127841dc9f231d9f0aafb01 --- /dev/null +++ b/ets2panda/test/parser/ets/declare_enum-expected.txt @@ -0,0 +1,268 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSEnumDeclaration", + "id": { + "type": "Identifier", + "name": "Enum", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 14 + }, + "end": { + "line": 16, + "column": 18 + } + } + }, + "members": [ + { + "type": "TSEnumMember", + "id": { + "type": "Identifier", + "name": "AAA", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "initializer": { + "type": "NumberLiteral", + "value": 0, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + { + "type": "TSEnumMember", + "id": { + "type": "Identifier", + "name": "BBB", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 5 + }, + "end": { + "line": 18, + "column": 8 + } + } + }, + "initializer": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 5 + }, + "end": { + "line": 18, + "column": 8 + } + } + } + ], + "const": false, + "loc": { + "start": { + "line": 16, + "column": 9 + }, + "end": { + "line": 19, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 20, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/declare_enum.ets b/ets2panda/test/parser/ets/declare_enum.ets new file mode 100644 index 0000000000000000000000000000000000000000..44b78d6bf6581f4ac7098e0a3aa3abe357d64772 --- /dev/null +++ b/ets2panda/test/parser/ets/declare_enum.ets @@ -0,0 +1,19 @@ +/* + * Copyright (c) 2022 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 enum Enum { + AAA, + BBB +} diff --git a/ets2panda/test/parser/ets/declare_namespace-expected.txt b/ets2panda/test/parser/ets/declare_namespace-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..bd586f4105cecd7b674c906123d9fdf57c913a42 --- /dev/null +++ b/ets2panda/test/parser/ets/declare_namespace-expected.txt @@ -0,0 +1,290 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "name", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 19 + }, + "end": { + "line": 16, + "column": 23 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 26 + }, + "end": { + "line": 16, + "column": 26 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 24 + }, + "end": { + "line": 16, + "column": 26 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 9 + }, + "end": { + "line": 16, + "column": 26 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 17, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/declare_namespace.ets b/ets2panda/test/parser/ets/declare_namespace.ets new file mode 100644 index 0000000000000000000000000000000000000000..47849cb880b375583deec12868f6893ae8af9857 --- /dev/null +++ b/ets2panda/test/parser/ets/declare_namespace.ets @@ -0,0 +1,16 @@ +/* + * Copyright (c) 2022 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 namespace name {} diff --git a/ets2panda/test/parser/ets/declare_namespace_2-expected.txt b/ets2panda/test/parser/ets/declare_namespace_2-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..ef0198eda6f78a50a67e0f22eb177e38cd1a6393 --- /dev/null +++ b/ets2panda/test/parser/ets/declare_namespace_2-expected.txt @@ -0,0 +1,411 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "NAME", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 19 + }, + "end": { + "line": 16, + "column": 23 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "foo", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "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": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "void", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 11 + }, + "end": { + "line": 17, + "column": 15 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 11 + }, + "end": { + "line": 17, + "column": 16 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 11 + }, + "end": { + "line": 17, + "column": 16 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 8 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 8 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 2 + }, + "end": { + "line": 18, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 24 + }, + "end": { + "line": 18, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 9 + }, + "end": { + "line": 18, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 19, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/declare_namespace_2.ets b/ets2panda/test/parser/ets/declare_namespace_2.ets new file mode 100644 index 0000000000000000000000000000000000000000..fb6d637df3eac7563422b79a288c52fc74565473 --- /dev/null +++ b/ets2panda/test/parser/ets/declare_namespace_2.ets @@ -0,0 +1,18 @@ +/* + * Copyright (c) 2022 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 namespace NAME { + foo():void; +} diff --git a/ets2panda/test/parser/ets/declare_type-expected.txt b/ets2panda/test/parser/ets/declare_type-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..0259aa62df8b138cf76932dc593730bc23d6c52e --- /dev/null +++ b/ets2panda/test/parser/ets/declare_type-expected.txt @@ -0,0 +1,194 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "t", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 14 + }, + "end": { + "line": 16, + "column": 15 + } + } + }, + "typeAnnotation": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 9 + }, + "end": { + "line": 16, + "column": 22 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 17, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/declare_type.ets b/ets2panda/test/parser/ets/declare_type.ets new file mode 100644 index 0000000000000000000000000000000000000000..0ee4caa1c1977bae58858e33346e55a75a01ccb3 --- /dev/null +++ b/ets2panda/test/parser/ets/declare_type.ets @@ -0,0 +1,16 @@ +/* + * Copyright (c) 2022 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 type t = int; diff --git a/ets2panda/test/parser/ets/import_tests/check_exported_default_class-expected.txt b/ets2panda/test/parser/ets/import_tests/check_exported_default_class-expected.txt index d13c5c166f781ef1cddef635b08527d0286b3a61..b91e82403884a057a0ac77e059b2601800c70ee6 100644 --- a/ets2panda/test/parser/ets/import_tests/check_exported_default_class-expected.txt +++ b/ets2panda/test/parser/ets/import_tests/check_exported_default_class-expected.txt @@ -13,7 +13,7 @@ }, "end": { "line": 16, - "column": 76 + "column": 75 } } }, @@ -54,7 +54,7 @@ }, "end": { "line": 16, - "column": 77 + "column": 76 } } }, diff --git a/ets2panda/test/parser/ets/import_tests/check_exported_default_class.ets b/ets2panda/test/parser/ets/import_tests/check_exported_default_class.ets index 03c02fe1ec2157fb38b15c0536a251300e284f19..836eeba03d6ec92ad8a414e90fe80b07c1733907 100644 --- a/ets2panda/test/parser/ets/import_tests/check_exported_default_class.ets +++ b/ets2panda/test/parser/ets/import_tests/check_exported_default_class.ets @@ -13,7 +13,7 @@ * limitations under the License. */ -import ExportDefaultClass from "import_tests/modules/struct_default_module"; +import ExportDefaultClass from "import_tests/modules/class_default_module"; function main() { let test_class: ExportDefaultClass = new ExportDefaultClass(); diff --git a/ets2panda/test/parser/ets/import_tests/import_interface_test-expected.txt b/ets2panda/test/parser/ets/import_tests/import_interface_test-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..dcc9310ba5ef1afbe2753680ff45a4c449de199e --- /dev/null +++ b/ets2panda/test/parser/ets/import_tests/import_interface_test-expected.txt @@ -0,0 +1,1162 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ImportDeclaration", + "source": { + "type": "StringLiteral", + "value": "./", + "loc": { + "start": { + "line": 16, + "column": 25 + }, + "end": { + "line": 16, + "column": 52 + } + } + }, + "specifiers": [ + { + "type": "ImportSpecifier", + "local": { + "type": "Identifier", + "name": "MyClass", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 10 + }, + "end": { + "line": 16, + "column": 17 + } + } + }, + "imported": { + "type": "Identifier", + "name": "MyClass", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 10 + }, + "end": { + "line": 16, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 10 + }, + "end": { + "line": 16, + "column": 17 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 16, + "column": 53 + } + } + }, + { + "type": "ImportDeclaration", + "source": { + "type": "StringLiteral", + "value": "./", + "loc": { + "start": { + "line": 17, + "column": 31 + }, + "end": { + "line": 17, + "column": 58 + } + } + }, + "specifiers": [ + { + "type": "ImportSpecifier", + "local": { + "type": "Identifier", + "name": "SameInterface", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 10 + }, + "end": { + "line": 17, + "column": 23 + } + } + }, + "imported": { + "type": "Identifier", + "name": "SameInterface", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 10 + }, + "end": { + "line": 17, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 10 + }, + "end": { + "line": 17, + "column": 23 + } + } + } + ], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 59 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "MyClass2", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 7 + }, + "end": { + "line": 19, + "column": 15 + } + } + }, + "superClass": null, + "implements": [ + { + "type": "TSClassImplements", + "expression": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "SameInterface", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 27 + }, + "end": { + "line": 19, + "column": 40 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 27 + }, + "end": { + "line": 19, + "column": 42 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 27 + }, + "end": { + "line": 19, + "column": 42 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 27 + }, + "end": { + "line": 19, + "column": 42 + } + } + } + ], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 5 + }, + "end": { + "line": 20, + "column": 9 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 5 + }, + "end": { + "line": 20, + "column": 9 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 20, + "column": 13 + }, + "end": { + "line": 20, + "column": 16 + } + } + }, + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ReturnStatement", + "argument": { + "type": "NumberLiteral", + "value": 2, + "loc": { + "start": { + "line": 21, + "column": 16 + }, + "end": { + "line": 21, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 9 + }, + "end": { + "line": 21, + "column": 18 + } + } + } + ], + "loc": { + "start": { + "line": 20, + "column": 17 + }, + "end": { + "line": 22, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 22, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 22, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 5 + }, + "end": { + "line": 22, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 2 + }, + "end": { + "line": 23, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 41 + }, + "end": { + "line": 23, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 1 + }, + "end": { + "line": 23, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 25, + "column": 10 + }, + "end": { + "line": 25, + "column": 14 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "main", + "decorators": [], + "loc": { + "start": { + "line": 25, + "column": 10 + }, + "end": { + "line": 25, + "column": 14 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "myclass1", + "decorators": [], + "loc": { + "start": { + "line": 26, + "column": 11 + }, + "end": { + "line": 26, + "column": 19 + } + } + }, + "init": { + "type": "ETSNewClassInstanceExpression", + "typeReference": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "MyClass", + "decorators": [], + "loc": { + "start": { + "line": 26, + "column": 26 + }, + "end": { + "line": 26, + "column": 33 + } + } + }, + "loc": { + "start": { + "line": 26, + "column": 26 + }, + "end": { + "line": 26, + "column": 34 + } + } + }, + "loc": { + "start": { + "line": 26, + "column": 26 + }, + "end": { + "line": 26, + "column": 34 + } + } + }, + "arguments": [], + "loc": { + "start": { + "line": 26, + "column": 22 + }, + "end": { + "line": 26, + "column": 36 + } + } + }, + "loc": { + "start": { + "line": 26, + "column": 11 + }, + "end": { + "line": 26, + "column": 36 + } + } + } + ], + "kind": "const", + "loc": { + "start": { + "line": 26, + "column": 5 + }, + "end": { + "line": 26, + "column": 36 + } + } + }, + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "myclass2", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 11 + }, + "end": { + "line": 27, + "column": 19 + } + } + }, + "init": { + "type": "ETSNewClassInstanceExpression", + "typeReference": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "MyClass2", + "decorators": [], + "loc": { + "start": { + "line": 27, + "column": 26 + }, + "end": { + "line": 27, + "column": 34 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 26 + }, + "end": { + "line": 27, + "column": 35 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 26 + }, + "end": { + "line": 27, + "column": 35 + } + } + }, + "arguments": [], + "loc": { + "start": { + "line": 27, + "column": 22 + }, + "end": { + "line": 27, + "column": 37 + } + } + }, + "loc": { + "start": { + "line": 27, + "column": 11 + }, + "end": { + "line": 27, + "column": 37 + } + } + } + ], + "kind": "const", + "loc": { + "start": { + "line": 27, + "column": 5 + }, + "end": { + "line": 27, + "column": 37 + } + } + }, + { + "type": "IfStatement", + "test": { + "type": "BinaryExpression", + "operator": "==", + "left": { + "type": "BinaryExpression", + "operator": "+", + "left": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "Identifier", + "name": "myclass1", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 10 + }, + "end": { + "line": 28, + "column": 18 + } + } + }, + "property": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 19 + }, + "end": { + "line": 28, + "column": 23 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 28, + "column": 10 + }, + "end": { + "line": 28, + "column": 23 + } + } + }, + "arguments": [], + "optional": false, + "loc": { + "start": { + "line": 28, + "column": 10 + }, + "end": { + "line": 28, + "column": 25 + } + } + }, + "right": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "Identifier", + "name": "myclass2", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 28 + }, + "end": { + "line": 28, + "column": 36 + } + } + }, + "property": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 28, + "column": 37 + }, + "end": { + "line": 28, + "column": 41 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 28, + "column": 28 + }, + "end": { + "line": 28, + "column": 41 + } + } + }, + "arguments": [], + "optional": false, + "loc": { + "start": { + "line": 28, + "column": 28 + }, + "end": { + "line": 28, + "column": 43 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 9 + }, + "end": { + "line": 28, + "column": 44 + } + } + }, + "right": { + "type": "NumberLiteral", + "value": 3, + "loc": { + "start": { + "line": 28, + "column": 48 + }, + "end": { + "line": 28, + "column": 49 + } + } + }, + "loc": { + "start": { + "line": 28, + "column": 9 + }, + "end": { + "line": 28, + "column": 49 + } + } + }, + "consequent": { + "type": "BlockStatement", + "statements": [ + { + "type": "ReturnStatement", + "argument": { + "type": "NumberLiteral", + "value": 0, + "loc": { + "start": { + "line": 29, + "column": 16 + }, + "end": { + "line": 29, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 29, + "column": 9 + }, + "end": { + "line": 29, + "column": 17 + } + } + } + ], + "loc": { + "start": { + "line": 28, + "column": 51 + }, + "end": { + "line": 30, + "column": 6 + } + } + }, + "alternate": null, + "loc": { + "start": { + "line": 28, + "column": 5 + }, + "end": { + "line": 30, + "column": 6 + } + } + }, + { + "type": "ReturnStatement", + "argument": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 31, + "column": 12 + }, + "end": { + "line": 31, + "column": 13 + } + } + }, + "loc": { + "start": { + "line": 31, + "column": 5 + }, + "end": { + "line": 31, + "column": 13 + } + } + } + ], + "loc": { + "start": { + "line": 25, + "column": 17 + }, + "end": { + "line": 32, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 25, + "column": 14 + }, + "end": { + "line": 32, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 25, + "column": 14 + }, + "end": { + "line": 32, + "column": 2 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 25, + "column": 1 + }, + "end": { + "line": 32, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 33, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/import_tests/import_interface_test.ets b/ets2panda/test/parser/ets/import_tests/import_interface_test.ets new file mode 100644 index 0000000000000000000000000000000000000000..24a8dd3bb411778ea1e44f0a0d7738146c7bf14a --- /dev/null +++ b/ets2panda/test/parser/ets/import_tests/import_interface_test.ets @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2023 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. + */ + +import { MyClass } from './import_interface_test_2'; +import { SameInterface } from './import_interface_test_1'; + +class MyClass2 implements SameInterface { + test(): int { + return 2; + } +} + +function main() { + const myclass1 = new MyClass(); + const myclass2 = new MyClass2(); + if ((myclass1.test() + myclass2.test()) == 3) { + return 0 + } + return 1 +} diff --git a/ets2panda/test/parser/ets/import_tests/import_interface_test_1-expected.txt b/ets2panda/test/parser/ets/import_tests/import_interface_test_1-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..ba2937c49319a4f8c54bcaa1e855a2468567fc0b --- /dev/null +++ b/ets2panda/test/parser/ets/import_tests/import_interface_test_1-expected.txt @@ -0,0 +1,291 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSInterfaceDeclaration", + "body": { + "type": "TSInterfaceBody", + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 9 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 9 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 17, + "column": 12 + }, + "end": { + "line": 17, + "column": 15 + } + } + }, + "declare": true, + "loc": { + "start": { + "line": 17, + "column": 9 + }, + "end": { + "line": 17, + "column": 15 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 9 + }, + "end": { + "line": 17, + "column": 15 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 5 + }, + "end": { + "line": 17, + "column": 16 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 32 + }, + "end": { + "line": 18, + "column": 2 + } + } + }, + "id": { + "type": "Identifier", + "name": "SameInterface", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 31 + } + } + }, + "extends": [], + "loc": { + "start": { + "line": 16, + "column": 8 + }, + "end": { + "line": 19, + "column": 1 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 19, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/import_tests/import_interface_test_1.ets b/ets2panda/test/parser/ets/import_tests/import_interface_test_1.ets new file mode 100644 index 0000000000000000000000000000000000000000..6dd7e5a2672bbce30e8f3effe84895885eda056c --- /dev/null +++ b/ets2panda/test/parser/ets/import_tests/import_interface_test_1.ets @@ -0,0 +1,18 @@ +/* + * Copyright (c) 2023 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. + */ + +export interface SameInterface { + test():int; +} diff --git a/ets2panda/test/parser/ets/import_tests/import_interface_test_2-expected.txt b/ets2panda/test/parser/ets/import_tests/import_interface_test_2-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..016b5bf1883430813a4aa70878d53911445406a7 --- /dev/null +++ b/ets2panda/test/parser/ets/import_tests/import_interface_test_2-expected.txt @@ -0,0 +1,552 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ImportDeclaration", + "source": { + "type": "StringLiteral", + "value": "./", + "loc": { + "start": { + "line": 16, + "column": 31 + }, + "end": { + "line": 16, + "column": 58 + } + } + }, + "specifiers": [ + { + "type": "ImportSpecifier", + "local": { + "type": "Identifier", + "name": "SameInterface", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 10 + }, + "end": { + "line": 16, + "column": 23 + } + } + }, + "imported": { + "type": "Identifier", + "name": "SameInterface", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 10 + }, + "end": { + "line": 16, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 10 + }, + "end": { + "line": 16, + "column": 23 + } + } + } + ], + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 16, + "column": 59 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "MyClass", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 18, + "column": 21 + } + } + }, + "superClass": null, + "implements": [ + { + "type": "TSClassImplements", + "expression": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "SameInterface", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 33 + }, + "end": { + "line": 18, + "column": 46 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 33 + }, + "end": { + "line": 18, + "column": 48 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 33 + }, + "end": { + "line": 18, + "column": 48 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 33 + }, + "end": { + "line": 18, + "column": 48 + } + } + } + ], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 19, + "column": 9 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "test", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 19, + "column": 9 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 19, + "column": 13 + }, + "end": { + "line": 19, + "column": 16 + } + } + }, + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ReturnStatement", + "argument": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 16 + }, + "end": { + "line": 20, + "column": 17 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 18 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 9 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 9 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 2 + }, + "end": { + "line": 22, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 47 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 8 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 22, + "column": 2 + } + } +} diff --git a/ets2panda/test/parser/ets/import_tests/import_interface_test_2.ets b/ets2panda/test/parser/ets/import_tests/import_interface_test_2.ets new file mode 100644 index 0000000000000000000000000000000000000000..44c393de3388fb4add7b87545ca3087190f08e41 --- /dev/null +++ b/ets2panda/test/parser/ets/import_tests/import_interface_test_2.ets @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2023 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. + */ + +import { SameInterface } from './import_interface_test_1'; + +export class MyClass implements SameInterface { + test(): int { + return 1; + } +} \ No newline at end of file diff --git a/ets2panda/test/parser/ets/test-type-alias-call1-expected.txt b/ets2panda/test/parser/ets/test-type-alias-call1-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..94885993386b408d4ef41c61022be77705ea7f4f --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call1-expected.txt @@ -0,0 +1,645 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 6 + }, + "end": { + "line": 16, + "column": 14 + } + } + }, + "typeAnnotation": { + "type": "ETSFunctionType", + "params": [ + { + "type": "ETSParameterExpression", + "name": { + "type": "Identifier", + "name": "n", + "typeAnnotation": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 21 + }, + "end": { + "line": 16, + "column": 24 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 24 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 24 + } + } + } + ], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 29 + }, + "end": { + "line": 16, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 17 + }, + "end": { + "line": 16, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 17, + "column": 6 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 12 + }, + "end": { + "line": 18, + "column": 20 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 22 + }, + "end": { + "line": 18, + "column": 30 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 22 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 22 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 12 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 12 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 12 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 13 + } + } + }, + "property": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 14 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + "arguments": [ + { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 23 + }, + "end": { + "line": 20, + "column": 24 + } + } + } + ], + "optional": false, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 25 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 24 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 21 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 21 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 2 + }, + "end": { + "line": 22, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 17, + "column": 9 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 23, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call1.ets b/ets2panda/test/parser/ets/test-type-alias-call1.ets new file mode 100644 index 0000000000000000000000000000000000000000..2899e73c5241f48ca95942cd2126b7744cbca842 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call1.ets @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2022 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. + */ + +type Callback = (n: int) => int +class A { + public callback: Callback + public increment() { + this.callback(1) + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call2-expected.txt b/ets2panda/test/parser/ets/test-type-alias-call2-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..8913c68014579744e7baf6c09dd9ae66619cd4eb --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call2-expected.txt @@ -0,0 +1,783 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 6 + }, + "end": { + "line": 16, + "column": 11 + } + } + }, + "typeAnnotation": { + "type": "ETSFunctionType", + "params": [ + { + "type": "ETSParameterExpression", + "name": { + "type": "Identifier", + "name": "n", + "typeAnnotation": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 21 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 15 + }, + "end": { + "line": 16, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 15 + }, + "end": { + "line": 16, + "column": 21 + } + } + } + ], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 26 + }, + "end": { + "line": 16, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 14 + }, + "end": { + "line": 16, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 17, + "column": 5 + } + } + }, + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Second", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 6 + }, + "end": { + "line": 17, + "column": 12 + } + } + }, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 17, + "column": 20 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 18, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 18, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 18, + "column": 5 + } + } + }, + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 6 + }, + "end": { + "line": 18, + "column": 14 + } + } + }, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Second", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 17 + }, + "end": { + "line": 18, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 17 + }, + "end": { + "line": 19, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 17 + }, + "end": { + "line": 19, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 1 + }, + "end": { + "line": 19, + "column": 6 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 7 + }, + "end": { + "line": 19, + "column": 8 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 12 + }, + "end": { + "line": 20, + "column": 20 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 22 + }, + "end": { + "line": 20, + "column": 30 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 22 + }, + "end": { + "line": 21, + "column": 11 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 22 + }, + "end": { + "line": 21, + "column": 11 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 12 + }, + "end": { + "line": 21, + "column": 11 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 12 + }, + "end": { + "line": 21, + "column": 21 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 12 + }, + "end": { + "line": 21, + "column": 21 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 22, + "column": 9 + }, + "end": { + "line": 22, + "column": 13 + } + } + }, + "property": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 14 + }, + "end": { + "line": 22, + "column": 22 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 22, + "column": 9 + }, + "end": { + "line": 22, + "column": 22 + } + } + }, + "arguments": [ + { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 22, + "column": 23 + }, + "end": { + "line": 22, + "column": 24 + } + } + } + ], + "optional": false, + "loc": { + "start": { + "line": 22, + "column": 9 + }, + "end": { + "line": 22, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 9 + }, + "end": { + "line": 22, + "column": 25 + } + } + } + ], + "loc": { + "start": { + "line": 21, + "column": 24 + }, + "end": { + "line": 23, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 21 + }, + "end": { + "line": 23, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 21 + }, + "end": { + "line": 23, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 5 + }, + "end": { + "line": 23, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 2 + }, + "end": { + "line": 24, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 9 + }, + "end": { + "line": 24, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 1 + }, + "end": { + "line": 24, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 25, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call2.ets b/ets2panda/test/parser/ets/test-type-alias-call2.ets new file mode 100644 index 0000000000000000000000000000000000000000..93b91c0087cd435ac5e160d434706e3d0d4808c9 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call2.ets @@ -0,0 +1,24 @@ +/* + * Copyright (c) 2022 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. + */ + +type First = (n: int) => int +type Second = First +type Callback = Second +class A { + public callback: Callback + public increment() { + this.callback(1) + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call3-expected.txt b/ets2panda/test/parser/ets/test-type-alias-call3-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..1076dcd57a43547560e86ee86f796e5e6239436b --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call3-expected.txt @@ -0,0 +1,647 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 6 + }, + "end": { + "line": 16, + "column": 14 + } + } + }, + "typeAnnotation": { + "type": "ETSFunctionType", + "params": [ + { + "type": "ETSParameterExpression", + "name": { + "type": "Identifier", + "name": "n", + "typeAnnotation": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 21 + }, + "end": { + "line": 16, + "column": 24 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 24 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 24 + } + } + } + ], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 29 + }, + "end": { + "line": 16, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 17 + }, + "end": { + "line": 16, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 17, + "column": 6 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 19 + }, + "end": { + "line": 18, + "column": 27 + } + } + }, + "accessibility": "public", + "static": true, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 29 + }, + "end": { + "line": 18, + "column": 37 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 29 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 29 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 19 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 12 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 12 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 10 + } + } + }, + "property": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 11 + }, + "end": { + "line": 20, + "column": 19 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 19 + } + } + }, + "arguments": [ + { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 20 + }, + "end": { + "line": 20, + "column": 21 + } + } + } + ], + "optional": false, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 22 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 24 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 21 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 21 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 2 + }, + "end": { + "line": 22, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 17, + "column": 9 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 23, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call3.ets b/ets2panda/test/parser/ets/test-type-alias-call3.ets new file mode 100644 index 0000000000000000000000000000000000000000..89743c8d482cac517a27efd44fb3e6e072a85d7b --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call3.ets @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2022 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. + */ + +type Callback = (n: int) => int +class A { + public static callback: Callback + public increment() { + A.callback(1) + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call4-expected.txt b/ets2panda/test/parser/ets/test-type-alias-call4-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..9c15b8c34fd5f0befe93abdeb17d31be72204829 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call4-expected.txt @@ -0,0 +1,647 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 6 + }, + "end": { + "line": 16, + "column": 14 + } + } + }, + "typeAnnotation": { + "type": "ETSFunctionType", + "params": [ + { + "type": "ETSParameterExpression", + "name": { + "type": "Identifier", + "name": "n", + "typeAnnotation": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 21 + }, + "end": { + "line": 16, + "column": 24 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 24 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 24 + } + } + } + ], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 29 + }, + "end": { + "line": 16, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 17 + }, + "end": { + "line": 16, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 17, + "column": 6 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 19 + }, + "end": { + "line": 18, + "column": 27 + } + } + }, + "accessibility": "public", + "static": true, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 29 + }, + "end": { + "line": 18, + "column": 37 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 29 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 29 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 19 + }, + "end": { + "line": 19, + "column": 11 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 19 + }, + "end": { + "line": 19, + "column": 28 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 19 + }, + "end": { + "line": 19, + "column": 28 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 10 + } + } + }, + "property": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 11 + }, + "end": { + "line": 20, + "column": 19 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 19 + } + } + }, + "arguments": [ + { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 20 + }, + "end": { + "line": 20, + "column": 21 + } + } + } + ], + "optional": false, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 22 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 31 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 28 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 28 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 2 + }, + "end": { + "line": 22, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 17, + "column": 9 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 23, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call4.ets b/ets2panda/test/parser/ets/test-type-alias-call4.ets new file mode 100644 index 0000000000000000000000000000000000000000..d02aa961d9774ac9f25c52c85f2324d54d43d082 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call4.ets @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2022 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. + */ + +type Callback = (n: int) => int +class A { + public static callback: Callback + public static increment() { + A.callback(1) + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call5-expected.txt b/ets2panda/test/parser/ets/test-type-alias-call5-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..f26b502997d24965defa200d3d48540daf5dba01 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call5-expected.txt @@ -0,0 +1,839 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 6 + }, + "end": { + "line": 16, + "column": 11 + } + } + }, + "typeAnnotation": { + "type": "ETSFunctionType", + "params": [ + { + "type": "ETSParameterExpression", + "name": { + "type": "Identifier", + "name": "n", + "typeAnnotation": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 21 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 15 + }, + "end": { + "line": 16, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 15 + }, + "end": { + "line": 16, + "column": 21 + } + } + } + ], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 26 + }, + "end": { + "line": 16, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 14 + }, + "end": { + "line": 16, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 16, + "column": 30 + } + } + }, + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Second", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 6 + }, + "end": { + "line": 17, + "column": 12 + } + } + }, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 17, + "column": 20 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 18, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 18, + "column": 5 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 18, + "column": 5 + } + } + }, + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 6 + }, + "end": { + "line": 18, + "column": 14 + } + } + }, + "typeAnnotation": { + "type": "ETSUnionType", + "types": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 17 + }, + "end": { + "line": 18, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 17 + }, + "end": { + "line": 18, + "column": 24 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 17 + }, + "end": { + "line": 18, + "column": 24 + } + } + }, + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Second", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 25 + }, + "end": { + "line": 18, + "column": 31 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 25 + }, + "end": { + "line": 18, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 25 + }, + "end": { + "line": 18, + "column": 32 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 17 + }, + "end": { + "line": 18, + "column": 32 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 1 + }, + "end": { + "line": 18, + "column": 32 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 7 + }, + "end": { + "line": 20, + "column": 8 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 12 + }, + "end": { + "line": 21, + "column": 20 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 22 + }, + "end": { + "line": 21, + "column": 30 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 22 + }, + "end": { + "line": 21, + "column": 31 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 22 + }, + "end": { + "line": 21, + "column": 31 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 12 + }, + "end": { + "line": 21, + "column": 31 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 12 + }, + "end": { + "line": 22, + "column": 21 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 12 + }, + "end": { + "line": 22, + "column": 21 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 13 + } + } + }, + "property": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 14 + }, + "end": { + "line": 23, + "column": 22 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 22 + } + } + }, + "arguments": [ + { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 23, + "column": 23 + }, + "end": { + "line": 23, + "column": 24 + } + } + } + ], + "optional": false, + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 26 + } + } + } + ], + "loc": { + "start": { + "line": 22, + "column": 24 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 21 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 21 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 5 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 25, + "column": 2 + }, + "end": { + "line": 25, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 25, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 1 + }, + "end": { + "line": 25, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 26, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call5.ets b/ets2panda/test/parser/ets/test-type-alias-call5.ets new file mode 100644 index 0000000000000000000000000000000000000000..8a7f8a3e988376706badcf726943c4d7a5612a7e --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call5.ets @@ -0,0 +1,25 @@ +/* + * Copyright (c) 2022 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. + */ + +type First = (n: int) => int; +type Second = First +type Callback = First | Second; + +class A { + public callback: Callback; + public increment() { + this.callback(1); + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call6-expected.txt b/ets2panda/test/parser/ets/test-type-alias-call6-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..3a470a4b777360172ed45c359e69fda11d46ccf3 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call6-expected.txt @@ -0,0 +1,908 @@ +{ + "type": "Program", + "statements": [ + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 6 + }, + "end": { + "line": 16, + "column": 11 + } + } + }, + "typeAnnotation": { + "type": "ETSFunctionType", + "params": [ + { + "type": "ETSParameterExpression", + "name": { + "type": "Identifier", + "name": "n", + "typeAnnotation": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 18 + }, + "end": { + "line": 16, + "column": 21 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 16, + "column": 15 + }, + "end": { + "line": 16, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 15 + }, + "end": { + "line": 16, + "column": 21 + } + } + } + ], + "returnType": { + "type": "ETSPrimitiveType", + "loc": { + "start": { + "line": 16, + "column": 26 + }, + "end": { + "line": 16, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 14 + }, + "end": { + "line": 16, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 16, + "column": 1 + }, + "end": { + "line": 16, + "column": 30 + } + } + }, + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Second", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 6 + }, + "end": { + "line": 17, + "column": 12 + } + } + }, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 17, + "column": 20 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 15 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Third", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 6 + }, + "end": { + "line": 18, + "column": 11 + } + } + }, + "typeAnnotation": { + "type": "ETSUnionType", + "types": [ + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "First", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 18, + "column": 19 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 18, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 18, + "column": 21 + } + } + }, + { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Second", + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 22 + }, + "end": { + "line": 18, + "column": 28 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 22 + }, + "end": { + "line": 18, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 22 + }, + "end": { + "line": 18, + "column": 29 + } + } + } + ], + "loc": { + "start": { + "line": 18, + "column": 14 + }, + "end": { + "line": 18, + "column": 29 + } + } + }, + "loc": { + "start": { + "line": 18, + "column": 1 + }, + "end": { + "line": 18, + "column": 29 + } + } + }, + { + "type": "TSTypeAliasDeclaration", + "id": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 6 + }, + "end": { + "line": 19, + "column": 14 + } + } + }, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Third", + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 1 + }, + "end": { + "line": 19, + "column": 23 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 7 + }, + "end": { + "line": 21, + "column": 8 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 12 + }, + "end": { + "line": 22, + "column": 20 + } + } + }, + "accessibility": "public", + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "ETSTypeReference", + "part": { + "type": "ETSTypeReferencePart", + "name": { + "type": "Identifier", + "name": "Callback", + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 22 + }, + "end": { + "line": 22, + "column": 30 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 22 + }, + "end": { + "line": 22, + "column": 31 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 22 + }, + "end": { + "line": 22, + "column": 31 + } + } + }, + "definite": false, + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 12 + }, + "end": { + "line": 22, + "column": 31 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 12 + }, + "end": { + "line": 23, + "column": 21 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "increment", + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 12 + }, + "end": { + "line": 23, + "column": 21 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 13 + } + } + }, + "property": { + "type": "Identifier", + "name": "callback", + "decorators": [], + "loc": { + "start": { + "line": 24, + "column": 14 + }, + "end": { + "line": 24, + "column": 22 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 22 + } + } + }, + "arguments": [ + { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 24, + "column": 23 + }, + "end": { + "line": 24, + "column": 24 + } + } + } + ], + "optional": false, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 25 + } + } + }, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 26 + } + } + } + ], + "loc": { + "start": { + "line": 23, + "column": 24 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 21 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 21 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 23, + "column": 5 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "constructor", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 26, + "column": 2 + }, + "end": { + "line": 26, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 21, + "column": 9 + }, + "end": { + "line": 26, + "column": 2 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 1 + }, + "end": { + "line": 26, + "column": 2 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "ETSGLOBAL", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "superClass": null, + "implements": [], + "body": [ + { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "method", + "accessibility": "public", + "static": true, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": { + "type": "Identifier", + "name": "_$init$_", + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 27, + "column": 1 + } + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call6.ets b/ets2panda/test/parser/ets/test-type-alias-call6.ets new file mode 100644 index 0000000000000000000000000000000000000000..8801b22e5489a74fa0732d9aa1da248a873233b5 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call6.ets @@ -0,0 +1,26 @@ +/* + * Copyright (c) 2022 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. + */ + +type First = (n: int) => int; +type Second = First; +type Third = First | Second; +type Callback = Third; + +class A { + public callback: Callback; + public increment() { + this.callback(1); + } +} diff --git a/ets2panda/test/parser/ets/test-type-alias-call7.ets b/ets2panda/test/parser/ets/test-type-alias-call7.ets new file mode 100644 index 0000000000000000000000000000000000000000..cc764f60c61f4d3f4865a30a86edaa5e76f35f69 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call7.ets @@ -0,0 +1,17 @@ +/* + * Copyright (c) 2022 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. + */ + +type Callback = (n: int) => int +export type {Callback} diff --git a/ets2panda/test/parser/ets/test-type-alias-call8.ets b/ets2panda/test/parser/ets/test-type-alias-call8.ets new file mode 100644 index 0000000000000000000000000000000000000000..27b26e180ac5a620cd40427a9128ce2bff47bec0 --- /dev/null +++ b/ets2panda/test/parser/ets/test-type-alias-call8.ets @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2022 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. + */ + +import type { Callback } from './test-type-alias-call3.ets'; +class A { + public callback: Callback + public increment(){ + this.callback(1) + } +} diff --git a/ets2panda/test/runtime/ets/BigInt.ets b/ets2panda/test/runtime/ets/BigInt.ets new file mode 100644 index 0000000000000000000000000000000000000000..d2fa645b16c4c61ea3a1576403745e23c553a233 --- /dev/null +++ b/ets2panda/test/runtime/ets/BigInt.ets @@ -0,0 +1,643 @@ +/* + * Copyright (c) 2023 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. + */ + +function test_bitwise_and(): void { + assert new BigInt("10").operatorBitwiseAnd(new BigInt("2")).toString().equals("2"); + assert new BigInt("256").operatorBitwiseAnd(new BigInt("1")).toString().equals("0"); + assert new BigInt("3124378143267041203423").operatorBitwiseAnd(new BigInt("43621978")).toString().equals("41948250"); + assert new BigInt("256").operatorBitwiseAnd(new BigInt("256")).toString().equals("256"); + assert new BigInt("12345678").operatorBitwiseAnd(new BigInt("1234")).toString().equals("66"); +} + +function test_bitwise_or(): void { + assert new BigInt("10").operatorBitwiseOr(new BigInt("2")).toString().equals("10"); + assert new BigInt("256").operatorBitwiseOr(new BigInt("1")).toString().equals("257"); + assert new BigInt("256").operatorBitwiseOr(new BigInt("256")).toString().equals("256"); + assert new BigInt("3124378143267041203423").operatorBitwiseOr(new BigInt("43621978")).toString().equals("3124378143267042877151"); + assert new BigInt("12345678").operatorBitwiseOr(new BigInt("1234")).toString().equals("12346846"); +} + +function test_bitwise_xor(): void { + assert new BigInt("10").operatorBitwiseXor(new BigInt("2")).toString().equals("8"); + assert new BigInt("256").operatorBitwiseXor(new BigInt("1")).toString().equals("257"); + assert new BigInt("256").operatorBitwiseXor(new BigInt("256")).toString().equals("0"); + assert new BigInt("3124378143267041203423").operatorBitwiseXor(new BigInt("43621978")).toString().equals("3124378143267000928901"); + assert new BigInt("12345678").operatorBitwiseXor(new BigInt("1234")).toString().equals("12346780"); +} + +function test_left_shift(): void { + assert new BigInt("0").operatorLeftShift(new BigInt("0")).toString().equals("0"); + assert new BigInt("0").operatorLeftShift(new BigInt("1")).toString().equals("0"); + assert new BigInt("1").operatorLeftShift(new BigInt("0")).toString().equals("1"); + assert new BigInt("10").operatorLeftShift(new BigInt("2")).toString().equals("40"); + assert new BigInt("255").operatorLeftShift(new BigInt("41")).toString().equals("560750930165760"); + assert new BigInt("65535").operatorLeftShift(new BigInt("60")).toString().equals("75556710804409716572160"); + assert new BigInt("4294967295").operatorLeftShift(new BigInt("5")).toString().equals("137438953440"); + assert new BigInt("18446744073709551615").operatorLeftShift(new BigInt("6")).toString().equals("1180591620717411303360"); + assert new BigInt("1275418875248948586535904902545412130").operatorLeftShift(new BigInt("123")).toString().equals("13562579802667292602585801202159372574330573695725523059072421474640855040"); + assert new BigInt("2").operatorLeftShift(new BigInt("218")).toString().equals("842498333348457493583344221469363458551160763204392890034487820288"); + assert new BigInt("-1").operatorLeftShift(new BigInt("0")).toString().equals("-1"); + assert new BigInt("-12").operatorLeftShift(new BigInt("4")).toString().equals("-192"); + assert new BigInt("-255").operatorLeftShift(new BigInt("19")).toString().equals("-133693440"); + assert new BigInt("-65535").operatorLeftShift(new BigInt("73")).toString().equals("-618960574909724398159134720"); + assert new BigInt("-4294967295").operatorLeftShift(new BigInt("24")).toString().equals("-72057594021150720"); + assert new BigInt("-18446744073709551615").operatorLeftShift(new BigInt("31")).toString().equals("-39614081257132168794624491520"); + assert new BigInt("-4095059032950818422890113130149234924134").operatorLeftShift(new BigInt("103")).toString().equals("-41528832328721100931613913139905162112381494314462183326283215847555072"); +} + +function test_right_shift(): void { + assert new BigInt("-200").operatorRightShift(new BigInt("2")).toString().equals("-50"); + assert new BigInt("-12").operatorRightShift(new BigInt("2")).toString().equals("-3"); + assert new BigInt("-1").operatorRightShift(new BigInt("0")).toString().equals("-1"); + assert new BigInt("0").operatorRightShift(new BigInt("0")).toString().equals("0"); + assert new BigInt("0").operatorRightShift(new BigInt("1")).toString().equals("0"); + assert new BigInt("1").operatorRightShift(new BigInt("0")).toString().equals("1"); + assert new BigInt("55").operatorRightShift(new BigInt("2")).toString().equals("13"); + assert new BigInt("-50").operatorRightShift(new BigInt("2")).toString().equals("-13"); + assert new BigInt("255").operatorRightShift(new BigInt("4")).toString().equals("15"); + assert new BigInt("255").operatorRightShift(new BigInt("8")).toString().equals("0"); + assert new BigInt("65535").operatorRightShift(new BigInt("10")).toString().equals("63"); + assert new BigInt("4294967295").operatorRightShift(new BigInt("17")).toString().equals("32767"); + assert new BigInt("4294967295").operatorRightShift(new BigInt("48")).toString().equals("0"); + assert new BigInt("18446744073709551615").operatorRightShift(new BigInt("55")).toString().equals("511"); + assert new BigInt("4930493049034092989191918392837727383823827").operatorRightShift(new BigInt("129")).toString().equals("7244"); + assert new BigInt("34930693049034092980065918370009389341341932481328231493102392100010239").operatorRightShift(new BigInt("41")).toString().equals("15884640128676479880626138024130973163365493965706369405371"); + assert new BigInt("34095405903900293499034024029409200000000000000000000094049304394284993939382949384984981018480144184891848991934893429489324901148449849382222222222222888384932890000103010381803018300103180381030084545225875678328499213403403984398439489384984287113383827387373382328328194394892948392222219791749717949183748237").operatorRightShift(new BigInt("511")).toString().equals("5085903091997271218878067997324523590835536101241386224503069830700984460490307918626942225457432781938207872710051592009243523341752202627425621983245162030428"); + assert new BigInt("-255").operatorRightShift(new BigInt("2")).toString().equals("-64"); + assert new BigInt("-65535").operatorRightShift(new BigInt("12")).toString().equals("-16"); + assert new BigInt("-4294967295").operatorRightShift(new BigInt("18")).toString().equals("-16384"); + assert new BigInt("-18446744073709551615").operatorRightShift(new BigInt("38")).toString().equals("-67108864"); + assert new BigInt("-4095059032950818422890113130149234924134").operatorRightShift(new BigInt("99")).toString().equals("-6460863952"); + assert new BigInt("-3294302940940294094923040592059302590950294502940294029029409029429042942049028100104029439420990952").operatorRightShift(new BigInt("100")).toString().equals("-2598746800062401791237527125433630339355687972972274247737341685088307"); +} + +function test_module(): void { + assert new BigInt("10").operatorModule(new BigInt("3")).toString().equals("1"); + assert new BigInt("10").operatorModule(new BigInt("-3")).toString().equals("1"); + assert new BigInt("-10").operatorModule(new BigInt("3")).toString().equals("-1"); + assert new BigInt("-10").operatorModule(new BigInt("-3")).toString().equals("-1"); + assert new BigInt("100").operatorModule(new BigInt("50")).toString().equals("0"); + assert new BigInt("100").operatorModule(new BigInt("-50")).toString().equals("0"); + assert new BigInt("-100").operatorModule(new BigInt("50")).toString().equals("0"); + assert new BigInt("-100").operatorModule(new BigInt("-50")).toString().equals("0"); + assert new BigInt("3124378143267041203423").operatorModule(new BigInt("43621978")).toString().equals("18802883"); + assert new BigInt("-3124378143267041203423").operatorModule(new BigInt("43621978")).toString().equals("-18802883"); + assert new BigInt("3124378143267041203423").operatorModule(new BigInt("-43621978")).toString().equals("18802883"); + assert new BigInt("-3124378143267041203423").operatorModule(new BigInt("-43621978")).toString().equals("-18802883"); + assert new BigInt("100").operatorModule(new BigInt("250")).toString().equals("100"); + assert new BigInt("-100").operatorModule(new BigInt("250")).toString().equals("-100"); + assert new BigInt("100").operatorModule(new BigInt("-250")).toString().equals("100"); + assert new BigInt("-100").operatorModule(new BigInt("-250")).toString().equals("-100"); + assert new BigInt("0").operatorModule(new BigInt("8")).toString().equals("0"); +} + +function test_divide(): void { + assert new BigInt("10").operatorDivide(new BigInt("3")).toString().equals("3"); + assert new BigInt("-10").operatorDivide(new BigInt("3")).toString().equals("-3"); + assert new BigInt("10").operatorDivide(new BigInt("-3")).toString().equals("-3"); + assert new BigInt("-10").operatorDivide(new BigInt("-3")).toString().equals("3"); + assert new BigInt("100").operatorDivide(new BigInt("50")).toString().equals("2"); + assert new BigInt("100").operatorDivide(new BigInt("-50")).toString().equals("-2"); + assert new BigInt("-100").operatorDivide(new BigInt("50")).toString().equals("-2"); + assert new BigInt("-100").operatorDivide(new BigInt("-50")).toString().equals("2"); + assert new BigInt("3124378143267041203423").operatorDivide(new BigInt("43621978")).toString().equals("71623944775430"); + assert new BigInt("-3124378143267041203423").operatorDivide(new BigInt("43621978")).toString().equals("-71623944775430"); + assert new BigInt("3124378143267041203423").operatorDivide(new BigInt("-43621978")).toString().equals("-71623944775430"); + assert new BigInt("-3124378143267041203423").operatorDivide(new BigInt("-43621978")).toString().equals("71623944775430"); + assert new BigInt("100").operatorDivide(new BigInt("250")).toString().equals("0"); + assert new BigInt("100").operatorDivide(new BigInt("-250")).toString().equals("0"); + assert new BigInt("-100").operatorDivide(new BigInt("250")).toString().equals("0"); + assert new BigInt("-100").operatorDivide(new BigInt("-250")).toString().equals("0"); + assert new BigInt("65000").operatorDivide(new BigInt("100")).toString().equals("650"); + assert new BigInt("65000").operatorDivide(new BigInt("-100")).toString().equals("-650"); + assert new BigInt("-65000").operatorDivide(new BigInt("100")).toString().equals("-650"); + assert new BigInt("-65000").operatorDivide(new BigInt("-100")).toString().equals("650"); +} + +function test_unary_minus(): void { + assert new BigInt("10").negate().toString().equals("-10"); + assert new BigInt("1000").negate().toString().equals("-1000"); + assert new BigInt("-1").negate().toString().equals("1"); + assert new BigInt("-10").negate().toString().equals("10"); + assert new BigInt("-100").negate().toString().equals("100"); + assert new BigInt("0").negate().toString().equals("0"); +} + +function test_plus(): void { + assert new BigInt("10").operatorAdd(new BigInt("20")).toString() == "30"; + assert new BigInt("1000").operatorAdd(new BigInt("10")).toString() == "1010"; + assert new BigInt("-10").operatorAdd(new BigInt("9")).toString() == "-1"; + assert new BigInt("-10").operatorAdd(new BigInt("10")).toString() == "0"; + assert new BigInt("-100").operatorAdd(new BigInt("10")).toString() == "-90"; + assert new BigInt("100").operatorAdd(new BigInt("10")).toString() == "110"; + assert new BigInt("65535").operatorAdd(new BigInt("65535")).toString() == "131070"; + assert new BigInt("65500").operatorAdd(new BigInt("1")).toString().equals("65501"); + assert new BigInt("65500").operatorAdd(new BigInt("-1")).toString().equals("65499"); + assert new BigInt("-65500").operatorAdd(new BigInt("-1")).toString().equals("-65501"); + assert new BigInt("-65500").operatorAdd(new BigInt("1")).toString().equals("-65499"); + assert new BigInt("-65500").operatorAdd(new BigInt("100000")).toString().equals("34500"); + assert new BigInt("100").operatorAdd(new BigInt("0")).toString().equals("100"); + assert new BigInt("-100").operatorAdd(new BigInt("0")).toString().equals("-100"); + assert new BigInt("-10").operatorAdd(new BigInt("-10")).toString().equals("-20"); +} + +function test_minus(): void { + assert new BigInt("10").operatorSubtract(new BigInt("2")).toString().equals("8"); + assert new BigInt("2").operatorSubtract(new BigInt("10")).toString().equals("-8"); + assert new BigInt("-10").operatorSubtract(new BigInt("-2")).toString().equals("-8"); + assert new BigInt("-100").operatorSubtract(new BigInt("1")).toString().equals("-101"); + assert new BigInt("-100").operatorSubtract(new BigInt("-1")).toString().equals("-99"); + assert new BigInt("-1000").operatorSubtract(new BigInt("10")).toString().equals("-1010"); + assert new BigInt("1237840127434312471243").operatorSubtract(new BigInt("234112342314526914672342143621463921469")).toString().equals("-234112342314526913434502016187151450226"); + assert new BigInt("-1237840127434312471243").operatorSubtract(new BigInt("234112342314526914672342143621463921469")).toString().equals("-234112342314526915910182271055776392712"); + assert new BigInt("1237840127434312471243").operatorSubtract(new BigInt("-234112342314526914672342143621463921469")).toString().equals("234112342314526915910182271055776392712"); + assert new BigInt("-1237840127434312471243").operatorSubtract(new BigInt("-234112342314526914672342143621463921469")).toString().equals("234112342314526913434502016187151450226"); + assert new BigInt("-1000").operatorSubtract(new BigInt("-10")).toString().equals("-990"); + assert new BigInt("-100").operatorSubtract(new BigInt("0")).toString().equals("-100"); + assert new BigInt("0").operatorSubtract(new BigInt("-100")).toString().equals("100"); + assert new BigInt("0").operatorSubtract(new BigInt("100")).toString().equals("-100"); + assert new BigInt("65500").operatorSubtract(new BigInt("1")).toString().equals("65499"); + assert new BigInt("65500").operatorSubtract(new BigInt("-1")).toString().equals("65501"); + assert new BigInt("-65500").operatorSubtract(new BigInt("-1")).toString().equals("-65499"); + assert new BigInt("-65500").operatorSubtract(new BigInt("1")).toString().equals("-65501"); + assert new BigInt("65500").operatorSubtract(new BigInt("100000")).toString().equals("-34500"); + assert new BigInt("49798775").operatorSubtract(new BigInt("43621978")).toString().equals("6176797"); + assert new BigInt("10").operatorSubtract(new BigInt("20")).toString().equals("-10"); +} + +function test_multiply(): void { + assert new BigInt("10").operatorMultiply(new BigInt("10")).toString() == "100"; + assert new BigInt("0").operatorMultiply(new BigInt("50")).toString() == "0"; + assert new BigInt("1").operatorMultiply(new BigInt("50")).toString() == "50"; + assert new BigInt("50").operatorMultiply(new BigInt("5")).toString() == "250"; + assert new BigInt("50").operatorMultiply(new BigInt("-5")).toString() == "-250"; + assert new BigInt("-1").operatorMultiply(new BigInt("-5")).toString() == "5"; + assert new BigInt("0").operatorMultiply(new BigInt("0")).toString() == "0"; + assert new BigInt("123").operatorMultiply(new BigInt("1")).toString() == "123"; + assert new BigInt("1234").operatorMultiply(new BigInt("987")).toString() == "1217958"; + assert new BigInt("3241847031247230147213740214703214721047312").operatorMultiply(new BigInt("412343124123421347812304712431421204731024")).toString() == "1336753332794721625246945391107220242430725631478413717131017736872102322242538207488"; + assert new BigInt("-3241847031247230147213740214703214721047312").operatorMultiply(new BigInt("-412343124123421347812304712431421204731024")).toString() == "1336753332794721625246945391107220242430725631478413717131017736872102322242538207488"; + assert new BigInt("-3241847031247230147213740214703214721047312").operatorMultiply(new BigInt("412343124123421347812304712431421204731024")).toString() == "-1336753332794721625246945391107220242430725631478413717131017736872102322242538207488"; + assert new BigInt("3241847031247230147213740214703214721047312").operatorMultiply(new BigInt("-412343124123421347812304712431421204731024")).toString() == "-1336753332794721625246945391107220242430725631478413717131017736872102322242538207488"; + assert new BigInt("256").operatorMultiply(new BigInt("256")).toString() == "65536"; +} + +function test_create_empty_bigint(): void { + let a = new BigInt() + assert a.positive() + assert a.toString() == "0" + + let b = new BigInt("") + assert b.positive() + assert b.toString() == "0" +} + +function test_invalid_bigint(): void { + // NOTE(kkonsw): implement validation +} + +function test_bigint_as_string(): void { + assert new BigInt("10").toString() == "10" + assert new BigInt("1000").toString() == "1000" + assert new BigInt("-1000").toString() == "-1000" + assert new BigInt("-1").toString() == "-1" + assert new BigInt("-10").toString() == "-10" + assert new BigInt("-100").toString() == "-100" + assert new BigInt("-100000000000000").toString() == "-100000000000000" + assert new BigInt("0").toString() == "0" +} + +function test_type(): void { + let num0 = 0n; + let num1 = 100_100_100_100_100_100n + let num2 = -57896044618658097711785492504343953926634992332820282019728792003956564819967n + + assert (num0 instanceof bigint) + assert (num1 instanceof bigint) + assert (num2 instanceof bigint) +} + +function test_assignment(): void { + let a = -24059059045444224545405903904190343043049209420234290480n + let b = a + assert (a instanceof bigint) + assert (b instanceof bigint) + assert (a.toString() == b.toString()); + + a = 123n; + assert (a instanceof bigint) + assert (a.toString() == "123"); + assert (a == 123n); + + const zero = 0n; + let c = zero; + assert (zero instanceof bigint) + assert (c instanceof bigint) + assert (zero.toString() == c.toString()); +} + +function test_compare(): void { + const a = 24400569094091093912039019089543850580328542852805043n + const b = 34034240244909504590902901119302940942904944029040950n + + assert 44493059209094029409209402940924902n < 140044940590459049067274048929058908989042385n + assert 44493059209094029409209402940924902n < a + assert a < 34034240244909504590902901119302940942904944029040950n + assert a < b + + assert 44493059209094029409209402940924902n <= 140044940590459049067274048929058908989042385n + assert 44493059209094029409209402940924902n <= a + assert a <= 34034240244909504590902901119302940942904944029040950n + assert a <= b + + assert 44493059209094029409209402940924902n <= 44493059209094029409209402940924902n + assert 24400569094091093912039019089543850580328542852805043n <= a + assert a <= 24400569094091093912039019089543850580328542852805043n + assert a <= a + + assert 40044940590459049067274048929058908989042385n > 44493059209094029409209402940924902n + assert 34034240244909504590902901119302940942904944029040950n > a + assert a > 140044940590459049067274048929058908989042385n + assert b > a + + assert 40044940590459049067274048929058908989042385n >= 44493059209094029409209402940924902n + assert 34034240244909504590902901119302940942904944029040950n >= a + assert a >= 140044940590459049067274048929058908989042385n + assert b >= a + + assert 44493059209094029409209402940924902n <= 44493059209094029409209402940924902n + assert 24400569094091093912039019089543850580328542852805043n <= a + assert a <= 24400569094091093912039019089543850580328542852805043n + assert a <= a +} + +function test_literals() : void { + let num0 = 0n + assert (num0.toString() == "0") + + let num1 = 127n + assert (num1.toString() == "127") + + let num2 = 32767n + assert (num2.toString() == "32767") + + let num3 = 2147483647n + assert (num3.toString() == "2147483647") + + let num4 = 9223372036854775807n + assert (num4.toString() == "9223372036854775807") + + let num5 = 170141183460469231731687303715884105727n + assert (num5.toString() == "170141183460469231731687303715884105727") + + let num6 = 57896044618658097711785492504343953926634992332820282019728792003956564819967n + assert (num6.toString() == "57896044618658097711785492504343953926634992332820282019728792003956564819967") + + let num1_n = -128n + assert (num1_n.toString() == "-128") + + let num2_n = -32768n + assert (num2_n.toString() == "-32768") + + let num3_n = -2147483648n + assert (num3_n.toString() == "-2147483648") + + let num4_n = -9223372036854775808n + assert (num4_n.toString() == "-9223372036854775808") + + let num5_n = -170141183460469231731687303715884105728n + assert (num5_n.toString() == "-170141183460469231731687303715884105728") + + let num6_n = -57896044618658097711785492504343953926634992332820282019728792003956564819968n + assert (num6_n.toString() == "-57896044618658097711785492504343953926634992332820282019728792003956564819968") + + let num1_sep = 1_991_653_125_841_217_555_434419_9091_123000000_3_3313_5775_3282_29n + assert (num1_sep.toString() == "19916531258412175554344199091123000000333135775328229") + + let num2_sep = -422_12_3333_9844_3333_3443_34111_43434_1111_11_1_3_3_411909_990081n + assert (num2_sep.toString() == "-4221233339844333334433411143434111111133411909990081") + + let num0_t: bigint = 0n + assert (num0_t.toString() == "0") + + let num1_t: bigint = 57896044618658097711785492504343953926634992332820282019728792003956564819967n + assert (num1_t.toString() == "57896044618658097711785492504343953926634992332820282019728792003956564819967") + + let num2_t: bigint = -9223372036854775808n + assert (num2_t.toString() == "-9223372036854775808") + + let num3_t: bigint = 1_991_653_125_841_217_555_434419_9091_123000000_3_3313_5775_3282_29n + assert (num3_t.toString() == "19916531258412175554344199091123000000333135775328229") + + let num4_t: bigint = -422_12_3333_9844_3333_3443_34111_43434_1111_11_1_3_3_411909_990081n + assert (num4_t.toString() == "-4221233339844333334433411143434111111133411909990081") + + const num0_c = 0n + assert (num0_c.toString() == "0") + + const num1_c = 1267650600228229401496703205376n + assert (num1_c.toString() == "1267650600228229401496703205376") + + const num2_c = -1427247692705959881058285969449495136382746624n + assert (num2_c.toString() == "-1427247692705959881058285969449495136382746624") + + const num3_c = 4_000_000_000_000_000_000_000_100n + assert (num3_c.toString() == "4000000000000000000000100") + + const num4_c: bigint = -7777777_666666_55555_4444_333_22_1n + assert (num4_c.toString() == "-7777777666666555554444333221") +} + +function test_cast(): void { + const v = 1559053 + const b: byte = 44 + const s: short = -17600 + const i: int = 1150483640 + const l: long = -8223372036854775808 + + // NOTE(kkonsw): casts currently do not work +} + +function test_bigint_methods(): void { + const b: byte = 44 + const s: short = -17600 + const i: int = 1150483640 + const l: long = -8223372036854775808 + + /* Testing BigInt constructor */ + let n0 = new BigInt(0) + assert n0 == 0n + assert(n0.toString() == "0") + + let n1 = new BigInt(654093) + assert(n1.toString() == "654093") + assert n1 == 654093n + + let n2 = new BigInt(b) + assert(n2.toString() == "44") + assert n2 == 44n + + let n3 = new BigInt(s) + assert(n3.toString() == "-17600") + assert n3 == -17600n + + let n4 = new BigInt(i) + assert(n4.toString() == "1150483640") + assert n4 == 1150483640n + + let n5 = new BigInt(l) + assert(n5.toString() == "-8223372036854775808") + assert n5 == -8223372036854775808n + + let dec = new BigInt("-12392320390239294724747283477947923471101032") + assert dec == -12392320390239294724747283477947923471101032n + + const n7 = 12392320390239294724747283477947923471101032n + + /* Testing asIntN() static method */ + // assert BigInt.asIntN(0, n7) == 0n + // assert BigInt.asIntN(8, n7) == 104n + // assert BigInt.asIntN(16, n7) == 27752n + // assert BigInt.asIntN(32, n7) == -737317784n + // assert BigInt.asIntN(64, n7) == -7098331616643290008n + + /* Testing asUintN() static method */ + // assert BigInt.asUintN(0, n7) == 0n + // assert BigInt.asUintN(8, n7) == 104n + // assert BigInt.asUintN(16, n7) == 27752n + // assert BigInt.asUintN(32, n7) == 3557649512n + // assert BigInt.asUintN(64, n7) == 11348412457066261608n +} + +function test_unary(): void { + let n = -128n + assert (n.toString() == "-128") + + let a = 123n; + assert(a == 123n); + assert(a.toString() == "123"); + + a = -123n; + assert(a == -123n); + assert(a.toString() == "-123"); + + a = 123n + assert(a == 123n); + assert(a.toString() == "123"); + + a = -a; + assert(a == -123n); + assert(a.toString() == "-123"); + + a = -a; + assert(a == 123n); + assert(a.toString() == "123"); + + let e: bigint; + assert(a == 123n); + assert(a.toString() == "123"); + e = -a; + + // Check that original value does not change + assert(a == 123n); + assert(a.toString() == "123"); + assert(e == -123n); + assert(e.toString() == "-123"); + e = a; + assert(e == 123n); + assert(e.toString() == "123"); + + let b = -123n; + assert(b == -123n) + assert(b.toString() == "-123"); + + let c = -(123n); + assert(c == -123n) + assert(c.toString() == "-123"); + + // Double unary minus + let d = -(-123n); + assert(d == 123n); + assert(d.toString() == "123"); + + // Triple unary minux + let f = -(-(-123n)); + assert(f == -123n); + assert(f.toString() == "-123"); + + a = new BigInt(321); + assert(a.toString() == "321") + assert(a == 321n) + + b = -a; + assert(a.toString() == "321") + assert(a == 321n) + assert(b == -321n); + assert(b.toString() == "-321"); +} + +function test_multiplication(): void { + const a = 23443495146314363289895841n + const b = 245000234343499329134n + const c = -245000234343499329134n + + /* Multiplication testing (*) */ + assert 978667632325344545n * 4534000101n == 4437279143808543031889799045n + assert a * b == 5743661804677708098900659843374372544236731694n + assert a * c == -5743661804677708098900659843374372544236731694n + assert a * 0n == 0n + assert c * 0n == 0n + + + /* Division testing (/) */ + assert 39735235034886462n / 89221422n == 445355321n + assert a / b == 95687n + assert a / c == -95687n + assert 0n / a == 0n + + let err = false; + try { + a / 0n + } catch (e) { + if (e instanceof Error) { + err = true + } + } + assert err + + /* Remainder of the division (%) */ + assert 493433405047004109n % 111114444n == 18100749n + assert a % b == a % c + assert 0n % a == 0n + + err = false; + try { + a % 0n + } catch (e) { + if (e instanceof Error) { + err = true + } + } + assert err +} + +function test_addition_1(): void { + const a = 97567789101304567800013210071n + const b = -533923234343411557221n + const c = 0n; + + /* Minus testing (-) */ + assert (-a == -97567789101304567800013210071n) + assert (-b == 533923234343411557221n) + assert (-c == -0n) + assert (-(-a) == a) + assert (-(-b) == b) + assert (-(-c) == c) + + /* Plus testing (+) */ + assert +a == a + assert +b == b + assert +c == 0n +} + +function test_addition_2(): void { + const a = 18446744073709551616n; + const b = 36893488147419103232n; + const c = -10000000000000000000n; + + /* Addition testing (+) */ + assert 999999999999999n + 1n == 1000000000000000n + assert a + b == 55340232221128654848n + assert a + a == b + assert a + c == 8446744073709551616n + assert a + b + b == 92233720368547758080n +} + +function test_subtraction(): void { + const a = 18446744073709551616n; + const b = 36893488147419103232n; + const c = -10000000000000000000n; + + // /* Subtraction testing (-) */ + assert 999999999999999n - 1n == 999999999999998n + assert b - a == a + assert a - b == -18446744073709551616n + assert b - a - a == 0n +} + +function test_inc_dec(): void { + const a = 340282366920938463463374607431768211456n + const b = -2313455919991034304490n + + /* Increment testing */ + /* Decrement testing */ +} + +function test_shift(): void { + const a = 245599210405555256299145n + + /* Testing left shift (<<) */ + assert a << 100n == 311333986486181324779687697000809288883015536628203520n + assert a << 0n == a + + /* Testing right shift (>>) */ + assert a >> 60n == 213023n + assert a >> 0n == a +} + +function test_bitwise(): void { + const a = 123456789123456789123456789123456789123456789123456789n + let b = 123456790n + const zero = 0n + + /* Testing bitwise NOT (~) */ + assert ~zero == -1n + assert ~a == -123456789123456789123456789123456789123456789123456790n + + /* Testing bitwise AND (&) */ + /* Testing bitwise XOR (^) */ + /* Testing bitwise OR (|) */ +} + +function main() : void { + test_create_empty_bigint(); + test_bigint_as_string(); + test_invalid_bigint(); + test_multiply(); + test_plus(); + test_minus(); + test_unary_minus(); + test_divide(); + test_module(); + test_bitwise_and(); + test_bitwise_or(); + test_bitwise_xor(); + test_left_shift(); + test_right_shift(); + test_type(); + test_assignment(); + test_compare(); + test_literals(); + test_cast(); + test_bigint_methods(); + test_unary(); + test_multiplication(); + test_addition_1(); + test_addition_2(); + test_subtraction(); + test_inc_dec(); + test_shift(); + test_bitwise(); +} diff --git a/ets2panda/test/runtime/ets/BitwiseOperationsOnFloat.ets b/ets2panda/test/runtime/ets/BitwiseOperationsOnFloat.ets new file mode 100644 index 0000000000000000000000000000000000000000..816928325c8749a9a27469d3161a1d996577f7a9 --- /dev/null +++ b/ets2panda/test/runtime/ets/BitwiseOperationsOnFloat.ets @@ -0,0 +1,252 @@ +/* + * Copyright (c) 2023 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. + */ + +function And(a: double, b: double): long { + return a & b +} + +function Or(a: double, b: double): long { + return a | b +} + +function Xor(a: double, b: double): long { + return a ^ b +} + +function LeftShift(a: double, b: double): long { + return a << b +} + +function RightShift(a: double, b: double): long { + return a >> b +} + +function UnsignedRightShift(a: double, b: double): long { + return a >>> b +} + +function Inversion(a: double): long { + return ~a; +} + +function main(): void { + /* ---- Compile time tests ---- */ + + // Testing "and" operator: + assert (542.910991 & -1903.2040221) == 16 + assert (-542.910991 & 1903.2040221) == 1378 + assert (-542.910991 & -1903.2040221) == -1920 + assert (9E120 & 56.75) == 56 + assert (0.0 & 0.0) == 0 + assert (NaN & 42.131330352) == 0 + assert (-NaN & -23432.34110144432) == 0 + assert (Infinity & -94.24445985981884) == 9223372036854775714 + assert (-Infinity & 94.24445985981884) == 0 + + // Testing "or" operator: + assert (542.910991 | 1903.2040221) == 1919 + assert (542.910991 | -1903.2040221) == -1377 + assert (-542.910991 | 1903.2040221) == -17 + assert (-542.910991 | -1903.2040221) == -525 + assert (9E120 | 0) == 9223372036854775807 + assert (824E3 | 21.018763) == 824021 + assert (1.0 | 0.1) == 1 + assert (NaN | 0.2) == 0 + assert (-NaN | 0.3) == 0 + assert (Infinity | 0.4) == 9223372036854775807 + assert (-Infinity | 0.5) == -9223372036854775808 + + // Testing "xor" operator: + assert (542.910991 ^ 1903.2040221) == 1393 + assert (542.910991 ^ -1903.2040221) == -1393 + assert (-542.910991 ^ 1903.2040221) == -1395 + assert (-542.910991 ^ -1903.2040221) == 1395 + assert (49509.2348100001 ^ 49509.2348100001) == 0 + assert (9E120 ^ 1.2) == 9223372036854775806 + assert (824E3 ^ 21.018763) == 824021 + assert (NaN ^ 99854258.24) == 99854258 + assert (-NaN ^ 30483040.293244) == 30483040 + assert (Infinity ^ 1.2) == 9223372036854775806 + assert (-Infinity ^ 10049329.80001) == -9223372036844726479 + + // Testing "left shift" operator: + assert (1E-100 << 0.0) == 0 + assert (0.00003 << 12.13) == 0 + assert (42.109 << 0.0120939) == 42 + assert (1.409240940 << 17.3) == 131072 + assert (4342435.309421 << 3.1) == 34739480 + assert (9010034745.3449093132 << 7.000000000001) == 1153284447360 + assert (-423.14981 << 20.32) == -443547648 + assert (500.13 << 128.3440) == 500 + assert (500.45 << 121.10000002) == -1729382256910270464 + assert (NaN << 330.3911) == 0 + assert (-NaN << 12.91213) == 0 + assert (Infinity << 1.0092) == -2 + assert (-Infinity << 1.0092) == 0 + assert (-52242.2301 << -8.7) == -1297036692682702848 + assert (52242.2301 << -8.7) == 1297036692682702848 + + // Testing "right shift" operator: + assert (1E-100 >> 0.0) == 0 + assert (0.00003 >> 12.13) == 0 + assert (42.109 >> 0.0120939) == 42 + assert (1.409240940 >> 17.3) == 0 + assert (4342435.309421 >> 3.1) == 542804 + assert (9010034.3449093132 >> 3.000000000001) == 1126254 + assert (-4599090490.24 >> 11) == -2245650 + assert (500.13 >> 128.3440) == 500 + assert (500.45 >> 121.10000002) == 0 + assert (NaN >> 11.000003) == 0 + assert (-NaN >> 7.912130001) == 0 + assert (Infinity >> 61) == 3 + assert (-Infinity >> 61) == -4 + assert (132090941883.34343 >> -32.2) == 30 + assert (-132090941883.34343 >> -32.2) == -31 + + // Testing "unsigned right shift" operator: + assert (1E-100 >>> 0.0) == 0 + assert (0.00003 >>> 12.13) == 0 + assert (42.109 >>> 0.0120939) == 42 + assert (1.409240940 >>> 17.3) == 0 + assert (4342435.309421 >>> 3.1) == 542804 + assert (9010034.3449093132 >>> 3.000000000001) == 1126254 + assert (-4599090490.24 >>> 11) == 9007199252495342 + assert (500.13 >>> 128.3440) == 500 + assert (500.45 >>> 121.10000002) == 0 + assert (NaN >>> 11.000003) == 0 + assert (-NaN >>> 7.912130001) == 0 + assert (Infinity >>> 61.8) == 3 + assert (-Infinity >>> 61.8) == 4 + assert (132090941883.34343 >>> -32.2) == 30 + assert (-132090941883.34343 >>> -32.2) == 4294967265 + + // Testing "bitwise complement" operator + assert ~0 == -1 + assert ~0.000034 == -1 + assert ~39530.93 == -39531 + assert ~93718001.5424230894 == -93718002 + assert ~Infinity == -9223372036854775808 + assert ~-Infinity == 9223372036854775807 + assert ~NaN == -1 + assert ~-NaN == -1 + assert ~1E210 == -9223372036854775808 + assert ~-1E210 == 9223372036854775807 + assert ~56E5 == -5600001 + assert ~-56E5 == 5599999 + + /* ---- Run time tests ---- */ + + // Testing "and" operator: + assert And(542.910991, -1903.2040221) == 16 + assert And(-542.910991, 1903.2040221) == 1378 + assert And(-542.910991, -1903.2040221) == -1920 + assert And(9E120, 56.75) == 56 + assert And(0.0, 0.0) == 0 + assert And(NaN, 42.131330352) == 0 + assert And(-NaN, -23432.34110144432) == 0 + assert And(Infinity, -94.24445985981884) == 9223372036854775714 + assert And(-Infinity, 94.24445985981884) == 0 + + // Testing "or" operator: + assert Or(542.910991, 1903.2040221) == 1919 + assert Or(542.910991, -1903.2040221) == -1377 + assert Or(-542.910991, 1903.2040221) == -17 + assert Or(-542.910991, -1903.2040221) == -525 + assert Or(9E120, 0) == 9223372036854775807 + assert Or(824E3, 21.018763) == 824021 + assert Or(1.0, 0.1) == 1 + assert Or(NaN, 0.2) == 0 + assert Or(-NaN, 0.3) == 0 + assert Or(Infinity, 0.4) == 9223372036854775807 + assert Or(-Infinity, 0.5) == -9223372036854775808 + + // Testing "xor" operator: + assert Xor(542.910991, 1903.2040221) == 1393 + assert Xor(542.910991, -1903.2040221) == -1393 + assert Xor(-542.910991, 1903.2040221) == -1395 + assert Xor(-542.910991, -1903.2040221) == 1395 + assert Xor(49509.2348100001, 49509.2348100001) == 0 + assert Xor(9E120, 1.2) == 9223372036854775806 + assert Xor(824E3, 21.018763) == 824021 + assert Xor(NaN, 99854258.24) == 99854258 + assert Xor(-NaN, 30483040.293244) == 30483040 + assert Xor(Infinity, 1.2) == 9223372036854775806 + assert Xor(-Infinity, 10049329.80001) == -9223372036844726479 + + // Testing "left shift" operator: + assert LeftShift(1E-100, 0.0) == 0 + assert LeftShift(0.00003, 12.13) == 0 + assert LeftShift(42.109, 0.0120939) == 42 + assert LeftShift(1.409240940, 17.3) == 131072 + assert LeftShift(4342435.309421, 3.1) == 34739480 + assert LeftShift(9010034745.3449093132, 7.000000000001) == 1153284447360 + assert LeftShift(-423.14981, 20.32) == -443547648 + assert LeftShift(500.13, 128.3440) == 500 + assert LeftShift(500.45, 121.10000002) == -1729382256910270464 + assert LeftShift(NaN, 330.3911) == 0 + assert LeftShift(-NaN, 12.91213) == 0 + assert LeftShift(Infinity, 1.0092) == -2 + assert LeftShift(-Infinity, 1.0092) == 0 + assert LeftShift(-52242.2301, -8.7) == -1297036692682702848 + assert LeftShift(52242.2301,-8.7) == 1297036692682702848 + + // Testing "right shift" operator: + assert RightShift(1E-100, 0.0) == 0 + assert RightShift(0.00003, 12.13) == 0 + assert RightShift(42.109, 0.0120939) == 42 + assert RightShift(1.409240940, 17.3) == 0 + assert RightShift(4342435.309421, 3.1) == 542804 + assert RightShift(9010034.3449093132, 3.000000000001) == 1126254 + assert RightShift(-4599090490.24, 11) == -2245650 + assert RightShift(500.13, 128.3440) == 500 + assert RightShift(500.45, 121.10000002) == 0 + assert RightShift(NaN, 11.000003) == 0 + assert RightShift(-NaN, 7.912130001) == 0 + assert RightShift(Infinity, 61) == 3 + assert RightShift(-Infinity, 61) == -4 + assert RightShift(132090941883.34343, -32.2) == 30 + assert RightShift(-132090941883.34343, -32.2) == -31 + + // Testing "unsigned right shift" operator: + assert UnsignedRightShift(1E-100, 0.0) == 0 + assert UnsignedRightShift(0.00003,12.13) == 0 + assert UnsignedRightShift(42.109, 0.0120939) == 42 + assert UnsignedRightShift(1.409240940, 17.3) == 0 + assert UnsignedRightShift(4342435.309421, 3.1) == 542804 + assert UnsignedRightShift(9010034.3449093132, 3.000000000001) == 1126254 + assert UnsignedRightShift(-4599090490.24, 11) == 9007199252495342 + assert UnsignedRightShift(500.13, 128.3440) == 500 + assert UnsignedRightShift(500.45, 121.10000002) == 0 + assert UnsignedRightShift(NaN, 11.000003) == 0 + assert UnsignedRightShift(-NaN, 7.912130001) == 0 + assert UnsignedRightShift(Infinity, 61.8) == 3 + assert UnsignedRightShift(-Infinity, 61.8) == 4 + assert UnsignedRightShift(132090941883.34343, -32.2) == 30 + assert UnsignedRightShift(-132090941883.34343, -32.2) == 4294967265 + + // Testing "bitwise complement" operator + assert Inversion(0) == -1 + assert Inversion(0.000034) == -1 + assert Inversion(39530.93) == -39531 + assert Inversion(93718001.5424230894) == -93718002 + assert Inversion(Infinity) == -9223372036854775808 + assert Inversion(-Infinity) == 9223372036854775807 + assert Inversion(NaN) == -1 + assert Inversion(-NaN) == -1 + assert Inversion(1E210) == -9223372036854775808 + assert Inversion(-1E210) == 9223372036854775807 + assert Inversion(56E5) == -5600001 + assert Inversion(-56E5) == 5599999 +} diff --git a/ets2panda/test/runtime/ets/InterfaceOverrideReturnTypes.ets b/ets2panda/test/runtime/ets/InterfaceOverrideReturnTypes.ets new file mode 100644 index 0000000000000000000000000000000000000000..87e57dfd1cfe85a7c12a5c7a82774664b8394819 --- /dev/null +++ b/ets2panda/test/runtime/ets/InterfaceOverrideReturnTypes.ets @@ -0,0 +1,58 @@ +/* + * Copyright (c) 2022-2023 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. + */ + +interface A { + foo(): A +} + +interface B extends A { + foo(): B +} + +class C implements A { + private value: string; + + foo(): A { + this.value = "foo(): A" + return new C(); + } + + getValue(): string { + return this.value; + } +} + +class D implements B { + private value: string; + + foo(): B { + this.value = "foo(): B" + return new D(); + } + + getValue(): string { + return this.value; + } +} + +function main() { + let c = new C(); + c.foo(); + assert c.getValue() == "foo(): A" + + let d = new D(); + d.foo(); + assert d.getValue() == "foo(): B" +} diff --git a/ets2panda/test/runtime/ets/NoConstraint.ets b/ets2panda/test/runtime/ets/NoConstraint.ets new file mode 100644 index 0000000000000000000000000000000000000000..7c54f31ebbdc9146bb92fd75be8d9366c5b8b230 --- /dev/null +++ b/ets2panda/test/runtime/ets/NoConstraint.ets @@ -0,0 +1,29 @@ +/* + * Copyright (c) 2023 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. + */ + +type NullishFoo = Object | null | undefined; + +function foo(x: T): NullishFoo { + return x; +} + +function bar(x: T): NullishFoo { + return x; +} + +function main() { + foo(new Object()); + bar(new Object()); +} diff --git a/ets2panda/test/runtime/ets/array-object.ets b/ets2panda/test/runtime/ets/array-object.ets index 0228add708c70ff3c90a15eaccdabda4c6a1bd83..9e656739d90180635a2f7d387eb97009f885f8cb 100644 --- a/ets2panda/test/runtime/ets/array-object.ets +++ b/ets2panda/test/runtime/ets/array-object.ets @@ -27,11 +27,11 @@ function main(): void { object.toString(); // TypeError: Cannot access property of non-object or non-enum type -// arr1.hashCode(); -// arr2.hashCode(); -// object_array.hashCode(); +// arr1.$_hashCode(); +// arr2.$_hashCode(); +// object_array.$_hashCode(); - object.hashCode(); + object.$_hashCode(); assert(arr1 == arr1); assert(arr1 == object_array); diff --git a/ets2panda/test/runtime/ets/array_inf.ets b/ets2panda/test/runtime/ets/array_inf.ets new file mode 100644 index 0000000000000000000000000000000000000000..5c09324c73c9a65d126c415696b3276b2640b7e5 --- /dev/null +++ b/ets2panda/test/runtime/ets/array_inf.ets @@ -0,0 +1,27 @@ +class A { + foo(p: Object[]): int { + let s = 0 + for (let v of p) { + s += v instanceof A ? 1 : 0 + } + return s + } + bar(p: A[]): int { + let s = 0 + for (let v of p) { + s += v instanceof A ? 1 : 0 + } + return s + } +} + + +class B extends A{} + +function main() { + assert new A().foo([new Object(), new Long(), new Int()]) == 0 + assert new A().foo([new A(), new A(), new Object()]) == 2 + assert new A().foo(["aaa", new A(), new Object()]) == 1 + assert new A().foo([1, "hello", new A()]) == 1 + assert new A().bar([new B(), new B(), new A()]) == 3 +} diff --git a/ets2panda/test/runtime/ets/class-fields-same-name.ets b/ets2panda/test/runtime/ets/class-fields-same-name.ets new file mode 100644 index 0000000000000000000000000000000000000000..ab04034da7b64008c273c30d5b88f4c3fe2eeadc --- /dev/null +++ b/ets2panda/test/runtime/ets/class-fields-same-name.ets @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2023 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. + */ + +class C { + public static foo: int = 10 + public foo: int = 20 +} + +class D extends C { + public static foo: int = 30 + public foo: int = 40 +} + +function main(): void { + assert (C.foo == 10) + assert (new C().foo == 20) + assert (D.foo == 30) + assert (new D().foo == 40) +} diff --git a/ets2panda/test/runtime/ets/conditionalExpression.ets b/ets2panda/test/runtime/ets/conditionalExpression1.ets similarity index 100% rename from ets2panda/test/runtime/ets/conditionalExpression.ets rename to ets2panda/test/runtime/ets/conditionalExpression1.ets diff --git a/ets2panda/test/runtime/ets/conditionalExpression2.ets b/ets2panda/test/runtime/ets/conditionalExpression2.ets new file mode 100644 index 0000000000000000000000000000000000000000..59805a5873c2ec89786d3fe9a33f0ab90133a434 --- /dev/null +++ b/ets2panda/test/runtime/ets/conditionalExpression2.ets @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2021-2023 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. + */ + +function foo(form?: String) { + const f = (form == undefined) ? "abc" : form! + switch (f) { + case "abc": + return 41 + case "xyz": + return 42 + default: + return 0 + } +} + +class A{} + +function main(): void { + assert foo() == 41: "Error! foo() must be equal 41"; + assert foo("xyz") == 42: "Error! foo(\"xyz\") must be equal 42"; + assert foo("NFD") == 0: "Error! foo(\"NFD\") must be equal 0"; + let x = foo() == 41 ? new A() : undefined; + assert x instanceof A; + let y = foo("wxyz") == 42 ? "TRUE" : new A(); + assert y instanceof A; + y = "JK"; + assert y == "JK"; +} diff --git a/ets2panda/test/runtime/ets/conditionalExpressionLUB.ets b/ets2panda/test/runtime/ets/conditionalExpressionLUB.ets index 3b36957fdec43265bdb4526cf2e289a7754ab292..6d20bf0e10229ddeea97c3a82cdd287a56750fa8 100644 --- a/ets2panda/test/runtime/ets/conditionalExpressionLUB.ets +++ b/ets2panda/test/runtime/ets/conditionalExpressionLUB.ets @@ -61,23 +61,23 @@ function sameTypeLUB(): void { function objectLUB(): void { let a : A = new A(); let b : Int = 2; - let c = true ? a : b; // Object + let c = true ? a : b; // A | Int assert(foo(c) == 1); let arr : Int[] | null = null; - let d = true ? a : arr; // Object + let d = true ? a : arr; // A | Int[] | null assert(foo(d) == 1); } function forkSubtypeLUB(): void { let a : F = new F(); let b : D = new D(); - let c = true ? a : b; // A + let c = true ? a : b; // F | D => call most specific foo(A) assert(foo(c) == 2); let d : A = new A(); - let e = true ? a : b; // A + let e = true ? a : d; // F | A => normalize to A assert(foo(e) == 2); let f : B = new B(); - let g = true ? a : f; // B + let g = true ? a : f; // F | B => normalize to B assert(foo(g) == 3); } diff --git a/ets2panda/test/runtime/ets/generic-function1.ets b/ets2panda/test/runtime/ets/generic-function1.ets new file mode 100644 index 0000000000000000000000000000000000000000..dec1e8fb55ffea6de0cbbfc31fa12d3841f97670 --- /dev/null +++ b/ets2panda/test/runtime/ets/generic-function1.ets @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2022 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. + */ + +class A { + static instantiate(factory: () => T, content: () => void): T { + const instance = factory() + instance.__initializeStruct() + content() + return instance + } + __initializeStruct(): A { + return this + } +} + +class B extends A { + constructor() {} + override __initializeStruct(): A { + return this + } +} + +export function main(): int { + console.println("Start") + + B(){} + + return 0; +} diff --git a/ets2panda/test/test-lists/ets-runtime/ets-runtime-ignored.txt b/ets2panda/test/test-lists/ets-runtime/ets-runtime-ignored.txt index 586ace81baf350d3b57dcb6aa0e61024e69607a4..b4b2ab58ce345a0b98abebf54c3e0ef1727ba4e5 100644 --- a/ets2panda/test/test-lists/ets-runtime/ets-runtime-ignored.txt +++ b/ets2panda/test/test-lists/ets-runtime/ets-runtime-ignored.txt @@ -34,3 +34,13 @@ trailing-lambda-with-capture.ets # ignored until union types are properly implemented and non nullish base type of array types can be properly handled notNullMultidimensionalArray.ets + +# ignored until verifier can't handle if a field name can be static and non-static at the same time +class-fields-same-name.ets + +# Disabled temporarily #I8EM2T implementation struct directly expanded to class +struct-identifier.ets +struct-init.ets +struct-init2.ets +struct_implements.ets +top_level_03.ets diff --git a/ets2panda/test/test-lists/parser/parser-ets-ignored.txt b/ets2panda/test/test-lists/parser/parser-ets-ignored.txt index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..de27323be467022892a7ff1d56c6205e070690fa 100644 --- a/ets2panda/test/test-lists/parser/parser-ets-ignored.txt +++ b/ets2panda/test/test-lists/parser/parser-ets-ignored.txt @@ -0,0 +1,13 @@ +parser/ets/test-type-alias-call7.ets +parser/ets/test-type-alias-call8.ets + +# Disabled temporarily #I8EM2T implementation struct directly expanded to class +parser/ets/struct_init.ets +parser/ets/struct_static_initializer.ets +parser/ets/struct_identifier.ets +parser/ets/struct_invalid_extends1.ets +parser/ets/struct_templete.ets +parser/ets/import_tests/modules/struct_module.ets +parser/ets/import_tests/check_exported_default_struct.ets +parser/ets/import_tests/modules/struct_default_module.ets +parser/ets/import_tests/check_exported_struct.ets diff --git a/ets2panda/test/test-lists/parser/parser-js-ignored.txt b/ets2panda/test/test-lists/parser/parser-js-ignored.txt index 49f4f01669340ff604b4971beeec37ff7c5e0fc0..a0cac35d0e8d349ebf833c8793d6cfe4aae7a44a 100644 --- a/ets2panda/test/test-lists/parser/parser-js-ignored.txt +++ b/ets2panda/test/test-lists/parser/parser-js-ignored.txt @@ -69,3 +69,12 @@ parser/ets/trailing_lambda_tests/trailing_lambda_define_lambda_in_body_capture_v # Bad test shadows Object with type parameter name #14913 compiler/ets/override13.ets + +# 15095 +compiler/ets/methodOverrideCovariantReturnType.ets +compiler/ets/override16.ets +compiler/ets/override17.ets +parser/ets/static_function_hide_2.ets + +# 14595 +compiler/ets/n_assignGenericWithNullableTypeParamToNonNullable.ets diff --git a/ets2panda/test/unit/union_normalization_test.cpp b/ets2panda/test/unit/union_normalization_test.cpp index 6da53b1a0bbed13429a1f015ea7c33197ee3a60a..cbffadb1fd445630a1b796dc48840e4f111a6dc0 100644 --- a/ets2panda/test/unit/union_normalization_test.cpp +++ b/ets2panda/test/unit/union_normalization_test.cpp @@ -433,6 +433,54 @@ TEST_F(UnionNormalizationTest, UnionLinearization) ASSERT_EQ(ut3->ConstituentTypes().at(IDX2), checker.GetGlobalTypesHolder()->GlobalDoubleBuiltinType()); } +TEST_F(UnionNormalizationTest, UnionStringLiterals) +{ + // NOLINTNEXTLINE(modernize-avoid-c-arrays) + const char *argv = "../../../bin/es2panda"; + checker::ETSChecker checker; + auto program = parser::Program::NewProgram(Allocator()); + InitializeChecker(&argv, "_.ets", "", &checker, &program); + + // Test normalization: string | "abc" ==> string + ArenaVector union_constituents1(checker.Allocator()->Adapter()); + union_constituents1.emplace_back(checker.GlobalBuiltinETSStringType()); + union_constituents1.emplace_back(checker.CreateETSStringLiteralType("abc")); + + // Create union type, which will be normalized inside creation function + auto *const normalized_type1 = checker.CreateETSUnionType(std::move(union_constituents1)); + ASSERT_NE(normalized_type1, nullptr); + ASSERT_TRUE(normalized_type1->IsETSObjectType()); + ASSERT_EQ(normalized_type1, checker.GlobalBuiltinETSStringType()); + + // Test normalization: "abc" | string | string ==> string + ArenaVector union_constituents2(checker.Allocator()->Adapter()); + union_constituents2.emplace_back(checker.CreateETSStringLiteralType("abc")); + union_constituents2.emplace_back(checker.GlobalBuiltinETSStringType()); + union_constituents2.emplace_back(checker.GlobalBuiltinETSStringType()); + + // Create union type, which will be normalized inside creation function + auto *const normalized_type2 = checker.CreateETSUnionType(std::move(union_constituents2)); + ASSERT_NE(normalized_type2, nullptr); + ASSERT_TRUE(normalized_type2->IsETSObjectType()); + ASSERT_EQ(normalized_type2, checker.GlobalBuiltinETSStringType()); + + // Test normalization: number | "abc" | string | "xy" ==> number | string + ArenaVector union_constituents3(checker.Allocator()->Adapter()); + union_constituents3.emplace_back(checker.GlobalDoubleType()); + union_constituents3.emplace_back(checker.CreateETSStringLiteralType("abc")); + union_constituents3.emplace_back(checker.GlobalBuiltinETSStringType()); + union_constituents3.emplace_back(checker.CreateETSStringLiteralType("xy")); + + // Create union type, which will be normalized inside creation function + auto *const normalized_type3 = checker.CreateETSUnionType(std::move(union_constituents3)); + ASSERT_NE(normalized_type3, nullptr); + ASSERT_TRUE(normalized_type3->IsETSUnionType()); + auto *const union_type = normalized_type3->AsETSUnionType(); + ASSERT_EQ(union_type->ConstituentTypes().size(), SIZE2); + ASSERT_EQ(union_type->ConstituentTypes().at(IDX0), checker.GetGlobalTypesHolder()->GlobalDoubleBuiltinType()); + ASSERT_EQ(union_type->ConstituentTypes().at(IDX1), checker.GlobalBuiltinETSStringType()); +} + TEST_F(UnionNormalizationTest, UnionWithNever) { // Test normalization: int | never | number ==> number diff --git a/ets2panda/varbinder/scope.cpp b/ets2panda/varbinder/scope.cpp index 7d685b6aa3439e9acc1d4260e72e85fd14256729..46c3c1366c19ee242cf4bc99a65e19554a1fa31b 100644 --- a/ets2panda/varbinder/scope.cpp +++ b/ets2panda/varbinder/scope.cpp @@ -744,8 +744,18 @@ Variable *ClassScope::AddBinding(ArenaAllocator *allocator, [[maybe_unused]] Var SetBindingProps(new_decl, &props, is_static); - if (FindLocal(new_decl->Name(), ResolveBindingOptions::ALL) != nullptr) { - return nullptr; + const auto *found_var = FindLocal(new_decl->Name(), ResolveBindingOptions::ALL); + if (found_var != nullptr) { + if (!new_decl->IsLetOrConstDecl()) { + return nullptr; + } + + found_var = FindLocal(new_decl->Name(), + ResolveBindingOptions::ALL ^ (is_static ? ResolveBindingOptions::VARIABLES + : ResolveBindingOptions::STATIC_VARIABLES)); + if (found_var != nullptr) { + return nullptr; + } } auto *var = props.GetTargetScope()->AddBinding(allocator, nullptr, new_decl, extension);