From fc23cf76d4004084502c2feeeaa5b7df51269f78 Mon Sep 17 00:00:00 2001 From: Dmitriy Novozhilov Date: Wed, 14 Oct 2020 18:51:24 +0300 Subject: [PATCH] [FIR] Force calculation of return type of fake overrides in return type calculator --- .../resolve/implicitTypeInFakeOverride.kt | 4 +++ .../resolve/implicitTypeInFakeOverride.txt | 7 +++-- .../transformers/ReturnTypeCalculator.kt | 2 ++ .../body/resolve/FirImplicitBodyResolve.kt | 10 +++++++ .../fir/scopes/FakeOverrideTypeCalculator.kt | 26 +++++++++++-------- 5 files changed, 36 insertions(+), 13 deletions(-) diff --git a/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.kt b/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.kt index cc52c9cdb71..55a9517365a 100644 --- a/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.kt +++ b/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.kt @@ -3,3 +3,7 @@ fun extract(x: Out) = x.get() class Out(val x: T) { fun get() = x } + +fun test(out: Out) { + extract(out) +} diff --git a/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.txt b/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.txt index fc36dce5145..2364ecf0b80 100644 --- a/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.txt +++ b/compiler/fir/analysis-tests/testData/resolve/implicitTypeInFakeOverride.txt @@ -1,6 +1,6 @@ FILE: implicitTypeInFakeOverride.kt - public final fun extract(x: R|Out|): R|T| { - ^extract R|/x|.R|/Out.get|() + public final fun extract(x: R|Out|): R|K| { + ^extract R|/x|.R|FakeOverride|() } public final class Out : R|kotlin/Any| { public constructor(x: R|T|): R|Out| { @@ -15,3 +15,6 @@ FILE: implicitTypeInFakeOverride.kt } } + public final fun test(out: R|Out|): R|kotlin/Unit| { + R|/extract|(R|/out|) + } diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/ReturnTypeCalculator.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/ReturnTypeCalculator.kt index c64f181ee01..ac59868c603 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/ReturnTypeCalculator.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/ReturnTypeCalculator.kt @@ -9,6 +9,8 @@ import org.jetbrains.kotlin.fir.declarations.FirTypedDeclaration import org.jetbrains.kotlin.fir.diagnostics.DiagnosticKind import org.jetbrains.kotlin.fir.diagnostics.ConeSimpleDiagnostic import org.jetbrains.kotlin.fir.render +import org.jetbrains.kotlin.fir.scopes.FakeOverrideTypeCalculator +import org.jetbrains.kotlin.fir.scopes.ForcedFakeOverrideTypeCalculator import org.jetbrains.kotlin.fir.types.FirResolvedTypeRef import org.jetbrains.kotlin.fir.types.builder.buildErrorTypeRef diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirImplicitBodyResolve.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirImplicitBodyResolve.kt index 2e784ce4cfc..8c3672918cd 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirImplicitBodyResolve.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirImplicitBodyResolve.kt @@ -17,6 +17,8 @@ import org.jetbrains.kotlin.fir.resolve.ScopeSession import org.jetbrains.kotlin.fir.resolve.firProvider import org.jetbrains.kotlin.fir.resolve.transformers.* import org.jetbrains.kotlin.fir.resolve.transformers.contracts.runContractResolveForLocalClass +import org.jetbrains.kotlin.fir.scopes.ForcedFakeOverrideTypeCalculator +import org.jetbrains.kotlin.fir.symbols.PossiblyFirFakeOverrideSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirAccessorSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol import org.jetbrains.kotlin.fir.types.FirImplicitTypeRef @@ -25,6 +27,7 @@ import org.jetbrains.kotlin.fir.types.builder.buildErrorTypeRef import org.jetbrains.kotlin.fir.visitors.CompositeTransformResult import org.jetbrains.kotlin.fir.visitors.FirTransformer import org.jetbrains.kotlin.fir.visitors.compose +import org.jetbrains.kotlin.utils.addToStdlib.runIf @OptIn(AdapterForResolveProcessor::class) class FirImplicitTypeBodyResolveProcessor( @@ -216,6 +219,13 @@ private class ReturnTypeCalculatorWithJump( return result } + runIf(declaration.origin == FirDeclarationOrigin.FakeOverride) { + val possiblyFirFakeOverrideSymbol = declaration.symbol as PossiblyFirFakeOverrideSymbol<*, *> + val overriddenDeclaration = possiblyFirFakeOverrideSymbol.overriddenSymbol?.fir as FirTypedDeclaration? ?: return@runIf + tryCalculateReturnType(overriddenDeclaration) + return ForcedFakeOverrideTypeCalculator.computeReturnType(declaration) + } + return when (val status = implicitBodyResolveComputationSession.getStatus(declaration.symbol)) { is ImplicitBodyResolveComputationStatus.Computed -> status.resolvedTypeRef is ImplicitBodyResolveComputationStatus.Computing -> diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/FakeOverrideTypeCalculator.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/FakeOverrideTypeCalculator.kt index 4b066df0907..c95592b157d 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/FakeOverrideTypeCalculator.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/FakeOverrideTypeCalculator.kt @@ -10,28 +10,32 @@ import org.jetbrains.kotlin.fir.declarations.FirDeclarationDataKey import org.jetbrains.kotlin.fir.declarations.FirDeclarationDataRegistry import org.jetbrains.kotlin.fir.declarations.FirTypedDeclaration import org.jetbrains.kotlin.fir.resolve.substitution.ConeSubstitutor +import org.jetbrains.kotlin.fir.resolvedTypeFromPrototype import org.jetbrains.kotlin.fir.symbols.AbstractFirBasedSymbol -import org.jetbrains.kotlin.fir.types.ConeKotlinType -import org.jetbrains.kotlin.fir.types.coneTypeSafe +import org.jetbrains.kotlin.fir.types.FirResolvedTypeRef +import org.jetbrains.kotlin.fir.types.FirTypeRef abstract class FakeOverrideTypeCalculator { - abstract fun computeReturnType(declaration: FirTypedDeclaration): ConeKotlinType? + abstract fun computeReturnType(declaration: FirTypedDeclaration): FirTypeRef - class DoNothing : FakeOverrideTypeCalculator() { - override fun computeReturnType(declaration: FirTypedDeclaration): ConeKotlinType? { - return declaration.returnTypeRef.coneTypeSafe() + object DoNothing : FakeOverrideTypeCalculator() { + override fun computeReturnType(declaration: FirTypedDeclaration): FirTypeRef { + return declaration.returnTypeRef } } } -class ForcedFakeOverrideTypeCalculator : FakeOverrideTypeCalculator() { - override fun computeReturnType(declaration: FirTypedDeclaration): ConeKotlinType { - declaration.returnTypeRef.coneTypeSafe()?.let { return it } +object ForcedFakeOverrideTypeCalculator : FakeOverrideTypeCalculator() { + override fun computeReturnType(declaration: FirTypedDeclaration): FirResolvedTypeRef { + (declaration.returnTypeRef as? FirResolvedTypeRef)?.let { return it } val (substitutor, baseSymbol) = declaration.attributes.fakeOverrideSubstitution ?: error("") val baseDeclaration = baseSymbol.fir as FirTypedDeclaration - val returnType = computeReturnType(baseDeclaration) + val baseReturnType = computeReturnType(baseDeclaration).type declaration.attributes.fakeOverrideSubstitution = null - return substitutor.substituteOrSelf(returnType) + val coneType = substitutor.substituteOrSelf(baseReturnType) + val returnType = declaration.returnTypeRef.resolvedTypeFromPrototype(coneType) + declaration.replaceReturnTypeRef(returnType) + return returnType } }