diff --git a/compiler/backend-common/src/org/jetbrains/kotlin/backend/common/CodegenUtil.kt b/compiler/backend-common/src/org/jetbrains/kotlin/backend/common/CodegenUtil.kt index 23ea5c80d00..9a075ccee78 100644 --- a/compiler/backend-common/src/org/jetbrains/kotlin/backend/common/CodegenUtil.kt +++ b/compiler/backend-common/src/org/jetbrains/kotlin/backend/common/CodegenUtil.kt @@ -17,10 +17,11 @@ import org.jetbrains.kotlin.psi.* import org.jetbrains.kotlin.psi.psiUtil.hasExpectModifier import org.jetbrains.kotlin.resolve.BindingContext import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils -import org.jetbrains.kotlin.resolve.DescriptorUtils import org.jetbrains.kotlin.resolve.bindingContextUtil.isUsedAsExpression import org.jetbrains.kotlin.resolve.calls.util.getResolvedCall +import org.jetbrains.kotlin.resolve.descriptorUtil.module import org.jetbrains.kotlin.resolve.multiplatform.ExpectedActualResolver +import org.jetbrains.kotlin.resolve.multiplatform.onlyFromThisModule import org.jetbrains.kotlin.types.KotlinType import org.jetbrains.kotlin.util.getExceptionMessage import org.jetbrains.kotlin.util.getNonPrivateTraitMembersForDelegation @@ -182,7 +183,7 @@ object CodegenUtil { @JvmStatic fun findExpectedFunctionForActual(descriptor: FunctionDescriptor): FunctionDescriptor? { val compatibleExpectedFunctions = with(ExpectedActualResolver) { - descriptor.findCompatibleExpectedForActual(DescriptorUtils.getContainingModule(descriptor)) + descriptor.findCompatibleExpectedForActual(onlyFromThisModule(descriptor.module)) } return compatibleExpectedFunctions.firstOrNull() as FunctionDescriptor? } diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectedActualDeclarationChecker.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectedActualDeclarationChecker.kt index 62da140acdc..e261ed65b27 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectedActualDeclarationChecker.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectedActualDeclarationChecker.kt @@ -30,11 +30,8 @@ import org.jetbrains.kotlin.resolve.constants.ConstantValue import org.jetbrains.kotlin.resolve.descriptorUtil.isAnnotationConstructor import org.jetbrains.kotlin.resolve.descriptorUtil.isPrimaryConstructorOfInlineClass import org.jetbrains.kotlin.resolve.descriptorUtil.module -import org.jetbrains.kotlin.resolve.multiplatform.ExpectActualCompatibility +import org.jetbrains.kotlin.resolve.multiplatform.* import org.jetbrains.kotlin.resolve.multiplatform.ExpectActualCompatibility.* -import org.jetbrains.kotlin.resolve.multiplatform.ExpectedActualResolver -import org.jetbrains.kotlin.resolve.multiplatform.ModuleFilter -import org.jetbrains.kotlin.resolve.multiplatform.OptionalAnnotationUtil import org.jetbrains.kotlin.resolve.source.KotlinSourceElement import org.jetbrains.kotlin.resolve.source.PsiSourceFile import org.jetbrains.kotlin.types.KotlinType @@ -69,13 +66,13 @@ class ExpectedActualDeclarationChecker( checkActualModifier, context.expectActualTracker ) } else if (descriptor.isActualOrSomeContainerIsActual()) { - val allImplementedModules = moduleStructureOracle.findAllDependsOnPaths(descriptor.module).flatMap { it.nodes }.toHashSet() + val allDependsOnModules = moduleStructureOracle.findAllDependsOnPaths(descriptor.module).flatMap { it.nodes }.toHashSet() checkActualDeclarationHasExpected( declaration, descriptor, checkActualModifier, context.trace, - moduleVisibilityFilter = { it in allImplementedModules } + moduleVisibilityFilter = { it in allDependsOnModules } ) } } @@ -222,7 +219,7 @@ class ExpectedActualDeclarationChecker( compatibility: Map, List> ): Boolean { return compatibility.values.flatMapTo(hashSetOf()) { it }.all { actual -> - val expectedOnes = ExpectedActualResolver.findExpectedForActual(actual, module) + val expectedOnes = ExpectedActualResolver.findExpectedForActual(actual, onlyFromThisModule(module)) expectedOnes != null && Compatible in expectedOnes.keys } } @@ -250,7 +247,7 @@ class ExpectedActualDeclarationChecker( trace: BindingTrace, moduleVisibilityFilter: ModuleFilter ) { - val compatibility = ExpectedActualResolver.findExpectedForActual(descriptor, descriptor.module, moduleVisibilityFilter) + val compatibility = ExpectedActualResolver.findExpectedForActual(descriptor, moduleVisibilityFilter) ?: return checkAmbiguousExpects(compatibility, trace, reportOn, descriptor) @@ -290,8 +287,7 @@ class ExpectedActualDeclarationChecker( actualMember.isExplicitActualDeclaration() && !incompatibility.allStrongIncompatibilities() && ExpectedActualResolver.findExpectedForActual( - actualMember, - expectedMember.module + actualMember, onlyFromThisModule(expectedMember.module) )?.values?.singleOrNull()?.singleOrNull() == expectedMember } diff --git a/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/ExpectDeclarationRemover.kt b/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/ExpectDeclarationRemover.kt index 02a56d93b01..b5d9651ba8c 100644 --- a/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/ExpectDeclarationRemover.kt +++ b/compiler/ir/backend.common/src/org/jetbrains/kotlin/backend/common/lower/ExpectDeclarationRemover.kt @@ -25,6 +25,7 @@ import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid import org.jetbrains.kotlin.resolve.descriptorUtil.module import org.jetbrains.kotlin.resolve.multiplatform.ExpectedActualResolver import org.jetbrains.kotlin.resolve.multiplatform.OptionalAnnotationUtil +import org.jetbrains.kotlin.resolve.multiplatform.onlyFromThisModule import org.jetbrains.kotlin.utils.addToStdlib.safeAs // `doRemove` means should expect-declaration be removed from IR @@ -143,7 +144,7 @@ class ExpectDeclarationRemover(val symbolTable: ReferenceSymbolTable, private va private fun MemberDescriptor.findExpectForActual(): MemberDescriptor? { if (!isActual) error(this) return with(ExpectedActualResolver) { - findCompatibleExpectedForActual(this@findExpectForActual.module).singleOrNull() + findCompatibleExpectedForActual(onlyFromThisModule(this@findExpectForActual.module)).singleOrNull() } } diff --git a/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/components/ArgumentsUtils.kt b/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/components/ArgumentsUtils.kt index 4ea556029d7..7dd48f84302 100644 --- a/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/components/ArgumentsUtils.kt +++ b/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/components/ArgumentsUtils.kt @@ -26,7 +26,7 @@ import org.jetbrains.kotlin.resolve.calls.model.CollectionLiteralKotlinCallArgum import org.jetbrains.kotlin.resolve.calls.model.KotlinCallArgument import org.jetbrains.kotlin.resolve.calls.model.SimpleKotlinCallArgument import org.jetbrains.kotlin.resolve.descriptorUtil.isParameterOfAnnotation -import org.jetbrains.kotlin.resolve.descriptorUtil.module +import org.jetbrains.kotlin.resolve.multiplatform.ALL_MODULES import org.jetbrains.kotlin.resolve.multiplatform.ExpectedActualResolver import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValueWithSmartCastInfo import org.jetbrains.kotlin.types.UnwrappedType @@ -113,7 +113,7 @@ private fun ValueParameterDescriptor.checkExpectedParameter(checker: (ValueParam val function = containingDeclaration if (function is FunctionDescriptor && function.isActual) { with(ExpectedActualResolver) { - val expected = function.findCompatibleExpectedForActual(function.module).firstOrNull() + val expected = function.findCompatibleExpectedForActual(ALL_MODULES).firstOrNull() return expected is FunctionDescriptor && checker(expected.valueParameters[index]) } } diff --git a/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt b/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt index 6c10869d24d..45b35320e82 100644 --- a/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt +++ b/compiler/resolution/src/org/jetbrains/kotlin/resolve/multiplatform/ExpectedActualResolver.kt @@ -26,22 +26,22 @@ import org.jetbrains.kotlin.utils.keysToMap object ExpectedActualResolver { // FIXME(dsavvinov): review clients, as they won't work properly in HMPP projects fun MemberDescriptor.findCompatibleActualForExpected(platformModule: ModuleDescriptor): List = - findActualForExpected(this, platformModule)?.get(Compatible).orEmpty() + findActualForExpected(this, platformModule, onlyFromThisModule(platformModule))?.get(Compatible).orEmpty() fun MemberDescriptor.findAnyActualForExpected(platformModule: ModuleDescriptor): List { - val actualsGroupedByCompatibility = findActualForExpected(this, platformModule) + val actualsGroupedByCompatibility = findActualForExpected(this, platformModule, onlyFromThisModule(platformModule)) return actualsGroupedByCompatibility?.get(Compatible) ?: actualsGroupedByCompatibility?.values?.flatten() ?: emptyList() } - fun MemberDescriptor.findCompatibleExpectedForActual(commonModule: ModuleDescriptor): List = - findExpectedForActual(this, commonModule)?.get(Compatible).orEmpty() + fun MemberDescriptor.findCompatibleExpectedForActual(moduleFilter: ModuleFilter): List = + findExpectedForActual(this, moduleFilter)?.get(Compatible).orEmpty() fun findActualForExpected( expected: MemberDescriptor, platformModule: ModuleDescriptor, - moduleVisibilityFilter: ModuleFilter = onlyFromThisModule(platformModule) + moduleVisibilityFilter: ModuleFilter, ): Map, List>? { return when (expected) { is CallableMemberDescriptor -> { @@ -69,8 +69,7 @@ object ExpectedActualResolver { fun findExpectedForActual( actual: MemberDescriptor, - commonModule: ModuleDescriptor, - moduleFilter: (ModuleDescriptor) -> Boolean = onlyFromThisModule(commonModule) + moduleFilter: (ModuleDescriptor) -> Boolean ): Map, List>? { return when (actual) { is CallableMemberDescriptor -> { @@ -79,10 +78,10 @@ object ExpectedActualResolver { is ClassifierDescriptorWithTypeParameters -> { // TODO: replace with 'singleOrNull' as soon as multi-module diagnostic tests are refactored val expectedClass = - findExpectedForActual(container, commonModule, moduleFilter)?.values?.firstOrNull()?.firstOrNull() as? ClassDescriptor + findExpectedForActual(container, moduleFilter)?.values?.firstOrNull()?.firstOrNull() as? ClassDescriptor expectedClass?.getMembers(actual.name)?.filterIsInstance().orEmpty() } - is PackageFragmentDescriptor -> actual.findNamesakesFromModule(commonModule, moduleFilter) + is PackageFragmentDescriptor -> actual.findNamesakesFromModule(actual.module, moduleFilter) else -> return null // do not report anything for incorrect code, e.g. 'actual' local function } @@ -101,7 +100,7 @@ object ExpectedActualResolver { } } is ClassifierDescriptorWithTypeParameters -> { - actual.findClassifiersFromModule(commonModule, moduleFilter).filter { declaration -> + actual.findClassifiersFromModule(actual.module, moduleFilter).filter { declaration -> actual != declaration && declaration is ClassDescriptor && declaration.isExpect }.groupBy { expected -> @@ -534,19 +533,15 @@ object ExpectedActualResolver { } } -fun DeclarationDescriptor.findExpects(inModule: ModuleDescriptor = this.module): List { +fun DeclarationDescriptor.findExpects(): List { return ExpectedActualResolver.findExpectedForActual( - this as MemberDescriptor, - inModule, - { true } + this as MemberDescriptor, ALL_MODULES )?.get(Compatible).orEmpty() } fun DeclarationDescriptor.findActuals(inModule: ModuleDescriptor = this.module): List { return ExpectedActualResolver.findActualForExpected( - (this as MemberDescriptor), - inModule, - { true } + (this as MemberDescriptor), inModule, ALL_MODULES )?.get(Compatible).orEmpty() }