Non local return implemented

This commit is contained in:
Konstantin Anisimov
2017-02-02 16:33:55 +07:00
parent 043fd8b0ec
commit be2b2f1b43
3 changed files with 10 additions and 4 deletions
@@ -20,6 +20,7 @@ internal class CodeGenerator(override val context: Context) : ContextUtils {
var returnSlot: LLVMValueRef? = null var returnSlot: LLVMValueRef? = null
var slotsPhi: LLVMValueRef? = null var slotsPhi: LLVMValueRef? = null
var slotCount = 0 var slotCount = 0
var functionDescriptor: FunctionDescriptor? = null
fun prologue(descriptor: FunctionDescriptor) { fun prologue(descriptor: FunctionDescriptor) {
prologue(llvmFunction(descriptor), prologue(llvmFunction(descriptor),
@@ -27,6 +28,7 @@ internal class CodeGenerator(override val context: Context) : ContextUtils {
if (descriptor is ConstructorDescriptor) { if (descriptor is ConstructorDescriptor) {
constructedClass = descriptor.constructedClass constructedClass = descriptor.constructedClass
} }
functionDescriptor = descriptor
} }
fun prologue(function:LLVMValueRef, returnType:LLVMTypeRef) { fun prologue(function:LLVMValueRef, returnType:LLVMTypeRef) {
@@ -1491,6 +1491,11 @@ internal class CodeGeneratorVisitor(val context: Context) : IrElementVisitorVoid
} }
override fun genReturn(target: CallableDescriptor, value: LLVMValueRef?) { override fun genReturn(target: CallableDescriptor, value: LLVMValueRef?) {
if (target == codegen.functionDescriptor) {
super.genReturn(target, value)
return
}
if (KotlinBuiltIns.isUnit(inlineBody.type) == false) { if (KotlinBuiltIns.isUnit(inlineBody.type) == false) {
codegen.assignPhis(getResult()!! to value!!) codegen.assignPhis(getResult()!! to value!!)
} }
@@ -35,7 +35,6 @@ internal class FunctionInlining(val context: Context): IrElementTransformerVoid(
//-------------------------------------------------------------------------// //-------------------------------------------------------------------------//
fun getLambdaStatements(value: IrExpression) : MutableList<IrStatement> { fun getLambdaStatements(value: IrExpression) : MutableList<IrStatement> {
val statements = (value as IrContainerExpressionBase).statements val statements = (value as IrContainerExpressionBase).statements
val lambdaFunction = statements[0] as IrFunction val lambdaFunction = statements[0] as IrFunction
val lambdaBody = lambdaFunction.body as IrBlockBody val lambdaBody = lambdaFunction.body as IrBlockBody
@@ -52,11 +51,11 @@ internal class FunctionInlining(val context: Context): IrElementTransformerVoid(
//-------------------------------------------------------------------------// //-------------------------------------------------------------------------//
fun evaluateParameters(callExpression: IrCall, fun evaluateParameters(irCall: IrCall,
statements: MutableList<IrStatement>): List<Pair<ParameterDescriptor, IrExpression>> { statements: MutableList<IrStatement>): List<Pair<ParameterDescriptor, IrExpression>> {
val scope = Scope(callExpression.descriptor as FunctionDescriptor) val scope = Scope(irCall.descriptor as FunctionDescriptor)
val parametersOld = callExpression.getArguments() // Create map inline_function_parameter -> containing_function_expression. val parametersOld = irCall.getArguments() // Create map inline_function_parameter -> containing_function_expression.
val parametersNew = parametersOld.map { val parametersNew = parametersOld.map {
val parameter = it.first val parameter = it.first
val expression = it.second val expression = it.second