JVM_IR KT-47492 fix 'for' loop generation
This commit is contained in:
committed by
TeamCityServer
parent
6993b86d3b
commit
768afc5ba4
+18
@@ -29694,6 +29694,24 @@ public class FirBlackBoxCodegenTestGenerated extends AbstractFirBlackBoxCodegenT
|
|||||||
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492.kt")
|
||||||
|
public void testKt47492() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492a.kt")
|
||||||
|
public void testKt47492a() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492a.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492b.kt")
|
||||||
|
public void testKt47492b() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492b.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
||||||
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
||||||
|
|||||||
+40
-1
@@ -41,6 +41,7 @@ import org.jetbrains.kotlin.ir.declarations.*
|
|||||||
import org.jetbrains.kotlin.ir.descriptors.toIrBasedDescriptor
|
import org.jetbrains.kotlin.ir.descriptors.toIrBasedDescriptor
|
||||||
import org.jetbrains.kotlin.ir.descriptors.toIrBasedKotlinType
|
import org.jetbrains.kotlin.ir.descriptors.toIrBasedKotlinType
|
||||||
import org.jetbrains.kotlin.ir.expressions.*
|
import org.jetbrains.kotlin.ir.expressions.*
|
||||||
|
import org.jetbrains.kotlin.ir.expressions.impl.IrCompositeImpl
|
||||||
import org.jetbrains.kotlin.ir.symbols.IrSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrSymbol
|
||||||
import org.jetbrains.kotlin.ir.symbols.IrTypeParameterSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrTypeParameterSymbol
|
||||||
import org.jetbrains.kotlin.ir.symbols.IrValueParameterSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrValueParameterSymbol
|
||||||
@@ -1061,9 +1062,47 @@ class ExpressionCodegen(
|
|||||||
val entry = markNewLabel()
|
val entry = markNewLabel()
|
||||||
val endLabel = linkedLabel()
|
val endLabel = linkedLabel()
|
||||||
val continueLabel = linkedLabel()
|
val continueLabel = linkedLabel()
|
||||||
|
|
||||||
|
val loopInfo = LoopInfo(loop, continueLabel, endLabel)
|
||||||
|
|
||||||
|
// If we have a 'for' loop transformed into a 'do-while' loop,
|
||||||
|
// then corresponding loop variable initialization should happen before we mark loop end and loop continue labels,
|
||||||
|
// because loop variable can be used in the loop condition,
|
||||||
|
// and corresponding slot might contain arbitrary garbage left over from previous computations (see KT-47492).
|
||||||
|
// TODO consider adding special intrinsics for loop body markers instead of generating them manually.
|
||||||
|
if (loop.origin == IrStatementOrigin.FOR_LOOP_INNER_WHILE) {
|
||||||
|
val body = loop.body
|
||||||
|
if (body is IrComposite && body.origin == IrStatementOrigin.FOR_LOOP_INNER_WHILE && body.statements.isNotEmpty()) {
|
||||||
|
val forLoopNext = body.statements[0]
|
||||||
|
if (forLoopNext is IrComposite && forLoopNext.origin == IrStatementOrigin.FOR_LOOP_NEXT) {
|
||||||
|
// We have a 'for' loop transformed into a 'do-while' loop.
|
||||||
|
// Generate it's loop variable initialization,
|
||||||
|
// then mark loop end and loop continue labels,
|
||||||
|
// then generate the for loop body.
|
||||||
|
val forLoopBody = IrCompositeImpl(
|
||||||
|
body.startOffset, body.endOffset, body.type, body.origin,
|
||||||
|
body.statements.subList(1, body.statements.size)
|
||||||
|
)
|
||||||
|
data.withBlock(loopInfo) {
|
||||||
|
forLoopNext.accept(this, data).discard()
|
||||||
|
mv.fakeAlwaysFalseIfeq(continueLabel)
|
||||||
|
mv.fakeAlwaysFalseIfeq(endLabel)
|
||||||
|
forLoopBody.accept(this, data).discard()
|
||||||
|
mv.visitLabel(continueLabel)
|
||||||
|
loop.condition.markLineNumber(true)
|
||||||
|
loop.condition.accept(this, data).coerceToBoolean().jumpIfTrue(entry)
|
||||||
|
}
|
||||||
|
mv.mark(endLabel)
|
||||||
|
addInlineMarker(mv, false)
|
||||||
|
return unitValue
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// We have a regular 'do-while' loop. Proceed as usual.
|
||||||
mv.fakeAlwaysFalseIfeq(continueLabel)
|
mv.fakeAlwaysFalseIfeq(continueLabel)
|
||||||
mv.fakeAlwaysFalseIfeq(endLabel)
|
mv.fakeAlwaysFalseIfeq(endLabel)
|
||||||
data.withBlock(LoopInfo(loop, continueLabel, endLabel)) {
|
data.withBlock(loopInfo) {
|
||||||
loop.body?.accept(this, data)?.discard()
|
loop.body?.accept(this, data)?.discard()
|
||||||
mv.visitLabel(continueLabel)
|
mv.visitLabel(continueLabel)
|
||||||
loop.condition.markLineNumber(true)
|
loop.condition.markLineNumber(true)
|
||||||
|
|||||||
+11
@@ -0,0 +1,11 @@
|
|||||||
|
// DONT_TARGET_EXACT_BACKEND: WASM
|
||||||
|
// WITH_RUNTIME
|
||||||
|
|
||||||
|
fun p() {}
|
||||||
|
|
||||||
|
fun box(): String {
|
||||||
|
var sum = 1
|
||||||
|
for (i: Int? in sum downTo sum.toULong().countTrailingZeroBits())
|
||||||
|
p()
|
||||||
|
return "OK"
|
||||||
|
}
|
||||||
@@ -0,0 +1,20 @@
|
|||||||
|
// DONT_TARGET_EXACT_BACKEND: WASM
|
||||||
|
// WITH_RUNTIME
|
||||||
|
|
||||||
|
fun a() = 5
|
||||||
|
fun b() = 1
|
||||||
|
fun p() {}
|
||||||
|
|
||||||
|
fun box(): String {
|
||||||
|
when (false) {
|
||||||
|
else -> {
|
||||||
|
val h1 = 1
|
||||||
|
val h2 = 2L
|
||||||
|
val h3 = 3L
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var sum = 1
|
||||||
|
for (i: Int? in a() downTo b())
|
||||||
|
p()
|
||||||
|
return "OK"
|
||||||
|
}
|
||||||
@@ -0,0 +1,19 @@
|
|||||||
|
// DONT_TARGET_EXACT_BACKEND: WASM
|
||||||
|
// WITH_RUNTIME
|
||||||
|
|
||||||
|
fun a() = 5
|
||||||
|
fun b() = 1
|
||||||
|
|
||||||
|
fun p() {}
|
||||||
|
|
||||||
|
fun box(): String {
|
||||||
|
try {
|
||||||
|
val h1 = 1
|
||||||
|
val h2 = 2L
|
||||||
|
val h3 = 3L
|
||||||
|
} catch (e: Exception) { throw e }
|
||||||
|
var sum = 1
|
||||||
|
for (i: Int? in a() downTo b())
|
||||||
|
p()
|
||||||
|
return "OK"
|
||||||
|
}
|
||||||
+18
@@ -29652,6 +29652,24 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest {
|
|||||||
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492.kt")
|
||||||
|
public void testKt47492() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492a.kt")
|
||||||
|
public void testKt47492a() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492a.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492b.kt")
|
||||||
|
public void testKt47492b() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492b.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
||||||
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
||||||
|
|||||||
+18
@@ -29694,6 +29694,24 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes
|
|||||||
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492.kt")
|
||||||
|
public void testKt47492() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492a.kt")
|
||||||
|
public void testKt47492a() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492a.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("kt47492b.kt")
|
||||||
|
public void testKt47492b() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492b.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
||||||
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
||||||
|
|||||||
+15
@@ -25203,6 +25203,21 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes
|
|||||||
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492.kt")
|
||||||
|
public void testKt47492() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492a.kt")
|
||||||
|
public void testKt47492a() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492a.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492b.kt")
|
||||||
|
public void testKt47492b() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492b.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
||||||
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
||||||
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
||||||
|
|||||||
js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/es6/semantics/IrJsCodegenBoxES6TestGenerated.java
Generated
+15
@@ -19942,6 +19942,21 @@ public class IrJsCodegenBoxES6TestGenerated extends AbstractIrJsCodegenBoxES6Tes
|
|||||||
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492.kt")
|
||||||
|
public void testKt47492() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492a.kt")
|
||||||
|
public void testKt47492a() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492a.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492b.kt")
|
||||||
|
public void testKt47492b() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492b.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
||||||
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
||||||
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
||||||
|
|||||||
Generated
+15
@@ -19348,6 +19348,21 @@ public class IrJsCodegenBoxTestGenerated extends AbstractIrJsCodegenBoxTest {
|
|||||||
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492.kt")
|
||||||
|
public void testKt47492() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492a.kt")
|
||||||
|
public void testKt47492a() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492a.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492b.kt")
|
||||||
|
public void testKt47492b() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492b.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
||||||
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
||||||
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
||||||
|
|||||||
Generated
+15
@@ -19398,6 +19398,21 @@ public class JsCodegenBoxTestGenerated extends AbstractJsCodegenBoxTest {
|
|||||||
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
runTest("compiler/testData/codegen/box/ranges/kt37370a.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492.kt")
|
||||||
|
public void testKt47492() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492a.kt")
|
||||||
|
public void testKt47492a() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492a.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("kt47492b.kt")
|
||||||
|
public void testKt47492b() throws Exception {
|
||||||
|
runTest("compiler/testData/codegen/box/ranges/kt47492b.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
@TestMetadata("multiAssignmentIterationOverIntRange.kt")
|
||||||
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
public void testMultiAssignmentIterationOverIntRange() throws Exception {
|
||||||
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
runTest("compiler/testData/codegen/box/ranges/multiAssignmentIterationOverIntRange.kt");
|
||||||
|
|||||||
Reference in New Issue
Block a user