From 18b218bfa827c96d8cdfd1f7f313763c0df0468f Mon Sep 17 00:00:00 2001 From: Mikhail Zarechenskiy Date: Mon, 17 Feb 2020 03:16:51 +0300 Subject: [PATCH] [NI] Use projected type for constraint like Cap(out A) <: out @Exact T This is an implicit semantics of Exact annotation --- ...ctTypeCheckerContextForConstraintSystem.kt | 20 ++++++++- .../valByMapDelegatedProperty.kt | 42 +++++++++++++++++++ .../codegen/BlackBoxCodegenTestGenerated.java | 5 +++ .../LightAnalysisModeTestGenerated.java | 5 +++ .../ir/FirBlackBoxCodegenTestGenerated.java | 5 +++ .../ir/IrBlackBoxCodegenTestGenerated.java | 5 +++ .../IrJsCodegenBoxTestGenerated.java | 5 +++ .../semantics/JsCodegenBoxTestGenerated.java | 5 +++ 8 files changed, 90 insertions(+), 2 deletions(-) create mode 100644 compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt diff --git a/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/inference/components/AbstractTypeCheckerContextForConstraintSystem.kt b/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/inference/components/AbstractTypeCheckerContextForConstraintSystem.kt index c571b921e79..4419b1bcef7 100644 --- a/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/inference/components/AbstractTypeCheckerContextForConstraintSystem.kt +++ b/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/inference/components/AbstractTypeCheckerContextForConstraintSystem.kt @@ -57,8 +57,10 @@ abstract class AbstractTypeCheckerContextForConstraintSystem : AbstractTypeCheck val hasExact = subType.isTypeVariableWithExact() || superType.isTypeVariableWithExact() // we should strip annotation's because we have incorporation operation and they should be not affected - val mySubType = if (hasExact) subType.removeExactAnnotation() else subType - val mySuperType = if (hasExact) superType.removeExactAnnotation() else superType + val mySubType = + if (hasExact) extractTypeForProjectedType(subType, out = true) ?: subType.removeExactAnnotation() else subType + val mySuperType = + if (hasExact) extractTypeForProjectedType(superType, out = false) ?: superType.removeExactAnnotation() else superType val result = internalAddSubtypeConstraint(mySubType, mySuperType) if (!hasExact) return result @@ -69,6 +71,20 @@ abstract class AbstractTypeCheckerContextForConstraintSystem : AbstractTypeCheck return (result ?: true) && (result2 ?: true) } + private fun extractTypeForProjectedType(type: KotlinTypeMarker, out: Boolean): KotlinTypeMarker? { + val typeMarker = type.asSimpleType()?.asCapturedType() ?: return null + + val projection = typeMarker.typeConstructorProjection() + if (projection.isStarProjection()) return null + + + return when (projection.getVariance()) { + TypeVariance.IN -> if (!out) typeMarker.lowerType() ?: projection.getType() else null + TypeVariance.OUT -> if (out) projection.getType() else null + TypeVariance.INV -> null + } + } + private fun KotlinTypeMarker.isTypeVariableWithExact() = hasExactAnnotation() && anyBound(this@AbstractTypeCheckerContextForConstraintSystem::isMyTypeVariable) diff --git a/compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt b/compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt new file mode 100644 index 00000000000..32ffed3c25c --- /dev/null +++ b/compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt @@ -0,0 +1,42 @@ +// WITH_RUNTIME +// KJS_WITH_FULL_RUNTIME +// IGNORE_BACKEND_FIR: JVM_IR + +import kotlin.test.* + +class ValByMapExtensionsTest { + val map: Map = hashMapOf("a" to "all", "b" to "bar", "c" to "code") + val genericMap = mapOf("i" to 1, "x" to 1.0) + val mmapOut: MutableMap = mutableMapOf("g" to "out", "g1" to "in") + val genericMmapOut: MutableMap = mmapOut + + val a by map + val b: String by map + val c: Any by map + val d: String? by map + val e: String by map.withDefault { "default" } + val f: String? by map.withDefault { null } + val g: String by mmapOut + val g1: String by genericMmapOut + + val i: Int by genericMap + val x: Double by genericMap + + fun doTest() { + assertEquals("all", a) + assertEquals("bar", b) + assertEquals("code", c) + assertEquals("default", e) + assertEquals(null, f) + assertEquals("out", g) + assertEquals("in", g1) + assertEquals(1, i) + assertEquals(1.0, x) + assertFailsWith { d } + } +} + +fun box(): String { + ValByMapExtensionsTest().doTest() + return "OK" +} diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java index 251c118dbbd..7c9630b57a6 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/BlackBoxCodegenTestGenerated.java @@ -9849,6 +9849,11 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest { runTest("compiler/testData/codegen/box/delegatedProperty/useReflectionOnKProperty.kt"); } + @TestMetadata("valByMapDelegatedProperty.kt") + public void testValByMapDelegatedProperty() throws Exception { + runTest("compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt"); + } + @TestMetadata("valInInnerClass.kt") public void testValInInnerClass() throws Exception { runTest("compiler/testData/codegen/box/delegatedProperty/valInInnerClass.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java index 0f8c8080d41..e35d68b13af 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java @@ -9849,6 +9849,11 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes runTest("compiler/testData/codegen/box/delegatedProperty/useReflectionOnKProperty.kt"); } + @TestMetadata("valByMapDelegatedProperty.kt") + public void testValByMapDelegatedProperty() throws Exception { + runTest("compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt"); + } + @TestMetadata("valInInnerClass.kt") public void testValInInnerClass() throws Exception { runTest("compiler/testData/codegen/box/delegatedProperty/valInInnerClass.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java index 24bdd7321c1..63e5e511d72 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/ir/FirBlackBoxCodegenTestGenerated.java @@ -8724,6 +8724,11 @@ public class FirBlackBoxCodegenTestGenerated extends AbstractFirBlackBoxCodegenT runTest("compiler/testData/codegen/box/delegatedProperty/useReflectionOnKProperty.kt"); } + @TestMetadata("valByMapDelegatedProperty.kt") + public void testValByMapDelegatedProperty() throws Exception { + runTest("compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt"); + } + @TestMetadata("valInInnerClass.kt") public void testValInInnerClass() throws Exception { runTest("compiler/testData/codegen/box/delegatedProperty/valInInnerClass.kt"); diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java index 812671bf50e..fc83685dac2 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/ir/IrBlackBoxCodegenTestGenerated.java @@ -8724,6 +8724,11 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes runTest("compiler/testData/codegen/box/delegatedProperty/useReflectionOnKProperty.kt"); } + @TestMetadata("valByMapDelegatedProperty.kt") + public void testValByMapDelegatedProperty() throws Exception { + runTest("compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt"); + } + @TestMetadata("valInInnerClass.kt") public void testValInInnerClass() throws Exception { runTest("compiler/testData/codegen/box/delegatedProperty/valInInnerClass.kt"); diff --git a/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java b/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java index 7c4d953ed90..1f65d2a1dc7 100644 --- a/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java +++ b/js/js.tests/test/org/jetbrains/kotlin/js/test/ir/semantics/IrJsCodegenBoxTestGenerated.java @@ -7479,6 +7479,11 @@ public class IrJsCodegenBoxTestGenerated extends AbstractIrJsCodegenBoxTest { runTest("compiler/testData/codegen/box/delegatedProperty/useReflectionOnKProperty.kt"); } + @TestMetadata("valByMapDelegatedProperty.kt") + public void testValByMapDelegatedProperty() throws Exception { + runTest("compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt"); + } + @TestMetadata("valInInnerClass.kt") public void testValInInnerClass() throws Exception { runTest("compiler/testData/codegen/box/delegatedProperty/valInInnerClass.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 0c6f22c8bff..5233cca7c3e 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 @@ -7479,6 +7479,11 @@ public class JsCodegenBoxTestGenerated extends AbstractJsCodegenBoxTest { runTest("compiler/testData/codegen/box/delegatedProperty/useReflectionOnKProperty.kt"); } + @TestMetadata("valByMapDelegatedProperty.kt") + public void testValByMapDelegatedProperty() throws Exception { + runTest("compiler/testData/codegen/box/delegatedProperty/valByMapDelegatedProperty.kt"); + } + @TestMetadata("valInInnerClass.kt") public void testValInInnerClass() throws Exception { runTest("compiler/testData/codegen/box/delegatedProperty/valInInnerClass.kt");