diff --git a/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirKotlinSymbolProvider.kt b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirKotlinSymbolProvider.kt new file mode 100644 index 00000000000..6e9d56b7264 --- /dev/null +++ b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirKotlinSymbolProvider.kt @@ -0,0 +1,79 @@ +/* + * Copyright 2010-2023 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.analysis.low.level.api.fir.providers + +import org.jetbrains.kotlin.analysis.low.level.api.fir.util.LLFirSymbolProviderNameCache +import org.jetbrains.kotlin.analysis.providers.KotlinDeclarationProvider +import org.jetbrains.kotlin.fir.FirSession +import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider +import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProviderInternals +import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol +import org.jetbrains.kotlin.fir.symbols.impl.FirClassLikeSymbol +import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol +import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol +import org.jetbrains.kotlin.name.CallableId +import org.jetbrains.kotlin.name.ClassId +import org.jetbrains.kotlin.name.FqName +import org.jetbrains.kotlin.name.Name +import org.jetbrains.kotlin.psi.KtCallableDeclaration +import org.jetbrains.kotlin.psi.KtClassLikeDeclaration +import org.jetbrains.kotlin.psi.KtNamedFunction +import org.jetbrains.kotlin.psi.KtProperty + +/** + * A [FirSymbolProvider] which provides symbols from Kotlin sources via [KotlinDeclarationProvider]. + * + * @see LLFirCombinedKotlinSymbolProvider + */ +internal abstract class LLFirKotlinSymbolProvider(session: FirSession) : FirSymbolProvider(session) { + /** + * This function is optimized for a known [classLikeDeclaration]. + */ + @FirSymbolProviderInternals + abstract fun getClassLikeSymbolByClassId(classId: ClassId, classLikeDeclaration: KtClassLikeDeclaration): FirClassLikeSymbol<*>? + + /** + * This function is optimized for known [callables]. + */ + @FirSymbolProviderInternals + abstract fun getTopLevelCallableSymbolsTo( + destination: MutableList>, + callableId: CallableId, + callables: Collection, + ) + + /** + * This function is optimized for known [functions]. + */ + @FirSymbolProviderInternals + abstract fun getTopLevelFunctionSymbolsTo( + destination: MutableList, + callableId: CallableId, + functions: Collection, + ) + + /** + * This function is optimized for known [properties]. + */ + @FirSymbolProviderInternals + abstract fun getTopLevelPropertySymbolsTo( + destination: MutableList, + callableId: CallableId, + properties: Collection, + ) +} + +internal abstract class LLFirKotlinSymbolProviderWithNameCache(session: FirSession) : LLFirKotlinSymbolProvider(session) { + protected abstract val symbolNameCache: LLFirSymbolProviderNameCache + + final override fun knownTopLevelClassifiersInPackage(packageFqName: FqName): Set? = + symbolNameCache.getTopLevelClassifierNamesInPackage(packageFqName) + + final override fun computeCallableNamesInPackage(packageFqName: FqName): Set? = + symbolNameCache.getTopLevelCallableNamesInPackage(packageFqName) + + final override fun computePackageSetWithTopLevelCallables(): Set? = symbolNameCache.getPackageNamesWithTopLevelCallables() +} diff --git a/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirProvider.kt b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirProvider.kt index 95f7aca91f8..36e0c75373b 100644 --- a/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirProvider.kt +++ b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirProvider.kt @@ -7,6 +7,7 @@ package org.jetbrains.kotlin.analysis.low.level.api.fir.providers import org.jetbrains.kotlin.analysis.low.level.api.fir.LLFirModuleResolveComponents import org.jetbrains.kotlin.analysis.low.level.api.fir.transformers.SyntheticFirClassProvider +import org.jetbrains.kotlin.analysis.low.level.api.fir.util.LLFirSymbolProviderNameCache import org.jetbrains.kotlin.analysis.providers.KotlinDeclarationProvider import org.jetbrains.kotlin.analysis.providers.KotlinPackageProvider import org.jetbrains.kotlin.fir.FirSession @@ -25,8 +26,10 @@ import org.jetbrains.kotlin.name.CallableId import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.Name +import org.jetbrains.kotlin.psi.KtCallableDeclaration import org.jetbrains.kotlin.psi.KtClassLikeDeclaration -import org.jetbrains.kotlin.psi.KtFile +import org.jetbrains.kotlin.psi.KtNamedFunction +import org.jetbrains.kotlin.psi.KtProperty @ThreadSafeMutableState internal class LLFirProvider( @@ -109,17 +112,17 @@ internal class LLFirProvider( declarationProvider.getTopLevelKotlinClassLikeDeclarationNamesInPackage(fqName) @NoMutableState - internal inner class SymbolProvider : FirSymbolProvider(session) { + internal inner class SymbolProvider : LLFirKotlinSymbolProviderWithNameCache(session) { + override val symbolNameCache: LLFirSymbolProviderNameCache + get() = providerHelper.symbolNameCache + override fun getClassLikeSymbolByClassId(classId: ClassId): FirClassLikeSymbol<*>? { if (!providerHelper.symbolNameCache.mayHaveTopLevelClassifier(classId, mayHaveFunctionClass = false)) return null return getFirClassifierByFqName(classId)?.symbol } - /** - * This function is optimized for a known [classLikeDeclaration]. - */ @FirSymbolProviderInternals - fun getClassLikeSymbolByClassId(classId: ClassId, classLikeDeclaration: KtClassLikeDeclaration): FirClassLikeSymbol<*>? { + override fun getClassLikeSymbolByClassId(classId: ClassId, classLikeDeclaration: KtClassLikeDeclaration): FirClassLikeSymbol<*>? { return getFirClassifierByFqNameAndDeclaration(classId, classLikeDeclaration)?.symbol } @@ -134,16 +137,13 @@ internal class LLFirProvider( destination += providerHelper.getTopLevelCallableSymbols(packageFqName, name) } - /** - * This function is optimized for known [callableFiles], which should be the list of all [KtFile]s that contain the callables. - */ @FirSymbolProviderInternals - fun getTopLevelCallableSymbolsTo( + override fun getTopLevelCallableSymbolsTo( destination: MutableList>, callableId: CallableId, - callableFiles: Collection, + callables: Collection ) { - destination += providerHelper.getTopLevelCallableSymbols(callableId, callableFiles) + destination += providerHelper.getTopLevelCallableSymbols(callableId, callables.map { it.containingKtFile }) } override fun getTopLevelFunctionSymbols(packageFqName: FqName, name: Name): List { @@ -157,16 +157,13 @@ internal class LLFirProvider( destination += providerHelper.getTopLevelFunctionSymbols(packageFqName, name) } - /** - * This function is optimized for known [callableFiles], which should be the list of all [KtFile]s that contain the functions. - */ @FirSymbolProviderInternals - fun getTopLevelFunctionSymbolsTo( + override fun getTopLevelFunctionSymbolsTo( destination: MutableList, callableId: CallableId, - callableFiles: Collection, + functions: Collection ) { - destination += providerHelper.getTopLevelFunctionSymbols(callableId, callableFiles) + destination += providerHelper.getTopLevelFunctionSymbols(callableId, functions.map { it.containingKtFile }) } override fun getTopLevelPropertySymbols(packageFqName: FqName, name: Name): List { @@ -180,28 +177,16 @@ internal class LLFirProvider( destination += providerHelper.getTopLevelPropertySymbols(packageFqName, name) } - /** - * This function is optimized for known [callableFiles], which should be the list of all [KtFile]s that contain the properties. - */ @FirSymbolProviderInternals - fun getTopLevelPropertySymbolsTo( + override fun getTopLevelPropertySymbolsTo( destination: MutableList, callableId: CallableId, - callableFiles: Collection, + properties: Collection ) { - destination += providerHelper.getTopLevelPropertySymbols(callableId, callableFiles) + destination += providerHelper.getTopLevelPropertySymbols(callableId, properties.mapTo(mutableSetOf()) { it.containingKtFile }) } override fun getPackage(fqName: FqName): FqName? = providerHelper.getPackage(fqName) - - override fun computePackageSetWithTopLevelCallables(): Set? = - providerHelper.symbolNameCache.getPackageNamesWithTopLevelCallables() - - override fun knownTopLevelClassifiersInPackage(packageFqName: FqName): Set? = - providerHelper.symbolNameCache.getTopLevelClassifierNamesInPackage(packageFqName) - - override fun computeCallableNamesInPackage(packageFqName: FqName): Set? = - providerHelper.symbolNameCache.getTopLevelCallableNamesInPackage(packageFqName) } }