From ef5ac7df939b93d1a697df8d7d2d819461cfa73c Mon Sep 17 00:00:00 2001 From: Dmitriy Novozhilov Date: Tue, 10 Sep 2019 12:00:49 +0300 Subject: [PATCH] [FIR] Don't create member function for each when and try expression Use one function (per session) instead --- .../kotlin/fir/resolve/calls/Synthetics.kt | 3 +- .../transformers/FirSyntheticCallGenerator.kt | 77 ++++++++----------- .../fir/resolve/transformers/PhaseUtils.kt | 1 - 3 files changed, 32 insertions(+), 49 deletions(-) diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/Synthetics.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/Synthetics.kt index 4c591c2ffaa..15e61a6ac69 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/Synthetics.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/Synthetics.kt @@ -26,8 +26,7 @@ interface SyntheticSymbol : ConeSymbol class SyntheticPropertySymbol(callableId: CallableId) : FirPropertySymbol(callableId), SyntheticSymbol class FirSyntheticFunctionSymbol( - callableId: CallableId, - val file: FirFile + callableId: CallableId ) : FirNamedFunctionSymbol(callableId), SyntheticSymbol class FirSyntheticPropertiesScope( diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/FirSyntheticCallGenerator.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/FirSyntheticCallGenerator.kt index 0f2b1223bf1..5071e654b8e 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/FirSyntheticCallGenerator.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/FirSyntheticCallGenerator.kt @@ -19,6 +19,7 @@ import org.jetbrains.kotlin.fir.expressions.FirWhenExpression import org.jetbrains.kotlin.fir.references.FirStubReference import org.jetbrains.kotlin.fir.resolve.BodyResolveComponents import org.jetbrains.kotlin.fir.resolve.calls.* +import org.jetbrains.kotlin.fir.symbols.CallableId import org.jetbrains.kotlin.fir.symbols.SyntheticCallableId import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol @@ -31,14 +32,19 @@ import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind import org.jetbrains.kotlin.types.Variance class FirSyntheticCallGenerator(private val transformer: FirBodyResolveTransformer) : BodyResolveComponents by transformer { + private val whenSelectFunction: FirMemberFunctionImpl = generateSyntheticSelectFunction(SyntheticCallableId.WHEN) + private val trySelectFunction: FirMemberFunctionImpl = generateSyntheticSelectFunction(SyntheticCallableId.TRY) + fun generateCalleeForWhenExpression(whenExpression: FirWhenExpression): FirWhenExpression? { val stubReference = whenExpression.calleeReference assert(stubReference is FirStubReference) - val function = generateWhenCallDeclaration() - val arguments = whenExpression.branches.map { it.result } - val reference = generateCalleeReferenceWithCandidate(function, arguments, SyntheticCallableId.WHEN.callableName) ?: return null // TODO + val reference = generateCalleeReferenceWithCandidate( + whenSelectFunction, + arguments, + SyntheticCallableId.WHEN.callableName + ) ?: return null // TODO return whenExpression.copy(calleeReference = reference) } @@ -47,61 +53,24 @@ class FirSyntheticCallGenerator(private val transformer: FirBodyResolveTransform val stubReference = tryExpression.calleeReference assert(stubReference is FirStubReference) - val function = generateTryCallDeclaration(tryExpression) val arguments = mutableListOf() with(tryExpression) { arguments += tryBlock - catches.map { + catches.forEach { arguments += it.block } } - val reference = generateCalleeReferenceWithCandidate(function, arguments, SyntheticCallableId.TRY.callableName) ?: return null // TODO + val reference = generateCalleeReferenceWithCandidate( + trySelectFunction, + arguments, + SyntheticCallableId.TRY.callableName + ) ?: return null // TODO return tryExpression.copy(calleeReference = reference) } - private fun generateTryCallDeclaration(tryExpression: FirTryExpression): FirMemberFunctionImpl { - val functionSymbol = FirSyntheticFunctionSymbol(SyntheticCallableId.TRY, file) - val typeParameterSymbol = FirTypeParameterSymbol() - val typeParameter = FirTypeParameterImpl(session, null, typeParameterSymbol, Name.identifier("K"), Variance.INVARIANT, false) - - val returnType = FirResolvedTypeRefImpl(null, ConeTypeParameterTypeImpl(typeParameterSymbol.toLookupTag(), false)) - - val tryType = FirResolvedTypeRefImpl(null, returnType.coneTypeUnsafe()) - val catchTypes = tryExpression.catches.map { - FirResolvedTypeRefImpl(null, returnType.coneTypeUnsafe()) - } - - val typeArgument = FirTypeProjectionWithVarianceImpl(null, Variance.INVARIANT, returnType) - - return generateMemberFunction(session, functionSymbol, SyntheticCallableId.TRY.callableName, typeArgument.typeRef).apply { - typeParameters += typeParameter - - valueParameters += tryType.toValueParameter(session, "tryBlock") - catchTypes.forEachIndexed { i, type -> - valueParameters += type.toValueParameter(session, "catchBlock_$i") - } - } - } - - private fun generateWhenCallDeclaration(): FirMemberFunctionImpl { - val functionSymbol = FirSyntheticFunctionSymbol(SyntheticCallableId.WHEN, file) - val typeParameterSymbol = FirTypeParameterSymbol() - val typeParameter = FirTypeParameterImpl(session, null, typeParameterSymbol, Name.identifier("K"), Variance.INVARIANT, false) - - val returnType = FirResolvedTypeRefImpl(null, ConeTypeParameterTypeImpl(typeParameterSymbol.toLookupTag(), false)) - val branchType = FirResolvedTypeRefImpl(null, returnType.coneTypeUnsafe().createArrayOf(session)) - - val typeArgument = FirTypeProjectionWithVarianceImpl(null, Variance.INVARIANT, returnType) - - return generateMemberFunction(session, functionSymbol, SyntheticCallableId.WHEN.callableName, typeArgument.typeRef).apply { - typeParameters += typeParameter - valueParameters += branchType.toValueParameter(session, "branches", true) - } - } - private fun generateCalleeReferenceWithCandidate( function: FirMemberFunctionImpl, arguments: List, @@ -136,6 +105,22 @@ class FirSyntheticCallGenerator(private val transformer: FirBodyResolveTransform container = container ) { it.resultType } + private fun generateSyntheticSelectFunction(callableId: CallableId): FirMemberFunctionImpl { + val functionSymbol = FirSyntheticFunctionSymbol(callableId) + val typeParameterSymbol = FirTypeParameterSymbol() + val typeParameter = FirTypeParameterImpl(session, null, typeParameterSymbol, Name.identifier("K"), Variance.INVARIANT, false) + + val returnType = FirResolvedTypeRefImpl(null, ConeTypeParameterTypeImpl(typeParameterSymbol.toLookupTag(), false)) + + val argumentType = FirResolvedTypeRefImpl(null, returnType.coneTypeUnsafe().createArrayOf(session)) + val typeArgument = FirTypeProjectionWithVarianceImpl(null, Variance.INVARIANT, returnType) + + return generateMemberFunction(session, functionSymbol, callableId.callableName, typeArgument.typeRef).apply { + typeParameters += typeParameter + valueParameters += argumentType.toValueParameter(session, "branches", isVararg = true) + } + } + private fun generateMemberFunction(session: FirSession, symbol: FirNamedFunctionSymbol, name: Name, returnType: FirTypeRef) = FirMemberFunctionImpl( session = session, diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/PhaseUtils.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/PhaseUtils.kt index f4d6c0b09d3..1f0d0fa7f7c 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/PhaseUtils.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/PhaseUtils.kt @@ -25,7 +25,6 @@ fun AbstractFirBasedSymbol.phasedFir( if (availablePhase < requiredPhase) { val provider = FirProvider.getInstance(session) val containingFile = when (this) { - is FirSyntheticFunctionSymbol -> file is ConeCallableSymbol -> provider.getFirCallableContainerFile(this) is ConeClassLikeSymbol -> provider.getFirClassifierContainerFile(this) else -> null