[FIR] Extract SyntheticFunctionsCache from builtins provider into separate one
This is needed because now set of available synthetic functional interfaces depends on session, because each module can contain different plugins, which provide different kinds of functional types
This commit is contained in:
committed by
Space Team
parent
e0c8f2354a
commit
87a9103cc6
+16
-173
@@ -5,43 +5,33 @@
|
||||
|
||||
package org.jetbrains.kotlin.fir.resolve.providers.impl
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.descriptors.SourceElement
|
||||
import org.jetbrains.kotlin.fir.FirModuleData
|
||||
import org.jetbrains.kotlin.fir.FirSession
|
||||
import org.jetbrains.kotlin.fir.ThreadSafeMutableState
|
||||
import org.jetbrains.kotlin.fir.caches.createCache
|
||||
import org.jetbrains.kotlin.fir.caches.firCachesFactory
|
||||
import org.jetbrains.kotlin.fir.caches.getValue
|
||||
import org.jetbrains.kotlin.fir.declarations.FirDeclarationOrigin
|
||||
import org.jetbrains.kotlin.fir.declarations.FirResolvePhase
|
||||
import org.jetbrains.kotlin.fir.declarations.builder.buildRegularClass
|
||||
import org.jetbrains.kotlin.fir.declarations.builder.buildSimpleFunction
|
||||
import org.jetbrains.kotlin.fir.declarations.builder.buildTypeParameter
|
||||
import org.jetbrains.kotlin.fir.declarations.builder.buildValueParameter
|
||||
import org.jetbrains.kotlin.fir.declarations.impl.FirResolvedDeclarationStatusImpl
|
||||
import org.jetbrains.kotlin.fir.declarations.utils.addDeclaration
|
||||
import org.jetbrains.kotlin.fir.deserialization.FirBuiltinAnnotationDeserializer
|
||||
import org.jetbrains.kotlin.fir.deserialization.FirConstDeserializer
|
||||
import org.jetbrains.kotlin.fir.deserialization.FirDeserializationContext
|
||||
import org.jetbrains.kotlin.fir.deserialization.deserializeClassToSymbol
|
||||
import org.jetbrains.kotlin.fir.expressions.builder.buildAnnotation
|
||||
import org.jetbrains.kotlin.fir.expressions.impl.FirEmptyAnnotationArgumentMapping
|
||||
import org.jetbrains.kotlin.fir.resolve.defaultType
|
||||
import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProvider
|
||||
import org.jetbrains.kotlin.fir.resolve.providers.FirSymbolProviderInternals
|
||||
import org.jetbrains.kotlin.fir.scopes.FirKotlinScopeProvider
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.*
|
||||
import org.jetbrains.kotlin.fir.types.*
|
||||
import org.jetbrains.kotlin.fir.types.impl.ConeTypeParameterTypeImpl
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.FirCallableSymbol
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol
|
||||
import org.jetbrains.kotlin.fir.symbols.impl.FirRegularClassSymbol
|
||||
import org.jetbrains.kotlin.metadata.ProtoBuf
|
||||
import org.jetbrains.kotlin.metadata.builtins.BuiltInsBinaryVersion
|
||||
import org.jetbrains.kotlin.metadata.deserialization.NameResolverImpl
|
||||
import org.jetbrains.kotlin.name.*
|
||||
import org.jetbrains.kotlin.name.ClassId
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.name.StandardClassIds
|
||||
import org.jetbrains.kotlin.serialization.deserialization.ProtoBasedClassDataFinder
|
||||
import org.jetbrains.kotlin.serialization.deserialization.builtins.BuiltInSerializerProtocol
|
||||
import org.jetbrains.kotlin.serialization.deserialization.getName
|
||||
import org.jetbrains.kotlin.types.Variance
|
||||
import org.jetbrains.kotlin.util.OperatorNameConventions
|
||||
import java.io.InputStream
|
||||
|
||||
@ThreadSafeMutableState
|
||||
@@ -50,8 +40,13 @@ open class FirBuiltinSymbolProvider(
|
||||
val moduleData: FirModuleData,
|
||||
val kotlinScopeProvider: FirKotlinScopeProvider
|
||||
) : FirSymbolProvider(session) {
|
||||
private val syntheticFunctionalInterfaceProvider = FirBuiltinSyntheticFunctionalInterfaceProvider(
|
||||
session,
|
||||
moduleData,
|
||||
kotlinScopeProvider
|
||||
)
|
||||
|
||||
private val allPackageFragments = loadBuiltIns().groupBy { it.fqName }
|
||||
private val syntheticFunctionalInterfaceCache = SyntheticFunctionalInterfaceCache(session, moduleData, kotlinScopeProvider)
|
||||
|
||||
private fun loadBuiltIns(): List<BuiltInsPackageFragment> {
|
||||
val classLoader = this::class.java.classLoader
|
||||
@@ -73,7 +68,7 @@ open class FirBuiltinSymbolProvider(
|
||||
override fun getClassLikeSymbolByClassId(classId: ClassId): FirRegularClassSymbol? {
|
||||
return allPackageFragments[classId.packageFqName]?.firstNotNullOfOrNull {
|
||||
it.getClassLikeSymbolByClassId(classId)
|
||||
} ?: syntheticFunctionalInterfaceCache.tryGetSyntheticFunctionalInterface(classId)
|
||||
} ?: syntheticFunctionalInterfaceProvider.getClassLikeSymbolByClassId(classId)
|
||||
}
|
||||
|
||||
override fun computePackageSetWithTopLevelCallables(): Set<String> =
|
||||
@@ -199,155 +194,3 @@ private data class BinaryVersionAndPackageFragment(
|
||||
}
|
||||
}
|
||||
|
||||
private class SyntheticFunctionalInterfaceCache(
|
||||
private val session: FirSession,
|
||||
private val moduleData: FirModuleData,
|
||||
private val kotlinScopeProvider: FirKotlinScopeProvider
|
||||
) {
|
||||
private val syntheticFunctionalInterfaceCache =
|
||||
moduleData.session.firCachesFactory.createCache(::createSyntheticFunctionalInterface)
|
||||
|
||||
fun tryGetSyntheticFunctionalInterface(classId: ClassId): FirRegularClassSymbol? {
|
||||
return syntheticFunctionalInterfaceCache.getValue(classId)
|
||||
}
|
||||
|
||||
private fun createSyntheticFunctionalInterface(classId: ClassId): FirRegularClassSymbol? {
|
||||
return with(classId) {
|
||||
val className = relativeClassName.asString()
|
||||
val kind = session.functionalTypeService.getKindByClassNamePrefix(packageFqName, className) ?: return null
|
||||
val prefix = kind.classNamePrefix
|
||||
val arity = className.substring(prefix.length).toIntOrNull() ?: return null
|
||||
FirRegularClassSymbol(classId).apply symbol@{
|
||||
buildRegularClass klass@{
|
||||
moduleData = this@SyntheticFunctionalInterfaceCache.moduleData
|
||||
origin = FirDeclarationOrigin.BuiltIns
|
||||
name = relativeClassName.shortName()
|
||||
status = FirResolvedDeclarationStatusImpl(
|
||||
Visibilities.Public,
|
||||
Modality.ABSTRACT,
|
||||
EffectiveVisibility.Public
|
||||
).apply {
|
||||
isExpect = false
|
||||
isActual = false
|
||||
isInner = false
|
||||
isCompanion = false
|
||||
isData = false
|
||||
isInline = false
|
||||
}
|
||||
classKind = ClassKind.INTERFACE
|
||||
scopeProvider = kotlinScopeProvider
|
||||
symbol = this@symbol
|
||||
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
|
||||
typeParameters.addAll(
|
||||
(1..arity).map {
|
||||
buildTypeParameter {
|
||||
moduleData = this@SyntheticFunctionalInterfaceCache.moduleData
|
||||
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
|
||||
origin = FirDeclarationOrigin.BuiltIns
|
||||
name = Name.identifier("P$it")
|
||||
symbol = FirTypeParameterSymbol()
|
||||
containingDeclarationSymbol = this@symbol
|
||||
variance = Variance.IN_VARIANCE
|
||||
isReified = false
|
||||
bounds += moduleData.session.builtinTypes.nullableAnyType
|
||||
}
|
||||
},
|
||||
)
|
||||
typeParameters.add(
|
||||
buildTypeParameter {
|
||||
moduleData = this@SyntheticFunctionalInterfaceCache.moduleData
|
||||
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
|
||||
origin = FirDeclarationOrigin.BuiltIns
|
||||
name = Name.identifier("R")
|
||||
symbol = FirTypeParameterSymbol()
|
||||
containingDeclarationSymbol = this@symbol
|
||||
variance = Variance.OUT_VARIANCE
|
||||
isReified = false
|
||||
bounds += moduleData.session.builtinTypes.nullableAnyType
|
||||
},
|
||||
)
|
||||
val name = OperatorNameConventions.INVOKE
|
||||
val functionStatus = FirResolvedDeclarationStatusImpl(
|
||||
Visibilities.Public,
|
||||
Modality.ABSTRACT,
|
||||
EffectiveVisibility.Public
|
||||
).apply {
|
||||
isExpect = false
|
||||
isActual = false
|
||||
isOverride = false
|
||||
isOperator = true
|
||||
isInfix = false
|
||||
isInline = false
|
||||
isTailRec = false
|
||||
isExternal = false
|
||||
isSuspend =
|
||||
kind == ConeFunctionalTypeKind.SuspendFunction ||
|
||||
kind == ConeFunctionalTypeKind.KSuspendFunction
|
||||
}
|
||||
val typeArguments = typeParameters.map {
|
||||
ConeTypeParameterTypeImpl(it.symbol.toLookupTag(), false).toFirResolvedTypeRef()
|
||||
}
|
||||
|
||||
fun createSuperType(kind: ConeFunctionalTypeKind): FirResolvedTypeRef {
|
||||
return kind.classId(arity).toLookupTag()
|
||||
.constructClassType(typeArguments.map { it.type }.toTypedArray(), isNullable = false)
|
||||
.toFirResolvedTypeRef()
|
||||
}
|
||||
|
||||
if (kind.isReflectType) {
|
||||
superTypeRefs += StandardClassIds.KFunction.toLookupTag()
|
||||
.constructClassType(arrayOf(typeArguments.last().type), isNullable = false)
|
||||
.toFirResolvedTypeRef()
|
||||
superTypeRefs += createSuperType(kind.nonReflectKind())
|
||||
} else {
|
||||
superTypeRefs += StandardClassIds.Function.toLookupTag()
|
||||
.constructClassType(arrayOf(typeArguments.last().type), isNullable = false)
|
||||
.toFirResolvedTypeRef()
|
||||
}
|
||||
|
||||
addDeclaration(
|
||||
buildSimpleFunction {
|
||||
moduleData = this@SyntheticFunctionalInterfaceCache.moduleData
|
||||
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
|
||||
origin = FirDeclarationOrigin.BuiltIns
|
||||
returnTypeRef = typeArguments.last()
|
||||
this.name = name
|
||||
status = functionStatus
|
||||
symbol = FirNamedFunctionSymbol(
|
||||
CallableId(packageFqName, relativeClassName, name)
|
||||
)
|
||||
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
|
||||
valueParameters += typeArguments.dropLast(1).mapIndexed { index, typeArgument ->
|
||||
val parameterName = Name.identifier("p${index + 1}")
|
||||
buildValueParameter {
|
||||
moduleData = this@SyntheticFunctionalInterfaceCache.moduleData
|
||||
containingFunctionSymbol = this@buildSimpleFunction.symbol
|
||||
origin = FirDeclarationOrigin.BuiltIns
|
||||
resolvePhase = FirResolvePhase.ANALYZED_DEPENDENCIES
|
||||
returnTypeRef = typeArgument
|
||||
this.name = parameterName
|
||||
symbol = FirValueParameterSymbol(parameterName)
|
||||
defaultValue = null
|
||||
isCrossinline = false
|
||||
isNoinline = false
|
||||
isVararg = false
|
||||
}
|
||||
}
|
||||
dispatchReceiverType = classId.defaultType(this@klass.typeParameters.map { it.symbol })
|
||||
kind.annotationOnInvokeClassId?.let { annotationClassId ->
|
||||
annotations += buildAnnotation {
|
||||
annotationTypeRef = annotationClassId
|
||||
.constructClassLikeType(emptyArray(), isNullable = false)
|
||||
.toFirResolvedTypeRef()
|
||||
argumentMapping = FirEmptyAnnotationArgumentMapping
|
||||
}
|
||||
}
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun ConeFunctionalTypeKind.classId(arity: Int) = ClassId(packageFqName, numberedClassName(arity))
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user