Extracted a separate phase for synthetic fields creation
This commit is contained in:
+2
-2
@@ -27,7 +27,7 @@ val CompilerOutputKind.isNativeBinary: Boolean get() = when (this) {
|
|||||||
CompilerOutputKind.LIBRARY, CompilerOutputKind.BITCODE -> false
|
CompilerOutputKind.LIBRARY, CompilerOutputKind.BITCODE -> false
|
||||||
}
|
}
|
||||||
|
|
||||||
internal fun produceOutput(context: Context) {
|
internal fun produceOutput(context: Context, phaser: PhaseManager) {
|
||||||
|
|
||||||
val llvmModule = context.llvmModule!!
|
val llvmModule = context.llvmModule!!
|
||||||
val config = context.config.configuration
|
val config = context.config.configuration
|
||||||
@@ -56,7 +56,7 @@ internal fun produceOutput(context: Context) {
|
|||||||
context.config.defaultNativeLibraries +
|
context.config.defaultNativeLibraries +
|
||||||
generatedBitcodeFiles
|
generatedBitcodeFiles
|
||||||
|
|
||||||
PhaseManager(context).phase(KonanPhase.BITCODE_LINKER) {
|
phaser.phase(KonanPhase.BITCODE_LINKER) {
|
||||||
for (library in nativeLibraries) {
|
for (library in nativeLibraries) {
|
||||||
val libraryModule = parseBitcodeFile(library)
|
val libraryModule = parseBitcodeFile(library)
|
||||||
val failed = LLVMLinkModules2(llvmModule, libraryModule)
|
val failed = LLVMLinkModules2(llvmModule, libraryModule)
|
||||||
|
|||||||
+8
-6
@@ -52,7 +52,7 @@ fun runTopLevelPhases(konanConfig: KonanConfig, environment: KotlinCoreEnvironme
|
|||||||
val analyzerWithCompilerReport = AnalyzerWithCompilerReport(context.messageCollector,
|
val analyzerWithCompilerReport = AnalyzerWithCompilerReport(context.messageCollector,
|
||||||
environment.configuration.languageVersionSettings)
|
environment.configuration.languageVersionSettings)
|
||||||
|
|
||||||
val phaser = PhaseManager(context)
|
val phaser = PhaseManager(context, null)
|
||||||
|
|
||||||
phaser.phase(KonanPhase.FRONTEND) {
|
phaser.phase(KonanPhase.FRONTEND) {
|
||||||
// Build AST and binding info.
|
// Build AST and binding info.
|
||||||
@@ -84,21 +84,23 @@ fun runTopLevelPhases(konanConfig: KonanConfig, environment: KotlinCoreEnvironme
|
|||||||
|
|
||||||
// validateIrModule(context, module)
|
// validateIrModule(context, module)
|
||||||
}
|
}
|
||||||
phaser.phase(KonanPhase.SERIALIZER) {
|
phaser.phase(KonanPhase.GEN_SYNTHETIC_FIELDS) {
|
||||||
markBackingFields(context)
|
markBackingFields(context)
|
||||||
|
}
|
||||||
|
phaser.phase(KonanPhase.SERIALIZER) {
|
||||||
val serializer = KonanSerializationUtil(context, context.config.configuration.get(CommonConfigurationKeys.METADATA_VERSION)!!)
|
val serializer = KonanSerializationUtil(context, context.config.configuration.get(CommonConfigurationKeys.METADATA_VERSION)!!)
|
||||||
context.serializedLinkData =
|
context.serializedLinkData =
|
||||||
serializer.serializeModule(context.moduleDescriptor)
|
serializer.serializeModule(context.moduleDescriptor)
|
||||||
}
|
}
|
||||||
phaser.phase(KonanPhase.BACKEND) {
|
phaser.phase(KonanPhase.BACKEND) {
|
||||||
phaser.phase(KonanPhase.LOWER) {
|
phaser.phase(KonanPhase.LOWER) {
|
||||||
KonanLower(context).lower()
|
KonanLower(context, phaser).lower()
|
||||||
// validateIrModule(context, context.ir.irModule) // Temporarily disabled until moving to new IR finished.
|
// validateIrModule(context, context.ir.irModule) // Temporarily disabled until moving to new IR finished.
|
||||||
context.ir.moduleIndexForCodegen = ModuleIndex(context.ir.irModule)
|
context.ir.moduleIndexForCodegen = ModuleIndex(context.ir.irModule)
|
||||||
}
|
}
|
||||||
phaser.phase(KonanPhase.BITCODE) {
|
phaser.phase(KonanPhase.BITCODE) {
|
||||||
emitLLVM(context)
|
emitLLVM(context, phaser)
|
||||||
produceOutput(context)
|
produceOutput(context, phaser)
|
||||||
}
|
}
|
||||||
// We always verify bitcode to prevent hard to debug bugs.
|
// We always verify bitcode to prevent hard to debug bugs.
|
||||||
context.verifyBitCode()
|
context.verifyBitCode()
|
||||||
@@ -109,7 +111,7 @@ fun runTopLevelPhases(konanConfig: KonanConfig, environment: KotlinCoreEnvironme
|
|||||||
}
|
}
|
||||||
|
|
||||||
phaser.phase(KonanPhase.LINK_STAGE) {
|
phaser.phase(KonanPhase.LINK_STAGE) {
|
||||||
LinkStage(context).linkStage()
|
LinkStage(context, phaser).linkStage()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+5
-9
@@ -28,25 +28,23 @@ import org.jetbrains.kotlin.ir.util.checkDeclarationParents
|
|||||||
import org.jetbrains.kotlin.ir.util.patchDeclarationParents
|
import org.jetbrains.kotlin.ir.util.patchDeclarationParents
|
||||||
import org.jetbrains.kotlin.ir.util.replaceUnboundSymbols
|
import org.jetbrains.kotlin.ir.util.replaceUnboundSymbols
|
||||||
|
|
||||||
internal class KonanLower(val context: Context) {
|
internal class KonanLower(val context: Context, val parentPhaser: PhaseManager) {
|
||||||
|
|
||||||
fun lower() {
|
fun lower() {
|
||||||
val irModule = context.irModule!!
|
val irModule = context.irModule!!
|
||||||
|
|
||||||
// Phases to run against whole module.
|
// Phases to run against whole module.
|
||||||
lowerModule(irModule)
|
lowerModule(irModule, parentPhaser)
|
||||||
|
|
||||||
// Phases to run against a file.
|
// Phases to run against a file.
|
||||||
irModule.files.forEach {
|
irModule.files.forEach {
|
||||||
lowerFile(it)
|
lowerFile(it, PhaseManager(context, parentPhaser))
|
||||||
}
|
}
|
||||||
|
|
||||||
irModule.checkDeclarationParents()
|
irModule.checkDeclarationParents()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun lowerModule(irModule: IrModuleFragment) {
|
private fun lowerModule(irModule: IrModuleFragment, phaser: PhaseManager) {
|
||||||
val phaser = PhaseManager(context)
|
|
||||||
|
|
||||||
phaser.phase(KonanPhase.REMOVE_EXPECT_DECLARATIONS) {
|
phaser.phase(KonanPhase.REMOVE_EXPECT_DECLARATIONS) {
|
||||||
irModule.files.forEach(ExpectDeclarationsRemoving(context)::lower)
|
irModule.files.forEach(ExpectDeclarationsRemoving(context)::lower)
|
||||||
}
|
}
|
||||||
@@ -90,9 +88,7 @@ internal class KonanLower(val context: Context) {
|
|||||||
// validateIrModule(context, irModule) // Temporarily disabled until moving to new IR finished.
|
// validateIrModule(context, irModule) // Temporarily disabled until moving to new IR finished.
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun lowerFile(irFile: IrFile) {
|
private fun lowerFile(irFile: IrFile, phaser: PhaseManager) {
|
||||||
val phaser = PhaseManager(context)
|
|
||||||
|
|
||||||
phaser.phase(KonanPhase.LOWER_STRING_CONCAT) {
|
phaser.phase(KonanPhase.LOWER_STRING_CONCAT) {
|
||||||
StringConcatenationLowering(context).lower(irFile)
|
StringConcatenationLowering(context).lower(irFile)
|
||||||
}
|
}
|
||||||
|
|||||||
+11
-5
@@ -25,7 +25,8 @@ enum class KonanPhase(val description: String,
|
|||||||
var verbose: Boolean = false) {
|
var verbose: Boolean = false) {
|
||||||
/* */ FRONTEND("Frontend builds AST"),
|
/* */ FRONTEND("Frontend builds AST"),
|
||||||
/* */ PSI_TO_IR("Psi to IR conversion"),
|
/* */ PSI_TO_IR("Psi to IR conversion"),
|
||||||
/* */ SERIALIZER("Serialize descriptor tree and inline IR bodies"),
|
/* */ GEN_SYNTHETIC_FIELDS("Generate synthetic fields"),
|
||||||
|
/* */ SERIALIZER("Serialize descriptor tree and inline IR bodies", GEN_SYNTHETIC_FIELDS),
|
||||||
/* */ BACKEND("All backend"),
|
/* */ BACKEND("All backend"),
|
||||||
/* ... */ LOWER("IR Lowering"),
|
/* ... */ LOWER("IR Lowering"),
|
||||||
/* ... ... */ REMOVE_EXPECT_DECLARATIONS("Expect declarations removing"),
|
/* ... ... */ REMOVE_EXPECT_DECLARATIONS("Expect declarations removing"),
|
||||||
@@ -49,7 +50,7 @@ enum class KonanPhase(val description: String,
|
|||||||
/* ... ... */ LOWER_DEFAULT_PARAMETER_EXTENT("Default Parameter Extent Lowering", LOWER_TAILREC, LOWER_ENUMS),
|
/* ... ... */ LOWER_DEFAULT_PARAMETER_EXTENT("Default Parameter Extent Lowering", LOWER_TAILREC, LOWER_ENUMS),
|
||||||
/* ... ... */ LOWER_VARARG("Vararg lowering", LOWER_CALLABLES, LOWER_DEFAULT_PARAMETER_EXTENT),
|
/* ... ... */ LOWER_VARARG("Vararg lowering", LOWER_CALLABLES, LOWER_DEFAULT_PARAMETER_EXTENT),
|
||||||
/* ... ... */ LOWER_COMPILE_TIME_EVAL("Compile time evaluation lowering", LOWER_VARARG),
|
/* ... ... */ LOWER_COMPILE_TIME_EVAL("Compile time evaluation lowering", LOWER_VARARG),
|
||||||
/* ... ... */ LOWER_INNER_CLASSES("Inner classes lowering", LOWER_DEFAULT_PARAMETER_EXTENT),
|
/* ... ... */ LOWER_INNER_CLASSES("Inner classes lowering", LOWER_DEFAULT_PARAMETER_EXTENT, GEN_SYNTHETIC_FIELDS),
|
||||||
/* ... ... */ LOWER_BUILTIN_OPERATORS("BuiltIn Operators Lowering", LOWER_DEFAULT_PARAMETER_EXTENT),
|
/* ... ... */ LOWER_BUILTIN_OPERATORS("BuiltIn Operators Lowering", LOWER_DEFAULT_PARAMETER_EXTENT),
|
||||||
/* ... ... */ LOWER_COROUTINES("Coroutines lowering", LOWER_LOCAL_FUNCTIONS),
|
/* ... ... */ LOWER_COROUTINES("Coroutines lowering", LOWER_LOCAL_FUNCTIONS),
|
||||||
/* ... ... */ LOWER_TYPE_OPERATORS("Type operators lowering", LOWER_COROUTINES),
|
/* ... ... */ LOWER_TYPE_OPERATORS("Type operators lowering", LOWER_COROUTINES),
|
||||||
@@ -115,16 +116,21 @@ object KonanPhases {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
internal class PhaseManager(val context: Context) {
|
internal class PhaseManager(val context: Context, val parent: PhaseManager? = null) {
|
||||||
|
|
||||||
val previousPhases = mutableSetOf<KonanPhase>()
|
val previousPhases = mutableSetOf<KonanPhase>()
|
||||||
|
|
||||||
internal fun phase(phase: KonanPhase, body: () -> Unit) {
|
fun createChild() = PhaseManager(context, this)
|
||||||
|
|
||||||
|
private fun checkPrerequisite(phase: KonanPhase): Boolean =
|
||||||
|
previousPhases.contains(phase) || parent?.checkPrerequisite(phase) == true
|
||||||
|
|
||||||
|
fun phase(phase: KonanPhase, body: () -> Unit) {
|
||||||
|
|
||||||
if (!phase.enabled) return
|
if (!phase.enabled) return
|
||||||
|
|
||||||
phase.prerequisite.forEach {
|
phase.prerequisite.forEach {
|
||||||
if (!previousPhases.contains(it))
|
if (!checkPrerequisite(it))
|
||||||
throw Error("$phase requires $it")
|
throw Error("$phase requires $it")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+1
-2
@@ -26,7 +26,7 @@ typealias BitcodeFile = String
|
|||||||
typealias ObjectFile = String
|
typealias ObjectFile = String
|
||||||
typealias ExecutableFile = String
|
typealias ExecutableFile = String
|
||||||
|
|
||||||
internal class LinkStage(val context: Context) {
|
internal class LinkStage(val context: Context, val phaser: PhaseManager) {
|
||||||
|
|
||||||
private val config = context.config.configuration
|
private val config = context.config.configuration
|
||||||
private val target = context.config.target
|
private val target = context.config.target
|
||||||
@@ -228,7 +228,6 @@ internal class LinkStage(val context: Context) {
|
|||||||
|
|
||||||
val objectFiles: MutableList<String> = mutableListOf()
|
val objectFiles: MutableList<String> = mutableListOf()
|
||||||
|
|
||||||
val phaser = PhaseManager(context)
|
|
||||||
phaser.phase(KonanPhase.OBJECT_FILES) {
|
phaser.phase(KonanPhase.OBJECT_FILES) {
|
||||||
objectFiles.add(
|
objectFiles.add(
|
||||||
when (platform.configurables) {
|
when (platform.configurables) {
|
||||||
|
|||||||
+1
-3
@@ -51,7 +51,7 @@ private val threadLocalAnnotationFqName = FqName("konan.ThreadLocal")
|
|||||||
val IrClassSymbol.objectIsShared get() =
|
val IrClassSymbol.objectIsShared get() =
|
||||||
!descriptor.annotations.hasAnnotation(threadLocalAnnotationFqName)
|
!descriptor.annotations.hasAnnotation(threadLocalAnnotationFqName)
|
||||||
|
|
||||||
internal fun emitLLVM(context: Context) {
|
internal fun emitLLVM(context: Context, phaser: PhaseManager) {
|
||||||
val irModule = context.irModule!!
|
val irModule = context.irModule!!
|
||||||
|
|
||||||
// Note that we don't set module target explicitly.
|
// Note that we don't set module target explicitly.
|
||||||
@@ -64,8 +64,6 @@ internal fun emitLLVM(context: Context) {
|
|||||||
context.debugInfo.builder = DICreateBuilder(llvmModule)
|
context.debugInfo.builder = DICreateBuilder(llvmModule)
|
||||||
context.llvmDeclarations = createLlvmDeclarations(context)
|
context.llvmDeclarations = createLlvmDeclarations(context)
|
||||||
|
|
||||||
val phaser = PhaseManager(context)
|
|
||||||
|
|
||||||
phaser.phase(KonanPhase.RTTI) {
|
phaser.phase(KonanPhase.RTTI) {
|
||||||
irModule.acceptVoid(RTTIGeneratorVisitor(context))
|
irModule.acceptVoid(RTTIGeneratorVisitor(context))
|
||||||
}
|
}
|
||||||
|
|||||||
+1
-4
@@ -32,7 +32,6 @@ import org.jetbrains.kotlin.ir.expressions.impl.IrGetValueImpl
|
|||||||
import org.jetbrains.kotlin.ir.expressions.impl.IrSetFieldImpl
|
import org.jetbrains.kotlin.ir.expressions.impl.IrSetFieldImpl
|
||||||
import org.jetbrains.kotlin.ir.symbols.IrConstructorSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrConstructorSymbol
|
||||||
import org.jetbrains.kotlin.ir.symbols.IrFieldSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrFieldSymbol
|
||||||
import org.jetbrains.kotlin.ir.util.addChild
|
|
||||||
import org.jetbrains.kotlin.ir.util.transformFlat
|
import org.jetbrains.kotlin.ir.util.transformFlat
|
||||||
import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid
|
import org.jetbrains.kotlin.ir.visitors.transformChildrenVoid
|
||||||
import org.jetbrains.kotlin.resolve.scopes.receivers.ImplicitClassReceiver
|
import org.jetbrains.kotlin.resolve.scopes.receivers.ImplicitClassReceiver
|
||||||
@@ -56,9 +55,7 @@ internal class InnerClassLowering(val context: Context) : ClassLoweringPass {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun createOuterThisField() {
|
private fun createOuterThisField() {
|
||||||
val field = context.specialDeclarationsFactory.getOuterThisField(irClass)
|
outerThisFieldSymbol = context.specialDeclarationsFactory.getOuterThisField(irClass).symbol
|
||||||
outerThisFieldSymbol = field.symbol
|
|
||||||
irClass.addChild(field)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun lowerConstructors() {
|
private fun lowerConstructors() {
|
||||||
|
|||||||
+8
-2
@@ -17,13 +17,12 @@
|
|||||||
package org.jetbrains.kotlin.backend.konan.serialization
|
package org.jetbrains.kotlin.backend.konan.serialization
|
||||||
|
|
||||||
import org.jetbrains.kotlin.backend.konan.Context
|
import org.jetbrains.kotlin.backend.konan.Context
|
||||||
import org.jetbrains.kotlin.descriptors.PropertyDescriptor
|
|
||||||
import org.jetbrains.kotlin.ir.IrElement
|
import org.jetbrains.kotlin.ir.IrElement
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrClass
|
import org.jetbrains.kotlin.ir.declarations.IrClass
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrField
|
import org.jetbrains.kotlin.ir.declarations.IrField
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrFile
|
import org.jetbrains.kotlin.ir.declarations.IrFile
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrProperty
|
import org.jetbrains.kotlin.ir.declarations.IrProperty
|
||||||
import org.jetbrains.kotlin.ir.util.parentAsClass
|
import org.jetbrains.kotlin.ir.util.addChild
|
||||||
import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid
|
import org.jetbrains.kotlin.ir.visitors.IrElementVisitorVoid
|
||||||
import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid
|
import org.jetbrains.kotlin.ir.visitors.acceptChildrenVoid
|
||||||
|
|
||||||
@@ -34,6 +33,8 @@ internal class BackingFieldVisitor(val context: Context) : IrElementVisitorVoid
|
|||||||
}
|
}
|
||||||
|
|
||||||
override fun visitProperty(declaration: IrProperty) {
|
override fun visitProperty(declaration: IrProperty) {
|
||||||
|
super.visitProperty(declaration)
|
||||||
|
|
||||||
if (declaration.isDelegated) {
|
if (declaration.isDelegated) {
|
||||||
val irClass = declaration.parent as? IrClass
|
val irClass = declaration.parent as? IrClass
|
||||||
val list = irClass?.let { context.ir.classesDelegatedBackingFields.getOrPut(irClass.descriptor) { mutableListOf() } }
|
val list = irClass?.let { context.ir.classesDelegatedBackingFields.getOrPut(irClass.descriptor) { mutableListOf() } }
|
||||||
@@ -46,10 +47,15 @@ internal class BackingFieldVisitor(val context: Context) : IrElementVisitorVoid
|
|||||||
}
|
}
|
||||||
|
|
||||||
override fun visitClass(declaration: IrClass) {
|
override fun visitClass(declaration: IrClass) {
|
||||||
|
if (declaration.isInner)
|
||||||
|
declaration.addChild(context.specialDeclarationsFactory.getOuterThisField(declaration))
|
||||||
|
|
||||||
|
// Mark all dangling fields (they are created when class is inherited via delegation).
|
||||||
declaration.declarations.filterIsInstance<IrField>().forEach {
|
declaration.declarations.filterIsInstance<IrField>().forEach {
|
||||||
val list = context.ir.classesDelegatedBackingFields.getOrPut(declaration.descriptor) { mutableListOf() }
|
val list = context.ir.classesDelegatedBackingFields.getOrPut(declaration.descriptor) { mutableListOf() }
|
||||||
list.add(it.descriptor)
|
list.add(it.descriptor)
|
||||||
}
|
}
|
||||||
|
|
||||||
super.visitClass(declaration)
|
super.visitClass(declaration)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user