backend: refactor ConstValue
also improve other code
This commit is contained in:
committed by
SvyatoslavScherbina
parent
e0dfd312e4
commit
e28a9c71a8
+8
-9
@@ -21,7 +21,7 @@ internal class CodeGenerator(override val context: Context) : ContextUtils {
|
||||
if (currentFunction == descriptor) return
|
||||
variableIndex = 0
|
||||
currentFunction = declaration.descriptor
|
||||
val fn = declaration.descriptor.llvmFunction.getLlvmValue()
|
||||
val fn = declaration.descriptor.llvmFunction
|
||||
prologueBb = LLVMAppendBasicBlock(fn, "prologue")
|
||||
entryBb = LLVMAppendBasicBlock(fn, "entry")
|
||||
positionAtEnd(entryBb!!)
|
||||
@@ -122,20 +122,19 @@ internal class CodeGenerator(override val context: Context) : ContextUtils {
|
||||
|
||||
/* to class descriptor */
|
||||
fun classType(descriptor: ClassDescriptor): LLVMTypeRef = LLVMGetTypeByName(context.llvmModule, descriptor.symbolName)!!
|
||||
fun typeInfoType(descriptor: ClassDescriptor): LLVMTypeRef = descriptor.llvmTypeInfoPtr.getLlvmType()
|
||||
fun typeInfoValue(descriptor: ClassDescriptor): LLVMValueRef = descriptor.llvmTypeInfoPtr.getLlvmValue()!!
|
||||
fun typeInfoValue(descriptor: ClassDescriptor): LLVMValueRef = descriptor.llvmTypeInfoPtr
|
||||
|
||||
fun param(fn: FunctionDescriptor, i: Int): LLVMValueRef {
|
||||
assert (i >= 0 && i < countParams(fn))
|
||||
return LLVMGetParam(fn.llvmFunction.getLlvmValue(), i)!!
|
||||
return LLVMGetParam(fn.llvmFunction, i)!!
|
||||
}
|
||||
fun countParams(fn: FunctionDescriptor) = LLVMCountParams(fn.llvmFunction.getLlvmValue())
|
||||
fun countParams(fn: FunctionDescriptor) = LLVMCountParams(fn.llvmFunction)
|
||||
|
||||
fun indexInClass(p:PropertyDescriptor):Int = (p.containingDeclaration as ClassDescriptor).fields.indexOf(p)
|
||||
|
||||
|
||||
fun basicBlock(name: String = "label_"): LLVMBasicBlockRef =
|
||||
LLVMAppendBasicBlock(currentFunction!!.llvmFunction.getLlvmValue(), name)!!
|
||||
LLVMAppendBasicBlock(currentFunction!!.llvmFunction, name)!!
|
||||
|
||||
fun basicBlock(name: String, code: () -> Unit) = basicBlock(name).apply {
|
||||
appendingTo(this) {
|
||||
@@ -143,10 +142,10 @@ internal class CodeGenerator(override val context: Context) : ContextUtils {
|
||||
}
|
||||
}
|
||||
|
||||
fun lastBasicBlock(): LLVMBasicBlockRef? = LLVMGetLastBasicBlock(currentFunction!!.llvmFunction.getLlvmValue())
|
||||
fun lastBasicBlock(): LLVMBasicBlockRef? = LLVMGetLastBasicBlock(currentFunction!!.llvmFunction)
|
||||
|
||||
fun functionLlvmValue(descriptor: FunctionDescriptor) = descriptor.llvmFunction.getLlvmValue()!!
|
||||
fun functionHash(descriptor: FunctionDescriptor): LLVMValueRef = descriptor.functionName.localHash.getLlvmValue()!!
|
||||
fun functionLlvmValue(descriptor: FunctionDescriptor) = descriptor.llvmFunction
|
||||
fun functionHash(descriptor: FunctionDescriptor): LLVMValueRef = descriptor.functionName.localHash.llvm
|
||||
|
||||
fun br(bbLabel: LLVMBasicBlockRef): LLVMValueRef {
|
||||
val res = LLVMBuildBr(builder, bbLabel)!!
|
||||
|
||||
+11
-7
@@ -56,15 +56,16 @@ internal interface ContextUtils {
|
||||
* LLVM function generated from the Kotlin function.
|
||||
* It may be declared as external function prototype.
|
||||
*/
|
||||
val FunctionDescriptor.llvmFunction: ConstValue
|
||||
val FunctionDescriptor.llvmFunction: LLVMValueRef
|
||||
get() {
|
||||
assert (this.kind.isReal)
|
||||
val globalName = this.symbolName
|
||||
val module = context.llvmModule
|
||||
|
||||
val functionType = getLlvmFunctionType(this)
|
||||
val function = LLVMGetNamedFunction(module, globalName) ?: LLVMAddFunction(module, globalName, functionType)
|
||||
return constValue(function)
|
||||
|
||||
return LLVMGetNamedFunction(module, globalName) ?:
|
||||
LLVMAddFunction(module, globalName, functionType)!!
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -72,7 +73,7 @@ internal interface ContextUtils {
|
||||
*/
|
||||
val FunctionDescriptor.entryPointAddress: ConstValue
|
||||
get() {
|
||||
val result = LLVMConstBitCast(this.llvmFunction.getLlvmValue(), pointerType(LLVMInt8Type()))
|
||||
val result = LLVMConstBitCast(this.llvmFunction, int8TypePtr)!!
|
||||
return constValue(result)
|
||||
}
|
||||
|
||||
@@ -80,16 +81,19 @@ internal interface ContextUtils {
|
||||
* Pointer to type info for given class.
|
||||
* It may be declared as pointer to external variable.
|
||||
*/
|
||||
val ClassDescriptor.llvmTypeInfoPtr: ConstPointer
|
||||
val ClassDescriptor.llvmTypeInfoPtr: LLVMValueRef
|
||||
get() {
|
||||
val module = context.llvmModule
|
||||
val globalName = this.typeInfoSymbolName
|
||||
val globalPtr = LLVMGetNamedGlobal(module, globalName) ?:
|
||||
LLVMAddGlobal(module, runtime.typeInfoType, globalName)
|
||||
LLVMAddGlobal(module, runtime.typeInfoType, globalName)!!
|
||||
|
||||
return constPointer(globalPtr)
|
||||
return globalPtr
|
||||
}
|
||||
|
||||
val ClassDescriptor.typeInfoPtr: ConstPointer
|
||||
get() = constPointer(this.llvmTypeInfoPtr)
|
||||
|
||||
/**
|
||||
* Returns contents of this [GlobalHash].
|
||||
*
|
||||
|
||||
+8
-8
@@ -470,7 +470,7 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
|
||||
return paramDescriptors.mapIndexed { i, paramDescriptor ->
|
||||
val param = codegen.param(descriptor, i)
|
||||
assert(codegen.getLLVMType(paramDescriptor.type) == LLVMTypeOf(param))
|
||||
assert(codegen.getLLVMType(paramDescriptor.type) == param.type)
|
||||
paramDescriptor to param
|
||||
}.toMap()
|
||||
}
|
||||
@@ -694,11 +694,11 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
//-------------------------------------------------------------------------//
|
||||
|
||||
private fun evaluateVararg(tmpVariableName: String, value: IrVararg): LLVMValueRef? {
|
||||
val arrayCreationArgs = listOf(codegen.kTheArrayTypeInfo!!, kImmInt32One!!, Int32(value.elements.size).getLlvmValue()!!)
|
||||
val arrayCreationArgs = listOf(codegen.kTheArrayTypeInfo, kImmInt32One, Int32(value.elements.size).llvm)
|
||||
val array = currentCodeContext.genCall(context.allocArrayFunction, arrayCreationArgs, tmpVariableName)
|
||||
value.elements.forEachIndexed { i, it ->
|
||||
val elementValueRaw = evaluateExpression(codegen.newVar(), it)
|
||||
currentCodeContext.genCall(context.setArrayFunction, listOf(array!!, Int32(i).getLlvmValue()!!, elementValueRaw!!), "")
|
||||
currentCodeContext.genCall(context.setArrayFunction, listOf(array, Int32(i).llvm, elementValueRaw!!), "")
|
||||
return@forEachIndexed
|
||||
}
|
||||
return array
|
||||
@@ -1316,7 +1316,7 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
IrConstKind.Int -> return LLVMConstInt(LLVMInt32Type(), (value.value as Int).toLong(), 1)
|
||||
IrConstKind.Long -> return LLVMConstInt(LLVMInt64Type(), value.value as Long, 1)
|
||||
IrConstKind.String ->
|
||||
return context.staticData.kotlinStringLiteral(value as IrConst<String>).getLlvmValue()
|
||||
return context.staticData.kotlinStringLiteral(value as IrConst<String>).llvm
|
||||
IrConstKind.Float -> return LLVMConstRealOfString(LLVMFloatType(), (value.value as Float).toString())
|
||||
IrConstKind.Double -> return LLVMConstRealOfString(LLVMDoubleType(), (value.value as Double).toString())
|
||||
}
|
||||
@@ -1464,9 +1464,9 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
memScoped {
|
||||
val containingClass = (callee.descriptor as ClassConstructorDescriptor).containingDeclaration
|
||||
val typeInfo = codegen.typeInfoValue(containingClass)
|
||||
val allocHint = Int32(1).getLlvmValue()!!
|
||||
val allocHint = Int32(1).llvm
|
||||
val thisValue = if (containingClass.isArray) {
|
||||
assert(args.size == 1 && LLVMTypeOf(args[0]) == LLVMInt32Type())
|
||||
assert(args.size == 1 && args[0].type == int32Type)
|
||||
val allocArrayInstanceArgs = listOf(typeInfo, allocHint, args[0])
|
||||
currentCodeContext.genCall(context.allocArrayFunction, allocArrayInstanceArgs, variableName)
|
||||
} else {
|
||||
@@ -1670,7 +1670,7 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
val thisPtr = currentCodeContext.genGetValue(constructedClass.thisAsReceiverParameter)
|
||||
|
||||
val thisPtrArgType = codegen.getLLVMType(descriptor.allValueParameters[0].type)
|
||||
val thisPtrArg = if (LLVMTypeOf(thisPtr) == thisPtrArgType) {
|
||||
val thisPtrArg = if (thisPtr.type == thisPtrArgType) {
|
||||
thisPtr
|
||||
} else {
|
||||
// e.g. when array constructor calls super (i.e. Any) constructor.
|
||||
@@ -1703,7 +1703,7 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
|
||||
memScoped {
|
||||
val arrayLength = args.size
|
||||
val argsCasted = args.map{it -> constPointer(LLVMConstBitCast(it, int8TypePtr)) }
|
||||
val argsCasted = args.map { it -> constPointer(it).bitcast(int8TypePtr) }
|
||||
val llvmUsedGlobal =
|
||||
context.staticData.placeGlobalArray("llvm.used", int8TypePtr, argsCasted)
|
||||
|
||||
|
||||
+56
-54
@@ -5,51 +5,51 @@ import llvm.*
|
||||
import org.jetbrains.kotlin.backend.konan.allValueParameters
|
||||
import org.jetbrains.kotlin.descriptors.FunctionDescriptor
|
||||
|
||||
internal val LLVMValueRef.type: LLVMTypeRef
|
||||
get() = LLVMTypeOf(this)!!
|
||||
|
||||
/**
|
||||
* Represents the value which can be emitted as bitcode const value
|
||||
*/
|
||||
internal interface ConstValue {
|
||||
|
||||
fun getLlvmValue(): LLVMValueRef?
|
||||
|
||||
fun getLlvmType(): LLVMTypeRef {
|
||||
return LLVMTypeOf(getLlvmValue())!!
|
||||
}
|
||||
|
||||
val llvm: LLVMValueRef
|
||||
}
|
||||
|
||||
internal val ConstValue.llvmType: LLVMTypeRef
|
||||
get() = this.llvm.type
|
||||
|
||||
internal interface ConstPointer : ConstValue {
|
||||
fun getElementPtr(index: Int): ConstPointer = ConstGetElementPtr(this, index)
|
||||
}
|
||||
|
||||
internal fun constPointer(value: LLVMValueRef?) = object : ConstPointer {
|
||||
override fun getLlvmValue() = value
|
||||
internal fun constPointer(value: LLVMValueRef) = object : ConstPointer {
|
||||
|
||||
init {
|
||||
assert (LLVMIsConstant(value) == 1)
|
||||
}
|
||||
|
||||
override val llvm = value
|
||||
}
|
||||
|
||||
private class ConstGetElementPtr(val pointer: ConstPointer, val index: Int) : ConstPointer {
|
||||
override fun getLlvmValue(): LLVMValueRef? {
|
||||
// TODO: probably it should be computed once when initialized?
|
||||
override val llvm = memScoped {
|
||||
// TODO: squash multiple GEPs
|
||||
val indices = intArrayOf(0, index).map { Int32(it).getLlvmValue() }
|
||||
memScoped {
|
||||
val indicesArray = allocArrayOf(indices)
|
||||
return LLVMConstInBoundsGEP(pointer.getLlvmValue(), indicesArray[0].ptr, indices.size)
|
||||
}
|
||||
val indices = intArrayOf(0, index).map { Int32(it).llvm }
|
||||
val indicesArray = allocArrayOf(indices)
|
||||
LLVMConstInBoundsGEP(pointer.llvm, indicesArray[0].ptr, indices.size)!!
|
||||
}
|
||||
}
|
||||
|
||||
internal fun ConstPointer.bitcast(toType: LLVMTypeRef) = constPointer(LLVMConstBitCast(this.getLlvmValue(), toType))
|
||||
internal fun ConstPointer.bitcast(toType: LLVMTypeRef) = constPointer(LLVMConstBitCast(this.llvm, toType)!!)
|
||||
|
||||
internal class ConstArray(val elemType: LLVMTypeRef?, val elements: List<ConstValue>) : ConstValue {
|
||||
|
||||
override fun getLlvmValue(): LLVMValueRef? {
|
||||
val values = elements.map { it.getLlvmValue() }.toTypedArray()
|
||||
override val llvm = memScoped {
|
||||
val values = elements.map { it.llvm }.toTypedArray()
|
||||
|
||||
memScoped {
|
||||
val valuesNativeArrayPtr = allocArrayOf(*values)[0].ptr
|
||||
|
||||
return LLVMConstArray(elemType, valuesNativeArrayPtr, values.size)
|
||||
}
|
||||
val valuesNativeArrayPtr = allocArrayOf(*values)[0].ptr
|
||||
LLVMConstArray(elemType, valuesNativeArrayPtr, values.size)!!
|
||||
}
|
||||
}
|
||||
|
||||
@@ -57,49 +57,51 @@ internal open class Struct(val type: LLVMTypeRef?, val elements: List<ConstValue
|
||||
|
||||
constructor(type: LLVMTypeRef?, vararg elements: ConstValue) : this(type, elements.toList())
|
||||
|
||||
override fun getLlvmValue(): LLVMValueRef? {
|
||||
val values = elements.map { it.getLlvmValue() }.toTypedArray()
|
||||
memScoped {
|
||||
val valuesNativeArrayPtr = allocArrayOf(*values)[0].ptr
|
||||
return LLVMConstNamedStruct(type, valuesNativeArrayPtr, values.size)
|
||||
}
|
||||
override val llvm = memScoped {
|
||||
val values = elements.map { it.llvm }.toTypedArray()
|
||||
val valuesNativeArrayPtr = allocArrayOf(*values)[0].ptr
|
||||
LLVMConstNamedStruct(type, valuesNativeArrayPtr, values.size)!!
|
||||
}
|
||||
}
|
||||
|
||||
internal class Int8(val value: Byte) : ConstValue {
|
||||
override fun getLlvmValue() = LLVMConstInt(LLVMInt8Type(), value.toLong(), 1)
|
||||
override val llvm = LLVMConstInt(LLVMInt8Type(), value.toLong(), 1)!!
|
||||
}
|
||||
|
||||
internal class Int32(val value: Int) : ConstValue {
|
||||
override fun getLlvmValue() = LLVMConstInt(LLVMInt32Type(), value.toLong(), 1)
|
||||
override val llvm = LLVMConstInt(LLVMInt32Type(), value.toLong(), 1)!!
|
||||
}
|
||||
|
||||
internal class Int64(val value: Long) : ConstValue {
|
||||
override fun getLlvmValue() = LLVMConstInt(LLVMInt64Type(), value, 1)
|
||||
override val llvm = LLVMConstInt(LLVMInt64Type(), value, 1)!!
|
||||
}
|
||||
|
||||
internal class Zero(val type: LLVMTypeRef?) : ConstValue {
|
||||
override fun getLlvmValue() = LLVMConstNull(type)
|
||||
internal class Zero(val type: LLVMTypeRef) : ConstValue {
|
||||
override val llvm = LLVMConstNull(type)!!
|
||||
}
|
||||
|
||||
internal class NullPointer(val pointeeType: LLVMTypeRef?): ConstPointer {
|
||||
override fun getLlvmValue() = LLVMConstNull(pointerType(pointeeType))
|
||||
internal class NullPointer(val pointeeType: LLVMTypeRef): ConstPointer {
|
||||
override val llvm = LLVMConstNull(pointerType(pointeeType))!!
|
||||
}
|
||||
|
||||
internal fun constValue(value: LLVMValueRef?) = object : ConstValue {
|
||||
override fun getLlvmValue() = value
|
||||
internal fun constValue(value: LLVMValueRef) = object : ConstValue {
|
||||
init {
|
||||
assert (LLVMIsConstant(value) == 1)
|
||||
}
|
||||
|
||||
override val llvm = value
|
||||
}
|
||||
|
||||
internal val int8Type = LLVMInt8Type()!!
|
||||
internal val int32Type = LLVMInt32Type()!!
|
||||
internal val int8TypePtr = pointerType(int8Type)
|
||||
|
||||
internal val voidType = LLVMVoidType()
|
||||
internal val voidType = LLVMVoidType()!!
|
||||
|
||||
internal val ContextUtils.kTheAnyTypeInfo: LLVMValueRef?
|
||||
get() = KonanPlatform.builtIns.any.llvmTypeInfoPtr.getLlvmValue()
|
||||
internal val ContextUtils.kTheArrayTypeInfo: LLVMValueRef?
|
||||
get() = KonanPlatform.builtIns.array.llvmTypeInfoPtr.getLlvmValue()
|
||||
internal val ContextUtils.kTheAnyTypeInfo: LLVMValueRef
|
||||
get() = KonanPlatform.builtIns.any.llvmTypeInfoPtr
|
||||
internal val ContextUtils.kTheArrayTypeInfo: LLVMValueRef
|
||||
get() = KonanPlatform.builtIns.array.llvmTypeInfoPtr
|
||||
internal val ContextUtils.kTypeInfo: LLVMTypeRef
|
||||
get() = LLVMGetTypeByName(context.llvmModule, "struct.TypeInfo")!!
|
||||
internal val ContextUtils.kObjHeader: LLVMTypeRef
|
||||
@@ -114,30 +116,30 @@ internal val ContextUtils.kArrayHeaderPtr: LLVMTypeRef
|
||||
get() = pointerType(kArrayHeader)
|
||||
internal val ContextUtils.kTypeInfoPtr: LLVMTypeRef
|
||||
get() = pointerType(kTypeInfo)
|
||||
internal val kInt1 = LLVMInt1Type()
|
||||
internal val kInt8Ptr = pointerType(LLVMInt8Type())
|
||||
internal val kInt1 = LLVMInt1Type()!!
|
||||
internal val kInt8Ptr = pointerType(int8Type)
|
||||
internal val kInt8PtrPtr = pointerType(kInt8Ptr)
|
||||
internal val kImmInt32One = Int32(1).getLlvmValue()
|
||||
internal val kImmInt32One = Int32(1).llvm
|
||||
internal val ContextUtils.kNullObjHeaderPtr: LLVMValueRef
|
||||
get() = LLVMConstNull(this.kObjHeaderPtr)!!
|
||||
internal val ContextUtils.kNullArrayHeaderPtr: LLVMValueRef
|
||||
get() = LLVMConstNull(this.kArrayHeaderPtr)!!
|
||||
|
||||
|
||||
internal fun pointerType(pointeeType: LLVMTypeRef?) = LLVMPointerType(pointeeType, 0)!!
|
||||
internal fun pointerType(pointeeType: LLVMTypeRef) = LLVMPointerType(pointeeType, 0)!!
|
||||
|
||||
internal fun structType(vararg types: LLVMTypeRef?): LLVMTypeRef = memScoped {
|
||||
internal fun structType(vararg types: LLVMTypeRef): LLVMTypeRef = memScoped {
|
||||
LLVMStructType(allocArrayOf(*types)[0].ptr, types.size, 0)!!
|
||||
}
|
||||
|
||||
internal fun ContextUtils.getLlvmFunctionType(function: FunctionDescriptor): LLVMTypeRef? {
|
||||
internal fun ContextUtils.getLlvmFunctionType(function: FunctionDescriptor): LLVMTypeRef {
|
||||
val returnType = getLLVMType(function.returnType!!)
|
||||
val params = function.allValueParameters
|
||||
val paramTypes = params.map { getLLVMType(it.type) }
|
||||
|
||||
memScoped {
|
||||
val paramTypesPtr = allocArrayOf(paramTypes)[0].ptr
|
||||
return LLVMFunctionType(returnType, paramTypesPtr, paramTypes.size, 0)
|
||||
return LLVMFunctionType(returnType, paramTypesPtr, paramTypes.size, 0)!!
|
||||
}
|
||||
}
|
||||
|
||||
@@ -147,12 +149,12 @@ internal fun ContextUtils.getLlvmFunctionType(function: FunctionDescriptor): LLV
|
||||
internal fun CArray<CInt8Var>.getBytes(size: Long) =
|
||||
(0 .. size-1).map { this[it].value }.toByteArray()
|
||||
|
||||
internal fun getFunctionType(ptrToFunction: LLVMValueRef?): LLVMTypeRef {
|
||||
internal fun getFunctionType(ptrToFunction: LLVMValueRef): LLVMTypeRef {
|
||||
return getGlobalType(ptrToFunction)
|
||||
}
|
||||
|
||||
internal fun getGlobalType(ptrToGlobal: LLVMValueRef?): LLVMTypeRef {
|
||||
return LLVMGetElementType(LLVMTypeOf(ptrToGlobal))!!
|
||||
internal fun getGlobalType(ptrToGlobal: LLVMValueRef): LLVMTypeRef {
|
||||
return LLVMGetElementType(ptrToGlobal.type)!!
|
||||
}
|
||||
|
||||
internal fun ContextUtils.externalFunction(name: String, type: LLVMTypeRef): LLVMValueRef {
|
||||
@@ -175,7 +177,7 @@ internal fun ContextUtils.externalGlobal(name: String, type: LLVMTypeRef): LLVMV
|
||||
}
|
||||
}
|
||||
|
||||
internal fun functionType(returnType: LLVMTypeRef?, isVarArg: Boolean = false, vararg paramTypes: LLVMTypeRef?) =
|
||||
internal fun functionType(returnType: LLVMTypeRef, isVarArg: Boolean = false, vararg paramTypes: LLVMTypeRef) =
|
||||
memScoped {
|
||||
val paramTypesPtr = allocArrayOf(*paramTypes)[0].ptr
|
||||
LLVMFunctionType(returnType, paramTypesPtr, paramTypes.size, if (isVarArg) 1 else 0)!!
|
||||
|
||||
+1
-1
@@ -21,7 +21,7 @@ internal class Logger(val generator: CodeGenerator, override val context: Contex
|
||||
fun logIr() {
|
||||
val function = generator.currentFunction ?: return
|
||||
|
||||
val irFunctionDeclaration = LLVMPrintValueToString(function.llvmFunction.getLlvmValue())!!.asCString().toString()
|
||||
val irFunctionDeclaration = LLVMPrintValueToString(function.llvmFunction)!!.asCString().toString()
|
||||
irFunctionDeclaration.lines().forEach { println(" $it") }
|
||||
}
|
||||
|
||||
|
||||
+11
-16
@@ -18,20 +18,15 @@ import java.io.*
|
||||
fun readModuleMetadata(file: File): String {
|
||||
|
||||
val reader = MetadataReader(file)
|
||||
var metadataString: String? = null
|
||||
|
||||
try {
|
||||
reader.use {
|
||||
val metadataNode = reader.namedMetadataNode("kmetadata", 0);
|
||||
val stringNode = reader.metadataOperand(metadataNode, 0)!!
|
||||
metadataString = reader.string(stringNode)
|
||||
} finally {
|
||||
reader.close()
|
||||
val stringNode = reader.metadataOperand(metadataNode, 0)
|
||||
return reader.string(stringNode)
|
||||
}
|
||||
|
||||
return metadataString!!
|
||||
}
|
||||
|
||||
class MetadataReader(file: File) {
|
||||
class MetadataReader(file: File) : Closeable {
|
||||
|
||||
lateinit var llvmModule: LLVMModuleRef
|
||||
lateinit var llvmContext: LLVMContextRef
|
||||
@@ -69,10 +64,10 @@ class MetadataReader(file: File) {
|
||||
|
||||
fun namedMetadataNode(name: String, index: Int): LLVMValueRef {
|
||||
memScoped {
|
||||
val nodeCount = LLVMGetNamedMetadataNumOperands(llvmModule, "kmetadata")!!
|
||||
val nodeCount = LLVMGetNamedMetadataNumOperands(llvmModule, "kmetadata")
|
||||
val nodeArray = allocArray<LLVMValueRefVar>(nodeCount)
|
||||
|
||||
LLVMGetNamedMetadataOperands(llvmModule, "kmetadata", nodeArray[0].ptr)!!
|
||||
LLVMGetNamedMetadataOperands(llvmModule, "kmetadata", nodeArray[0].ptr)
|
||||
|
||||
return nodeArray[0].value!!
|
||||
}
|
||||
@@ -80,16 +75,16 @@ class MetadataReader(file: File) {
|
||||
|
||||
fun metadataOperand(metadataNode: LLVMValueRef, index: Int): LLVMValueRef {
|
||||
memScoped {
|
||||
val operandCount = LLVMGetMDNodeNumOperands(metadataNode)!!
|
||||
val operandCount = LLVMGetMDNodeNumOperands(metadataNode)
|
||||
val operandArray = allocArray<LLVMValueRefVar>(operandCount)
|
||||
|
||||
LLVMGetMDNodeOperands(metadataNode, operandArray[0].ptr)!!
|
||||
LLVMGetMDNodeOperands(metadataNode, operandArray[0].ptr)
|
||||
|
||||
return operandArray[0].value!!
|
||||
}
|
||||
}
|
||||
|
||||
fun close() {
|
||||
override fun close() {
|
||||
LLVMDisposeModule(llvmModule)
|
||||
LLVMContextDispose(llvmContext)
|
||||
}
|
||||
@@ -155,7 +150,7 @@ internal class MetadataGenerator(override val context: Context): ContextUtils {
|
||||
}
|
||||
|
||||
internal fun function(declaration: IrFunction) {
|
||||
val fn = declaration.descriptor.llvmFunction.getLlvmValue()
|
||||
val fn = declaration.descriptor.llvmFunction
|
||||
|
||||
val proto = serializeFunSignature(declaration)
|
||||
|
||||
@@ -165,7 +160,7 @@ internal class MetadataGenerator(override val context: Context): ContextUtils {
|
||||
|
||||
// Quick check consistency
|
||||
private fun debug_blob(blob: String) {
|
||||
var metadataList = mutableListOf<KotlinKonanMetadata>()
|
||||
val metadataList = mutableListOf<KotlinKonanMetadata>()
|
||||
KotlinKonanMetadataUtils.parseMetadata(blob, metadataList)
|
||||
|
||||
val body = metadataList.first().body
|
||||
|
||||
+4
-4
@@ -151,9 +151,9 @@ internal class RTTIGenerator(override val context: Context) : ContextUtils {
|
||||
|
||||
val superTypeOrAny = classDesc.getSuperClassOrAny()
|
||||
val superType = if (KotlinBuiltIns.isAny(classDesc)) NullPointer(runtime.typeInfoType)
|
||||
else superTypeOrAny.llvmTypeInfoPtr
|
||||
else superTypeOrAny.typeInfoPtr
|
||||
|
||||
val interfaces = classDesc.implementedInterfaces.map { it.llvmTypeInfoPtr }
|
||||
val interfaces = classDesc.implementedInterfaces.map { it.typeInfoPtr }
|
||||
val interfacesPtr = staticData.placeGlobalConstArray("kintf:$className",
|
||||
pointerType(runtime.typeInfoType), interfaces)
|
||||
|
||||
@@ -212,8 +212,8 @@ internal class RTTIGenerator(override val context: Context) : ContextUtils {
|
||||
methodsPtr, methods.size,
|
||||
fieldsPtr, if (classDesc.isInterface) -1 else fields.size)
|
||||
|
||||
val typeInfoGlobal = classDesc.llvmTypeInfoPtr.getLlvmValue() // TODO: it is a hack
|
||||
LLVMSetInitializer(typeInfoGlobal, typeInfo.getLlvmValue())
|
||||
val typeInfoGlobal = classDesc.llvmTypeInfoPtr // TODO: it is a hack
|
||||
LLVMSetInitializer(typeInfoGlobal, typeInfo.llvm)
|
||||
LLVMSetGlobalConstant(typeInfoGlobal, 1)
|
||||
|
||||
exportTypeInfoIfRequired(classDesc, typeInfoGlobal)
|
||||
|
||||
+3
-3
@@ -25,7 +25,7 @@ internal class StaticData(override val context: Context): ContextUtils {
|
||||
}
|
||||
|
||||
fun setInitializer(value: ConstValue) {
|
||||
LLVMSetInitializer(llvmGlobal, value.getLlvmValue())
|
||||
LLVMSetInitializer(llvmGlobal, value.llvm)
|
||||
}
|
||||
|
||||
fun setConstant(value: Boolean) {
|
||||
@@ -51,7 +51,7 @@ internal class StaticData(override val context: Context): ContextUtils {
|
||||
|
||||
private fun getElementOffset(index: Int): Long {
|
||||
val llvmTargetData = global.staticData.llvmTargetData
|
||||
val type = LLVMGetElementType(delegate.getLlvmType())
|
||||
val type = LLVMGetElementType(delegate.llvmType)
|
||||
return when (LLVMGetTypeKind(type)) {
|
||||
LLVMTypeKind.LLVMStructTypeKind -> LLVMOffsetOfElement(llvmTargetData, type, index)
|
||||
LLVMTypeKind.LLVMArrayTypeKind -> LLVMABISizeOfType(llvmTargetData, LLVMGetElementType(type)) * index
|
||||
@@ -95,7 +95,7 @@ internal class StaticData(override val context: Context): ContextUtils {
|
||||
* Creates [Global] with given name and value.
|
||||
*/
|
||||
fun placeGlobal(name: String, initializer: ConstValue): Global {
|
||||
val global = createGlobal(initializer.getLlvmType(), name)
|
||||
val global = createGlobal(initializer.llvmType, name)
|
||||
global.setInitializer(initializer)
|
||||
return global
|
||||
}
|
||||
|
||||
+3
-3
@@ -10,9 +10,9 @@ import llvm.*
|
||||
* If [elements] is empty, then null pointer is returned.
|
||||
*/
|
||||
internal fun StaticData.placeGlobalConstArray(name: String,
|
||||
elemType: LLVMTypeRef?,
|
||||
elemType: LLVMTypeRef,
|
||||
elements: List<ConstValue>): ConstPointer {
|
||||
if (elements.size > 0) {
|
||||
if (elements.isNotEmpty()) {
|
||||
val global = this.placeGlobalArray(name, elemType, elements)
|
||||
global.setConstant(true)
|
||||
return global.pointer.getElementPtr(0)
|
||||
@@ -22,6 +22,6 @@ internal fun StaticData.placeGlobalConstArray(name: String,
|
||||
}
|
||||
|
||||
internal fun StaticData.createAlias(name: String, aliasee: ConstPointer): ConstPointer {
|
||||
val alias = LLVMAddAlias(context.llvmModule, aliasee.getLlvmType(), aliasee.getLlvmValue(), name)!!
|
||||
val alias = LLVMAddAlias(context.llvmModule, aliasee.llvmType, aliasee.llvm, name)!!
|
||||
return constPointer(alias)
|
||||
}
|
||||
|
||||
+2
-2
@@ -42,7 +42,7 @@ internal fun StaticData.createKotlinStringLiteral(value: IrConst<String>): Const
|
||||
|
||||
val stringClass = value.type.constructor.declarationDescriptor as ClassDescriptor
|
||||
assert (stringClass.fqNameSafe.asString() == "kotlin.String")
|
||||
val arrayHeader = arrayHeader(containerOffsetNegative, stringClass.llvmTypeInfoPtr, arrayCount)
|
||||
val arrayHeader = arrayHeader(containerOffsetNegative, stringClass.typeInfoPtr, arrayCount)
|
||||
|
||||
val array = ConstArray(int8Type, valueBytes.map { Int8(it) } )
|
||||
|
||||
@@ -50,7 +50,7 @@ internal fun StaticData.createKotlinStringLiteral(value: IrConst<String>): Const
|
||||
|
||||
val stringRef = objHeaderPtr.bitcast(getLLVMType(value.type))
|
||||
val res = createAlias("kstr:$base64Str", stringRef)
|
||||
LLVMSetLinkage(res.getLlvmValue(), LLVMLinkage.LLVMWeakAnyLinkage)
|
||||
LLVMSetLinkage(res.llvm, LLVMLinkage.LLVMWeakAnyLinkage)
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user