diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/results/FlatSignatureSpecificity.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/results/FlatSignatureSpecificity.kt index 0d0d55ac8e8..0ebd9b90c55 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/results/FlatSignatureSpecificity.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/results/FlatSignatureSpecificity.kt @@ -20,7 +20,11 @@ import org.jetbrains.kotlin.resolve.calls.inference.CallHandle import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystem import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystemBuilderImpl import org.jetbrains.kotlin.resolve.calls.inference.constraintPosition.valueParameterPosition -import org.jetbrains.kotlin.types.* +import org.jetbrains.kotlin.types.Flexibility +import org.jetbrains.kotlin.types.Flexibility.SpecificityRelation +import org.jetbrains.kotlin.types.KotlinType +import org.jetbrains.kotlin.types.TypeUtils +import org.jetbrains.kotlin.types.Variance import org.jetbrains.kotlin.types.checker.KotlinTypeChecker interface SpecificityComparisonCallbacks { @@ -66,9 +70,12 @@ fun isSignatureNotLessSpecific( return !constraintSystem.status.hasContradiction() } +private fun KotlinType.getSpecificityRelationTo(otherType: KotlinType) = + this.getCapability(Flexibility::class.java)?.getSpecificityRelationTo(otherType) ?: Flexibility.SpecificityRelation.DONT_KNOW + private fun isDefinitelyLessSpecificByTypeSpecificity(specific: KotlinType, general: KotlinType): Boolean { val sThanG = specific.getSpecificityRelationTo(general) val gThanS = general.getSpecificityRelationTo(specific) - return sThanG == Specificity.Relation.LESS_SPECIFIC && - gThanS != Specificity.Relation.LESS_SPECIFIC + return sThanG == SpecificityRelation.LESS_SPECIFIC && + gThanS != SpecificityRelation.LESS_SPECIFIC } \ No newline at end of file diff --git a/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/java/lazy/types/LazyJavaTypeResolver.kt b/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/java/lazy/types/LazyJavaTypeResolver.kt index 20c448932b7..17e9e8d0b9e 100644 --- a/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/java/lazy/types/LazyJavaTypeResolver.kt +++ b/core/descriptor.loader.java/src/org/jetbrains/kotlin/load/java/lazy/types/LazyJavaTypeResolver.kt @@ -34,6 +34,7 @@ import org.jetbrains.kotlin.load.java.structure.* import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.platform.JavaToKotlinClassMap import org.jetbrains.kotlin.types.* +import org.jetbrains.kotlin.types.Flexibility.SpecificityRelation import org.jetbrains.kotlin.types.Variance.* import org.jetbrains.kotlin.types.typeUtil.createProjection import org.jetbrains.kotlin.types.typeUtil.replaceAnnotations @@ -313,20 +314,20 @@ class LazyJavaTypeResolver( else create(replacement, TypeUtils.makeNullable(replacement)) } - override fun getSpecificityRelationTo(otherType: KotlinType): Specificity.Relation { + override fun getSpecificityRelationTo(otherType: KotlinType): SpecificityRelation { // For primitive types we have to take care of the case when there are two overloaded methods like // foo(int) and foo(Integer) // if we do not discriminate one of them, any call to foo(kotlin.Int) will result in overload resolution ambiguity // so, for such cases, we discriminate Integer in favour of int if (!KotlinBuiltIns.isPrimitiveType(otherType) || !KotlinBuiltIns.isPrimitiveType(lowerBound)) { - return Specificity.Relation.DONT_KNOW + return SpecificityRelation.DONT_KNOW } // Int! >< Int? - if (otherType.isFlexible()) return Specificity.Relation.DONT_KNOW + if (otherType.isFlexible()) return SpecificityRelation.DONT_KNOW // Int? >< Int! - if (otherType.isMarkedNullable) return Specificity.Relation.DONT_KNOW + if (otherType.isMarkedNullable) return SpecificityRelation.DONT_KNOW // Int! lessSpecific Int - return Specificity.Relation.LESS_SPECIFIC + return SpecificityRelation.LESS_SPECIFIC } } } diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/TypeCapabilities.kt b/core/descriptors/src/org/jetbrains/kotlin/types/TypeCapabilities.kt index 8a2af3cb9b7..01c7e049acc 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/TypeCapabilities.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/TypeCapabilities.kt @@ -1,5 +1,5 @@ /* - * Copyright 2010-2015 JetBrains s.r.o. + * 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. @@ -49,19 +49,6 @@ fun TypeCapabilities.addCapability(clazz: Class, typeCap inline fun KotlinType.getCapability(): T? = getCapability(T::class.java) -interface Specificity : TypeCapability { - - enum class Relation { - LESS_SPECIFIC, - MORE_SPECIFIC, - DONT_KNOW - } - - fun getSpecificityRelationTo(otherType: KotlinType): Relation -} - -fun KotlinType.getSpecificityRelationTo(otherType: KotlinType) = - this.getCapability(Specificity::class.java)?.getSpecificityRelationTo(otherType) ?: Specificity.Relation.DONT_KNOW // To facilitate laziness, any KotlinType implementation may inherit from this trait, // even if it turns out that the type an instance represents is not actually a type variable diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java b/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java index 485d8aabf44..716e044bc06 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java +++ b/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java @@ -1,5 +1,5 @@ /* - * Copyright 2010-2015 JetBrains s.r.o. + * 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. @@ -25,7 +25,6 @@ import org.jetbrains.kotlin.descriptors.ClassDescriptor; import org.jetbrains.kotlin.descriptors.DeclarationDescriptor; import org.jetbrains.kotlin.descriptors.TypeParameterDescriptor; import org.jetbrains.kotlin.descriptors.annotations.Annotations; -import org.jetbrains.kotlin.resolve.calls.inference.CapturedType; import org.jetbrains.kotlin.resolve.constants.IntegerValueTypeConstructor; import org.jetbrains.kotlin.resolve.scopes.MemberScope; import org.jetbrains.kotlin.types.checker.KotlinTypeChecker; @@ -126,9 +125,9 @@ public class TypeUtils { @NotNull public static KotlinType makeNullableAsSpecified(@NotNull KotlinType type, boolean nullable) { - NullAwareness nullAwareness = type.getCapability(NullAwareness.class); - if (nullAwareness != null) { - return nullAwareness.makeNullableAsSpecified(nullable); + Flexibility flexibility = type.getCapability(Flexibility.class); + if (flexibility != null) { + return flexibility.makeNullableAsSpecified(nullable); } // Wrapping serves two purposes here diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt index a881d0068c5..9af00bdd855 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt @@ -17,6 +17,7 @@ package org.jetbrains.kotlin.types import org.jetbrains.kotlin.builtins.KotlinBuiltIns +import org.jetbrains.kotlin.types.Flexibility.SpecificityRelation import org.jetbrains.kotlin.types.typeUtil.builtIns open class DynamicTypesSettings { @@ -55,8 +56,8 @@ object DynamicTypeFactory : FlexibleTypeFactory { override val delegateType: KotlinType get() = upperBound - override fun getSpecificityRelationTo(otherType: KotlinType): Specificity.Relation { - return if (!otherType.isDynamic()) Specificity.Relation.LESS_SPECIFIC else Specificity.Relation.DONT_KNOW + override fun getSpecificityRelationTo(otherType: KotlinType): SpecificityRelation { + return if (!otherType.isDynamic()) SpecificityRelation.LESS_SPECIFIC else SpecificityRelation.DONT_KNOW } override fun makeNullableAsSpecified(nullable: Boolean): KotlinType { diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt index 5c0722b060a..d6b112fa5f7 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt @@ -38,6 +38,16 @@ interface Flexibility : TypeCapability, SubtypingRepresentatives { get() = upperBound override fun sameTypeConstructor(type: KotlinType) = false + + fun makeNullableAsSpecified(nullable: Boolean): KotlinType + + enum class SpecificityRelation { + LESS_SPECIFIC, + MORE_SPECIFIC, + DONT_KNOW + } + + fun getSpecificityRelationTo(otherType: KotlinType): SpecificityRelation } fun KotlinType.isFlexible(): Boolean = this.getCapability(Flexibility::class.java) != null @@ -85,23 +95,12 @@ fun Collection.singleBestRepresentative(): TypeProjection? { fun KotlinType.lowerIfFlexible(): KotlinType = if (this.isFlexible()) this.flexibility().lowerBound else this fun KotlinType.upperIfFlexible(): KotlinType = if (this.isFlexible()) this.flexibility().upperBound else this -interface NullAwareness : TypeCapability { - fun makeNullableAsSpecified(nullable: Boolean): KotlinType -} - abstract class DelegatingFlexibleType protected constructor( override val lowerBound: KotlinType, override val upperBound: KotlinType, override val factory: FlexibleTypeFactory -) : DelegatingType(), NullAwareness, Flexibility, Specificity { +) : DelegatingType(), Flexibility { companion object { - internal val capabilityClasses = hashSetOf( - NullAwareness::class.java, - Flexibility::class.java, - SubtypingRepresentatives::class.java, - Specificity::class.java - ) - @JvmField var RUN_SLOW_ASSERTIONS = false } @@ -130,9 +129,10 @@ abstract class DelegatingFlexibleType protected constructor( override fun getCapability(capabilityClass: Class): T? { @Suppress("UNCHECKED_CAST") - if (capabilityClass in capabilityClasses) return this as T - - return super.getCapability(capabilityClass) + return when(capabilityClass) { + Flexibility::class.java, SubtypingRepresentatives::class.java -> this as T + else -> super.getCapability(capabilityClass) + } } override fun makeNullableAsSpecified(nullable: Boolean): KotlinType {