[KLIB] Create an abstract class for module deserializer
- Introduce Ir-based Functional interface factory - Switch from LazyIr to pure - Use kotlin library to access raw bytes - Link dirty files against IC cache and dependencies instead of LazyIr - Move `DescriptorByIdSignatureFinder` from K/N to common - Support inline-bodies only MODE
This commit is contained in:
+63
@@ -0,0 +1,63 @@
|
||||
/*
|
||||
* 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.backend.common.serialization
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.ir.util.IdSignature
|
||||
import org.jetbrains.kotlin.ir.util.KotlinMangler
|
||||
|
||||
class DescriptorByIdSignatureFinder(private val moduleDescriptor: ModuleDescriptor, private val mangler: KotlinMangler.DescriptorMangler) {
|
||||
fun findDescriptorBySignature(signature: IdSignature): DeclarationDescriptor? = when (signature) {
|
||||
is IdSignature.AccessorSignature -> findDescriptorForAccessorSignature(signature)
|
||||
is IdSignature.PublicSignature -> findDescriptorForPublicSignature(signature)
|
||||
else -> error("only PublicSignature or AccessorSignature should reach this point, got $signature")
|
||||
}
|
||||
|
||||
private fun findDescriptorForAccessorSignature(signature: IdSignature.AccessorSignature): DeclarationDescriptor? {
|
||||
val propertyDescriptor = findDescriptorBySignature(signature.propertySignature) as? PropertyDescriptor
|
||||
?: return null
|
||||
return propertyDescriptor.accessors.singleOrNull {
|
||||
it.name == signature.accessorSignature.declarationFqn.shortName()
|
||||
}
|
||||
}
|
||||
|
||||
private fun findDescriptorForPublicSignature(signature: IdSignature.PublicSignature): DeclarationDescriptor? {
|
||||
val packageDescriptor = moduleDescriptor.getPackage(signature.packageFqName())
|
||||
val pathSegments = signature.declarationFqn.pathSegments()
|
||||
val toplevelDescriptors = packageDescriptor.memberScope.getContributedDescriptors { name -> name == pathSegments.first() }
|
||||
.filter { it.name == pathSegments.first() }
|
||||
val candidates = pathSegments.drop(1).fold(toplevelDescriptors) { acc, current ->
|
||||
acc.flatMap { container ->
|
||||
val classDescriptor = container as? ClassDescriptor
|
||||
?: return@flatMap emptyList<DeclarationDescriptor>()
|
||||
val nextStepCandidates = classDescriptor.constructors +
|
||||
classDescriptor.unsubstitutedMemberScope.getContributedDescriptors { name -> name == current } +
|
||||
// Static scope is required only for Enum.values() and Enum.valueOf().
|
||||
classDescriptor.staticScope.getContributedDescriptors { name -> name == current }
|
||||
nextStepCandidates.filter { it.name == current }
|
||||
}
|
||||
}
|
||||
|
||||
return when (candidates.size) {
|
||||
1 -> candidates.first()
|
||||
else -> {
|
||||
findDescriptorByHash(candidates, signature.id)
|
||||
?: error("No descriptor found for $signature")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun findDescriptorByHash(candidates: List<DeclarationDescriptor>, id: Long?): DeclarationDescriptor? =
|
||||
candidates.firstOrNull { candidate ->
|
||||
if (id == null) {
|
||||
// We don't compute id for typealiases and classes.
|
||||
candidate is ClassDescriptor || candidate is TypeAliasDescriptor
|
||||
} else {
|
||||
val candidateHash = with(mangler) { candidate.signatureMangle }
|
||||
candidateHash == id
|
||||
}
|
||||
}
|
||||
}
|
||||
+137
@@ -0,0 +1,137 @@
|
||||
/*
|
||||
* 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.backend.common.serialization
|
||||
|
||||
import org.jetbrains.kotlin.backend.common.serialization.encodings.BinarySymbolData
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.DeserializedDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.PropertyAccessorDescriptor
|
||||
import org.jetbrains.kotlin.ir.declarations.IrModuleFragment
|
||||
import org.jetbrains.kotlin.ir.declarations.IrSymbolOwner
|
||||
import org.jetbrains.kotlin.ir.descriptors.IrBuiltIns
|
||||
import org.jetbrains.kotlin.ir.symbols.IrSymbol
|
||||
import org.jetbrains.kotlin.ir.util.IdSignature
|
||||
import org.jetbrains.kotlin.ir.util.SymbolTable
|
||||
import org.jetbrains.kotlin.library.IrLibrary
|
||||
import org.jetbrains.kotlin.library.SerializedIrFile
|
||||
import org.jetbrains.kotlin.library.impl.*
|
||||
|
||||
|
||||
class ICKotlinLibrary(private val icData: List<SerializedIrFile>) : IrLibrary {
|
||||
override val dataFlowGraph: ByteArray? = null
|
||||
|
||||
private inline fun <K, R : IrTableReader<K>> Array<R?>.itemBytes(fileIndex: Int, key: K, factory: () -> R): ByteArray {
|
||||
val reader = this[fileIndex] ?: factory().also { this[fileIndex] = it }
|
||||
|
||||
return reader.tableItemBytes(key)
|
||||
}
|
||||
|
||||
private inline fun <R : IrArrayReader> Array<R?>.itemBytes(fileIndex: Int, index: Int, factory: () -> R): ByteArray {
|
||||
val reader = this[fileIndex] ?: factory().also { this[fileIndex] = it }
|
||||
|
||||
return reader.tableItemBytes(index)
|
||||
}
|
||||
|
||||
private val indexedDeclarations = arrayOfNulls<DeclarationIrTableMemoryReader>(icData.size)
|
||||
private val indexedTypes = arrayOfNulls<IrArrayMemoryReader>(icData.size)
|
||||
private val indexedSignatures = arrayOfNulls<IrArrayMemoryReader>(icData.size)
|
||||
private val indexedStrings = arrayOfNulls<IrArrayMemoryReader>(icData.size)
|
||||
private val indexedBodies = arrayOfNulls<IrArrayMemoryReader>(icData.size)
|
||||
|
||||
override fun irDeclaration(index: Int, fileIndex: Int): ByteArray =
|
||||
indexedDeclarations.itemBytes(fileIndex, DeclarationId(index)) {
|
||||
DeclarationIrTableMemoryReader(icData[fileIndex].declarations)
|
||||
}
|
||||
|
||||
override fun type(index: Int, fileIndex: Int): ByteArray =
|
||||
indexedTypes.itemBytes(fileIndex, index) {
|
||||
IrArrayMemoryReader(icData[fileIndex].types)
|
||||
}
|
||||
|
||||
override fun signature(index: Int, fileIndex: Int): ByteArray =
|
||||
indexedSignatures.itemBytes(fileIndex, index) {
|
||||
IrArrayMemoryReader(icData[fileIndex].signatures)
|
||||
}
|
||||
|
||||
override fun string(index: Int, fileIndex: Int): ByteArray =
|
||||
indexedStrings.itemBytes(fileIndex, index) {
|
||||
IrArrayMemoryReader(icData[fileIndex].strings)
|
||||
}
|
||||
|
||||
override fun body(index: Int, fileIndex: Int): ByteArray =
|
||||
indexedBodies.itemBytes(fileIndex, index) {
|
||||
IrArrayMemoryReader(icData[fileIndex].bodies)
|
||||
}
|
||||
|
||||
override fun file(index: Int): ByteArray = icData[index].fileData
|
||||
|
||||
override fun fileCount(): Int = icData.size
|
||||
}
|
||||
|
||||
class CurrentModuleWithICDeserializer(
|
||||
private val delegate: IrModuleDeserializer,
|
||||
private val symbolTable: SymbolTable,
|
||||
private val irBuiltIns: IrBuiltIns,
|
||||
icData: List<SerializedIrFile>,
|
||||
icReaderFactory: (IrLibrary) -> IrModuleDeserializer) :
|
||||
IrModuleDeserializer(delegate.moduleDescriptor) {
|
||||
|
||||
private val dirtyDeclarations = mutableMapOf<IdSignature, IrSymbol>()
|
||||
private val icKlib = ICKotlinLibrary(icData)
|
||||
|
||||
private val icDeserializer: IrModuleDeserializer = icReaderFactory(icKlib)
|
||||
|
||||
override fun contains(idSig: IdSignature): Boolean {
|
||||
return idSig in dirtyDeclarations || idSig.topLevelSignature() in icDeserializer || idSig in delegate
|
||||
}
|
||||
|
||||
override fun deserializeIrSymbol(idSig: IdSignature, symbolKind: BinarySymbolData.SymbolKind): IrSymbol {
|
||||
dirtyDeclarations[idSig]?.let { return it }
|
||||
|
||||
if (idSig.topLevelSignature() in icDeserializer) return icDeserializer.deserializeIrSymbol(idSig, symbolKind)
|
||||
|
||||
return delegate.deserializeIrSymbol(idSig, symbolKind)
|
||||
}
|
||||
|
||||
override fun addModuleReachableTopLevel(idSig: IdSignature) {
|
||||
assert(idSig in icDeserializer)
|
||||
icDeserializer.addModuleReachableTopLevel(idSig)
|
||||
}
|
||||
|
||||
override fun deserializeReachableDeclarations() {
|
||||
icDeserializer.deserializeReachableDeclarations()
|
||||
}
|
||||
|
||||
override fun postProcess() {
|
||||
icDeserializer.postProcess()
|
||||
}
|
||||
|
||||
private fun DeclarationDescriptor.isDirtyDescriptor(): Boolean {
|
||||
if (this is PropertyAccessorDescriptor) return correspondingProperty.isDirtyDescriptor()
|
||||
return this !is DeserializedDescriptor
|
||||
}
|
||||
|
||||
override fun init() {
|
||||
val knownBuiltIns = irBuiltIns.knownBuiltins.map { (it as IrSymbolOwner).symbol }.toSet()
|
||||
symbolTable.forEachPublicSymbol {
|
||||
if (it.descriptor.isDirtyDescriptor()) { // public && non-deserialized should be dirty symbol
|
||||
if (it !in knownBuiltIns) {
|
||||
dirtyDeclarations[it.signature] = it
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
icDeserializer.init(this)
|
||||
}
|
||||
|
||||
override val klib: IrLibrary
|
||||
get() = icDeserializer.klib
|
||||
|
||||
override val moduleFragment: IrModuleFragment
|
||||
get() = delegate.moduleFragment
|
||||
override val moduleDependencies: Collection<IrModuleDeserializer>
|
||||
get() = delegate.moduleDependencies
|
||||
}
|
||||
-76
@@ -1,76 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2019 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.backend.common.serialization
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.Modality
|
||||
import org.jetbrains.kotlin.ir.declarations.*
|
||||
import org.jetbrains.kotlin.ir.symbols.IrBindableSymbol
|
||||
import org.jetbrains.kotlin.ir.util.isReal
|
||||
import org.jetbrains.kotlin.ir.util.original
|
||||
|
||||
// We may get several real supers here (e.g. see the code snippet from KT-33034).
|
||||
// TODO: Consider reworking the resolution algorithm to get a determined super declaration.
|
||||
private fun <S: IrBindableSymbol<*, D>, D: IrOverridableDeclaration<S>> D.getRealSupers(): Set<D> {
|
||||
if (this.isReal) {
|
||||
return setOf(this)
|
||||
}
|
||||
|
||||
val visited = mutableSetOf<D>()
|
||||
val realSupers = mutableSetOf<D>()
|
||||
|
||||
fun findRealSupers(declaration: D) {
|
||||
if (declaration in visited) return
|
||||
visited += declaration
|
||||
if (declaration.isReal) {
|
||||
realSupers += declaration
|
||||
} else {
|
||||
declaration.overriddenSymbols.forEach { findRealSupers(it.owner) }
|
||||
}
|
||||
}
|
||||
|
||||
findRealSupers(this)
|
||||
|
||||
if (realSupers.size > 1) {
|
||||
visited.clear()
|
||||
|
||||
fun excludeOverridden(declaration: D) {
|
||||
if (declaration in visited) return
|
||||
visited += declaration
|
||||
declaration.overriddenSymbols.forEach {
|
||||
realSupers.remove(it.owner)
|
||||
excludeOverridden(it.owner)
|
||||
}
|
||||
}
|
||||
|
||||
realSupers.toList().forEach { excludeOverridden(it) }
|
||||
}
|
||||
|
||||
return realSupers
|
||||
}
|
||||
|
||||
/**
|
||||
* Implementation of given method.
|
||||
*
|
||||
* TODO: this method is actually a part of resolve and probably duplicates another one
|
||||
*/
|
||||
fun IrSimpleFunction.resolveFakeOverride(allowAbstract: Boolean = false): IrSimpleFunction {
|
||||
val realSupers = getRealSupers()
|
||||
|
||||
return if (allowAbstract) {
|
||||
realSupers.first()
|
||||
} else {
|
||||
realSupers.single { it.modality != Modality.ABSTRACT }
|
||||
}
|
||||
}
|
||||
|
||||
val IrSimpleFunction.target: IrSimpleFunction
|
||||
get() = (if (modality == Modality.ABSTRACT) this else resolveFakeOverride()).original
|
||||
|
||||
val IrFunction.target: IrFunction get() = when (this) {
|
||||
is IrSimpleFunction -> this.target
|
||||
is IrConstructor -> this
|
||||
else -> error(this)
|
||||
}
|
||||
+87
-52
@@ -104,7 +104,7 @@ import org.jetbrains.kotlin.backend.common.serialization.proto.PublicIdSignature
|
||||
import org.jetbrains.kotlin.backend.common.serialization.proto.AccessorIdSignature as ProtoAccessorIdSignature
|
||||
import org.jetbrains.kotlin.backend.common.serialization.proto.FileLocalIdSignature as ProtoFileLocalIdSignature
|
||||
|
||||
abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBuiltIns, val symbolTable: SymbolTable) {
|
||||
abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBuiltIns, val symbolTable: SymbolTable, protected var deserializeBodies: Boolean) {
|
||||
|
||||
abstract fun deserializeIrSymbolToDeclare(code: Long): Pair<IrSymbol, IdSignature>
|
||||
abstract fun deserializeIrSymbol(code: Long): IrSymbol
|
||||
@@ -118,6 +118,9 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
abstract fun referenceIrSymbol(symbol: IrSymbol, signature: IdSignature)
|
||||
|
||||
private val parentsStack = mutableListOf<IrDeclarationParent>()
|
||||
private val delegatedSymbolMap = mutableMapOf<IrSymbol, IrSymbol>()
|
||||
|
||||
abstract val deserializeInlineFunctions: Boolean
|
||||
|
||||
fun deserializeFqName(fqn: List<Int>): FqName {
|
||||
return fqn.run {
|
||||
@@ -125,6 +128,13 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
}
|
||||
}
|
||||
|
||||
private fun deserializeIrSymbolAndRemap(code: Long): IrSymbol {
|
||||
// TODO: could be simplified
|
||||
return deserializeIrSymbol(code).let {
|
||||
delegatedSymbolMap[it] ?: it
|
||||
}
|
||||
}
|
||||
|
||||
private fun deserializeName(index: Int): Name {
|
||||
val name = deserializeString(index)
|
||||
return Name.guessByFirstCharacter(name)
|
||||
@@ -145,7 +155,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
}
|
||||
|
||||
private fun deserializeSimpleType(proto: ProtoSimpleType): IrSimpleType {
|
||||
val symbol = deserializeIrSymbol(proto.classifier) as? IrClassifierSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.classifier) as? IrClassifierSymbol
|
||||
?: error("could not convert sym to ClassifierSymbol")
|
||||
logger.log { "deserializeSimpleType: symbol=$symbol" }
|
||||
|
||||
@@ -167,7 +177,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
|
||||
private fun deserializeTypeAbbreviation(proto: ProtoTypeAbbreviation): IrTypeAbbreviation =
|
||||
IrTypeAbbreviationImpl(
|
||||
deserializeIrSymbol(proto.typeAlias).let {
|
||||
deserializeIrSymbolAndRemap(proto.typeAlias).let {
|
||||
it as? IrTypeAliasSymbol
|
||||
?: error("IrTypeAliasSymbol expected: $it")
|
||||
},
|
||||
@@ -344,14 +354,14 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
end: Int,
|
||||
type: IrType
|
||||
): IrClassReference {
|
||||
val symbol = deserializeIrSymbol(proto.classSymbol) as IrClassifierSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.classSymbol) as IrClassifierSymbol
|
||||
val classType = deserializeIrType(proto.classType)
|
||||
/** TODO: [createClassifierSymbolForClassReference] is internal function */
|
||||
return IrClassReferenceImpl(start, end, type, symbol, classType)
|
||||
}
|
||||
|
||||
private fun deserializeConstructorCall(proto: ProtoConstructorCall, start: Int, end: Int, type: IrType): IrConstructorCall {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrConstructorSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrConstructorSymbol
|
||||
return IrConstructorCallImpl(
|
||||
start, end, type,
|
||||
symbol, typeArgumentsCount = proto.memberAccess.typeArgumentCount,
|
||||
@@ -363,10 +373,10 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
}
|
||||
|
||||
private fun deserializeCall(proto: ProtoCall, start: Int, end: Int, type: IrType): IrCall {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrFunctionSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrFunctionSymbol
|
||||
|
||||
val superSymbol = if (proto.hasSuper()) {
|
||||
deserializeIrSymbol(proto.`super`) as IrClassSymbol
|
||||
deserializeIrSymbolAndRemap(proto.`super`) as IrClassSymbol
|
||||
} else null
|
||||
|
||||
val origin = if (proto.hasOriginName()) deserializeIrStatementOrigin(proto.originName) else null
|
||||
@@ -400,7 +410,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
start: Int,
|
||||
end: Int
|
||||
): IrDelegatingConstructorCall {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrConstructorSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrConstructorSymbol
|
||||
val call = IrDelegatingConstructorCallImpl(
|
||||
start,
|
||||
end,
|
||||
@@ -421,7 +431,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
end: Int,
|
||||
type: IrType
|
||||
): IrEnumConstructorCall {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrConstructorSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrConstructorSymbol
|
||||
val call = IrEnumConstructorCallImpl(
|
||||
start,
|
||||
end,
|
||||
@@ -451,10 +461,10 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
start: Int, end: Int, type: IrType
|
||||
): IrFunctionReference {
|
||||
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrFunctionSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrFunctionSymbol
|
||||
val origin = if (proto.hasOriginName()) deserializeIrStatementOrigin(proto.originName) else null
|
||||
val reflectionTarget =
|
||||
if (proto.hasReflectionTargetSymbol()) deserializeIrSymbol(proto.reflectionTargetSymbol) as IrFunctionSymbol else null
|
||||
if (proto.hasReflectionTargetSymbol()) deserializeIrSymbolAndRemap(proto.reflectionTargetSymbol) as IrFunctionSymbol else null
|
||||
val callable = IrFunctionReferenceImpl(
|
||||
start,
|
||||
end,
|
||||
@@ -477,11 +487,11 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
|
||||
private fun deserializeGetField(proto: ProtoGetField, start: Int, end: Int, type: IrType): IrGetField {
|
||||
val access = proto.fieldAccess
|
||||
val symbol = deserializeIrSymbol(access.symbol) as IrFieldSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(access.symbol) as IrFieldSymbol
|
||||
val origin = if (proto.hasOriginName()) deserializeIrStatementOrigin(proto.originName) else null
|
||||
|
||||
val superQualifier = if (access.hasSuper()) {
|
||||
deserializeIrSymbol(access.symbol) as IrClassSymbol
|
||||
deserializeIrSymbolAndRemap(access.symbol) as IrClassSymbol
|
||||
} else null
|
||||
val receiver = if (access.hasReceiver()) {
|
||||
deserializeExpression(access.receiver)
|
||||
@@ -491,7 +501,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
}
|
||||
|
||||
private fun deserializeGetValue(proto: ProtoGetValue, start: Int, end: Int, type: IrType): IrGetValue {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrValueSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrValueSymbol
|
||||
val origin = if (proto.hasOriginName()) deserializeIrStatementOrigin(proto.originName) else null
|
||||
// TODO: origin!
|
||||
return IrGetValueImpl(start, end, type, symbol, origin)
|
||||
@@ -503,7 +513,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
end: Int,
|
||||
type: IrType
|
||||
): IrGetEnumValue {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrEnumEntrySymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrEnumEntrySymbol
|
||||
return IrGetEnumValueImpl(start, end, type, symbol)
|
||||
}
|
||||
|
||||
@@ -513,7 +523,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
end: Int,
|
||||
type: IrType
|
||||
): IrGetObjectValue {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrClassSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrClassSymbol
|
||||
return IrGetObjectValueImpl(start, end, type, symbol)
|
||||
}
|
||||
|
||||
@@ -522,7 +532,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
start: Int,
|
||||
end: Int
|
||||
): IrInstanceInitializerCall {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrClassSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrClassSymbol
|
||||
return IrInstanceInitializerCallImpl(start, end, symbol, builtIns.unitType)
|
||||
}
|
||||
|
||||
@@ -533,10 +543,10 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
type: IrType
|
||||
): IrLocalDelegatedPropertyReference {
|
||||
|
||||
val delegate = deserializeIrSymbol(proto.delegate) as IrVariableSymbol
|
||||
val getter = deserializeIrSymbol(proto.getter) as IrSimpleFunctionSymbol
|
||||
val setter = if (proto.hasSetter()) deserializeIrSymbol(proto.setter) as IrSimpleFunctionSymbol else null
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrLocalDelegatedPropertySymbol
|
||||
val delegate = deserializeIrSymbolAndRemap(proto.delegate) as IrVariableSymbol
|
||||
val getter = deserializeIrSymbolAndRemap(proto.getter) as IrSimpleFunctionSymbol
|
||||
val setter = if (proto.hasSetter()) deserializeIrSymbolAndRemap(proto.setter) as IrSimpleFunctionSymbol else null
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrLocalDelegatedPropertySymbol
|
||||
val origin = if (proto.hasOriginName()) deserializeIrStatementOrigin(proto.originName) else null
|
||||
|
||||
return IrLocalDelegatedPropertyReferenceImpl(
|
||||
@@ -551,11 +561,11 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
|
||||
private fun deserializePropertyReference(proto: ProtoPropertyReference, start: Int, end: Int, type: IrType): IrPropertyReference {
|
||||
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrPropertySymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrPropertySymbol
|
||||
|
||||
val field = if (proto.hasField()) deserializeIrSymbol(proto.field) as IrFieldSymbol else null
|
||||
val getter = if (proto.hasGetter()) deserializeIrSymbol(proto.getter) as IrSimpleFunctionSymbol else null
|
||||
val setter = if (proto.hasSetter()) deserializeIrSymbol(proto.setter) as IrSimpleFunctionSymbol else null
|
||||
val field = if (proto.hasField()) deserializeIrSymbolAndRemap(proto.field) as IrFieldSymbol else null
|
||||
val getter = if (proto.hasGetter()) deserializeIrSymbolAndRemap(proto.getter) as IrSimpleFunctionSymbol else null
|
||||
val setter = if (proto.hasSetter()) deserializeIrSymbolAndRemap(proto.setter) as IrSimpleFunctionSymbol else null
|
||||
val origin = if (proto.hasOriginName()) deserializeIrStatementOrigin(proto.originName) else null
|
||||
|
||||
val callable = IrPropertyReferenceImpl(
|
||||
@@ -572,16 +582,16 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
}
|
||||
|
||||
private fun deserializeReturn(proto: ProtoReturn, start: Int, end: Int, type: IrType): IrReturn {
|
||||
val symbol = deserializeIrSymbol(proto.returnTarget) as IrReturnTargetSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.returnTarget) as IrReturnTargetSymbol
|
||||
val value = deserializeExpression(proto.value)
|
||||
return IrReturnImpl(start, end, builtIns.nothingType, symbol, value)
|
||||
}
|
||||
|
||||
private fun deserializeSetField(proto: ProtoSetField, start: Int, end: Int): IrSetField {
|
||||
val access = proto.fieldAccess
|
||||
val symbol = deserializeIrSymbol(access.symbol) as IrFieldSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(access.symbol) as IrFieldSymbol
|
||||
val superQualifier = if (access.hasSuper()) {
|
||||
deserializeIrSymbol(access.symbol) as IrClassSymbol
|
||||
deserializeIrSymbolAndRemap(access.symbol) as IrClassSymbol
|
||||
} else null
|
||||
val receiver = if (access.hasReceiver()) {
|
||||
deserializeExpression(access.receiver)
|
||||
@@ -593,7 +603,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
}
|
||||
|
||||
private fun deserializeSetVariable(proto: ProtoSetVariable, start: Int, end: Int): IrSetVariable {
|
||||
val symbol = deserializeIrSymbol(proto.symbol) as IrVariableSymbol
|
||||
val symbol = deserializeIrSymbolAndRemap(proto.symbol) as IrVariableSymbol
|
||||
val value = deserializeExpression(proto.value)
|
||||
val origin = if (proto.hasOriginName()) deserializeIrStatementOrigin(proto.originName) else null
|
||||
return IrSetVariableImpl(start, end, builtIns.unitType, symbol, value, origin)
|
||||
@@ -902,6 +912,16 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
}
|
||||
}
|
||||
|
||||
private fun recordDelegatedSymbol(symbol: IrSymbol) {
|
||||
if (symbol is IrDelegatingSymbol<*, *, *>) {
|
||||
delegatedSymbolMap[symbol] = symbol.delegate
|
||||
}
|
||||
}
|
||||
|
||||
private fun eraseDelegatedSymbol(symbol: IrSymbol) {
|
||||
delegatedSymbolMap.remove(symbol)
|
||||
}
|
||||
|
||||
private inline fun <T : IrDeclarationParent> T.usingParent(block: T.() -> Unit): T =
|
||||
this.apply { usingParent(this) { block(it) } }
|
||||
|
||||
@@ -911,15 +931,20 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
): T where T : IrDeclaration, T : IrSymbolOwner {
|
||||
val (s, uid) = deserializeIrSymbolToDeclare(proto.symbol)
|
||||
val coordinates = BinaryCoordinates.decode(proto.coordinates)
|
||||
val result = block(
|
||||
s,
|
||||
uid,
|
||||
coordinates.startOffset, coordinates.endOffset,
|
||||
deserializeIrDeclarationOrigin(proto.originName), proto.flags
|
||||
)
|
||||
result.annotations += deserializeAnnotations(proto.annotationList)
|
||||
result.parent = parentsStack.peek()!!
|
||||
return result
|
||||
try {
|
||||
recordDelegatedSymbol(s)
|
||||
val result = block(
|
||||
s,
|
||||
uid,
|
||||
coordinates.startOffset, coordinates.endOffset,
|
||||
deserializeIrDeclarationOrigin(proto.originName), proto.flags
|
||||
)
|
||||
result.annotations += deserializeAnnotations(proto.annotationList)
|
||||
result.parent = parentsStack.peek()!!
|
||||
return result
|
||||
} finally {
|
||||
eraseDelegatedSymbol(s)
|
||||
}
|
||||
}
|
||||
|
||||
private fun deserializeIrTypeParameter(proto: ProtoTypeParameter, index: Int, isGlobal: Boolean): IrTypeParameter {
|
||||
@@ -1067,24 +1092,36 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
return result
|
||||
}
|
||||
|
||||
private inline fun <T : IrFunction> T.withInlineGuard(block: T.() -> Unit) {
|
||||
val oldInline = deserializeBodies
|
||||
try {
|
||||
deserializeBodies = oldInline || (deserializeInlineFunctions && this is IrSimpleFunction && isInline)
|
||||
block()
|
||||
} finally {
|
||||
deserializeBodies = oldInline
|
||||
}
|
||||
}
|
||||
|
||||
private inline fun <T : IrFunction> withDeserializedIrFunctionBase(
|
||||
proto: ProtoFunctionBase,
|
||||
block: (IrFunctionSymbol, IdSignature, Int, Int, IrDeclarationOrigin, Long) -> T
|
||||
) = withDeserializedIrDeclarationBase(proto.base) { symbol, idSig, startOffset, endOffset, origin, fcode ->
|
||||
symbolTable.withScope(symbol.descriptor) {
|
||||
block(symbol as IrFunctionSymbol, idSig, startOffset, endOffset, origin, fcode).usingParent {
|
||||
typeParameters = deserializeTypeParameters(proto.typeParameterList, false)
|
||||
valueParameters = deserializeValueParameters(proto.valueParameterList)
|
||||
withInlineGuard {
|
||||
typeParameters = deserializeTypeParameters(proto.typeParameterList, false)
|
||||
valueParameters = deserializeValueParameters(proto.valueParameterList)
|
||||
|
||||
val nameType = BinaryNameAndType.decode(proto.nameType)
|
||||
returnType = deserializeIrType(nameType.typeIndex)
|
||||
val nameType = BinaryNameAndType.decode(proto.nameType)
|
||||
returnType = deserializeIrType(nameType.typeIndex)
|
||||
|
||||
if (proto.hasDispatchReceiver())
|
||||
dispatchReceiverParameter = deserializeIrValueParameter(proto.dispatchReceiver, -1)
|
||||
if (proto.hasExtensionReceiver())
|
||||
extensionReceiverParameter = deserializeIrValueParameter(proto.extensionReceiver, -1)
|
||||
if (proto.hasBody()) {
|
||||
body = deserializeStatementBody(proto.body) as IrBody
|
||||
if (proto.hasDispatchReceiver())
|
||||
dispatchReceiverParameter = deserializeIrValueParameter(proto.dispatchReceiver, -1)
|
||||
if (proto.hasExtensionReceiver())
|
||||
extensionReceiverParameter = deserializeIrValueParameter(proto.extensionReceiver, -1)
|
||||
if (proto.hasBody()) {
|
||||
body = deserializeStatementBody(proto.body) as IrBody
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1111,7 +1148,7 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
flags.isFakeOverride
|
||||
)
|
||||
}.apply {
|
||||
overriddenSymbols = proto.overriddenList.map { deserializeIrSymbol(it) as IrSimpleFunctionSymbol }
|
||||
overriddenSymbols = proto.overriddenList.map { deserializeIrSymbolAndRemap(it) as IrSimpleFunctionSymbol }
|
||||
|
||||
(descriptor as? WrappedSimpleFunctionDescriptor)?.bind(this)
|
||||
}
|
||||
@@ -1328,6 +1365,4 @@ abstract class IrFileDeserializer(val logger: LoggingContext, val builtIns: IrBu
|
||||
usingParent(parent) {
|
||||
deserializeDeclaration(proto)
|
||||
}
|
||||
}
|
||||
|
||||
val irrelevantOrigin = object : IrDeclarationOriginImpl("irrelevant") {}
|
||||
}
|
||||
+276
@@ -0,0 +1,276 @@
|
||||
/*
|
||||
* 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.backend.common.serialization
|
||||
|
||||
import org.jetbrains.kotlin.backend.common.serialization.encodings.BinarySymbolData
|
||||
import org.jetbrains.kotlin.builtins.functions.FunctionClassDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.ir.UNDEFINED_OFFSET
|
||||
import org.jetbrains.kotlin.ir.declarations.*
|
||||
import org.jetbrains.kotlin.ir.descriptors.IrAbstractFunctionFactory
|
||||
import org.jetbrains.kotlin.ir.descriptors.IrBuiltIns
|
||||
import org.jetbrains.kotlin.ir.descriptors.WrappedDeclarationDescriptor
|
||||
import org.jetbrains.kotlin.ir.symbols.*
|
||||
import org.jetbrains.kotlin.ir.util.IdSignature
|
||||
import org.jetbrains.kotlin.ir.util.IrExtensionGenerator
|
||||
import org.jetbrains.kotlin.ir.util.SymbolTable
|
||||
import org.jetbrains.kotlin.library.IrLibrary
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
|
||||
internal fun IrSymbol.kind(): BinarySymbolData.SymbolKind {
|
||||
return when (this) {
|
||||
is IrClassSymbol -> BinarySymbolData.SymbolKind.CLASS_SYMBOL
|
||||
is IrConstructorSymbol -> BinarySymbolData.SymbolKind.CONSTRUCTOR_SYMBOL
|
||||
is IrSimpleFunctionSymbol -> BinarySymbolData.SymbolKind.FUNCTION_SYMBOL
|
||||
is IrPropertySymbol -> BinarySymbolData.SymbolKind.PROPERTY_SYMBOL
|
||||
is IrEnumEntrySymbol -> BinarySymbolData.SymbolKind.ENUM_ENTRY_SYMBOL
|
||||
is IrTypeAliasSymbol -> BinarySymbolData.SymbolKind.TYPEALIAS_SYMBOL
|
||||
else -> error("Unexpected symbol kind $this")
|
||||
}
|
||||
}
|
||||
|
||||
abstract class IrModuleDeserializer(val moduleDescriptor: ModuleDescriptor) {
|
||||
abstract operator fun contains(idSig: IdSignature): Boolean
|
||||
abstract fun deserializeIrSymbol(idSig: IdSignature, symbolKind: BinarySymbolData.SymbolKind): IrSymbol
|
||||
|
||||
open fun declareIrSymbol(symbol: IrSymbol) {
|
||||
assert(symbol.isPublicApi)
|
||||
assert(symbol.descriptor !is WrappedDeclarationDescriptor<*>)
|
||||
deserializeIrSymbol(symbol.signature, symbol.kind())
|
||||
}
|
||||
|
||||
open val klib: IrLibrary get() = error("Unsupported operation")
|
||||
|
||||
open fun init() = init(this)
|
||||
|
||||
open fun init(delegate: IrModuleDeserializer) {}
|
||||
|
||||
open fun addModuleReachableTopLevel(idSig: IdSignature) { error("Unsupported Operation (sig: $idSig") }
|
||||
|
||||
open fun deserializeReachableDeclarations() { error("Unsupported Operation") }
|
||||
|
||||
open fun postProcess() {}
|
||||
|
||||
abstract val moduleFragment: IrModuleFragment
|
||||
|
||||
abstract val moduleDependencies: Collection<IrModuleDeserializer>
|
||||
|
||||
open val strategy: DeserializationStrategy = DeserializationStrategy.ONLY_DECLARATION_HEADERS
|
||||
}
|
||||
|
||||
// Used to resolve built in symbols like `kotlin.ir.internal.*` or `kotlin.FunctionN`
|
||||
class IrModuleDeserializerWithBuiltIns(
|
||||
private val builtIns: IrBuiltIns,
|
||||
private val functionFactory: IrAbstractFunctionFactory,
|
||||
private val delegate: IrModuleDeserializer
|
||||
) : IrModuleDeserializer(delegate.moduleDescriptor) {
|
||||
|
||||
init {
|
||||
// TODO: figure out how it should work for K/N
|
||||
// assert(builtIns.builtIns.builtInsModule === delegate.moduleDescriptor)
|
||||
}
|
||||
|
||||
private val irBuiltInsMap = builtIns.knownBuiltins.map {
|
||||
val symbol = (it as IrSymbolOwner).symbol
|
||||
symbol.signature to symbol
|
||||
}.toMap()
|
||||
|
||||
private fun checkIsFunctionInterface(idSig: IdSignature): Boolean {
|
||||
val publicSig = idSig.asPublic() ?: return false
|
||||
|
||||
if (publicSig.packageFqn !in functionalPackages) return false
|
||||
|
||||
val declarationFqn = publicSig.declarationFqn
|
||||
|
||||
if (declarationFqn.isRoot) return false
|
||||
|
||||
val fqnParts = declarationFqn.pathSegments()
|
||||
|
||||
val className = fqnParts.first()
|
||||
|
||||
return functionPattern.matcher(className.asString()).find()
|
||||
}
|
||||
|
||||
override operator fun contains(idSig: IdSignature): Boolean {
|
||||
if (idSig in irBuiltInsMap) return true
|
||||
|
||||
return checkIsFunctionInterface(idSig) || idSig in delegate
|
||||
}
|
||||
|
||||
override fun deserializeReachableDeclarations() {
|
||||
delegate.deserializeReachableDeclarations()
|
||||
}
|
||||
|
||||
private fun computeFunctionDescriptor(className: Name): FunctionClassDescriptor {
|
||||
val nameString = className.asString()
|
||||
val isK = nameString[0] == 'K'
|
||||
val isSuspend = (if (isK) nameString[1] else nameString[0]) == 'S'
|
||||
val arity = nameString.run { substring(indexOfFirst { it.isDigit() }).toInt(10) }
|
||||
return functionFactory.run {
|
||||
when {
|
||||
isK && isSuspend -> kSuspendFunctionClassDescriptor(arity)
|
||||
isK -> kFunctionClassDescriptor(arity)
|
||||
isSuspend -> suspendFunctionClassDescriptor(arity)
|
||||
else -> functionClassDescriptor(arity)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun resolveFunctionalInterface(idSig: IdSignature, symbolKind: BinarySymbolData.SymbolKind): IrSymbol {
|
||||
val publicSig = idSig.asPublic() ?: error("$idSig has to be public")
|
||||
|
||||
val fqnParts = publicSig.declarationFqn.pathSegments()
|
||||
val className = fqnParts.firstOrNull() ?: error("Expected class name for $idSig")
|
||||
|
||||
val functionDescriptor = computeFunctionDescriptor(className)
|
||||
val topLevelSignature = IdSignature.PublicSignature(publicSig.packageFqn, FqName(className.asString()), null, publicSig.mask)
|
||||
|
||||
val functionClass = when (functionDescriptor.functionKind) {
|
||||
FunctionClassDescriptor.Kind.KSuspendFunction -> functionFactory.kSuspendFunctionN(functionDescriptor.arity) { callback ->
|
||||
declareClassFromLinker(functionDescriptor, topLevelSignature) { callback(it) }
|
||||
}
|
||||
FunctionClassDescriptor.Kind.KFunction -> functionFactory.kFunctionN(functionDescriptor.arity) { callback ->
|
||||
declareClassFromLinker(functionDescriptor, topLevelSignature) { callback(it) }
|
||||
}
|
||||
FunctionClassDescriptor.Kind.SuspendFunction -> functionFactory.suspendFunctionN(functionDescriptor.arity) { callback ->
|
||||
declareClassFromLinker(functionDescriptor, topLevelSignature) { callback(it) }
|
||||
}
|
||||
FunctionClassDescriptor.Kind.Function -> functionFactory.functionN(functionDescriptor.arity) { callback ->
|
||||
declareClassFromLinker(functionDescriptor, topLevelSignature) { callback(it) }
|
||||
}
|
||||
}
|
||||
|
||||
return when (fqnParts.size) {
|
||||
1 -> functionClass.symbol.also { assert(symbolKind == BinarySymbolData.SymbolKind.CLASS_SYMBOL) }
|
||||
2 -> {
|
||||
val memberName = fqnParts[1]!!
|
||||
functionClass.declarations.single { it is IrDeclarationWithName && it.name == memberName }.let {
|
||||
(it as IrSymbolOwner).symbol
|
||||
}
|
||||
}
|
||||
3 -> {
|
||||
assert(idSig is IdSignature.AccessorSignature)
|
||||
assert(symbolKind == BinarySymbolData.SymbolKind.FUNCTION_SYMBOL)
|
||||
val propertyName = fqnParts[1]!!
|
||||
val accessorName = fqnParts[2]!!
|
||||
functionClass.declarations.filterIsInstance<IrProperty>().single { it.name == propertyName }.let { p ->
|
||||
p.getter?.let { g -> if (g.name == accessorName) return g.symbol }
|
||||
p.setter?.let { s -> if (s.name == accessorName) return s.symbol }
|
||||
error("No accessor found for signature $idSig")
|
||||
}
|
||||
}
|
||||
else -> error("No member found for signature $idSig")
|
||||
}
|
||||
}
|
||||
|
||||
override fun deserializeIrSymbol(idSig: IdSignature, symbolKind: BinarySymbolData.SymbolKind): IrSymbol {
|
||||
irBuiltInsMap[idSig]?.let { return it }
|
||||
|
||||
if (checkIsFunctionInterface(idSig)) return resolveFunctionalInterface(idSig, symbolKind)
|
||||
|
||||
return delegate.deserializeIrSymbol(idSig, symbolKind)
|
||||
}
|
||||
|
||||
override fun postProcess() {
|
||||
delegate.postProcess()
|
||||
}
|
||||
|
||||
override fun init() {
|
||||
delegate.init(this)
|
||||
}
|
||||
|
||||
override val klib: IrLibrary
|
||||
get() = delegate.klib
|
||||
|
||||
override val strategy: DeserializationStrategy
|
||||
get() = delegate.strategy
|
||||
|
||||
override fun addModuleReachableTopLevel(idSig: IdSignature) {
|
||||
delegate.addModuleReachableTopLevel(idSig)
|
||||
}
|
||||
|
||||
override val moduleFragment: IrModuleFragment get() = delegate.moduleFragment
|
||||
override val moduleDependencies: Collection<IrModuleDeserializer> get() = delegate.moduleDependencies
|
||||
}
|
||||
|
||||
open class CurrentModuleDeserializer(
|
||||
override val moduleFragment: IrModuleFragment,
|
||||
override val moduleDependencies: Collection<IrModuleDeserializer>,
|
||||
private val symbolTable: SymbolTable,
|
||||
private val extensions: Collection<IrExtensionGenerator>
|
||||
) : IrModuleDeserializer(moduleFragment.descriptor) {
|
||||
override fun contains(idSig: IdSignature): Boolean = false // TODO:
|
||||
|
||||
override fun deserializeIrSymbol(idSig: IdSignature, symbolKind: BinarySymbolData.SymbolKind): IrSymbol {
|
||||
error("Unreachable execution: there could not be back-links")
|
||||
}
|
||||
|
||||
override fun declareIrSymbol(symbol: IrSymbol) {
|
||||
declareIrSymbolImpl(symbol)
|
||||
}
|
||||
|
||||
private fun referenceParentDescriptor(descriptor: DeclarationDescriptor): IrSymbol {
|
||||
return when (descriptor) {
|
||||
is ClassDescriptor -> symbolTable.referenceClass(descriptor)
|
||||
is PropertyDescriptor -> symbolTable.referenceProperty(descriptor)
|
||||
is PackageFragmentDescriptor -> moduleFragment.files.single { it.symbol.descriptor === descriptor }.symbol
|
||||
else -> error("Unexpected declaration parent $descriptor")
|
||||
}
|
||||
}
|
||||
|
||||
private fun declareIrDeclaration(symbol: IrSymbol): IrDeclaration {
|
||||
for (extension in extensions) {
|
||||
extension.declare(symbol)?.let { return it }
|
||||
}
|
||||
|
||||
return declareIrDeclarationDefault(symbol)
|
||||
}
|
||||
|
||||
private fun declareIrDeclarationDefault(symbol: IrSymbol): IrDeclaration {
|
||||
return when (symbol) {
|
||||
is IrClassSymbol -> symbolTable.declareClass(offset, offset, IrDeclarationOrigin.DEFINED, symbol.descriptor)
|
||||
is IrConstructorSymbol -> symbolTable.declareConstructor(offset, offset, IrDeclarationOrigin.DEFINED, symbol.descriptor)
|
||||
is IrSimpleFunctionSymbol -> symbolTable.declareSimpleFunction(offset, offset, IrDeclarationOrigin.DEFINED, symbol.descriptor)
|
||||
is IrPropertySymbol -> symbolTable.declareProperty(offset, offset, IrDeclarationOrigin.DEFINED, symbol.descriptor)
|
||||
is IrTypeAliasSymbol -> TODO("Implement type alias $symbol")
|
||||
is IrEnumEntrySymbol -> symbolTable.declareEnumEntry(offset, offset, IrDeclarationOrigin.DEFINED, symbol.descriptor)
|
||||
else -> error("Unexpected symbol $symbol")
|
||||
}
|
||||
}
|
||||
|
||||
private fun declareIrSymbolImpl(symbol: IrSymbol): IrSymbolOwner {
|
||||
if (symbol.isBound) return symbol.owner
|
||||
val descriptor = symbol.descriptor
|
||||
|
||||
assert(descriptor !is WrappedDeclarationDescriptor<*>)
|
||||
|
||||
val accessor = descriptor as? PropertyAccessorDescriptor
|
||||
|
||||
val parent = descriptor.containingDeclaration ?: error("Expect non-root declaration $descriptor")
|
||||
val parentDeclaration = declareIrSymbolImpl(referenceParentDescriptor(parent)) as IrDeclarationContainer
|
||||
|
||||
val declaredDeclaration = declareIrDeclaration(symbol).also {
|
||||
it.parent = parentDeclaration
|
||||
if (accessor != null) {
|
||||
val property = accessor.correspondingProperty
|
||||
val irProperty = declareIrSymbolImpl(referenceParentDescriptor(property)) as IrProperty
|
||||
val irAccessor = it as IrSimpleFunction
|
||||
irAccessor.correspondingPropertySymbol = irProperty.symbol
|
||||
if (accessor === property.getter) irProperty.getter = irAccessor
|
||||
if (accessor === property.setter) irProperty.setter = irAccessor
|
||||
} else {
|
||||
parentDeclaration.declarations.add(it)
|
||||
}
|
||||
}
|
||||
|
||||
return declaredDeclaration as IrSymbolOwner
|
||||
}
|
||||
|
||||
companion object {
|
||||
private const val offset = UNDEFINED_OFFSET
|
||||
}
|
||||
}
|
||||
+367
-532
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user