[JS IR BE] Copy Runtime IR after inline preparation passes

This commit is contained in:
Svyatoslav Kuzmich
2019-02-12 13:47:13 +03:00
parent 74ee64fcf1
commit d0e7fb7af3
3 changed files with 22 additions and 12 deletions
@@ -181,6 +181,8 @@ class JsIrBackendContext(
val originalModuleIndex = ModuleIndex(irModuleFragment) val originalModuleIndex = ModuleIndex(irModuleFragment)
lateinit var moduleFragmentCopy: IrModuleFragment
fun getOperatorByName(name: Name, type: KotlinType) = operatorMap[name]?.get(type) fun getOperatorByName(name: Name, type: KotlinType) = operatorMap[name]?.get(type)
override val ir = object : Ir<CommonBackendContext>(this, irModuleFragment) { override val ir = object : Ir<CommonBackendContext>(this, irModuleFragment) {
@@ -10,6 +10,7 @@ import org.jetbrains.kotlin.backend.common.lower.*
import org.jetbrains.kotlin.backend.common.phaser.* import org.jetbrains.kotlin.backend.common.phaser.*
import org.jetbrains.kotlin.ir.backend.js.lower.* import org.jetbrains.kotlin.ir.backend.js.lower.*
import org.jetbrains.kotlin.ir.backend.js.lower.calls.CallsLowering import org.jetbrains.kotlin.ir.backend.js.lower.calls.CallsLowering
import org.jetbrains.kotlin.ir.backend.js.lower.coroutines.CoroutineIntrinsicLowering
import org.jetbrains.kotlin.ir.backend.js.lower.coroutines.SuspendFunctionsLowering import org.jetbrains.kotlin.ir.backend.js.lower.coroutines.SuspendFunctionsLowering
import org.jetbrains.kotlin.ir.backend.js.lower.inline.FunctionInlining import org.jetbrains.kotlin.ir.backend.js.lower.inline.FunctionInlining
import org.jetbrains.kotlin.ir.backend.js.lower.inline.RemoveInlineFunctionsWithReifiedTypeParametersLowering import org.jetbrains.kotlin.ir.backend.js.lower.inline.RemoveInlineFunctionsWithReifiedTypeParametersLowering
@@ -17,6 +18,7 @@ import org.jetbrains.kotlin.ir.backend.js.lower.inline.ReturnableBlockLowering
import org.jetbrains.kotlin.ir.backend.js.lower.inline.replaceUnboundSymbols import org.jetbrains.kotlin.ir.backend.js.lower.inline.replaceUnboundSymbols
import org.jetbrains.kotlin.ir.declarations.IrFile import org.jetbrains.kotlin.ir.declarations.IrFile
import org.jetbrains.kotlin.ir.declarations.IrModuleFragment import org.jetbrains.kotlin.ir.declarations.IrModuleFragment
import org.jetbrains.kotlin.ir.util.deepCopyWithSymbols
import org.jetbrains.kotlin.ir.util.patchDeclarationParents import org.jetbrains.kotlin.ir.util.patchDeclarationParents
private fun DeclarationContainerLoweringPass.runOnFilesPostfix(files: Iterable<IrFile>) = files.forEach { runOnFilePostfix(it) } private fun DeclarationContainerLoweringPass.runOnFilesPostfix(files: Iterable<IrFile>) = files.forEach { runOnFilePostfix(it) }
@@ -79,6 +81,12 @@ private val expectDeclarationsRemovingPhase = makeJsModulePhase(
description = "Remove expect declaration from module fragment" description = "Remove expect declaration from module fragment"
) )
private val coroutineIntrinsicLoweringPhase = makeJsModulePhase(
::CoroutineIntrinsicLowering,
name = "CoroutineIntrinsicLowering",
description = "Replace common coroutine intrinsics with platform specific ones"
)
private val arrayInlineConstructorLoweringPhase = makeJsModulePhase( private val arrayInlineConstructorLoweringPhase = makeJsModulePhase(
::ArrayInlineConstructorLowering, ::ArrayInlineConstructorLowering,
name = "ArrayInlineConstructorLowering", name = "ArrayInlineConstructorLowering",
@@ -91,6 +99,13 @@ private val lateinitLoweringPhase = makeJsModulePhase(
description = "Insert checks for lateinit field references" description = "Insert checks for lateinit field references"
) )
private val moduleCopyingPhase = makeCustomJsModulePhase(
{ context, module -> context.moduleFragmentCopy = module.deepCopyWithSymbols() },
name = "ModuleCopying",
description = "<Supposed to be removed> Copy current module to make it accessible from different one",
prerequisite = setOf(lateinitLoweringPhase)
)
private val functionInliningPhase = makeCustomJsModulePhase( private val functionInliningPhase = makeCustomJsModulePhase(
{ context, module -> { context, module ->
FunctionInlining(context).inline(module) FunctionInlining(context).inline(module)
@@ -99,7 +114,7 @@ private val functionInliningPhase = makeCustomJsModulePhase(
}, },
name = "FunctionInliningPhase", name = "FunctionInliningPhase",
description = "Perform function inlining", description = "Perform function inlining",
prerequisite = setOf(lateinitLoweringPhase, arrayInlineConstructorLoweringPhase) prerequisite = setOf(moduleCopyingPhase, lateinitLoweringPhase, arrayInlineConstructorLoweringPhase, coroutineIntrinsicLoweringPhase)
) )
private val removeInlineFunctionsWithReifiedTypeParametersLoweringPhase = makeJsModulePhase( private val removeInlineFunctionsWithReifiedTypeParametersLoweringPhase = makeJsModulePhase(
@@ -182,7 +197,7 @@ private val suspendFunctionsLoweringPhase = makeJsModulePhase(
::SuspendFunctionsLowering, ::SuspendFunctionsLowering,
name = "SuspendFunctionsLowering", name = "SuspendFunctionsLowering",
description = "Transform suspend functions into CoroutineImpl instance and build state machine", description = "Transform suspend functions into CoroutineImpl instance and build state machine",
prerequisite = setOf(unitMaterializationLoweringPhase) prerequisite = setOf(unitMaterializationLoweringPhase, coroutineIntrinsicLoweringPhase)
) )
private val privateMembersLoweringPhase = makeJsModulePhase( private val privateMembersLoweringPhase = makeJsModulePhase(
@@ -338,8 +353,10 @@ val jsPhases = namedIrModulePhase(
description = "IR module lowering", description = "IR module lowering",
lower = moveBodilessDeclarationsToSeparatePlacePhase then lower = moveBodilessDeclarationsToSeparatePlacePhase then
expectDeclarationsRemovingPhase then expectDeclarationsRemovingPhase then
coroutineIntrinsicLoweringPhase then
arrayInlineConstructorLoweringPhase then arrayInlineConstructorLoweringPhase then
lateinitLoweringPhase then lateinitLoweringPhase then
moduleCopyingPhase then
functionInliningPhase then functionInliningPhase then
removeInlineFunctionsWithReifiedTypeParametersLoweringPhase then removeInlineFunctionsWithReifiedTypeParametersLoweringPhase then
throwableSuccessorsLoweringPhase then throwableSuccessorsLoweringPhase then
@@ -82,16 +82,8 @@ fun compile(
moduleType moduleType
) )
// CoroutineIntrinsicLowering currently have to be applied to dependencies
// before running inline pass for current module.
// Therefore we run it here before producing ir for current module.
// TODO: Find a better way to implement coroutine intrinsics
val coroutineIntrinsicLowering = CoroutineIntrinsicLowering(context)
moduleFragment.files.forEach { file -> coroutineIntrinsicLowering.lower(file) }
// TODO: Split compilation into two steps: kt -> ir, ir -> js // TODO: Split compilation into two steps: kt -> ir, ir -> js
val moduleName = configuration[CommonConfigurationKeys.MODULE_NAME]!! val moduleName = configuration[CommonConfigurationKeys.MODULE_NAME]!!
var moduleFragmentCopy: IrModuleFragment? = null
when (moduleType) { when (moduleType) {
ModuleType.MAIN -> { ModuleType.MAIN -> {
val moduleDependencies: List<CompiledModule> = val moduleDependencies: List<CompiledModule> =
@@ -108,7 +100,6 @@ fun compile(
} }
ModuleType.TEST_RUNTIME -> { ModuleType.TEST_RUNTIME -> {
moduleFragmentCopy = moduleFragment.deepCopyWithSymbols()
} }
} }
@@ -116,5 +107,5 @@ fun compile(
val jsProgram = moduleFragment.accept(IrModuleToJsTransformer(context), null) val jsProgram = moduleFragment.accept(IrModuleToJsTransformer(context), null)
return CompiledModule(moduleName, jsProgram.toString(), moduleFragmentCopy, moduleType, dependencies) return CompiledModule(moduleName, jsProgram.toString(), context.moduleFragmentCopy, moduleType, dependencies)
} }