From 2cf079abedbfe748e8991bcddf6b1f0534da3c66 Mon Sep 17 00:00:00 2001 From: Svyatoslav Scherbina Date: Mon, 27 Jan 2020 19:47:30 +0300 Subject: [PATCH] Apply interop lowering to new declarations it produces #KT-36182 Fixed --- .../backend/konan/lower/InteropLowering.kt | 12 +++++++++++- .../interop/basics/callbacksAndVarargs.kt | 19 ++++++++++++++++++- .../interop/basics/ccallbacksAndVarargs.def | 4 ++++ 3 files changed, 33 insertions(+), 2 deletions(-) diff --git a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/lower/InteropLowering.kt b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/lower/InteropLowering.kt index 3511cdce7f4..f8dc2d8ef9e 100644 --- a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/lower/InteropLowering.kt +++ b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/lower/InteropLowering.kt @@ -815,7 +815,17 @@ private class InteropLoweringPart2(val context: Context) : FileLoweringPass { val transformer = InteropTransformer(context, irFile) irFile.transformChildrenVoid(transformer) - irFile.addChildren(transformer.newTopLevelDeclarations) + while (transformer.newTopLevelDeclarations.isNotEmpty()) { + val newTopLevelDeclarations = transformer.newTopLevelDeclarations.toList() + transformer.newTopLevelDeclarations.clear() + + // Assuming these declarations contain only new IR (i.e. existing lowered IR has not been moved there). + // TODO: make this more reliable. + val loweredNewTopLevelDeclarations = + newTopLevelDeclarations.map { it.transform(transformer, null) as IrDeclaration } + + irFile.addChildren(loweredNewTopLevelDeclarations) + } } } diff --git a/backend.native/tests/interop/basics/callbacksAndVarargs.kt b/backend.native/tests/interop/basics/callbacksAndVarargs.kt index a88d12c9cc0..5ac6aa863aa 100644 --- a/backend.native/tests/interop/basics/callbacksAndVarargs.kt +++ b/backend.native/tests/interop/basics/callbacksAndVarargs.kt @@ -7,13 +7,22 @@ import kotlin.test.* import kotlinx.cinterop.* import ccallbacksAndVarargs.* -fun main(args: Array) { +fun main() { + testStructCallbacks() + testVarargs() + testCallableReferences() +} + +fun testStructCallbacks() { assertEquals(42, getX(staticCFunction { -> cValue { x = 42 } })) applyCallback(cValue { x = 17 }, staticCFunction { it: CValue -> assertEquals(17, it.useContents { x }) }) assertEquals(66, makeS(66, 111).useContents { x }) +} + +fun testVarargs() { assertEquals(E.ONE, makeE(1)) getVarargs( @@ -51,3 +60,11 @@ fun main(args: Array) { assertEquals(null, a15) } } + +fun testCallableReferences() { + val sumRef = ::sum + assertEquals(3, sumRef(1, 2)) + + val sumPtr = staticCFunction(::sum) + assertEquals(7, sumPtr(3, 4)) +} diff --git a/backend.native/tests/interop/basics/ccallbacksAndVarargs.def b/backend.native/tests/interop/basics/ccallbacksAndVarargs.def index e6b2038430f..e38c45b9c3d 100644 --- a/backend.native/tests/interop/basics/ccallbacksAndVarargs.def +++ b/backend.native/tests/interop/basics/ccallbacksAndVarargs.def @@ -72,3 +72,7 @@ static struct Args getVarargs(int ignore, ...) { return result; } + +static int sum(int first, int second) { + return first + second; +}