IR: minor refactorings around IrType/IrCapturedType
- use identity in equals/hashCode. It was already effectively working like this because of `constructor === other.constructor` - implement variance and declare it in IrSimpleType - remove obsolete TODO - simplify code in captureFromArguments - use data objects
This commit is contained in:
committed by
Space Team
parent
dec41e8c46
commit
898d3aeea9
@@ -91,6 +91,9 @@ abstract class IrSimpleType(kotlinType: KotlinType?) : IrTypeBase(kotlinType), S
|
|||||||
)
|
)
|
||||||
val hasQuestionMark: Boolean
|
val hasQuestionMark: Boolean
|
||||||
get() = nullability == SimpleTypeNullability.MARKED_NULLABLE
|
get() = nullability == SimpleTypeNullability.MARKED_NULLABLE
|
||||||
|
|
||||||
|
override val variance: Variance
|
||||||
|
get() = Variance.INVARIANT
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -90,7 +90,7 @@ class IrTypeSubstitutor(
|
|||||||
override fun isEmptySubstitution(): Boolean = substitution.isEmpty()
|
override fun isEmptySubstitution(): Boolean = substitution.isEmpty()
|
||||||
}
|
}
|
||||||
|
|
||||||
class IrCapturedTypeSubstitutor(
|
internal class IrCapturedTypeSubstitutor(
|
||||||
typeParameters: List<IrTypeParameterSymbol>,
|
typeParameters: List<IrTypeParameterSymbol>,
|
||||||
typeArguments: List<IrTypeArgument>,
|
typeArguments: List<IrTypeArgument>,
|
||||||
capturedTypes: List<IrCapturedType?>,
|
capturedTypes: List<IrCapturedType?>,
|
||||||
|
|||||||
@@ -239,9 +239,7 @@ interface IrTypeSystemContext : TypeSystemContext, TypeSystemCommonSuperTypesCon
|
|||||||
*
|
*
|
||||||
* See https://kotlinlang.org/spec/type-system.html#type-capturing
|
* See https://kotlinlang.org/spec/type-system.html#type-capturing
|
||||||
*/
|
*/
|
||||||
|
|
||||||
override fun captureFromArguments(type: SimpleTypeMarker, status: CaptureStatus): SimpleTypeMarker? {
|
override fun captureFromArguments(type: SimpleTypeMarker, status: CaptureStatus): SimpleTypeMarker? {
|
||||||
// TODO: is that correct?
|
|
||||||
require(type is IrSimpleType)
|
require(type is IrSimpleType)
|
||||||
|
|
||||||
if (type is IrCapturedType) return null
|
if (type is IrCapturedType) return null
|
||||||
@@ -252,43 +250,33 @@ interface IrTypeSystemContext : TypeSystemContext, TypeSystemCommonSuperTypesCon
|
|||||||
if (!classifier.isBound) return null
|
if (!classifier.isBound) return null
|
||||||
|
|
||||||
val typeParameters = extractTypeParameters(classifier.owner)
|
val typeParameters = extractTypeParameters(classifier.owner)
|
||||||
|
|
||||||
require(typeArguments.size == typeParameters.size)
|
require(typeArguments.size == typeParameters.size)
|
||||||
|
|
||||||
if (typeArguments.all { it is IrTypeProjection && it.variance == Variance.INVARIANT }) return type
|
if (typeArguments.all { it is IrTypeProjection && it.variance == Variance.INVARIANT }) return type
|
||||||
|
|
||||||
val capturedTypes = ArrayList<IrCapturedType?>(typeArguments.size)
|
val capturedTypes = typeArguments.mapIndexed { index, argument ->
|
||||||
|
|
||||||
for (index in typeArguments.indices) {
|
|
||||||
val parameter = typeParameters[index]
|
|
||||||
val argument = typeArguments[index]
|
|
||||||
|
|
||||||
if (argument is IrTypeProjection && argument.variance == Variance.INVARIANT) {
|
if (argument is IrTypeProjection && argument.variance == Variance.INVARIANT) {
|
||||||
capturedTypes.add(null)
|
null
|
||||||
} else {
|
} else {
|
||||||
val lowerType = if (argument is IrTypeProjection && argument.variance == Variance.IN_VARIANCE) {
|
val lowerType = if (argument is IrTypeProjection && argument.variance == Variance.IN_VARIANCE) {
|
||||||
argument.type
|
argument.type
|
||||||
} else null
|
} else null
|
||||||
|
|
||||||
capturedTypes.add(IrCapturedType(status, lowerType, argument, parameter))
|
IrCapturedType(status, lowerType, argument, typeParameters[index])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
val newArguments = ArrayList<IrTypeArgument>(typeArguments.size)
|
|
||||||
|
|
||||||
val typeSubstitutor = IrCapturedTypeSubstitutor(typeParameters.memoryOptimizedMap { it.symbol }, typeArguments, capturedTypes)
|
val typeSubstitutor = IrCapturedTypeSubstitutor(typeParameters.memoryOptimizedMap { it.symbol }, typeArguments, capturedTypes)
|
||||||
|
|
||||||
for (index in typeArguments.indices) {
|
val newArguments = typeArguments.mapIndexed { index, oldArgument ->
|
||||||
val oldArgument = typeArguments[index]
|
|
||||||
val parameter = typeParameters[index]
|
|
||||||
val capturedType = capturedTypes[index]
|
val capturedType = capturedTypes[index]
|
||||||
|
|
||||||
if (capturedType == null) {
|
if (capturedType == null) {
|
||||||
assert(oldArgument is IrTypeProjection && oldArgument.variance == Variance.INVARIANT)
|
assert(oldArgument is IrTypeProjection && oldArgument.variance == Variance.INVARIANT)
|
||||||
newArguments.add(oldArgument)
|
oldArgument
|
||||||
} else {
|
} else {
|
||||||
val capturedSuperTypes = mutableListOf<IrType>()
|
val capturedSuperTypes = mutableListOf<IrType>()
|
||||||
parameter.superTypes.mapTo(capturedSuperTypes) {
|
typeParameters[index].superTypes.mapTo(capturedSuperTypes) {
|
||||||
typeSubstitutor.substitute(it)
|
typeSubstitutor.substitute(it)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -298,7 +286,7 @@ interface IrTypeSystemContext : TypeSystemContext, TypeSystemCommonSuperTypesCon
|
|||||||
|
|
||||||
capturedType.constructor.initSuperTypes(capturedSuperTypes)
|
capturedType.constructor.initSuperTypes(capturedSuperTypes)
|
||||||
|
|
||||||
newArguments.add(makeTypeProjection(capturedType, Variance.INVARIANT))
|
makeTypeProjection(capturedType, Variance.INVARIANT)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -10,15 +10,11 @@ import org.jetbrains.kotlin.ir.symbols.FqNameEqualityChecker
|
|||||||
import org.jetbrains.kotlin.ir.symbols.IrClassifierSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrClassifierSymbol
|
||||||
import org.jetbrains.kotlin.ir.symbols.IrTypeParameterSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrTypeParameterSymbol
|
||||||
import org.jetbrains.kotlin.ir.types.*
|
import org.jetbrains.kotlin.ir.types.*
|
||||||
import org.jetbrains.kotlin.utils.compactIfPossible
|
|
||||||
import org.jetbrains.kotlin.types.KotlinType
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
import org.jetbrains.kotlin.types.Variance
|
import org.jetbrains.kotlin.types.Variance
|
||||||
|
import org.jetbrains.kotlin.utils.compactIfPossible
|
||||||
|
|
||||||
abstract class IrAbstractSimpleType(kotlinType: KotlinType?) : IrSimpleType(kotlinType) {
|
abstract class IrAbstractSimpleType(kotlinType: KotlinType?) : IrSimpleType(kotlinType) {
|
||||||
|
|
||||||
override val variance: Variance
|
|
||||||
get() = Variance.INVARIANT
|
|
||||||
|
|
||||||
abstract override val classifier: IrClassifierSymbol
|
abstract override val classifier: IrClassifierSymbol
|
||||||
abstract override val nullability: SimpleTypeNullability
|
abstract override val nullability: SimpleTypeNullability
|
||||||
abstract override val arguments: List<IrTypeArgument>
|
abstract override val arguments: List<IrTypeArgument>
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import org.jetbrains.kotlin.ir.declarations.IrTypeParameter
|
|||||||
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
||||||
import org.jetbrains.kotlin.ir.symbols.IrClassifierSymbol
|
import org.jetbrains.kotlin.ir.symbols.IrClassifierSymbol
|
||||||
import org.jetbrains.kotlin.ir.types.*
|
import org.jetbrains.kotlin.ir.types.*
|
||||||
|
import org.jetbrains.kotlin.ir.util.render
|
||||||
import org.jetbrains.kotlin.types.KotlinType
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
import org.jetbrains.kotlin.types.Variance
|
import org.jetbrains.kotlin.types.Variance
|
||||||
import org.jetbrains.kotlin.types.model.CaptureStatus
|
import org.jetbrains.kotlin.types.model.CaptureStatus
|
||||||
@@ -44,11 +45,7 @@ class IrDynamicTypeImpl(
|
|||||||
val IrType.originalKotlinType: KotlinType?
|
val IrType.originalKotlinType: KotlinType?
|
||||||
get() = (this as? IrTypeBase)?.kotlinType
|
get() = (this as? IrTypeBase)?.kotlinType
|
||||||
|
|
||||||
object IrStarProjectionImpl : IrStarProjection {
|
data object IrStarProjectionImpl : IrStarProjection
|
||||||
override fun equals(other: Any?): Boolean = this === other
|
|
||||||
|
|
||||||
override fun hashCode(): Int = System.identityHashCode(this)
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An instance which should be used when creating an IR element whose type cannot be determined at the moment of creation.
|
* An instance which should be used when creating an IR element whose type cannot be determined at the moment of creation.
|
||||||
@@ -60,15 +57,11 @@ object IrStarProjectionImpl : IrStarProjection {
|
|||||||
* however this could lead to a situation where we forget to set return type sometimes. This would result in crashes at unexpected moments,
|
* however this could lead to a situation where we forget to set return type sometimes. This would result in crashes at unexpected moments,
|
||||||
* especially in Kotlin/JS where function return types are not present in the resulting binary files.
|
* especially in Kotlin/JS where function return types are not present in the resulting binary files.
|
||||||
*/
|
*/
|
||||||
object IrUninitializedType : IrType() {
|
data object IrUninitializedType : IrType() {
|
||||||
override val annotations: List<IrConstructorCall> = emptyList()
|
override val annotations: List<IrConstructorCall> = emptyList()
|
||||||
|
|
||||||
override fun equals(other: Any?): Boolean = this === other
|
|
||||||
|
|
||||||
override fun hashCode(): Int = System.identityHashCode(this)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class ReturnTypeIsNotInitializedException(function: IrFunction) : IllegalStateException(
|
internal class ReturnTypeIsNotInitializedException(function: IrFunction) : IllegalStateException(
|
||||||
"Return type is not initialized for function '${function.name}'"
|
"Return type is not initialized for function '${function.name}'"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -80,19 +73,12 @@ class IrCapturedType(
|
|||||||
projection: IrTypeArgument,
|
projection: IrTypeArgument,
|
||||||
typeParameter: IrTypeParameter
|
typeParameter: IrTypeParameter
|
||||||
) : IrSimpleType(null), CapturedTypeMarker {
|
) : IrSimpleType(null), CapturedTypeMarker {
|
||||||
|
class Constructor(val argument: IrTypeArgument, val typeParameter: IrTypeParameter) : CapturedTypeConstructorMarker {
|
||||||
override val variance: Variance
|
var superTypes: List<IrType> = emptyList()
|
||||||
get() = TODO("Not yet implemented")
|
private set
|
||||||
|
|
||||||
class Constructor(val argument: IrTypeArgument, val typeParameter: IrTypeParameter) :
|
|
||||||
CapturedTypeConstructorMarker {
|
|
||||||
|
|
||||||
private var _superTypes: List<IrType> = emptyList()
|
|
||||||
|
|
||||||
val superTypes: List<IrType> get() = _superTypes
|
|
||||||
|
|
||||||
fun initSuperTypes(superTypes: List<IrType>) {
|
fun initSuperTypes(superTypes: List<IrType>) {
|
||||||
_superTypes = superTypes
|
this.superTypes = superTypes
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -100,18 +86,13 @@ class IrCapturedType(
|
|||||||
|
|
||||||
override val classifier: IrClassifierSymbol get() = error("Captured Type does not have a classifier")
|
override val classifier: IrClassifierSymbol get() = error("Captured Type does not have a classifier")
|
||||||
override val arguments: List<IrTypeArgument> get() = emptyList()
|
override val arguments: List<IrTypeArgument> get() = emptyList()
|
||||||
override val abbreviation: IrTypeAbbreviation? get () = null
|
override val abbreviation: IrTypeAbbreviation? get() = null
|
||||||
override val nullability: SimpleTypeNullability get() = SimpleTypeNullability.DEFINITELY_NOT_NULL
|
override val nullability: SimpleTypeNullability get() = SimpleTypeNullability.DEFINITELY_NOT_NULL
|
||||||
override val annotations: List<IrConstructorCall> get() = emptyList()
|
override val annotations: List<IrConstructorCall> get() = emptyList()
|
||||||
|
|
||||||
override fun equals(other: Any?): Boolean {
|
override fun equals(other: Any?): Boolean = this === other
|
||||||
return other is IrCapturedType
|
|
||||||
&& captureStatus == other.captureStatus
|
|
||||||
&& lowerType == other.lowerType
|
|
||||||
&& constructor === other.constructor
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun hashCode(): Int {
|
override fun hashCode(): Int = System.identityHashCode(this)
|
||||||
return (captureStatus.hashCode() * 31 + (lowerType?.hashCode() ?: 0)) * 31 + constructor.hashCode()
|
|
||||||
}
|
override fun toString(): String = "IrCapturedType(${constructor.argument.render()}"
|
||||||
}
|
}
|
||||||
|
|||||||
+12
-10
@@ -8,8 +8,11 @@ package org.jetbrains.kotlin.backend.common.linkage.partial
|
|||||||
import org.jetbrains.kotlin.ir.IrBuiltIns
|
import org.jetbrains.kotlin.ir.IrBuiltIns
|
||||||
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
||||||
import org.jetbrains.kotlin.ir.linkage.partial.ExploredClassifier
|
import org.jetbrains.kotlin.ir.linkage.partial.ExploredClassifier
|
||||||
import org.jetbrains.kotlin.ir.types.*
|
import org.jetbrains.kotlin.ir.symbols.IrClassSymbol
|
||||||
import org.jetbrains.kotlin.types.Variance
|
import org.jetbrains.kotlin.ir.types.IrSimpleType
|
||||||
|
import org.jetbrains.kotlin.ir.types.IrTypeAbbreviation
|
||||||
|
import org.jetbrains.kotlin.ir.types.IrTypeArgument
|
||||||
|
import org.jetbrains.kotlin.ir.types.SimpleTypeNullability
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Replacement for IR types that reference unusable classifier symbols.
|
* Replacement for IR types that reference unusable classifier symbols.
|
||||||
@@ -17,15 +20,14 @@ import org.jetbrains.kotlin.types.Variance
|
|||||||
*/
|
*/
|
||||||
internal class PartiallyLinkedMarkerType(
|
internal class PartiallyLinkedMarkerType(
|
||||||
builtIns: IrBuiltIns,
|
builtIns: IrBuiltIns,
|
||||||
val unusableClassifier: ExploredClassifier.Unusable
|
val unusableClassifier: ExploredClassifier.Unusable,
|
||||||
) : IrSimpleType(null) {
|
) : IrSimpleType(null) {
|
||||||
override val annotations get() = emptyList<IrConstructorCall>()
|
override val annotations: List<IrConstructorCall> get() = emptyList()
|
||||||
override val classifier = builtIns.anyClass
|
override val classifier: IrClassSymbol = builtIns.anyClass
|
||||||
override val nullability get() = SimpleTypeNullability.MARKED_NULLABLE
|
override val nullability: SimpleTypeNullability get() = SimpleTypeNullability.MARKED_NULLABLE
|
||||||
override val arguments get() = emptyList<IrTypeArgument>()
|
override val arguments: List<IrTypeArgument> get() = emptyList()
|
||||||
override val abbreviation: IrTypeAbbreviation? get() = null
|
override val abbreviation: IrTypeAbbreviation? get() = null
|
||||||
override val variance get() = Variance.INVARIANT
|
|
||||||
|
|
||||||
override fun equals(other: Any?) = (other as? PartiallyLinkedMarkerType)?.unusableClassifier == unusableClassifier
|
override fun equals(other: Any?): Boolean = (other as? PartiallyLinkedMarkerType)?.unusableClassifier == unusableClassifier
|
||||||
override fun hashCode() = unusableClassifier.hashCode()
|
override fun hashCode(): Int = unusableClassifier.hashCode()
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user