diff --git a/compiler/frontend/src/org/jetbrains/kotlin/types/TypeIntersector.java b/compiler/frontend/src/org/jetbrains/kotlin/types/TypeIntersector.java index b6923d19654..106df7dcf9d 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/types/TypeIntersector.java +++ b/compiler/frontend/src/org/jetbrains/kotlin/types/TypeIntersector.java @@ -117,6 +117,11 @@ public class TypeIntersector { // TODO: maybe return the most specific among the types that are subtypes to all others in the `nullabilityStripped`? // TODO: e.g. among {Int, Int?, Int!}, return `Int` (now it returns `Int!`). KotlinType bestRepresentative = FlexibleTypesKt.singleBestRepresentative(nullabilityStripped); + + if (bestRepresentative == null) { + bestRepresentative = UtilsKt.hackForTypeIntersector(nullabilityStripped); + } + if (bestRepresentative == null) { throw new AssertionError("Empty intersection for types " + types); } diff --git a/compiler/frontend/src/org/jetbrains/kotlin/types/Utils.kt b/compiler/frontend/src/org/jetbrains/kotlin/types/Utils.kt new file mode 100644 index 00000000000..e3fe5723ed9 --- /dev/null +++ b/compiler/frontend/src/org/jetbrains/kotlin/types/Utils.kt @@ -0,0 +1,39 @@ +/* + * Copyright 2010-2016 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.jetbrains.kotlin.types + +import org.jetbrains.kotlin.types.checker.KotlinTypeChecker + +/** + * This is temporary hack for type intersector. + * + * It is almost save, because: + * - it running only if general algorithm is failed + * - returned type is subtype of all [types]. + * + * But it is hack, because it can give unstable result, but it better than exception. + * See KT-11266. + */ +internal fun hackForTypeIntersector(types: Collection): KotlinType? { + if (types.size < 2) return types.firstOrNull() + + return types.firstOrNull { candidate -> + types.all { + KotlinTypeChecker.ERROR_TYPES_ARE_EQUAL_TO_ANYTHING.isSubtypeOf(candidate, it) + } + } +} \ No newline at end of file diff --git a/compiler/testData/diagnostics/testsWithStdLib/inference/kt11266.kt b/compiler/testData/diagnostics/testsWithStdLib/inference/kt11266.kt new file mode 100644 index 00000000000..c4cb696f7d6 --- /dev/null +++ b/compiler/testData/diagnostics/testsWithStdLib/inference/kt11266.kt @@ -0,0 +1,2 @@ + +fun foo(first: Array, second: Array) = Pair(first.toCollection(), second.toCollection()) \ No newline at end of file diff --git a/compiler/testData/diagnostics/testsWithStdLib/inference/kt11266.txt b/compiler/testData/diagnostics/testsWithStdLib/inference/kt11266.txt new file mode 100644 index 00000000000..440cae3e1b7 --- /dev/null +++ b/compiler/testData/diagnostics/testsWithStdLib/inference/kt11266.txt @@ -0,0 +1,3 @@ +package + +public fun foo(/*0*/ first: kotlin.Array, /*1*/ second: kotlin.Array): kotlin.Pair, kotlin.collections.MutableCollection> diff --git a/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestWithStdLibGenerated.java b/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestWithStdLibGenerated.java index 40ceef41d4d..7ccd4a02a00 100644 --- a/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestWithStdLibGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/checkers/DiagnosticsTestWithStdLibGenerated.java @@ -784,6 +784,12 @@ public class DiagnosticsTestWithStdLibGenerated extends AbstractDiagnosticsTestW doTest(fileName); } + @TestMetadata("kt11266.kt") + public void testKt11266() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/testsWithStdLib/inference/kt11266.kt"); + doTest(fileName); + } + @TestMetadata("kt1558.kt") public void testKt1558() throws Exception { String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/diagnostics/testsWithStdLib/inference/kt1558.kt");