[Wasm] Add Wasm platform and K1 FE infrastructure
This commit is contained in:
+44
@@ -17,6 +17,7 @@ import org.jetbrains.kotlin.builtins.KotlinBuiltIns
|
||||
import org.jetbrains.kotlin.builtins.jvm.JvmBuiltIns
|
||||
import org.jetbrains.kotlin.cli.common.messages.AnalyzerWithCompilerReport
|
||||
import org.jetbrains.kotlin.cli.js.klib.TopDownAnalyzerFacadeForJSIR
|
||||
import org.jetbrains.kotlin.cli.js.klib.TopDownAnalyzerFacadeForWasm
|
||||
import org.jetbrains.kotlin.cli.jvm.compiler.JvmPackagePartProvider
|
||||
import org.jetbrains.kotlin.cli.jvm.compiler.NoScopeRecordCliBindingTrace
|
||||
import org.jetbrains.kotlin.cli.jvm.compiler.TopDownAnalyzerFacadeForJVM
|
||||
@@ -51,6 +52,7 @@ 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.isWasm
|
||||
import org.jetbrains.kotlin.platform.jvm.JvmPlatforms
|
||||
import org.jetbrains.kotlin.platform.jvm.isJvm
|
||||
import org.jetbrains.kotlin.platform.konan.isNative
|
||||
@@ -65,6 +67,7 @@ import org.jetbrains.kotlin.resolve.lazy.declarations.FileBasedDeclarationProvid
|
||||
import org.jetbrains.kotlin.serialization.deserialization.MetadataPartProvider
|
||||
import org.jetbrains.kotlin.storage.LockBasedStorageManager
|
||||
import org.jetbrains.kotlin.storage.StorageManager
|
||||
import org.jetbrains.kotlin.test.directives.ConfigurationDirectives
|
||||
import org.jetbrains.kotlin.test.directives.JvmEnvironmentConfigurationDirectives
|
||||
import org.jetbrains.kotlin.test.directives.MultiplatformDiagnosticsDirectives.ENABLE_MULTIPLATFORM_COMPOSITE_ANALYSIS_MODE
|
||||
import org.jetbrains.kotlin.test.model.DependencyRelation
|
||||
@@ -73,6 +76,7 @@ import org.jetbrains.kotlin.test.model.FrontendKinds
|
||||
import org.jetbrains.kotlin.test.model.TestModule
|
||||
import org.jetbrains.kotlin.test.services.*
|
||||
import org.jetbrains.kotlin.test.services.configuration.JsEnvironmentConfigurator
|
||||
import org.jetbrains.kotlin.test.services.configuration.WasmEnvironmentConfigurator
|
||||
import org.jetbrains.kotlin.test.util.KtTestUtil
|
||||
import org.jetbrains.kotlin.types.typeUtil.closure
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.runIf
|
||||
@@ -159,6 +163,9 @@ class ClassicFrontendFacade(
|
||||
module, project, configuration, compilerEnvironment, files, dependencyDescriptors, friendsDescriptors
|
||||
)
|
||||
}
|
||||
targetPlatform.isWasm() -> performWasmModuleResolve(
|
||||
module, project, configuration, compilerEnvironment, files, dependencyDescriptors, friendsDescriptors
|
||||
)
|
||||
targetPlatform.isNative() -> performNativeModuleResolve(
|
||||
module, project, compilerEnvironment, files, dependencyDescriptors, friendsDescriptors, dependsOnDescriptors
|
||||
)
|
||||
@@ -331,6 +338,43 @@ class ClassicFrontendFacade(
|
||||
return analyzer.analysisResult
|
||||
}
|
||||
|
||||
private fun performWasmModuleResolve(
|
||||
module: TestModule,
|
||||
project: Project,
|
||||
configuration: CompilerConfiguration,
|
||||
compilerEnvironment: TargetEnvironment,
|
||||
files: List<KtFile>,
|
||||
dependencyDescriptors: List<ModuleDescriptor>,
|
||||
friendsDescriptors: List<ModuleDescriptor>,
|
||||
): AnalysisResult {
|
||||
val needsKotlinTest = ConfigurationDirectives.WITH_STDLIB in module.directives
|
||||
|
||||
val runtimeKlibsNames =
|
||||
listOfNotNull(
|
||||
System.getProperty("kotlin.wasm.stdlib.path")!!,
|
||||
System.getProperty("kotlin.wasm.kotlin.test.path")!!.takeIf { needsKotlinTest }
|
||||
).map {
|
||||
File(it).absolutePath
|
||||
}
|
||||
|
||||
val runtimeKlibs = loadKlib(runtimeKlibsNames, configuration)
|
||||
val transitiveLibraries = WasmEnvironmentConfigurator.getDependencies(module, testServices, DependencyRelation.RegularDependency)
|
||||
val friendLibraries = WasmEnvironmentConfigurator.getDependencies(module, testServices, DependencyRelation.FriendDependency)
|
||||
val allDependencies = runtimeKlibs + dependencyDescriptors + friendLibraries + friendsDescriptors + transitiveLibraries
|
||||
|
||||
val builtInModuleDescriptor = allDependencies.firstNotNullOfOrNull { it.builtIns }?.builtInsModule
|
||||
return TopDownAnalyzerFacadeForWasm.analyzeFiles(
|
||||
files,
|
||||
project,
|
||||
configuration,
|
||||
allDependencies,
|
||||
friendsDescriptors + friendLibraries,
|
||||
compilerEnvironment,
|
||||
thisIsBuiltInsModule = builtInModuleDescriptor == null,
|
||||
customBuiltInsModule = builtInModuleDescriptor
|
||||
)
|
||||
}
|
||||
|
||||
private fun performNativeModuleResolve(
|
||||
module: TestModule,
|
||||
project: Project,
|
||||
|
||||
+2
@@ -27,6 +27,7 @@ import org.jetbrains.kotlin.js.config.JSConfigurationKeys
|
||||
import org.jetbrains.kotlin.platform.TargetPlatform
|
||||
import org.jetbrains.kotlin.platform.isCommon
|
||||
import org.jetbrains.kotlin.platform.isJs
|
||||
import org.jetbrains.kotlin.platform.isWasm
|
||||
import org.jetbrains.kotlin.platform.jvm.isJvm
|
||||
import org.jetbrains.kotlin.platform.konan.isNative
|
||||
import org.jetbrains.kotlin.psi.KtFile
|
||||
@@ -117,6 +118,7 @@ fun TargetPlatform.platformToEnvironmentConfigFiles() = when {
|
||||
isJvm() -> EnvironmentConfigFiles.JVM_CONFIG_FILES
|
||||
isJs() -> EnvironmentConfigFiles.JS_CONFIG_FILES
|
||||
isNative() -> EnvironmentConfigFiles.NATIVE_CONFIG_FILES
|
||||
isWasm() -> EnvironmentConfigFiles.WASM_CONFIG_FILES
|
||||
// TODO: is it correct?
|
||||
isCommon() -> EnvironmentConfigFiles.METADATA_CONFIG_FILES
|
||||
else -> error("Unknown platform: ${this}")
|
||||
|
||||
+98
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.test.services.configuration
|
||||
|
||||
import org.jetbrains.kotlin.config.AnalysisFlag
|
||||
import org.jetbrains.kotlin.config.AnalysisFlags.allowFullyQualifiedNameInKClass
|
||||
import org.jetbrains.kotlin.config.AnalysisFlags.skipPrereleaseCheck
|
||||
import org.jetbrains.kotlin.config.CommonConfigurationKeys
|
||||
import org.jetbrains.kotlin.config.CompilerConfiguration
|
||||
import org.jetbrains.kotlin.config.LanguageVersion
|
||||
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
|
||||
import org.jetbrains.kotlin.js.config.JSConfigurationKeys
|
||||
import org.jetbrains.kotlin.js.config.SourceMapSourceEmbedding
|
||||
import org.jetbrains.kotlin.serialization.js.ModuleKind
|
||||
import org.jetbrains.kotlin.test.directives.JsEnvironmentConfigurationDirectives
|
||||
import org.jetbrains.kotlin.test.directives.JsEnvironmentConfigurationDirectives.EXPECT_ACTUAL_LINKER
|
||||
import org.jetbrains.kotlin.test.directives.JsEnvironmentConfigurationDirectives.GENERATE_INLINE_ANONYMOUS_FUNCTIONS
|
||||
import org.jetbrains.kotlin.test.directives.JsEnvironmentConfigurationDirectives.NO_INLINE
|
||||
import org.jetbrains.kotlin.test.directives.JsEnvironmentConfigurationDirectives.PROPERTY_LAZY_INITIALIZATION
|
||||
import org.jetbrains.kotlin.test.directives.JsEnvironmentConfigurationDirectives.SOURCE_MAP_EMBED_SOURCES
|
||||
import org.jetbrains.kotlin.test.directives.model.DirectivesContainer
|
||||
import org.jetbrains.kotlin.test.directives.model.RegisteredDirectives
|
||||
import org.jetbrains.kotlin.test.model.ArtifactKinds
|
||||
import org.jetbrains.kotlin.test.model.DependencyKind
|
||||
import org.jetbrains.kotlin.test.model.DependencyRelation
|
||||
import org.jetbrains.kotlin.test.model.TestModule
|
||||
import org.jetbrains.kotlin.test.services.*
|
||||
import java.io.File
|
||||
|
||||
class WasmEnvironmentConfigurator(testServices: TestServices) : EnvironmentConfigurator(testServices) {
|
||||
override val directiveContainers: List<DirectivesContainer>
|
||||
get() = listOf(JsEnvironmentConfigurationDirectives)
|
||||
|
||||
companion object {
|
||||
private fun getKlibDependencies(module: TestModule, testServices: TestServices, kind: DependencyRelation): List<File> {
|
||||
val visited = mutableSetOf<TestModule>()
|
||||
fun getRecursive(module: TestModule, relation: DependencyRelation) {
|
||||
val dependencies = if (relation == DependencyRelation.FriendDependency) {
|
||||
module.friendDependencies
|
||||
} else {
|
||||
module.regularDependencies
|
||||
}
|
||||
dependencies
|
||||
// See: `dependencyKind =` in AbstractJsBlackBoxCodegenTestBase.kt
|
||||
.filter { it.kind != DependencyKind.Source }
|
||||
.map { testServices.dependencyProvider.getTestModule(it.moduleName) }.forEach {
|
||||
if (it !in visited) {
|
||||
visited += it
|
||||
getRecursive(it, relation)
|
||||
}
|
||||
}
|
||||
}
|
||||
getRecursive(module, kind)
|
||||
return visited.map { testServices.dependencyProvider.getArtifact(it, ArtifactKinds.KLib).outputFile }
|
||||
}
|
||||
|
||||
fun getDependencies(module: TestModule, testServices: TestServices, kind: DependencyRelation): List<ModuleDescriptor> {
|
||||
return getKlibDependencies(module, testServices, kind)
|
||||
.map { testServices.jsLibraryProvider.getDescriptorByPath(it.absolutePath) }
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
override fun provideAdditionalAnalysisFlags(
|
||||
directives: RegisteredDirectives,
|
||||
languageVersion: LanguageVersion
|
||||
): Map<AnalysisFlag<*>, Any?> {
|
||||
return super.provideAdditionalAnalysisFlags(directives, languageVersion).toMutableMap().also {
|
||||
it[allowFullyQualifiedNameInKClass] = false
|
||||
}
|
||||
}
|
||||
|
||||
override fun DirectiveToConfigurationKeyExtractor.provideConfigurationKeys() {
|
||||
register(PROPERTY_LAZY_INITIALIZATION, JSConfigurationKeys.PROPERTY_LAZY_INITIALIZATION)
|
||||
}
|
||||
|
||||
override fun configureCompilerConfiguration(configuration: CompilerConfiguration, module: TestModule) {
|
||||
val registeredDirectives = module.directives
|
||||
configuration.put(JSConfigurationKeys.MODULE_KIND, ModuleKind.ES)
|
||||
|
||||
val noInline = registeredDirectives.contains(NO_INLINE)
|
||||
configuration.put(CommonConfigurationKeys.DISABLE_INLINE, noInline)
|
||||
configuration.put(CommonConfigurationKeys.MODULE_NAME, module.name)
|
||||
|
||||
val sourceDirs = module.files.map { it.originalFile.parent }.distinct()
|
||||
configuration.put(JSConfigurationKeys.SOURCE_MAP_SOURCE_ROOTS, sourceDirs)
|
||||
configuration.put(JSConfigurationKeys.SOURCE_MAP, true)
|
||||
|
||||
val sourceMapSourceEmbedding = registeredDirectives[SOURCE_MAP_EMBED_SOURCES].singleOrNull() ?: SourceMapSourceEmbedding.NEVER
|
||||
configuration.put(JSConfigurationKeys.SOURCE_MAP_EMBED_SOURCES, sourceMapSourceEmbedding)
|
||||
|
||||
configuration.put(CommonConfigurationKeys.EXPECT_ACTUAL_LINKER, EXPECT_ACTUAL_LINKER in registeredDirectives)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user