From caeb0b43be775d977d0ad7673dce5f9580934300 Mon Sep 17 00:00:00 2001 From: Mikhail Glukhikh Date: Fri, 2 Apr 2021 12:29:59 +0300 Subject: [PATCH] FIR: introduce JvmPlatformOverloadsConflictResolver The added here JvmPlatformOverloadsConflictResolver prefers Java field to property in case of conflicts. --- .../jvm/JvmCallConflictResolverFactory.kt | 3 +- .../JvmPlatformOverloadsConflictResolver.kt | 48 +++++++++++++++++++ .../jvmField/clashWithJavaSuperClassField.kt | 1 - .../tests/j+k/fieldOverridesNothing.fir.kt | 21 -------- .../tests/j+k/fieldOverridesNothing.kt | 1 + .../properties/fieldPropertyOverloads.fir.kt | 27 ----------- .../j+k/properties/fieldPropertyOverloads.kt | 1 + .../fieldPropertyOverloadsNI.fir.kt | 27 ----------- .../properties/fieldPropertyOverloadsNI.kt | 1 + 9 files changed, 53 insertions(+), 77 deletions(-) create mode 100644 compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmPlatformOverloadsConflictResolver.kt delete mode 100644 compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.fir.kt delete mode 100644 compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.fir.kt delete mode 100644 compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.fir.kt diff --git a/compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmCallConflictResolverFactory.kt b/compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmCallConflictResolverFactory.kt index e9ccd6be8d7..f1b5087d373 100644 --- a/compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmCallConflictResolverFactory.kt +++ b/compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmCallConflictResolverFactory.kt @@ -22,7 +22,8 @@ object JvmCallConflictResolverFactory : ConeCallConflictResolverFactory() { val specificityComparator = JvmTypeSpecificityComparator(components.ctx) return ConeCompositeConflictResolver( ConeOverloadConflictResolver(specificityComparator, components), - ConeEquivalentCallConflictResolver(specificityComparator, components) + ConeEquivalentCallConflictResolver(specificityComparator, components), + JvmPlatformOverloadsConflictResolver(specificityComparator, components) ) } } diff --git a/compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmPlatformOverloadsConflictResolver.kt b/compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmPlatformOverloadsConflictResolver.kt new file mode 100644 index 00000000000..72fa77c29b4 --- /dev/null +++ b/compiler/fir/jvm/src/org/jetbrains/kotlin/fir/resolve/calls/jvm/JvmPlatformOverloadsConflictResolver.kt @@ -0,0 +1,48 @@ +/* + * Copyright 2010-2021 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.fir.resolve.calls.jvm + +import org.jetbrains.kotlin.config.LanguageFeature +import org.jetbrains.kotlin.fir.containingClass +import org.jetbrains.kotlin.fir.declarations.FirField +import org.jetbrains.kotlin.fir.declarations.FirProperty +import org.jetbrains.kotlin.fir.languageVersionSettings +import org.jetbrains.kotlin.fir.resolve.calls.AbstractConeCallConflictResolver +import org.jetbrains.kotlin.fir.resolve.calls.Candidate +import org.jetbrains.kotlin.fir.resolve.inference.InferenceComponents +import org.jetbrains.kotlin.resolve.calls.results.TypeSpecificityComparator + +class JvmPlatformOverloadsConflictResolver( + specificityComparator: TypeSpecificityComparator, + inferenceComponents: InferenceComponents +) : AbstractConeCallConflictResolver(specificityComparator, inferenceComponents) { + override fun chooseMaximallySpecificCandidates( + candidates: Set, + discriminateGenerics: Boolean, + discriminateAbstracts: Boolean + ): Set { + if (!inferenceComponents.session.languageVersionSettings.supportsFeature(LanguageFeature.PreferJavaFieldOverload)) { + return candidates + } + val result = mutableSetOf() + outerLoop@ for (myCandidate in candidates) { + val me = myCandidate.symbol.fir + if (me is FirProperty && me.symbol.containingClass() != null) { + for (otherCandidate in candidates) { + val other = otherCandidate.symbol.fir + if (other is FirField && other.symbol.containingClass() != null) { + // NB: FE 1.0 does class equivalence check here + // However, in FIR container classes aren't the same for our samples (see fieldPropertyOverloads.kt) + // E.g. we can have SomeConcreteJavaEnum for field and kotlin.Enum for static property 'name' + continue@outerLoop + } + } + } + result += myCandidate + } + return result + } +} \ No newline at end of file diff --git a/compiler/testData/codegen/box/jvmField/clashWithJavaSuperClassField.kt b/compiler/testData/codegen/box/jvmField/clashWithJavaSuperClassField.kt index d80e232695e..70bb49657d9 100644 --- a/compiler/testData/codegen/box/jvmField/clashWithJavaSuperClassField.kt +++ b/compiler/testData/codegen/box/jvmField/clashWithJavaSuperClassField.kt @@ -1,5 +1,4 @@ // TARGET_BACKEND: JVM -// IGNORE_BACKEND_FIR: JVM_IR // WITH_RUNTIME // FILE: test.kt diff --git a/compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.fir.kt b/compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.fir.kt deleted file mode 100644 index 22597ce5383..00000000000 --- a/compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.fir.kt +++ /dev/null @@ -1,21 +0,0 @@ -// !LANGUAGE: +PreferJavaFieldOverload - -// FILE: B.java - -public abstract class B implements A { - public int size = 1; -} - -// FILE: main.kt - -interface A { - val size: Int -} - -class C : B() { - override val size: Int get() = 1 -} - -fun foo() { - C().size -} \ No newline at end of file diff --git a/compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.kt b/compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.kt index 388391607f5..47a7971833c 100644 --- a/compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.kt +++ b/compiler/testData/diagnostics/tests/j+k/fieldOverridesNothing.kt @@ -1,3 +1,4 @@ +// FIR_IDENTICAL // !LANGUAGE: +PreferJavaFieldOverload // FILE: B.java diff --git a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.fir.kt b/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.fir.kt deleted file mode 100644 index 7bbee3f0ca6..00000000000 --- a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.fir.kt +++ /dev/null @@ -1,27 +0,0 @@ -// SKIP_TXT -// !LANGUAGE: +PreferJavaFieldOverload -// !CHECK_TYPE - -// FILE: CompressionType.java -public enum CompressionType { - ZIP(1.0); - public final double name; - CompressionType(double name) { - this.name = name; - } -} - -// FILE: CollectionWithSize.java -public abstract class CollectionWithSize implements java.util.Collection { - public final String size = ""; -} - -// FILE: main.kt - -fun main(c: CollectionWithSize) { - CompressionType.ZIP.name checkType { _() } - c.size checkType { _() } - - CompressionType.ZIP::name checkType { _>() } - c::size checkType { _>() } -} diff --git a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.kt b/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.kt index 76f58ec7f95..0c03ddbb404 100644 --- a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.kt +++ b/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloads.kt @@ -1,3 +1,4 @@ +// FIR_IDENTICAL // SKIP_TXT // !LANGUAGE: +PreferJavaFieldOverload // !CHECK_TYPE diff --git a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.fir.kt b/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.fir.kt deleted file mode 100644 index de3cb2b490b..00000000000 --- a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.fir.kt +++ /dev/null @@ -1,27 +0,0 @@ -// SKIP_TXT -// !LANGUAGE: +PreferJavaFieldOverload +NewInference -// !CHECK_TYPE - -// FILE: CompressionType.java -public enum CompressionType { - ZIP(1.0); - public final double name; - CompressionType(double name) { - this.name = name; - } -} - -// FILE: CollectionWithSize.java -public abstract class CollectionWithSize implements java.util.Collection { - public final String size = ""; -} - -// FILE: main.kt - -fun main(c: CollectionWithSize) { - CompressionType.ZIP.name checkType { _() } - c.size checkType { _() } - - CompressionType.ZIP::name checkType { _>() } - c::size checkType { _>() } -} diff --git a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.kt b/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.kt index 77fd034669b..19ddbaa136b 100644 --- a/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.kt +++ b/compiler/testData/diagnostics/tests/j+k/properties/fieldPropertyOverloadsNI.kt @@ -1,3 +1,4 @@ +// FIR_IDENTICAL // SKIP_TXT // !LANGUAGE: +PreferJavaFieldOverload +NewInference // !CHECK_TYPE