JVM_IR: add coercion for index in ArrayGet intrinsic

This commit is contained in:
Georgy Bronnikov
2019-12-17 15:50:36 +03:00
parent cca3f13e48
commit 220ea72d65
9 changed files with 50 additions and 2 deletions
@@ -19,12 +19,15 @@ package org.jetbrains.kotlin.backend.jvm.intrinsics
import org.jetbrains.kotlin.backend.jvm.codegen.* import org.jetbrains.kotlin.backend.jvm.codegen.*
import org.jetbrains.kotlin.codegen.AsmUtil import org.jetbrains.kotlin.codegen.AsmUtil
import org.jetbrains.kotlin.ir.expressions.IrFunctionAccessExpression import org.jetbrains.kotlin.ir.expressions.IrFunctionAccessExpression
import org.jetbrains.org.objectweb.asm.Type
object ArrayGet : IntrinsicMethod() { object ArrayGet : IntrinsicMethod() {
override fun invoke(expression: IrFunctionAccessExpression, codegen: ExpressionCodegen, data: BlockInfo): PromisedValue? { override fun invoke(expression: IrFunctionAccessExpression, codegen: ExpressionCodegen, data: BlockInfo): PromisedValue? {
val receiver = expression.dispatchReceiver!!.accept(codegen, data).materialized val receiver = expression.dispatchReceiver!!.accept(codegen, data).materialized
val elementType = AsmUtil.correctElementType(receiver.type) val elementType = AsmUtil.correctElementType(receiver.type)
expression.getValueArgument(0)!!.accept(codegen, data).materialize() expression.getValueArgument(0)!!.accept(codegen, data)
.coerce(Type.INT_TYPE, codegen.context.irBuiltIns.intType)
.materialize()
codegen.mv.aload(elementType) codegen.mv.aload(elementType)
return MaterialValue(codegen, elementType, expression.type) return MaterialValue(codegen, elementType, expression.type)
} }
@@ -20,13 +20,14 @@ import org.jetbrains.kotlin.backend.jvm.codegen.*
import org.jetbrains.kotlin.backend.jvm.ir.getArrayElementType import org.jetbrains.kotlin.backend.jvm.ir.getArrayElementType
import org.jetbrains.kotlin.codegen.AsmUtil import org.jetbrains.kotlin.codegen.AsmUtil
import org.jetbrains.kotlin.ir.expressions.IrFunctionAccessExpression import org.jetbrains.kotlin.ir.expressions.IrFunctionAccessExpression
import org.jetbrains.org.objectweb.asm.Type
object ArraySet : IntrinsicMethod() { object ArraySet : IntrinsicMethod() {
override fun invoke(expression: IrFunctionAccessExpression, codegen: ExpressionCodegen, data: BlockInfo): PromisedValue? { override fun invoke(expression: IrFunctionAccessExpression, codegen: ExpressionCodegen, data: BlockInfo): PromisedValue? {
val receiver = expression.dispatchReceiver!!.accept(codegen, data).materialized val receiver = expression.dispatchReceiver!!.accept(codegen, data).materialized
val elementType = AsmUtil.correctElementType(receiver.type) val elementType = AsmUtil.correctElementType(receiver.type)
val elementIrType = receiver.irType.getArrayElementType(codegen.context.irBuiltIns) val elementIrType = receiver.irType.getArrayElementType(codegen.context.irBuiltIns)
expression.getValueArgument(0)!!.accept(codegen, data).materialize() expression.getValueArgument(0)!!.accept(codegen, data).coerce(Type.INT_TYPE, codegen.context.irBuiltIns.intType).materialize()
expression.getValueArgument(1)!!.accept(codegen, data).coerce(elementType, elementIrType).materialize() expression.getValueArgument(1)!!.accept(codegen, data).coerce(elementType, elementIrType).materialize()
codegen.mv.astore(elementType) codegen.mv.astore(elementType)
return codegen.immaterialUnitValue return codegen.immaterialUnitValue
@@ -0,0 +1,14 @@
// IGNORE_BACKEND_FIR: JVM_IR
fun test(ix: Int?): String {
val arr = arrayOf("fail 1")
if (ix != null) {
arr[ix] = "OK"
return arr[ix]
}
return "fail 2"
}
fun box() = test(0)
@@ -18693,6 +18693,11 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest {
runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt");
} }
@TestMetadata("nullableAsIndex.kt")
public void testNullableAsIndex() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableAsIndex.kt");
}
@TestMetadata("nullableCharBoolean.kt") @TestMetadata("nullableCharBoolean.kt")
public void testNullableCharBoolean() throws Exception { public void testNullableCharBoolean() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt");
@@ -18693,6 +18693,11 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes
runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt");
} }
@TestMetadata("nullableAsIndex.kt")
public void testNullableAsIndex() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableAsIndex.kt");
}
@TestMetadata("nullableCharBoolean.kt") @TestMetadata("nullableCharBoolean.kt")
public void testNullableCharBoolean() throws Exception { public void testNullableCharBoolean() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt");
@@ -17177,6 +17177,11 @@ public class FirBlackBoxCodegenTestGenerated extends AbstractFirBlackBoxCodegenT
runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt");
} }
@TestMetadata("nullableAsIndex.kt")
public void testNullableAsIndex() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableAsIndex.kt");
}
@TestMetadata("nullableCharBoolean.kt") @TestMetadata("nullableCharBoolean.kt")
public void testNullableCharBoolean() throws Exception { public void testNullableCharBoolean() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt");
@@ -17177,6 +17177,11 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes
runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt");
} }
@TestMetadata("nullableAsIndex.kt")
public void testNullableAsIndex() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableAsIndex.kt");
}
@TestMetadata("nullableCharBoolean.kt") @TestMetadata("nullableCharBoolean.kt")
public void testNullableCharBoolean() throws Exception { public void testNullableCharBoolean() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt");
@@ -14413,6 +14413,11 @@ public class IrJsCodegenBoxTestGenerated extends AbstractIrJsCodegenBoxTest {
runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt");
} }
@TestMetadata("nullableAsIndex.kt")
public void testNullableAsIndex() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableAsIndex.kt");
}
@TestMetadata("nullableCharBoolean.kt") @TestMetadata("nullableCharBoolean.kt")
public void testNullableCharBoolean() throws Exception { public void testNullableCharBoolean() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt");
@@ -15593,6 +15593,11 @@ public class JsCodegenBoxTestGenerated extends AbstractJsCodegenBoxTest {
runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullAsNullableIntIsNull.kt");
} }
@TestMetadata("nullableAsIndex.kt")
public void testNullableAsIndex() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableAsIndex.kt");
}
@TestMetadata("nullableCharBoolean.kt") @TestMetadata("nullableCharBoolean.kt")
public void testNullableCharBoolean() throws Exception { public void testNullableCharBoolean() throws Exception {
runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt"); runTest("compiler/testData/codegen/box/primitiveTypes/nullableCharBoolean.kt");