New J2K: calculate type correctly for vararg parameter in nullability analysis

This commit is contained in:
Ilya Kirillov
2019-05-29 14:11:38 +03:00
parent 419f6c80de
commit d6e07ca693
2 changed files with 22 additions and 10 deletions
@@ -10,6 +10,7 @@ import org.jetbrains.kotlin.descriptors.CallableDescriptor
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.TypeParameterDescriptor
import org.jetbrains.kotlin.idea.caches.resolve.analyze
import org.jetbrains.kotlin.idea.references.mainReference
import org.jetbrains.kotlin.nj2k.postProcessing.resolve
import org.jetbrains.kotlin.psi.*
import org.jetbrains.kotlin.psi.psiUtil.getNextSiblingIgnoringWhitespace
@@ -97,8 +98,24 @@ internal class BoundTypeStorage(private val analysisAnalysisContext: AnalysisCon
analysisAnalysisContext.declarationToTypeVariable[it]
} ?: KtPsiUtil.deparenthesize(this)?.let { analysisAnalysisContext.declarationToTypeVariable[it] }
private fun KtExpression.toBoundTypeAsTypeVariable(): BoundType? =
resolveToTypeVariable()?.let { TypeVariableBoundType(it, getForcedNullability()) }
private fun KtExpression.toBoundTypeAsTypeVariable(): BoundType? {
val typeVariableBoundType = resolveToTypeVariable()?.let {
TypeVariableBoundType(it, null)
} ?: return null
val asReferenceToVarArgParameter =
safeAs<KtNameReferenceExpression>()
?.mainReference
?.resolve()
?.safeAs<KtParameter>()
?.takeIf { it.isVarArg }
return if (asReferenceToVarArgParameter != null) {
GenericBoundType(
UnknownClassReference("Array"),//TODO
listOf(BoundTypeTypeParameter(typeVariableBoundType, Variance.INVARIANT)),
isNull = false
)
} else typeVariableBoundType
}
private fun KtExpression.toBoundTypeAsCallExpression(contextBoundType: BoundType?): BoundType? {
val typeElement = getCalleeExpressionIfAny()
@@ -135,12 +152,9 @@ internal class BoundTypeStorage(private val analysisAnalysisContext: AnalysisCon
}
private fun KtExpression.toBoundType(contextBoundType: BoundType?): BoundType? =
run {
toBoundTypeAsTypeVariable()?.also { return@run it }
toBoundTypeAsCallExpression(contextBoundType)?.also { return@run it }
toBoundTypeAsCastExpression()?.also { return@run it }
return@run null
}?.withForcedNullability(getForcedNullability())
toBoundTypeAsTypeVariable()
?: toBoundTypeAsCallExpression(contextBoundType)
?: toBoundTypeAsCastExpression()
private fun KotlinType.toBoundType(
contextBoundType: BoundType?,
@@ -20,7 +20,6 @@ internal class ConstraintBuilder(val boundTypeStorage: BoundTypeStorage) {
fun KtExpression.addEqualsNullabilityConstraint(nullability: Nullability, cameFrom: ConstraintCameFrom) {
val boundType = boundTypeStorage.boundTypeFor(this).safeAs<TypeVariableBoundType>()
?.withForcedNullability(getForcedNullability())
?: return
constraints += EqualConstraint(boundType.bound, LiteralBound(nullability), cameFrom)
}
@@ -35,7 +34,6 @@ internal class ConstraintBuilder(val boundTypeStorage: BoundTypeStorage) {
fun KtExpression.addSubtypeNullabilityConstraint(upperBoundType: BoundType, cameFrom: ConstraintCameFrom) {
boundTypeStorage.boundTypeFor(this)
.withForcedNullability(getForcedNullability())
.subtypeOf(upperBoundType, cameFrom)
}