From bdfb3c3ac97bc37be77c1194b64df82bc71f84f8 Mon Sep 17 00:00:00 2001 From: Mads Ager Date: Thu, 12 Oct 2023 15:16:10 +0200 Subject: [PATCH] [Native] Move remaining usages for LLVMBuildLoad to LLVMBuildLoad2. Step towards LLVM opaque pointers. --- .../kotlin/backend/konan/CheckExternalCalls.kt | 2 +- .../kotlin/backend/konan/llvm/CodeGenerator.kt | 17 ++++++++++++----- .../backend/konan/llvm/IntrinsicGenerator.kt | 2 +- .../kotlin/backend/konan/llvm/IrToBitcode.kt | 7 +++++-- .../backend/konan/llvm/VariableManager.kt | 16 +++++++++------- .../llvm/objcexport/BlockPointerSupport.kt | 2 +- kotlin-native/backend.native/llvm.def | 5 ++++- 7 files changed, 33 insertions(+), 18 deletions(-) diff --git a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/CheckExternalCalls.kt b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/CheckExternalCalls.kt index 582e1448c21..2de34d243d9 100644 --- a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/CheckExternalCalls.kt +++ b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/CheckExternalCalls.kt @@ -128,7 +128,7 @@ private class CallsChecker(generationState: NativeGenerationState, goodFunctions calledName = null val superStruct = LLVMGetArgOperand(call, 0) val superClassPtrPtr = LLVMBuildGEP(builder, superStruct, listOf(llvm.int32(0), llvm.int32(1)).toCValues(), 2, "") - val superClassPtr = LLVMBuildLoad(builder, superClassPtrPtr, "")!! + val superClassPtr = LLVMBuildLoad2(builder, llvm.int8PtrType, superClassPtrPtr, "")!! val classPtr = getSuperClass.buildCall(builder, listOf(superClassPtr)) val calledPtrLlvmFunPtr = getMethodImpl.buildCall(builder, listOf(classPtr, LLVMGetArgOperand(call, 1)!!)) calledPtrLlvm = LLVMBuildBitCast(builder, calledPtrLlvmFunPtr, llvm.int8PtrType, "")!! diff --git a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/CodeGenerator.kt b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/CodeGenerator.kt index 22c7cb1d930..b9b5e4605cc 100644 --- a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/CodeGenerator.kt +++ b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/CodeGenerator.kt @@ -725,13 +725,20 @@ internal abstract class FunctionGenerationContext( return applyMemoryOrderAndAlignment(LLVMBuildLoad2(builder, type, address, name)!!, memoryOrder, alignment) } - fun loadSlot(address: LLVMValueRef, isVar: Boolean, resultSlot: LLVMValueRef? = null, name: String = "", - memoryOrder: LLVMAtomicOrdering? = null, alignment: Int? = null): LLVMValueRef { - val value = LLVMBuildLoad(builder, address, name)!! + fun loadSlot( + type: LLVMTypeRef, + address: LLVMValueRef, + isVar: Boolean, + resultSlot: LLVMValueRef? = null, + name: String = "", + memoryOrder: LLVMAtomicOrdering? = null, + alignment: Int? = null + ): LLVMValueRef { + val value = LLVMBuildLoad2(builder, type, address, name)!! memoryOrder?.let { LLVMSetOrdering(value, it) } alignment?.let { LLVMSetAlignment(value, it) } - if (isObjectRef(value) && isVar) { - val slot = resultSlot ?: alloca(LLVMTypeOf(value), variableLocation = null) + if (isObjectType(type) && isVar) { + val slot = resultSlot ?: alloca(type, variableLocation = null) storeStackRef(value, slot) } return value diff --git a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IntrinsicGenerator.kt b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IntrinsicGenerator.kt index ec1a7142126..b10c6d8f09d 100644 --- a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IntrinsicGenerator.kt +++ b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IntrinsicGenerator.kt @@ -419,7 +419,7 @@ internal class IntrinsicGenerator(private val environment: IntrinsicGeneratorEnv private fun FunctionGenerationContext.emitAtomicGetArrayElement(callSite: IrCall, args: List, resultSlot: LLVMValueRef?): LLVMValueRef { require(args.size == 2) { "The call to ${callSite.symbol.owner.name.asString()} expects 2 value arguments." } val address = arrayGetElementAddress(callSite, args[0], args[1]) - return loadSlot(address, isVar = true, resultSlot, memoryOrder = LLVMAtomicOrdering.LLVMAtomicOrderingSequentiallyConsistent) + return loadSlot(callSite.llvmReturnType, address, isVar = true, resultSlot, memoryOrder = LLVMAtomicOrdering.LLVMAtomicOrderingSequentiallyConsistent) } private fun FunctionGenerationContext.transformArgsForAtomicArray(callSite: IrCall, args: List): List { diff --git a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IrToBitcode.kt b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IrToBitcode.kt index f4c8c6a6958..a8eb22a2838 100644 --- a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IrToBitcode.kt +++ b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/IrToBitcode.kt @@ -1785,7 +1785,10 @@ internal class CodeGeneratorVisitor( } } return functionGenerationContext.loadSlot( - fieldAddress, !value.symbol.owner.isFinal, resultSlot, + value.type.toLLVMType(llvm), + fieldAddress, + !value.symbol.owner.isFinal, + resultSlot, memoryOrder = order, alignment = alignment ) @@ -2938,7 +2941,7 @@ internal class CodeGeneratorVisitor( val bbNeedInit = basicBlock("need_init", null) - val value = LLVMBuildLoad(builder, initGuard, "")!! + val value = LLVMBuildLoad2(builder, llvm.int32Type, initGuard, "")!! condBr(icmpEq(value, llvm.kImmInt32Zero), bbNeedInit, bbInited) appendingTo(bbInited) { diff --git a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/VariableManager.kt b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/VariableManager.kt index 6c91e7d3a9d..e42a3d24c33 100644 --- a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/VariableManager.kt +++ b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/VariableManager.kt @@ -23,8 +23,9 @@ internal class VariableManager(val functionGenerationContext: FunctionGeneration fun address() : LLVMValueRef } - inner class SlotRecord(val address: LLVMValueRef, val refSlot: Boolean, val isVar: Boolean) : Record { - override fun load(resultSlot: LLVMValueRef?) : LLVMValueRef = functionGenerationContext.loadSlot(address, isVar, resultSlot) + inner class SlotRecord(val address: LLVMValueRef, val type: LLVMTypeRef, val isVar: Boolean) : Record { + val refSlot = functionGenerationContext.isObjectType(type) + override fun load(resultSlot: LLVMValueRef?) : LLVMValueRef = functionGenerationContext.loadSlot(type, address, isVar, resultSlot) override fun store(value: LLVMValueRef) { functionGenerationContext.storeAny(value, address, true) } @@ -32,8 +33,9 @@ internal class VariableManager(val functionGenerationContext: FunctionGeneration override fun toString() = (if (refSlot) "refslot" else "slot") + " for ${address}" } - inner class ParameterRecord(val address: LLVMValueRef, val refSlot: Boolean) : Record { - override fun load(resultSlot: LLVMValueRef?): LLVMValueRef = functionGenerationContext.loadSlot(address, false, resultSlot) + inner class ParameterRecord(val address: LLVMValueRef, val type: LLVMTypeRef) : Record { + val refSlot = functionGenerationContext.isObjectType(type) + override fun load(resultSlot: LLVMValueRef?): LLVMValueRef = functionGenerationContext.loadSlot(type, address, false, resultSlot) override fun store(value: LLVMValueRef) = functionGenerationContext.store(value, address) override fun address() : LLVMValueRef = this.address override fun toString() = (if (refSlot) "refslot" else "slot") + " for ${address}" @@ -79,7 +81,7 @@ internal class VariableManager(val functionGenerationContext: FunctionGeneration val slot = functionGenerationContext.alloca(type, valueDeclaration.name.asString(), variableLocation) if (value != null) functionGenerationContext.storeAny(value, slot, true) - variables.add(SlotRecord(slot, functionGenerationContext.isObjectType(type), isVar)) + variables.add(SlotRecord(slot, type, isVar)) contextVariablesToIndex[valueDeclaration] = index return index } @@ -92,7 +94,7 @@ internal class VariableManager(val functionGenerationContext: FunctionGeneration val slot = functionGenerationContext.alloca( type, "p-${valueDeclaration.name.asString()}", variableLocation) val isObject = functionGenerationContext.isObjectType(type) - variables.add(ParameterRecord(slot, isObject)) + variables.add(ParameterRecord(slot, type)) contextVariablesToIndex[valueDeclaration] = index if (isObject) skipSlots++ @@ -114,7 +116,7 @@ internal class VariableManager(val functionGenerationContext: FunctionGeneration val slot = functionGenerationContext.alloca(type, variableLocation = null) if (value != null) functionGenerationContext.storeAny(value, slot, true) - variables.add(SlotRecord(slot, functionGenerationContext.isObjectType(type), true)) + variables.add(SlotRecord(slot, type, true)) return index } diff --git a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/objcexport/BlockPointerSupport.kt b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/objcexport/BlockPointerSupport.kt index a0b1aa5bbbb..cee152a52dc 100644 --- a/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/objcexport/BlockPointerSupport.kt +++ b/kotlin-native/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/llvm/objcexport/BlockPointerSupport.kt @@ -41,7 +41,7 @@ internal fun ObjCExportCodeGeneratorBase.generateBlockToKotlinFunctionConverter( val thisRef = param(0) val associatedObjectHolder = if (useSeparateHolder) { val bodyPtr = bitcast(pointerType(bodyType), thisRef) - loadSlot(structGep(bodyPtr, 1), isVar = false) + loadSlot(codegen.kObjHeaderPtr, structGep(bodyPtr, 1), isVar = false) } else { thisRef } diff --git a/kotlin-native/backend.native/llvm.def b/kotlin-native/backend.native/llvm.def index e10cc2734b6..fb94f9db1d7 100644 --- a/kotlin-native/backend.native/llvm.def +++ b/kotlin-native/backend.native/llvm.def @@ -76,6 +76,8 @@ excludedFunctions.mingw = LLVMDumpType # Functions from LLVMIntPtrType to LLVMModuleCreateWithName are excluded because they work with the GlobalContext. # This might not be safe if the compiler is called from a daemon process. +# +# Also exclude the functions that rely on typed pointers as we get rid of them from the code generator. excludedFunctions = LLVMInitializeAllAsmParsers LLVMInitializeAllAsmPrinters LLVMInitializeAllDisassemblers \ LLVMInitializeAllTargetInfos LLVMInitializeAllTargetMCs LLVMInitializeAllTargets LLVMInitializeNativeTarget \ LLVMInitializeNativeAsmParser LLVMInitializeNativeAsmPrinter LLVMInitializeNativeDisassembler \ @@ -83,6 +85,7 @@ excludedFunctions = LLVMInitializeAllAsmParsers LLVMInitializeAllAsmPrinters LLV LLVMInt16Type LLVMInt32Type LLVMInt64Type LLVMInt128Type LLVMIntType LLVMHalfType LLVMFloatType LLVMDoubleType \ LLVMX86FP80Type LLVMFP128Type LLVMPPCFP128Type LLVMX86MMXType LLVMStructType LLVMVoidType LLVMLabelType \ LLVMMDString LLVMMDNode LLVMConstString LLVMConstStruct LLVMAppendBasicBlock LLVMInsertBasicBlock LLVMCreateBuilder \ - LLVMParseBitcode LLVMParseBitcode2 LLVMGetBitcodeModule LLVMGetBitcodeModule2 LLVMGetGlobalContext LLVMModuleCreateWithName + LLVMParseBitcode LLVMParseBitcode2 LLVMGetBitcodeModule LLVMGetBitcodeModule2 LLVMGetGlobalContext LLVMModuleCreateWithName \ + LLVMBuildLoad strictEnums = LLVMIntPredicate LLVMOpcode LLVMDLLStorageClass LLVMCallConv LLVMThreadLocalMode LLVMAtomicOrdering