backend/codegen, runtime: support interop intrinsics and natives

This commit is contained in:
Svyatoslav Scherbina
2017-01-31 13:32:43 +07:00
committed by SvyatoslavScherbina
parent 3892820052
commit 4b694225c1
2 changed files with 45 additions and 4 deletions
@@ -1761,16 +1761,16 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
//-------------------------------------------------------------------------// //-------------------------------------------------------------------------//
private fun evaluateIntrinsicCall(callee: IrCall, args: List<LLVMValueRef>): LLVMValueRef { private fun evaluateIntrinsicCall(callee: IrCall, args: List<LLVMValueRef>): LLVMValueRef {
val descriptor = callee.descriptor val descriptor = callee.descriptor.original
val name = descriptor.fqNameUnsafe.asString() val name = descriptor.fqNameUnsafe.asString()
return when (name) { when (name) {
"konan.internal.areEqualByValue" -> { "konan.internal.areEqualByValue" -> {
val arg0 = args[0] val arg0 = args[0]
val arg1 = args[1] val arg1 = args[1]
assert (arg0.type == arg1.type) assert (arg0.type == arg1.type)
when (LLVMGetTypeKind(arg0.type)) { return when (LLVMGetTypeKind(arg0.type)) {
LLVMTypeKind.LLVMFloatTypeKind, LLVMTypeKind.LLVMDoubleTypeKind -> LLVMTypeKind.LLVMFloatTypeKind, LLVMTypeKind.LLVMDoubleTypeKind ->
codegen.fcmpEq(arg0, arg1) codegen.fcmpEq(arg0, arg1)
@@ -1778,8 +1778,28 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
codegen.icmpEq(arg0, arg1) codegen.icmpEq(arg0, arg1)
} }
} }
}
else -> TODO(name) val interop = context.interopBuiltIns
return when (descriptor) {
in interop.readPrimitive -> {
val pointerType = pointerType(codegen.getLLVMType(descriptor.returnType!!))
val rawPointer = args.last()
val pointer = codegen.bitcast(pointerType, rawPointer)
codegen.load(pointer)
}
in interop.writePrimitive -> {
val pointerType = pointerType(codegen.getLLVMType(descriptor.valueParameters.last().type))
val rawPointer = args[1]
val pointer = codegen.bitcast(pointerType, rawPointer)
codegen.store(args[2], pointer)
codegen.theUnitInstanceRef.llvm
}
interop.nativePtrPlusLong -> codegen.gep(args[0], args[1])
interop.getNativeNullPtr -> kNullInt8Ptr
interop.getPointerSize -> Int32(LLVMPointerSize(codegen.llvmTargetData)).llvm
else -> TODO(callee.descriptor.original.toString())
} }
} }
+21
View File
@@ -1,3 +1,6 @@
#include <limits.h>
#include <stdint.h>
#include <stdlib.h>
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
#include <unistd.h> #include <unistd.h>
@@ -187,4 +190,22 @@ OBJ_GETTER0(Kotlin_konan_internal_undefined) {
RETURN_OBJ(nullptr); RETURN_OBJ(nullptr);
} }
void* Kotlin_interop_malloc(KLong size, KInt align) {
if (size > SIZE_MAX) {
return nullptr;
}
void* result = malloc(size);
if ((reinterpret_cast<uintptr_t>(result) & (align - 1)) != 0) {
// Unaligned!
RuntimeAssert(false, "unsupported alignment");
}
return result;
}
void Kotlin_interop_free(void* ptr) {
free(ptr);
}
} // extern "C" } // extern "C"