FIR checkers: use isNullableType() instead of isSubtypeOfAny()
This commit is contained in:
@@ -40,7 +40,6 @@ import org.jetbrains.kotlin.psi.KtModifierList
|
|||||||
import org.jetbrains.kotlin.psi.KtParameter
|
import org.jetbrains.kotlin.psi.KtParameter
|
||||||
import org.jetbrains.kotlin.psi.KtParameter.VAL_VAR_TOKEN_SET
|
import org.jetbrains.kotlin.psi.KtParameter.VAL_VAR_TOKEN_SET
|
||||||
import org.jetbrains.kotlin.psi.psiUtil.visibilityModifierType
|
import org.jetbrains.kotlin.psi.psiUtil.visibilityModifierType
|
||||||
import org.jetbrains.kotlin.types.AbstractTypeChecker
|
|
||||||
import org.jetbrains.kotlin.utils.addToStdlib.safeAs
|
import org.jetbrains.kotlin.utils.addToStdlib.safeAs
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -128,7 +127,7 @@ fun ConeKotlinType.toRegularClass(session: FirSession): FirRegularClass? {
|
|||||||
return safeAs<ConeClassLikeType>()?.fullyExpandedType(session)?.toRegularClass(session)
|
return safeAs<ConeClassLikeType>()?.fullyExpandedType(session)?.toRegularClass(session)
|
||||||
}
|
}
|
||||||
|
|
||||||
fun ConeKotlinType.isInline(session: FirSession) : Boolean = toRegularClass(session)?.isInline == true
|
fun ConeKotlinType.isInline(session: FirSession): Boolean = toRegularClass(session)?.isInline == true
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the FirRegularClass associated with this
|
* Returns the FirRegularClass associated with this
|
||||||
@@ -144,7 +143,7 @@ fun FirTypeRef.toRegularClass(session: FirSession): FirRegularClass? {
|
|||||||
inline fun <reified T : Any> FirQualifiedAccessExpression.getDeclaration(): T? {
|
inline fun <reified T : Any> FirQualifiedAccessExpression.getDeclaration(): T? {
|
||||||
return this.calleeReference.safeAs<FirResolvedNamedReference>()
|
return this.calleeReference.safeAs<FirResolvedNamedReference>()
|
||||||
?.resolvedSymbol
|
?.resolvedSymbol
|
||||||
?.fir.safeAs<T>()
|
?.fir.safeAs()
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -154,17 +153,6 @@ inline fun <reified T : Any> FirQualifiedAccessExpression.getDeclaration(): T? {
|
|||||||
fun FirSymbolOwner<*>.getContainingClass(context: CheckerContext): FirClassLikeDeclaration<*>? =
|
fun FirSymbolOwner<*>.getContainingClass(context: CheckerContext): FirClassLikeDeclaration<*>? =
|
||||||
this.safeAs<FirCallableMemberDeclaration<*>>()?.containingClass()?.toSymbol(context.session)?.fir
|
this.safeAs<FirCallableMemberDeclaration<*>>()?.containingClass()?.toSymbol(context.session)?.fir
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the FirClassLikeDeclaration the type alias is pointing
|
|
||||||
* to provided `this` is a FirTypeAlias. Returns this otherwise.
|
|
||||||
*/
|
|
||||||
fun FirClassLikeDeclaration<*>.followAlias(session: FirSession): FirClassLikeDeclaration<*> {
|
|
||||||
return this.safeAs<FirTypeAlias>()
|
|
||||||
?.expandedTypeRef
|
|
||||||
?.firClassLike(session)
|
|
||||||
?: return this
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the FirClassLikeDeclaration that the
|
* Returns the FirClassLikeDeclaration that the
|
||||||
* sequence of FirTypeAlias'es points to starting
|
* sequence of FirTypeAlias'es points to starting
|
||||||
@@ -320,10 +308,6 @@ fun Modality.toToken(): KtModifierKeywordToken = when (this) {
|
|||||||
val FirFunctionCall.isIterator
|
val FirFunctionCall.isIterator
|
||||||
get() = this.calleeReference.name.asString() == "<iterator>"
|
get() = this.calleeReference.name.asString() == "<iterator>"
|
||||||
|
|
||||||
fun ConeKotlinType.isSubtypeOfAny(session: FirSession): Boolean {
|
|
||||||
return AbstractTypeChecker.isSubtypeOf(session.typeContext, this.fullyExpandedType(session), session.builtinTypes.anyType.type)
|
|
||||||
}
|
|
||||||
|
|
||||||
internal fun throwableClassLikeType(session: FirSession) = session.builtinTypes.throwableType.type
|
internal fun throwableClassLikeType(session: FirSession) = session.builtinTypes.throwableType.type
|
||||||
|
|
||||||
fun ConeKotlinType.isSubtypeOfThrowable(session: FirSession) =
|
fun ConeKotlinType.isSubtypeOfThrowable(session: FirSession) =
|
||||||
|
|||||||
+8
-7
@@ -6,14 +6,13 @@
|
|||||||
package org.jetbrains.kotlin.fir.analysis.checkers.declaration
|
package org.jetbrains.kotlin.fir.analysis.checkers.declaration
|
||||||
|
|
||||||
import org.jetbrains.kotlin.fir.FirFakeSourceElementKind
|
import org.jetbrains.kotlin.fir.FirFakeSourceElementKind
|
||||||
import org.jetbrains.kotlin.fir.FirSession
|
|
||||||
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
||||||
import org.jetbrains.kotlin.fir.analysis.checkers.isSubtypeOfAny
|
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.DiagnosticReporter
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.DiagnosticReporter
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.reportOn
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.reportOn
|
||||||
import org.jetbrains.kotlin.fir.declarations.*
|
import org.jetbrains.kotlin.fir.declarations.*
|
||||||
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeTypeParameterInQualifiedAccess
|
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeTypeParameterInQualifiedAccess
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.inference.inferenceComponents
|
||||||
import org.jetbrains.kotlin.fir.resolve.inference.isKClassType
|
import org.jetbrains.kotlin.fir.resolve.inference.isKClassType
|
||||||
import org.jetbrains.kotlin.fir.scopes.impl.toConeType
|
import org.jetbrains.kotlin.fir.scopes.impl.toConeType
|
||||||
import org.jetbrains.kotlin.fir.types.*
|
import org.jetbrains.kotlin.fir.types.*
|
||||||
@@ -40,7 +39,7 @@ object FirKClassWithIncorrectTypeArgumentChecker : FirFileChecker() {
|
|||||||
if (source.kind is FirFakeSourceElementKind) return
|
if (source.kind is FirFakeSourceElementKind) return
|
||||||
|
|
||||||
val returnType = declaration.returnTypeRef.coneType
|
val returnType = declaration.returnTypeRef.coneType
|
||||||
if (!returnType.isKClassTypeWithErrorOrNullableArgument(context.session)) return
|
if (!returnType.isKClassTypeWithErrorOrNullableArgument(context.session.inferenceComponents.ctx)) return
|
||||||
|
|
||||||
val typeArgument = (returnType.typeArguments[0] as ConeKotlinTypeProjection).type
|
val typeArgument = (returnType.typeArguments[0] as ConeKotlinTypeProjection).type
|
||||||
typeArgument.typeParameterFromError?.let {
|
typeArgument.typeParameterFromError?.let {
|
||||||
@@ -48,7 +47,7 @@ object FirKClassWithIncorrectTypeArgumentChecker : FirFileChecker() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun ConeKotlinType.isKClassTypeWithErrorOrNullableArgument(session: FirSession): Boolean {
|
private fun ConeKotlinType.isKClassTypeWithErrorOrNullableArgument(context: ConeInferenceContext): Boolean {
|
||||||
if (!this.isKClassType()) return false
|
if (!this.isKClassType()) return false
|
||||||
val argumentType = typeArguments.toList().singleOrNull()?.let {
|
val argumentType = typeArguments.toList().singleOrNull()?.let {
|
||||||
when (it) {
|
when (it) {
|
||||||
@@ -56,10 +55,12 @@ object FirKClassWithIncorrectTypeArgumentChecker : FirFileChecker() {
|
|||||||
is ConeKotlinTypeProjection -> it.type
|
is ConeKotlinTypeProjection -> it.type
|
||||||
}
|
}
|
||||||
} ?: return false
|
} ?: return false
|
||||||
argumentType.typeParameterFromError?.let { typeParameter ->
|
with(context) {
|
||||||
return !typeParameter.toConeType().isSubtypeOfAny(session)
|
argumentType.typeParameterFromError?.let { typeParameter ->
|
||||||
|
return typeParameter.toConeType().isNullableType()
|
||||||
|
}
|
||||||
|
return argumentType is ConeKotlinErrorType || argumentType.isNullableType()
|
||||||
}
|
}
|
||||||
return argumentType is ConeKotlinErrorType || !argumentType.isSubtypeOfAny(session)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private val ConeKotlinType.typeParameterFromError: FirTypeParameter?
|
private val ConeKotlinType.typeParameterFromError: FirTypeParameter?
|
||||||
|
|||||||
+8
-7
@@ -6,9 +6,7 @@
|
|||||||
package org.jetbrains.kotlin.fir.analysis.checkers.expression
|
package org.jetbrains.kotlin.fir.analysis.checkers.expression
|
||||||
|
|
||||||
import org.jetbrains.kotlin.fir.FirFakeSourceElementKind
|
import org.jetbrains.kotlin.fir.FirFakeSourceElementKind
|
||||||
import org.jetbrains.kotlin.fir.FirSession
|
|
||||||
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext
|
||||||
import org.jetbrains.kotlin.fir.analysis.checkers.isSubtypeOfAny
|
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.DiagnosticReporter
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.DiagnosticReporter
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors
|
||||||
import org.jetbrains.kotlin.fir.analysis.diagnostics.reportOn
|
import org.jetbrains.kotlin.fir.analysis.diagnostics.reportOn
|
||||||
@@ -17,6 +15,7 @@ import org.jetbrains.kotlin.fir.declarations.FirTypeParameter
|
|||||||
import org.jetbrains.kotlin.fir.declarations.FirTypeParameterRefsOwner
|
import org.jetbrains.kotlin.fir.declarations.FirTypeParameterRefsOwner
|
||||||
import org.jetbrains.kotlin.fir.expressions.*
|
import org.jetbrains.kotlin.fir.expressions.*
|
||||||
import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference
|
import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.inference.inferenceComponents
|
||||||
import org.jetbrains.kotlin.fir.scopes.impl.toConeType
|
import org.jetbrains.kotlin.fir.scopes.impl.toConeType
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol
|
||||||
import org.jetbrains.kotlin.fir.types.*
|
import org.jetbrains.kotlin.fir.types.*
|
||||||
@@ -42,7 +41,7 @@ object FirGetClassCallChecker : FirBasicExpressionChecker() {
|
|||||||
val isNullable = markedNullable ||
|
val isNullable = markedNullable ||
|
||||||
(argument as? FirResolvedQualifier)?.isNullableLHSForCallableReference == true ||
|
(argument as? FirResolvedQualifier)?.isNullableLHSForCallableReference == true ||
|
||||||
argument.typeRef.coneType.isMarkedNullable ||
|
argument.typeRef.coneType.isMarkedNullable ||
|
||||||
argument.typeRef.coneType.isNullableTypeParameter(context.session)
|
argument.typeRef.coneType.isNullableTypeParameter(context.session.inferenceComponents.ctx)
|
||||||
if (isNullable) {
|
if (isNullable) {
|
||||||
if (argument.canBeDoubleColonLHSAsType) {
|
if (argument.canBeDoubleColonLHSAsType) {
|
||||||
reporter.reportOn(source, FirErrors.NULLABLE_TYPE_IN_CLASS_LITERAL_LHS, context)
|
reporter.reportOn(source, FirErrors.NULLABLE_TYPE_IN_CLASS_LITERAL_LHS, context)
|
||||||
@@ -78,12 +77,14 @@ object FirGetClassCallChecker : FirBasicExpressionChecker() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun ConeKotlinType.isNullableTypeParameter(session: FirSession): Boolean {
|
private fun ConeKotlinType.isNullableTypeParameter(context: ConeInferenceContext): Boolean {
|
||||||
if (this !is ConeTypeParameterType) return false
|
if (this !is ConeTypeParameterType) return false
|
||||||
val typeParameter = lookupTag.typeParameterSymbol.fir
|
val typeParameter = lookupTag.typeParameterSymbol.fir
|
||||||
return !typeParameter.isReified &&
|
with(context) {
|
||||||
// E.g., fun <T> f2(t: T): Any = t::class
|
return !typeParameter.isReified &&
|
||||||
!typeParameter.toConeType().isSubtypeOfAny(session)
|
// E.g., fun <T> f2(t: T): Any = t::class
|
||||||
|
typeParameter.toConeType().isNullableType()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private val FirExpression.canBeDoubleColonLHSAsType: Boolean
|
private val FirExpression.canBeDoubleColonLHSAsType: Boolean
|
||||||
|
|||||||
Reference in New Issue
Block a user