From 9a865e4c55ebc32a42f0bb41291590b36d818ebc Mon Sep 17 00:00:00 2001 From: Nikita Bobko Date: Wed, 15 Feb 2023 17:45:04 +0100 Subject: [PATCH] [FE 1.0] Issue a warning if expect and actual are declared in the same module The commit is based on b09561c3c3031879865505859b30f3e8e4033c1e Co-authored-by: Dmitriy Novozhilov ^KT-40904 Fixed ^KT-55177 Fixed Review: https://jetbrains.team/p/kt/reviews/8731 True negative test already exist: `compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/intermediateWithActualAndExpect.kt` --- ...CompilerTestFE10TestdataTestGenerated.java | 6 + ...irOldFrontendDiagnosticsTestGenerated.java | 6 + ...DiagnosticsWithLightTreeTestGenerated.java | 6 + .../jetbrains/kotlin/diagnostics/Errors.java | 2 + .../rendering/DefaultErrorMessages.java | 3 + .../resolve/PlatformConfiguratorBase.kt | 1 + .../ExpectActualInTheSameModuleChecker.kt | 66 +++++++++ .../expectActualLv14.kt | 2 + .../expectActualLv16.kt | 2 + .../tests/IncDecOperatorsInExpectClass.kt | 4 +- .../expectAndActualInTheSameModule.fir.kt | 64 +++++++++ .../expectAndActualInTheSameModule.kt | 64 +++++++++ .../expectAndActualInTheSameModule.txt | 130 ++++++++++++++++++ .../test/runners/DiagnosticTestGenerated.java | 6 + .../frontend/classic/ClassicFrontendFacade.kt | 4 +- .../common/test/jsCollectionFactories.kt | 1 + libraries/stdlib/common/test/testUtils.kt | 3 +- libraries/stdlib/jvm/test/js/StubsJVM.kt | 1 + libraries/stdlib/jvm/test/testUtilsJVM.kt | 3 +- 19 files changed, 368 insertions(+), 6 deletions(-) create mode 100644 compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectActualInTheSameModuleChecker.kt create mode 100644 compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.fir.kt create mode 100644 compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt create mode 100644 compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.txt diff --git a/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java b/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java index 9d570a7112a..0cd37e048f3 100644 --- a/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java +++ b/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java @@ -22002,6 +22002,12 @@ public class DiagnosisCompilerTestFE10TestdataTestGenerated extends AbstractDiag KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true); } + @Test + @TestMetadata("expectAndActualInTheSameModule.kt") + public void testExpectAndActualInTheSameModule() throws Exception { + runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt"); + } + @Test @TestMetadata("intermediateWithActualAndExpect.kt") public void testIntermediateWithActualAndExpect() throws Exception { diff --git a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java index 6ba25b5b08c..cf75b759237 100644 --- a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java +++ b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java @@ -22008,6 +22008,12 @@ public class FirOldFrontendDiagnosticsTestGenerated extends AbstractFirDiagnosti KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.*)\\.kts?$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true); } + @Test + @TestMetadata("expectAndActualInTheSameModule.kt") + public void testExpectAndActualInTheSameModule() throws Exception { + runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt"); + } + @Test @TestMetadata("intermediateWithActualAndExpect.kt") public void testIntermediateWithActualAndExpect() throws Exception { diff --git a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java index 442bba38811..dbec21849df 100644 --- a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java +++ b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java @@ -22002,6 +22002,12 @@ public class FirOldFrontendDiagnosticsWithLightTreeTestGenerated extends Abstrac KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true); } + @Test + @TestMetadata("expectAndActualInTheSameModule.kt") + public void testExpectAndActualInTheSameModule() throws Exception { + runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt"); + } + @Test @TestMetadata("intermediateWithActualAndExpect.kt") public void testIntermediateWithActualAndExpect() throws Exception { diff --git a/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/Errors.java b/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/Errors.java index 6fd95c75f19..cc290d3e415 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/Errors.java +++ b/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/Errors.java @@ -804,6 +804,8 @@ public interface Errors { DiagnosticFactory2.create(ERROR, ACTUAL_DECLARATION_NAME); DiagnosticFactory0 ACTUAL_MISSING = DiagnosticFactory0.create(ERROR, ACTUAL_DECLARATION_NAME); + DiagnosticFactory1 EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE = DiagnosticFactory1.create(WARNING, DECLARATION_NAME); + DiagnosticFactory0 OPTIONAL_EXPECTATION_NOT_ON_EXPECTED = DiagnosticFactory0.create(ERROR); DiagnosticFactory0 OPTIONAL_DECLARATION_OUTSIDE_OF_ANNOTATION_ENTRY = DiagnosticFactory0.create(ERROR); DiagnosticFactory0 OPTIONAL_DECLARATION_USAGE_IN_NON_COMMON_SOURCE = DiagnosticFactory0.create(ERROR); diff --git a/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/rendering/DefaultErrorMessages.java b/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/rendering/DefaultErrorMessages.java index 6747ce578b3..bc8cbacf765 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/rendering/DefaultErrorMessages.java +++ b/compiler/frontend/src/org/jetbrains/kotlin/diagnostics/rendering/DefaultErrorMessages.java @@ -339,6 +339,9 @@ public class DefaultErrorMessages { MAP.put(NO_ACTUAL_CLASS_MEMBER_FOR_EXPECTED_CLASS, "Actual class ''{0}'' has no corresponding members for expected class members:{1}", NAME, adaptGenerics2(IncompatibleExpectedActualClassScopesRenderer.TEXT)); MAP.put(ACTUAL_MISSING, "Declaration must be marked with 'actual'"); + MAP.put(EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE, + "{0}: expect and corresponding actual are declared in the same module, which will be prohibited in Kotlin 2.0. See https://youtrack.jetbrains.com/issue/KT-55177", + CAPITALIZED_DECLARATION_NAME_WITH_KIND_AND_PLATFORM); MAP.put(OPTIONAL_EXPECTATION_NOT_ON_EXPECTED, "'@OptionalExpectation' can only be used on an expected annotation class"); MAP.put(OPTIONAL_DECLARATION_OUTSIDE_OF_ANNOTATION_ENTRY, "Declaration annotated with '@OptionalExpectation' can only be used inside an annotation entry"); diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/PlatformConfiguratorBase.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/PlatformConfiguratorBase.kt index 8cba3c38c88..205e40fbd1e 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/PlatformConfiguratorBase.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/PlatformConfiguratorBase.kt @@ -14,6 +14,7 @@ import org.jetbrains.kotlin.resolve.lazy.DelegationFilter import org.jetbrains.kotlin.types.DynamicTypesSettings private val DEFAULT_DECLARATION_CHECKERS = listOf( + ExpectActualInTheSameModuleChecker, DataClassDeclarationChecker(), ConstModifierChecker, UnderscoreChecker, diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectActualInTheSameModuleChecker.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectActualInTheSameModuleChecker.kt new file mode 100644 index 00000000000..a4b6aa6d44a --- /dev/null +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/checkers/ExpectActualInTheSameModuleChecker.kt @@ -0,0 +1,66 @@ +/* + * Copyright 2010-2023 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.resolve.checkers + +import org.jetbrains.kotlin.config.LanguageFeature +import org.jetbrains.kotlin.descriptors.DeclarationDescriptor +import org.jetbrains.kotlin.descriptors.MemberDescriptor +import org.jetbrains.kotlin.descriptors.PackageFragmentDescriptor +import org.jetbrains.kotlin.diagnostics.Errors +import org.jetbrains.kotlin.platform.isCommon +import org.jetbrains.kotlin.psi.KtDeclaration +import org.jetbrains.kotlin.psi.KtNamedDeclaration +import org.jetbrains.kotlin.resolve.descriptorUtil.module +import org.jetbrains.kotlin.resolve.multiplatform.ExpectedActualResolver +import org.jetbrains.kotlin.resolve.multiplatform.isCommonSource +import org.jetbrains.kotlin.resolve.source.KotlinSourceElement + +object ExpectActualInTheSameModuleChecker : DeclarationChecker { + override fun check(declaration: KtDeclaration, descriptor: DeclarationDescriptor, context: DeclarationCheckerContext) { + if (!context.languageVersionSettings.supportsFeature(LanguageFeature.MultiPlatformProjects)) return + if (descriptor !is MemberDescriptor) return + if (declaration !is KtNamedDeclaration) return + if (!descriptor.isExpect) return + // Only look for top level actual members; class members will be handled as a part of that expected class + if (descriptor.containingDeclaration !is PackageFragmentDescriptor) return + val module = descriptor.module + val actuals = ExpectedActualResolver.findActualForExpected(descriptor, module)?.flatMap { it.value } + ?.takeIf(List::isNotEmpty) ?: return + + // There are 4 cases: + // 1. `expect` in common module, `actual` in platform module. It's a legal situation. In K2MetadataCompiler compiler, the + // declarations have different modules. In backend specific compiler, `expect` declaration is in common module so warning won't + // be issued + // 2. `expect` in common module X, `actual` in common module Y (Y depends on X). It's a legal situation. In K2MetadataCompiler + // compiler, the declarations have different modules. In backend specific compiler, `expect` declaration is in common so warning + // won't be issued + // 3. `expect` in common module X, `actual` in the very same common module X. It's an illegal situation. In K2MetadataCompiler + // compiler, the declarations have the same module, so the warning will be issue. In backend specific compiler, `expect` + // declaration is in common so warning won't be issued + // 4. `expect` in platform module X, `actual` in the very same platform module X. It's an illegal situation. K2MetadataCompiler is + // invoked only for common modules, so it won't issue a warning. In backend specific compiler, `expect` declaration is in + // platform module, the warning will be issued + // + // The checker doesn't consider cases when platform module depend on another platform module. + if (module.platform.isCommon()) { /* If true then we are in K2MetadataCompiler. `isCommon` never returns `true` in backend specific + compilers (even when the source is truly common) */ + // modules can be distinguished only in K2MetadataCompiler because in platform specific compiler all sources are put in + // a single module + if (actuals.all { it.module != module }) return + } else { // backend specific compiler + if (declaration.containingKtFile.isCommonSource == true) return + } + + context.trace.report(Errors.EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE.on(declaration, descriptor)) + for (actual in actuals) { + val actualSource = actual.declarationSource ?: continue + context.trace.report(Errors.EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE.on(actualSource, descriptor)) + } + } + + private val MemberDescriptor.declarationSource: KtNamedDeclaration? + get() = (this.source as? KotlinSourceElement)?.psi as? KtNamedDeclaration +} diff --git a/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv14.kt b/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv14.kt index 1584cbb7b84..50633ab4ccc 100644 --- a/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv14.kt +++ b/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv14.kt @@ -1,3 +1,5 @@ +@file:Suppress("EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE") + package test @Suppress("INLINE_CLASS_DEPRECATED", "EXPERIMENTAL_FEATURE_WARNING") diff --git a/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv16.kt b/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv16.kt index fd0a542f705..71d80a26d81 100644 --- a/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv16.kt +++ b/compiler/testData/compileKotlinAgainstCustomBinaries/actualTypealiasToCompiledInlineClass/expectActualLv16.kt @@ -1,3 +1,5 @@ +@file:Suppress("EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE") + package test @kotlin.jvm.JvmInline diff --git a/compiler/testData/diagnostics/tests/IncDecOperatorsInExpectClass.kt b/compiler/testData/diagnostics/tests/IncDecOperatorsInExpectClass.kt index 581eb66e89d..cb74ed08853 100644 --- a/compiler/testData/diagnostics/tests/IncDecOperatorsInExpectClass.kt +++ b/compiler/testData/diagnostics/tests/IncDecOperatorsInExpectClass.kt @@ -5,9 +5,9 @@ // SKIP_TXT // Issue: KT-49714 -expect class Counter { +expect class Counter { operator fun inc(): Counter operator fun dec(): Counter } -actual typealias Counter = Int +actual typealias Counter = Int diff --git a/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.fir.kt b/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.fir.kt new file mode 100644 index 00000000000..75505abc569 --- /dev/null +++ b/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.fir.kt @@ -0,0 +1,64 @@ +// MODULE: common +// TARGET_PLATFORM: Common +expect class CommonClass { + fun memberFun() + val memberProp: Int + class Nested + inner class Inner +} +actual class CommonClass { + actual fun memberFun() {} + actual val memberProp: Int = 42 + actual class Nested + actual inner class Inner +} + +expect fun commonFun() +actual fun commonFun() {} + +expect val commonProperty: String +actual val commonProperty: String + get() = "hello" + +// MODULE: intermediate()()(common) +// TARGET_PLATFORM: Common +expect class IntermediateClass { + fun memberFun() + val memberProp: Int + class Nested + inner class Inner +} +actual class IntermediateClass { + actual fun memberFun() {} + actual val memberProp: Int = 42 + actual class Nested + actual inner class Inner +} + +expect fun intermediateFun() +actual fun intermediateFun() {} + +expect val intermediateProperty: String +actual val intermediateProperty: String + get() = "hello" + +// MODULE: main()()(intermediate) +expect class PlatformClass { + fun memberFun() + val memberProp: Int + class Nested + inner class Inner +} +actual class PlatformClass { + actual fun memberFun() {} + actual val memberProp: Int = 42 + actual class Nested + actual inner class Inner +} + +expect fun platformFun() +actual fun platformFun() {} + +expect val platformProperty: String +actual val platformProperty: String + get() = "hello" diff --git a/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt b/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt new file mode 100644 index 00000000000..63ec3b9f719 --- /dev/null +++ b/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt @@ -0,0 +1,64 @@ +// MODULE: common +// TARGET_PLATFORM: Common +expect class CommonClass { + fun memberFun() + val memberProp: Int + class Nested + inner class Inner +} +actual class CommonClass { + actual fun memberFun() {} + actual val memberProp: Int = 42 + actual class Nested + actual inner class Inner +} + +expect fun commonFun() +actual fun commonFun() {} + +expect val commonProperty: String +actual val commonProperty: String + get() = "hello" + +// MODULE: intermediate()()(common) +// TARGET_PLATFORM: Common +expect class IntermediateClass { + fun memberFun() + val memberProp: Int + class Nested + inner class Inner +} +actual class IntermediateClass { + actual fun memberFun() {} + actual val memberProp: Int = 42 + actual class Nested + actual inner class Inner +} + +expect fun intermediateFun() +actual fun intermediateFun() {} + +expect val intermediateProperty: String +actual val intermediateProperty: String + get() = "hello" + +// MODULE: main()()(intermediate) +expect class PlatformClass { + fun memberFun() + val memberProp: Int + class Nested + inner class Inner +} +actual class PlatformClass { + actual fun memberFun() {} + actual val memberProp: Int = 42 + actual class Nested + actual inner class Inner +} + +expect fun platformFun() +actual fun platformFun() {} + +expect val platformProperty: String +actual val platformProperty: String + get() = "hello" diff --git a/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.txt b/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.txt new file mode 100644 index 00000000000..81c48285e94 --- /dev/null +++ b/compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.txt @@ -0,0 +1,130 @@ +// -- Module: -- +package + +public actual val commonProperty: kotlin.String +public expect val commonProperty: kotlin.String +public actual fun commonFun(): kotlin.Unit +public expect fun commonFun(): kotlin.Unit + +public final actual class CommonClass { + public constructor CommonClass() + public actual final val memberProp: kotlin.Int = 42 + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public final actual fun memberFun(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + + public final actual inner class Inner { + public constructor Inner() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } + + public final actual class Nested { + public constructor Nested() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } +} + +public final expect class CommonClass { + public expect final val memberProp: kotlin.Int + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public final expect fun memberFun(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + + public final expect inner class Inner { + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } + + public final expect class Nested { + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } +} + +// -- Module: -- +package + +public actual val intermediateProperty: kotlin.String +public expect val intermediateProperty: kotlin.String +public actual fun intermediateFun(): kotlin.Unit +public expect fun intermediateFun(): kotlin.Unit + +public final actual class IntermediateClass { + public constructor IntermediateClass() + public actual final val memberProp: kotlin.Int = 42 + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public final actual fun memberFun(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + + public final actual inner class Inner { + public constructor Inner() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } + + public final actual class Nested { + public constructor Nested() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } +} + +public final expect class IntermediateClass { + public expect final val memberProp: kotlin.Int + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public final expect fun memberFun(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + + public final expect inner class Inner { + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } + + public final expect class Nested { + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } +} + +// -- Module:
-- +package + +public actual val platformProperty: kotlin.String +public actual fun platformFun(): kotlin.Unit + +public final actual class PlatformClass { + public constructor PlatformClass() + public actual final val memberProp: kotlin.Int = 42 + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public final actual fun memberFun(): kotlin.Unit + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + + public final actual inner class Inner { + public constructor Inner() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } + + public final actual class Nested { + public constructor Nested() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + } +} diff --git a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java index 9fdcff72627..6fb615720b2 100644 --- a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java +++ b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java @@ -22008,6 +22008,12 @@ public class DiagnosticTestGenerated extends AbstractDiagnosticTest { KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.*)\\.kts?$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true); } + @Test + @TestMetadata("expectAndActualInTheSameModule.kt") + public void testExpectAndActualInTheSameModule() throws Exception { + runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/expectAndActualInTheSameModule.kt"); + } + @Test @TestMetadata("intermediateWithActualAndExpect.kt") public void testIntermediateWithActualAndExpect() throws Exception { diff --git a/compiler/tests-common-new/tests/org/jetbrains/kotlin/test/frontend/classic/ClassicFrontendFacade.kt b/compiler/tests-common-new/tests/org/jetbrains/kotlin/test/frontend/classic/ClassicFrontendFacade.kt index 0759a4f093c..5f94c49c10f 100644 --- a/compiler/tests-common-new/tests/org/jetbrains/kotlin/test/frontend/classic/ClassicFrontendFacade.kt +++ b/compiler/tests-common-new/tests/org/jetbrains/kotlin/test/frontend/classic/ClassicFrontendFacade.kt @@ -409,8 +409,8 @@ class ClassicFrontendFacade( override fun registerDependencyForAllModules(moduleInfo: ModuleInfo, descriptorForModule: ModuleDescriptorImpl) = Unit override fun packageFragmentProviderForModuleInfo(moduleInfo: ModuleInfo): PackageFragmentProvider? = null - override val friendModuleInfos: List get() = emptyList() - override val refinesModuleInfos: List get() = emptyList() + override val friendModuleInfos: List = _moduleInfos.filter { it.module.shouldSeeInternalsOf(module) } + override val refinesModuleInfos: List = _moduleInfos.filter { it.module in module.allExpectedByModules } } @OptIn(ExperimentalStdlibApi::class) diff --git a/libraries/stdlib/common/test/jsCollectionFactories.kt b/libraries/stdlib/common/test/jsCollectionFactories.kt index 47d5e8a665b..e12aef2a8d0 100644 --- a/libraries/stdlib/common/test/jsCollectionFactories.kt +++ b/libraries/stdlib/common/test/jsCollectionFactories.kt @@ -2,6 +2,7 @@ * Copyright 2010-2018 JetBrains s.r.o. and Kotlin Programming Language contributors. * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:Suppress("EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE") package test.collections.js diff --git a/libraries/stdlib/common/test/testUtils.kt b/libraries/stdlib/common/test/testUtils.kt index 9b5ffaf3ee8..1ac998dda47 100644 --- a/libraries/stdlib/common/test/testUtils.kt +++ b/libraries/stdlib/common/test/testUtils.kt @@ -2,6 +2,7 @@ * Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors. * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:Suppress("EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE") package test @@ -33,4 +34,4 @@ public expect object BackReferenceHandling { val nonExistentGroup: HandlingOption val nonExistentNamedGroup: HandlingOption val groupZero: HandlingOption -} \ No newline at end of file +} diff --git a/libraries/stdlib/jvm/test/js/StubsJVM.kt b/libraries/stdlib/jvm/test/js/StubsJVM.kt index 0fd5c148140..36e3e7ccf09 100644 --- a/libraries/stdlib/jvm/test/js/StubsJVM.kt +++ b/libraries/stdlib/jvm/test/js/StubsJVM.kt @@ -2,6 +2,7 @@ * Copyright 2010-2018 JetBrains s.r.o. and Kotlin Programming Language contributors. * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:Suppress("EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE") package test.collections.js diff --git a/libraries/stdlib/jvm/test/testUtilsJVM.kt b/libraries/stdlib/jvm/test/testUtilsJVM.kt index 22a7d06535d..ac503baec8d 100644 --- a/libraries/stdlib/jvm/test/testUtilsJVM.kt +++ b/libraries/stdlib/jvm/test/testUtilsJVM.kt @@ -2,6 +2,7 @@ * Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors. * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:Suppress("EXPECT_AND_ACTUAL_IN_THE_SAME_MODULE") package test @@ -38,4 +39,4 @@ public actual object BackReferenceHandling { actual val nonExistentGroup: HandlingOption = HandlingOption.MATCH_NOTHING actual val nonExistentNamedGroup: HandlingOption = HandlingOption.THROW actual val groupZero: HandlingOption = HandlingOption.THROW -} \ No newline at end of file +}