Make it possible to run hmpp tests with ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE

In scope of KT-40904 KT-55177
Review: https://jetbrains.team/p/kt/reviews/8731

In order to make it possible to run hmpp tests with
`ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE`, a dependency manager
must be implemented. This commit implements some basic dependency
manager. I'm not sure in its correctness because
`CommonDependenciesContainer` is an awkward API, but this dependency
manager works for my cases.

Why: I need hmpp + `ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE`
infrastructure to cover `ExpectActualInTheSameModuleChecker` (I will add
the checker in the next commit) with tests. The checker couldn't be
covered with regular hmpp tests because regular hmpp tests and
`K2MetadataCompiler` run the compiler in a different way.
Contrary, `ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE` runs the compiler in a
way `K2MetadataCompiler` does it.

I moved some tests from hmpp to `hmpp/multiplatformCompositeAnalysis`
because otherwise the tests would fail after I implement
`ExpectActualInTheSameModuleChecker` in the next commit.

Also the descriptor dumps were changed
(intermediateWithActualAndExpect.txt and
sealedInheritorsInComplexModuleStructure.txt). It happened because now
common source sets are no longer "squashed" into a single source set but
rather correct dependencies between source sets are established. And
each source set is analyzed separately (exactly like in
K2MetadataCompiler)
This commit is contained in:
Nikita Bobko
2023-02-15 17:50:40 +01:00
parent 14ca12b50b
commit 456605542c
11 changed files with 147 additions and 103 deletions
@@ -21981,29 +21981,39 @@ public class DiagnosisCompilerTestFE10TestdataTestGenerated extends AbstractDiag
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("kt-55570.kt")
public void testKt_55570() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/kt-55570.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/sealedInheritorsInComplexModuleStructure.kt");
}
@Test
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/simple.kt");
}
@Nested
@TestMetadata("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis")
@TestDataPath("$PROJECT_ROOT")
public class MultiplatformCompositeAnalysis {
@Test
public void testAllFilesPresentInMultiplatformCompositeAnalysis() throws Exception {
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/sealedInheritorsInComplexModuleStructure.kt");
}
}
}
@Nested
@@ -21987,29 +21987,39 @@ public class FirOldFrontendDiagnosticsTestGenerated extends AbstractFirDiagnosti
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp"), Pattern.compile("^(.*)\\.kts?$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("kt-55570.kt")
public void testKt_55570() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/kt-55570.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/sealedInheritorsInComplexModuleStructure.kt");
}
@Test
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/simple.kt");
}
@Nested
@TestMetadata("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis")
@TestDataPath("$PROJECT_ROOT")
public class MultiplatformCompositeAnalysis {
@Test
public void testAllFilesPresentInMultiplatformCompositeAnalysis() throws Exception {
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.*)\\.kts?$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/sealedInheritorsInComplexModuleStructure.kt");
}
}
}
@Nested
@@ -21981,29 +21981,39 @@ public class FirOldFrontendDiagnosticsWithLightTreeTestGenerated extends Abstrac
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("kt-55570.kt")
public void testKt_55570() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/kt-55570.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/sealedInheritorsInComplexModuleStructure.kt");
}
@Test
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/simple.kt");
}
@Nested
@TestMetadata("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis")
@TestDataPath("$PROJECT_ROOT")
public class MultiplatformCompositeAnalysis {
@Test
public void testAllFilesPresentInMultiplatformCompositeAnalysis() throws Exception {
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.+)\\.kt$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/sealedInheritorsInComplexModuleStructure.kt");
}
}
}
@Nested
@@ -16,12 +16,6 @@ public final expect class B {
// -- Module: <intermediate> --
package
public final expect class A {
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 B {
public constructor B()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
@@ -29,12 +23,6 @@ public final actual class B {
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public final expect class B {
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 C {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
@@ -51,13 +39,6 @@ public final actual class A {
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public final actual class B {
public constructor B()
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 C {
public constructor C()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
@@ -22,12 +22,6 @@ package
package foo {
public sealed expect class SealedWithPlatformActuals : foo.SealedWithSharedActual {
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 sealed actual class SealedWithSharedActual {
protected constructor SealedWithSharedActual()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
@@ -35,13 +29,6 @@ package foo {
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public sealed expect class SealedWithSharedActual {
protected constructor SealedWithSharedActual()
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 class SimpleShared : foo.SealedWithPlatformActuals {
public constructor SimpleShared()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
@@ -61,19 +48,5 @@ package foo {
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public sealed actual class SealedWithSharedActual {
protected constructor SealedWithSharedActual()
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 class SimpleShared : foo.SealedWithPlatformActuals {
public constructor SimpleShared()
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
}
}
@@ -21987,29 +21987,39 @@ public class DiagnosticTestGenerated extends AbstractDiagnosticTest {
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp"), Pattern.compile("^(.*)\\.kts?$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("kt-55570.kt")
public void testKt_55570() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/kt-55570.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/sealedInheritorsInComplexModuleStructure.kt");
}
@Test
@TestMetadata("simple.kt")
public void testSimple() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/simple.kt");
}
@Nested
@TestMetadata("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis")
@TestDataPath("$PROJECT_ROOT")
public class MultiplatformCompositeAnalysis {
@Test
public void testAllFilesPresentInMultiplatformCompositeAnalysis() throws Exception {
KtTestUtil.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis"), Pattern.compile("^(.*)\\.kts?$"), Pattern.compile("^(.+)\\.(fir|ll)\\.kts?$"), true);
}
@Test
@TestMetadata("intermediateWithActualAndExpect.kt")
public void testIntermediateWithActualAndExpect() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/intermediateWithActualAndExpect.kt");
}
@Test
@TestMetadata("sealedInheritorsInComplexModuleStructure.kt")
public void testSealedInheritorsInComplexModuleStructure() throws Exception {
runTest("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/sealedInheritorsInComplexModuleStructure.kt");
}
}
}
@Nested
@@ -8,6 +8,9 @@ package org.jetbrains.kotlin.test.frontend.classic
import com.intellij.openapi.project.Project
import com.intellij.psi.search.GlobalSearchScope
import org.jetbrains.kotlin.analyzer.AnalysisResult
import org.jetbrains.kotlin.analyzer.ModuleInfo
import org.jetbrains.kotlin.analyzer.common.CommonDependenciesContainer
import org.jetbrains.kotlin.analyzer.common.CommonPlatformAnalyzerServices
import org.jetbrains.kotlin.analyzer.common.CommonResolverForModuleFactory
import org.jetbrains.kotlin.builtins.DefaultBuiltIns
import org.jetbrains.kotlin.builtins.KotlinBuiltIns
@@ -27,6 +30,7 @@ import org.jetbrains.kotlin.context.ModuleContext
import org.jetbrains.kotlin.context.ProjectContext
import org.jetbrains.kotlin.context.withModule
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
import org.jetbrains.kotlin.descriptors.PackageFragmentProvider
import org.jetbrains.kotlin.descriptors.impl.CompositePackageFragmentProvider
import org.jetbrains.kotlin.descriptors.impl.ModuleDependenciesImpl
import org.jetbrains.kotlin.descriptors.impl.ModuleDescriptorImpl
@@ -38,12 +42,13 @@ import org.jetbrains.kotlin.incremental.components.InlineConstTracker
import org.jetbrains.kotlin.incremental.components.LookupTracker
import org.jetbrains.kotlin.ir.backend.js.*
import org.jetbrains.kotlin.js.analyze.TopDownAnalyzerFacadeForJS
import org.jetbrains.kotlin.js.config.JSConfigurationKeys
import org.jetbrains.kotlin.library.unresolvedDependencies
import org.jetbrains.kotlin.load.java.lazy.SingleModuleClassResolver
import org.jetbrains.kotlin.load.kotlin.ModuleVisibilityManager
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.native.FakeTopDownAnalyzerFacadeForNative
import org.jetbrains.kotlin.platform.CommonPlatforms
import org.jetbrains.kotlin.platform.TargetPlatform
import org.jetbrains.kotlin.platform.isCommon
import org.jetbrains.kotlin.platform.isJs
import org.jetbrains.kotlin.platform.jvm.JvmPlatforms
@@ -51,6 +56,7 @@ import org.jetbrains.kotlin.platform.jvm.isJvm
import org.jetbrains.kotlin.platform.konan.isNative
import org.jetbrains.kotlin.psi.KtFile
import org.jetbrains.kotlin.resolve.LazyTopDownAnalyzer
import org.jetbrains.kotlin.resolve.PlatformDependentAnalyzerServices
import org.jetbrains.kotlin.resolve.TargetEnvironment
import org.jetbrains.kotlin.resolve.TopDownAnalysisMode
import org.jetbrains.kotlin.resolve.jvm.JavaDescriptorResolver
@@ -156,7 +162,14 @@ class ClassicFrontendFacade(
targetPlatform.isNative() -> performNativeModuleResolve(
module, project, compilerEnvironment, files, dependencyDescriptors, friendsDescriptors, dependsOnDescriptors
)
targetPlatform.isCommon() -> performCommonModuleResolve(module, compilerEnvironment, files)
targetPlatform.isCommon() -> performCommonModuleResolve(
module,
project,
compilerEnvironment,
dependencyDescriptors,
friendsDescriptors,
files
)
else -> error("Should not be here")
}
}
@@ -347,15 +360,19 @@ class ClassicFrontendFacade(
private fun performCommonModuleResolve(
module: TestModule,
project: Project,
compilerEnvironment: TargetEnvironment,
dependencyDescriptors: List<ModuleDescriptorImpl>,
friendsDescriptors: List<ModuleDescriptorImpl>,
files: List<KtFile>,
): AnalysisResult {
// See 'TODO' for adding dependency manager
require(module.dependsOnDependencies.isEmpty() || ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE !in module.directives) {
"Analyzing common modules with 'dependsOn' edges in ${ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE.name} is not supported yet.\n" +
"Module: ${module.name}\n" +
"dependsOn: ${module.dependsOnDependencies.map { it.moduleName }}"
}
val moduleDescriptor = createModuleContext(
module, project,
dependencyDescriptors = dependencyDescriptors,
friendsDescriptors = friendsDescriptors,
dependsOnDescriptors = dependencyDescriptors
) { DefaultBuiltIns.Instance }.module
(moduleDescriptor as ModuleDescriptorImpl).initialize(PackageFragmentProvider.Empty)
return CommonResolverForModuleFactory.analyzeFiles(
files,
Name.special("<${module.name}>"),
@@ -363,13 +380,39 @@ class ClassicFrontendFacade(
module.languageVersionSettings,
module.targetPlatform,
compilerEnvironment,
// TODO: add dependency manager
dependenciesContainer = CommonDependenciesContainerImpl(moduleDescriptor)
) {
// TODO
MetadataPartProvider.Empty
}
}
private class CommonDependenciesContainerImpl(module: ModuleDescriptor) : CommonDependenciesContainer {
private class ModuleInfoImpl(val module: ModuleDescriptor) : ModuleInfo {
override val name: Name get() = module.name
override fun dependencies(): List<ModuleInfo> = module.allDependencyModules.map(::ModuleInfoImpl)
override fun dependencyOnBuiltIns(): ModuleInfo.DependencyOnBuiltIns = ModuleInfo.DependencyOnBuiltIns.LAST
override val platform: TargetPlatform get() = CommonPlatforms.defaultCommonPlatform
override val analyzerServices: PlatformDependentAnalyzerServices get() = CommonPlatformAnalyzerServices
}
private val _moduleInfos: List<ModuleInfoImpl> =
ModuleInfoImpl(module).let { listOf(it) + it.module.allDependencyModules.map(::ModuleInfoImpl) }
override val moduleInfos: List<ModuleInfo> get() = _moduleInfos
override fun moduleDescriptorForModuleInfo(moduleInfo: ModuleInfo): ModuleDescriptor =
_moduleInfos.singleOrNull { it.name == moduleInfo.name }?.module ?: error("Can't find ModuleDescriptor for $moduleInfo")
override fun registerDependencyForAllModules(moduleInfo: ModuleInfo, descriptorForModule: ModuleDescriptorImpl) = Unit
override fun packageFragmentProviderForModuleInfo(moduleInfo: ModuleInfo): PackageFragmentProvider? = null
override val friendModuleInfos: List<ModuleInfo> get() = emptyList()
override val refinesModuleInfos: List<ModuleInfo> get() = emptyList()
}
@OptIn(ExperimentalStdlibApi::class)
private fun createModuleContext(
module: TestModule,
@@ -21,6 +21,7 @@ import org.jetbrains.kotlin.test.directives.JvmEnvironmentConfigurationDirective
import org.jetbrains.kotlin.test.directives.LanguageSettingsDirectives.EXPLICIT_API_MODE
import org.jetbrains.kotlin.test.directives.LanguageSettingsDirectives.LANGUAGE
import org.jetbrains.kotlin.test.directives.LanguageSettingsDirectives.OPT_IN
import org.jetbrains.kotlin.test.directives.MultiplatformDiagnosticsDirectives
import org.jetbrains.kotlin.test.frontend.classic.ClassicFrontendFailingTestSuppressor
import org.jetbrains.kotlin.test.frontend.classic.handlers.*
import org.jetbrains.kotlin.test.model.DependencyKind
@@ -127,6 +128,12 @@ abstract class AbstractDiagnosticTest : AbstractKotlinCompilerTest() {
}
}
forTestsMatching("compiler/testData/diagnostics/tests/multiplatform/hmpp/multiplatformCompositeAnalysis/*") {
defaultDirectives {
+MultiplatformDiagnosticsDirectives.ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE
}
}
// ----------------------- constant evaluation tests -----------------------
forTestsMatching("compiler/testData/diagnostics/tests/constantEvaluator/constant/*") {
defaultDirectives {