FIR inference: implement simple constraint system properly
This commit is contained in:
committed by
Mikhail Glukhikh
parent
ddb08777d9
commit
b02b090bdf
+27
-3
@@ -8,7 +8,10 @@ package org.jetbrains.kotlin.fir.resolve.calls
|
||||
import org.jetbrains.kotlin.fir.declarations.FirCallableDeclaration
|
||||
import org.jetbrains.kotlin.fir.declarations.FirConstructor
|
||||
import org.jetbrains.kotlin.fir.declarations.FirNamedFunction
|
||||
import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutorByMap
|
||||
import org.jetbrains.kotlin.fir.resolve.transformers.firUnsafe
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol
|
||||
import org.jetbrains.kotlin.fir.types.ConeKotlinType
|
||||
import org.jetbrains.kotlin.fir.types.coneTypeUnsafe
|
||||
import org.jetbrains.kotlin.resolve.OverloadabilitySpecificityCallbacks
|
||||
import org.jetbrains.kotlin.resolve.calls.inference.model.NewConstraintSystemImpl
|
||||
@@ -21,6 +24,7 @@ import org.jetbrains.kotlin.types.model.KotlinTypeMarker
|
||||
import org.jetbrains.kotlin.types.model.TypeParameterMarker
|
||||
import org.jetbrains.kotlin.types.model.TypeSubstitutorMarker
|
||||
import org.jetbrains.kotlin.types.model.TypeSystemInferenceExtensionContext
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.cast
|
||||
|
||||
class ConeOverloadConflictResolver(
|
||||
val specificityComparator: TypeSpecificityComparator,
|
||||
@@ -73,7 +77,8 @@ class ConeOverloadConflictResolver(
|
||||
return FlatSignature(
|
||||
call,
|
||||
function.typeParameters.map { it.symbol },
|
||||
call.argumentMapping!!.map { it.value.returnTypeRef.coneTypeUnsafe() },
|
||||
listOfNotNull<ConeKotlinType>(function.receiverTypeRef?.coneTypeUnsafe()) +
|
||||
call.argumentMapping!!.map { it.value.returnTypeRef.coneTypeUnsafe() },
|
||||
function.receiverTypeRef != null,
|
||||
function.valueParameters.any { it.isVararg },
|
||||
function.valueParameters.count { it.defaultValue != null },
|
||||
@@ -199,8 +204,24 @@ class ConeOverloadConflictResolver(
|
||||
object NoSubstitutor : TypeSubstitutorMarker
|
||||
|
||||
class ConeSimpleConstraintSystemImpl(val system: NewConstraintSystemImpl) : SimpleConstraintSystem {
|
||||
override fun registerTypeVariables(typeParameters: Collection<TypeParameterMarker>): TypeSubstitutorMarker {
|
||||
return NoSubstitutor
|
||||
override fun registerTypeVariables(typeParameters: Collection<TypeParameterMarker>): TypeSubstitutorMarker = with(context) {
|
||||
val csBuilder = system.getBuilder()
|
||||
val substitutionMap = typeParameters.associate {
|
||||
require(it is FirTypeParameterSymbol)
|
||||
val variable = TypeParameterBasedTypeVariable(it)
|
||||
csBuilder.registerVariable(variable)
|
||||
|
||||
|
||||
it to variable.defaultType
|
||||
}
|
||||
val substitutor = ConeSubstitutorByMap(substitutionMap.cast())
|
||||
for (typeParameter in typeParameters) {
|
||||
require(typeParameter is FirTypeParameterSymbol)
|
||||
for (upperBound in typeParameter.fir.bounds) {
|
||||
addSubtypeConstraint(substitutionMap[typeParameter]!!, substitutor.substituteOrSelf(upperBound.coneTypeUnsafe()))
|
||||
}
|
||||
}
|
||||
return substitutor
|
||||
}
|
||||
|
||||
override fun addSubtypeConstraint(subType: KotlinTypeMarker, superType: KotlinTypeMarker) {
|
||||
@@ -209,6 +230,9 @@ class ConeSimpleConstraintSystemImpl(val system: NewConstraintSystemImpl) : Simp
|
||||
|
||||
override fun hasContradiction(): Boolean = system.hasContradiction
|
||||
|
||||
override val captureFromArgument: Boolean
|
||||
get() = true
|
||||
|
||||
override val context: TypeSystemInferenceExtensionContext
|
||||
get() = system
|
||||
|
||||
|
||||
+2
-1
@@ -10,9 +10,10 @@ import org.jetbrains.kotlin.fir.symbols.ConeTypeParameterSymbol
|
||||
import org.jetbrains.kotlin.fir.types.*
|
||||
import org.jetbrains.kotlin.fir.types.impl.ConeAbbreviatedTypeImpl
|
||||
import org.jetbrains.kotlin.fir.types.impl.ConeClassTypeImpl
|
||||
import org.jetbrains.kotlin.types.model.TypeSubstitutorMarker
|
||||
|
||||
|
||||
interface ConeSubstitutor {
|
||||
interface ConeSubstitutor : TypeSubstitutorMarker {
|
||||
fun substituteOrSelf(type: ConeKotlinType): ConeKotlinType
|
||||
fun substituteOrNull(type: ConeKotlinType): ConeKotlinType?
|
||||
|
||||
|
||||
@@ -28,9 +28,9 @@ FILE: components.kt
|
||||
lval y: R|kotlin/String| = R|<local>/<destruct>|.R|/D.component2|()
|
||||
}
|
||||
|
||||
lval <destruct>: <ERROR TYPE REF: Ambiguity: first, [kotlin/collections/first, kotlin/collections/first]> = R|<local>/list|.<Ambiguity: first, [kotlin/collections/first, kotlin/collections/first]>#()
|
||||
lval x: <ERROR TYPE REF: Ambiguity: component1, [kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1, kotlin/collections/component1]> = R|<local>/<destruct>|.component1()
|
||||
lval y: <ERROR TYPE REF: Ambiguity: component2, [kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2, kotlin/collections/component2]> = R|<local>/<destruct>|.component2()
|
||||
lval <destruct>: R|D| = R|<local>/list|.R|kotlin/collections/first|<R|D|>()
|
||||
lval x: R|kotlin/Int| = R|<local>/<destruct>|.R|/D.component1|()
|
||||
lval y: R|kotlin/String| = R|<local>/<destruct>|.R|/D.component2|()
|
||||
R|<local>/list|.R|kotlin/collections/forEach|<R|D|>(<L> = forEach@fun <anonymous>(<destruct>: R|D|): R|kotlin/Unit| {
|
||||
lval x: R|kotlin/Int| = R|<local>/<destruct>|.R|/D.component1|()
|
||||
lval y: R|kotlin/String| = R|<local>/<destruct>|.R|/D.component2|()
|
||||
|
||||
Reference in New Issue
Block a user