Do subtyping with stub types properly
1) Return stub type if we are calculating super type between two same stub types 2) Return nullable Any if those stub types are different
This commit is contained in:
@@ -478,7 +478,11 @@ object AbstractTypeChecker {
|
||||
)
|
||||
}
|
||||
|
||||
if (subType.isStubType() || superType.isStubType()) return context.isStubTypeEqualsToAnything
|
||||
if (subType.isStubType() && superType.isStubType())
|
||||
return subType.typeConstructor() === superType.typeConstructor()
|
||||
|
||||
if (subType.isStubType() || superType.isStubType() || subType.isStubTypeForVariableInSubtyping() || superType.isStubTypeForVariableInSubtyping())
|
||||
return context.isStubTypeEqualsToAnything
|
||||
|
||||
// superType might be a definitely notNull type (see KT-42824)
|
||||
val superOriginalType = superType.asDefinitelyNotNullType()?.original() ?: superType
|
||||
@@ -742,7 +746,7 @@ object AbstractNullabilityChecker {
|
||||
if (type.isNothing()) return true
|
||||
if (type.isMarkedNullable()) return false
|
||||
|
||||
if (context.isStubTypeEqualsToAnything && type.isStubType()) return true
|
||||
if (context.isStubTypeEqualsToAnything && (type.isStubTypeForVariableInSubtyping() || type.isStubType())) return true
|
||||
|
||||
return areEqualTypeConstructors(type.typeConstructor(), end)
|
||||
}
|
||||
|
||||
@@ -73,7 +73,7 @@ interface TypeSystemBuiltInsContext {
|
||||
/**
|
||||
* Context that allow construction of types
|
||||
*/
|
||||
interface TypeSystemTypeFactoryContext {
|
||||
interface TypeSystemTypeFactoryContext: TypeSystemBuiltInsContext {
|
||||
fun createFlexibleType(lowerBound: SimpleTypeMarker, upperBound: SimpleTypeMarker): KotlinTypeMarker
|
||||
fun createSimpleType(
|
||||
constructor: TypeConstructorMarker,
|
||||
@@ -169,7 +169,7 @@ interface TypeSystemInferenceExtensionContext : TypeSystemContext, TypeSystemBui
|
||||
): CapturedTypeMarker
|
||||
|
||||
fun createStubType(typeVariable: TypeVariableMarker): StubTypeMarker
|
||||
|
||||
fun createStubTypeForTypeVariablesInSubtyping(typeVariable: TypeVariableMarker): StubTypeMarker
|
||||
|
||||
fun KotlinTypeMarker.removeAnnotations(): KotlinTypeMarker
|
||||
fun KotlinTypeMarker.removeExactAnnotation(): KotlinTypeMarker
|
||||
@@ -299,6 +299,7 @@ interface TypeSystemContext : TypeSystemOptimizationContext {
|
||||
}
|
||||
|
||||
fun SimpleTypeMarker.isStubType(): Boolean
|
||||
fun SimpleTypeMarker.isStubTypeForVariableInSubtyping(): Boolean
|
||||
|
||||
fun KotlinTypeMarker.asTypeArgument(): TypeArgumentMarker
|
||||
|
||||
|
||||
@@ -288,7 +288,11 @@ internal class DescriptorRendererImpl(
|
||||
|
||||
override fun renderTypeConstructor(typeConstructor: TypeConstructor): String = when (val cd = typeConstructor.declarationDescriptor) {
|
||||
is TypeParameterDescriptor, is ClassDescriptor, is TypeAliasDescriptor -> renderClassifierName(cd)
|
||||
null -> typeConstructor.toString()
|
||||
null -> {
|
||||
if (typeConstructor is IntersectionTypeConstructor) {
|
||||
typeConstructor.makeDebugNameForIntersectionType { if (it is StubType) it.originalTypeVariable else it }
|
||||
} else typeConstructor.toString()
|
||||
}
|
||||
else -> error("Unexpected classifier: " + cd::class.java)
|
||||
}
|
||||
|
||||
|
||||
@@ -61,11 +61,12 @@ class IntersectionTypeConstructor(typesToIntersect: Collection<KotlinType>) : Ty
|
||||
override fun getBuiltIns(): KotlinBuiltIns =
|
||||
intersectedTypes.iterator().next().constructor.builtIns
|
||||
|
||||
override fun toString(): String =
|
||||
makeDebugNameForIntersectionType(intersectedTypes)
|
||||
override fun toString(): String = makeDebugNameForIntersectionType()
|
||||
|
||||
private fun makeDebugNameForIntersectionType(resultingTypes: Iterable<KotlinType>): String =
|
||||
resultingTypes.sortedBy { it.toString() }.joinToString(separator = " & ", prefix = "{", postfix = "}")
|
||||
fun makeDebugNameForIntersectionType(getProperTypeRelatedToStringify: (KotlinType) -> Any = { it.toString() }): String {
|
||||
return intersectedTypes.sortedBy { getProperTypeRelatedToStringify(it).toString() }
|
||||
.joinToString(separator = " & ", prefix = "{", postfix = "}") { getProperTypeRelatedToStringify(it).toString() }
|
||||
}
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) return true
|
||||
|
||||
@@ -23,6 +23,17 @@ class StubType(
|
||||
}
|
||||
}
|
||||
|
||||
class StubTypeForTypeVariablesInSubtyping(
|
||||
originalTypeVariable: TypeConstructor,
|
||||
isMarkedNullable: Boolean,
|
||||
constructor: TypeConstructor = ErrorUtils.createErrorTypeConstructor("Constructor for non fixed type: $originalTypeVariable"),
|
||||
memberScope: MemberScope = ErrorUtils.createErrorScope("Scope for non fixed type: $originalTypeVariable")
|
||||
) : AbstractStubType(originalTypeVariable, isMarkedNullable, constructor, memberScope), StubTypeMarker {
|
||||
override fun materialize(newNullability: Boolean): AbstractStubType {
|
||||
return StubTypeForTypeVariablesInSubtyping(originalTypeVariable, newNullability, constructor, memberScope)
|
||||
}
|
||||
}
|
||||
|
||||
// This type is used as a replacement of type variables for provideDelegate resolve
|
||||
class StubTypeForProvideDelegateReceiver(
|
||||
originalTypeVariable: TypeConstructor,
|
||||
@@ -54,7 +65,7 @@ abstract class AbstractStubType(
|
||||
}
|
||||
|
||||
override fun toString(): String {
|
||||
return "NonFixed: $originalTypeVariable"
|
||||
return "NonFixed: $originalTypeVariable${if (isMarkedNullable) "?" else ""}"
|
||||
}
|
||||
|
||||
@TypeRefinement
|
||||
|
||||
+10
-1
@@ -81,7 +81,12 @@ interface ClassicTypeSystemContext : TypeSystemInferenceExtensionContext, TypeSy
|
||||
|
||||
override fun SimpleTypeMarker.isStubType(): Boolean {
|
||||
require(this is SimpleType, this::errorMessage)
|
||||
return this is AbstractStubType
|
||||
return this is StubType || this is StubTypeForProvideDelegateReceiver
|
||||
}
|
||||
|
||||
override fun SimpleTypeMarker.isStubTypeForVariableInSubtyping(): Boolean {
|
||||
require(this is SimpleType, this::errorMessage)
|
||||
return this is StubTypeForTypeVariablesInSubtyping
|
||||
}
|
||||
|
||||
override fun CapturedTypeMarker.lowerType(): KotlinTypeMarker? {
|
||||
@@ -543,6 +548,10 @@ interface ClassicTypeSystemContext : TypeSystemInferenceExtensionContext, TypeSy
|
||||
errorSupportedOnlyInTypeInference()
|
||||
}
|
||||
|
||||
override fun createStubTypeForTypeVariablesInSubtyping(typeVariable: TypeVariableMarker): StubTypeMarker {
|
||||
errorSupportedOnlyInTypeInference()
|
||||
}
|
||||
|
||||
override fun KotlinTypeMarker.isSpecial(): Boolean {
|
||||
require(this is KotlinType)
|
||||
return this is TypeUtils.SpecialType
|
||||
|
||||
@@ -136,6 +136,8 @@ class FlexibleTypeImpl(lowerBound: SimpleType, upperBound: SimpleType) : Flexibl
|
||||
return renderer.renderFlexibleType(renderer.renderType(lowerBound), renderer.renderType(upperBound), builtIns)
|
||||
}
|
||||
|
||||
override fun toString() = "($lowerBound..$upperBound)"
|
||||
|
||||
override fun makeNullableAsSpecified(newNullability: Boolean): UnwrappedType = KotlinTypeFactory.flexibleType(
|
||||
lowerBound.makeNullableAsSpecified(newNullability),
|
||||
upperBound.makeNullableAsSpecified(newNullability)
|
||||
|
||||
Reference in New Issue
Block a user