From 30c97e6cb46f9a95d6ae2e76aa30596163b907ab Mon Sep 17 00:00:00 2001 From: Jinseong Jeon Date: Fri, 20 Nov 2020 15:49:04 -0800 Subject: [PATCH] FIR: update unsubstituted return types in builder #KT-43340 Fixed --- .../inference/FirBuilderInferenceSession.kt | 30 ++++++++++--- .../typeVariableAfterBuildMap.fir.txt | 45 ++++++++++--------- .../castsInsideCoroutineInference.fir.txt | 2 +- 3 files changed, 51 insertions(+), 26 deletions(-) diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/inference/FirBuilderInferenceSession.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/inference/FirBuilderInferenceSession.kt index efe53431a2b8d..1f995e9b6d69c 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/inference/FirBuilderInferenceSession.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/inference/FirBuilderInferenceSession.kt @@ -5,15 +5,13 @@ package org.jetbrains.kotlin.fir.resolve.inference +import org.jetbrains.kotlin.fir.expressions.FirFunctionCall import org.jetbrains.kotlin.fir.expressions.FirResolvable import org.jetbrains.kotlin.fir.expressions.FirStatement import org.jetbrains.kotlin.fir.resolve.calls.Candidate import org.jetbrains.kotlin.fir.resolve.calls.ResolutionContext import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor -import org.jetbrains.kotlin.fir.types.ConeKotlinType -import org.jetbrains.kotlin.fir.types.ConeStubType -import org.jetbrains.kotlin.fir.types.ConeTypeVariable -import org.jetbrains.kotlin.fir.types.ConeTypeVariableTypeConstructor +import org.jetbrains.kotlin.fir.types.* import org.jetbrains.kotlin.fir.visitors.transformSingle import org.jetbrains.kotlin.resolve.calls.inference.buildAbstractResultingSubstitutor import org.jetbrains.kotlin.resolve.calls.inference.components.ConstraintSystemCompletionMode @@ -203,11 +201,33 @@ class FirBuilderInferenceSession( val commonSystemSubstitutor = commonSystem.buildCurrentSubstitutor() as ConeSubstitutor val nonFixedTypesToResultSubstitutor = ConeComposedSubstitutor(commonSystemSubstitutor, nonFixedToVariablesSubstitutor) val completionResultsWriter = components.callCompleter.createCompletionResultsWriter(nonFixedTypesToResultSubstitutor) + + for ((completedCall, _) in commonCalls) { + // TODO: Only update return type? Should we need to visit all appearances of unsubstituted postponed variables in types? + // [transformSingle] bails out very early since the completed call is literally completed, and not a named reference. + (completedCall as? FirFunctionCall)?.let { call -> + val resultType = call.typeRef.substituteTypeRef(nonFixedTypesToResultSubstitutor) + if (resultType != call.typeRef) { + call.replaceTypeRef(resultType) + } + } + // TODO: support diagnostics, see [CoroutineInferenceSession#updateCalls] + } + for ((call, _) in partiallyResolvedCalls) { call.transformSingle(completionResultsWriter, null) - // TODO: support diagnostics, see CoroutineInferenceSession.kt:286 + // TODO: support diagnostics, see [CoroutineInferenceSession#updateCalls] } } + + private fun FirTypeRef.substituteTypeRef( + substitutor: ConeSubstitutor, + ): FirTypeRef = + (this as? FirResolvedTypeRef)?.let { + substitutor.substituteOrNull(this.type)?.let { + this.withReplacedConeType(it) + } + } ?: this } class ConeComposedSubstitutor(val left: ConeSubstitutor, val right: ConeSubstitutor) : ConeSubstitutor() { diff --git a/compiler/testData/ir/irText/firProblems/typeVariableAfterBuildMap.fir.txt b/compiler/testData/ir/irText/firProblems/typeVariableAfterBuildMap.fir.txt index 6e20e8a46782d..5891084312987 100644 --- a/compiler/testData/ir/irText/firProblems/typeVariableAfterBuildMap.fir.txt +++ b/compiler/testData/ir/irText/firProblems/typeVariableAfterBuildMap.fir.txt @@ -552,27 +552,32 @@ FILE fqName: fileName:/typeVariableAfterBuildMap.kt FUN LOCAL_FUNCTION_FOR_LAMBDA name: visibility:local modality:FINAL <> ($receiver:kotlin.collections.MutableMap<.Visibility, kotlin.Int>) returnType:kotlin.Unit $receiver: VALUE_PARAMETER name: type:kotlin.collections.MutableMap<.Visibility, kotlin.Int> BLOCK_BODY - CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=IrErrorType origin=null - $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null - key: GET_OBJECT 'CLASS OBJECT name:PrivateToThis modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.PrivateToThis - value: CONST Int type=kotlin.Int value=0 - CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=IrErrorType origin=null - $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null - key: GET_OBJECT 'CLASS OBJECT name:Private modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Private - value: CONST Int type=kotlin.Int value=0 - CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=IrErrorType origin=null - $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null - key: GET_OBJECT 'CLASS OBJECT name:Internal modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Internal - value: CONST Int type=kotlin.Int value=1 - CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=IrErrorType origin=null - $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null - key: GET_OBJECT 'CLASS OBJECT name:Protected modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Protected - value: CONST Int type=kotlin.Int value=1 - RETURN type=kotlin.Nothing from='local final fun (): kotlin.Unit declared in .Visibilities.ORDERED_VISIBILITIES' - CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=IrErrorType origin=null + TYPE_OP type=kotlin.Unit origin=IMPLICIT_COERCION_TO_UNIT typeOperand=kotlin.Unit + CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=kotlin.Int? origin=null + $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null + key: GET_OBJECT 'CLASS OBJECT name:PrivateToThis modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.PrivateToThis + value: CONST Int type=kotlin.Int value=0 + TYPE_OP type=kotlin.Unit origin=IMPLICIT_COERCION_TO_UNIT typeOperand=kotlin.Unit + CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=kotlin.Int? origin=null + $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null + key: GET_OBJECT 'CLASS OBJECT name:Private modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Private + value: CONST Int type=kotlin.Int value=0 + TYPE_OP type=kotlin.Unit origin=IMPLICIT_COERCION_TO_UNIT typeOperand=kotlin.Unit + CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=kotlin.Int? origin=null $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null - key: GET_OBJECT 'CLASS OBJECT name:Public modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Public - value: CONST Int type=kotlin.Int value=2 + key: GET_OBJECT 'CLASS OBJECT name:Internal modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Internal + value: CONST Int type=kotlin.Int value=1 + TYPE_OP type=kotlin.Unit origin=IMPLICIT_COERCION_TO_UNIT typeOperand=kotlin.Unit + CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=kotlin.Int? origin=null + $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null + key: GET_OBJECT 'CLASS OBJECT name:Protected modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Protected + value: CONST Int type=kotlin.Int value=1 + RETURN type=kotlin.Nothing from='local final fun (): kotlin.Unit declared in .Visibilities.ORDERED_VISIBILITIES' + TYPE_OP type=kotlin.Unit origin=IMPLICIT_COERCION_TO_UNIT typeOperand=kotlin.Unit + CALL 'public abstract fun put (key: K of kotlin.collections.MutableMap, value: V of kotlin.collections.MutableMap): V of kotlin.collections.MutableMap? declared in kotlin.collections.MutableMap' type=kotlin.Int? origin=null + $this: GET_VAR ': kotlin.collections.MutableMap<.Visibility, kotlin.Int> declared in .Visibilities.ORDERED_VISIBILITIES.' type=kotlin.collections.MutableMap origin=null + key: GET_OBJECT 'CLASS OBJECT name:Public modality:FINAL visibility:public superTypes:[.Visibility]' type=.Visibilities.Public + value: CONST Int type=kotlin.Int value=2 FUN DEFAULT_PROPERTY_ACCESSOR name: visibility:private modality:FINAL <> ($this:.Visibilities) returnType:kotlin.collections.Map<.Visibility, kotlin.Int> correspondingProperty: PROPERTY name:ORDERED_VISIBILITIES visibility:private modality:FINAL [val] $this: VALUE_PARAMETER name: type:.Visibilities diff --git a/compiler/testData/ir/irText/types/castsInsideCoroutineInference.fir.txt b/compiler/testData/ir/irText/types/castsInsideCoroutineInference.fir.txt index 1da9b222f7e03..a804528e8516d 100644 --- a/compiler/testData/ir/irText/types/castsInsideCoroutineInference.fir.txt +++ b/compiler/testData/ir/irText/types/castsInsideCoroutineInference.fir.txt @@ -39,7 +39,7 @@ FILE fqName: fileName:/castsInsideCoroutineInference.kt $receiver: VALUE_PARAMETER name: type:.FlowCollector.onCompletion> BLOCK_BODY VAR name:safeCollector type:.SafeCollector [val] - CONSTRUCTOR_CALL 'public constructor (collector: .FlowCollector.SafeCollector>) [primary] declared in .SafeCollector' type=.SafeCollector origin=null + CONSTRUCTOR_CALL 'public constructor (collector: .FlowCollector.SafeCollector>) [primary] declared in .SafeCollector' type=.SafeCollector.onCompletion> origin=null : IrErrorType collector: GET_VAR ': .FlowCollector.onCompletion> declared in .onCompletion.' type=.FlowCollector origin=null CALL 'public final fun invokeSafely (action: @[ExtensionFunctionType] @[ExtensionFunctionType] kotlin.coroutines.SuspendFunction2<.FlowCollector.invokeSafely>, kotlin.Throwable?, kotlin.Unit>): kotlin.Unit [suspend] declared in ' type=kotlin.Unit origin=null