[IR] Introduce API to register generated IR declaration to be present in metatada
KT-63881
This commit is contained in:
+33
-43
@@ -7,17 +7,18 @@ package org.jetbrains.kotlin.fir.serialization
|
|||||||
|
|
||||||
import org.jetbrains.kotlin.fir.FirSession
|
import org.jetbrains.kotlin.fir.FirSession
|
||||||
import org.jetbrains.kotlin.fir.FirSessionComponent
|
import org.jetbrains.kotlin.fir.FirSessionComponent
|
||||||
import org.jetbrains.kotlin.fir.caches.FirCache
|
import org.jetbrains.kotlin.fir.containingClassLookupTag
|
||||||
import org.jetbrains.kotlin.fir.caches.firCachesFactory
|
|
||||||
import org.jetbrains.kotlin.fir.declarations.*
|
import org.jetbrains.kotlin.fir.declarations.*
|
||||||
import org.jetbrains.kotlin.fir.extensions.FirDeclarationsForMetadataProviderExtension
|
import org.jetbrains.kotlin.fir.extensions.FirDeclarationsForMetadataProviderExtension
|
||||||
import org.jetbrains.kotlin.fir.extensions.declarationForMetadataProviders
|
import org.jetbrains.kotlin.fir.extensions.declarationForMetadataProviders
|
||||||
import org.jetbrains.kotlin.fir.extensions.extensionService
|
import org.jetbrains.kotlin.fir.extensions.extensionService
|
||||||
import org.jetbrains.kotlin.fir.render
|
|
||||||
import org.jetbrains.kotlin.fir.resolve.ScopeSession
|
import org.jetbrains.kotlin.fir.resolve.ScopeSession
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.toFirRegularClass
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirClassLikeSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirClassLikeSymbol
|
||||||
import org.jetbrains.kotlin.fir.symbols.impl.FirClassSymbol
|
import org.jetbrains.kotlin.fir.symbols.impl.FirClassSymbol
|
||||||
import org.jetbrains.kotlin.name.FqName
|
import org.jetbrains.kotlin.name.FqName
|
||||||
|
import org.jetbrains.kotlin.utils.addToStdlib.getOrPut
|
||||||
|
import org.jetbrains.kotlin.utils.addToStdlib.shouldNotBeCalled
|
||||||
|
|
||||||
abstract class FirProvidedDeclarationsForMetadataService : FirSessionComponent {
|
abstract class FirProvidedDeclarationsForMetadataService : FirSessionComponent {
|
||||||
companion object {
|
companion object {
|
||||||
@@ -32,6 +33,8 @@ abstract class FirProvidedDeclarationsForMetadataService : FirSessionComponent {
|
|||||||
abstract fun getProvidedCallables(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirCallableDeclaration>
|
abstract fun getProvidedCallables(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirCallableDeclaration>
|
||||||
abstract fun getProvidedNestedClassifiers(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirClassLikeSymbol<*>>
|
abstract fun getProvidedNestedClassifiers(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirClassLikeSymbol<*>>
|
||||||
|
|
||||||
|
abstract fun registerDeclaration(declaration: FirCallableDeclaration)
|
||||||
|
|
||||||
private object Empty : FirProvidedDeclarationsForMetadataService() {
|
private object Empty : FirProvidedDeclarationsForMetadataService() {
|
||||||
override fun getProvidedTopLevelDeclarations(packageFqName: FqName, scopeSession: ScopeSession): List<FirDeclaration> {
|
override fun getProvidedTopLevelDeclarations(packageFqName: FqName, scopeSession: ScopeSession): List<FirDeclaration> {
|
||||||
return emptyList()
|
return emptyList()
|
||||||
@@ -48,70 +51,57 @@ abstract class FirProvidedDeclarationsForMetadataService : FirSessionComponent {
|
|||||||
override fun getProvidedNestedClassifiers(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirClassLikeSymbol<*>> {
|
override fun getProvidedNestedClassifiers(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirClassLikeSymbol<*>> {
|
||||||
return emptyList()
|
return emptyList()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun registerDeclaration(declaration: FirCallableDeclaration) {
|
||||||
|
shouldNotBeCalled()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private class FirProvidedDeclarationsForMetadataServiceImpl(
|
private class FirProvidedDeclarationsForMetadataServiceImpl(
|
||||||
session: FirSession,
|
private val session: FirSession,
|
||||||
private val extensionDeclarationProviders: List<FirDeclarationsForMetadataProviderExtension>
|
private val extensionDeclarationProviders: List<FirDeclarationsForMetadataProviderExtension>
|
||||||
) : FirProvidedDeclarationsForMetadataService() {
|
) : FirProvidedDeclarationsForMetadataService() {
|
||||||
private val cachesFactory = session.firCachesFactory
|
private val topLevelsCache: MutableMap<FqName, MutableList<FirDeclaration>> =
|
||||||
|
mutableMapOf()
|
||||||
|
|
||||||
private val topLevelsCache: FirCache<FqName, List<FirDeclaration>, ScopeSession> =
|
private val memberCache: MutableMap<FirClassSymbol<*>, ClassDeclarations> =
|
||||||
cachesFactory.createCache(::computeTopLevelDeclarations)
|
mutableMapOf()
|
||||||
|
|
||||||
private val membersCache: FirCache<FirClassSymbol<*>, ClassDeclarations, ScopeSession> =
|
override fun registerDeclaration(declaration: FirCallableDeclaration) {
|
||||||
cachesFactory.createCache(::computeMemberDeclarations)
|
val containingClass = declaration.containingClassLookupTag()?.toFirRegularClass(session)
|
||||||
|
if (containingClass == null) {
|
||||||
private fun computeTopLevelDeclarations(packageFqName: FqName, scopeSession: ScopeSession): List<FirDeclaration> {
|
val list = topLevelsCache.getOrPut(declaration.symbol.callableId.packageName) { mutableListOf() }
|
||||||
return buildList {
|
list += declaration
|
||||||
for (extensionProvider in extensionDeclarationProviders) {
|
} else {
|
||||||
for (declaration in extensionProvider.provideTopLevelDeclarations(packageFqName, scopeSession)) {
|
val declarations = memberCache.getOrPut(containingClass.symbol) { ClassDeclarations() }
|
||||||
add(declaration)
|
when (declaration) {
|
||||||
}
|
is FirConstructor -> declarations.providedConstructors += declaration
|
||||||
|
else -> declarations.providedCallables += declaration
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getProvidedTopLevelDeclarations(packageFqName: FqName, scopeSession: ScopeSession): List<FirDeclaration> {
|
override fun getProvidedTopLevelDeclarations(packageFqName: FqName, scopeSession: ScopeSession): List<FirDeclaration> {
|
||||||
return topLevelsCache.getValue(packageFqName, scopeSession)
|
return topLevelsCache[packageFqName] ?: emptyList()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getProvidedConstructors(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirConstructor> {
|
override fun getProvidedConstructors(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirConstructor> {
|
||||||
return membersCache.getValue(owner, scopeSession).providedConstructors
|
return memberCache[owner]?.providedConstructors ?: emptyList()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getProvidedCallables(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirCallableDeclaration> {
|
override fun getProvidedCallables(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirCallableDeclaration> {
|
||||||
return membersCache.getValue(owner, scopeSession).providedCallables
|
return memberCache[owner]?.providedCallables ?: emptyList()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getProvidedNestedClassifiers(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirClassLikeSymbol<*>> {
|
override fun getProvidedNestedClassifiers(owner: FirClassSymbol<*>, scopeSession: ScopeSession): List<FirClassLikeSymbol<*>> {
|
||||||
return membersCache.getValue(owner, scopeSession).providedNestedClasses
|
// TODO: remove
|
||||||
|
return emptyList()
|
||||||
}
|
}
|
||||||
|
|
||||||
private data class ClassDeclarations(
|
private class ClassDeclarations {
|
||||||
val providedCallables: List<FirCallableDeclaration>,
|
val providedCallables: MutableList<FirCallableDeclaration> = mutableListOf()
|
||||||
val providedConstructors: List<FirConstructor>,
|
val providedConstructors: MutableList<FirConstructor> = mutableListOf()
|
||||||
val providedNestedClasses: List<FirClassLikeSymbol<*>>,
|
|
||||||
)
|
|
||||||
|
|
||||||
private fun computeMemberDeclarations(symbol: FirClassSymbol<*>, scopeSession: ScopeSession): ClassDeclarations {
|
|
||||||
val providedCallables = mutableListOf<FirCallableDeclaration>()
|
|
||||||
val providedConstructors = mutableListOf<FirConstructor>()
|
|
||||||
val providedNestedClassifiers = mutableListOf<FirClassLikeSymbol<*>>()
|
|
||||||
|
|
||||||
for (extensionProvider in extensionDeclarationProviders) {
|
|
||||||
for (declaration in extensionProvider.provideDeclarationsForClass(symbol.fir, scopeSession)) {
|
|
||||||
when (declaration) {
|
|
||||||
is FirConstructor -> providedConstructors += declaration
|
|
||||||
is FirCallableDeclaration -> providedCallables += declaration
|
|
||||||
is FirClassLikeDeclaration -> providedNestedClassifiers += declaration.symbol
|
|
||||||
else -> error("Unsupported declaration type in: $symbol ${declaration.render()}")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return ClassDeclarations(providedCallables, providedConstructors, providedNestedClassifiers)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+292
-88
@@ -5,29 +5,39 @@
|
|||||||
|
|
||||||
package org.jetbrains.kotlin.fir.backend
|
package org.jetbrains.kotlin.fir.backend
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.GeneratedDeclarationKey
|
||||||
import org.jetbrains.kotlin.backend.common.extensions.IrGeneratedDeclarationsRegistrar
|
import org.jetbrains.kotlin.backend.common.extensions.IrGeneratedDeclarationsRegistrar
|
||||||
import org.jetbrains.kotlin.fir.FirSession
|
import org.jetbrains.kotlin.descriptors.Modality
|
||||||
|
import org.jetbrains.kotlin.fir.*
|
||||||
import org.jetbrains.kotlin.fir.declarations.*
|
import org.jetbrains.kotlin.fir.declarations.*
|
||||||
|
import org.jetbrains.kotlin.fir.declarations.builder.*
|
||||||
|
import org.jetbrains.kotlin.fir.declarations.impl.FirResolvedDeclarationStatusImpl
|
||||||
import org.jetbrains.kotlin.fir.declarations.utils.classId
|
import org.jetbrains.kotlin.fir.declarations.utils.classId
|
||||||
import org.jetbrains.kotlin.fir.expressions.FirAnnotation
|
import org.jetbrains.kotlin.fir.expressions.FirAnnotation
|
||||||
import org.jetbrains.kotlin.fir.expressions.builder.buildAnnotation
|
import org.jetbrains.kotlin.fir.expressions.builder.buildAnnotation
|
||||||
import org.jetbrains.kotlin.fir.expressions.builder.buildAnnotationArgumentMapping
|
import org.jetbrains.kotlin.fir.expressions.builder.buildAnnotationArgumentMapping
|
||||||
import org.jetbrains.kotlin.fir.expressions.builder.buildConstExpression
|
import org.jetbrains.kotlin.fir.expressions.builder.buildConstExpression
|
||||||
import org.jetbrains.kotlin.fir.packageFqName
|
import org.jetbrains.kotlin.fir.expressions.builder.buildExpressionStub
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.defaultType
|
||||||
import org.jetbrains.kotlin.fir.resolve.providers.getContainingFile
|
import org.jetbrains.kotlin.fir.resolve.providers.getContainingFile
|
||||||
import org.jetbrains.kotlin.fir.resolve.providers.toSymbol
|
import org.jetbrains.kotlin.fir.resolve.providers.toSymbol
|
||||||
|
import org.jetbrains.kotlin.fir.resolve.toFirRegularClass
|
||||||
import org.jetbrains.kotlin.fir.serialization.FirAdditionalMetadataProvider
|
import org.jetbrains.kotlin.fir.serialization.FirAdditionalMetadataProvider
|
||||||
import org.jetbrains.kotlin.fir.types.constructClassType
|
import org.jetbrains.kotlin.fir.serialization.providedDeclarationsForMetadataService
|
||||||
import org.jetbrains.kotlin.fir.types.toFirResolvedTypeRef
|
import org.jetbrains.kotlin.fir.symbols.ConeClassifierLookupTag
|
||||||
import org.jetbrains.kotlin.fir.types.toLookupTag
|
import org.jetbrains.kotlin.fir.symbols.impl.FirConstructorSymbol
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrConstructor
|
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrDeclaration
|
import org.jetbrains.kotlin.fir.symbols.impl.FirTypeParameterSymbol
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrSimpleFunction
|
import org.jetbrains.kotlin.fir.symbols.impl.FirValueParameterSymbol
|
||||||
import org.jetbrains.kotlin.ir.declarations.nameWithPackage
|
import org.jetbrains.kotlin.fir.types.*
|
||||||
|
import org.jetbrains.kotlin.fir.types.impl.FirImplicitTypeRefImplWithoutSource
|
||||||
|
import org.jetbrains.kotlin.ir.declarations.*
|
||||||
import org.jetbrains.kotlin.ir.expressions.IrConst
|
import org.jetbrains.kotlin.ir.expressions.IrConst
|
||||||
import org.jetbrains.kotlin.ir.expressions.IrConstKind
|
import org.jetbrains.kotlin.ir.expressions.IrConstKind
|
||||||
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
||||||
|
import org.jetbrains.kotlin.ir.symbols.IrClassifierSymbol
|
||||||
import org.jetbrains.kotlin.ir.symbols.UnsafeDuringIrConstructionAPI
|
import org.jetbrains.kotlin.ir.symbols.UnsafeDuringIrConstructionAPI
|
||||||
|
import org.jetbrains.kotlin.ir.types.*
|
||||||
import org.jetbrains.kotlin.ir.util.*
|
import org.jetbrains.kotlin.ir.util.*
|
||||||
import org.jetbrains.kotlin.name.ClassId
|
import org.jetbrains.kotlin.name.ClassId
|
||||||
import org.jetbrains.kotlin.name.Name
|
import org.jetbrains.kotlin.name.Name
|
||||||
@@ -37,6 +47,12 @@ import org.jetbrains.kotlin.utils.addToStdlib.runIf
|
|||||||
// opt-in is safe, this code runs after fir2ir is over and all symbols are bound
|
// opt-in is safe, this code runs after fir2ir is over and all symbols are bound
|
||||||
@OptIn(UnsafeDuringIrConstructionAPI::class)
|
@OptIn(UnsafeDuringIrConstructionAPI::class)
|
||||||
class Fir2IrIrGeneratedDeclarationsRegistrar(private val components: Fir2IrComponents) : IrGeneratedDeclarationsRegistrar() {
|
class Fir2IrIrGeneratedDeclarationsRegistrar(private val components: Fir2IrComponents) : IrGeneratedDeclarationsRegistrar() {
|
||||||
|
private val session: FirSession
|
||||||
|
get() = components.session
|
||||||
|
|
||||||
|
private val implicitType: FirImplicitTypeRef
|
||||||
|
get() = FirImplicitTypeRefImplWithoutSource
|
||||||
|
|
||||||
private val generatedIrDeclarationsByFileByOffset = mutableMapOf<String, MutableMap<Pair<Int, Int>, MutableList<IrConstructorCall>>>()
|
private val generatedIrDeclarationsByFileByOffset = mutableMapOf<String, MutableMap<Pair<Int, Int>, MutableList<IrConstructorCall>>>()
|
||||||
|
|
||||||
private fun IrConstructorCall.hasOnlySupportedAnnotationArgumentTypes(): Boolean {
|
private fun IrConstructorCall.hasOnlySupportedAnnotationArgumentTypes(): Boolean {
|
||||||
@@ -62,10 +78,276 @@ class Fir2IrIrGeneratedDeclarationsRegistrar(private val components: Fir2IrCompo
|
|||||||
declaration.annotations += annotations
|
declaration.annotations += annotations
|
||||||
}
|
}
|
||||||
|
|
||||||
fun createMetadataAnnotationsProvider(): FirAdditionalMetadataAnnotationsProvider {
|
override fun registerFunctionAsMetadataVisible(irFunction: IrSimpleFunction) {
|
||||||
|
if (irFunction.isLocal || irFunction.parentClassOrNull?.isLocal == true) return
|
||||||
|
val firFunction = buildSimpleFunction {
|
||||||
|
moduleData = session.moduleData
|
||||||
|
origin = GeneratedForMetadata.origin
|
||||||
|
status = FirResolvedDeclarationStatusImpl(
|
||||||
|
irFunction.visibility.delegate,
|
||||||
|
irFunction.modality,
|
||||||
|
irFunction.visibility.delegate.toEffectiveVisibility(owner = null)
|
||||||
|
).apply {
|
||||||
|
isExpect = irFunction.isExpect
|
||||||
|
isActual = false
|
||||||
|
isOverride = irFunction.overriddenSymbols.isNotEmpty()
|
||||||
|
isInfix = irFunction.isInfix
|
||||||
|
isInline = irFunction.isInline
|
||||||
|
isTailRec = irFunction.isTailrec
|
||||||
|
isSuspend = irFunction.isSuspend
|
||||||
|
}
|
||||||
|
returnTypeRef = implicitType
|
||||||
|
dispatchReceiverType = irFunction.parent.toFirClass()?.defaultType()
|
||||||
|
// contextReceivers
|
||||||
|
// valueParameters
|
||||||
|
name = irFunction.name
|
||||||
|
symbol = FirNamedFunctionSymbol(irFunction.callableId)
|
||||||
|
// annotations
|
||||||
|
irFunction.typeParameters.mapTo(typeParameters) {
|
||||||
|
buildTypeParameter {
|
||||||
|
moduleData = session.moduleData
|
||||||
|
origin = GeneratedForMetadata.origin
|
||||||
|
name = it.name
|
||||||
|
symbol = FirTypeParameterSymbol()
|
||||||
|
containingDeclarationSymbol = this@buildSimpleFunction.symbol
|
||||||
|
variance = it.variance
|
||||||
|
isReified = it.isReified
|
||||||
|
// bounds
|
||||||
|
// annotations
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
with(TypeConverter(irFunction, firFunction)) {
|
||||||
|
with(firFunction) {
|
||||||
|
replaceReturnTypeRef(irFunction.returnType.toConeType().toFirResolvedTypeRef())
|
||||||
|
val valueParameters = irFunction.valueParameters.map {
|
||||||
|
buildValueParameter {
|
||||||
|
moduleData = session.moduleData
|
||||||
|
origin = GeneratedForMetadata.origin
|
||||||
|
returnTypeRef = it.type.toConeType().toFirResolvedTypeRef()
|
||||||
|
name = it.name
|
||||||
|
symbol = FirValueParameterSymbol(name)
|
||||||
|
if (it.defaultValue != null) {
|
||||||
|
defaultValue = buildExpressionStub {
|
||||||
|
coneTypeOrNull = this@buildValueParameter.returnTypeRef.coneType
|
||||||
|
}
|
||||||
|
}
|
||||||
|
containingFunctionSymbol = firFunction.symbol
|
||||||
|
isCrossinline = it.isCrossinline
|
||||||
|
isNoinline = it.isNoinline
|
||||||
|
isVararg = it.isVararg
|
||||||
|
annotations.addAll(it.convertAnnotations())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
replaceValueParameters(valueParameters)
|
||||||
|
|
||||||
|
for ((firParameter, irParameter) in typeParameters.zip(irFunction.typeParameters)) {
|
||||||
|
val newBounds = irParameter.superTypes.map { it.toConeType().toFirResolvedTypeRef() }
|
||||||
|
firParameter.replaceBounds(newBounds)
|
||||||
|
firParameter.replaceAnnotations(irParameter.convertAnnotations())
|
||||||
|
}
|
||||||
|
|
||||||
|
replaceAnnotations(irFunction.convertAnnotations())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
session.providedDeclarationsForMetadataService.registerDeclaration(firFunction)
|
||||||
|
|
||||||
|
irFunction.metadata = FirMetadataSource.Function(firFunction)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun registerConstructorAsMetadataVisible(irConstructor: IrConstructor) {
|
||||||
|
if (irConstructor.isLocal || irConstructor.parentAsClass.isLocal) return
|
||||||
|
val constructedClass = irConstructor.parent.toFirClass()
|
||||||
|
?: error("Fir class for constructor ${irConstructor.render()} not found")
|
||||||
|
val firConstructor = buildConstructor {
|
||||||
|
moduleData = session.moduleData
|
||||||
|
origin = GeneratedForMetadata.origin
|
||||||
|
status = FirResolvedDeclarationStatusImpl(
|
||||||
|
irConstructor.visibility.delegate,
|
||||||
|
Modality.FINAL,
|
||||||
|
irConstructor.visibility.delegate.toEffectiveVisibility(owner = null)
|
||||||
|
).apply {
|
||||||
|
isExpect = irConstructor.isExpect
|
||||||
|
isActual = false
|
||||||
|
}
|
||||||
|
returnTypeRef = implicitType
|
||||||
|
|
||||||
|
// contextReceivers
|
||||||
|
// valueParameters
|
||||||
|
symbol = FirConstructorSymbol(constructedClass.classId)
|
||||||
|
// annotations
|
||||||
|
constructedClass.typeParameters.mapTo(typeParameters) { buildConstructedClassTypeParameterRef { symbol = it.symbol } }
|
||||||
|
}
|
||||||
|
|
||||||
|
with(TypeConverter(irConstructor, firConstructor)) {
|
||||||
|
with(firConstructor) {
|
||||||
|
replaceReturnTypeRef(irConstructor.returnType.toConeType().toFirResolvedTypeRef())
|
||||||
|
val valueParameters = irConstructor.valueParameters.map {
|
||||||
|
buildValueParameter {
|
||||||
|
moduleData = session.moduleData
|
||||||
|
origin = GeneratedForMetadata.origin
|
||||||
|
returnTypeRef = it.type.toConeType().toFirResolvedTypeRef()
|
||||||
|
name = it.name
|
||||||
|
symbol = FirValueParameterSymbol(name)
|
||||||
|
if (it.defaultValue != null) {
|
||||||
|
defaultValue = buildExpressionStub {
|
||||||
|
coneTypeOrNull = this@buildValueParameter.returnTypeRef.coneType
|
||||||
|
}
|
||||||
|
}
|
||||||
|
containingFunctionSymbol = firConstructor.symbol
|
||||||
|
isCrossinline = it.isCrossinline
|
||||||
|
isNoinline = it.isNoinline
|
||||||
|
isVararg = it.isVararg
|
||||||
|
annotations.addAll(it.convertAnnotations())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
replaceValueParameters(valueParameters)
|
||||||
|
replaceAnnotations(irConstructor.convertAnnotations())
|
||||||
|
containingClassForStaticMemberAttr = constructedClass.symbol.toLookupTag()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
session.providedDeclarationsForMetadataService.registerDeclaration(firConstructor)
|
||||||
|
|
||||||
|
irConstructor.metadata = FirMetadataSource.Function(firConstructor)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun createAdditionalMetadataProvider(): FirAdditionalMetadataProvider {
|
||||||
return Provider()
|
return Provider()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun IrDeclarationParent.toFirClass(): FirRegularClass? {
|
||||||
|
return (this as? IrClass)?.classIdOrFail?.toLookupTag()?.toFirRegularClass(session)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun IrAnnotationContainer.convertAnnotations(): List<FirAnnotation> {
|
||||||
|
return this.annotations.map { it.toFirAnnotation() }
|
||||||
|
}
|
||||||
|
|
||||||
|
private inner class TypeConverter(val originalFunction: IrFunction, val convertedFunction: FirFunction) {
|
||||||
|
fun IrType.toConeType(): ConeKotlinType {
|
||||||
|
return when (this) {
|
||||||
|
is IrSimpleType -> {
|
||||||
|
val lookupTag = classifier.toLookupTag()
|
||||||
|
lookupTag.constructType(
|
||||||
|
this.arguments.map { it.toConeTypeProjection() }.toTypedArray(),
|
||||||
|
isNullable = this.isNullable()
|
||||||
|
)
|
||||||
|
}
|
||||||
|
is IrDynamicType -> ConeDynamicType.create(session)
|
||||||
|
else -> error("Unsupported IR type: $this")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun IrTypeArgument.toConeTypeProjection(): ConeTypeProjection {
|
||||||
|
return when (this) {
|
||||||
|
is IrStarProjection -> ConeStarProjection
|
||||||
|
is IrTypeProjection -> type.toConeType().toTypeProjection(variance)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun IrClassifierSymbol.toLookupTag(): ConeClassifierLookupTag {
|
||||||
|
return when (val owner = owner) {
|
||||||
|
is IrClass -> owner.classIdOrFail.toLookupTag()
|
||||||
|
is IrTypeParameter -> {
|
||||||
|
val typeParameter = when (val parent = owner.parent) {
|
||||||
|
originalFunction -> convertedFunction.typeParameters[owner.index]
|
||||||
|
is IrClass -> {
|
||||||
|
val firClass = parent.classIdOrFail.toLookupTag().toFirRegularClass(session)
|
||||||
|
?: error("Fir class for ${parent.render()} not found")
|
||||||
|
firClass.typeParameters[owner.index]
|
||||||
|
}
|
||||||
|
else -> error("Unsupported type parameter container: ${parent.render()}")
|
||||||
|
}
|
||||||
|
typeParameter.symbol.toLookupTag()
|
||||||
|
}
|
||||||
|
else -> error("Unsupported IR classifier: ${owner.render()}")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun IrConstructorCall.toFirAnnotation(): FirAnnotation {
|
||||||
|
val annotationClassId = this.symbol.owner.constructedClass.classId!!
|
||||||
|
return buildAnnotation {
|
||||||
|
annotationTypeRef = annotationClassId
|
||||||
|
.toLookupTag()
|
||||||
|
.constructClassType(typeArguments = emptyArray(), isNullable = false)
|
||||||
|
.toFirResolvedTypeRef()
|
||||||
|
argumentMapping = buildAnnotationArgumentMapping {
|
||||||
|
for (i in 0 until this@toFirAnnotation.valueArgumentsCount) {
|
||||||
|
val name = this@toFirAnnotation.symbol.owner.valueParameters[i].name
|
||||||
|
val argument = this@toFirAnnotation.getValueArgument(i) as IrConst<*>
|
||||||
|
this.mapping[name] = when (argument.kind) {
|
||||||
|
IrConstKind.Boolean -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Boolean,
|
||||||
|
argument.value as Boolean,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Byte -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Byte,
|
||||||
|
argument.value as Byte,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Char -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Char,
|
||||||
|
argument.value as Char,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Double -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Double,
|
||||||
|
argument.value as Double,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Float -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Float,
|
||||||
|
argument.value as Float,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Int -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Int,
|
||||||
|
argument.value as Int,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Long -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Long,
|
||||||
|
argument.value as Long,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Null -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Null,
|
||||||
|
value = null,
|
||||||
|
setType = true
|
||||||
|
)
|
||||||
|
IrConstKind.Short -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.Short,
|
||||||
|
argument.value as Short,
|
||||||
|
setType = false
|
||||||
|
)
|
||||||
|
IrConstKind.String -> buildConstExpression(
|
||||||
|
source = null,
|
||||||
|
ConstantValueKind.String,
|
||||||
|
argument.value as String,
|
||||||
|
setType = false
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private object GeneratedForMetadata : GeneratedDeclarationKey()
|
||||||
|
|
||||||
private inner class Provider : FirAdditionalMetadataProvider() {
|
private inner class Provider : FirAdditionalMetadataProvider() {
|
||||||
override fun findGeneratedAnnotationsFor(declaration: FirDeclaration): List<FirAnnotation> {
|
override fun findGeneratedAnnotationsFor(declaration: FirDeclaration): List<FirAnnotation> {
|
||||||
val irAnnotations = extractGeneratedIrDeclarations(declaration).takeUnless { it.isEmpty() } ?: return emptyList()
|
val irAnnotations = extractGeneratedIrDeclarations(declaration).takeUnless { it.isEmpty() } ?: return emptyList()
|
||||||
@@ -111,83 +393,5 @@ class Fir2IrIrGeneratedDeclarationsRegistrar(private val components: Fir2IrCompo
|
|||||||
|
|
||||||
private val ClassId.topmostParentClassId: ClassId
|
private val ClassId.topmostParentClassId: ClassId
|
||||||
get() = parentClassId?.topmostParentClassId ?: this
|
get() = parentClassId?.topmostParentClassId ?: this
|
||||||
|
|
||||||
private fun IrConstructorCall.toFirAnnotation(): FirAnnotation {
|
|
||||||
val annotationClassId = this.symbol.owner.constructedClass.classId!!
|
|
||||||
return buildAnnotation {
|
|
||||||
annotationTypeRef = annotationClassId
|
|
||||||
.toLookupTag()
|
|
||||||
.constructClassType(typeArguments = emptyArray(), isNullable = false)
|
|
||||||
.toFirResolvedTypeRef()
|
|
||||||
argumentMapping = buildAnnotationArgumentMapping {
|
|
||||||
for (i in 0 until this@toFirAnnotation.valueArgumentsCount) {
|
|
||||||
val name = this@toFirAnnotation.symbol.owner.valueParameters[i].name
|
|
||||||
val argument = this@toFirAnnotation.getValueArgument(i) as IrConst<*>
|
|
||||||
this.mapping[name] = when (argument.kind) {
|
|
||||||
IrConstKind.Boolean -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Boolean,
|
|
||||||
argument.value as Boolean,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Byte -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Byte,
|
|
||||||
argument.value as Byte,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Char -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Char,
|
|
||||||
argument.value as Char,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Double -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Double,
|
|
||||||
argument.value as Double,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Float -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Float,
|
|
||||||
argument.value as Float,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Int -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Int,
|
|
||||||
argument.value as Int,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Long -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Long,
|
|
||||||
argument.value as Long,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Null -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Null,
|
|
||||||
value = null,
|
|
||||||
setType = true
|
|
||||||
)
|
|
||||||
IrConstKind.Short -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.Short,
|
|
||||||
argument.value as Short,
|
|
||||||
setType = false
|
|
||||||
)
|
|
||||||
IrConstKind.String -> buildConstExpression(
|
|
||||||
source = null,
|
|
||||||
ConstantValueKind.String,
|
|
||||||
argument.value as String,
|
|
||||||
setType = false
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+8
@@ -5,7 +5,9 @@
|
|||||||
|
|
||||||
package org.jetbrains.kotlin.backend.common.extensions
|
package org.jetbrains.kotlin.backend.common.extensions
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.ir.declarations.IrConstructor
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrDeclaration
|
import org.jetbrains.kotlin.ir.declarations.IrDeclaration
|
||||||
|
import org.jetbrains.kotlin.ir.declarations.IrSimpleFunction
|
||||||
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
import org.jetbrains.kotlin.ir.expressions.IrConstructorCall
|
||||||
|
|
||||||
abstract class IrGeneratedDeclarationsRegistrar {
|
abstract class IrGeneratedDeclarationsRegistrar {
|
||||||
@@ -14,4 +16,10 @@ abstract class IrGeneratedDeclarationsRegistrar {
|
|||||||
fun addMetadataVisibleAnnotationsToElement(declaration: IrDeclaration, vararg annotations: IrConstructorCall) {
|
fun addMetadataVisibleAnnotationsToElement(declaration: IrDeclaration, vararg annotations: IrConstructorCall) {
|
||||||
addMetadataVisibleAnnotationsToElement(declaration, annotations.toList())
|
addMetadataVisibleAnnotationsToElement(declaration, annotations.toList())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
abstract fun registerFunctionAsMetadataVisible(irFunction: IrSimpleFunction)
|
||||||
|
abstract fun registerConstructorAsMetadataVisible(irConstructor: IrConstructor)
|
||||||
|
|
||||||
|
// TODO: KT-63881
|
||||||
|
// abstract fun registerPropertyAsMetadataVisible(irProperty: IrProperty)
|
||||||
}
|
}
|
||||||
|
|||||||
+5
@@ -186,5 +186,10 @@ open class IrPluginContextImpl constructor(
|
|||||||
override fun addMetadataVisibleAnnotationsToElement(declaration: IrDeclaration, annotations: List<IrConstructorCall>) {
|
override fun addMetadataVisibleAnnotationsToElement(declaration: IrDeclaration, annotations: List<IrConstructorCall>) {
|
||||||
declaration.annotations += annotations
|
declaration.annotations += annotations
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun registerFunctionAsMetadataVisible(irFunction: IrSimpleFunction) {}
|
||||||
|
|
||||||
|
override fun registerConstructorAsMetadataVisible(irConstructor: IrConstructor) {}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+1
-1
@@ -89,7 +89,7 @@ internal fun PhaseContext.firSerializerBase(
|
|||||||
},
|
},
|
||||||
allowErrorTypes = false,
|
allowErrorTypes = false,
|
||||||
exportKDoc = shouldExportKDoc(),
|
exportKDoc = shouldExportKDoc(),
|
||||||
additionalMetadataProvider = fir2IrInput?.components?.annotationsFromPluginRegistrar?.createMetadataAnnotationsProvider()
|
additionalMetadataProvider = fir2IrInput?.components?.annotationsFromPluginRegistrar?.createAdditionalMetadataProvider()
|
||||||
),
|
),
|
||||||
configuration.languageVersionSettings,
|
configuration.languageVersionSettings,
|
||||||
produceHeaderKlib,
|
produceHeaderKlib,
|
||||||
|
|||||||
+1
@@ -84,6 +84,7 @@ class AllPropertiesConstructorIrGenerator(val context: IrPluginContext) : IrElem
|
|||||||
}
|
}
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
context.metadataDeclarationRegistrar.registerConstructorAsMetadataVisible(ctor)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user