From fad3c1f2f615ac6f6b3dc1031689259b58b8b7ee Mon Sep 17 00:00:00 2001 From: Irene Dea Date: Fri, 8 Oct 2021 17:05:11 -0700 Subject: [PATCH] Add initial type attributes infra --- .../cli/jvm/compiler/KotlinCoreEnvironment.kt | 1 + .../extensions/TypeAttributeTranslators.kt | 37 +++++ .../jetbrains/kotlin/resolve/TypeResolver.kt | 16 ++- .../calls/inference/BuilderInferenceUtil.kt | 2 + .../kotlin/load/java/lazy/types/RawType.kt | 4 + .../java/typeEnhancement/typeEnhancement.kt | 1 + .../inference/CapturedTypeConstructor.kt | 11 +- .../kotlin/types/CompilerTypeAttributes.kt | 112 +++++++++++++++ .../types/CustomAnnotationTypeAttribute.kt | 34 +++++ .../org/jetbrains/kotlin/types/ErrorType.kt | 5 + .../org/jetbrains/kotlin/types/KotlinType.kt | 11 +- .../kotlin/types/KotlinTypeFactory.kt | 106 +++++++++++++- .../jetbrains/kotlin/types/SpecialTypes.kt | 17 ++- .../org/jetbrains/kotlin/types/StubTypes.kt | 5 + .../jetbrains/kotlin/types/TypeAttributes.kt | 129 ++++++++++++++++++ .../kotlin/types/TypeAttributesTranslator.kt | 44 ++++++ .../org/jetbrains/kotlin/types/TypeUtils.java | 6 + .../kotlin/types/TypeWithEnhancement.kt | 6 + .../types/checker/ClassicTypeSystemContext.kt | 2 +- .../types/checker/KotlinTypePreparator.kt | 2 +- .../kotlin/types/checker/NewCapturedType.kt | 11 +- .../jetbrains/kotlin/types/dynamicTypes.kt | 10 +- .../jetbrains/kotlin/types/flexibleTypes.kt | 3 + 23 files changed, 545 insertions(+), 30 deletions(-) create mode 100644 compiler/frontend/src/org/jetbrains/kotlin/extensions/TypeAttributeTranslators.kt create mode 100644 core/descriptors/src/org/jetbrains/kotlin/types/CompilerTypeAttributes.kt create mode 100644 core/descriptors/src/org/jetbrains/kotlin/types/CustomAnnotationTypeAttribute.kt create mode 100644 core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributes.kt create mode 100644 core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributesTranslator.kt diff --git a/compiler/cli/src/org/jetbrains/kotlin/cli/jvm/compiler/KotlinCoreEnvironment.kt b/compiler/cli/src/org/jetbrains/kotlin/cli/jvm/compiler/KotlinCoreEnvironment.kt index cfde9a38a40..194bdfae834 100644 --- a/compiler/cli/src/org/jetbrains/kotlin/cli/jvm/compiler/KotlinCoreEnvironment.kt +++ b/compiler/cli/src/org/jetbrains/kotlin/cli/jvm/compiler/KotlinCoreEnvironment.kt @@ -651,6 +651,7 @@ class KotlinCoreEnvironment private constructor( CandidateInterceptor.registerExtensionPoint(project) DescriptorSerializerPlugin.registerExtensionPoint(project) FirExtensionRegistrarAdapter.registerExtensionPoint(project) + TypeAttributeTranslators.registerExtensionPoint(project) } internal fun registerExtensionsFromPlugins(project: MockProject, configuration: CompilerConfiguration) { diff --git a/compiler/frontend/src/org/jetbrains/kotlin/extensions/TypeAttributeTranslators.kt b/compiler/frontend/src/org/jetbrains/kotlin/extensions/TypeAttributeTranslators.kt new file mode 100644 index 00000000000..2591c67b808 --- /dev/null +++ b/compiler/frontend/src/org/jetbrains/kotlin/extensions/TypeAttributeTranslators.kt @@ -0,0 +1,37 @@ +/* + * 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.extensions + +import com.intellij.openapi.project.Project +import org.jetbrains.kotlin.descriptors.annotations.Annotations +import org.jetbrains.kotlin.types.* + +interface TypeAttributeTranslatorExtension : TypeAttributesTranslator + +class TypeAttributeTranslators(project: Project) { + val translators: List = + getInstances(project) + DefaultTypeAttributesTranslator + + fun toAttributes(annotations: Annotations): TypeAttributes { + val translated = translators.mapNotNull { translator -> + translator.toAttributes(annotations) + }.flatten() + return TypeAttributes.create(translated) + } + + fun toAnnotations(attributes: TypeAttributes): Annotations { + val translated = translators.mapNotNull { translator -> + translator.toAnnotations(attributes) + }.flatten() + return Annotations.create(translated) + } + + companion object : + ProjectExtensionDescriptor( + "org.jetbrains.kotlin.extensions.typeAttribute", + TypeAttributeTranslatorExtension::class.java + ) +} diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeResolver.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeResolver.kt index cb8f9c17615..90f1459a2e1 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeResolver.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeResolver.kt @@ -28,6 +28,7 @@ import org.jetbrains.kotlin.descriptors.annotations.composeAnnotations import org.jetbrains.kotlin.descriptors.impl.VariableDescriptorImpl import org.jetbrains.kotlin.diagnostics.Errors import org.jetbrains.kotlin.diagnostics.Errors.* +import org.jetbrains.kotlin.extensions.TypeAttributeTranslators import org.jetbrains.kotlin.lexer.KtTokens import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.psi.* @@ -69,7 +70,8 @@ class TypeResolver( private val identifierChecker: IdentifierChecker, private val platformToKotlinClassMapper: PlatformToKotlinClassMapper, private val languageVersionSettings: LanguageVersionSettings, - private val upperBoundChecker: UpperBoundChecker + private val upperBoundChecker: UpperBoundChecker, + private val typeAttributeTranslators: TypeAttributeTranslators ) { private val isNonParenthesizedAnnotationsOnFunctionalTypesEnabled = languageVersionSettings.getFeatureSupport(LanguageFeature.NonParenthesizedAnnotationsOnFunctionalTypes) == LanguageFeature.State.ENABLED @@ -521,7 +523,7 @@ class TypeResolver( ErrorUtils.createErrorType("?") else KotlinTypeFactory.simpleTypeWithNonTrivialMemberScope( - annotations, + typeAttributeTranslators.toAttributes(annotations), typeParameter.typeConstructor, listOf(), false, @@ -602,7 +604,8 @@ class TypeResolver( " but ${collectedArgumentAsTypeProjections.size} instead of ${parameters.size} found in ${element.text}" } - val resultingType = KotlinTypeFactory.simpleNotNullType(annotations, classDescriptor, arguments) + val resultingType = + KotlinTypeFactory.simpleNotNullType(typeAttributeTranslators.toAttributes(annotations), classDescriptor, arguments) // We create flexible types by convention here // This is not intended to be used in normal users' environments, only for tests and debugger etc @@ -699,7 +702,12 @@ class TypeResolver( } return if (c.abbreviated) { - val abbreviatedType = KotlinTypeFactory.simpleType(annotations, descriptor.typeConstructor, arguments, false) + val abbreviatedType = KotlinTypeFactory.simpleType( + typeAttributeTranslators.toAttributes(annotations), + descriptor.typeConstructor, + arguments, + false + ) type(abbreviatedType) } else { val typeAliasExpansion = TypeAliasExpansion.create(null, descriptor, arguments) diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/inference/BuilderInferenceUtil.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/inference/BuilderInferenceUtil.kt index 5e4e09f0fe8..28f37b957c2 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/inference/BuilderInferenceUtil.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/calls/inference/BuilderInferenceUtil.kt @@ -56,6 +56,8 @@ class TypeTemplate( ) { override fun replaceAnnotations(newAnnotations: Annotations) = this + override fun replaceAttributes(newAttributes: TypeAttributes) = this + override fun makeNullableAsSpecified(newNullability: Boolean) = TypeTemplate(typeVariable, builderInferenceData, newNullability) override val delegate: SimpleType diff --git a/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/lazy/types/RawType.kt b/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/lazy/types/RawType.kt index 26cc016473f..77a5add3e59 100644 --- a/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/lazy/types/RawType.kt +++ b/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/lazy/types/RawType.kt @@ -57,6 +57,10 @@ class RawTypeImpl private constructor(lowerBound: SimpleType, upperBound: Simple override fun replaceAnnotations(newAnnotations: Annotations) = RawTypeImpl(lowerBound.replaceAnnotations(newAnnotations), upperBound.replaceAnnotations(newAnnotations)) + override fun replaceAttributes(newAttributes: TypeAttributes) = + RawTypeImpl(lowerBound.replaceAttributes(newAttributes), upperBound.replaceAttributes(newAttributes)) + + override fun makeNullableAsSpecified(newNullability: Boolean) = RawTypeImpl(lowerBound.makeNullableAsSpecified(newNullability), upperBound.makeNullableAsSpecified(newNullability)) diff --git a/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/typeEnhancement/typeEnhancement.kt b/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/typeEnhancement/typeEnhancement.kt index bfd705d36ea..f2c877ba8f2 100644 --- a/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/typeEnhancement/typeEnhancement.kt +++ b/core/descriptors.jvm/src/org/jetbrains/kotlin/load/java/typeEnhancement/typeEnhancement.kt @@ -253,6 +253,7 @@ internal class NotNullTypeParameterImpl(override val delegate: SimpleType) : Not } override fun replaceAnnotations(newAnnotations: Annotations) = NotNullTypeParameterImpl(delegate.replaceAnnotations(newAnnotations)) + override fun replaceAttributes(newAttributes: TypeAttributes) = NotNullTypeParameterImpl(delegate.replaceAttributes(newAttributes)) override fun makeNullableAsSpecified(newNullability: Boolean) = if (newNullability) delegate.makeNullableAsSpecified(true) else this diff --git a/core/descriptors/src/org/jetbrains/kotlin/resolve/calls/inference/CapturedTypeConstructor.kt b/core/descriptors/src/org/jetbrains/kotlin/resolve/calls/inference/CapturedTypeConstructor.kt index 8ad85c09cbb..a2bf2f37063 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/resolve/calls/inference/CapturedTypeConstructor.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/resolve/calls/inference/CapturedTypeConstructor.kt @@ -75,7 +75,7 @@ class CapturedType( val typeProjection: TypeProjection, override val constructor: CapturedTypeConstructor = CapturedTypeConstructorImpl(typeProjection), override val isMarkedNullable: Boolean = false, - override val annotations: Annotations = Annotations.EMPTY + override val attributes: TypeAttributes = TypeAttributes.Empty ) : SimpleType(), SubtypingRepresentatives, CapturedTypeMarker { override val arguments: List get() = listOf() @@ -100,15 +100,18 @@ class CapturedType( override fun makeNullableAsSpecified(newNullability: Boolean): CapturedType { if (newNullability == isMarkedNullable) return this - return CapturedType(typeProjection, constructor, newNullability, annotations) + return CapturedType(typeProjection, constructor, newNullability, attributes) } override fun replaceAnnotations(newAnnotations: Annotations): CapturedType = - CapturedType(typeProjection, constructor, isMarkedNullable, newAnnotations) + CapturedType(typeProjection, constructor, isMarkedNullable, newAnnotations.toAttributes()) + + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = + CapturedType(typeProjection, constructor, isMarkedNullable, newAttributes) @TypeRefinement override fun refine(kotlinTypeRefiner: KotlinTypeRefiner) = - CapturedType(typeProjection.refine(kotlinTypeRefiner), constructor, isMarkedNullable, annotations) + CapturedType(typeProjection.refine(kotlinTypeRefiner), constructor, isMarkedNullable, attributes) } fun createCapturedType(typeProjection: TypeProjection): KotlinType = CapturedType(typeProjection) diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/CompilerTypeAttributes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/CompilerTypeAttributes.kt new file mode 100644 index 00000000000..47321aadfa2 --- /dev/null +++ b/core/descriptors/src/org/jetbrains/kotlin/types/CompilerTypeAttributes.kt @@ -0,0 +1,112 @@ +/* + * 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.types + +import org.jetbrains.kotlin.name.ClassId +import org.jetbrains.kotlin.name.FqName +import org.jetbrains.kotlin.name.Name +import org.jetbrains.kotlin.name.StandardClassIds +import kotlin.reflect.KClass + +object CompilerTypeAttributes { + object Exact : TypeAttribute() { + val ANNOTATION_CLASS_ID = ClassId(FqName("kotlin.internal"), Name.identifier("Exact")) + + override fun union(other: Exact?): Exact? = null + override fun intersect(other: Exact?): Exact? = null + override fun add(other: Exact?): Exact = this + + override fun isSubtypeOf(other: Exact?): Boolean = true + + override val key: KClass = Exact::class + + override fun toString(): String = "@Exact" + } + + object NoInfer : TypeAttribute() { + val ANNOTATION_CLASS_ID = ClassId(FqName("kotlin.internal"), Name.identifier("NoInfer")) + + override fun union(other: NoInfer?): NoInfer? = null + override fun intersect(other: NoInfer?): NoInfer? = null + override fun add(other: NoInfer?): NoInfer = this + override fun isSubtypeOf(other: NoInfer?): Boolean = true + + override val key: KClass = NoInfer::class + + override fun toString(): String = "@NoInfer" + } + + object EnhancedNullability : TypeAttribute() { + val ANNOTATION_CLASS_ID = StandardClassIds.Annotations.EnhancedNullability + + override fun union(other: EnhancedNullability?): EnhancedNullability? = other + override fun intersect(other: EnhancedNullability?): EnhancedNullability = this + override fun add(other: EnhancedNullability?): EnhancedNullability = this + + override fun isSubtypeOf(other: EnhancedNullability?): Boolean = true + + override val key: KClass = EnhancedNullability::class + + override fun toString(): String = "@EnhancedNullability" + } + + object ExtensionFunctionType : TypeAttribute() { + val ANNOTATION_CLASS_ID = ClassId(FqName("kotlin"), Name.identifier("ExtensionFunctionType")) + + override fun union(other: ExtensionFunctionType?): ExtensionFunctionType? = other + override fun intersect(other: ExtensionFunctionType?): ExtensionFunctionType = this + override fun add(other: ExtensionFunctionType?): ExtensionFunctionType = this + + override fun isSubtypeOf(other: ExtensionFunctionType?): Boolean = true + + override val key: KClass = ExtensionFunctionType::class + + override fun toString(): String = "@ExtensionFunctionType" + } + + object UnsafeVariance : TypeAttribute() { + val ANNOTATION_CLASS_ID = ClassId(FqName("kotlin"), Name.identifier("UnsafeVariance")) + + override fun union(other: UnsafeVariance?): UnsafeVariance? = null + override fun intersect(other: UnsafeVariance?): UnsafeVariance? = null + override fun add(other: UnsafeVariance?): UnsafeVariance = this + + override fun isSubtypeOf(other: UnsafeVariance?): Boolean = true + + override val key: KClass = UnsafeVariance::class + + override fun toString(): String = "@UnsafeVariance" + } + + val compilerAttributeByClassId: Map> = mapOf( + Exact.ANNOTATION_CLASS_ID to Exact, + NoInfer.ANNOTATION_CLASS_ID to NoInfer, + EnhancedNullability.ANNOTATION_CLASS_ID to EnhancedNullability, + ExtensionFunctionType.ANNOTATION_CLASS_ID to ExtensionFunctionType, + UnsafeVariance.ANNOTATION_CLASS_ID to UnsafeVariance + ) + + val compilerAttributeByFqName: Map> = compilerAttributeByClassId.mapKeys { it.key.asSingleFqName() } +} + +val TypeAttributes.exact: CompilerTypeAttributes.Exact? by TypeAttributes.attributeAccessor() +val TypeAttributes.noInfer: CompilerTypeAttributes.NoInfer? by TypeAttributes.attributeAccessor() +val TypeAttributes.enhancedNullability: CompilerTypeAttributes.EnhancedNullability? by TypeAttributes.attributeAccessor() +val TypeAttributes.extensionFunctionType: CompilerTypeAttributes.ExtensionFunctionType? by TypeAttributes.attributeAccessor() +val TypeAttributes.unsafeVarianceType: CompilerTypeAttributes.UnsafeVariance? by TypeAttributes.attributeAccessor() + +// ------------------------------------------------------------------ + +val TypeAttributes.hasEnhancedNullability: Boolean + get() = enhancedNullability != null + +// ------------------------------------------------------------------ + +val KotlinType.hasEnhancedNullability: Boolean + get() = attributes.enhancedNullability != null + +val KotlinType.isExtensionFunctionType: Boolean + get() = attributes.extensionFunctionType != null diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/CustomAnnotationTypeAttribute.kt b/core/descriptors/src/org/jetbrains/kotlin/types/CustomAnnotationTypeAttribute.kt new file mode 100644 index 00000000000..4fdb481128d --- /dev/null +++ b/core/descriptors/src/org/jetbrains/kotlin/types/CustomAnnotationTypeAttribute.kt @@ -0,0 +1,34 @@ +/* + * 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.types + +import org.jetbrains.kotlin.builtins.KotlinBuiltIns +import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor +import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptorImpl +import org.jetbrains.kotlin.descriptors.annotations.Annotations +import kotlin.reflect.KClass + +class CustomAnnotationTypeAttribute(val annotations: Annotations) : TypeAttribute() { + constructor(annotations: List) : this(Annotations.create(annotations)) + + override fun union(other: CustomAnnotationTypeAttribute?): CustomAnnotationTypeAttribute? = null + + override fun intersect(other: CustomAnnotationTypeAttribute?): CustomAnnotationTypeAttribute? = null + + override fun add(other: CustomAnnotationTypeAttribute?): CustomAnnotationTypeAttribute { + if (other == null) return this + return CustomAnnotationTypeAttribute(Annotations.create(annotations + other.annotations)) + } + + override fun isSubtypeOf(other: CustomAnnotationTypeAttribute?): Boolean = true + + override val key: KClass + get() = CustomAnnotationTypeAttribute::class +} + +val TypeAttributes.custom: CustomAnnotationTypeAttribute? by TypeAttributes.attributeAccessor() + +val TypeAttributes.customAnnotations: Annotations get() = custom?.annotations ?: Annotations.EMPTY diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/ErrorType.kt b/core/descriptors/src/org/jetbrains/kotlin/types/ErrorType.kt index 9ff6c8c1205..0d5ecb59154 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/ErrorType.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/ErrorType.kt @@ -30,11 +30,16 @@ open class ErrorType @JvmOverloads internal constructor( override val annotations: Annotations get() = Annotations.EMPTY + override val attributes: TypeAttributes + get() = TypeAttributes.Empty + override fun toString(): String = constructor.toString() + if (arguments.isEmpty()) "" else arguments.joinToString(", ", "<", ">", -1, "...", null) override fun replaceAnnotations(newAnnotations: Annotations): SimpleType = this + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = this + override fun makeNullableAsSpecified(newNullability: Boolean): SimpleType = ErrorType(constructor, memberScope, arguments, newNullability) diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/KotlinType.kt b/core/descriptors/src/org/jetbrains/kotlin/types/KotlinType.kt index ae46ab60409..2649ac08c7d 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/KotlinType.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/KotlinType.kt @@ -27,6 +27,7 @@ import org.jetbrains.kotlin.types.model.FlexibleTypeMarker import org.jetbrains.kotlin.types.model.KotlinTypeMarker import org.jetbrains.kotlin.types.model.SimpleTypeMarker import org.jetbrains.kotlin.types.model.TypeArgumentListMarker +import org.jetbrains.kotlin.types.typeUtil.builtIns /** * [KotlinType] has only two direct subclasses: [WrappedType] and [UnwrappedType]. @@ -51,6 +52,9 @@ sealed class KotlinType : Annotated, KotlinTypeMarker { abstract val arguments: List abstract val isMarkedNullable: Boolean abstract val memberScope: MemberScope + abstract val attributes: TypeAttributes + override val annotations: Annotations + get() = attributes.toAnnotations() abstract fun unwrap(): UnwrappedType @@ -74,7 +78,8 @@ sealed class KotlinType : Annotated, KotlinTypeMarker { abstract fun refine(kotlinTypeRefiner: KotlinTypeRefiner): KotlinType @TypeRefinement - open val hasNotTrivialRefinementFactory: Boolean get() = false + open val hasNotTrivialRefinementFactory: Boolean + get() = false /* '0' means "hashCode wasn't computed" @@ -128,6 +133,7 @@ abstract class WrappedType : KotlinType() { override val arguments: List get() = delegate.arguments override val isMarkedNullable: Boolean get() = delegate.isMarkedNullable override val memberScope: MemberScope get() = delegate.memberScope + override val attributes: TypeAttributes get() = delegate.attributes final override fun unwrap(): UnwrappedType { var result = delegate @@ -159,6 +165,7 @@ abstract class WrappedType : KotlinType() { */ sealed class UnwrappedType : KotlinType() { abstract fun replaceAnnotations(newAnnotations: Annotations): UnwrappedType + abstract fun replaceAttributes(newAttributes: TypeAttributes): UnwrappedType abstract fun makeNullableAsSpecified(newNullability: Boolean): UnwrappedType final override fun unwrap(): UnwrappedType = this @@ -174,6 +181,7 @@ sealed class UnwrappedType : KotlinType() { */ abstract class SimpleType : UnwrappedType(), SimpleTypeMarker, TypeArgumentListMarker { abstract override fun replaceAnnotations(newAnnotations: Annotations): SimpleType + abstract override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType abstract override fun makeNullableAsSpecified(newNullability: Boolean): SimpleType @TypeRefinement @@ -212,6 +220,7 @@ abstract class FlexibleType(val lowerBound: SimpleType, val upperBound: SimpleTy override val arguments: List get() = delegate.arguments override val isMarkedNullable: Boolean get() = delegate.isMarkedNullable override val memberScope: MemberScope get() = delegate.memberScope + override val attributes: TypeAttributes get() = delegate.attributes override fun toString(): String = DescriptorRenderer.DEBUG_TEXT.renderType(this) diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/KotlinTypeFactory.kt b/core/descriptors/src/org/jetbrains/kotlin/types/KotlinTypeFactory.kt index 97ae4288ae0..b63be59d348 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/KotlinTypeFactory.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/KotlinTypeFactory.kt @@ -90,6 +90,31 @@ object KotlinTypeFactory { } } + @JvmStatic + @JvmOverloads + @OptIn(TypeRefinement::class) + fun simpleType( + attributes: TypeAttributes, + constructor: TypeConstructor, + arguments: List, + nullable: Boolean, + kotlinTypeRefiner: KotlinTypeRefiner? = null + ): SimpleType { + if (attributes.isEmpty() && arguments.isEmpty() && !nullable && constructor.declarationDescriptor != null) { + return constructor.declarationDescriptor!!.defaultType + } + + return simpleTypeWithNonTrivialMemberScope( + attributes, constructor, arguments, nullable, + computeMemberScope(constructor, arguments, kotlinTypeRefiner) + ) f@{ refiner -> + val expandedTypeOrRefinedConstructor = refineConstructor(constructor, refiner, arguments) ?: return@f null + expandedTypeOrRefinedConstructor.expandedType?.let { return@f it } + + simpleType(attributes, expandedTypeOrRefinedConstructor.refinedConstructor!!, arguments, nullable, refiner) + } + } + @JvmStatic fun TypeAliasDescriptor.computeExpandedType(arguments: List): SimpleType { return TypeAliasExpander(TypeAliasExpansionReportStrategy.DO_NOTHING, false).expand( @@ -140,7 +165,34 @@ object KotlinTypeFactory { if (annotations.isEmpty()) it else - AnnotatedSimpleType(it, annotations) + SimpleTypeWithAttributes(it, annotations.toAttributes()) + } + + @JvmStatic + @OptIn(TypeRefinement::class) + fun simpleTypeWithNonTrivialMemberScope( + attributes: TypeAttributes, + constructor: TypeConstructor, + arguments: List, + nullable: Boolean, + memberScope: MemberScope + ): SimpleType = + SimpleTypeImpl(constructor, arguments, nullable, memberScope) { kotlinTypeRefiner -> + val expandedTypeOrRefinedConstructor = refineConstructor(constructor, kotlinTypeRefiner, arguments) ?: return@SimpleTypeImpl null + expandedTypeOrRefinedConstructor.expandedType?.let { return@SimpleTypeImpl it } + + simpleTypeWithNonTrivialMemberScope( + attributes, + expandedTypeOrRefinedConstructor.refinedConstructor!!, + arguments, + nullable, + memberScope + ) + }.let { + if (attributes.isEmpty()) + it + else + SimpleTypeWithAttributes(it, attributes) } @JvmStatic @@ -157,7 +209,24 @@ object KotlinTypeFactory { if (annotations.isEmpty()) it else - AnnotatedSimpleType(it, annotations) + SimpleTypeWithAttributes(it, annotations.toAttributes()) + } + + @JvmStatic + fun simpleTypeWithNonTrivialMemberScope( + attributes: TypeAttributes, + constructor: TypeConstructor, + arguments: List, + nullable: Boolean, + memberScope: MemberScope, + refinedTypeFactory: RefinedTypeFactory + ): SimpleType = + SimpleTypeImpl(constructor, arguments, nullable, memberScope, refinedTypeFactory) + .let { + if (attributes.isEmpty()) + it + else + SimpleTypeWithAttributes(it, attributes) } @JvmStatic @@ -167,6 +236,13 @@ object KotlinTypeFactory { arguments: List ): SimpleType = simpleType(annotations, descriptor.typeConstructor, arguments, nullable = false) + @JvmStatic + fun simpleNotNullType( + attributes: TypeAttributes, + descriptor: ClassDescriptor, + arguments: List + ): SimpleType = simpleType(attributes, descriptor.typeConstructor, arguments, nullable = false) + @JvmStatic fun simpleType( baseType: SimpleType, @@ -207,12 +283,18 @@ private class SimpleTypeImpl( override val hasNotTrivialRefinementFactory: Boolean get() = true override val annotations: Annotations get() = Annotations.EMPTY + override val attributes: TypeAttributes get() = TypeAttributes.Empty + + override fun replaceAttributes(newAttributes: TypeAttributes) = + if (newAttributes.isEmpty()) + this + else SimpleTypeWithAttributes(this, newAttributes) override fun replaceAnnotations(newAnnotations: Annotations) = if (newAnnotations.isEmpty()) this else - AnnotatedSimpleType(this, newAnnotations) + SimpleTypeWithAttributes(this, attributes.replaceAnnotations(newAnnotations)) override fun makeNullableAsSpecified(newNullability: Boolean) = when { newNullability == isMarkedNullable -> this @@ -243,6 +325,9 @@ class SupposititiousSimpleType(private val realType: SimpleType, val overwritten override fun replaceAnnotations(newAnnotations: Annotations): SimpleType = maybeWrap(realType.replaceAnnotations(newAnnotations)) + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = + maybeWrap(realType.replaceAttributes(newAttributes)) + override fun makeNullableAsSpecified(newNullability: Boolean): SimpleType = maybeWrap(realType.makeNullableAsSpecified(newNullability)) @@ -255,12 +340,19 @@ class SupposititiousSimpleType(private val realType: SimpleType, val overwritten override val isMarkedNullable: Boolean = realType.isMarkedNullable override val memberScope: MemberScope = realType.memberScope override val annotations: Annotations = realType.annotations + override val attributes: TypeAttributes get() = realType.attributes } abstract class DelegatingSimpleTypeImpl(override val delegate: SimpleType) : DelegatingSimpleType() { + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = + if (newAttributes !== attributes) + SimpleTypeWithAttributes(this, newAttributes) + else + this + override fun replaceAnnotations(newAnnotations: Annotations) = if (newAnnotations !== annotations) - AnnotatedSimpleType(this, newAnnotations) + SimpleTypeWithAttributes(this, attributes.replaceAnnotations(newAnnotations)) else this @@ -270,12 +362,12 @@ abstract class DelegatingSimpleTypeImpl(override val delegate: SimpleType) : Del } } -private class AnnotatedSimpleType( +private class SimpleTypeWithAttributes( delegate: SimpleType, - override val annotations: Annotations + override val attributes: TypeAttributes ) : DelegatingSimpleTypeImpl(delegate) { @TypeRefinement - override fun replaceDelegate(delegate: SimpleType) = AnnotatedSimpleType(delegate, annotations) + override fun replaceDelegate(delegate: SimpleType) = SimpleTypeWithAttributes(delegate, attributes) } private class NullableSimpleType(delegate: SimpleType) : DelegatingSimpleTypeImpl(delegate) { diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/SpecialTypes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/SpecialTypes.kt index 88bdd009736..70f8822a03c 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/SpecialTypes.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/SpecialTypes.kt @@ -35,6 +35,7 @@ abstract class DelegatingSimpleType : SimpleType() { override val arguments: List get() = delegate.arguments override val isMarkedNullable: Boolean get() = delegate.isMarkedNullable override val memberScope: MemberScope get() = delegate.memberScope + override val attributes: TypeAttributes get() = delegate.attributes @TypeRefinement abstract fun replaceDelegate(delegate: SimpleType): DelegatingSimpleType @@ -47,11 +48,14 @@ abstract class DelegatingSimpleType : SimpleType() { class AbbreviatedType(override val delegate: SimpleType, val abbreviation: SimpleType) : DelegatingSimpleType() { val expandedType: SimpleType get() = delegate - override fun replaceAnnotations(newAnnotations: Annotations) - = AbbreviatedType(delegate.replaceAnnotations(newAnnotations), abbreviation) + override fun replaceAnnotations(newAnnotations: Annotations) = + AbbreviatedType(delegate.replaceAnnotations(newAnnotations), abbreviation) - override fun makeNullableAsSpecified(newNullability: Boolean) - = AbbreviatedType(delegate.makeNullableAsSpecified(newNullability), abbreviation.makeNullableAsSpecified(newNullability)) + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = + AbbreviatedType(delegate.replaceAttributes(newAttributes), abbreviation) + + override fun makeNullableAsSpecified(newNullability: Boolean) = + AbbreviatedType(delegate.makeNullableAsSpecified(newNullability), abbreviation.makeNullableAsSpecified(newNullability)) @TypeRefinement override fun replaceDelegate(delegate: SimpleType) = AbbreviatedType(delegate, abbreviation) @@ -171,6 +175,9 @@ class DefinitelyNotNullType private constructor( override fun replaceAnnotations(newAnnotations: Annotations): DefinitelyNotNullType = DefinitelyNotNullType(delegate.replaceAnnotations(newAnnotations), useCorrectedNullabilityForTypeParameters) + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = + DefinitelyNotNullType(delegate.replaceAttributes(newAttributes), useCorrectedNullabilityForTypeParameters) + override fun makeNullableAsSpecified(newNullability: Boolean): SimpleType = if (newNullability) delegate.makeNullableAsSpecified(newNullability) else this @@ -189,7 +196,7 @@ fun SimpleType.makeSimpleTypeDefinitelyNotNullOrNotNull(useCorrectedNullabilityF ?: makeNullableAsSpecified(false) fun NewCapturedType.withNotNullProjection() = - NewCapturedType(captureStatus, constructor, lowerType, annotations, isMarkedNullable, isProjectionNotNull = true) + NewCapturedType(captureStatus, constructor, lowerType, attributes, isMarkedNullable, isProjectionNotNull = true) fun UnwrappedType.makeDefinitelyNotNullOrNotNull(useCorrectedNullabilityForTypeParameters: Boolean = false): UnwrappedType = DefinitelyNotNullType.makeDefinitelyNotNull(this, useCorrectedNullabilityForTypeParameters) diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/StubTypes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/StubTypes.kt index d51a85b5fa2..b2d4d22633f 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/StubTypes.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/StubTypes.kt @@ -61,8 +61,13 @@ abstract class AbstractStubType(val originalTypeVariable: TypeConstructor, overr override val annotations: Annotations get() = Annotations.EMPTY + override val attributes: TypeAttributes + get() = TypeAttributes.Empty + override fun replaceAnnotations(newAnnotations: Annotations): SimpleType = this + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = this + override fun makeNullableAsSpecified(newNullability: Boolean): SimpleType { return if (newNullability == isMarkedNullable) this else materialize(newNullability) } diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributes.kt new file mode 100644 index 00000000000..d71751ae2ba --- /dev/null +++ b/core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributes.kt @@ -0,0 +1,129 @@ +/* + * 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.types + +import org.jetbrains.kotlin.descriptors.annotations.Annotations +import org.jetbrains.kotlin.types.model.AnnotationMarker +import org.jetbrains.kotlin.util.AttributeArrayOwner +import org.jetbrains.kotlin.util.TypeRegistry +import org.jetbrains.kotlin.utils.addIfNotNull +import kotlin.properties.ReadOnlyProperty +import kotlin.reflect.KClass + +abstract class TypeAttribute> : AnnotationMarker { + abstract fun union(other: @UnsafeVariance T?): T? + abstract fun intersect(other: @UnsafeVariance T?): T? + + /* + * This function is used to decide how multiple attributes should be united in presence of typealiases: + * typealias B = @SomeAttribute(1) A + * typealias C = @SomeAttribute(2) B + * + * For determining attribute value of expanded type of C we should add @SomeAttribute(2) to @SomeAttribute(1) + * + * This function must be symmetrical: a.add(b) == b.add(a) + */ + abstract fun add(other: @UnsafeVariance T?): T + abstract fun isSubtypeOf(other: @UnsafeVariance T?): Boolean + + abstract val key: KClass +} + +class TypeAttributes private constructor(attributes: List>) : AttributeArrayOwner, TypeAttribute<*>>(), + Iterable> { + + companion object : TypeRegistry, TypeAttribute<*>>() { + inline fun > attributeAccessor(): ReadOnlyProperty { + @Suppress("UNCHECKED_CAST") + return generateNullableAccessor, T>(T::class) as ReadOnlyProperty + } + + val Empty: TypeAttributes = TypeAttributes(emptyList()) + val WithExtensionFunctionType: TypeAttributes = TypeAttributes(listOf(CompilerTypeAttributes.ExtensionFunctionType)) + + private val predefinedAttributes: Map, TypeAttributes> = mapOf( + CompilerTypeAttributes.EnhancedNullability.predefined() + ) + + private fun TypeAttribute<*>.predefined(): Pair, TypeAttributes> = this to TypeAttributes(this) + + fun create(attributes: List>): TypeAttributes { + return if (attributes.isEmpty()) { + Empty + } else { + TypeAttributes(attributes) + } + } + } + + private constructor(attribute: TypeAttribute<*>) : this(listOf(attribute)) + + init { + for (attribute in attributes) { + registerComponent(attribute.key, attribute) + } + } + + fun union(other: TypeAttributes): TypeAttributes { + return perform(other) { this.union(it) } + } + + fun intersect(other: TypeAttributes): TypeAttributes { + return perform(other) { this.intersect(it) } + } + + fun add(other: TypeAttributes): TypeAttributes { + return perform(other) { this.add(it) } + } + + operator fun contains(attribute: TypeAttribute<*>): Boolean { + val index = getId(attribute.key) + return arrayMap[index] != null + } + + @OptIn(ExperimentalStdlibApi::class) + operator fun plus(attribute: TypeAttribute<*>): TypeAttributes { + if (attribute in this) return this + if (isEmpty()) return predefinedAttributes[attribute] ?: TypeAttributes(attribute) + val newAttributes = buildList { + addAll(this) + add(attribute) + } + return TypeAttributes(newAttributes) + } + + fun remove(attribute: TypeAttribute<*>): TypeAttributes { + if (isEmpty()) return this + val attributes = arrayMap.filter { it != attribute } + if (attributes.size == arrayMap.size) return this + return create(attributes) + } + + private inline fun perform(other: TypeAttributes, op: TypeAttribute<*>.(TypeAttribute<*>?) -> TypeAttribute<*>?): TypeAttributes { + if (this.isEmpty() && other.isEmpty()) return this + val attributes = mutableListOf>() + for (index in indices) { + val a = arrayMap[index] + val b = other.arrayMap[index] + val res = if (a == null) b?.op(a) else a.op(b) + attributes.addIfNotNull(res) + } + return create(attributes) + } + + override val typeRegistry: TypeRegistry, TypeAttribute<*>> + get() = Companion +} + +fun TypeAttributes.toAnnotations(): Annotations = + DefaultTypeAttributesTranslator.toAnnotations(this) + +fun Annotations.toAttributes(): TypeAttributes = DefaultTypeAttributesTranslator.toAttributes(this) + +fun TypeAttributes.replaceAnnotations(newAnnotations: Annotations): TypeAttributes { + val withoutCustom = (custom?.let { this.remove(it) } ?: this) + return withoutCustom.add(newAnnotations.toAttributes()) +} diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributesTranslator.kt b/core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributesTranslator.kt new file mode 100644 index 00000000000..929830a6f05 --- /dev/null +++ b/core/descriptors/src/org/jetbrains/kotlin/types/TypeAttributesTranslator.kt @@ -0,0 +1,44 @@ +/* + * 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.types + +import org.jetbrains.kotlin.builtins.DefaultBuiltIns +import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor +import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptorImpl +import org.jetbrains.kotlin.descriptors.annotations.Annotations + +interface TypeAttributesTranslator { + fun toAttributes(annotations: Annotations): TypeAttributes + fun toAnnotations(attributes: TypeAttributes): Annotations? +} + +object DefaultTypeAttributesTranslator : TypeAttributesTranslator { + override fun toAnnotations(attributes: TypeAttributes): Annotations { + val compilerAnnotations = CompilerTypeAttributes.compilerAttributeByFqName.mapNotNull { (fqName, attribute) -> + val annotationClass = DefaultBuiltIns.Instance.getBuiltInClassByFqName(fqName) + if (attribute in attributes) + AnnotationDescriptorImpl(annotationClass.defaultType, mapOf(), annotationClass.source) + else null + } + return Annotations.create(compilerAnnotations + attributes.customAnnotations) + } + + override fun toAttributes(annotations: Annotations): TypeAttributes { + val customAnnotations = mutableListOf() + val compilerAttributes = mutableListOf>() + annotations.forEach { annotation -> + val compilerAttribute = CompilerTypeAttributes.compilerAttributeByFqName[annotation.fqName] + if (compilerAttribute != null) + compilerAttributes.add(compilerAttribute) + else + customAnnotations.add(annotation) + } + + return TypeAttributes.create( + compilerAttributes + CustomAnnotationTypeAttribute(customAnnotations) + ) + } +} diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java b/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java index 11914e2b81d..9f3b34e710a 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java +++ b/core/descriptors/src/org/jetbrains/kotlin/types/TypeUtils.java @@ -52,6 +52,12 @@ public class TypeUtils { throw new IllegalStateException(name); } + @NotNull + @Override + public SimpleType replaceAttributes(@NotNull TypeAttributes newAttributes) { + throw new IllegalStateException(name); + } + @NotNull @Override public SimpleType makeNullableAsSpecified(boolean newNullability) { diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/TypeWithEnhancement.kt b/core/descriptors/src/org/jetbrains/kotlin/types/TypeWithEnhancement.kt index 9a41986efd7..d2d89ef080c 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/TypeWithEnhancement.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/TypeWithEnhancement.kt @@ -37,6 +37,9 @@ class SimpleTypeWithEnhancement( override fun replaceAnnotations(newAnnotations: Annotations): SimpleType = origin.replaceAnnotations(newAnnotations).wrapEnhancement(enhancement) as SimpleType + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = + origin.replaceAttributes(newAttributes).wrapEnhancement(enhancement) as SimpleType + override fun makeNullableAsSpecified(newNullability: Boolean): SimpleType = origin.makeNullableAsSpecified(newNullability) .wrapEnhancement(enhancement.unwrap().makeNullableAsSpecified(newNullability)) as SimpleType @@ -64,6 +67,9 @@ class FlexibleTypeWithEnhancement( override fun replaceAnnotations(newAnnotations: Annotations): UnwrappedType = origin.replaceAnnotations(newAnnotations).wrapEnhancement(enhancement) + override fun replaceAttributes(newAttributes: TypeAttributes): UnwrappedType = + origin.replaceAttributes(newAttributes).wrapEnhancement(enhancement) + override fun makeNullableAsSpecified(newNullability: Boolean): UnwrappedType = origin.makeNullableAsSpecified(newNullability).wrapEnhancement(enhancement.unwrap().makeNullableAsSpecified(newNullability)) diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/checker/ClassicTypeSystemContext.kt b/core/descriptors/src/org/jetbrains/kotlin/types/checker/ClassicTypeSystemContext.kt index 04064096b24..d675decf34a 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/checker/ClassicTypeSystemContext.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/checker/ClassicTypeSystemContext.kt @@ -486,7 +486,7 @@ interface ClassicTypeSystemContext : TypeSystemInferenceExtensionContext, TypeSy override fun CapturedTypeMarker.withNotNullProjection(): KotlinTypeMarker { require(this is NewCapturedType, this::errorMessage) - return NewCapturedType(captureStatus, constructor, lowerType, annotations, isMarkedNullable, isProjectionNotNull = true) + return NewCapturedType(captureStatus, constructor, lowerType, attributes, isMarkedNullable, isProjectionNotNull = true) } override fun CapturedTypeMarker.isProjectionNotNull(): Boolean { diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/checker/KotlinTypePreparator.kt b/core/descriptors/src/org/jetbrains/kotlin/types/checker/KotlinTypePreparator.kt index ed38dab1eac..c068d6b1c77 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/checker/KotlinTypePreparator.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/checker/KotlinTypePreparator.kt @@ -28,7 +28,7 @@ abstract class KotlinTypePreparator : AbstractTypePreparator() { } return NewCapturedType( CaptureStatus.FOR_SUBTYPING, constructor.newTypeConstructor!!, - lowerType, type.annotations, type.isMarkedNullable + lowerType, type.attributes, type.isMarkedNullable ) } diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/checker/NewCapturedType.kt b/core/descriptors/src/org/jetbrains/kotlin/types/checker/NewCapturedType.kt index b7ec1402762..afaeab00aa4 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/checker/NewCapturedType.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/checker/NewCapturedType.kt @@ -199,7 +199,7 @@ class NewCapturedType( val captureStatus: CaptureStatus, override val constructor: NewCapturedTypeConstructor, val lowerType: UnwrappedType?, // todo check lower type for nullable captured types - override val annotations: Annotations = Annotations.EMPTY, + override val attributes: TypeAttributes = TypeAttributes.Empty, override val isMarkedNullable: Boolean = false, val isProjectionNotNull: Boolean = false ) : SimpleType(), CapturedTypeMarker { @@ -213,10 +213,13 @@ class NewCapturedType( get() = ErrorUtils.createErrorScope("No member resolution should be done on captured type!", true) override fun replaceAnnotations(newAnnotations: Annotations) = - NewCapturedType(captureStatus, constructor, lowerType, newAnnotations, isMarkedNullable) + NewCapturedType(captureStatus, constructor, lowerType, newAnnotations.toAttributes(), isMarkedNullable) + + override fun replaceAttributes(newAttributes: TypeAttributes): SimpleType = + NewCapturedType(captureStatus, constructor, lowerType, newAttributes, isMarkedNullable) override fun makeNullableAsSpecified(newNullability: Boolean) = - NewCapturedType(captureStatus, constructor, lowerType, annotations, newNullability) + NewCapturedType(captureStatus, constructor, lowerType, attributes, newNullability) @TypeRefinement override fun refine(kotlinTypeRefiner: KotlinTypeRefiner) = @@ -224,7 +227,7 @@ class NewCapturedType( captureStatus, constructor.refine(kotlinTypeRefiner), lowerType?.let { kotlinTypeRefiner.refineType(it).unwrap() }, - annotations, + attributes, isMarkedNullable ) } diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt index 54fdd815a4c..6764d8ae960 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/dynamicTypes.kt @@ -39,11 +39,11 @@ class DynamicTypesAllowed : DynamicTypesSettings() { fun KotlinType.isDynamic(): Boolean = unwrap() is DynamicType -fun createDynamicType(builtIns: KotlinBuiltIns) = DynamicType(builtIns, Annotations.EMPTY) +fun createDynamicType(builtIns: KotlinBuiltIns) = DynamicType(builtIns, TypeAttributes.Empty) class DynamicType( builtIns: KotlinBuiltIns, - override val annotations: Annotations + override val attributes: TypeAttributes ) : FlexibleType(builtIns.nothingType, builtIns.nullableAnyType), DynamicTypeMarker { override val delegate: SimpleType get() = upperBound @@ -52,7 +52,11 @@ class DynamicType( override val isMarkedNullable: Boolean get() = false - override fun replaceAnnotations(newAnnotations: Annotations): DynamicType = DynamicType(delegate.builtIns, newAnnotations) + override fun replaceAnnotations(newAnnotations: Annotations): DynamicType = + DynamicType(delegate.builtIns, attributes.replaceAnnotations(newAnnotations)) + + override fun replaceAttributes(newAttributes: TypeAttributes): DynamicType = + DynamicType(delegate.builtIns, newAttributes) override fun render(renderer: DescriptorRenderer, options: DescriptorRendererOptions): String = "dynamic" diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt b/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt index 802ad7ed1ef..d13df6e7153 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/types/flexibleTypes.kt @@ -128,6 +128,9 @@ class FlexibleTypeImpl(lowerBound: SimpleType, upperBound: SimpleType) : Flexibl override fun replaceAnnotations(newAnnotations: Annotations): UnwrappedType = KotlinTypeFactory.flexibleType(lowerBound.replaceAnnotations(newAnnotations), upperBound.replaceAnnotations(newAnnotations)) + override fun replaceAttributes(newAttributes: TypeAttributes): UnwrappedType = + KotlinTypeFactory.flexibleType(lowerBound.replaceAttributes(newAttributes), upperBound.replaceAttributes(newAttributes)) + override fun render(renderer: DescriptorRenderer, options: DescriptorRendererOptions): String { if (options.debugMode) { return "(${renderer.renderType(lowerBound)}..${renderer.renderType(upperBound)})"