From 50742a46868967ce1c66b0e5182324edf482cd69 Mon Sep 17 00:00:00 2001 From: Dmitriy Novozhilov Date: Tue, 3 Mar 2020 12:28:23 +0300 Subject: [PATCH] [FIR] Move local scopes immutable --- .../jetbrains/kotlin/fir/FirCallResolver.kt | 10 +-- .../fir/resolve/ImplicitReceiverStack.kt | 34 +-------- .../kotlin/fir/resolve/PersistentMultimap.kt | 66 ++++++++++++++++ .../kotlin/fir/resolve/SessionHolder.kt | 7 ++ .../fir/resolve/calls/FirTowerResolver.kt | 4 +- .../FirAbstractBodyResolveTransformer.kt | 75 ++++++++++++++++--- ...ControlFlowStatementsResolveTransformer.kt | 8 +- .../FirDeclarationsResolveTransformer.kt | 36 ++++----- .../kotlin/fir/scopes/impl/FirLocalScope.kt | 44 +++++++---- .../impl/FirTypeResolveScopeForBodyResolve.kt | 10 +-- 10 files changed, 202 insertions(+), 92 deletions(-) create mode 100644 compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/PersistentMultimap.kt diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/FirCallResolver.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/FirCallResolver.kt index 61f658a3130..fd03a542f5d 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/FirCallResolver.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/FirCallResolver.kt @@ -30,8 +30,6 @@ import org.jetbrains.kotlin.fir.resolve.transformers.StoreReceiver import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.FirExpressionsResolveTransformer import org.jetbrains.kotlin.fir.resolve.transformers.body.resolve.resultType import org.jetbrains.kotlin.fir.resolve.transformers.phasedFir -import org.jetbrains.kotlin.fir.scopes.FirScope -import org.jetbrains.kotlin.fir.scopes.impl.FirLocalScope import org.jetbrains.kotlin.fir.scopes.unsubstitutedScope import org.jetbrains.kotlin.fir.symbols.impl.* import org.jetbrains.kotlin.fir.types.* @@ -42,9 +40,7 @@ import org.jetbrains.kotlin.resolve.calls.results.TypeSpecificityComparator import org.jetbrains.kotlin.resolve.calls.tasks.ExplicitReceiverKind class FirCallResolver( - components: BodyResolveComponents, - topLevelScopes: List, - localScopes: List, + private val components: BodyResolveComponents, private val qualifiedResolver: FirQualifiedNameResolver, ) : BodyResolveComponents by components { @@ -55,9 +51,7 @@ class FirCallResolver( } private val towerResolver = FirTowerResolver( - returnTypeCalculator, this, resolutionStageRunner, - topLevelScopes = topLevelScopes.asReversed(), - localScopes = localScopes.asReversed(), + returnTypeCalculator, components, resolutionStageRunner, ) private val conflictResolver = diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/ImplicitReceiverStack.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/ImplicitReceiverStack.kt index ca541f62053..e8d9823248f 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/ImplicitReceiverStack.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/ImplicitReceiverStack.kt @@ -5,7 +5,10 @@ package org.jetbrains.kotlin.fir.resolve -import kotlinx.collections.immutable.* +import kotlinx.collections.immutable.PersistentList +import kotlinx.collections.immutable.PersistentMap +import kotlinx.collections.immutable.persistentListOf +import kotlinx.collections.immutable.persistentMapOf import org.jetbrains.kotlin.fir.resolve.calls.ImplicitDispatchReceiverValue import org.jetbrains.kotlin.fir.resolve.calls.ImplicitReceiverValue import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol @@ -91,32 +94,3 @@ class ImplicitReceiverStackImpl private constructor( return ImplicitReceiverStackImpl(stack, originalTypes, indexesPerLabel, indexesPerSymbol) } } - -class PersistentSetMultimap private constructor(private val map: PersistentMap>) { - - constructor() : this(persistentMapOf()) - - fun put(key: K, value: V): PersistentSetMultimap { - val set = map[key] ?: persistentSetOf() - val newSet = set.add(value) - if (newSet === set) return this - val newMap = map.put(key, newSet) - return PersistentSetMultimap(newMap) - } - - fun remove(key: K, value: V): PersistentSetMultimap { - val set = map.get(key) ?: return this - val newSet = set.remove(value) - if (set === newSet) return this - val newMap = if (newSet.isEmpty()) { - map.remove(key) - } else { - map.put(key, newSet) - } - return PersistentSetMultimap(newMap) - } - - operator fun get(key: K): Set { - return map[key] ?: emptySet() - } -} \ No newline at end of file diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/PersistentMultimap.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/PersistentMultimap.kt new file mode 100644 index 00000000000..c33ff9ebcae --- /dev/null +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/PersistentMultimap.kt @@ -0,0 +1,66 @@ +/* + * 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.fir.resolve + +import kotlinx.collections.immutable.* + +class PersistentMultimap private constructor(private val map: PersistentMap>) { + + constructor() : this(persistentMapOf()) + + fun put(key: K, value: V): PersistentMultimap { + val collection = map[key] ?: persistentListOf() + val newSet = collection.add(value) + if (newSet === collection) return this + val newMap = map.put(key, newSet) + return PersistentMultimap(newMap) + } + + fun remove(key: K, value: V): PersistentMultimap { + val list = map.get(key) ?: return this + val newSet = list.remove(value) + if (list === newSet) return this + val newMap = if (newSet.isEmpty()) { + map.remove(key) + } else { + map.put(key, newSet) + } + return PersistentMultimap(newMap) + } + + operator fun get(key: K): List { + return map[key] ?: emptyList() + } +} + +class PersistentSetMultimap private constructor(private val map: PersistentMap>) { + + constructor() : this(persistentMapOf()) + + fun put(key: K, value: V): PersistentSetMultimap { + val set = map[key] ?: persistentSetOf() + val newSet = set.add(value) + if (newSet === set) return this + val newMap = map.put(key, newSet) + return PersistentSetMultimap(newMap) + } + + fun remove(key: K, value: V): PersistentSetMultimap { + val set = map.get(key) ?: return this + val newSet = set.remove(value) + if (set === newSet) return this + val newMap = if (newSet.isEmpty()) { + map.remove(key) + } else { + map.put(key, newSet) + } + return PersistentSetMultimap(newMap) + } + + operator fun get(key: K): Set { + return map[key] ?: emptySet() + } +} \ No newline at end of file diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/SessionHolder.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/SessionHolder.kt index 4b71f805077..173ebe84346 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/SessionHolder.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/SessionHolder.kt @@ -5,6 +5,7 @@ package org.jetbrains.kotlin.fir.resolve +import kotlinx.collections.immutable.PersistentList import org.jetbrains.kotlin.fir.FirCallResolver import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSymbolOwner @@ -16,9 +17,13 @@ import org.jetbrains.kotlin.fir.resolve.dfa.FirDataFlowAnalyzer import org.jetbrains.kotlin.fir.resolve.inference.FirCallCompleter import org.jetbrains.kotlin.fir.resolve.inference.InferenceComponents import org.jetbrains.kotlin.fir.resolve.transformers.* +import org.jetbrains.kotlin.fir.scopes.FirScope +import org.jetbrains.kotlin.fir.scopes.impl.FirLocalScope import org.jetbrains.kotlin.fir.symbols.AbstractFirBasedSymbol import org.jetbrains.kotlin.fir.types.FirTypeRef +typealias FirLocalScopes = PersistentList + interface SessionHolder { val session: FirSession } @@ -26,6 +31,8 @@ interface SessionHolder { interface BodyResolveComponents : SessionHolder { val returnTypeCalculator: ReturnTypeCalculator val implicitReceiverStack: ImplicitReceiverStack + val topLevelScopes: List + val localScopes: FirLocalScopes val noExpectedType: FirTypeRef val symbolProvider: FirSymbolProvider val file: FirFile diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/FirTowerResolver.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/FirTowerResolver.kt index 1b3dbf7accf..b3558a03ffc 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/FirTowerResolver.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/FirTowerResolver.kt @@ -32,9 +32,9 @@ class FirTowerResolver( val typeCalculator: ReturnTypeCalculator, val components: BodyResolveComponents, resolutionStageRunner: ResolutionStageRunner, - private val topLevelScopes: List, - private val localScopes: List ) { + private val localScopes: List get() = components.localScopes.asReversed() + private val topLevelScopes: List get() = components.topLevelScopes.asReversed() private val session: FirSession get() = components.session private val collector = CandidateCollector(components, resolutionStageRunner) diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirAbstractBodyResolveTransformer.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirAbstractBodyResolveTransformer.kt index 870b02bd2ca..7feba02a2db 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirAbstractBodyResolveTransformer.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirAbstractBodyResolveTransformer.kt @@ -5,10 +5,9 @@ package org.jetbrains.kotlin.fir.resolve.transformers.body.resolve +import kotlinx.collections.immutable.persistentListOf import org.jetbrains.kotlin.fir.* -import org.jetbrains.kotlin.fir.declarations.FirDeclaration -import org.jetbrains.kotlin.fir.declarations.FirFile -import org.jetbrains.kotlin.fir.declarations.FirResolvePhase +import org.jetbrains.kotlin.fir.declarations.* import org.jetbrains.kotlin.fir.resolve.* import org.jetbrains.kotlin.fir.resolve.calls.ResolutionStageRunner import org.jetbrains.kotlin.fir.resolve.dfa.FirDataFlowAnalyzer @@ -50,6 +49,16 @@ abstract class FirAbstractBodyResolveTransformer(phase: FirResolvePhase) : FirAb } } + protected inline fun withLocalScopeCleanup(crossinline l: () -> T): T { + return components.withLocalScopesCleanup(l) + } + + protected fun addLocalScope(localScope: FirLocalScope?) { + if (localScope == null) return + components.addLocalScope(localScope) + } + + @UseExperimental(PrivateForInline::class) internal inline fun withFullBodyResolve(crossinline l: () -> T): T { if (!implicitTypeOnly) return l() @@ -62,7 +71,7 @@ abstract class FirAbstractBodyResolveTransformer(phase: FirResolvePhase) : FirAb } protected inline val topLevelScopes: MutableList get() = components.topLevelScopes - protected inline val localScopes: MutableList get() = components.localScopes + protected inline val localScopes: List get() = components.localScopes protected inline val noExpectedType: FirTypeRef get() = components.noExpectedType @@ -94,8 +103,10 @@ abstract class FirAbstractBodyResolveTransformer(phase: FirResolvePhase) : FirAb override val scopeSession: ScopeSession, val transformer: FirBodyResolveTransformer ) : BodyResolveComponents { - val topLevelScopes: MutableList = mutableListOf() - val localScopes: MutableList = mutableListOf() + override val topLevelScopes: MutableList = mutableListOf() + + @set:PrivateForInline + override var localScopes: FirLocalScopes = persistentListOf() override val noExpectedType: FirTypeRef = buildImplicitTypeRef() @@ -117,12 +128,10 @@ abstract class FirAbstractBodyResolveTransformer(phase: FirResolvePhase) : FirAb private val qualifiedResolver: FirQualifiedNameResolver = FirQualifiedNameResolver(this) override val callResolver: FirCallResolver = FirCallResolver( this, - topLevelScopes, - localScopes, qualifiedResolver ) val typeResolverTransformer = FirSpecificTypeResolverTransformer( - FirTypeResolveScopeForBodyResolve(topLevelScopes, implicitReceiverStack, localScopes), session + FirTypeResolveScopeForBodyResolve(this), session ) override val callCompleter: FirCallCompleter = FirCallCompleter(transformer, this) override val dataFlowAnalyzer: FirDataFlowAnalyzer<*> = FirDataFlowAnalyzer.createFirDataFlowAnalyzer(this) @@ -160,6 +169,54 @@ abstract class FirAbstractBodyResolveTransformer(phase: FirResolvePhase) : FirAb this.implicitReceiverStack = existedStack } } + + @UseExperimental(PrivateForInline::class) + inline fun withLocalScopes(localScopes: FirLocalScopes, l: () -> R): R { + val initialLocalScopes = this.localScopes + this.localScopes = localScopes + return try { + l() + } finally { + this.localScopes = initialLocalScopes + } + } + + @UseExperimental(PrivateForInline::class) + inline fun withLocalScopesCleanup(l: () -> R): R { + val initialLocalScopes = localScopes + return try { + l() + } finally { + localScopes = initialLocalScopes + } + } + + @UseExperimental(PrivateForInline::class) + fun addLocalScope(localScope: FirLocalScope) { + localScopes = localScopes.add(localScope) + } + + fun storeClass(klass: FirRegularClass) { + updateLastScope { storeClass(klass) } + } + + fun storeFunction(function: FirSimpleFunction) { + updateLastScope { storeFunction(function) } + } + + fun storeVariable(variable: FirVariable<*>) { + updateLastScope { storeVariable(variable) } + } + + fun storeBackingField(property: FirProperty) { + updateLastScope { storeBackingField(property) } + } + + @UseExperimental(PrivateForInline::class) + private inline fun updateLastScope(transform: FirLocalScope.() -> FirLocalScope) { + val lastScope = localScopes.lastOrNull() ?: return + localScopes = localScopes.set(localScopes.size - 1, lastScope.transform()) + } } } diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirControlFlowStatementsResolveTransformer.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirControlFlowStatementsResolveTransformer.kt index 26c08d8ac28..65c59aff7be 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirControlFlowStatementsResolveTransformer.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirControlFlowStatementsResolveTransformer.kt @@ -56,9 +56,9 @@ class FirControlFlowStatementsResolveTransformer(transformer: FirBodyResolveTran } whenExpression.annotations.forEach { it.accept(this, data) } dataFlowAnalyzer.enterWhenExpression(whenExpression) - return withScopeCleanup(localScopes) with@{ + return withLocalScopeCleanup with@{ if (whenExpression.subjectVariable != null) { - localScopes += FirLocalScope() + addLocalScope(FirLocalScope()) } @Suppress("NAME_SHADOWING") var whenExpression = whenExpression.transformSubject(transformer, ResolutionMode.ContextIndependent) @@ -164,8 +164,8 @@ class FirControlFlowStatementsResolveTransformer(transformer: FirBodyResolveTran override fun transformCatch(catch: FirCatch, data: ResolutionMode): CompositeTransformResult { dataFlowAnalyzer.enterCatchClause(catch) catch.parameter.transformReturnTypeRef(transformer, ResolutionMode.ContextIndependent) - return withScopeCleanup(localScopes) { - localScopes += FirLocalScope() + return withLocalScopeCleanup { + addLocalScope(FirLocalScope()) catch.transformParameter(transformer, ResolutionMode.ContextIndependent) catch.transformBlock(transformer, ResolutionMode.ContextDependent) }.also { dataFlowAnalyzer.exitCatchClause(it) }.compose() diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirDeclarationsResolveTransformer.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirDeclarationsResolveTransformer.kt index 16f998e34c6..f214c641b73 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirDeclarationsResolveTransformer.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirDeclarationsResolveTransformer.kt @@ -100,24 +100,22 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) } dataFlowAnalyzer.enterProperty(property) withFullBodyResolve { - withScopeCleanup(localScopes) { + withLocalScopeCleanup { components.withContainer(property) { if (property.delegate != null) { - localScopes.addIfNotNull(primaryConstructorParametersScope) + addLocalScope(primaryConstructorParametersScope) transformPropertyWithDelegate(property) } else { - withScopeCleanup(localScopes) { - localScopes.addIfNotNull(primaryConstructorParametersScope) + withLocalScopeCleanup { + addLocalScope(primaryConstructorParametersScope) property.transformChildrenWithoutAccessors(returnTypeRef) property.transformInitializer(integerLiteralTypeApproximator, null) } if (property.initializer != null) { storeVariableReturnType(property) } - withScopeCleanup(localScopes) { - localScopes.add(FirLocalScope().apply { - storeBackingField(property) - }) + withLocalScopeCleanup { + addLocalScope(FirLocalScope().storeBackingField(property)) property.transformAccessors() } } @@ -193,7 +191,7 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) } variable.transformAccessors() } - localScopes.lastOrNull()?.storeVariable(variable) + components.storeVariable(variable) variable.replaceResolvePhase(transformerPhase) dataFlowAnalyzer.exitLocalVariableDeclaration(variable) return variable.compose() @@ -292,7 +290,7 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) } override fun transformRegularClass(regularClass: FirRegularClass, data: ResolutionMode): CompositeTransformResult { - localScopes.lastOrNull()?.storeClass(regularClass) + components.storeClass(regularClass) return withScopeCleanup(topLevelScopes) { prepareTypeParameterOwnerForBodyResolve(regularClass) if (regularClass.symbol.classId.isLocal) { @@ -307,8 +305,10 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) val result = withLabelAndReceiverType(regularClass.name, regularClass, type) { val constructor = regularClass.declarations.firstOrNull() as? FirConstructor if (constructor?.isPrimary == true) { - primaryConstructorParametersScope = FirLocalScope().apply { - constructor.valueParameters.forEach { this.storeVariable(it) } + primaryConstructorParametersScope = FirLocalScope().let { + var scope = it + constructor.valueParameters.forEach { scope = scope.storeVariable(it) } + scope } } transformDeclaration(regularClass, data) @@ -402,7 +402,7 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) returnTypeRef: FirTypeRef, ): CompositeTransformResult { if (function is FirSimpleFunction) { - localScopes.lastOrNull()?.storeFunction(function) + components.storeFunction(function) } @Suppress("UNCHECKED_CAST") @@ -424,8 +424,8 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) } override fun > transformFunction(function: FirFunction, data: ResolutionMode): CompositeTransformResult { - return withScopeCleanup(localScopes) { - localScopes += FirLocalScope() + return withLocalScopeCleanup { + addLocalScope(FirLocalScope()) dataFlowAnalyzer.enterFunction(function) @Suppress("UNCHECKED_CAST") transformDeclaration(function, data).also { @@ -448,9 +448,9 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) data: ResolutionMode ): CompositeTransformResult { if (implicitTypeOnly) return anonymousInitializer.compose() - return withScopeCleanup(localScopes) { + return withLocalScopeCleanup { dataFlowAnalyzer.enterInitBlock(anonymousInitializer) - localScopes.addIfNotNull(primaryConstructorParametersScope) + addLocalScope(primaryConstructorParametersScope) transformDeclaration(anonymousInitializer, ResolutionMode.ContextIndependent).also { dataFlowAnalyzer.exitInitBlock(it.single as FirAnonymousInitializer) } @@ -458,7 +458,7 @@ class FirDeclarationsResolveTransformer(transformer: FirBodyResolveTransformer) } override fun transformValueParameter(valueParameter: FirValueParameter, data: ResolutionMode): CompositeTransformResult { - localScopes.lastOrNull()?.storeVariable(valueParameter) + components.storeVariable(valueParameter) if (valueParameter.returnTypeRef is FirImplicitTypeRef) { valueParameter.replaceResolvePhase(transformerPhase) return valueParameter.compose() // TODO diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirLocalScope.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirLocalScope.kt index 7b04b98a625..650d9f27be7 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirLocalScope.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirLocalScope.kt @@ -5,38 +5,52 @@ package org.jetbrains.kotlin.fir.scopes.impl +import kotlinx.collections.immutable.PersistentMap +import kotlinx.collections.immutable.persistentMapOf import org.jetbrains.kotlin.fir.declarations.* import org.jetbrains.kotlin.fir.NAME_FOR_BACKING_FIELD +import org.jetbrains.kotlin.fir.resolve.PersistentMultimap import org.jetbrains.kotlin.fir.scopes.FirScope import org.jetbrains.kotlin.fir.symbols.impl.* import org.jetbrains.kotlin.name.Name -class FirLocalScope : FirScope() { +class FirLocalScope( + properties: PersistentMap>, + functions: PersistentMultimap>, + classes: PersistentMap +) : FirScope() { + val properties: PersistentMap> = properties + val functions: PersistentMultimap> = functions + val classes: PersistentMap = classes - val properties = mutableMapOf>() - val functions = mutableMapOf>>() - val classes = mutableMapOf() + constructor() : this(persistentMapOf(), PersistentMultimap(), persistentMapOf()) - fun storeClass(klass: FirRegularClass) { - classes[klass.name] = klass.symbol + fun storeClass(klass: FirRegularClass): FirLocalScope { + return FirLocalScope( + properties, functions, classes.put(klass.name, klass.symbol) + ) } - fun storeFunction(function: FirSimpleFunction) { - functions.getOrPut(function.name) { - mutableListOf() - }.add(function.symbol as FirNamedFunctionSymbol) + fun storeFunction(function: FirSimpleFunction): FirLocalScope { + return FirLocalScope( + properties, functions.put(function.name, function.symbol as FirNamedFunctionSymbol), classes + ) } - fun storeVariable(variable: FirVariable<*>) { - properties[variable.name] = variable.symbol + fun storeVariable(variable: FirVariable<*>): FirLocalScope { + return FirLocalScope( + properties.put(variable.name, variable.symbol), functions, classes + ) } - fun storeBackingField(property: FirProperty) { - properties[NAME_FOR_BACKING_FIELD] = property.backingFieldSymbol + fun storeBackingField(property: FirProperty): FirLocalScope { + return FirLocalScope( + properties.put(NAME_FOR_BACKING_FIELD, property.backingFieldSymbol), functions, classes + ) } override fun processFunctionsByName(name: Name, processor: (FirFunctionSymbol<*>) -> Unit) { - for (function in functions[name].orEmpty()) { + for (function in functions[name]) { processor(function) } } diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirTypeResolveScopeForBodyResolve.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirTypeResolveScopeForBodyResolve.kt index 7d04f066332..037a6a03b81 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirTypeResolveScopeForBodyResolve.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/scopes/impl/FirTypeResolveScopeForBodyResolve.kt @@ -5,18 +5,16 @@ package org.jetbrains.kotlin.fir.scopes.impl -import org.jetbrains.kotlin.fir.resolve.ImplicitReceiverStack +import org.jetbrains.kotlin.fir.resolve.BodyResolveComponents import org.jetbrains.kotlin.fir.resolve.calls.ImplicitDispatchReceiverValue import org.jetbrains.kotlin.fir.scopes.FirIterableScope import org.jetbrains.kotlin.fir.scopes.FirScope class FirTypeResolveScopeForBodyResolve( - private val topLevelScopes: List, - private val implicitReceiverStack: ImplicitReceiverStack, - private val localScopes: List + private val components: BodyResolveComponents ) : FirIterableScope() { override val scopes: Iterable - get() = localScopes.asReversed() + implicitReceiverStack.receiversAsReversed().mapNotNull { + get() = components.localScopes.asReversed() + components.implicitReceiverStack.receiversAsReversed().mapNotNull { (it as? ImplicitDispatchReceiverValue)?.implicitScope - } + topLevelScopes.asReversed() + } + components.topLevelScopes.asReversed() } \ No newline at end of file