JVM IR: move jvmPhases to backend.jvm.entrypoint

This will be used for two purposes:
1) call lowerings and codegen separately from
   KotlinToJVMBytecodeCompiler to support cyclical module dependencies
   (KT-49575)
2) split lowerings and codegen into separate modules
This commit is contained in:
Alexander Udalov
2021-09-15 02:15:07 +02:00
parent 79f9bd9c29
commit f701f04326
4 changed files with 73 additions and 65 deletions
-1
View File
@@ -12,7 +12,6 @@ dependencies {
api(project(":compiler:backend-common"))
api(project(":compiler:backend"))
api(project(":compiler:backend.jvm"))
implementation(project(":compiler:backend.jvm.lower"))
implementation(project(":compiler:backend.jvm.entrypoint"))
api(project(":compiler:ir.backend.common"))
api(project(":compiler:light-classes"))
@@ -0,0 +1,72 @@
/*
* Copyright 2010-2021 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.backend.jvm
import org.jetbrains.kotlin.backend.common.FileLoweringPass
import org.jetbrains.kotlin.backend.common.phaser.*
import org.jetbrains.kotlin.backend.jvm.codegen.ClassCodegen
import org.jetbrains.kotlin.ir.declarations.IrClass
import org.jetbrains.kotlin.ir.declarations.IrFile
import org.jetbrains.kotlin.ir.declarations.IrModuleFragment
import org.jetbrains.kotlin.ir.util.render
private val notifyCodegenStartPhase = makeCustomPhase<JvmBackendContext, IrModuleFragment>(
op = { context, _ -> context.notifyCodegenStart() },
name = "NotifyCodegenStart",
description = "Notify time measuring subsystem that code generation is being started",
)
private fun codegenPhase(generateMultifileFacade: Boolean): NamedCompilerPhase<JvmBackendContext, IrModuleFragment> {
val suffix = if (generateMultifileFacade) "MultifileFacades" else "Regular"
val descriptionSuffix = if (generateMultifileFacade) ", multifile facades" else ", regular files"
return performByIrFile(
name = "CodegenByIrFile$suffix",
description = "Code generation by IrFile$descriptionSuffix",
copyBeforeLowering = false,
lower = listOf(
makeIrFilePhase(
{ context ->
object : FileLoweringPass {
override fun lower(irFile: IrFile) {
val isMultifileFacade = irFile.fileEntry is MultifileFacadeFileEntry
if (isMultifileFacade == generateMultifileFacade) {
for (loweredClass in irFile.declarations) {
if (loweredClass !is IrClass) {
throw AssertionError("File-level declaration should be IrClass after JvmLower, got: " + loweredClass.render())
}
ClassCodegen.getOrCreate(loweredClass, context).generate()
}
}
}
}
},
name = "Codegen$suffix",
description = "Code generation"
)
)
)
}
// Generate multifile facades first, to compute and store JVM signatures of const properties which are later used
// when serializing metadata in the multifile parts.
// TODO: consider dividing codegen itself into separate phases (bytecode generation, metadata serialization) to avoid this
private val jvmCodegenPhases = NamedCompilerPhase(
name = "Codegen",
description = "Code generation",
nlevels = 1,
lower = codegenPhase(generateMultifileFacade = true) then
codegenPhase(generateMultifileFacade = false)
)
val jvmPhases = NamedCompilerPhase(
name = "IrBackend",
description = "IR Backend for JVM",
nlevels = 1,
actions = setOf(defaultDumper, validationAction),
lower = jvmLoweringPhases then
notifyCodegenStartPhase then
jvmCodegenPhases
)
@@ -11,7 +11,6 @@ import org.jetbrains.kotlin.backend.common.lower.*
import org.jetbrains.kotlin.backend.common.lower.loops.forLoopsPhase
import org.jetbrains.kotlin.backend.common.lower.optimizations.foldConstantLoweringPhase
import org.jetbrains.kotlin.backend.common.phaser.*
import org.jetbrains.kotlin.backend.jvm.codegen.ClassCodegen
import org.jetbrains.kotlin.backend.jvm.codegen.shouldContainSuspendMarkers
import org.jetbrains.kotlin.backend.jvm.ir.constantValue
import org.jetbrains.kotlin.backend.jvm.lower.*
@@ -23,7 +22,6 @@ import org.jetbrains.kotlin.ir.symbols.IrValueSymbol
import org.jetbrains.kotlin.ir.util.PatchDeclarationParentsVisitor
import org.jetbrains.kotlin.ir.util.isAnonymousObject
import org.jetbrains.kotlin.ir.util.parentAsClass
import org.jetbrains.kotlin.ir.util.render
import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid
import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid
import org.jetbrains.kotlin.ir.visitors.acceptVoid
@@ -277,43 +275,6 @@ private val kotlinNothingValueExceptionPhase = makeIrFilePhase<CommonBackendCont
description = "Throw proper exception for calls returning value of type 'kotlin.Nothing'"
)
private val notifyCodegenStartPhase = makeCustomPhase<JvmBackendContext, IrModuleFragment>(
op = { context, _ -> context.notifyCodegenStart() },
name = "NotifyCodegenStart",
description = "Notify time measuring subsystem that code generation is being started",
)
private fun codegenPhase(generateMultifileFacade: Boolean): NamedCompilerPhase<JvmBackendContext, IrModuleFragment> {
val suffix = if (generateMultifileFacade) "MultifileFacades" else "Regular"
val descriptionSuffix = if (generateMultifileFacade) ", multifile facades" else ", regular files"
return performByIrFile(
name = "CodegenByIrFile$suffix",
description = "Code generation by IrFile$descriptionSuffix",
copyBeforeLowering = false,
lower = listOf(
makeIrFilePhase(
{ context ->
object : FileLoweringPass {
override fun lower(irFile: IrFile) {
val isMultifileFacade = irFile.fileEntry is MultifileFacadeFileEntry
if (isMultifileFacade == generateMultifileFacade) {
for (loweredClass in irFile.declarations) {
if (loweredClass !is IrClass) {
throw AssertionError("File-level declaration should be IrClass after JvmLower, got: " + loweredClass.render())
}
ClassCodegen.getOrCreate(loweredClass, context).generate()
}
}
}
}
},
name = "Codegen$suffix",
description = "Code generation"
)
)
)
}
private val jvmFilePhases = listOf(
typeAliasAnnotationMethodsPhase,
stripTypeAliasDeclarationsPhase,
@@ -425,7 +386,7 @@ private val jvmFilePhases = listOf(
makePatchParentsPhase(4)
)
private val jvmLoweringPhases = NamedCompilerPhase(
val jvmLoweringPhases = NamedCompilerPhase(
name = "IrLowering",
description = "IR lowering",
nlevels = 1,
@@ -444,26 +405,3 @@ private val jvmLoweringPhases = NamedCompilerPhase(
prepareForBytecodeInlining then
validateIrAfterLowering
)
// Generate multifile facades first, to compute and store JVM signatures of const properties which are later used
// when serializing metadata in the multifile parts.
// TODO: consider dividing codegen itself into separate phases (bytecode generation, metadata serialization) to avoid this
private val jvmCodegenPhases = NamedCompilerPhase(
name = "Codegen",
description = "Code generation",
nlevels = 1,
lower = codegenPhase(generateMultifileFacade = true) then
codegenPhase(generateMultifileFacade = false)
)
val jvmPhases = NamedCompilerPhase(
name = "IrBackend",
description = "IR Backend for JVM",
nlevels = 1,
actions = setOf(defaultDumper, validationAction),
lower = jvmLoweringPhases then
notifyCodegenStartPhase then
jvmCodegenPhases
)
@@ -9,7 +9,6 @@ dependencies {
testApi(project(":compiler:fir:entrypoint"))
testApi(project(":compiler:cli"))
testImplementation(project(":compiler:ir.tree.impl"))
testImplementation(project(":compiler:backend.jvm.lower"))
testImplementation(project(":compiler:backend.jvm.entrypoint"))
testImplementation(intellijCoreDep()) { includeJars("intellij-core") }