FIR: Simplify delegating constructors call resolution
This commit is contained in:
+30
-5
@@ -7,7 +7,11 @@ package org.jetbrains.kotlin.fir.resolve.calls.tower
|
|||||||
|
|
||||||
import org.jetbrains.kotlin.fir.resolve.BodyResolveComponents
|
import org.jetbrains.kotlin.fir.resolve.BodyResolveComponents
|
||||||
import org.jetbrains.kotlin.fir.resolve.calls.*
|
import org.jetbrains.kotlin.fir.resolve.calls.*
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.scope
|
||||||
|
import org.jetbrains.kotlin.fir.typeContext
|
||||||
import org.jetbrains.kotlin.fir.types.ConeClassLikeType
|
import org.jetbrains.kotlin.fir.types.ConeClassLikeType
|
||||||
|
import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind
|
||||||
|
import org.jetbrains.kotlin.types.AbstractTypeChecker
|
||||||
|
|
||||||
class FirTowerResolver(
|
class FirTowerResolver(
|
||||||
private val components: BodyResolveComponents,
|
private val components: BodyResolveComponents,
|
||||||
@@ -32,14 +36,35 @@ class FirTowerResolver(
|
|||||||
|
|
||||||
fun runResolverForDelegatingConstructor(
|
fun runResolverForDelegatingConstructor(
|
||||||
info: CallInfo,
|
info: CallInfo,
|
||||||
constructedType: ConeClassLikeType,
|
constructedType: ConeClassLikeType
|
||||||
): CandidateCollector {
|
): CandidateCollector {
|
||||||
val candidateFactoriesAndCollectors = buildCandidateFactoriesAndCollectors(info, collector)
|
val outerType = components.outerClassManager.outerType(constructedType)
|
||||||
|
val scope = constructedType.scope(components.session, components.scopeSession) ?: return collector
|
||||||
|
|
||||||
val towerResolverSession = FirTowerResolverSession(components, manager, candidateFactoriesAndCollectors, info)
|
val dispatchReceiver =
|
||||||
towerResolverSession.runResolutionForDelegatingConstructor(info, constructedType)
|
if (outerType != null)
|
||||||
|
components.implicitReceiverStack.receiversAsReversed().drop(1).firstOrNull {
|
||||||
|
AbstractTypeChecker.isSubtypeOf(components.session.typeContext, it.type, outerType)
|
||||||
|
} ?: return collector // TODO: report diagnostic about not-found receiver
|
||||||
|
else
|
||||||
|
null
|
||||||
|
|
||||||
|
val candidateFactory = CandidateFactory(components, info)
|
||||||
|
val resultCollector = collector
|
||||||
|
|
||||||
|
scope.processDeclaredConstructors {
|
||||||
|
resultCollector.consumeCandidate(
|
||||||
|
TowerGroup.Member,
|
||||||
|
candidateFactory.createCandidate(
|
||||||
|
it,
|
||||||
|
ExplicitReceiverKind.NO_EXPLICIT_RECEIVER,
|
||||||
|
dispatchReceiver,
|
||||||
|
implicitExtensionReceiverValue = null,
|
||||||
|
builtInExtensionFunctionReceiverValue = null
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
manager.runTasks()
|
|
||||||
return collector
|
return collector
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
-33
@@ -22,12 +22,10 @@ import org.jetbrains.kotlin.fir.scopes.ProcessorAction
|
|||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeAliasSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeAliasSymbol
|
||||||
import org.jetbrains.kotlin.fir.typeContext
|
|
||||||
import org.jetbrains.kotlin.fir.types.*
|
import org.jetbrains.kotlin.fir.types.*
|
||||||
import org.jetbrains.kotlin.fir.types.impl.FirImplicitBuiltinTypeRef
|
import org.jetbrains.kotlin.fir.types.impl.FirImplicitBuiltinTypeRef
|
||||||
import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind
|
import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind
|
||||||
import org.jetbrains.kotlin.resolve.descriptorUtil.HIDES_MEMBERS_NAME_LIST
|
import org.jetbrains.kotlin.resolve.descriptorUtil.HIDES_MEMBERS_NAME_LIST
|
||||||
import org.jetbrains.kotlin.types.AbstractTypeChecker
|
|
||||||
import org.jetbrains.kotlin.util.OperatorNameConventions
|
import org.jetbrains.kotlin.util.OperatorNameConventions
|
||||||
|
|
||||||
class FirTowerResolverSession internal constructor(
|
class FirTowerResolverSession internal constructor(
|
||||||
@@ -66,13 +64,6 @@ class FirTowerResolverSession internal constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun runResolutionForDelegatingConstructor(
|
|
||||||
info: CallInfo,
|
|
||||||
constructedType: ConeClassLikeType
|
|
||||||
) {
|
|
||||||
manager.enqueueResolverTask { runResolverForDelegatingConstructorCall(info, constructedType) }
|
|
||||||
}
|
|
||||||
|
|
||||||
fun runResolution(info: CallInfo) {
|
fun runResolution(info: CallInfo) {
|
||||||
when (val receiver = info.explicitReceiver) {
|
when (val receiver = info.explicitReceiver) {
|
||||||
is FirResolvedQualifier -> manager.enqueueResolverTask { runResolverForQualifierReceiver(info, receiver) }
|
is FirResolvedQualifier -> manager.enqueueResolverTask { runResolverForQualifierReceiver(info, receiver) }
|
||||||
@@ -140,9 +131,6 @@ class FirTowerResolverSession internal constructor(
|
|||||||
extensionReceiver, extensionsOnly, includeInnerConstructors
|
extensionReceiver, extensionsOnly, includeInnerConstructors
|
||||||
)
|
)
|
||||||
|
|
||||||
private fun FirScope.toConstructorScopeTowerLevel(dispatchReceiver: ImplicitReceiver?): ConstructorScopeTowerLevel =
|
|
||||||
ConstructorScopeTowerLevel(session, this, dispatchReceiver?.receiver)
|
|
||||||
|
|
||||||
private fun ReceiverValue.toMemberScopeTowerLevel(
|
private fun ReceiverValue.toMemberScopeTowerLevel(
|
||||||
extensionReceiver: ReceiverValue? = null,
|
extensionReceiver: ReceiverValue? = null,
|
||||||
implicitExtensionInvokeMode: Boolean = false
|
implicitExtensionInvokeMode: Boolean = false
|
||||||
@@ -213,27 +201,6 @@ class FirTowerResolverSession internal constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private suspend fun runResolverForDelegatingConstructorCall(
|
|
||||||
info: CallInfo,
|
|
||||||
constructedType: ConeClassLikeType
|
|
||||||
) {
|
|
||||||
val outerType = components.outerClassManager.outerType(constructedType)
|
|
||||||
val scope = constructedType.scope(session, components.scopeSession) ?: return
|
|
||||||
|
|
||||||
val dispatchReceiver =
|
|
||||||
if (outerType != null)
|
|
||||||
implicitReceivers.drop(1).firstOrNull {
|
|
||||||
AbstractTypeChecker.isSubtypeOf(components.session.typeContext, it.receiver.type, outerType)
|
|
||||||
} ?: return // TODO: report diagnostic about not-found receiver
|
|
||||||
else
|
|
||||||
null
|
|
||||||
|
|
||||||
processLevel(
|
|
||||||
scope.toConstructorScopeTowerLevel(dispatchReceiver),
|
|
||||||
info, TowerGroup.Member
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
private suspend fun runResolverForNoReceiver(
|
private suspend fun runResolverForNoReceiver(
|
||||||
info: CallInfo
|
info: CallInfo
|
||||||
) {
|
) {
|
||||||
|
|||||||
-3
@@ -122,9 +122,6 @@ internal class TowerLevelHandler {
|
|||||||
towerLevel.processFunctionsAndProperties(info.name, processor)
|
towerLevel.processFunctionsAndProperties(info.name, processor)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
CallKind.DelegatingConstructorCall -> {
|
|
||||||
towerLevel.processElementsByNameAndStoreResult(TowerScopeLevel.Token.ConstructorsForDelegationCall, info.name, processor)
|
|
||||||
}
|
|
||||||
else -> {
|
else -> {
|
||||||
throw AssertionError("Unsupported call kind in tower resolver: ${info.callKind}")
|
throw AssertionError("Unsupported call kind in tower resolver: ${info.callKind}")
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -35,7 +35,6 @@ interface TowerScopeLevel {
|
|||||||
sealed class Token<out T : AbstractFirBasedSymbol<*>> {
|
sealed class Token<out T : AbstractFirBasedSymbol<*>> {
|
||||||
object Properties : Token<FirVariableSymbol<*>>()
|
object Properties : Token<FirVariableSymbol<*>>()
|
||||||
object Functions : Token<FirFunctionSymbol<*>>()
|
object Functions : Token<FirFunctionSymbol<*>>()
|
||||||
object ConstructorsForDelegationCall : Token<FirConstructorSymbol>()
|
|
||||||
object Objects : Token<AbstractFirBasedSymbol<*>>()
|
object Objects : Token<AbstractFirBasedSymbol<*>>()
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -156,7 +155,6 @@ class MemberScopeTowerLevel(
|
|||||||
consumer(it as T)
|
consumer(it as T)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TowerScopeLevel.Token.ConstructorsForDelegationCall -> error("ConstructorsForDelegationCall should be handled via ConstructorScopeTowerLevel")
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -263,38 +261,6 @@ class ScopeTowerLevel(
|
|||||||
implicitExtensionReceiverValue = null
|
implicitExtensionReceiverValue = null
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
TowerScopeLevel.Token.ConstructorsForDelegationCall -> {
|
|
||||||
throw AssertionError("Should not be here")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return if (empty) ProcessorAction.NONE else ProcessorAction.NEXT
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class ConstructorScopeTowerLevel(
|
|
||||||
session: FirSession,
|
|
||||||
private val scope: FirScope,
|
|
||||||
private val dispatchReceiver: ImplicitReceiverValue<*>?,
|
|
||||||
) : SessionBasedTowerLevel(session) {
|
|
||||||
override fun <T : AbstractFirBasedSymbol<*>> processElementsByName(
|
|
||||||
token: TowerScopeLevel.Token<T>,
|
|
||||||
name: Name,
|
|
||||||
processor: TowerScopeLevel.TowerScopeLevelProcessor<T>
|
|
||||||
): ProcessorAction {
|
|
||||||
var empty = true
|
|
||||||
when (token) {
|
|
||||||
TowerScopeLevel.Token.ConstructorsForDelegationCall -> scope.processDeclaredConstructors { candidate ->
|
|
||||||
empty = false
|
|
||||||
@Suppress("UNCHECKED_CAST")
|
|
||||||
processor.consumeCandidate(
|
|
||||||
candidate as T,
|
|
||||||
dispatchReceiverValue = dispatchReceiver,
|
|
||||||
implicitExtensionReceiverValue = null
|
|
||||||
)
|
|
||||||
}
|
|
||||||
else -> {
|
|
||||||
throw AssertionError("Should not be here: token = $token")
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return if (empty) ProcessorAction.NONE else ProcessorAction.NEXT
|
return if (empty) ProcessorAction.NONE else ProcessorAction.NEXT
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user