From 8f9ea3e08bbdf894fb1c52508910a4fd427b9d28 Mon Sep 17 00:00:00 2001 From: Dmitry Petrov Date: Mon, 25 Sep 2017 11:51:47 +0300 Subject: [PATCH] Fix const range bounds generation --- .../jetbrains/kotlin/codegen/StackValue.java | 13 +++++++ .../ForInUntilConstantRangeLoopGenerator.kt | 4 +- .../forInRangeLiteralWithMixedTypeBounds.kt | 39 +++++++++++++++++++ .../ir/IrBlackBoxCodegenTestGenerated.java | 6 +++ .../codegen/BlackBoxCodegenTestGenerated.java | 6 +++ .../LightAnalysisModeTestGenerated.java | 6 +++ .../semantics/JsCodegenBoxTestGenerated.java | 6 +++ 7 files changed, 77 insertions(+), 3 deletions(-) create mode 100644 compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt diff --git a/compiler/backend/src/org/jetbrains/kotlin/codegen/StackValue.java b/compiler/backend/src/org/jetbrains/kotlin/codegen/StackValue.java index cf8f4a5a6da..7fbb9ed385c 100644 --- a/compiler/backend/src/org/jetbrains/kotlin/codegen/StackValue.java +++ b/compiler/backend/src/org/jetbrains/kotlin/codegen/StackValue.java @@ -179,6 +179,19 @@ public abstract class StackValue { return type == Type.VOID_TYPE ? none() : new OnStack(type); } + @NotNull + public static StackValue integerConstant(int value, @NotNull Type type) { + if (type == Type.LONG_TYPE) { + return constant(Long.valueOf(value), type); + } + else if (type == Type.BYTE_TYPE || type == Type.SHORT_TYPE || type == Type.INT_TYPE) { + return constant(Integer.valueOf(value), type); + } + else { + throw new AssertionError("Unexpected integer type: " + type); + } + } + @NotNull public static StackValue constant(@Nullable Object value, @NotNull Type type) { if (type == Type.BOOLEAN_TYPE) { diff --git a/compiler/backend/src/org/jetbrains/kotlin/codegen/range/forLoop/ForInUntilConstantRangeLoopGenerator.kt b/compiler/backend/src/org/jetbrains/kotlin/codegen/range/forLoop/ForInUntilConstantRangeLoopGenerator.kt index 37d870157bb..23872324fee 100644 --- a/compiler/backend/src/org/jetbrains/kotlin/codegen/range/forLoop/ForInUntilConstantRangeLoopGenerator.kt +++ b/compiler/backend/src/org/jetbrains/kotlin/codegen/range/forLoop/ForInUntilConstantRangeLoopGenerator.kt @@ -18,10 +18,8 @@ package org.jetbrains.kotlin.codegen.range.forLoop import org.jetbrains.kotlin.codegen.ExpressionCodegen import org.jetbrains.kotlin.codegen.StackValue -import org.jetbrains.kotlin.psi.KtExpression import org.jetbrains.kotlin.psi.KtForExpression import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall -import org.jetbrains.kotlin.resolve.constants.* import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue class ForInUntilConstantRangeLoopGenerator( @@ -36,5 +34,5 @@ class ForInUntilConstantRangeLoopGenerator( codegen.generateReceiverValue(from, false) override fun generateTo(): StackValue = - StackValue.constant(untilValue, asmElementType) + StackValue.integerConstant(untilValue, asmElementType) } \ No newline at end of file diff --git a/compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt b/compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt new file mode 100644 index 00000000000..0fdbe711937 --- /dev/null +++ b/compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt @@ -0,0 +1,39 @@ +fun test1(): Long { + var s = 0L + for (i in 1L..4) { + s = s * 10 + i + } + return s +} + +fun test2(): Long { + var s = 0L + for (i in 1L..4.toShort()) { + s = s * 10 + i + } + return s +} + +fun testLI(a: Long, b: Int): Long { + var s = 0L + for (i in a..b) { + s = s * 10 + i + } + return s +} + +fun testLS(a: Long, b: Short): Long { + var s = 0L + for (i in a..b) { + s = s * 10 + i + } + return s +} + +fun box(): String { + if (test1() != 1234L) return "Fail 1" + if (test2() != 1234L) return "Fail 1" + if (testLI(1L, 4) != 1234L) return "Fail 2" + if (testLS(1L, 4.toShort()) != 1234L) return "Fail 2" + return "OK" +} \ No newline at end of file diff --git a/compiler/tests-ir-jvm/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java b/compiler/tests-ir-jvm/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java index 0607d17ad88..91a730010b4 100644 --- a/compiler/tests-ir-jvm/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java +++ b/compiler/tests-ir-jvm/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java @@ -13739,6 +13739,12 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes doTest(fileName); } + @TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt") + public void testForInRangeLiteralWithMixedTypeBounds() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt"); + doTest(fileName); + } + @TestMetadata("forInRangeToConstWithOverflow.kt") public void testForInRangeToConstWithOverflow() throws Exception { String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeToConstWithOverflow.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java index 70dbdb452b6..d893bfb2768 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java @@ -13739,6 +13739,12 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest { doTest(fileName); } + @TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt") + public void testForInRangeLiteralWithMixedTypeBounds() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt"); + doTest(fileName); + } + @TestMetadata("forInRangeToConstWithOverflow.kt") public void testForInRangeToConstWithOverflow() throws Exception { String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeToConstWithOverflow.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java index fdbc08cca65..5fff2fbb6f4 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java @@ -13739,6 +13739,12 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes doTest(fileName); } + @TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt") + public void testForInRangeLiteralWithMixedTypeBounds() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt"); + doTest(fileName); + } + @TestMetadata("forInRangeToConstWithOverflow.kt") public void testForInRangeToConstWithOverflow() throws Exception { String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeToConstWithOverflow.kt"); 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 a71dd67d870..ec688353b26 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 @@ -15203,6 +15203,12 @@ public class JsCodegenBoxTestGenerated extends AbstractJsCodegenBoxTest { doTest(fileName); } + @TestMetadata("forInRangeLiteralWithMixedTypeBounds.kt") + public void testForInRangeLiteralWithMixedTypeBounds() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeLiteralWithMixedTypeBounds.kt"); + doTest(fileName); + } + @TestMetadata("forInRangeToConstWithOverflow.kt") public void testForInRangeToConstWithOverflow() throws Exception { String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/ranges/forInRangeToConstWithOverflow.kt");