diff --git a/compiler/testData/codegen/box/reflection/call/inlineClasses/primitive/suspendFunction.kt b/compiler/testData/codegen/box/reflection/call/inlineClasses/primitive/suspendFunction.kt index bb63fc07e58..7ecee21f424 100644 --- a/compiler/testData/codegen/box/reflection/call/inlineClasses/primitive/suspendFunction.kt +++ b/compiler/testData/codegen/box/reflection/call/inlineClasses/primitive/suspendFunction.kt @@ -5,7 +5,6 @@ import kotlin.coroutines.startCoroutine import kotlin.reflect.full.callSuspend import kotlin.test.assertEquals -import kotlin.test.assertFailsWith import helpers.* inline class Z(val value: Int) @@ -32,33 +31,27 @@ private fun run0(f: suspend () -> Int): Int { fun box(): String { val c = C() - assertFailsWith("Remove assertFailsWith and try again, as this problem may have been fixed.") { - run0 { - C::nonNullConsume.callSuspend(c, Z(1)) - C::nonNullProduce.callSuspend(c).value - }.let { assertEquals(1, it) } - } + run0 { + C::nonNullConsume.callSuspend(c, Z(1)) + C::nonNullProduce.callSuspend(c).value + }.let { assertEquals(1, it) } run0 { C::nullableConsume.callSuspend(c, Z(2)) C::nullableProduce.callSuspend(c)!!.value }.let { assertEquals(2, it) } - assertFailsWith("Remove assertFailsWith and try again, as this problem may have been fixed.") { - run0 { - C::nonNull_nonNullConsumeAndProduce.callSuspend(c, Z(3)).value - }.let { assertEquals(3, it) } - } + run0 { + C::nonNull_nonNullConsumeAndProduce.callSuspend(c, Z(3)).value + }.let { assertEquals(3, it) } run0 { C::nonNull_nullableConsumeAndProduce.callSuspend(c, Z(4))!!.value }.let { assertEquals(4, it) } - assertFailsWith("Remove assertFailsWith and try again, as this problem may have been fixed.") { - run0 { - C::nullable_nonNullConsumeAndProduce.callSuspend(c, Z(5)).value - }.let { assertEquals(5, it) } - } + run0 { + C::nullable_nonNullConsumeAndProduce.callSuspend(c, Z(5)).value + }.let { assertEquals(5, it) } run0 { C::nullable_nullableConsumeAndProduce.callSuspend(c, Z(6))!!.value diff --git a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/calls/ValueClassAwareCaller.kt b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/calls/ValueClassAwareCaller.kt index ff31b72c94a..bb460d04500 100644 --- a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/calls/ValueClassAwareCaller.kt +++ b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/calls/ValueClassAwareCaller.kt @@ -62,7 +62,17 @@ internal class ValueClassAwareCaller( private class BoxUnboxData(val argumentRange: IntRange, val unboxParameters: Array?>, val box: Method?) private val data: BoxUnboxData = run { - val box = descriptor.returnType!!.toInlineClass()?.getBoxMethod(descriptor) + val returnType = descriptor.returnType!! + val box = if ( + descriptor is FunctionDescriptor && descriptor.isSuspend && + returnType.substitutedUnderlyingType()?.let { KotlinBuiltIns.isPrimitiveType(it) } == true + ) { + // Suspend functions always return java.lang.Object, and value classes over primitives are already boxed there. + null + } else { + returnType.toInlineClass()?.getBoxMethod(descriptor) + } + if (descriptor.isGetterOfUnderlyingPropertyOfValueClass()) { // Getter of the underlying val of a value class is always called on a boxed receiver, // no argument unboxing is required.