From 696a5b6c68dd8448c0b91157422a91106970d777 Mon Sep 17 00:00:00 2001 From: turgutbababalim Date: Sun, 25 May 2025 23:24:14 +0300 Subject: [PATCH] Set node from function arguments Issue: ICADES Description: Relation node is nullptr on etsEnumType AssignmentSource which causes a crash Signed-off-by: turgutbababalim --- ets2panda/checker/ets/function.cpp | 43 +++++++++++++++++++++ ets2panda/checker/types/ets/etsEnumType.cpp | 4 ++ 2 files changed, 47 insertions(+) diff --git a/ets2panda/checker/ets/function.cpp b/ets2panda/checker/ets/function.cpp index 40338b0c4a..d073550e4a 100644 --- a/ets2panda/checker/ets/function.cpp +++ b/ets2panda/checker/ets/function.cpp @@ -1130,12 +1130,22 @@ ArenaMultiMap ETSChecker::GetSuitableSignaturesForParameter // NOTE: first we choose the some signature with possibly widest argumetns' types // Then we search for the most specific signature InitMostSpecificType(Relation(), signatures, mostSpecificType, prevSig, i); + bool hasEnumSignature = false; + arguments.at(i)->RemoveAstNodeFlags(ir::AstNodeFlags::GENERATE_VALUE_OF); + for (auto *sig : signatures) { + hasEnumSignature = GetParameterTypeOrRestAtIdx(this, sig, i)->IsETSEnumType(); + } + if (hasEnumSignature) { + arguments.at(i)->RemoveAstNodeFlags(ir::AstNodeFlags::GENERATE_VALUE_OF); + } + Relation()->SetNode(arguments.at(i)); for (auto *sig : signatures) { SearchAmongMostSpecificTypes(mostSpecificType, prevSig, std::make_tuple(pos, i, sig), true); } for (auto *sig : signatures) { SearchAmongMostSpecificTypes(mostSpecificType, prevSig, std::make_tuple(pos, i, sig), false); } + Relation()->SetNode(nullptr); for (auto *sig : signatures) { Type *sigType = GetParameterTypeOrRestAtIdx(this, sig, i); @@ -2447,6 +2457,33 @@ size_t &ETSChecker::ConstraintCheckScopesCount() return constraintCheckScopesCount_; } +static void GetGenericDepth(ETSObjectType *object, size_t &depth) +{ + // To check for generic type depth, such as comparing Array and Array>, + // we iterate each type argument recursively. Array and Array> should be considered + // two different types and their depths should be checked. + for (auto *arg : object->TypeArguments()) { + if (arg->IsETSObjectType() && !arg->AsETSObjectType()->TypeArguments().empty()) { + depth++; + GetGenericDepth(arg->AsETSObjectType(), depth); + } + } +} + +static bool CheckTypeArguments(ETSObjectType *obj1, ETSObjectType *obj2) +{ + if (!(obj1->HasObjectFlag(ETSObjectFlags::BUILTIN_ARRAY) && obj2->HasObjectFlag(ETSObjectFlags::BUILTIN_ARRAY))) { + return true; + } + + size_t depth1 = 0; + size_t depth2 = 0; + GetGenericDepth(obj1, depth1); + GetGenericDepth(obj2, depth2); + + return depth1 == depth2; +} + bool ETSChecker::HasSameAssemblySignature(Signature const *const sig1, Signature const *const sig2) noexcept { if (sig1->ReturnType()->ToAssemblerTypeWithRank() != sig2->ReturnType()->ToAssemblerTypeWithRank()) { @@ -2458,6 +2495,12 @@ bool ETSChecker::HasSameAssemblySignature(Signature const *const sig1, Signature } for (size_t ix = 0U; ix < sig1->Params().size(); ++ix) { + if (sig1->Params()[ix]->TsType()->IsETSObjectType() && sig2->Params()[ix]->TsType()->IsETSObjectType()) { + if (!CheckTypeArguments(sig1->Params()[ix]->TsType()->AsETSObjectType(), + sig2->Params()[ix]->TsType()->AsETSObjectType())) { + return false; + } + } if (sig1->Params()[ix]->TsType()->ToAssemblerTypeWithRank() != sig2->Params()[ix]->TsType()->ToAssemblerTypeWithRank()) { return false; diff --git a/ets2panda/checker/types/ets/etsEnumType.cpp b/ets2panda/checker/types/ets/etsEnumType.cpp index bea6d5044b..f714d0bf28 100644 --- a/ets2panda/checker/types/ets/etsEnumType.cpp +++ b/ets2panda/checker/types/ets/etsEnumType.cpp @@ -72,6 +72,10 @@ void ETSStringEnumType::CastTarget(TypeRelation *relation, Type *source) bool ETSIntEnumType::AssignmentSource(TypeRelation *relation, Type *target) { + if (relation->GetNode() == nullptr) { + return false; + } + bool result = false; if (target->IsETSObjectType()) { if (target->AsETSObjectType()->IsGlobalETSObjectType() || -- Gitee