[K/N] Get rid of outdated module initializers

This commit is contained in:
Pavel Kunyavskiy
2022-07-08 12:18:55 +02:00
committed by Space Team
parent cf80a86855
commit d09a18c88b
6 changed files with 19 additions and 49 deletions
@@ -240,16 +240,12 @@ internal class InitializersGenerationState {
val fileThreadLocalInitStates = mutableMapOf<IrFile, AddressAccess>() val fileThreadLocalInitStates = mutableMapOf<IrFile, AddressAccess>()
val topLevelFields = mutableListOf<IrField>() val topLevelFields = mutableListOf<IrField>()
val moduleThreadLocalInitializers = mutableListOf<IrFunction>()
val moduleGlobalInitializers = mutableListOf<IrFunction>()
var globalInitFunction: IrFunction? = null var globalInitFunction: IrFunction? = null
var globalInitState: LLVMValueRef? = null var globalInitState: LLVMValueRef? = null
var threadLocalInitFunction: IrFunction? = null var threadLocalInitFunction: IrFunction? = null
var threadLocalInitState: AddressAccess? = null var threadLocalInitState: AddressAccess? = null
fun reset() { fun reset() {
moduleThreadLocalInitializers.clear()
moduleGlobalInitializers.clear()
topLevelFields.clear() topLevelFields.clear()
globalInitFunction = null globalInitFunction = null
globalInitState = null globalInitState = null
@@ -258,7 +254,6 @@ internal class InitializersGenerationState {
} }
fun isEmpty() = topLevelFields.isEmpty() && globalInitState == null && threadLocalInitState == null fun isEmpty() = topLevelFields.isEmpty() && globalInitState == null && threadLocalInitState == null
&& moduleGlobalInitializers.isEmpty() && moduleThreadLocalInitializers.isEmpty()
} }
internal class ConstInt1(llvm: Llvm, val value: Boolean) : ConstValue { internal class ConstInt1(llvm: Llvm, val value: Boolean) : ConstValue {
@@ -18,8 +18,6 @@ import org.jetbrains.kotlin.backend.konan.lower.*
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_FILE_GLOBAL_INITIALIZER import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_FILE_GLOBAL_INITIALIZER
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_FILE_STANDALONE_THREAD_LOCAL_INITIALIZER import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_FILE_STANDALONE_THREAD_LOCAL_INITIALIZER
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_FILE_THREAD_LOCAL_INITIALIZER import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_FILE_THREAD_LOCAL_INITIALIZER
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_MODULE_GLOBAL_INITIALIZER
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_MODULE_THREAD_LOCAL_INITIALIZER
import org.jetbrains.kotlin.builtins.UnsignedType import org.jetbrains.kotlin.builtins.UnsignedType
import org.jetbrains.kotlin.descriptors.Modality import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.ir.IrElement import org.jetbrains.kotlin.ir.IrElement
@@ -501,9 +499,6 @@ internal class CodeGeneratorVisitor(val context: Context, val lifetimes: Map<IrE
.filter { !context.useLazyFileInitializers() || it.shouldBeInitializedEagerly } .filter { !context.useLazyFileInitializers() || it.shouldBeInitializedEagerly }
.filterNot { it.storageKind(context) == FieldStorageKind.THREAD_LOCAL } .filterNot { it.storageKind(context) == FieldStorageKind.THREAD_LOCAL }
.forEach { initGlobalField(it) } .forEach { initGlobalField(it) }
llvm.initializersGenerationState.moduleGlobalInitializers.forEach {
evaluateSimpleFunctionCall(it, emptyList(), Lifetime.IRRELEVANT)
}
ret(null) ret(null)
} }
@@ -517,9 +512,6 @@ internal class CodeGeneratorVisitor(val context: Context, val lifetimes: Map<IrE
.filter { !context.useLazyFileInitializers() || it.shouldBeInitializedEagerly } .filter { !context.useLazyFileInitializers() || it.shouldBeInitializedEagerly }
.filter { it.storageKind(context) == FieldStorageKind.THREAD_LOCAL } .filter { it.storageKind(context) == FieldStorageKind.THREAD_LOCAL }
.forEach { initThreadLocalField(it) } .forEach { initThreadLocalField(it) }
llvm.initializersGenerationState.moduleThreadLocalInitializers.forEach {
evaluateSimpleFunctionCall(it, emptyList(), Lifetime.IRRELEVANT, null)
}
ret(null) ret(null)
} }
@@ -816,16 +808,7 @@ internal class CodeGeneratorVisitor(val context: Context, val lifetimes: Map<IrE
llvm.initializersGenerationState.threadLocalInitFunction = declaration llvm.initializersGenerationState.threadLocalInitFunction = declaration
llvm.initializersGenerationState.threadLocalInitState = getThreadLocalInitStateFor(declaration.parent as IrFile) llvm.initializersGenerationState.threadLocalInitState = getThreadLocalInitStateFor(declaration.parent as IrFile)
} }
if (declaration.origin == DECLARATION_ORIGIN_MODULE_GLOBAL_INITIALIZER) {
require(declaration.valueParameters.isEmpty()) { "Module initializer must be a parameterless function" }
require(declaration.returnsUnit()) { "Module initializer must return Unit" }
llvm.initializersGenerationState.moduleGlobalInitializers.add(declaration)
}
if (declaration.origin == DECLARATION_ORIGIN_MODULE_THREAD_LOCAL_INITIALIZER) {
require(declaration.valueParameters.isEmpty()) { "Module initializer must be a parameterless function" }
require(declaration.returnsUnit()) { "Module initializer must return Unit" }
llvm.initializersGenerationState.moduleThreadLocalInitializers.add(declaration)
}
if ((declaration as? IrSimpleFunction)?.modality == Modality.ABSTRACT if ((declaration as? IrSimpleFunction)?.modality == Modality.ABSTRACT
|| declaration.isExternal || declaration.isExternal
@@ -25,8 +25,6 @@ import org.jetbrains.kotlin.ir.util.hasNonConstInitializer
import org.jetbrains.kotlin.ir.util.simpleFunctions import org.jetbrains.kotlin.ir.util.simpleFunctions
import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.name.Name
internal object DECLARATION_ORIGIN_MODULE_GLOBAL_INITIALIZER : IrDeclarationOriginImpl("MODULE_GLOBAL_INITIALIZER")
internal object DECLARATION_ORIGIN_MODULE_THREAD_LOCAL_INITIALIZER : IrDeclarationOriginImpl("MODULE_THREAD_LOCAL_INITIALIZER")
internal object DECLARATION_ORIGIN_FILE_GLOBAL_INITIALIZER : IrDeclarationOriginImpl("FILE_GLOBAL_INITIALIZER") internal object DECLARATION_ORIGIN_FILE_GLOBAL_INITIALIZER : IrDeclarationOriginImpl("FILE_GLOBAL_INITIALIZER")
internal object DECLARATION_ORIGIN_FILE_THREAD_LOCAL_INITIALIZER : IrDeclarationOriginImpl("FILE_THREAD_LOCAL_INITIALIZER") internal object DECLARATION_ORIGIN_FILE_THREAD_LOCAL_INITIALIZER : IrDeclarationOriginImpl("FILE_THREAD_LOCAL_INITIALIZER")
internal object DECLARATION_ORIGIN_FILE_STANDALONE_THREAD_LOCAL_INITIALIZER : IrDeclarationOriginImpl("FILE_STANDALONE_THREAD_LOCAL_INITIALIZER") internal object DECLARATION_ORIGIN_FILE_STANDALONE_THREAD_LOCAL_INITIALIZER : IrDeclarationOriginImpl("FILE_STANDALONE_THREAD_LOCAL_INITIALIZER")
@@ -36,10 +34,6 @@ internal val IrFunction.isFileInitializer: Boolean
|| origin == DECLARATION_ORIGIN_FILE_THREAD_LOCAL_INITIALIZER || origin == DECLARATION_ORIGIN_FILE_THREAD_LOCAL_INITIALIZER
|| origin == DECLARATION_ORIGIN_FILE_STANDALONE_THREAD_LOCAL_INITIALIZER || origin == DECLARATION_ORIGIN_FILE_STANDALONE_THREAD_LOCAL_INITIALIZER
internal val IrFunction.isModuleInitializer: Boolean
get() = origin == DECLARATION_ORIGIN_MODULE_GLOBAL_INITIALIZER
|| origin == DECLARATION_ORIGIN_MODULE_THREAD_LOCAL_INITIALIZER
internal fun IrBuilderWithScope.irCallFileInitializer(initializer: IrFunctionSymbol) = internal fun IrBuilderWithScope.irCallFileInitializer(initializer: IrFunctionSymbol) =
irCall(initializer) irCall(initializer)
@@ -82,7 +76,7 @@ internal class FileInitializersLowering(val context: Context) : FileLoweringPass
else null else null
irFile.simpleFunctions() irFile.simpleFunctions()
.filterNot { it.isModuleInitializer || it.origin == DECLARATION_ORIGIN_ENTRY_POINT } .filterNot { it.origin == DECLARATION_ORIGIN_ENTRY_POINT }
.forEach { .forEach {
val body = it.body ?: return@forEach val body = it.body ?: return@forEach
val statements = (body as IrBlockBody).statements val statements = (body as IrBlockBody).statements
@@ -12,21 +12,22 @@ import org.jetbrains.kotlin.backend.konan.Context
import org.jetbrains.kotlin.backend.konan.descriptors.isAbstract import org.jetbrains.kotlin.backend.konan.descriptors.isAbstract
import org.jetbrains.kotlin.backend.konan.descriptors.synthesizedName import org.jetbrains.kotlin.backend.konan.descriptors.synthesizedName
import org.jetbrains.kotlin.backend.konan.getIncludedLibraryDescriptors import org.jetbrains.kotlin.backend.konan.getIncludedLibraryDescriptors
import org.jetbrains.kotlin.backend.konan.ir.buildSimpleAnnotation
import org.jetbrains.kotlin.backend.konan.reportCompilationError import org.jetbrains.kotlin.backend.konan.reportCompilationError
import org.jetbrains.kotlin.descriptors.ClassKind import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.DescriptorVisibilities import org.jetbrains.kotlin.descriptors.DescriptorVisibilities
import org.jetbrains.kotlin.descriptors.Modality import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.ir.IrElement import org.jetbrains.kotlin.ir.IrElement
import org.jetbrains.kotlin.ir.IrStatement
import org.jetbrains.kotlin.ir.builders.* import org.jetbrains.kotlin.ir.builders.*
import org.jetbrains.kotlin.ir.builders.declarations.buildField
import org.jetbrains.kotlin.ir.builders.declarations.buildFun import org.jetbrains.kotlin.ir.builders.declarations.buildFun
import org.jetbrains.kotlin.ir.declarations.* import org.jetbrains.kotlin.ir.declarations.*
import org.jetbrains.kotlin.ir.declarations.impl.IrClassImpl import org.jetbrains.kotlin.ir.declarations.impl.IrClassImpl
import org.jetbrains.kotlin.ir.declarations.impl.IrConstructorImpl import org.jetbrains.kotlin.ir.declarations.impl.IrConstructorImpl
import org.jetbrains.kotlin.ir.declarations.impl.IrFunctionImpl import org.jetbrains.kotlin.ir.declarations.impl.IrFunctionImpl
import org.jetbrains.kotlin.ir.expressions.IrExpression import org.jetbrains.kotlin.ir.expressions.IrExpression
import org.jetbrains.kotlin.ir.expressions.impl.IrBlockBodyImpl import org.jetbrains.kotlin.ir.expressions.impl.*
import org.jetbrains.kotlin.ir.expressions.impl.IrFunctionReferenceImpl
import org.jetbrains.kotlin.ir.expressions.impl.IrGetEnumValueImpl
import org.jetbrains.kotlin.ir.symbols.IrClassSymbol import org.jetbrains.kotlin.ir.symbols.IrClassSymbol
import org.jetbrains.kotlin.ir.symbols.IrEnumEntrySymbol import org.jetbrains.kotlin.ir.symbols.IrEnumEntrySymbol
import org.jetbrains.kotlin.ir.symbols.IrFunctionSymbol import org.jetbrains.kotlin.ir.symbols.IrFunctionSymbol
@@ -590,7 +591,7 @@ internal class TestProcessor (val context: Context) {
} }
private fun createTestSuites(irFile: IrFile, annotationCollector: AnnotationCollector) { private fun createTestSuites(irFile: IrFile, annotationCollector: AnnotationCollector) {
val statements = mutableListOf<IrExpression>() val statements = mutableListOf<IrStatement>()
// There is no specified order on fake override functions, so to ensure all the tests are run deterministically, // There is no specified order on fake override functions, so to ensure all the tests are run deterministically,
// sort the fake override functions by name. // sort the fake override functions by name.
@@ -619,19 +620,23 @@ internal class TestProcessor (val context: Context) {
} }
if (statements.isNotEmpty()) { if (statements.isNotEmpty()) {
context.irFactory.buildFun { context.irFactory.buildField {
startOffset = SYNTHETIC_OFFSET startOffset = SYNTHETIC_OFFSET
endOffset = SYNTHETIC_OFFSET endOffset = SYNTHETIC_OFFSET
origin = DECLARATION_ORIGIN_MODULE_THREAD_LOCAL_INITIALIZER name = "createTestSuites".synthesizedName
name = Name.identifier("\$createTestSuites")
visibility = DescriptorVisibilities.PRIVATE visibility = DescriptorVisibilities.PRIVATE
returnType = context.irBuiltIns.unitType isFinal = true
isStatic = true
type = context.irBuiltIns.unitType
}.apply { }.apply {
parent = irFile parent = irFile
irFile.declarations.add(this) irFile.declarations.add(this)
annotations += buildSimpleAnnotation(context.irBuiltIns, startOffset, endOffset, context.ir.symbols.eagerInitialization.owner)
annotations += buildSimpleAnnotation(context.irBuiltIns, startOffset, endOffset, context.ir.symbols.threadLocal.owner)
statements.forEach { it.accept(SetDeclarationsParentVisitor, this) } statements.forEach { it.accept(SetDeclarationsParentVisitor, this) }
body = IrBlockBodyImpl(SYNTHETIC_OFFSET, SYNTHETIC_OFFSET, statements) initializer = IrExpressionBodyImpl(SYNTHETIC_OFFSET, SYNTHETIC_OFFSET,
IrCompositeImpl(SYNTHETIC_OFFSET, SYNTHETIC_OFFSET, context.irBuiltIns.unitType, null, statements)
)
} }
} }
} }
@@ -13,8 +13,6 @@ import org.jetbrains.kotlin.backend.konan.llvm.computeSymbolName
import org.jetbrains.kotlin.backend.konan.llvm.isExported import org.jetbrains.kotlin.backend.konan.llvm.isExported
import org.jetbrains.kotlin.backend.konan.llvm.localHash import org.jetbrains.kotlin.backend.konan.llvm.localHash
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_BRIDGE_METHOD import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_BRIDGE_METHOD
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_MODULE_GLOBAL_INITIALIZER
import org.jetbrains.kotlin.backend.konan.lower.DECLARATION_ORIGIN_MODULE_THREAD_LOCAL_INITIALIZER
import org.jetbrains.kotlin.backend.konan.lower.bridgeTarget import org.jetbrains.kotlin.backend.konan.lower.bridgeTarget
import org.jetbrains.kotlin.descriptors.Modality import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.descriptors.ModuleDescriptor import org.jetbrains.kotlin.descriptors.ModuleDescriptor
@@ -113,7 +111,6 @@ internal object DataFlowIR {
object FunctionAttributes { object FunctionAttributes {
val IS_TOP_LEVEL_FIELD_INITIALIZER = 1 val IS_TOP_LEVEL_FIELD_INITIALIZER = 1
val IS_GLOBAL_INITIALIZER = 2
val RETURNS_UNIT = 4 val RETURNS_UNIT = 4
val RETURNS_NOTHING = 8 val RETURNS_NOTHING = 8
val EXPLICITLY_EXPORTED = 16 val EXPLICITLY_EXPORTED = 16
@@ -126,7 +123,6 @@ internal object DataFlowIR {
lateinit var returnParameter: FunctionParameter lateinit var returnParameter: FunctionParameter
val isTopLevelFieldInitializer = attributes.and(FunctionAttributes.IS_TOP_LEVEL_FIELD_INITIALIZER) != 0 val isTopLevelFieldInitializer = attributes.and(FunctionAttributes.IS_TOP_LEVEL_FIELD_INITIALIZER) != 0
val isGlobalInitializer = attributes.and(FunctionAttributes.IS_GLOBAL_INITIALIZER) != 0
val returnsUnit = attributes.and(FunctionAttributes.RETURNS_UNIT) != 0 val returnsUnit = attributes.and(FunctionAttributes.RETURNS_UNIT) != 0
val returnsNothing = attributes.and(FunctionAttributes.RETURNS_NOTHING) != 0 val returnsNothing = attributes.and(FunctionAttributes.RETURNS_NOTHING) != 0
val explicitlyExported = attributes.and(FunctionAttributes.EXPLICITLY_EXPORTED) != 0 val explicitlyExported = attributes.and(FunctionAttributes.EXPLICITLY_EXPORTED) != 0
@@ -607,9 +603,6 @@ internal object DataFlowIR {
|| it.hasAnnotation(RuntimeNames.objCMethodImp)) { || it.hasAnnotation(RuntimeNames.objCMethodImp)) {
attributes = attributes or FunctionAttributes.EXPLICITLY_EXPORTED attributes = attributes or FunctionAttributes.EXPLICITLY_EXPORTED
} }
if (it.origin == DECLARATION_ORIGIN_MODULE_GLOBAL_INITIALIZER
|| it.origin == DECLARATION_ORIGIN_MODULE_THREAD_LOCAL_INITIALIZER)
attributes = attributes or FunctionAttributes.IS_GLOBAL_INITIALIZER
val symbol = when { val symbol = when {
it.isExternal || it.isBuiltInOperator -> { it.isExternal || it.isBuiltInOperator -> {
val escapesAnnotation = it.annotations.findAnnotation(FQ_NAME_ESCAPES) val escapesAnnotation = it.annotations.findAnnotation(FQ_NAME_ESCAPES)
@@ -83,8 +83,8 @@ internal object DevirtualizationAnalysis {
// TODO: Are globals initializers always called whether they are actually reachable from roots or not? // TODO: Are globals initializers always called whether they are actually reachable from roots or not?
// TODO: With the changed semantics of global initializers this is no longer the case - rework. // TODO: With the changed semantics of global initializers this is no longer the case - rework.
val globalInitializers = val globalInitializers =
moduleDFG.symbolTable.functionMap.values.filter { it.isTopLevelFieldInitializer || it.isGlobalInitializer } + moduleDFG.symbolTable.functionMap.values.filter { it.isTopLevelFieldInitializer } +
externalModulesDFG.functionDFGs.keys.filter { it.isTopLevelFieldInitializer || it.isGlobalInitializer } externalModulesDFG.functionDFGs.keys.filter { it.isTopLevelFieldInitializer }
val explicitlyExported = val explicitlyExported =
moduleDFG.symbolTable.functionMap.values.filter { it.explicitlyExported } + moduleDFG.symbolTable.functionMap.values.filter { it.explicitlyExported } +