From 5b4eb472355620c0d1a27a970538f870d81f118d Mon Sep 17 00:00:00 2001 From: Alexander Gorshenev Date: Mon, 24 Apr 2017 14:51:38 +0300 Subject: [PATCH] Simplified IR awareness of KonanDescriptorSerializer. --- .../KonanDescriptorSerializer.kt | 36 ++++---- .../serialization/KonanSerializerExtension.kt | 85 +++++++------------ .../konan/serialization/ProtobufUtil.kt | 10 +++ .../kotlin/backend/konan/util/util.kt | 2 +- 4 files changed, 63 insertions(+), 70 deletions(-) diff --git a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanDescriptorSerializer.kt b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanDescriptorSerializer.kt index bceeac2786b..f3d1a72ad06 100644 --- a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanDescriptorSerializer.kt +++ b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanDescriptorSerializer.kt @@ -16,6 +16,9 @@ package org.jetbrains.kotlin.serialization +import org.jetbrains.kotlin.backend.konan.descriptors.needsInlining +import org.jetbrains.kotlin.backend.konan.serialization.IrAwareExtension +import org.jetbrains.kotlin.backend.konan.util.onlyIf import org.jetbrains.kotlin.builtins.KotlinBuiltIns import org.jetbrains.kotlin.builtins.isSuspendFunctionType import org.jetbrains.kotlin.builtins.transformSuspendFunctionToRuntimeFunctionType @@ -36,13 +39,6 @@ import org.jetbrains.kotlin.utils.Interner import java.io.ByteArrayOutputStream import java.util.* -import org.jetbrains.kotlin.backend.konan.serialization.KonanSerializerExtension - -// This is an almost exact copy of DescriptorSerializer -// from the big Kotlin. -// The only difference for now is typeId is public now. -// Consider bringing the new functionaity upstream. - class KonanDescriptorSerializer private constructor( private val containingDeclaration: DeclarationDescriptor?, private val typeParameters: Interner, @@ -229,12 +225,18 @@ class KonanDescriptorSerializer private constructor( builder.sinceKotlinInfo = writeSinceKotlinInfo(LanguageFeature.Coroutines) } - if (extension is KonanSerializerExtension) { - extension.serializePropertyWithIR(descriptor, builder, {it -> typeId(it)}) - } else { - extension.serializeProperty(descriptor, builder) - } + extension.serializeProperty(descriptor, builder) + if (extension is IrAwareExtension) { + descriptor.getter?.onlyIf({needsInlining}) { + extension.addGetterIR(builder, + extension.serializeInlineBody(it, {it -> typeId(it)})) + } + descriptor.setter?.onlyIf({needsInlining}) { + extension.addSetterIR(builder, + extension.serializeInlineBody(it, {it -> typeId(it)})) + } + } return builder } @@ -291,10 +293,12 @@ class KonanDescriptorSerializer private constructor( builder.sinceKotlinInfo = writeSinceKotlinInfo(LanguageFeature.Coroutines) } - if (extension is KonanSerializerExtension) { - extension.serializeFunctionWithIR(descriptor, builder, {it -> typeId(it)}) - } else { - extension.serializeFunction(descriptor, builder) + extension.serializeFunction(descriptor, builder) + + if (extension is IrAwareExtension + && descriptor.needsInlining) { + extension.addFunctionIR(builder, + extension.serializeInlineBody(descriptor, {it -> typeId(it)})) } return builder diff --git a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanSerializerExtension.kt b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanSerializerExtension.kt index 8a941f078d1..626488435ff 100644 --- a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanSerializerExtension.kt +++ b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/KonanSerializerExtension.kt @@ -18,33 +18,15 @@ package org.jetbrains.kotlin.backend.konan.serialization import org.jetbrains.kotlin.backend.konan.Context import org.jetbrains.kotlin.backend.konan.descriptors.getKonanInternalClass -import org.jetbrains.kotlin.backend.konan.descriptors.needsInlining -import org.jetbrains.kotlin.backend.konan.util.only -import org.jetbrains.kotlin.descriptors.PropertyDescriptor -import org.jetbrains.kotlin.descriptors.SourceElement +import org.jetbrains.kotlin.descriptors.* import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptorImpl import org.jetbrains.kotlin.protobuf.ExtensionRegistryLite import org.jetbrains.kotlin.serialization.* -import org.jetbrains.kotlin.serialization.Flags -import org.jetbrains.kotlin.serialization.KonanLinkData -import org.jetbrains.kotlin.serialization.KonanLinkData.InlineIrBody -import org.jetbrains.kotlin.descriptors.* -import org.jetbrains.kotlin.descriptors.annotations.* -import org.jetbrains.kotlin.backend.konan.descriptors.* -import org.jetbrains.kotlin.name.FqName -import org.jetbrains.kotlin.psi.KtFile -import org.jetbrains.kotlin.resolve.DescriptorUtils -import org.jetbrains.kotlin.resolve.source.PsiSourceFile -import org.jetbrains.kotlin.serialization.KotlinSerializerExtensionBase -import org.jetbrains.kotlin.serialization.ProtoBuf -import org.jetbrains.kotlin.serialization.StringTableImpl -import org.jetbrains.kotlin.serialization.SerializerExtensionProtocol -import org.jetbrains.kotlin.types.FlexibleType import org.jetbrains.kotlin.types.KotlinType internal class KonanSerializerExtension(val context: Context, val util: KonanSerializationUtil) : - KotlinSerializerExtensionBase(KonanSerializerProtocol) { + KotlinSerializerExtensionBase(KonanSerializerProtocol), IrAwareExtension { val inlineDescriptorTable = DescriptorTable(context.irBuiltIns) val originalVariables = mutableMapOf() @@ -99,31 +81,12 @@ internal class KonanSerializerExtension(val context: Context, val util: KonanSer super.serializeClass(descriptor, proto) } - private fun serializeInlineBody(descriptor: FunctionDescriptor, typeSerializer: ((KotlinType)->Int)): KonanLinkData.InlineIrBody { - - val encodedIR = IrSerializer( - context, inlineDescriptorTable, stringTable, util, - typeSerializer, descriptor).serializeInlineBody() - - return KonanLinkData.InlineIrBody - .newBuilder() - .setEncodedIr(encodedIR) - .build() - } - - override fun serializeFunction(descriptor: FunctionDescriptor, proto: ProtoBuf.Function.Builder) = serializeFunctionWithIR(descriptor, proto, null) - - fun serializeFunctionWithIR(descriptor: FunctionDescriptor, proto: ProtoBuf.Function.Builder, typeSerializer: ((KotlinType)->Int)?) { + override fun serializeFunction(descriptor: FunctionDescriptor, proto: ProtoBuf.Function.Builder) { proto.setFunctionIndex( inlineDescriptorTable.indexByValue(descriptor)) val parentIndex = descriptor.parentFqNameIndex() proto.setExtension(KonanLinkData.functionParent, parentIndex) - if (descriptor.needsInlining) { - proto.setInlineIr( - serializeInlineBody(descriptor, typeSerializer!!)) - } - super.serializeFunction(descriptor, proto) } @@ -133,9 +96,7 @@ internal class KonanSerializerExtension(val context: Context, val util: KonanSer private val backingFieldAnnotation = AnnotationDescriptorImpl( backingFieldClass, emptyMap(), SourceElement.NO_SOURCE) - override fun serializeProperty(descriptor: PropertyDescriptor, proto: ProtoBuf.Property.Builder) = serializePropertyWithIR(descriptor, proto, null) - - fun serializePropertyWithIR(descriptor: PropertyDescriptor, proto: ProtoBuf.Property.Builder, typeSerializer: ((KotlinType)->Int)?) { + override fun serializeProperty(descriptor: PropertyDescriptor, proto: ProtoBuf.Property.Builder) { val parentIndex = descriptor.parentFqNameIndex() proto.setExtension(KonanLinkData.propertyParent, parentIndex) val variable = originalVariables[descriptor] @@ -149,16 +110,6 @@ internal class KonanSerializerExtension(val context: Context, val util: KonanSer inlineDescriptorTable.indexByValue(descriptor)) } - descriptor.getter?.only({needsInlining}) { - proto.setGetterIr( - serializeInlineBody(it, typeSerializer!!)) - } - - descriptor.setter?.only({needsInlining}) { - proto.setSetterIr( - serializeInlineBody(it, typeSerializer!!)) - } - super.serializeProperty(descriptor, proto) if (context.ir.propertiesWithBackingFields.contains(descriptor)) { @@ -168,6 +119,22 @@ internal class KonanSerializerExtension(val context: Context, val util: KonanSer proto.flags = proto.flags or Flags.HAS_ANNOTATIONS.toFlags(true) } } + + override fun addFunctionIR(proto: ProtoBuf.Function.Builder, serializedIR: String) + = proto.setInlineIr(inlineBody(serializedIR)) + + override fun addGetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String) + = proto.setGetterIr(inlineBody(serializedIR)) + + override fun addSetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String) + = proto.setSetterIr(inlineBody(serializedIR)) + + override fun serializeInlineBody(descriptor: FunctionDescriptor, typeSerializer: ((KotlinType)->Int)): String { + + return IrSerializer( + context, inlineDescriptorTable, stringTable, util, + typeSerializer, descriptor).serializeInlineBody() + } } object KonanSerializerProtocol : SerializerExtensionProtocol( @@ -185,3 +152,15 @@ object KonanSerializerProtocol : SerializerExtensionProtocol( KonanLinkData.typeAnnotation, KonanLinkData.typeParameterAnnotation ) + +internal interface IrAwareExtension { + + fun serializeInlineBody(descriptor: FunctionDescriptor, typeSerializer: ((KotlinType)->Int)): String + + fun addFunctionIR(proto: ProtoBuf.Function.Builder, serializedIR: String): ProtoBuf.Function.Builder + + fun addSetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String): ProtoBuf.Property.Builder + + fun addGetterIR(proto: ProtoBuf.Property.Builder, serializedIR: String): ProtoBuf.Property.Builder +} + diff --git a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/ProtobufUtil.kt b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/ProtobufUtil.kt index e23063e4471..d769c99f7d4 100644 --- a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/ProtobufUtil.kt +++ b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/serialization/ProtobufUtil.kt @@ -76,6 +76,16 @@ val ProtoBuf.Function.inlineIr: InlineIrBody fun ProtoBuf.Function.Builder.setInlineIr(body: InlineIrBody): ProtoBuf.Function.Builder = this.setExtension(inlineIrBody, body) +// ----------------------------------------------------------- + +fun inlineBody(encodedIR: String) + = KonanLinkData.InlineIrBody + .newBuilder() + .setEncodedIr(encodedIR) + .build() + +// ----------------------------------------------------------- + internal fun printType(proto: ProtoBuf.Type) { println("debug text: " + proto.getExtension(KonanLinkData.typeText)) } diff --git a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/util/util.kt b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/util/util.kt index 743c035b425..b866b254af0 100644 --- a/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/util/util.kt +++ b/backend.native/compiler/ir/backend.native/src/org/jetbrains/kotlin/backend/konan/util/util.kt @@ -46,7 +46,7 @@ fun Collection.atMostOne(): T? { inline fun Iterable.atMostOne(predicate: (T) -> Boolean): T? = this.filter(predicate).atMostOne() -fun T.only(condition: T.()->Boolean, then: (T)->Unit): T { +fun T.onlyIf(condition: T.()->Boolean, then: (T)->Unit): T { if (this.condition()) then(this) return this }