Added support for inline class members.
Inline constructors in particular.
This commit is contained in:
committed by
alexander-gorshenev
parent
2a246a9a3a
commit
d4c34b29c1
+14
@@ -296,6 +296,20 @@ internal fun FunctionDescriptor.bridgeDirectionsTo(overriddenDescriptor: Functio
|
|||||||
return ourDirections
|
return ourDirections
|
||||||
}
|
}
|
||||||
|
|
||||||
|
internal fun DeclarationDescriptor.findPackage(): PackageFragmentDescriptor {
|
||||||
|
return if (this is PackageFragmentDescriptor) this
|
||||||
|
else this.containingDeclaration!!.findPackage()
|
||||||
|
}
|
||||||
|
|
||||||
|
internal fun DeclarationDescriptor.allContainingDeclarations(): List<DeclarationDescriptor> {
|
||||||
|
var list = mutableListOf<DeclarationDescriptor>()
|
||||||
|
var current = this.containingDeclaration
|
||||||
|
while (current != null) {
|
||||||
|
list.add(current)
|
||||||
|
current = current.containingDeclaration
|
||||||
|
}
|
||||||
|
return list
|
||||||
|
}
|
||||||
|
|
||||||
internal fun DeclarationDescriptor.getMemberScope(): MemberScope {
|
internal fun DeclarationDescriptor.getMemberScope(): MemberScope {
|
||||||
val containingScope = when (this) {
|
val containingScope = when (this) {
|
||||||
|
|||||||
+23
-27
@@ -20,6 +20,7 @@ import org.jetbrains.kotlin.backend.konan.Context
|
|||||||
import org.jetbrains.kotlin.backend.konan.KonanIrDeserializationException
|
import org.jetbrains.kotlin.backend.konan.KonanIrDeserializationException
|
||||||
import org.jetbrains.kotlin.backend.konan.descriptors.contributedMethods
|
import org.jetbrains.kotlin.backend.konan.descriptors.contributedMethods
|
||||||
import org.jetbrains.kotlin.backend.konan.descriptors.isFunctionInvoke
|
import org.jetbrains.kotlin.backend.konan.descriptors.isFunctionInvoke
|
||||||
|
import org.jetbrains.kotlin.backend.konan.descriptors.findPackage
|
||||||
import org.jetbrains.kotlin.backend.konan.llvm.isExported
|
import org.jetbrains.kotlin.backend.konan.llvm.isExported
|
||||||
import org.jetbrains.kotlin.descriptors.*
|
import org.jetbrains.kotlin.descriptors.*
|
||||||
import org.jetbrains.kotlin.incremental.components.NoLookupLocation
|
import org.jetbrains.kotlin.incremental.components.NoLookupLocation
|
||||||
@@ -29,6 +30,7 @@ import org.jetbrains.kotlin.resolve.calls.tasks.createSynthesizedInvokes
|
|||||||
import org.jetbrains.kotlin.resolve.scopes.MemberScope
|
import org.jetbrains.kotlin.resolve.scopes.MemberScope
|
||||||
import org.jetbrains.kotlin.serialization.KonanIr
|
import org.jetbrains.kotlin.serialization.KonanIr
|
||||||
import org.jetbrains.kotlin.serialization.KonanIr.KotlinDescriptor
|
import org.jetbrains.kotlin.serialization.KonanIr.KotlinDescriptor
|
||||||
|
import org.jetbrains.kotlin.serialization.KonanIr.DeclarationDescriptor.DescriptorCase.*
|
||||||
import org.jetbrains.kotlin.serialization.KonanLinkData
|
import org.jetbrains.kotlin.serialization.KonanLinkData
|
||||||
import org.jetbrains.kotlin.serialization.ProtoBuf
|
import org.jetbrains.kotlin.serialization.ProtoBuf
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
|
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
|
||||||
@@ -36,18 +38,12 @@ import org.jetbrains.kotlin.serialization.deserialization.NameResolverImpl
|
|||||||
import org.jetbrains.kotlin.serialization.deserialization.descriptors.*
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.*
|
||||||
import org.jetbrains.kotlin.types.*
|
import org.jetbrains.kotlin.types.*
|
||||||
|
|
||||||
internal fun DeclarationDescriptor.findPackage(): PackageFragmentDescriptor {
|
|
||||||
return if (this is PackageFragmentDescriptor) this
|
|
||||||
else this.containingDeclaration!!.findPackage()
|
|
||||||
}
|
|
||||||
|
|
||||||
internal fun DeserializedMemberDescriptor.nameTable(): ProtoBuf.QualifiedNameTable {
|
internal fun DeserializedMemberDescriptor.nameTable(): ProtoBuf.QualifiedNameTable {
|
||||||
val pkg = this.findPackage()
|
val pkg = this.findPackage()
|
||||||
assert(pkg is KonanPackageFragment)
|
assert(pkg is KonanPackageFragment)
|
||||||
return (pkg as KonanPackageFragment).proto.getNameTable()
|
return (pkg as KonanPackageFragment).proto.getNameTable()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
internal fun DeserializedMemberDescriptor.nameResolver(): NameResolver {
|
internal fun DeserializedMemberDescriptor.nameResolver(): NameResolver {
|
||||||
val pkg = this.findPackage() as KonanPackageFragment
|
val pkg = this.findPackage() as KonanPackageFragment
|
||||||
return NameResolverImpl(pkg.proto.getStringTable(), pkg.proto.getNameTable())
|
return NameResolverImpl(pkg.proto.getStringTable(), pkg.proto.getNameTable())
|
||||||
@@ -68,9 +64,10 @@ internal class IrDescriptorDeserializer(val context: Context,
|
|||||||
fun deserializeKotlinType(proto: KonanIr.KotlinType): KotlinType {
|
fun deserializeKotlinType(proto: KonanIr.KotlinType): KotlinType {
|
||||||
val index = proto.getIndex()
|
val index = proto.getIndex()
|
||||||
val text = proto.getDebugText()
|
val text = proto.getDebugText()
|
||||||
val typeProto = localDeserializer.typeTable[index]
|
val typeProto = localDeserializer.parentTypeTable[index]
|
||||||
val type = localDeserializer.deserializeInlineType(typeProto)
|
val type = localDeserializer.deserializeInlineType(typeProto)
|
||||||
if (type.isError) throw KonanIrDeserializationException("Could not deserialize KotlinType: $text $type")
|
if (type.isError)
|
||||||
|
throw KonanIrDeserializationException("Could not deserialize KotlinType: $text $type")
|
||||||
|
|
||||||
val realType = if (proto.isCaptured) {
|
val realType = if (proto.isCaptured) {
|
||||||
unpackCapturedType(type)
|
unpackCapturedType(type)
|
||||||
@@ -80,26 +77,24 @@ internal class IrDescriptorDeserializer(val context: Context,
|
|||||||
context.log{"### deserialized Kotlin Type index=$index, text=$text:\t$realType"}
|
context.log{"### deserialized Kotlin Type index=$index, text=$text:\t$realType"}
|
||||||
return realType
|
return realType
|
||||||
}
|
}
|
||||||
|
|
||||||
fun deserializeLocalDeclaration(irProto: KonanIr.KotlinDescriptor): DeclarationDescriptor {
|
fun deserializeLocalDeclaration(irProto: KonanIr.KotlinDescriptor): DeclarationDescriptor {
|
||||||
val localDeclarationProto = irProto.irLocalDeclaration.descriptor
|
val localDeclarationProto = irProto.irLocalDeclaration.descriptor
|
||||||
when {
|
val index = irProto.index
|
||||||
localDeclarationProto.hasFunction() -> {
|
//val localDeserializer = LocalDeclarationDeserializer(parent)
|
||||||
val index = irProto.index
|
val descriptor: DeclarationDescriptor = when(localDeclarationProto.descriptorCase) {
|
||||||
val descriptor = localDeserializer.deserializeFunction(irProto)
|
FUNCTION ->
|
||||||
descriptorIndex.put(index, descriptor)
|
localDeserializer.deserializeFunction(irProto)
|
||||||
return descriptor
|
PROPERTY ->
|
||||||
}
|
localDeserializer.deserializeProperty(irProto)
|
||||||
|
CLAZZ ->
|
||||||
localDeclarationProto.hasProperty() -> {
|
localDeserializer.deserializeClass(irProto)
|
||||||
val index = irProto.index
|
CONSTRUCTOR ->
|
||||||
val descriptor = localDeserializer.deserializeProperty(irProto)
|
localDeserializer.deserializeConstructor(irProto)
|
||||||
descriptorIndex.put(index, descriptor)
|
|
||||||
return descriptor
|
|
||||||
}
|
|
||||||
// TODO
|
|
||||||
// localDclarationProto.hasClazz() ->
|
|
||||||
else -> TODO("Unexpected descriptor kind")
|
else -> TODO("Unexpected descriptor kind")
|
||||||
}
|
}
|
||||||
|
descriptorIndex.put(index, descriptor)
|
||||||
|
return descriptor
|
||||||
}
|
}
|
||||||
|
|
||||||
// Either (a substitution of) a public descriptor
|
// Either (a substitution of) a public descriptor
|
||||||
@@ -113,6 +108,10 @@ internal class IrDescriptorDeserializer(val context: Context,
|
|||||||
KonanIr.KotlinDescriptor.Kind.VALUE_PARAMETER,
|
KonanIr.KotlinDescriptor.Kind.VALUE_PARAMETER,
|
||||||
KonanIr.KotlinDescriptor.Kind.TYPE_PARAMETER,
|
KonanIr.KotlinDescriptor.Kind.TYPE_PARAMETER,
|
||||||
KonanIr.KotlinDescriptor.Kind.RECEIVER,
|
KonanIr.KotlinDescriptor.Kind.RECEIVER,
|
||||||
|
// Properties can only be found in local
|
||||||
|
// classes, so no need to look for them
|
||||||
|
// in the public descriptor tree.
|
||||||
|
KonanIr.KotlinDescriptor.Kind.PROPERTY,
|
||||||
KonanIr.KotlinDescriptor.Kind.VARIABLE ->
|
KonanIr.KotlinDescriptor.Kind.VARIABLE ->
|
||||||
descriptorIndex[index]!!
|
descriptorIndex[index]!!
|
||||||
|
|
||||||
@@ -133,7 +132,6 @@ internal class IrDescriptorDeserializer(val context: Context,
|
|||||||
fun deserializeDescriptor(proto: KonanIr.KotlinDescriptor): DeclarationDescriptor {
|
fun deserializeDescriptor(proto: KonanIr.KotlinDescriptor): DeclarationDescriptor {
|
||||||
|
|
||||||
context.log{"### deserializeDescriptor ${proto.kind} ${proto.index}"}
|
context.log{"### deserializeDescriptor ${proto.kind} ${proto.index}"}
|
||||||
|
|
||||||
val descriptor = if (proto.hasIrLocalDeclaration()) {
|
val descriptor = if (proto.hasIrLocalDeclaration()) {
|
||||||
deserializeLocalDeclaration(proto)
|
deserializeLocalDeclaration(proto)
|
||||||
} else
|
} else
|
||||||
@@ -307,7 +305,6 @@ internal class IrDescriptorDeserializer(val context: Context,
|
|||||||
fun matchNameInParentScope(proto: KonanIr.KotlinDescriptor): Collection<DeclarationDescriptor> {
|
fun matchNameInParentScope(proto: KonanIr.KotlinDescriptor): Collection<DeclarationDescriptor> {
|
||||||
val classOrPackage = proto.classOrPackage
|
val classOrPackage = proto.classOrPackage
|
||||||
val name = proto.name
|
val name = proto.name
|
||||||
|
|
||||||
when (proto.kind) {
|
when (proto.kind) {
|
||||||
KotlinDescriptor.Kind.CLASS -> {
|
KotlinDescriptor.Kind.CLASS -> {
|
||||||
val parentScope =
|
val parentScope =
|
||||||
@@ -362,7 +359,6 @@ internal class IrDescriptorDeserializer(val context: Context,
|
|||||||
constructors: Collection<DeclarationDescriptor>,
|
constructors: Collection<DeclarationDescriptor>,
|
||||||
descriptorProto: KonanIr.KotlinDescriptor):
|
descriptorProto: KonanIr.KotlinDescriptor):
|
||||||
DeserializedClassConstructorDescriptor {
|
DeserializedClassConstructorDescriptor {
|
||||||
|
|
||||||
val originalIndex = descriptorProto.originalIndex
|
val originalIndex = descriptorProto.originalIndex
|
||||||
return constructors.single {
|
return constructors.single {
|
||||||
it.uniqId == originalIndex
|
it.uniqId == originalIndex
|
||||||
|
|||||||
+9
-5
@@ -19,6 +19,7 @@ package org.jetbrains.kotlin.backend.konan.serialization
|
|||||||
import org.jetbrains.kotlin.backend.konan.Context
|
import org.jetbrains.kotlin.backend.konan.Context
|
||||||
import org.jetbrains.kotlin.backend.konan.descriptors.*
|
import org.jetbrains.kotlin.backend.konan.descriptors.*
|
||||||
import org.jetbrains.kotlin.descriptors.*
|
import org.jetbrains.kotlin.descriptors.*
|
||||||
|
import org.jetbrains.kotlin.serialization.KonanDescriptorSerializer
|
||||||
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
|
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
|
||||||
import org.jetbrains.kotlin.ir.descriptors.IrTemporaryVariableDescriptor
|
import org.jetbrains.kotlin.ir.descriptors.IrTemporaryVariableDescriptor
|
||||||
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
||||||
@@ -38,7 +39,7 @@ internal class IrDescriptorSerializer(
|
|||||||
val context: Context,
|
val context: Context,
|
||||||
val descriptorTable: DescriptorTable,
|
val descriptorTable: DescriptorTable,
|
||||||
val stringTable: KonanStringTable,
|
val stringTable: KonanStringTable,
|
||||||
var typeSerializer: ((KotlinType)->Int),
|
val localDeclarationSerializer: LocalDeclarationSerializer,
|
||||||
var rootFunction: FunctionDescriptor) {
|
var rootFunction: FunctionDescriptor) {
|
||||||
|
|
||||||
fun serializeKotlinType(type: KotlinType): KonanIr.KotlinType {
|
fun serializeKotlinType(type: KotlinType): KonanIr.KotlinType {
|
||||||
@@ -48,7 +49,7 @@ internal class IrDescriptorSerializer(
|
|||||||
} else {
|
} else {
|
||||||
type
|
type
|
||||||
}
|
}
|
||||||
val index = typeSerializer(typeToSerialize)
|
val index = localDeclarationSerializer.typeSerializer(typeToSerialize)
|
||||||
val proto = KonanIr.KotlinType.newBuilder()
|
val proto = KonanIr.KotlinType.newBuilder()
|
||||||
.setIndex(index)
|
.setIndex(index)
|
||||||
.setDebugText(type.toString())
|
.setDebugText(type.toString())
|
||||||
@@ -76,7 +77,9 @@ internal class IrDescriptorSerializer(
|
|||||||
-> KonanIr.KotlinDescriptor.Kind.TYPE_PARAMETER
|
-> KonanIr.KotlinDescriptor.Kind.TYPE_PARAMETER
|
||||||
is ReceiverParameterDescriptor
|
is ReceiverParameterDescriptor
|
||||||
-> KonanIr.KotlinDescriptor.Kind.RECEIVER
|
-> KonanIr.KotlinDescriptor.Kind.RECEIVER
|
||||||
else -> TODO("Unexpected local descriptor.")
|
is PropertyDescriptor
|
||||||
|
-> KonanIr.KotlinDescriptor.Kind.PROPERTY
|
||||||
|
else -> TODO("Unexpected local descriptor: $descriptor")
|
||||||
}
|
}
|
||||||
|
|
||||||
fun functionDescriptorSpecifics(descriptor: FunctionDescriptor, proto: KonanIr.KotlinDescriptor.Builder) {
|
fun functionDescriptorSpecifics(descriptor: FunctionDescriptor, proto: KonanIr.KotlinDescriptor.Builder) {
|
||||||
@@ -89,7 +92,7 @@ internal class IrDescriptorSerializer(
|
|||||||
// natural order of declaration. Otherwise
|
// natural order of declaration. Otherwise
|
||||||
// they appear in the order of appearence in the
|
// they appear in the order of appearence in the
|
||||||
// body of the function, and get wrong indices.
|
// body of the function, and get wrong indices.
|
||||||
typeSerializer(it.defaultType)
|
localDeclarationSerializer.typeSerializer(it.defaultType)
|
||||||
}
|
}
|
||||||
|
|
||||||
descriptor.valueParameters.forEach {
|
descriptor.valueParameters.forEach {
|
||||||
@@ -120,6 +123,7 @@ internal class IrDescriptorSerializer(
|
|||||||
|
|
||||||
fun variableDescriptorSpecifics(descriptor: VariableDescriptor, proto: KonanIr.KotlinDescriptor.Builder) {
|
fun variableDescriptorSpecifics(descriptor: VariableDescriptor, proto: KonanIr.KotlinDescriptor.Builder) {
|
||||||
proto.setType(serializeKotlinType(descriptor.type))
|
proto.setType(serializeKotlinType(descriptor.type))
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fun serializeDescriptor(descriptor: DeclarationDescriptor): KonanIr.KotlinDescriptor {
|
fun serializeDescriptor(descriptor: DeclarationDescriptor): KonanIr.KotlinDescriptor {
|
||||||
@@ -145,7 +149,7 @@ internal class IrDescriptorSerializer(
|
|||||||
context.log{"originalIndex = $originalIndex"}
|
context.log{"originalIndex = $originalIndex"}
|
||||||
context.log{""}
|
context.log{""}
|
||||||
|
|
||||||
val proto = KonanIr.KotlinDescriptor.newBuilder()
|
val proto = KonanIr.KotlinDescriptor.newBuilder()
|
||||||
.setName(descriptor.name.asString())
|
.setName(descriptor.name.asString())
|
||||||
.setKind(kotlinDescriptorKind(descriptor))
|
.setKind(kotlinDescriptorKind(descriptor))
|
||||||
.setIndex(index)
|
.setIndex(index)
|
||||||
|
|||||||
+15
-6
@@ -54,7 +54,7 @@ class KonanDescriptorSerializer private constructor(
|
|||||||
}.toByteArray()
|
}.toByteArray()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun createChildSerializer(descriptor: DeclarationDescriptor): KonanDescriptorSerializer =
|
fun createChildSerializer(descriptor: DeclarationDescriptor): KonanDescriptorSerializer =
|
||||||
KonanDescriptorSerializer(descriptor, Interner(typeParameters), extension, typeTable, sinceKotlinInfoTable,
|
KonanDescriptorSerializer(descriptor, Interner(typeParameters), extension, typeTable, sinceKotlinInfoTable,
|
||||||
serializeTypeTableToFunction = false)
|
serializeTypeTableToFunction = false)
|
||||||
|
|
||||||
@@ -230,11 +230,11 @@ class KonanDescriptorSerializer private constructor(
|
|||||||
if (extension is IrAwareExtension) {
|
if (extension is IrAwareExtension) {
|
||||||
descriptor.getter?.onlyIf({needsSerializedIr}) {
|
descriptor.getter?.onlyIf({needsSerializedIr}) {
|
||||||
extension.addGetterIR(builder,
|
extension.addGetterIR(builder,
|
||||||
extension.serializeInlineBody(it, {it -> typeId(it)}))
|
extension.serializeInlineBody(it, local))
|
||||||
}
|
}
|
||||||
descriptor.setter?.onlyIf({needsSerializedIr}) {
|
descriptor.setter?.onlyIf({needsSerializedIr}) {
|
||||||
extension.addSetterIR(builder,
|
extension.addSetterIR(builder,
|
||||||
extension.serializeInlineBody(it, {it -> typeId(it)}))
|
extension.serializeInlineBody(it, local))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -296,9 +296,9 @@ class KonanDescriptorSerializer private constructor(
|
|||||||
extension.serializeFunction(descriptor, builder)
|
extension.serializeFunction(descriptor, builder)
|
||||||
|
|
||||||
if (extension is IrAwareExtension
|
if (extension is IrAwareExtension
|
||||||
&& descriptor.needsSerializedIr) {
|
&& descriptor.needsSerializedIr) {
|
||||||
extension.addFunctionIR(builder,
|
extension.addFunctionIR(builder,
|
||||||
extension.serializeInlineBody(descriptor, {it -> typeId(it)}))
|
extension.serializeInlineBody(descriptor, local))
|
||||||
}
|
}
|
||||||
|
|
||||||
return builder
|
return builder
|
||||||
@@ -324,6 +324,12 @@ class KonanDescriptorSerializer private constructor(
|
|||||||
|
|
||||||
extension.serializeConstructor(descriptor, builder)
|
extension.serializeConstructor(descriptor, builder)
|
||||||
|
|
||||||
|
if (extension is IrAwareExtension
|
||||||
|
&& descriptor.needsSerializedIr) {
|
||||||
|
extension.addConstructorIR(builder,
|
||||||
|
extension.serializeInlineBody(descriptor, local))
|
||||||
|
}
|
||||||
|
|
||||||
return builder
|
return builder
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -447,7 +453,10 @@ class KonanDescriptorSerializer private constructor(
|
|||||||
return builder
|
return builder
|
||||||
}
|
}
|
||||||
|
|
||||||
public fun typeId(type: KotlinType): Int = typeTable[type(type)]
|
public fun typeId(type: KotlinType): Int {
|
||||||
|
val result = typeTable[type(type)]
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
private fun type(type: KotlinType): ProtoBuf.Type.Builder {
|
private fun type(type: KotlinType): ProtoBuf.Type.Builder {
|
||||||
val builder = ProtoBuf.Type.newBuilder()
|
val builder = ProtoBuf.Type.newBuilder()
|
||||||
|
|||||||
+43
-14
@@ -19,6 +19,7 @@ message KotlinDescriptor {
|
|||||||
TYPE_PARAMETER = 6;
|
TYPE_PARAMETER = 6;
|
||||||
RECEIVER = 7;
|
RECEIVER = 7;
|
||||||
ACCESSOR = 8;
|
ACCESSOR = 8;
|
||||||
|
PROPERTY = 9;
|
||||||
}
|
}
|
||||||
// TODO: Use the string table index.
|
// TODO: Use the string table index.
|
||||||
optional string name = 1;
|
optional string name = 1;
|
||||||
@@ -150,6 +151,16 @@ message IrGetEnumValue {
|
|||||||
required KotlinDescriptor descriptor = 2;
|
required KotlinDescriptor descriptor = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
message FieldAccessCommon {
|
||||||
|
required KotlinDescriptor descriptor = 1;
|
||||||
|
optional KotlinDescriptor super = 2;
|
||||||
|
required IrExpression reciever = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message IrGetField {
|
||||||
|
required FieldAccessCommon field_access = 1;
|
||||||
|
}
|
||||||
|
|
||||||
message IrGetValue {
|
message IrGetValue {
|
||||||
required KotlinDescriptor descriptor = 1;
|
required KotlinDescriptor descriptor = 1;
|
||||||
}
|
}
|
||||||
@@ -167,6 +178,11 @@ message IrReturn {
|
|||||||
required IrExpression value = 2;
|
required IrExpression value = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
message IrSetField {
|
||||||
|
required FieldAccessCommon field_access = 1;
|
||||||
|
required IrExpression value = 2;
|
||||||
|
}
|
||||||
|
|
||||||
message IrSetVariable {
|
message IrSetVariable {
|
||||||
required KotlinDescriptor descriptor = 1;
|
required KotlinDescriptor descriptor = 1;
|
||||||
required IrExpression value = 2;
|
required IrExpression value = 2;
|
||||||
@@ -220,18 +236,20 @@ message IrOperation {
|
|||||||
IrDelegatingConstructorCall delegating_constructor_call = 7;
|
IrDelegatingConstructorCall delegating_constructor_call = 7;
|
||||||
IrEnumConstructorCall enum_constructor_call = 8;
|
IrEnumConstructorCall enum_constructor_call = 8;
|
||||||
IrGetEnumValue get_enum_value = 9;
|
IrGetEnumValue get_enum_value = 9;
|
||||||
IrGetValue get_value = 10;
|
IrGetField get_field = 10;
|
||||||
IrGetObject get_object = 11;
|
IrGetValue get_value = 11;
|
||||||
IrInstanceInitializerCall instance_initializer_call = 12;
|
IrGetObject get_object = 12;
|
||||||
IrReturn return = 13;
|
IrInstanceInitializerCall instance_initializer_call = 13;
|
||||||
IrSetVariable set_variable = 14;
|
IrReturn return = 14;
|
||||||
IrStringConcat string_concat = 15;
|
IrSetField set_field = 15;
|
||||||
IrThrow throw = 16;
|
IrSetVariable set_variable = 16;
|
||||||
IrTry try = 17;
|
IrStringConcat string_concat = 17;
|
||||||
IrTypeOp type_op = 18;
|
IrThrow throw = 18;
|
||||||
IrVararg vararg = 19;
|
IrTry try = 19;
|
||||||
IrWhen when = 20;
|
IrTypeOp type_op = 20;
|
||||||
IrWhile while = 21;
|
IrVararg vararg = 21;
|
||||||
|
IrWhen when = 22;
|
||||||
|
IrWhile while = 23;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -254,7 +272,7 @@ message IrExpression {
|
|||||||
|
|
||||||
/* ------ Declarations --------------------------------------------- */
|
/* ------ Declarations --------------------------------------------- */
|
||||||
|
|
||||||
message IrFunc {
|
message IrFunction {
|
||||||
message DefaultArgument {
|
message DefaultArgument {
|
||||||
required int32 position = 1;
|
required int32 position = 1;
|
||||||
required IrExpression value = 2;
|
required IrExpression value = 2;
|
||||||
@@ -263,6 +281,16 @@ message IrFunc {
|
|||||||
repeated DefaultArgument default_argument = 2;
|
repeated DefaultArgument default_argument = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
message IrProperty {
|
||||||
|
message IrField {
|
||||||
|
required IrExpression initializer = 1;
|
||||||
|
}
|
||||||
|
required bool is_delegated = 1;
|
||||||
|
optional IrField backing_field = 2;
|
||||||
|
optional IrFunction getter = 3;
|
||||||
|
optional IrFunction setter = 4;
|
||||||
|
}
|
||||||
|
|
||||||
message IrVar {
|
message IrVar {
|
||||||
optional IrExpression initializer = 1;
|
optional IrExpression initializer = 1;
|
||||||
}
|
}
|
||||||
@@ -281,9 +309,10 @@ message IrEnumEntry {
|
|||||||
message IrDeclarator {
|
message IrDeclarator {
|
||||||
oneof symbol {
|
oneof symbol {
|
||||||
IrVar variable = 1;
|
IrVar variable = 1;
|
||||||
IrFunc function = 2;
|
IrFunction function = 2;
|
||||||
IrClass ir_class = 3;
|
IrClass ir_class = 3;
|
||||||
IrEnumEntry ir_enum_entry = 4;
|
IrEnumEntry ir_enum_entry = 4;
|
||||||
|
IrProperty ir_property = 5;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+1
@@ -25,6 +25,7 @@ extend Class {
|
|||||||
|
|
||||||
extend Constructor {
|
extend Constructor {
|
||||||
repeated Annotation constructor_annotation = 170;
|
repeated Annotation constructor_annotation = 170;
|
||||||
|
optional InlineIrBody inline_constructor_ir_body = 171;
|
||||||
}
|
}
|
||||||
|
|
||||||
extend Function {
|
extend Function {
|
||||||
|
|||||||
+26
-77
@@ -21,14 +21,10 @@ import org.jetbrains.kotlin.backend.konan.LinkData
|
|||||||
import org.jetbrains.kotlin.backend.konan.KonanBuiltIns
|
import org.jetbrains.kotlin.backend.konan.KonanBuiltIns
|
||||||
import org.jetbrains.kotlin.backend.konan.llvm.base64Decode
|
import org.jetbrains.kotlin.backend.konan.llvm.base64Decode
|
||||||
import org.jetbrains.kotlin.backend.konan.llvm.base64Encode
|
import org.jetbrains.kotlin.backend.konan.llvm.base64Encode
|
||||||
|
import org.jetbrains.kotlin.backend.konan.llvm.isExported
|
||||||
import org.jetbrains.kotlin.config.CompilerConfiguration
|
import org.jetbrains.kotlin.config.CompilerConfiguration
|
||||||
import org.jetbrains.kotlin.config.languageVersionSettings
|
import org.jetbrains.kotlin.config.languageVersionSettings
|
||||||
import org.jetbrains.kotlin.descriptors.*
|
import org.jetbrains.kotlin.descriptors.*
|
||||||
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor.Kind.DECLARATION
|
|
||||||
import org.jetbrains.kotlin.descriptors.Modality.FINAL
|
|
||||||
import org.jetbrains.kotlin.descriptors.SourceElement.NO_SOURCE
|
|
||||||
import org.jetbrains.kotlin.descriptors.Visibilities.INTERNAL
|
|
||||||
import org.jetbrains.kotlin.descriptors.annotations.Annotations.Companion.EMPTY
|
|
||||||
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
|
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
|
||||||
import org.jetbrains.kotlin.descriptors.impl.ModuleDescriptorImpl
|
import org.jetbrains.kotlin.descriptors.impl.ModuleDescriptorImpl
|
||||||
import org.jetbrains.kotlin.descriptors.impl.PropertyDescriptorImpl
|
import org.jetbrains.kotlin.descriptors.impl.PropertyDescriptorImpl
|
||||||
@@ -41,7 +37,6 @@ import org.jetbrains.kotlin.resolve.DescriptorUtils
|
|||||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
||||||
import org.jetbrains.kotlin.resolve.scopes.MemberScope
|
import org.jetbrains.kotlin.resolve.scopes.MemberScope
|
||||||
import org.jetbrains.kotlin.serialization.KonanDescriptorSerializer
|
import org.jetbrains.kotlin.serialization.KonanDescriptorSerializer
|
||||||
import org.jetbrains.kotlin.serialization.KonanIr
|
|
||||||
import org.jetbrains.kotlin.serialization.KonanLinkData
|
import org.jetbrains.kotlin.serialization.KonanLinkData
|
||||||
import org.jetbrains.kotlin.serialization.ProtoBuf
|
import org.jetbrains.kotlin.serialization.ProtoBuf
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.*
|
import org.jetbrains.kotlin.serialization.deserialization.*
|
||||||
@@ -55,6 +50,17 @@ import java.io.InputStream
|
|||||||
import java.io.ByteArrayInputStream
|
import java.io.ByteArrayInputStream
|
||||||
import java.io.ByteArrayOutputStream
|
import java.io.ByteArrayOutputStream
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This is Konan specific part of public descriptor
|
||||||
|
* tree serialization and deserialization.
|
||||||
|
*
|
||||||
|
* It takes care of module and package fragment serializations.
|
||||||
|
* The lower level (classes and members) serializations are delegated
|
||||||
|
* to the KonanDescriptorSerializer class.
|
||||||
|
* The lower level deserializations are performed by the frontend
|
||||||
|
* with MemberDeserializer class.
|
||||||
|
*/
|
||||||
|
|
||||||
typealias Base64 = String
|
typealias Base64 = String
|
||||||
|
|
||||||
fun byteArrayToBase64(byteArray: ByteArray): Base64 {
|
fun byteArrayToBase64(byteArray: ByteArray): Base64 {
|
||||||
@@ -150,25 +156,32 @@ internal fun deserializeModule(configuration: CompilerConfiguration,
|
|||||||
|
|
||||||
internal class KonanSerializationUtil(val context: Context) {
|
internal class KonanSerializationUtil(val context: Context) {
|
||||||
|
|
||||||
val serializerExtension = KonanSerializerExtension(context, this)
|
val serializerExtension = KonanSerializerExtension(context)
|
||||||
val serializer = KonanDescriptorSerializer.createTopLevel(serializerExtension)
|
val topSerializer = KonanDescriptorSerializer.createTopLevel(serializerExtension)
|
||||||
val typeSerializer: (KotlinType)->Int = { it -> serializer.typeId(it) }
|
var classSerializer: KonanDescriptorSerializer = topSerializer
|
||||||
|
|
||||||
fun serializeClass(packageName: FqName,
|
fun serializeClass(packageName: FqName,
|
||||||
builder: KonanLinkData.Classes.Builder,
|
builder: KonanLinkData.Classes.Builder,
|
||||||
classDescriptor: ClassDescriptor) {
|
classDescriptor: ClassDescriptor) {
|
||||||
|
|
||||||
val localSerializer = KonanDescriptorSerializer.create(classDescriptor, serializerExtension)
|
val previousSerializer = classSerializer
|
||||||
val classProto = localSerializer.classProto(classDescriptor).build()
|
|
||||||
|
// TODO: this is to filter out object{}. Change me.
|
||||||
|
if (classDescriptor.isExported())
|
||||||
|
classSerializer = KonanDescriptorSerializer.create(classDescriptor, serializerExtension)
|
||||||
|
|
||||||
|
val classProto = classSerializer.classProto(classDescriptor).build()
|
||||||
?: error("Class not serialized: $classDescriptor")
|
?: error("Class not serialized: $classDescriptor")
|
||||||
|
|
||||||
builder.addClasses(classProto)
|
builder.addClasses(classProto)
|
||||||
val index = localSerializer.stringTable.getFqNameIndex(classDescriptor)
|
val index = classSerializer.stringTable.getFqNameIndex(classDescriptor)
|
||||||
builder.addClassName(index)
|
builder.addClassName(index)
|
||||||
|
|
||||||
serializeClasses(packageName, builder,
|
serializeClasses(packageName, builder,
|
||||||
classDescriptor.unsubstitutedInnerClassesScope
|
classDescriptor.unsubstitutedInnerClassesScope
|
||||||
.getContributedDescriptors(DescriptorKindFilter.CLASSIFIERS))
|
.getContributedDescriptors(DescriptorKindFilter.CLASSIFIERS))
|
||||||
|
|
||||||
|
classSerializer = previousSerializer
|
||||||
}
|
}
|
||||||
|
|
||||||
fun serializeClasses(packageName: FqName,
|
fun serializeClasses(packageName: FqName,
|
||||||
@@ -208,7 +221,7 @@ internal class KonanSerializationUtil(val context: Context) {
|
|||||||
serializeClasses(fqName, classesBuilder, classifierDescriptors)
|
serializeClasses(fqName, classesBuilder, classifierDescriptors)
|
||||||
val classesProto = classesBuilder.build()
|
val classesProto = classesBuilder.build()
|
||||||
|
|
||||||
val packageProto = serializer.packagePartProto(fqName, members).build()
|
val packageProto = topSerializer.packagePartProto(fqName, members).build()
|
||||||
?: error("Package fragments not serialized: $fragments")
|
?: error("Package fragments not serialized: $fragments")
|
||||||
|
|
||||||
val strings = serializerExtension.stringTable
|
val strings = serializerExtension.stringTable
|
||||||
@@ -263,69 +276,5 @@ internal class KonanSerializationUtil(val context: Context) {
|
|||||||
val library = byteArrayToBase64(libraryAsByteArray)
|
val library = byteArrayToBase64(libraryAsByteArray)
|
||||||
return LinkData(library, fragments, fragmentNames)
|
return LinkData(library, fragments, fragmentNames)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* The section below is specific for IR serialization */
|
|
||||||
|
|
||||||
// TODO: We utilize DescriptorSerializer's property
|
|
||||||
// serialization to serialize variables for now.
|
|
||||||
// Need to negotiate the ability to deserialize
|
|
||||||
// variables with the big kotlin somehow.
|
|
||||||
fun variableAsProperty(variable: VariableDescriptor): PropertyDescriptor {
|
|
||||||
|
|
||||||
val isDelegated = when (variable) {
|
|
||||||
is LocalVariableDescriptor -> variable.isDelegated
|
|
||||||
is IrTemporaryVariableDescriptor -> false
|
|
||||||
else -> error("Unexpected variable descriptor.")
|
|
||||||
}
|
|
||||||
|
|
||||||
val property = PropertyDescriptorImpl.create(
|
|
||||||
variable.containingDeclaration,
|
|
||||||
EMPTY,
|
|
||||||
FINAL,
|
|
||||||
INTERNAL,
|
|
||||||
variable.isVar(),
|
|
||||||
variable.name,
|
|
||||||
DECLARATION,
|
|
||||||
NO_SOURCE,
|
|
||||||
false, false, false, false, false,
|
|
||||||
isDelegated)
|
|
||||||
|
|
||||||
property.setType(variable.type, listOf(), null, null as KotlinType?)
|
|
||||||
|
|
||||||
// TODO: transform the getter and the setter too.
|
|
||||||
property.initialize(null, null)
|
|
||||||
return property
|
|
||||||
}
|
|
||||||
|
|
||||||
fun serializeLocalDeclaration(descriptor: DeclarationDescriptor): KonanIr.DeclarationDescriptor {
|
|
||||||
|
|
||||||
val proto = KonanIr.DeclarationDescriptor.newBuilder()
|
|
||||||
|
|
||||||
context.log{"### serializeLocalDeclaration: $descriptor"}
|
|
||||||
|
|
||||||
when (descriptor) {
|
|
||||||
is FunctionDescriptor ->
|
|
||||||
proto.setFunction(serializer.functionProto(descriptor))
|
|
||||||
|
|
||||||
is PropertyDescriptor ->
|
|
||||||
proto.setProperty(serializer.propertyProto(descriptor))
|
|
||||||
|
|
||||||
is ClassDescriptor ->
|
|
||||||
proto.setClazz(serializer.classProto(descriptor))
|
|
||||||
|
|
||||||
is VariableDescriptor -> {
|
|
||||||
val property = variableAsProperty(descriptor)
|
|
||||||
serializerExtension.originalVariables.put(property, descriptor)
|
|
||||||
proto.setProperty(serializer.propertyProto(property))
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> error("Unexpected descriptor kind: $descriptor")
|
|
||||||
}
|
|
||||||
|
|
||||||
return proto.build()
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+9
-7
@@ -24,12 +24,10 @@ import org.jetbrains.kotlin.protobuf.ExtensionRegistryLite
|
|||||||
import org.jetbrains.kotlin.serialization.*
|
import org.jetbrains.kotlin.serialization.*
|
||||||
import org.jetbrains.kotlin.types.KotlinType
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
|
|
||||||
|
internal class KonanSerializerExtension(val context: Context) :
|
||||||
internal class KonanSerializerExtension(val context: Context, val util: KonanSerializationUtil) :
|
|
||||||
KotlinSerializerExtensionBase(KonanSerializerProtocol), IrAwareExtension {
|
KotlinSerializerExtensionBase(KonanSerializerProtocol), IrAwareExtension {
|
||||||
|
|
||||||
val inlineDescriptorTable = DescriptorTable(context.irBuiltIns)
|
val inlineDescriptorTable = DescriptorTable(context.irBuiltIns)
|
||||||
val originalVariables = mutableMapOf<PropertyDescriptor, VariableDescriptor>()
|
|
||||||
override val stringTable = KonanStringTable()
|
override val stringTable = KonanStringTable()
|
||||||
override fun shouldUseTypeTable(): Boolean = true
|
override fun shouldUseTypeTable(): Boolean = true
|
||||||
|
|
||||||
@@ -85,17 +83,19 @@ internal class KonanSerializerExtension(val context: Context, val util: KonanSer
|
|||||||
override fun addFunctionIR(proto: ProtoBuf.Function.Builder, serializedIR: String)
|
override fun addFunctionIR(proto: ProtoBuf.Function.Builder, serializedIR: String)
|
||||||
= proto.setInlineIr(inlineBody(serializedIR))
|
= proto.setInlineIr(inlineBody(serializedIR))
|
||||||
|
|
||||||
|
override fun addConstructorIR(proto: ProtoBuf.Constructor.Builder, serializedIR: String)
|
||||||
|
= proto.setConstructorIr(inlineBody(serializedIR))
|
||||||
|
|
||||||
override fun addGetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String)
|
override fun addGetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String)
|
||||||
= proto.setGetterIr(inlineBody(serializedIR))
|
= proto.setGetterIr(inlineBody(serializedIR))
|
||||||
|
|
||||||
override fun addSetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String)
|
override fun addSetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String)
|
||||||
= proto.setSetterIr(inlineBody(serializedIR))
|
= proto.setSetterIr(inlineBody(serializedIR))
|
||||||
|
|
||||||
override fun serializeInlineBody(descriptor: FunctionDescriptor, typeSerializer: ((KotlinType)->Int)): String {
|
override fun serializeInlineBody(descriptor: FunctionDescriptor, serializer: KonanDescriptorSerializer): String {
|
||||||
|
|
||||||
return IrSerializer(
|
return IrSerializer(
|
||||||
context, inlineDescriptorTable, stringTable, util,
|
context, inlineDescriptorTable, stringTable, serializer, descriptor).serializeInlineBody()
|
||||||
typeSerializer, descriptor).serializeInlineBody()
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -117,10 +117,12 @@ object KonanSerializerProtocol : SerializerExtensionProtocol(
|
|||||||
|
|
||||||
internal interface IrAwareExtension {
|
internal interface IrAwareExtension {
|
||||||
|
|
||||||
fun serializeInlineBody(descriptor: FunctionDescriptor, typeSerializer: ((KotlinType)->Int)): String
|
fun serializeInlineBody(descriptor: FunctionDescriptor, serializer: KonanDescriptorSerializer): String
|
||||||
|
|
||||||
fun addFunctionIR(proto: ProtoBuf.Function.Builder, serializedIR: String): ProtoBuf.Function.Builder
|
fun addFunctionIR(proto: ProtoBuf.Function.Builder, serializedIR: String): ProtoBuf.Function.Builder
|
||||||
|
|
||||||
|
fun addConstructorIR(proto: ProtoBuf.Constructor.Builder, serializedIR: String): ProtoBuf.Constructor.Builder
|
||||||
|
|
||||||
fun addSetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String): ProtoBuf.Property.Builder
|
fun addSetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String): ProtoBuf.Property.Builder
|
||||||
|
|
||||||
fun addGetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String): ProtoBuf.Property.Builder
|
fun addGetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String): ProtoBuf.Property.Builder
|
||||||
|
|||||||
+67
-59
@@ -16,6 +16,7 @@
|
|||||||
|
|
||||||
package org.jetbrains.kotlin.backend.konan.serialization
|
package org.jetbrains.kotlin.backend.konan.serialization
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.backend.konan.descriptors.allContainingDeclarations
|
||||||
import org.jetbrains.kotlin.descriptors.*
|
import org.jetbrains.kotlin.descriptors.*
|
||||||
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
|
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
|
||||||
import org.jetbrains.kotlin.serialization.Flags
|
import org.jetbrains.kotlin.serialization.Flags
|
||||||
@@ -23,96 +24,103 @@ import org.jetbrains.kotlin.serialization.KonanIr
|
|||||||
import org.jetbrains.kotlin.serialization.KonanLinkData
|
import org.jetbrains.kotlin.serialization.KonanLinkData
|
||||||
import org.jetbrains.kotlin.serialization.ProtoBuf
|
import org.jetbrains.kotlin.serialization.ProtoBuf
|
||||||
import org.jetbrains.kotlin.serialization.ProtoBuf.QualifiedNameTable.QualifiedName
|
import org.jetbrains.kotlin.serialization.ProtoBuf.QualifiedNameTable.QualifiedName
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.MemberDeserializer
|
import org.jetbrains.kotlin.serialization.deserialization.*
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.NameResolverImpl
|
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.TypeTable
|
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.descriptors.*
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.*
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.descriptors.SinceKotlinInfoTable
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.SinceKotlinInfoTable
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.findClassAcrossModuleDependencies
|
|
||||||
import org.jetbrains.kotlin.types.KotlinType
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
|
import org.jetbrains.kotlin.backend.common.peek
|
||||||
|
import org.jetbrains.kotlin.backend.common.push
|
||||||
|
import org.jetbrains.kotlin.backend.common.pop
|
||||||
|
|
||||||
// This class knows how to construct contexts for
|
// This class knows how to construct contexts for
|
||||||
// MemberDeserializer to deserialize descriptors declared in IR.
|
// MemberDeserializer to deserialize descriptors declared in IR.
|
||||||
// Consider merging it all to the very MemberDesereializer itself eventually.
|
// Eventually, these descriptors shall be reconstructed from IR declarations,
|
||||||
|
// or may be just go away completely.
|
||||||
|
|
||||||
class LocalDeclarationDeserializer(val rootDescriptor: DeserializedCallableMemberDescriptor, val module: ModuleDescriptor) {
|
class LocalDeclarationDeserializer(val rootDescriptor: DeclarationDescriptor) {
|
||||||
|
|
||||||
val pkg = rootDescriptor.getContainingDeclaration() as KonanPackageFragment
|
val tower: List<DeclarationDescriptor> =
|
||||||
|
(listOf(rootDescriptor) + rootDescriptor.allContainingDeclarations()).reversed()
|
||||||
init {
|
init {
|
||||||
assert(pkg is KonanPackageFragment)
|
assert(tower.first() is ModuleDescriptor)
|
||||||
}
|
}
|
||||||
|
val parents = tower.drop(1)
|
||||||
|
|
||||||
|
val pkg = parents.first() as KonanPackageFragment
|
||||||
val components = pkg.components
|
val components = pkg.components
|
||||||
val nameResolver = NameResolverImpl(pkg.proto.getStringTable(), pkg.proto.getNameTable())
|
val nameTable = pkg.proto.nameTable
|
||||||
val nameTable = pkg.proto.getNameTable()
|
val nameResolver = NameResolverImpl(pkg.proto.stringTable, nameTable)
|
||||||
val typeTable = TypeTable(pkg.proto.getPackage().getTypeTable())
|
|
||||||
val context = components.createContext(
|
|
||||||
pkg, nameResolver, typeTable, SinceKotlinInfoTable.EMPTY, null)
|
|
||||||
|
|
||||||
val typeParameterProtos = when (rootDescriptor) {
|
val contextStack = mutableListOf<Pair<DeserializationContext, MemberDeserializer>>()
|
||||||
// These are two different typeParameterLists not
|
|
||||||
// having a common ancestor.
|
init {
|
||||||
is DeserializedSimpleFunctionDescriptor
|
parents.forEach{
|
||||||
-> rootDescriptor.proto.typeParameterList
|
pushContext(it)
|
||||||
is DeserializedPropertyDescriptor
|
}
|
||||||
-> rootDescriptor.proto.typeParameterList
|
|
||||||
else -> error("Unexpected descriptor kind")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
val childContext = context.childContext(rootDescriptor, typeParameterProtos, nameResolver, typeTable)
|
val parentContext: DeserializationContext
|
||||||
val typeDeserializer = childContext.typeDeserializer
|
get() = contextStack.peek()!!.first
|
||||||
|
|
||||||
val memberDeserializer = MemberDeserializer(childContext)
|
val parentTypeTable: TypeTable
|
||||||
|
get() = parentContext.typeTable
|
||||||
|
|
||||||
|
val typeDeserializer: TypeDeserializer
|
||||||
|
get() = parentContext.typeDeserializer
|
||||||
|
|
||||||
|
val memberDeserializer: MemberDeserializer
|
||||||
|
get() = contextStack.peek()!!.second
|
||||||
|
|
||||||
|
fun newContext(descriptor: DeclarationDescriptor): DeserializationContext {
|
||||||
|
if (descriptor is KonanPackageFragment) {
|
||||||
|
val packageTypeTable = TypeTable(pkg.proto.getPackage().typeTable)
|
||||||
|
return components.createContext(
|
||||||
|
pkg, nameResolver, packageTypeTable, SinceKotlinInfoTable.EMPTY, null)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Only packages and classes have their type tables.
|
||||||
|
val typeTable = if (descriptor is DeserializedClassDescriptor) {
|
||||||
|
TypeTable(descriptor.classProto.typeTable)
|
||||||
|
} else {
|
||||||
|
parentTypeTable
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
val oldContext = contextStack.peek()!!.first
|
||||||
|
|
||||||
|
return oldContext.childContext(descriptor,
|
||||||
|
descriptor.typeParameterProtos, nameResolver, typeTable)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun pushContext(descriptor: DeclarationDescriptor) {
|
||||||
|
val newContext = newContext(descriptor)
|
||||||
|
contextStack.push(Pair(newContext, MemberDeserializer(newContext)))
|
||||||
|
}
|
||||||
|
|
||||||
|
fun popContext(descriptor: DeclarationDescriptor) {
|
||||||
|
assert(contextStack.peek()!!.first.containingDeclaration == descriptor)
|
||||||
|
contextStack.pop()
|
||||||
|
}
|
||||||
|
|
||||||
fun deserializeInlineType(type: ProtoBuf.Type): KotlinType {
|
fun deserializeInlineType(type: ProtoBuf.Type): KotlinType {
|
||||||
|
|
||||||
val result = typeDeserializer.type(type)
|
val result = typeDeserializer.type(type)
|
||||||
|
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
fun getDescriptorByFqNameIndex(module: ModuleDescriptor, fqNameIndex: Int): DeclarationDescriptor {
|
fun deserializeClass(irProto: KonanIr.KotlinDescriptor): ClassDescriptor {
|
||||||
|
return DeserializedClassDescriptor(parentContext, irProto.irLocalDeclaration.descriptor.clazz, nameResolver, SourceElement.NO_SOURCE)
|
||||||
|
|
||||||
val packageName = nameResolver.getPackageFqName(fqNameIndex)
|
|
||||||
// Here we using internals of NameresolverImpl.
|
|
||||||
val proto = nameTable.getQualifiedName(fqNameIndex)
|
|
||||||
when (proto.kind) {
|
|
||||||
QualifiedName.Kind.CLASS,
|
|
||||||
QualifiedName.Kind.LOCAL ->
|
|
||||||
return module.findClassAcrossModuleDependencies(nameResolver.getClassId(fqNameIndex))!!
|
|
||||||
QualifiedName.Kind.PACKAGE ->
|
|
||||||
return module.getPackage(packageName)
|
|
||||||
else -> TODO("Unexpected descriptor kind.")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun memberDeserializerByParentFqNameIndex(fqNameIndex: Int): MemberDeserializer {
|
|
||||||
|
|
||||||
val parent = getDescriptorByFqNameIndex(module, fqNameIndex)
|
|
||||||
val typeParameters = if (parent is DeserializedClassDescriptor) {
|
|
||||||
parent.classProto.typeParameterList
|
|
||||||
} else listOf<ProtoBuf.TypeParameter>()
|
|
||||||
|
|
||||||
val childContext = context.childContext(parent, typeParameters, nameResolver, typeTable)
|
|
||||||
return MemberDeserializer(childContext)
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun memberDeserializer(irProto: KonanIr.KotlinDescriptor): MemberDeserializer {
|
|
||||||
return if (irProto.hasClassOrPackage()) {
|
|
||||||
memberDeserializerByParentFqNameIndex(irProto.classOrPackage)
|
|
||||||
} else {
|
|
||||||
// TODO: learn to take the containing IR declaration
|
|
||||||
this.memberDeserializer
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fun deserializeFunction(irProto: KonanIr.KotlinDescriptor): FunctionDescriptor =
|
fun deserializeFunction(irProto: KonanIr.KotlinDescriptor): FunctionDescriptor =
|
||||||
memberDeserializer(irProto).loadFunction(irProto.irLocalDeclaration.descriptor.function)
|
memberDeserializer.loadFunction(irProto.irLocalDeclaration.descriptor.function)
|
||||||
|
|
||||||
fun deserializeConstructor(irProto: KonanIr.KotlinDescriptor): ConstructorDescriptor {
|
fun deserializeConstructor(irProto: KonanIr.KotlinDescriptor): ConstructorDescriptor {
|
||||||
|
|
||||||
val proto = irProto.irLocalDeclaration.descriptor.constructor
|
val proto = irProto.irLocalDeclaration.descriptor.constructor
|
||||||
val memberDeserializer = memberDeserializerByParentFqNameIndex(irProto.classOrPackage)
|
|
||||||
val isPrimary = !Flags.IS_SECONDARY.get(proto.flags)
|
val isPrimary = !Flags.IS_SECONDARY.get(proto.flags)
|
||||||
val constructor = memberDeserializer.loadConstructor(proto, isPrimary)
|
val constructor = memberDeserializer.loadConstructor(proto, isPrimary)
|
||||||
|
|
||||||
@@ -122,7 +130,7 @@ class LocalDeclarationDeserializer(val rootDescriptor: DeserializedCallableMembe
|
|||||||
fun deserializeProperty(irProto: KonanIr.KotlinDescriptor): VariableDescriptor {
|
fun deserializeProperty(irProto: KonanIr.KotlinDescriptor): VariableDescriptor {
|
||||||
|
|
||||||
val proto = irProto.irLocalDeclaration.descriptor.property
|
val proto = irProto.irLocalDeclaration.descriptor.property
|
||||||
val property = memberDeserializer(irProto).loadProperty(proto)
|
val property = memberDeserializer.loadProperty(proto)
|
||||||
|
|
||||||
return if (proto.getExtension(KonanLinkData.usedAsVariable)) {
|
return if (proto.getExtension(KonanLinkData.usedAsVariable)) {
|
||||||
propertyToVariable(property)
|
propertyToVariable(property)
|
||||||
|
|||||||
+133
@@ -0,0 +1,133 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.jetbrains.kotlin.backend.konan.serialization
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.backend.common.peek
|
||||||
|
import org.jetbrains.kotlin.backend.common.pop
|
||||||
|
import org.jetbrains.kotlin.backend.common.push
|
||||||
|
import org.jetbrains.kotlin.backend.konan.Context
|
||||||
|
import org.jetbrains.kotlin.descriptors.*
|
||||||
|
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor.Kind.DECLARATION
|
||||||
|
import org.jetbrains.kotlin.descriptors.Modality.FINAL
|
||||||
|
import org.jetbrains.kotlin.descriptors.SourceElement.NO_SOURCE
|
||||||
|
import org.jetbrains.kotlin.descriptors.Visibilities.INTERNAL
|
||||||
|
import org.jetbrains.kotlin.descriptors.annotations.Annotations.Companion.EMPTY
|
||||||
|
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
|
||||||
|
import org.jetbrains.kotlin.descriptors.impl.PropertyDescriptorImpl
|
||||||
|
import org.jetbrains.kotlin.ir.descriptors.IrTemporaryVariableDescriptor
|
||||||
|
import org.jetbrains.kotlin.serialization.KonanDescriptorSerializer
|
||||||
|
import org.jetbrains.kotlin.serialization.KonanIr
|
||||||
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This class knows how to create KonanDescriptorSerializer
|
||||||
|
* invocations to serialize function local declaration descriptors.
|
||||||
|
* Those descriptors are not part of the public descriptor tree.
|
||||||
|
*
|
||||||
|
* We maintain the stack of the serializers because this class
|
||||||
|
* provides type serialization facility for all the types in IR.
|
||||||
|
* And class serialization is context specific.
|
||||||
|
*/
|
||||||
|
|
||||||
|
internal class LocalDeclarationSerializer(val context: Context, val rootFunctionSerializer: KonanDescriptorSerializer) {
|
||||||
|
|
||||||
|
private val contextStack = mutableListOf<KonanDescriptorSerializer>(rootFunctionSerializer)
|
||||||
|
|
||||||
|
fun pushContext(descriptor: DeclarationDescriptor) {
|
||||||
|
val previousContext = contextStack.peek()!!
|
||||||
|
val newSerializer = previousContext.createChildSerializer(descriptor)
|
||||||
|
contextStack.push(newSerializer)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun popContext(descriptor: DeclarationDescriptor) {
|
||||||
|
contextStack.pop()
|
||||||
|
}
|
||||||
|
|
||||||
|
val localSerializer
|
||||||
|
get() = contextStack.peek()!!
|
||||||
|
|
||||||
|
val typeSerializer: ((KotlinType)->Int)
|
||||||
|
get() = {it -> localSerializer.typeId(it)}
|
||||||
|
|
||||||
|
fun serializeLocalDeclaration(descriptor: DeclarationDescriptor): KonanIr.DeclarationDescriptor {
|
||||||
|
|
||||||
|
val proto = KonanIr.DeclarationDescriptor.newBuilder()
|
||||||
|
|
||||||
|
context.log{"### serializeLocalDeclaration: $descriptor"}
|
||||||
|
|
||||||
|
val parent = descriptor.classOrPackage
|
||||||
|
|
||||||
|
|
||||||
|
when (descriptor) {
|
||||||
|
is ClassConstructorDescriptor ->
|
||||||
|
proto.setConstructor(localSerializer.constructorProto(descriptor))
|
||||||
|
|
||||||
|
is FunctionDescriptor ->
|
||||||
|
proto.setFunction(localSerializer.functionProto(descriptor))
|
||||||
|
|
||||||
|
is PropertyDescriptor ->
|
||||||
|
proto.setProperty(localSerializer.propertyProto(descriptor))
|
||||||
|
|
||||||
|
is ClassDescriptor ->
|
||||||
|
proto.setClazz(localSerializer.classProto(descriptor))
|
||||||
|
|
||||||
|
is VariableDescriptor -> {
|
||||||
|
val property = variableAsProperty(descriptor)
|
||||||
|
originalVariables.put(property, descriptor)
|
||||||
|
proto.setProperty(localSerializer.propertyProto(property))
|
||||||
|
}
|
||||||
|
|
||||||
|
else -> error("Unexpected descriptor kind: $descriptor")
|
||||||
|
}
|
||||||
|
|
||||||
|
return proto.build()
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: We utilize DescriptorSerializer's property
|
||||||
|
// serialization to serialize variables for now.
|
||||||
|
// Need to introduce an extension protobuf message
|
||||||
|
// and serialize variables directly.
|
||||||
|
fun variableAsProperty(variable: VariableDescriptor): PropertyDescriptor {
|
||||||
|
|
||||||
|
val isDelegated = when (variable) {
|
||||||
|
is LocalVariableDescriptor -> variable.isDelegated
|
||||||
|
is IrTemporaryVariableDescriptor -> false
|
||||||
|
else -> error("Unexpected variable descriptor.")
|
||||||
|
}
|
||||||
|
|
||||||
|
val property = PropertyDescriptorImpl.create(
|
||||||
|
variable.containingDeclaration,
|
||||||
|
EMPTY,
|
||||||
|
FINAL,
|
||||||
|
INTERNAL,
|
||||||
|
variable.isVar(),
|
||||||
|
variable.name,
|
||||||
|
DECLARATION,
|
||||||
|
NO_SOURCE,
|
||||||
|
false, false, false, false, false,
|
||||||
|
isDelegated)
|
||||||
|
|
||||||
|
property.setType(variable.type, listOf(), null, null as KotlinType?)
|
||||||
|
|
||||||
|
// TODO: transform the getter and the setter too.
|
||||||
|
property.initialize(null, null)
|
||||||
|
return property
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
val originalVariables = mutableMapOf<PropertyDescriptor, VariableDescriptor>()
|
||||||
|
|
||||||
+27
@@ -1,5 +1,7 @@
|
|||||||
package org.jetbrains.kotlin.backend.konan.serialization
|
package org.jetbrains.kotlin.backend.konan.serialization
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.descriptors.*
|
||||||
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.*
|
||||||
import org.jetbrains.kotlin.serialization.KonanIr
|
import org.jetbrains.kotlin.serialization.KonanIr
|
||||||
import org.jetbrains.kotlin.serialization.KonanLinkData
|
import org.jetbrains.kotlin.serialization.KonanLinkData
|
||||||
import org.jetbrains.kotlin.serialization.KonanLinkData.*
|
import org.jetbrains.kotlin.serialization.KonanLinkData.*
|
||||||
@@ -48,6 +50,12 @@ val ProtoBuf.Property.setterIr: InlineIrBody
|
|||||||
fun ProtoBuf.Property.Builder.setSetterIr(body: InlineIrBody): ProtoBuf.Property.Builder =
|
fun ProtoBuf.Property.Builder.setSetterIr(body: InlineIrBody): ProtoBuf.Property.Builder =
|
||||||
this.setExtension(inlineSetterIrBody, body)
|
this.setExtension(inlineSetterIrBody, body)
|
||||||
|
|
||||||
|
val ProtoBuf.Constructor.constructorIr: InlineIrBody
|
||||||
|
get() = this.getExtension(inlineConstructorIrBody)
|
||||||
|
|
||||||
|
fun ProtoBuf.Constructor.Builder.setConstructorIr(body: InlineIrBody): ProtoBuf.Constructor.Builder =
|
||||||
|
this.setExtension(inlineConstructorIrBody, body)
|
||||||
|
|
||||||
val ProtoBuf.Function.inlineIr: InlineIrBody
|
val ProtoBuf.Function.inlineIr: InlineIrBody
|
||||||
get() = this.getExtension(inlineIrBody)
|
get() = this.getExtension(inlineIrBody)
|
||||||
|
|
||||||
@@ -74,4 +82,23 @@ internal fun printTypeTable(proto: ProtoBuf.TypeTable) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// -----------------------------------------------------------
|
||||||
|
|
||||||
|
internal val DeclarationDescriptor.typeParameterProtos: List<ProtoBuf.TypeParameter>
|
||||||
|
get() = when (this) {
|
||||||
|
// These are different typeParameterLists not
|
||||||
|
// having a common ancestor.
|
||||||
|
is DeserializedSimpleFunctionDescriptor
|
||||||
|
-> this.proto.typeParameterList
|
||||||
|
is DeserializedPropertyDescriptor
|
||||||
|
-> this.proto.typeParameterList
|
||||||
|
is DeserializedClassDescriptor
|
||||||
|
-> this.classProto.typeParameterList
|
||||||
|
is DeserializedTypeAliasDescriptor
|
||||||
|
-> this.proto.typeParameterList
|
||||||
|
is DeserializedClassConstructorDescriptor
|
||||||
|
-> listOf()
|
||||||
|
else -> error("Unexpected descriptor kind: $this")
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
+128
-42
@@ -18,10 +18,9 @@ package org.jetbrains.kotlin.backend.konan.serialization
|
|||||||
|
|
||||||
|
|
||||||
import org.jetbrains.kotlin.backend.common.DeepCopyIrTreeWithDescriptors
|
import org.jetbrains.kotlin.backend.common.DeepCopyIrTreeWithDescriptors
|
||||||
import org.jetbrains.kotlin.backend.common.ScopeWithIr
|
|
||||||
import org.jetbrains.kotlin.backend.konan.Context
|
import org.jetbrains.kotlin.backend.konan.Context
|
||||||
import org.jetbrains.kotlin.backend.konan.descriptors.*
|
import org.jetbrains.kotlin.backend.konan.descriptors.deserializedPropertyIfAccessor
|
||||||
import org.jetbrains.kotlin.backend.konan.KonanIrDeserializationException
|
import org.jetbrains.kotlin.backend.konan.descriptors.isDeserializableCallable
|
||||||
import org.jetbrains.kotlin.backend.konan.ir.ir2string
|
import org.jetbrains.kotlin.backend.konan.ir.ir2string
|
||||||
import org.jetbrains.kotlin.backend.konan.ir.ir2stringWhole
|
import org.jetbrains.kotlin.backend.konan.ir.ir2stringWhole
|
||||||
import org.jetbrains.kotlin.backend.konan.llvm.base64Decode
|
import org.jetbrains.kotlin.backend.konan.llvm.base64Decode
|
||||||
@@ -29,7 +28,6 @@ import org.jetbrains.kotlin.backend.konan.llvm.base64Encode
|
|||||||
import org.jetbrains.kotlin.descriptors.*
|
import org.jetbrains.kotlin.descriptors.*
|
||||||
import org.jetbrains.kotlin.ir.IrElement
|
import org.jetbrains.kotlin.ir.IrElement
|
||||||
import org.jetbrains.kotlin.ir.IrStatement
|
import org.jetbrains.kotlin.ir.IrStatement
|
||||||
import org.jetbrains.kotlin.ir.builders.Scope
|
|
||||||
import org.jetbrains.kotlin.ir.declarations.*
|
import org.jetbrains.kotlin.ir.declarations.*
|
||||||
import org.jetbrains.kotlin.ir.declarations.IrDeclarationOrigin.DEFINED
|
import org.jetbrains.kotlin.ir.declarations.IrDeclarationOrigin.DEFINED
|
||||||
import org.jetbrains.kotlin.ir.declarations.impl.IrClassImpl
|
import org.jetbrains.kotlin.ir.declarations.impl.IrClassImpl
|
||||||
@@ -40,11 +38,14 @@ import org.jetbrains.kotlin.ir.expressions.*
|
|||||||
import org.jetbrains.kotlin.ir.expressions.impl.*
|
import org.jetbrains.kotlin.ir.expressions.impl.*
|
||||||
import org.jetbrains.kotlin.ir.symbols.impl.createFunctionSymbol
|
import org.jetbrains.kotlin.ir.symbols.impl.createFunctionSymbol
|
||||||
import org.jetbrains.kotlin.ir.util.createParameterDeclarations
|
import org.jetbrains.kotlin.ir.util.createParameterDeclarations
|
||||||
|
import org.jetbrains.kotlin.serialization.KonanDescriptorSerializer
|
||||||
import org.jetbrains.kotlin.serialization.KonanIr
|
import org.jetbrains.kotlin.serialization.KonanIr
|
||||||
import org.jetbrains.kotlin.serialization.KonanIr.IrConst.ValueCase.*
|
import org.jetbrains.kotlin.serialization.KonanIr.IrConst.ValueCase.*
|
||||||
import org.jetbrains.kotlin.serialization.KonanIr.IrOperation.OperationCase.*
|
import org.jetbrains.kotlin.serialization.KonanIr.IrOperation.OperationCase.*
|
||||||
import org.jetbrains.kotlin.serialization.KonanLinkData
|
import org.jetbrains.kotlin.serialization.KonanLinkData
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.descriptors.*
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedClassConstructorDescriptor
|
||||||
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedPropertyDescriptor
|
||||||
|
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedSimpleFunctionDescriptor
|
||||||
import org.jetbrains.kotlin.types.KotlinType
|
import org.jetbrains.kotlin.types.KotlinType
|
||||||
import org.jetbrains.kotlin.types.TypeProjectionImpl
|
import org.jetbrains.kotlin.types.TypeProjectionImpl
|
||||||
import org.jetbrains.kotlin.types.TypeSubstitutor
|
import org.jetbrains.kotlin.types.TypeSubstitutor
|
||||||
@@ -53,14 +54,16 @@ import org.jetbrains.kotlin.types.TypeSubstitutor
|
|||||||
internal class IrSerializer(val context: Context,
|
internal class IrSerializer(val context: Context,
|
||||||
val descriptorTable: DescriptorTable,
|
val descriptorTable: DescriptorTable,
|
||||||
val stringTable: KonanStringTable,
|
val stringTable: KonanStringTable,
|
||||||
val util: KonanSerializationUtil,
|
val rootFunctionSerializer: KonanDescriptorSerializer,
|
||||||
val typeSerializer: ((KotlinType)->Int),
|
|
||||||
var rootFunction: FunctionDescriptor) {
|
var rootFunction: FunctionDescriptor) {
|
||||||
|
|
||||||
val loopIndex = mutableMapOf<IrLoop, Int>()
|
val loopIndex = mutableMapOf<IrLoop, Int>()
|
||||||
var currentLoopIndex = 0
|
var currentLoopIndex = 0
|
||||||
val irDescriptorSerializer = IrDescriptorSerializer(context,
|
val localDeclarationSerializer
|
||||||
descriptorTable, stringTable, typeSerializer, rootFunction)
|
= LocalDeclarationSerializer(context, rootFunctionSerializer)
|
||||||
|
val irDescriptorSerializer
|
||||||
|
= IrDescriptorSerializer(context, descriptorTable,
|
||||||
|
stringTable, localDeclarationSerializer, rootFunction)
|
||||||
|
|
||||||
fun serializeInlineBody(): String {
|
fun serializeInlineBody(): String {
|
||||||
val declaration = context.ir.originalModuleIndex.functions[rootFunction]!!
|
val declaration = context.ir.originalModuleIndex.functions[rootFunction]!!
|
||||||
@@ -259,6 +262,24 @@ internal class IrSerializer(val context: Context,
|
|||||||
return proto.build()
|
return proto.build()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun serializeFieldAccessCommon(expression: IrFieldAccessExpression): KonanIr.FieldAccessCommon {
|
||||||
|
val proto = KonanIr.FieldAccessCommon.newBuilder()
|
||||||
|
.setDescriptor(serializeDescriptor(expression.descriptor))
|
||||||
|
val superQualifier = expression.superQualifier
|
||||||
|
if (superQualifier != null)
|
||||||
|
proto.setSuper(serializeDescriptor(superQualifier))
|
||||||
|
val receiver = expression.receiver
|
||||||
|
if (receiver != null)
|
||||||
|
proto.setReciever(serializeExpression(receiver))
|
||||||
|
return proto.build()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun serializeGetField(expression: IrGetField): KonanIr.IrGetField {
|
||||||
|
val proto = KonanIr.IrGetField.newBuilder()
|
||||||
|
.setFieldAccess(serializeFieldAccessCommon(expression))
|
||||||
|
return proto.build()
|
||||||
|
}
|
||||||
|
|
||||||
fun serializeGetValue(expression: IrGetValue): KonanIr.IrGetValue {
|
fun serializeGetValue(expression: IrGetValue): KonanIr.IrGetValue {
|
||||||
val proto = KonanIr.IrGetValue.newBuilder()
|
val proto = KonanIr.IrGetValue.newBuilder()
|
||||||
.setDescriptor(serializeDescriptor(expression.descriptor))
|
.setDescriptor(serializeDescriptor(expression.descriptor))
|
||||||
@@ -286,6 +307,13 @@ internal class IrSerializer(val context: Context,
|
|||||||
return proto.build()
|
return proto.build()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun serializeSetField(expression: IrSetField): KonanIr.IrSetField {
|
||||||
|
val proto = KonanIr.IrSetField.newBuilder()
|
||||||
|
.setFieldAccess(serializeFieldAccessCommon(expression))
|
||||||
|
.setValue(serializeExpression(expression.value))
|
||||||
|
return proto.build()
|
||||||
|
}
|
||||||
|
|
||||||
fun serializeSetVariable(expression: IrSetVariable): KonanIr.IrSetVariable {
|
fun serializeSetVariable(expression: IrSetVariable): KonanIr.IrSetVariable {
|
||||||
val proto = KonanIr.IrSetVariable.newBuilder()
|
val proto = KonanIr.IrSetVariable.newBuilder()
|
||||||
.setDescriptor(serializeDescriptor(expression.descriptor))
|
.setDescriptor(serializeDescriptor(expression.descriptor))
|
||||||
@@ -420,6 +448,7 @@ internal class IrSerializer(val context: Context,
|
|||||||
is IrContinue -> operationProto.setContinue(serializeContinue(expression))
|
is IrContinue -> operationProto.setContinue(serializeContinue(expression))
|
||||||
is IrDelegatingConstructorCall
|
is IrDelegatingConstructorCall
|
||||||
-> operationProto.setDelegatingConstructorCall(serializeDelegatingConstructorCall(expression))
|
-> operationProto.setDelegatingConstructorCall(serializeDelegatingConstructorCall(expression))
|
||||||
|
is IrGetField -> operationProto.setGetField(serializeGetField(expression))
|
||||||
is IrGetValue -> operationProto.setGetValue(serializeGetValue(expression))
|
is IrGetValue -> operationProto.setGetValue(serializeGetValue(expression))
|
||||||
is IrGetEnumValue
|
is IrGetEnumValue
|
||||||
-> operationProto.setGetEnumValue(serializeGetEnumValue(expression))
|
-> operationProto.setGetEnumValue(serializeGetEnumValue(expression))
|
||||||
@@ -428,6 +457,7 @@ internal class IrSerializer(val context: Context,
|
|||||||
is IrInstanceInitializerCall
|
is IrInstanceInitializerCall
|
||||||
-> operationProto.setInstanceInitializerCall(serializeInstanceInitializerCall(expression))
|
-> operationProto.setInstanceInitializerCall(serializeInstanceInitializerCall(expression))
|
||||||
is IrReturn -> operationProto.setReturn(serializeReturn(expression))
|
is IrReturn -> operationProto.setReturn(serializeReturn(expression))
|
||||||
|
is IrSetField -> operationProto.setSetField(serializeSetField(expression))
|
||||||
is IrSetVariable -> operationProto.setSetVariable(serializeSetVariable(expression))
|
is IrSetVariable -> operationProto.setSetVariable(serializeSetVariable(expression))
|
||||||
is IrStringConcatenation
|
is IrStringConcatenation
|
||||||
-> operationProto.setStringConcat(serializeStringConcat(expression))
|
-> operationProto.setStringConcat(serializeStringConcat(expression))
|
||||||
@@ -467,15 +497,15 @@ internal class IrSerializer(val context: Context,
|
|||||||
return proto.build()
|
return proto.build()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun serializeFunction(function: IrFunction): KonanIr.IrFunc {
|
fun serializeIrFunction(function: IrFunction): KonanIr.IrFunction {
|
||||||
val proto = KonanIr.IrFunc.newBuilder()
|
val proto = KonanIr.IrFunction.newBuilder()
|
||||||
val body = function.body
|
val body = function.body
|
||||||
if (body != null) proto.setBody(serializeStatement(body))
|
if (body != null) proto.setBody(serializeStatement(body))
|
||||||
|
|
||||||
function.descriptor.valueParameters.forEachIndexed { index, it ->
|
function.descriptor.valueParameters.forEachIndexed { index, it ->
|
||||||
val default = function.getDefault(it)
|
val default = function.getDefault(it)
|
||||||
if (default != null) {
|
if (default != null) {
|
||||||
val pair = KonanIr.IrFunc.DefaultArgument.newBuilder()
|
val pair = KonanIr.IrFunction.DefaultArgument.newBuilder()
|
||||||
pair.position = index
|
pair.position = index
|
||||||
pair.value = serializeExpression(default.expression)
|
pair.value = serializeExpression(default.expression)
|
||||||
proto.addDefaultArgument(pair)
|
proto.addDefaultArgument(pair)
|
||||||
@@ -485,7 +515,33 @@ internal class IrSerializer(val context: Context,
|
|||||||
return proto.build()
|
return proto.build()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun serializeVariable(variable: IrVariable): KonanIr.IrVar {
|
fun serializeIrProperty(property: IrProperty): KonanIr.IrProperty {
|
||||||
|
val proto = KonanIr.IrProperty.newBuilder()
|
||||||
|
.setIsDelegated(property.isDelegated)
|
||||||
|
val backingField = property.backingField
|
||||||
|
val getter = property.getter
|
||||||
|
val setter = property.setter
|
||||||
|
if (backingField != null)
|
||||||
|
proto.setBackingField(serializeIrField(backingField))
|
||||||
|
if (getter != null)
|
||||||
|
proto.setGetter(serializeIrFunction(getter))
|
||||||
|
if (setter != null)
|
||||||
|
proto.setSetter(serializeIrFunction(setter))
|
||||||
|
|
||||||
|
return proto.build()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun serializeIrField(field: IrField): KonanIr.IrProperty.IrField {
|
||||||
|
val proto = KonanIr.IrProperty.IrField.newBuilder()
|
||||||
|
val field = field.initializer?.expression
|
||||||
|
if (field != null) {
|
||||||
|
proto.setInitializer(
|
||||||
|
serializeExpression(field))
|
||||||
|
}
|
||||||
|
return proto.build()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun serializeIrVariable(variable: IrVariable): KonanIr.IrVar {
|
||||||
val proto = KonanIr.IrVar.newBuilder()
|
val proto = KonanIr.IrVar.newBuilder()
|
||||||
val initializer = variable.initializer
|
val initializer = variable.initializer
|
||||||
if (initializer != null) {
|
if (initializer != null) {
|
||||||
@@ -496,6 +552,12 @@ internal class IrSerializer(val context: Context,
|
|||||||
|
|
||||||
fun serializeIrClass(clazz: IrClass): KonanIr.IrClass {
|
fun serializeIrClass(clazz: IrClass): KonanIr.IrClass {
|
||||||
val proto = KonanIr.IrClass.newBuilder()
|
val proto = KonanIr.IrClass.newBuilder()
|
||||||
|
|
||||||
|
// TODO: As of now we get here only for anonymous local objects.
|
||||||
|
// There is still some work needed to support them.
|
||||||
|
// Until it is done, let's pretend all IrClasses are empty.
|
||||||
|
// So that we don't have to deal with their type tables.
|
||||||
|
/*
|
||||||
val declarations = clazz.declarations
|
val declarations = clazz.declarations
|
||||||
declarations.forEach {
|
declarations.forEach {
|
||||||
val descriptor = it.descriptor
|
val descriptor = it.descriptor
|
||||||
@@ -503,6 +565,7 @@ internal class IrSerializer(val context: Context,
|
|||||||
proto.addMember(serializeDeclaration(it))
|
proto.addMember(serializeDeclaration(it))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
return proto.build()
|
return proto.build()
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -521,20 +584,49 @@ internal class IrSerializer(val context: Context,
|
|||||||
context.log{"### serializing Declaration: ${ir2string(declaration)}"}
|
context.log{"### serializing Declaration: ${ir2string(declaration)}"}
|
||||||
|
|
||||||
val descriptor = declaration.descriptor
|
val descriptor = declaration.descriptor
|
||||||
|
|
||||||
|
if (descriptor != rootFunction &&
|
||||||
|
!(declaration is IrVariable)) {
|
||||||
|
localDeclarationSerializer.pushContext(descriptor)
|
||||||
|
}
|
||||||
|
|
||||||
var kotlinDescriptor = serializeDescriptor(descriptor)
|
var kotlinDescriptor = serializeDescriptor(descriptor)
|
||||||
|
var realDescriptor: KonanIr.DeclarationDescriptor? = null
|
||||||
|
if (descriptor != rootFunction) {
|
||||||
|
realDescriptor = localDeclarationSerializer.serializeLocalDeclaration(descriptor)
|
||||||
|
}
|
||||||
|
val declarator = KonanIr.IrDeclarator.newBuilder()
|
||||||
|
|
||||||
|
when (declaration) {
|
||||||
|
is IrFunction
|
||||||
|
-> declarator.setFunction(serializeIrFunction(declaration))
|
||||||
|
is IrVariable
|
||||||
|
-> declarator.setVariable(serializeIrVariable(declaration))
|
||||||
|
is IrClass
|
||||||
|
-> declarator.setIrClass(serializeIrClass(declaration))
|
||||||
|
is IrEnumEntry
|
||||||
|
-> declarator.setIrEnumEntry(serializeIrEnumEntry(declaration))
|
||||||
|
is IrProperty
|
||||||
|
-> declarator.setIrProperty(serializeIrProperty(declaration))
|
||||||
|
else
|
||||||
|
-> {
|
||||||
|
TODO("Declaration serialization not supported yet: $declaration")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(declaration is IrVariable)) {
|
||||||
|
localDeclarationSerializer.popContext(descriptor)
|
||||||
|
}
|
||||||
|
|
||||||
if (descriptor != rootFunction) {
|
if (descriptor != rootFunction) {
|
||||||
val realDescriptor = util.serializeLocalDeclaration(descriptor)
|
|
||||||
val localDeclaration = KonanIr.LocalDeclaration
|
val localDeclaration = KonanIr.LocalDeclaration
|
||||||
.newBuilder()
|
.newBuilder()
|
||||||
.setDescriptor(realDescriptor)
|
.setDescriptor(realDescriptor!!)
|
||||||
.build()
|
.build()
|
||||||
kotlinDescriptor = kotlinDescriptor
|
kotlinDescriptor = kotlinDescriptor
|
||||||
.toBuilder()
|
.toBuilder()
|
||||||
.setIrLocalDeclaration(localDeclaration)
|
.setIrLocalDeclaration(localDeclaration)
|
||||||
.build()
|
.build()
|
||||||
} else if (descriptor is ClassDescriptor) {
|
|
||||||
// TODO
|
|
||||||
context.log{"Can't serialize local class declarations in inline functions yet"}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
val coordinates = serializeCoordinates(declaration.startOffset, declaration.endOffset)
|
val coordinates = serializeCoordinates(declaration.startOffset, declaration.endOffset)
|
||||||
@@ -543,22 +635,6 @@ internal class IrSerializer(val context: Context,
|
|||||||
.setDescriptor(kotlinDescriptor)
|
.setDescriptor(kotlinDescriptor)
|
||||||
.setCoordinates(coordinates)
|
.setCoordinates(coordinates)
|
||||||
|
|
||||||
val declarator = KonanIr.IrDeclarator.newBuilder()
|
|
||||||
|
|
||||||
when (declaration) {
|
|
||||||
is IrFunction
|
|
||||||
-> declarator.setFunction(serializeFunction(declaration))
|
|
||||||
is IrVariable
|
|
||||||
-> declarator.setVariable(serializeVariable(declaration))
|
|
||||||
is IrClass
|
|
||||||
-> declarator.setIrClass(serializeIrClass(declaration))
|
|
||||||
is IrEnumEntry
|
|
||||||
-> declarator.setIrEnumEntry(serializeIrEnumEntry(declaration))
|
|
||||||
else
|
|
||||||
-> {
|
|
||||||
TODO("Declaration serialization not supported yet.")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
proto.setDeclarator(declarator)
|
proto.setDeclarator(declarator)
|
||||||
|
|
||||||
@@ -583,7 +659,7 @@ internal class IrDeserializer(val context: Context,
|
|||||||
val loopIndex = mutableMapOf<Int, IrLoop>()
|
val loopIndex = mutableMapOf<Int, IrLoop>()
|
||||||
|
|
||||||
val rootMember = rootFunction.deserializedPropertyIfAccessor
|
val rootMember = rootFunction.deserializedPropertyIfAccessor
|
||||||
val localDeserializer = LocalDeclarationDeserializer(rootMember, context.moduleDescriptor)
|
val localDeserializer = LocalDeclarationDeserializer(rootMember)
|
||||||
|
|
||||||
val descriptorDeserializer = IrDescriptorDeserializer(
|
val descriptorDeserializer = IrDescriptorDeserializer(
|
||||||
context, rootMember, localDeserializer)
|
context, rootMember, localDeserializer)
|
||||||
@@ -656,7 +732,7 @@ internal class IrDeserializer(val context: Context,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
context.log{"Deserialized statement: ${ir2string(element)}"}
|
context.log{"### Deserialized statement: ${ir2string(element)}"}
|
||||||
|
|
||||||
return element
|
return element
|
||||||
}
|
}
|
||||||
@@ -967,7 +1043,7 @@ internal class IrDeserializer(val context: Context,
|
|||||||
val operation = proto.getOperation()
|
val operation = proto.getOperation()
|
||||||
val expression = deserializeOperation(operation, start, end, type)
|
val expression = deserializeOperation(operation, start, end, type)
|
||||||
|
|
||||||
context.log{"Deserialized expression: ${ir2string(expression)}"}
|
context.log{"### Deserialized expression: ${ir2string(expression)}"}
|
||||||
return expression
|
return expression
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -986,7 +1062,7 @@ internal class IrDeserializer(val context: Context,
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fun deserializeIrFunction(proto: KonanIr.IrFunc, descriptor: FunctionDescriptor,
|
fun deserializeIrFunction(proto: KonanIr.IrFunction, descriptor: FunctionDescriptor,
|
||||||
start: Int, end: Int, origin: IrDeclarationOrigin): IrFunction {
|
start: Int, end: Int, origin: IrDeclarationOrigin): IrFunction {
|
||||||
|
|
||||||
val body = deserializeStatement(proto.getBody())
|
val body = deserializeStatement(proto.getBody())
|
||||||
@@ -1031,6 +1107,9 @@ internal class IrDeserializer(val context: Context,
|
|||||||
|
|
||||||
val descriptor = deserializeDescriptor(proto.descriptor)
|
val descriptor = deserializeDescriptor(proto.descriptor)
|
||||||
|
|
||||||
|
if (!(descriptor is VariableDescriptor) && descriptor != rootFunction)
|
||||||
|
localDeserializer.pushContext(descriptor)
|
||||||
|
|
||||||
val start = proto.getCoordinates().getStartOffset()
|
val start = proto.getCoordinates().getStartOffset()
|
||||||
val end = proto.getCoordinates().getEndOffset()
|
val end = proto.getCoordinates().getEndOffset()
|
||||||
val origin = DEFINED // TODO: retore the real origins
|
val origin = DEFINED // TODO: retore the real origins
|
||||||
@@ -1053,7 +1132,10 @@ internal class IrDeserializer(val context: Context,
|
|||||||
TODO("Declaration deserialization not implemented")
|
TODO("Declaration deserialization not implemented")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
context.log{"Deserialized declaration: ${ir2string(declaration)}"}
|
|
||||||
|
if (!(descriptor is VariableDescriptor) && descriptor != rootFunction)
|
||||||
|
localDeserializer.popContext(descriptor)
|
||||||
|
context.log{"### Deserialized declaration: ${ir2string(declaration)}"}
|
||||||
return declaration
|
return declaration
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1068,8 +1150,9 @@ internal class IrDeserializer(val context: Context,
|
|||||||
// I tried to copy over TypeDeserializaer, MemberDeserializer,
|
// I tried to copy over TypeDeserializaer, MemberDeserializer,
|
||||||
// and the rest of what's needed, but it didn't work out.
|
// and the rest of what's needed, but it didn't work out.
|
||||||
fun adaptDeserializedTypeParameters(declaration: IrDeclaration): IrDeclaration {
|
fun adaptDeserializedTypeParameters(declaration: IrDeclaration): IrDeclaration {
|
||||||
|
|
||||||
val rootFunctionTypeParameters =
|
val rootFunctionTypeParameters =
|
||||||
descriptorDeserializer.localDeserializer.childContext.typeDeserializer.ownTypeParameters
|
localDeserializer.typeDeserializer.ownTypeParameters
|
||||||
|
|
||||||
val realTypeParameters =
|
val realTypeParameters =
|
||||||
rootFunction.deserializedPropertyIfAccessor.typeParameters
|
rootFunction.deserializedPropertyIfAccessor.typeParameters
|
||||||
@@ -1094,13 +1177,16 @@ internal class IrDeserializer(val context: Context,
|
|||||||
is DeserializedSimpleFunctionDescriptor -> {
|
is DeserializedSimpleFunctionDescriptor -> {
|
||||||
rootFunction.proto.inlineIr
|
rootFunction.proto.inlineIr
|
||||||
}
|
}
|
||||||
|
is DeserializedClassConstructorDescriptor -> {
|
||||||
|
rootFunction.proto.constructorIr
|
||||||
|
}
|
||||||
is PropertyGetterDescriptor -> {
|
is PropertyGetterDescriptor -> {
|
||||||
(rootMember as DeserializedPropertyDescriptor).proto.getterIr
|
(rootMember as DeserializedPropertyDescriptor).proto.getterIr
|
||||||
}
|
}
|
||||||
is PropertySetterDescriptor -> {
|
is PropertySetterDescriptor -> {
|
||||||
(rootMember as DeserializedPropertyDescriptor).proto.setterIr
|
(rootMember as DeserializedPropertyDescriptor).proto.setterIr
|
||||||
}
|
}
|
||||||
else -> error("Unexpected descriptor: rootFunction")
|
else -> error("Unexpected descriptor: $rootFunction")
|
||||||
}
|
}
|
||||||
|
|
||||||
fun decodeDeclaration(): IrDeclaration {
|
fun decodeDeclaration(): IrDeclaration {
|
||||||
@@ -1110,7 +1196,7 @@ internal class IrDeserializer(val context: Context,
|
|||||||
val base64 = inlineProto.encodedIr
|
val base64 = inlineProto.encodedIr
|
||||||
val byteArray = base64Decode(base64)
|
val byteArray = base64Decode(base64)
|
||||||
val irProto = KonanIr.IrDeclaration.parseFrom(byteArray, KonanSerializerProtocol.extensionRegistry)
|
val irProto = KonanIr.IrDeclaration.parseFrom(byteArray, KonanSerializerProtocol.extensionRegistry)
|
||||||
val declaration = deserializeDeclaration(irProto)
|
val declaration = deserializeDeclaration(irProto)
|
||||||
|
|
||||||
val copyFunctionDeclaration = adaptDeserializedTypeParameters(declaration)
|
val copyFunctionDeclaration = adaptDeserializedTypeParameters(declaration)
|
||||||
|
|
||||||
|
|||||||
+1
-1
@@ -32,8 +32,8 @@ internal fun NameResolverImpl.getDescriptorByFqNameIndex(
|
|||||||
nameTable: ProtoBuf.QualifiedNameTable,
|
nameTable: ProtoBuf.QualifiedNameTable,
|
||||||
fqNameIndex: Int): DeclarationDescriptor {
|
fqNameIndex: Int): DeclarationDescriptor {
|
||||||
|
|
||||||
|
if (fqNameIndex == -1) return module.getPackage(FqName.ROOT)
|
||||||
val packageName = this.getPackageFqName(fqNameIndex)
|
val packageName = this.getPackageFqName(fqNameIndex)
|
||||||
if (packageName.isRoot) return module.getPackage(FqName.ROOT)
|
|
||||||
// TODO: Here we are using internals of NameresolverImpl.
|
// TODO: Here we are using internals of NameresolverImpl.
|
||||||
// Consider extending NameResolver.
|
// Consider extending NameResolver.
|
||||||
val proto = nameTable.getQualifiedName(fqNameIndex)
|
val proto = nameTable.getQualifiedName(fqNameIndex)
|
||||||
|
|||||||
Reference in New Issue
Block a user