[FIR] Use default language settings in inference components

Without settings common inference components require additional parameters
to be passed explicitly from components not shared between FIR and FE10.
Proper configuration can be postponed in FIR, defaults are good enough for now.

^KT-42080 In progress
This commit is contained in:
Pavel Kirpichenkov
2020-09-28 14:48:33 +03:00
parent dba1b50aed
commit 8f31b1ca83
12 changed files with 30 additions and 70 deletions
@@ -30,8 +30,10 @@ import org.jetbrains.kotlin.utils.addIfNotNull
import org.jetbrains.kotlin.utils.addToStdlib.safeAs
class ConstraintSystemCompleter(private val components: BodyResolveComponents) {
val inferenceComponents = components.session.inferenceComponents
val variableFixationFinder = VariableFixationFinder(inferenceComponents.trivialConstraintTypeInferenceOracle)
private val inferenceComponents
get() = components.session.inferenceComponents
val variableFixationFinder
get() = inferenceComponents.variableFixationFinder
fun complete(
c: ConstraintSystemCompletionContext,
@@ -50,7 +52,7 @@ class ConstraintSystemCompleter(private val components: BodyResolveComponents) {
val postponedAtoms = getOrderedNotAnalyzedPostponedArguments(topLevelAtoms)
val variableForFixation =
variableFixationFinder.findFirstVariableForFixation(
c, allTypeVariables, postponedAtoms, completionMode, candidateReturnType, inferenceCompatibilityMode = true
c, allTypeVariables, postponedAtoms, completionMode, candidateReturnType
) ?: break
if (
@@ -5,22 +5,21 @@
package org.jetbrains.kotlin.fir.resolve.inference
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.config.LanguageVersionSettingsImpl
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.FirSessionComponent
import org.jetbrains.kotlin.fir.NoMutableState
import org.jetbrains.kotlin.fir.types.ConeInferenceContext
import org.jetbrains.kotlin.fir.types.ConeTypeCheckerContext
import org.jetbrains.kotlin.resolve.calls.inference.InferenceCompatibilityChecker
import org.jetbrains.kotlin.resolve.calls.inference.components.ConstraintIncorporator
import org.jetbrains.kotlin.resolve.calls.inference.components.ConstraintInjector
import org.jetbrains.kotlin.resolve.calls.inference.components.ResultTypeResolver
import org.jetbrains.kotlin.resolve.calls.inference.components.TrivialConstraintTypeInferenceOracle
import org.jetbrains.kotlin.resolve.calls.inference.components.*
import org.jetbrains.kotlin.resolve.calls.inference.model.NewConstraintSystemImpl
import org.jetbrains.kotlin.types.AbstractTypeApproximator
@NoMutableState
class InferenceComponents(val session: FirSession) : FirSessionComponent {
val ctx: ConeTypeCheckerContext = ConeTypeCheckerContext(isErrorTypeEqualsToAnything = false, isStubTypeEqualsToAnything = false, session)
val languageVersionSettings: LanguageVersionSettings = LanguageVersionSettingsImpl.DEFAULT // TODO
val approximator: AbstractTypeApproximator = object : AbstractTypeApproximator(ctx) {}
val trivialConstraintTypeInferenceOracle = TrivialConstraintTypeInferenceOracle.create(ctx)
@@ -28,14 +27,14 @@ class InferenceComponents(val session: FirSession) : FirSessionComponent {
private val injector = ConstraintInjector(
incorporator,
approximator,
object : InferenceCompatibilityChecker {
override val isCompatibilityModeEnabled = true
}
languageVersionSettings,
)
val resultTypeResolver = ResultTypeResolver(approximator, trivialConstraintTypeInferenceOracle)
val constraintSystemFactory = ConstraintSystemFactory()
val variableFixationFinder = VariableFixationFinder(trivialConstraintTypeInferenceOracle, languageVersionSettings)
fun createConstraintSystem(): NewConstraintSystemImpl {
return NewConstraintSystemImpl(injector, ctx)
}
@@ -8,7 +8,6 @@ package org.jetbrains.kotlin.resolve
import org.jetbrains.kotlin.builtins.PlatformToKotlinClassMapper
import org.jetbrains.kotlin.container.*
import org.jetbrains.kotlin.resolve.calls.checkers.*
import org.jetbrains.kotlin.resolve.calls.inference.InferenceCompatibilityCheckerImpl
import org.jetbrains.kotlin.resolve.calls.results.TypeSpecificityComparator
import org.jetbrains.kotlin.resolve.checkers.*
import org.jetbrains.kotlin.resolve.lazy.DelegationFilter
@@ -110,7 +109,6 @@ abstract class PlatformConfiguratorBase(
override fun configureModuleDependentCheckers(container: StorageComponentContainer) {
container.useImpl<ExperimentalMarkerDeclarationAnnotationChecker>()
container.useImpl<InferenceCompatibilityCheckerImpl>()
}
fun configureExtensionsAndCheckers(container: StorageComponentContainer) {
@@ -82,12 +82,9 @@ class CoroutineInferenceSession(
return !storage.notFixedTypeVariables.keys.any {
val variable = storage.allTypeVariables[it]
val isPostponed = variable != null && variable in storage.postponedTypeVariables
val useInferenceCompatibilityMode =
topLevelCallContext.languageVersionSettings.supportsFeature(LanguageFeature.InferenceCompatibility)
!isPostponed && !kotlinConstraintSystemCompleter.variableFixationFinder.isTypeVariableHasProperConstraint(
system,
it,
useInferenceCompatibilityMode
)
} || candidate.getSubResolvedAtoms().any { it.hasPostponed() }
}
@@ -5,6 +5,7 @@ plugins {
dependencies {
api(project(":core:compiler.common"))
api(project(":compiler:util"))
}
sourceSets {
@@ -1,10 +0,0 @@
/*
* Copyright 2010-2020 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.resolve.calls.inference
interface InferenceCompatibilityChecker {
val isCompatibilityModeEnabled: Boolean
}
@@ -6,8 +6,9 @@
package org.jetbrains.kotlin.resolve.calls.inference.components
import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.resolve.calls.inference.ConstraintSystemOperation
import org.jetbrains.kotlin.resolve.calls.inference.InferenceCompatibilityChecker
import org.jetbrains.kotlin.resolve.calls.inference.model.*
import org.jetbrains.kotlin.resolve.calls.inference.model.ConstraintKind.*
import org.jetbrains.kotlin.types.AbstractTypeApproximator
@@ -21,7 +22,7 @@ import kotlin.math.max
class ConstraintInjector(
val constraintIncorporator: ConstraintIncorporator,
val typeApproximator: AbstractTypeApproximator,
val inferenceCompatibilityChecker: InferenceCompatibilityChecker
private val languageVersionSettings: LanguageVersionSettings,
) {
private val ALLOWED_DEPTH_DELTA_FOR_INCORPORATION = 1
@@ -131,7 +132,7 @@ class ConstraintInjector(
// We use `var` intentionally to avoid extra allocations as this property is quite "hot"
private var possibleNewConstraints: MutableList<Pair<TypeVariableMarker, Constraint>>? = null
override val isInferenceCompatibilityEnabled = inferenceCompatibilityChecker.isCompatibilityModeEnabled
override val isInferenceCompatibilityEnabled = languageVersionSettings.supportsFeature(LanguageFeature.InferenceCompatibility)
private var baseLowerType = position.initialConstraint.a
private var baseUpperType = position.initialConstraint.b
@@ -5,6 +5,8 @@
package org.jetbrains.kotlin.resolve.calls.inference.components
import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.resolve.calls.inference.components.ConstraintSystemCompletionMode.PARTIAL
import org.jetbrains.kotlin.resolve.calls.inference.model.Constraint
import org.jetbrains.kotlin.resolve.calls.inference.model.DeclaredUpperBoundConstraintPosition
@@ -13,7 +15,8 @@ import org.jetbrains.kotlin.resolve.calls.model.PostponedResolvedAtomMarker
import org.jetbrains.kotlin.types.model.*
class VariableFixationFinder(
private val trivialConstraintTypeInferenceOracle: TrivialConstraintTypeInferenceOracle
private val trivialConstraintTypeInferenceOracle: TrivialConstraintTypeInferenceOracle,
private val languageVersionSettings: LanguageVersionSettings,
) {
interface Context : TypeSystemInferenceExtensionContext {
val notFixedTypeVariables: Map<TypeConstructorMarker, VariableWithConstraints>
@@ -33,9 +36,7 @@ class VariableFixationFinder(
postponedKtPrimitives: List<PostponedResolvedAtomMarker>,
completionMode: ConstraintSystemCompletionMode,
topLevelType: KotlinTypeMarker,
inferenceCompatibilityMode: Boolean = false,
): VariableForFixation? =
c.findTypeVariableForFixation(allTypeVariables, postponedKtPrimitives, completionMode, topLevelType, inferenceCompatibilityMode)
): VariableForFixation? = c.findTypeVariableForFixation(allTypeVariables, postponedKtPrimitives, completionMode, topLevelType)
enum class TypeVariableFixationReadiness {
FORBIDDEN,
@@ -50,10 +51,12 @@ class VariableFixationFinder(
READY_FOR_FIXATION_REIFIED,
}
private val inferenceCompatibilityModeEnabled: Boolean
get() = languageVersionSettings.supportsFeature(LanguageFeature.InferenceCompatibility)
private fun Context.getTypeVariableReadiness(
variable: TypeConstructorMarker,
dependencyProvider: TypeVariableDependencyInformationProvider,
inferenceCompatibilityMode: Boolean
): TypeVariableFixationReadiness = when {
!notFixedTypeVariables.contains(variable) ||
dependencyProvider.isVariableRelatedToTopLevelType(variable) -> TypeVariableFixationReadiness.FORBIDDEN
@@ -64,7 +67,7 @@ class VariableFixationFinder(
variableHasOnlyIncorporatedConstraintsFromDeclaredUpperBound(variable) ->
TypeVariableFixationReadiness.FROM_INCORPORATION_OF_DECLARED_UPPER_BOUND
isReified(variable) -> TypeVariableFixationReadiness.READY_FOR_FIXATION_REIFIED
inferenceCompatibilityMode -> {
inferenceCompatibilityModeEnabled -> {
when {
variableHasLowerProperConstraint(variable) -> TypeVariableFixationReadiness.READY_FOR_FIXATION_LOWER
else -> TypeVariableFixationReadiness.READY_FOR_FIXATION_UPPER
@@ -76,13 +79,12 @@ class VariableFixationFinder(
fun isTypeVariableHasProperConstraint(
context: Context,
typeVariable: TypeConstructorMarker,
inferenceCompatibilityMode: Boolean = false
): Boolean {
return with(context) {
val dependencyProvider = TypeVariableDependencyInformationProvider(
notFixedTypeVariables, emptyList(), topLevelType = null, context
)
when (getTypeVariableReadiness(typeVariable, dependencyProvider, inferenceCompatibilityMode)) {
when (getTypeVariableReadiness(typeVariable, dependencyProvider)) {
TypeVariableFixationReadiness.FORBIDDEN, TypeVariableFixationReadiness.WITHOUT_PROPER_ARGUMENT_CONSTRAINT -> false
else -> true
}
@@ -107,7 +109,6 @@ class VariableFixationFinder(
postponedArguments: List<PostponedResolvedAtomMarker>,
completionMode: ConstraintSystemCompletionMode,
topLevelType: KotlinTypeMarker,
inferenceCompatibilityMode: Boolean,
): VariableForFixation? {
if (allTypeVariables.isEmpty()) return null
@@ -116,9 +117,9 @@ class VariableFixationFinder(
)
val candidate =
allTypeVariables.maxByOrNull { getTypeVariableReadiness(it, dependencyProvider, inferenceCompatibilityMode) } ?: return null
allTypeVariables.maxByOrNull { getTypeVariableReadiness(it, dependencyProvider) } ?: return null
return when (getTypeVariableReadiness(candidate, dependencyProvider, inferenceCompatibilityMode)) {
return when (getTypeVariableReadiness(candidate, dependencyProvider)) {
TypeVariableFixationReadiness.FORBIDDEN -> null
TypeVariableFixationReadiness.WITHOUT_PROPER_ARGUMENT_CONSTRAINT -> VariableForFixation(candidate, false)
TypeVariableFixationReadiness.WITH_TRIVIAL_OR_NON_PROPER_CONSTRAINTS ->
@@ -1,14 +0,0 @@
/*
* Copyright 2010-2020 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.resolve.calls.inference
import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings
class InferenceCompatibilityCheckerImpl(val languageVersionSettings: LanguageVersionSettings) : InferenceCompatibilityChecker {
override val isCompatibilityModeEnabled: Boolean
get() = languageVersionSettings.getFeatureSupport(LanguageFeature.InferenceCompatibility) == LanguageFeature.State.ENABLED
}
@@ -5,8 +5,6 @@
package org.jetbrains.kotlin.resolve.calls.inference.components
import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings
import org.jetbrains.kotlin.resolve.calls.components.transformToResolvedLambda
import org.jetbrains.kotlin.resolve.calls.inference.model.*
import org.jetbrains.kotlin.resolve.calls.model.*
@@ -21,7 +19,6 @@ import org.jetbrains.kotlin.utils.addToStdlib.safeAs
class KotlinConstraintSystemCompleter(
private val resultTypeResolver: ResultTypeResolver,
val variableFixationFinder: VariableFixationFinder,
val languageVersionSettings: LanguageVersionSettings,
) {
private val postponedArgumentInputTypesResolver = PostponedArgumentInputTypesResolver(resultTypeResolver, variableFixationFinder)
@@ -108,7 +105,6 @@ class KotlinConstraintSystemCompleter(
topLevelType,
topLevelAtoms,
dependencyProvider,
inferenceCompatibilityMode = isInferenceCompatibilityModeEnabled(),
)
if (wasFixedSomeVariable)
@@ -262,7 +258,6 @@ class KotlinConstraintSystemCompleter(
postponedArguments,
completionMode,
topLevelType,
inferenceCompatibilityMode = isInferenceCompatibilityModeEnabled(),
) ?: break
if (!variableForFixation.hasProperConstraint && completionMode == ConstraintSystemCompletionMode.PARTIAL)
@@ -373,12 +368,8 @@ class KotlinConstraintSystemCompleter(
postponedArguments,
completionMode,
topLevelType,
inferenceCompatibilityMode = isInferenceCompatibilityModeEnabled(),
) != null
private fun isInferenceCompatibilityModeEnabled(): Boolean =
languageVersionSettings.supportsFeature(LanguageFeature.InferenceCompatibility)
companion object {
fun getOrderedNotAnalyzedPostponedArguments(topLevelAtoms: List<ResolvedAtom>): List<PostponedResolvedAtom> {
fun ResolvedAtom.process(to: MutableList<PostponedResolvedAtom>) {
@@ -455,7 +455,6 @@ class PostponedArgumentInputTypesResolver(
topLevelType: UnwrappedType,
topLevelAtoms: List<ResolvedAtom>,
dependencyProvider: TypeVariableDependencyInformationProvider,
inferenceCompatibilityMode: Boolean = false,
): Boolean {
val expectedType = argument.run { safeAs<PostponedAtomWithRevisableExpectedType>()?.revisedExpectedType ?: expectedType }
@@ -467,7 +466,6 @@ class PostponedArgumentInputTypesResolver(
topLevelType,
topLevelAtoms,
dependencyProvider,
inferenceCompatibilityMode
)
if (wasFixedSomeVariable)
@@ -483,12 +481,11 @@ class PostponedArgumentInputTypesResolver(
topLevelType: UnwrappedType,
topLevelAtoms: List<ResolvedAtom>,
dependencyProvider: TypeVariableDependencyInformationProvider,
inferenceCompatibilityMode: Boolean,
): Boolean {
val relatedVariables = type.getPureArgumentsForFunctionalTypeOrSubtype()
.flatMap { getAllDeeplyRelatedTypeVariables(it, dependencyProvider) }
val variableForFixation = variableFixationFinder.findFirstVariableForFixation(
this, relatedVariables, postponedArguments, ConstraintSystemCompletionMode.FULL, topLevelType, inferenceCompatibilityMode
this, relatedVariables, postponedArguments, ConstraintSystemCompletionMode.FULL, topLevelType
)
if (variableForFixation == null || !variableForFixation.hasProperConstraint)
@@ -23,7 +23,6 @@ import org.jetbrains.kotlin.frontend.di.configureStandardResolveComponents
import org.jetbrains.kotlin.frontend.java.di.configureJavaSpecificComponents
import org.jetbrains.kotlin.frontend.java.di.initializeJavaSpecificComponents
import org.jetbrains.kotlin.idea.project.IdeaEnvironment
import org.jetbrains.kotlin.incremental.components.LookupTracker
import org.jetbrains.kotlin.load.java.lazy.ModuleClassResolver
import org.jetbrains.kotlin.load.java.lazy.ModuleClassResolverImpl
import org.jetbrains.kotlin.load.kotlin.PackagePartProvider
@@ -36,7 +35,6 @@ import org.jetbrains.kotlin.platform.jvm.JvmPlatform
import org.jetbrains.kotlin.platform.konan.NativePlatform
import org.jetbrains.kotlin.platform.konan.NativePlatforms
import org.jetbrains.kotlin.resolve.*
import org.jetbrains.kotlin.resolve.calls.inference.InferenceCompatibilityCheckerImpl
import org.jetbrains.kotlin.resolve.checkers.ExperimentalMarkerDeclarationAnnotationChecker
import org.jetbrains.kotlin.resolve.jvm.JavaDescriptorResolver
import org.jetbrains.kotlin.resolve.jvm.JvmPlatformParameters
@@ -254,6 +252,5 @@ class CompositePlatformConigurator(private val componentConfigurators: List<Plat
// Unfortunately, it is declared in base class, so repeating call to 'configureModuleDependentCheckers' will lead
// to multiple registrrations.
container.useImpl<ExperimentalMarkerDeclarationAnnotationChecker>()
container.useImpl<InferenceCompatibilityCheckerImpl>()
}
}