diff --git a/compiler/fir/fir2ir/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java b/compiler/fir/fir2ir/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java index 34de0272d04..175bce90688 100644 --- a/compiler/fir/fir2ir/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java +++ b/compiler/fir/fir2ir/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java @@ -6465,6 +6465,11 @@ public class FirBlackBoxCodegenTestGenerated extends AbstractFirBlackBoxCodegenT runTest("compiler/testData/codegen/box/coroutines/suspendJavaOverrides.kt"); } + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_3() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines"); + } + @TestMetadata("suspendReturningPlatformType.kt") public void testSuspendReturningPlatformType() throws Exception { runTest("compiler/testData/codegen/box/coroutines/suspendReturningPlatformType.kt"); diff --git a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/CallGenerator.kt b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/CallGenerator.kt index 5fc05accfef..98e3a77c7e2 100644 --- a/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/CallGenerator.kt +++ b/compiler/ir/ir.psi2ir/src/org/jetbrains/kotlin/psi2ir/generators/CallGenerator.kt @@ -384,7 +384,10 @@ class CallGenerator(statementGenerator: StatementGenerator) : StatementGenerator for (valueArgument in valueArgumentsInEvaluationOrder) { val valueParameter = valueArgumentsToValueParameters[valueArgument]!! val irArgument = call.getValueArgument(valueParameter) ?: continue - val irArgumentValue = scope.createTemporaryVariableInBlock(context, irArgument, irBlock, valueParameter.name.asString()) + val irArgumentValue = if (irArgument.hasNoSideEffects()) + generateExpressionValue(irArgument.type) { irArgument } // Computing a lambda has no side effects, can generate in place + else + scope.createTemporaryVariableInBlock(context, irArgument, irBlock, valueParameter.name.asString()) irArgumentValues[valueParameter] = irArgumentValue } @@ -399,6 +402,12 @@ class CallGenerator(statementGenerator: StatementGenerator) : StatementGenerator } } +fun IrExpression.hasNoSideEffects() = + this is IrFunctionExpression || + (this is IrCallableReference && dispatchReceiver == null && extensionReceiver == null) || + this is IrClassReference || + this is IrConst<*> + fun CallGenerator.generateCall(ktElement: KtElement, call: CallBuilder, origin: IrStatementOrigin? = null) = generateCall(ktElement.startOffsetSkippingComments, ktElement.endOffset, call, origin) diff --git a/compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt b/compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt new file mode 100644 index 00000000000..b5a6e0a9454 --- /dev/null +++ b/compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt @@ -0,0 +1,32 @@ +// IGNORE_BACKEND_FIR: JVM_IR +// IGNORE_BACKEND: JS +// WITH_RUNTIME +// WITH_COROUTINES +// COMMON_COROUTINES_TEST +import helpers.* +import COROUTINES_PACKAGE.* +import COROUTINES_PACKAGE.intrinsics.* + +inline fun callAction(aux: Int, action: () -> String): String { + return action() +} + +suspend fun get() = "OK" + +suspend fun callSuspend(): String { + return callAction(action = { + get() + }, aux = 0) +} + +fun builder(c: suspend () -> Unit) { + c.startCoroutine(EmptyContinuation) +} + +fun box(): String { + var v = "fail" + builder { + v = callSuspend() + } + return v +} diff --git a/compiler/testData/ir/irText/expressions/callWithReorderedArguments.txt b/compiler/testData/ir/irText/expressions/callWithReorderedArguments.txt index bdc22f5af30..acc634caadb 100644 --- a/compiler/testData/ir/irText/expressions/callWithReorderedArguments.txt +++ b/compiler/testData/ir/irText/expressions/callWithReorderedArguments.txt @@ -34,9 +34,7 @@ FILE fqName: fileName:/callWithReorderedArguments.kt b: GET_VAR 'val tmp_0: kotlin.Int [val] declared in .test' type=kotlin.Int origin=null BLOCK type=kotlin.Unit origin=ARGUMENTS_REORDERING_FOR_CALL VAR IR_TEMPORARY_VARIABLE name:tmp_2 type:kotlin.Int [val] - CONST Int type=kotlin.Int value=1 - VAR IR_TEMPORARY_VARIABLE name:tmp_3 type:kotlin.Int [val] CALL 'public final fun reordered2 (): kotlin.Int declared in ' type=kotlin.Int origin=null CALL 'public final fun foo (a: kotlin.Int, b: kotlin.Int): kotlin.Unit declared in ' type=kotlin.Unit origin=null - a: GET_VAR 'val tmp_3: kotlin.Int [val] declared in .test' type=kotlin.Int origin=null - b: GET_VAR 'val tmp_2: kotlin.Int [val] declared in .test' type=kotlin.Int origin=null + a: GET_VAR 'val tmp_2: kotlin.Int [val] declared in .test' type=kotlin.Int origin=null + b: CONST Int type=kotlin.Int value=1 diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java index 08c4a845ad8..e1edc1fc7f3 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java @@ -6880,6 +6880,16 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest { runTest("compiler/testData/codegen/box/coroutines/suspendJavaOverrides.kt"); } + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_2() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines.experimental"); + } + + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_3() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines"); + } + @TestMetadata("suspendReturningPlatformType.kt") public void testSuspendReturningPlatformType() throws Exception { runTest("compiler/testData/codegen/box/coroutines/suspendReturningPlatformType.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java index dab112bea72..6cea7f6be2a 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java @@ -6880,6 +6880,16 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes runTest("compiler/testData/codegen/box/coroutines/suspendJavaOverrides.kt"); } + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_2() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines.experimental"); + } + + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_3() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines"); + } + @TestMetadata("suspendReturningPlatformType.kt") public void testSuspendReturningPlatformType() throws Exception { runTest("compiler/testData/codegen/box/coroutines/suspendReturningPlatformType.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java index 4fca346ad33..b625db521e7 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java @@ -6465,6 +6465,11 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes runTest("compiler/testData/codegen/box/coroutines/suspendJavaOverrides.kt"); } + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_3() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines"); + } + @TestMetadata("suspendReturningPlatformType.kt") public void testSuspendReturningPlatformType() throws Exception { runTest("compiler/testData/codegen/box/coroutines/suspendReturningPlatformType.kt"); diff --git a/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java b/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java index 20d494af17e..369df0195a6 100644 --- a/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java +++ b/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java @@ -5455,6 +5455,11 @@ public class IrJsCodegenBoxTestGenerated extends AbstractIrJsCodegenBoxTest { runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendInTheMiddleOfObjectConstruction.kt", "kotlin.coroutines"); } + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_3() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines"); + } + @TestMetadata("suspensionInsideSafeCallWithElvis.kt") public void testSuspensionInsideSafeCallWithElvis_1_3() throws Exception { runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspensionInsideSafeCallWithElvis.kt", "kotlin.coroutines"); diff --git a/js/js.tests/test/org/jetbrains/kotlin/js/test/semantics/JsCodegenBoxTestGenerated.java b/js/js.tests/test/org/jetbrains/kotlin/js/test/semantics/JsCodegenBoxTestGenerated.java index 033946a68d1..d30c626eadc 100644 --- a/js/js.tests/test/org/jetbrains/kotlin/js/test/semantics/JsCodegenBoxTestGenerated.java +++ b/js/js.tests/test/org/jetbrains/kotlin/js/test/semantics/JsCodegenBoxTestGenerated.java @@ -5455,6 +5455,11 @@ public class JsCodegenBoxTestGenerated extends AbstractJsCodegenBoxTest { runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendInTheMiddleOfObjectConstruction.kt", "kotlin.coroutines"); } + @TestMetadata("suspendLambdaWithArgumentRearrangement.kt") + public void testSuspendLambdaWithArgumentRearrangement_1_3() throws Exception { + runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspendLambdaWithArgumentRearrangement.kt", "kotlin.coroutines"); + } + @TestMetadata("suspensionInsideSafeCallWithElvis.kt") public void testSuspensionInsideSafeCallWithElvis_1_3() throws Exception { runTestWithPackageReplacement("compiler/testData/codegen/box/coroutines/suspensionInsideSafeCallWithElvis.kt", "kotlin.coroutines");