FIR IDE: always approximate non-denotable types for creating PsiType
This commit is contained in:
+24
-16
@@ -73,26 +73,34 @@ private fun ConeKotlinType.simplifyType(
|
||||
currentType = currentType.fullyExpandedType(session)
|
||||
currentType = currentType.upperBoundIfFlexible()
|
||||
currentType = substitutor.substituteOrSelf(currentType)
|
||||
if (shouldHideLocalType(visibilityForApproximation, isInlineFunction)) {
|
||||
val localTypes: List<ConeKotlinType> = if (isLocal(session)) listOf(this) else {
|
||||
typeArguments.mapNotNull {
|
||||
if (it is ConeKotlinTypeProjection && it.type.isLocal(session)) {
|
||||
it.type
|
||||
} else null
|
||||
}
|
||||
}
|
||||
val unavailableLocalTypes = localTypes.filterNot { it.isLocalButAvailableAtPosition(session, useSitePosition) }
|
||||
// Need to approximate if there are local types that are not available in this scope
|
||||
val needsApproximation = localTypes.isNotEmpty() && unavailableLocalTypes.isNotEmpty()
|
||||
if (needsApproximation) {
|
||||
// TODO: can we approximate local types in type arguments *selectively* ?
|
||||
currentType = PublicTypeApproximator.approximateTypeToPublicDenotable(currentType, session) ?: currentType
|
||||
}
|
||||
}
|
||||
val needLocalTypeApproximation = needLocalTypeApproximation(visibilityForApproximation, isInlineFunction, session, useSitePosition)
|
||||
// TODO: can we approximate local types in type arguments *selectively* ?
|
||||
currentType = PublicTypeApproximator.approximateTypeToPublicDenotable(currentType, session, needLocalTypeApproximation)
|
||||
?: currentType
|
||||
|
||||
} while (oldType !== currentType)
|
||||
return currentType
|
||||
}
|
||||
|
||||
private fun ConeKotlinType.needLocalTypeApproximation(
|
||||
visibilityForApproximation: Visibility,
|
||||
isInlineFunction: Boolean,
|
||||
session: FirSession,
|
||||
useSitePosition: PsiElement
|
||||
): Boolean {
|
||||
if (!shouldHideLocalType(visibilityForApproximation, isInlineFunction)) return false
|
||||
val localTypes: List<ConeKotlinType> = if (isLocal(session)) listOf(this) else {
|
||||
typeArguments.mapNotNull {
|
||||
if (it is ConeKotlinTypeProjection && it.type.isLocal(session)) {
|
||||
it.type
|
||||
} else null
|
||||
}
|
||||
}
|
||||
val unavailableLocalTypes = localTypes.filterNot { it.isLocalButAvailableAtPosition(session, useSitePosition) }
|
||||
// Need to approximate if there are local types that are not available in this scope
|
||||
return localTypes.isNotEmpty() && unavailableLocalTypes.isNotEmpty()
|
||||
}
|
||||
|
||||
// Mimic FirDeclaration.visibilityForApproximation
|
||||
private val PsiElement.visibilityForApproximation: Visibility
|
||||
get() {
|
||||
|
||||
+2
-1
@@ -59,7 +59,8 @@ internal class KtFirTypeProvider(
|
||||
val coneType = type.coneType
|
||||
val approximatedConeType = PublicTypeApproximator.approximateTypeToPublicDenotable(
|
||||
coneType,
|
||||
rootModuleSession
|
||||
rootModuleSession,
|
||||
approximateLocalTypes = true,
|
||||
)
|
||||
|
||||
return approximatedConeType?.asKtType()
|
||||
|
||||
+1
-1
@@ -50,7 +50,7 @@ internal class FirIdeRenderer private constructor(
|
||||
require(firRef is FirResolvedTypeRef)
|
||||
|
||||
val approximatedIfNeeded = approximate.ifTrue {
|
||||
PublicTypeApproximator.approximateTypeToPublicDenotable(firRef.coneType, session)
|
||||
PublicTypeApproximator.approximateTypeToPublicDenotable(firRef.coneType, session, approximateLocalTypes = true)
|
||||
} ?: firRef.coneType
|
||||
val annotations = if (RendererModifier.ANNOTATIONS in options.modifiers) {
|
||||
firRef.annotations
|
||||
|
||||
+5
-3
@@ -14,17 +14,19 @@ internal object PublicTypeApproximator {
|
||||
fun approximateTypeToPublicDenotable(
|
||||
type: ConeKotlinType,
|
||||
session: FirSession,
|
||||
approximateLocalTypes: Boolean
|
||||
): ConeKotlinType? {
|
||||
val approximator = session.typeApproximator
|
||||
return approximator.approximateToSuperType(type, PublicApproximatorConfiguration)
|
||||
return approximator.approximateToSuperType(type, PublicApproximatorConfiguration(approximateLocalTypes))
|
||||
}
|
||||
|
||||
private object PublicApproximatorConfiguration : TypeApproximatorConfiguration.AllFlexibleSameValue() {
|
||||
private class PublicApproximatorConfiguration(
|
||||
override val localTypes: Boolean
|
||||
) : TypeApproximatorConfiguration.AllFlexibleSameValue() {
|
||||
override val allFlexible: Boolean get() = false
|
||||
override val errorType: Boolean get() = true
|
||||
override val definitelyNotNullType: Boolean get() = false
|
||||
override val integerLiteralType: Boolean get() = true
|
||||
override val intersectionTypesInContravariantPositions: Boolean get() = true
|
||||
override val localTypes: Boolean get() = true
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user