Simplify coroutine generation in JS backend
Stop making aliasing suspend function descriptor with reference to instance of state machine. This may cause problems in some cases, for example, when compiling recursive suspend function. See KT-17281. Instead, make alias for synthetic continuation parameter. This additionally required some refactoring, e.g. *always* generating continuation parameter during codegen.
This commit is contained in:
@@ -0,0 +1,42 @@
|
||||
// IGNORE_BACKEND: NATIVE
|
||||
// WITH_RUNTIME
|
||||
// WITH_COROUTINES
|
||||
import kotlin.coroutines.experimental.*
|
||||
import kotlin.coroutines.experimental.intrinsics.*
|
||||
|
||||
fun box(): String {
|
||||
var result = 0
|
||||
|
||||
builder {
|
||||
result = factorial(4)
|
||||
}
|
||||
|
||||
while (postponed != null) {
|
||||
postponed!!()
|
||||
}
|
||||
|
||||
if (result != 24) return "fail1: $result"
|
||||
if (log != "1;1;2;6;24;") return "fail2: $log"
|
||||
|
||||
return "OK"
|
||||
}
|
||||
|
||||
suspend fun factorial(a: Int): Int = if (a > 0) suspendHere(factorial(a - 1) * a) else suspendHere(1)
|
||||
|
||||
suspend fun suspendHere(value: Int): Int = suspendCoroutineOrReturn { x ->
|
||||
postponed = {
|
||||
log += "$value;"
|
||||
x.resume(value)
|
||||
}
|
||||
COROUTINE_SUSPENDED
|
||||
}
|
||||
|
||||
fun builder(c: suspend () -> Unit) {
|
||||
c.startCoroutine(handleResultContinuation {
|
||||
postponed = null
|
||||
})
|
||||
}
|
||||
|
||||
var postponed: (() -> Unit)? = { }
|
||||
|
||||
var log = ""
|
||||
+6
@@ -5114,6 +5114,12 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("recursiveSuspend.kt")
|
||||
public void testRecursiveSuspend() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/coroutines/recursiveSuspend.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("returnByLabel.kt")
|
||||
public void testReturnByLabel() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/coroutines/returnByLabel.kt");
|
||||
|
||||
@@ -5114,6 +5114,12 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest {
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("recursiveSuspend.kt")
|
||||
public void testRecursiveSuspend() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/coroutines/recursiveSuspend.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("returnByLabel.kt")
|
||||
public void testReturnByLabel() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/coroutines/returnByLabel.kt");
|
||||
|
||||
@@ -5114,6 +5114,12 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("recursiveSuspend.kt")
|
||||
public void testRecursiveSuspend() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/coroutines/recursiveSuspend.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("returnByLabel.kt")
|
||||
public void testReturnByLabel() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/coroutines/returnByLabel.kt");
|
||||
|
||||
Reference in New Issue
Block a user