CODEGEN: get_object implementation
This commit is contained in:
committed by
vvlevchenko
parent
efdb896d2c
commit
bab2b8bc3f
+6
@@ -60,11 +60,15 @@ internal class CodeGenerator(override val context: Context) : ContextUtils {
|
||||
fun icmpLe(arg0: LLVMValueRef, arg1: LLVMValueRef, result: String): LLVMValueRef = LLVMBuildICmp(builder, LLVMIntPredicate.LLVMIntSLE, arg0, arg1, result)!!
|
||||
fun icmpNe(arg0: LLVMValueRef, arg1: LLVMValueRef, result: String): LLVMValueRef = LLVMBuildICmp(builder, LLVMIntPredicate.LLVMIntNE, arg0, arg1, result)!!
|
||||
|
||||
fun ucmpGt(arg0: LLVMValueRef, arg1: LLVMValueRef, result: String): LLVMValueRef = LLVMBuildICmp(builder, LLVMIntPredicate.LLVMIntUGT, arg0, arg1, result)!!
|
||||
|
||||
/* floating-point comparisons */
|
||||
fun fcmpEq(arg0: LLVMValueRef, arg1: LLVMValueRef, result: String): LLVMValueRef = LLVMBuildFCmp(builder, LLVMRealPredicate.LLVMRealOEQ, arg0, arg1, result)!!
|
||||
|
||||
fun bitcast(type: LLVMTypeRef?, value: LLVMValueRef, result: String) = LLVMBuildBitCast(builder, value, type, result)!!
|
||||
|
||||
fun intToPtr(imm: LLVMValueRef?, DestTy: LLVMTypeRef, Name: String) = LLVMBuildIntToPtr(builder, imm, DestTy, Name)
|
||||
|
||||
fun alloca(type: KotlinType, varName: String): LLVMValueRef = alloca( getLLVMType(type), varName)
|
||||
fun alloca(type: LLVMTypeRef?, varName: String): LLVMValueRef {
|
||||
appendingTo(prologueBb!!) {
|
||||
@@ -256,6 +260,8 @@ internal class CodeGenerator(override val context: Context) : ContextUtils {
|
||||
code()
|
||||
}
|
||||
|
||||
fun llvmFunction(function: FunctionDescriptor): LLVMValueRef = function.llvmFunction
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
+1
@@ -23,6 +23,7 @@ internal class Context(val irModule: IrModuleFragment, val runtime: Runtime, val
|
||||
private fun importRtFunction(name: String) = importFunction(name, runtime.llvmModule)
|
||||
|
||||
val allocInstanceFunction = importRtFunction("AllocInstance")
|
||||
val initInstanceFunction = importRtFunction("InitInstance")
|
||||
val allocArrayFunction = importRtFunction("AllocArrayInstance")
|
||||
val setArrayFunction = importRtFunction("Kotlin_Array_set")
|
||||
val lookupFieldOffset = importRtFunction("LookupFieldOffset")
|
||||
|
||||
+33
-1
@@ -279,7 +279,7 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
if (!skipConstructorBodyGeneration(constructorDeclaration))
|
||||
constructorDeclaration.acceptChildrenVoid(this)
|
||||
|
||||
if (constructorDescriptor.isPrimary && !DescriptorUtils.isCompanionObject(constructorDescriptor.constructedClass)) {
|
||||
if (constructorDescriptor.isPrimary) {
|
||||
val irOfCurrentClass = context.moduleIndex.classes[classDescriptor.classId]
|
||||
irOfCurrentClass!!.acceptChildrenVoid(object : IrElementVisitorVoid {
|
||||
override fun visitElement(element: IrElement) {
|
||||
@@ -602,6 +602,7 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
is IrVararg -> return evaluateVararg (tmpVariableName, value)
|
||||
is IrBreak -> return evaluateBreak ( value)
|
||||
is IrContinue -> return evaluateContinue ( value)
|
||||
is IrGetObjectValue -> return evaluateGetObjectValue (tmpVariableName, value)
|
||||
null -> return null
|
||||
else -> {
|
||||
TODO("${ir2string(value)}")
|
||||
@@ -609,6 +610,37 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
|
||||
}
|
||||
}
|
||||
|
||||
//-------------------------------------------------------------------------//
|
||||
|
||||
private fun evaluateGetObjectValue(tmpVariableName: String, value: IrGetObjectValue): LLVMValueRef? {
|
||||
val objName = value.descriptor.fqNameSafe.asString()
|
||||
var objectPtr = LLVMGetNamedGlobal(context.llvmModule, objName)
|
||||
if (objectPtr == null) {
|
||||
objectPtr = LLVMAddGlobal(context.llvmModule, codegen.getLLVMType(value.type), objName)
|
||||
LLVMSetInitializer(objectPtr, codegen.kNullObjHeaderPtr)
|
||||
}
|
||||
|
||||
val bbInit = codegen.basicBlock("label_init")
|
||||
val bbExit = codegen.basicBlock("label_continue")
|
||||
val onePtr = codegen.intToPtr(kImmInt64One, codegen.kObjHeaderPtr, codegen.newVar())
|
||||
val objectVal = codegen.load(objectPtr!!, codegen.newVar())
|
||||
val condition = codegen.ucmpGt(objectVal, onePtr!!, codegen.newVar())
|
||||
codegen.condBr(condition, bbExit, bbInit)
|
||||
|
||||
codegen.positionAtEnd(bbInit)
|
||||
val typeInfo = codegen.typeInfoValue(value.descriptor)
|
||||
val allocHint = Int32(1).llvm
|
||||
val initFunction = value.descriptor.constructors.first { it.valueParameters.size == 0 }
|
||||
val ctor = codegen.llvmFunction(initFunction)
|
||||
val args = listOf(objectPtr, typeInfo, allocHint, ctor)
|
||||
currentCodeContext.genCall(context.initInstanceFunction, args, codegen.newVar())
|
||||
codegen.br(bbExit)
|
||||
|
||||
codegen.positionAtEnd(bbExit)
|
||||
return objectVal
|
||||
}
|
||||
//-------------------------------------------------------------------------//
|
||||
|
||||
private fun evaluateExpressionAndJump(expression: IrExpression, destination: ContinuationBlock) {
|
||||
val result = evaluateExpression("res", expression)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user