From 0199c76c06f71238de6952b597a6da7b65d43474 Mon Sep 17 00:00:00 2001 From: Victor Petukhov Date: Wed, 25 May 2022 11:00:51 +0200 Subject: [PATCH] [FE 1.0] Check callable reference return type safety during resolution ^KT-51844 ^KT-52503 Fixed --- ...CompilerTestFE10TestdataTestGenerated.java | 6 ++++ ...irOldFrontendDiagnosticsTestGenerated.java | 6 ++++ ...DiagnosticsWithLightTreeTestGenerated.java | 6 ++++ .../FirBlackBoxCodegenTestGenerated.java | 6 ++++ ...enteringLazyValueComputationException.java | 3 +- .../CallableReferencesCandidateFactory.kt | 10 +++++- .../codegen/box/callableReference/kt51844.kt | 15 +++++++++ .../tests/callableReference/kt52503.kt | 16 ++++++++++ .../tests/callableReference/kt52503.txt | 19 ++++++++++++ .../tests/platformTypes/kt50877.fir.kt | 31 ------------------- .../tests/platformTypes/kt50877.kt | 1 + .../test/runners/DiagnosticTestGenerated.java | 6 ++++ .../codegen/BlackBoxCodegenTestGenerated.java | 6 ++++ .../IrBlackBoxCodegenTestGenerated.java | 6 ++++ .../LightAnalysisModeTestGenerated.java | 5 +++ .../LazyWrappedTypeComputationException.kt | 8 +++++ .../js/test/JsCodegenBoxTestGenerated.java | 6 ++++ .../test/ir/IrJsCodegenBoxTestGenerated.java | 6 ++++ .../IrCodegenBoxWasmTestGenerated.java | 5 +++ .../NativeCodegenBoxTestGenerated.java | 6 ++++ 20 files changed, 140 insertions(+), 33 deletions(-) create mode 100644 compiler/testData/codegen/box/callableReference/kt51844.kt create mode 100644 compiler/testData/diagnostics/tests/callableReference/kt52503.kt create mode 100644 compiler/testData/diagnostics/tests/callableReference/kt52503.txt delete mode 100644 compiler/testData/diagnostics/tests/platformTypes/kt50877.fir.kt create mode 100644 core/descriptors/src/org/jetbrains/kotlin/types/error/LazyWrappedTypeComputationException.kt diff --git a/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java b/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java index 30c80f45168..aaaa03ed162 100644 --- a/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java +++ b/analysis/low-level-api-fir/tests/org/jetbrains/kotlin/analysis/low/level/api/fir/diagnostic/compiler/based/DiagnosisCompilerTestFE10TestdataTestGenerated.java @@ -2826,6 +2826,12 @@ public class DiagnosisCompilerTestFE10TestdataTestGenerated extends AbstractDiag runTest("compiler/testData/diagnostics/tests/callableReference/kt49038.kt"); } + @Test + @TestMetadata("kt52503.kt") + public void testKt52503() throws Exception { + runTest("compiler/testData/diagnostics/tests/callableReference/kt52503.kt"); + } + @Test @TestMetadata("kt7430_wrongClassOnLHS.kt") public void testKt7430_wrongClassOnLHS() throws Exception { diff --git a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java index 2080834f42f..0d3d56e8b9a 100644 --- a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java +++ b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsTestGenerated.java @@ -2826,6 +2826,12 @@ public class FirOldFrontendDiagnosticsTestGenerated extends AbstractFirDiagnosti runTest("compiler/testData/diagnostics/tests/callableReference/kt49038.kt"); } + @Test + @TestMetadata("kt52503.kt") + public void testKt52503() throws Exception { + runTest("compiler/testData/diagnostics/tests/callableReference/kt52503.kt"); + } + @Test @TestMetadata("kt7430_wrongClassOnLHS.kt") public void testKt7430_wrongClassOnLHS() throws Exception { diff --git a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java index 9f5f4cc12a9..c5e5e16dafa 100644 --- a/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java +++ b/compiler/fir/analysis-tests/tests-gen/org/jetbrains/kotlin/test/runners/FirOldFrontendDiagnosticsWithLightTreeTestGenerated.java @@ -2826,6 +2826,12 @@ public class FirOldFrontendDiagnosticsWithLightTreeTestGenerated extends Abstrac runTest("compiler/testData/diagnostics/tests/callableReference/kt49038.kt"); } + @Test + @TestMetadata("kt52503.kt") + public void testKt52503() throws Exception { + runTest("compiler/testData/diagnostics/tests/callableReference/kt52503.kt"); + } + @Test @TestMetadata("kt7430_wrongClassOnLHS.kt") public void testKt7430_wrongClassOnLHS() throws Exception { diff --git a/compiler/fir/fir2ir/tests-gen/org/jetbrains/kotlin/test/runners/codegen/FirBlackBoxCodegenTestGenerated.java b/compiler/fir/fir2ir/tests-gen/org/jetbrains/kotlin/test/runners/codegen/FirBlackBoxCodegenTestGenerated.java index 7b132431cf8..403cc958715 100644 --- a/compiler/fir/fir2ir/tests-gen/org/jetbrains/kotlin/test/runners/codegen/FirBlackBoxCodegenTestGenerated.java +++ b/compiler/fir/fir2ir/tests-gen/org/jetbrains/kotlin/test/runners/codegen/FirBlackBoxCodegenTestGenerated.java @@ -3129,6 +3129,12 @@ public class FirBlackBoxCodegenTestGenerated extends AbstractFirBlackBoxCodegenT runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @Test + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @Test @TestMetadata("nested.kt") public void testNested() throws Exception { diff --git a/compiler/frontend/src/org/jetbrains/kotlin/util/ReenteringLazyValueComputationException.java b/compiler/frontend/src/org/jetbrains/kotlin/util/ReenteringLazyValueComputationException.java index 5be947c2021..ed607710a45 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/util/ReenteringLazyValueComputationException.java +++ b/compiler/frontend/src/org/jetbrains/kotlin/util/ReenteringLazyValueComputationException.java @@ -19,8 +19,9 @@ package org.jetbrains.kotlin.util; import com.intellij.openapi.application.Application; import com.intellij.openapi.application.ApplicationManager; import org.jetbrains.annotations.NotNull; +import org.jetbrains.kotlin.types.error.LazyWrappedTypeComputationException; -public class ReenteringLazyValueComputationException extends RuntimeException { +public class ReenteringLazyValueComputationException extends LazyWrappedTypeComputationException { public ReenteringLazyValueComputationException() { } diff --git a/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/model/CallableReferencesCandidateFactory.kt b/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/model/CallableReferencesCandidateFactory.kt index ba69a1ef2b7..92a83736f13 100644 --- a/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/model/CallableReferencesCandidateFactory.kt +++ b/compiler/resolution/src/org/jetbrains/kotlin/resolve/calls/model/CallableReferencesCandidateFactory.kt @@ -27,6 +27,7 @@ import org.jetbrains.kotlin.types.* import org.jetbrains.kotlin.types.error.ErrorScopeKind import org.jetbrains.kotlin.types.error.ErrorUtils import org.jetbrains.kotlin.types.error.ErrorTypeKind +import org.jetbrains.kotlin.types.error.LazyWrappedTypeComputationException import org.jetbrains.kotlin.types.expressions.CoercionStrategy import org.jetbrains.kotlin.types.typeUtil.isUnit import org.jetbrains.kotlin.utils.SmartList @@ -239,8 +240,15 @@ class CallableReferencesCandidateFactory( // lower(Unit!) = Unit val returnExpectedType = inputOutputTypes.outputType + fun isReturnTypeNonUnitSafe(): Boolean = + try { + descriptor.returnType?.isUnit() == false + } catch (e: LazyWrappedTypeComputationException) { + false + } + val coercion = - if (returnExpectedType.isUnit() && descriptor.returnType?.isUnit() == false) + if (returnExpectedType.isUnit() && isReturnTypeNonUnitSafe()) CoercionStrategy.COERCION_TO_UNIT else CoercionStrategy.NO_COERCION diff --git a/compiler/testData/codegen/box/callableReference/kt51844.kt b/compiler/testData/codegen/box/callableReference/kt51844.kt new file mode 100644 index 00000000000..83712bb4021 --- /dev/null +++ b/compiler/testData/codegen/box/callableReference/kt51844.kt @@ -0,0 +1,15 @@ +// WITH_STDLIB + +abstract class Foo { + abstract fun contains(x: Int); +} + +// ERROR: Type checking has run into a recursive problem. Easiest workaround: specify types of your declarations explicitly +fun Foo.contains(vararg xs: Int) = xs.forEach(this::contains) + +fun box(): String { + object : Foo() { + override fun contains(x: Int) {} + }.contains(1) + return "OK" +} diff --git a/compiler/testData/diagnostics/tests/callableReference/kt52503.kt b/compiler/testData/diagnostics/tests/callableReference/kt52503.kt new file mode 100644 index 00000000000..4c12774c8c7 --- /dev/null +++ b/compiler/testData/diagnostics/tests/callableReference/kt52503.kt @@ -0,0 +1,16 @@ +// FIR_IDENTICAL +// WITH_STDLIB + +abstract class Foo + +object A { + fun Foo.contains(vararg xs: Int) = // 1 + xs.forEach(this::contains) // resolved to (2) in 1.7.0-RC, should be error "Type checking has run into a recursive problem" +} + +fun Any.contains(vararg xs: Int) {} // 2 + +fun box(): String { + object : Foo() {}.contains(1) + return "OK" +} \ No newline at end of file diff --git a/compiler/testData/diagnostics/tests/callableReference/kt52503.txt b/compiler/testData/diagnostics/tests/callableReference/kt52503.txt new file mode 100644 index 00000000000..59a01895ac5 --- /dev/null +++ b/compiler/testData/diagnostics/tests/callableReference/kt52503.txt @@ -0,0 +1,19 @@ +package + +public fun box(): kotlin.String +public fun kotlin.Any.contains(/*0*/ vararg xs: kotlin.Int /*kotlin.IntArray*/): kotlin.Unit + +public object A { + private constructor A() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String + public final fun Foo.contains(/*0*/ vararg xs: kotlin.Int /*kotlin.IntArray*/): kotlin.Unit +} + +public abstract class Foo { + public constructor Foo() + public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean + public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int + public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String +} diff --git a/compiler/testData/diagnostics/tests/platformTypes/kt50877.fir.kt b/compiler/testData/diagnostics/tests/platformTypes/kt50877.fir.kt deleted file mode 100644 index 99d5b007510..00000000000 --- a/compiler/testData/diagnostics/tests/platformTypes/kt50877.fir.kt +++ /dev/null @@ -1,31 +0,0 @@ -// FULL_JDK -// WITH_STDLIB - -// FILE: Schematic.kt -class Schematic { - var name: String? = null - - var error: String? = null - - override fun toString(): String { - return name!! - } -} - -// FILE: SortedListModel.java -import java.util.Comparator; - -public class SortedListModel { - public SortedListModel(Comparator comparator) { - } -} - - -// FILE: main.kt -val model = SortedListModel(Comparator.comparing { b1: Schematic -> - when { - b1.error != null -> 2 - b1.name!!.contains(":") -> 1 - else -> 0 - } -}.thenComparing { b1: Schematic -> b1.name!! }) \ No newline at end of file diff --git a/compiler/testData/diagnostics/tests/platformTypes/kt50877.kt b/compiler/testData/diagnostics/tests/platformTypes/kt50877.kt index 99d5b007510..1b57f849afd 100644 --- a/compiler/testData/diagnostics/tests/platformTypes/kt50877.kt +++ b/compiler/testData/diagnostics/tests/platformTypes/kt50877.kt @@ -1,3 +1,4 @@ +// FIR_IDENTICAL // FULL_JDK // WITH_STDLIB diff --git a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java index 95a7198b149..da83634f7f3 100644 --- a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java +++ b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/DiagnosticTestGenerated.java @@ -2832,6 +2832,12 @@ public class DiagnosticTestGenerated extends AbstractDiagnosticTest { runTest("compiler/testData/diagnostics/tests/callableReference/kt49038.kt"); } + @Test + @TestMetadata("kt52503.kt") + public void testKt52503() throws Exception { + runTest("compiler/testData/diagnostics/tests/callableReference/kt52503.kt"); + } + @Test @TestMetadata("kt7430_wrongClassOnLHS.kt") public void testKt7430_wrongClassOnLHS() throws Exception { diff --git a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/BlackBoxCodegenTestGenerated.java b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/BlackBoxCodegenTestGenerated.java index d3c9c37a9a3..18f8ca3ec16 100644 --- a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/BlackBoxCodegenTestGenerated.java +++ b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/BlackBoxCodegenTestGenerated.java @@ -3033,6 +3033,12 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest { runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @Test + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @Test @TestMetadata("nested.kt") public void testNested() throws Exception { diff --git a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/IrBlackBoxCodegenTestGenerated.java b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/IrBlackBoxCodegenTestGenerated.java index ce22763964c..e5785d14433 100644 --- a/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/IrBlackBoxCodegenTestGenerated.java +++ b/compiler/tests-common-new/tests-gen/org/jetbrains/kotlin/test/runners/codegen/IrBlackBoxCodegenTestGenerated.java @@ -3129,6 +3129,12 @@ public class IrBlackBoxCodegenTestGenerated extends AbstractIrBlackBoxCodegenTes runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @Test + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @Test @TestMetadata("nested.kt") public void testNested() throws Exception { diff --git a/compiler/tests-gen/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java b/compiler/tests-gen/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java index 1d6418aa4f5..34f1f9bcf27 100644 --- a/compiler/tests-gen/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java +++ b/compiler/tests-gen/org/jetbrains/kotlin/codegen/LightAnalysisModeTestGenerated.java @@ -2658,6 +2658,11 @@ public class LightAnalysisModeTestGenerated extends AbstractLightAnalysisModeTes runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @TestMetadata("nested.kt") public void testNested() throws Exception { runTest("compiler/testData/codegen/box/callableReference/nested.kt"); diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/error/LazyWrappedTypeComputationException.kt b/core/descriptors/src/org/jetbrains/kotlin/types/error/LazyWrappedTypeComputationException.kt new file mode 100644 index 00000000000..44d0ee1f6da --- /dev/null +++ b/core/descriptors/src/org/jetbrains/kotlin/types/error/LazyWrappedTypeComputationException.kt @@ -0,0 +1,8 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.types.error + +abstract class LazyWrappedTypeComputationException : RuntimeException() diff --git a/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/JsCodegenBoxTestGenerated.java b/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/JsCodegenBoxTestGenerated.java index 22626d75f4b..6505409d931 100644 --- a/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/JsCodegenBoxTestGenerated.java +++ b/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/JsCodegenBoxTestGenerated.java @@ -1983,6 +1983,12 @@ public class JsCodegenBoxTestGenerated extends AbstractJsCodegenBoxTest { runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @Test + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @Test @TestMetadata("nested.kt") public void testNested() throws Exception { diff --git a/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/ir/IrJsCodegenBoxTestGenerated.java b/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/ir/IrJsCodegenBoxTestGenerated.java index 1fc7e9047b5..ec01a63ce6c 100644 --- a/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/ir/IrJsCodegenBoxTestGenerated.java +++ b/js/js.tests/tests-gen/org/jetbrains/kotlin/js/test/ir/IrJsCodegenBoxTestGenerated.java @@ -2025,6 +2025,12 @@ public class IrJsCodegenBoxTestGenerated extends AbstractIrJsCodegenBoxTest { runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @Test + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @Test @TestMetadata("nested.kt") public void testNested() throws Exception { diff --git a/js/js.tests/tests-gen/org/jetbrains/kotlin/js/testOld/wasm/semantics/IrCodegenBoxWasmTestGenerated.java b/js/js.tests/tests-gen/org/jetbrains/kotlin/js/testOld/wasm/semantics/IrCodegenBoxWasmTestGenerated.java index 7dc996e6a5f..3d4bd282c94 100644 --- a/js/js.tests/tests-gen/org/jetbrains/kotlin/js/testOld/wasm/semantics/IrCodegenBoxWasmTestGenerated.java +++ b/js/js.tests/tests-gen/org/jetbrains/kotlin/js/testOld/wasm/semantics/IrCodegenBoxWasmTestGenerated.java @@ -1808,6 +1808,11 @@ public class IrCodegenBoxWasmTestGenerated extends AbstractIrCodegenBoxWasmTest runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @TestMetadata("nested.kt") public void testNested() throws Exception { runTest("compiler/testData/codegen/box/callableReference/nested.kt"); diff --git a/native/native.tests/tests-gen/org/jetbrains/kotlin/konan/blackboxtest/NativeCodegenBoxTestGenerated.java b/native/native.tests/tests-gen/org/jetbrains/kotlin/konan/blackboxtest/NativeCodegenBoxTestGenerated.java index 61f56a3f821..1ca36677f3c 100644 --- a/native/native.tests/tests-gen/org/jetbrains/kotlin/konan/blackboxtest/NativeCodegenBoxTestGenerated.java +++ b/native/native.tests/tests-gen/org/jetbrains/kotlin/konan/blackboxtest/NativeCodegenBoxTestGenerated.java @@ -2077,6 +2077,12 @@ public class NativeCodegenBoxTestGenerated extends AbstractNativeCodegenBoxTest runTest("compiler/testData/codegen/box/callableReference/kt50172.kt"); } + @Test + @TestMetadata("kt51844.kt") + public void testKt51844() throws Exception { + runTest("compiler/testData/codegen/box/callableReference/kt51844.kt"); + } + @Test @TestMetadata("nested.kt") public void testNested() throws Exception {