Store source file info in klib. (#2243)
This commit is contained in:
+30
-2
@@ -7,12 +7,21 @@ package org.jetbrains.kotlin.backend.konan.descriptors
|
||||
|
||||
import org.jetbrains.kotlin.backend.konan.binaryTypeIsReference
|
||||
import org.jetbrains.kotlin.backend.konan.irasdescriptors.*
|
||||
import org.jetbrains.kotlin.backend.konan.irasdescriptors.ClassDescriptor
|
||||
import org.jetbrains.kotlin.backend.konan.irasdescriptors.ConstructorDescriptor
|
||||
import org.jetbrains.kotlin.backend.konan.irasdescriptors.DeclarationDescriptor
|
||||
import org.jetbrains.kotlin.backend.konan.irasdescriptors.FunctionDescriptor
|
||||
import org.jetbrains.kotlin.backend.konan.irasdescriptors.PackageFragmentDescriptor
|
||||
import org.jetbrains.kotlin.backend.konan.irasdescriptors.SimpleFunctionDescriptor
|
||||
import org.jetbrains.kotlin.backend.konan.isInlined
|
||||
import org.jetbrains.kotlin.descriptors.ClassKind
|
||||
import org.jetbrains.kotlin.descriptors.Modality
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.ir.declarations.IrSimpleFunction
|
||||
import org.jetbrains.kotlin.ir.types.isUnit
|
||||
import org.jetbrains.kotlin.metadata.konan.KonanProtoBuf
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedPropertyDescriptor
|
||||
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedSimpleFunctionDescriptor
|
||||
import org.jetbrains.kotlin.serialization.konan.KonanPackageFragment
|
||||
import org.jetbrains.kotlin.types.SimpleType
|
||||
|
||||
/**
|
||||
@@ -231,3 +240,22 @@ tailrec internal fun DeclarationDescriptor.findPackage(): PackageFragmentDescrip
|
||||
|
||||
fun FunctionDescriptor.isComparisonDescriptor(map: Map<SimpleType, IrSimpleFunction>): Boolean =
|
||||
this in map.values
|
||||
|
||||
private fun sourceByIndex(descriptor: CallableMemberDescriptor, index: Int): SourceFile {
|
||||
val fragment = descriptor.findPackage() as KonanPackageFragment
|
||||
return fragment.sourceFileMap.sourceFile(index)
|
||||
}
|
||||
|
||||
fun CallableMemberDescriptor.findSourceFile(): SourceFile {
|
||||
val source = this.source.containingFile
|
||||
if (source != SourceFile.NO_SOURCE_FILE)
|
||||
return source
|
||||
return when {
|
||||
this is DeserializedSimpleFunctionDescriptor && proto.hasExtension(KonanProtoBuf.functionFile) -> sourceByIndex(
|
||||
this, proto.getExtension(KonanProtoBuf.functionFile))
|
||||
this is DeserializedPropertyDescriptor && proto.hasExtension(KonanProtoBuf.propertyFile) ->
|
||||
sourceByIndex(
|
||||
this, proto.getExtension(KonanProtoBuf.propertyFile))
|
||||
else -> TODO()
|
||||
}
|
||||
}
|
||||
|
||||
+1
-1
@@ -26,7 +26,7 @@ interface KonanLibraryWriter {
|
||||
class LinkData(
|
||||
val module: ByteArray,
|
||||
val fragments: List<List<ByteArray>>,
|
||||
val fragmentNames: List<String>
|
||||
val fragmentNames: List<String>
|
||||
)
|
||||
|
||||
interface MetadataWriter {
|
||||
|
||||
+1
-1
@@ -193,7 +193,7 @@ abstract class ObjCExportHeaderGenerator(
|
||||
if (classDescriptor != null) {
|
||||
extensions.getOrPut(classDescriptor, { mutableListOf() }) += it
|
||||
} else {
|
||||
topLevel.getOrPut(it.source.containingFile, { mutableListOf() }) += it
|
||||
topLevel.getOrPut(it.findSourceFile(), { mutableListOf() }) += it
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+12
-4
@@ -13,14 +13,13 @@ import org.jetbrains.kotlin.metadata.ProtoBuf
|
||||
import org.jetbrains.kotlin.metadata.deserialization.BinaryVersion
|
||||
import org.jetbrains.kotlin.metadata.konan.KonanProtoBuf
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
||||
import org.jetbrains.kotlin.resolve.checkers.ExpectedActualDeclarationChecker
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.module
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter.Companion.CALLABLES
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter.Companion.CLASSIFIERS
|
||||
import org.jetbrains.kotlin.resolve.scopes.getDescriptorsFiltered
|
||||
import org.jetbrains.kotlin.serialization.KonanDescriptorSerializer
|
||||
import org.jetbrains.kotlin.serialization.konan.SourceFileMap
|
||||
|
||||
/*
|
||||
* This is Konan specific part of public descriptor
|
||||
@@ -37,6 +36,8 @@ internal class KonanSerializationUtil(val context: Context, private val metadata
|
||||
|
||||
lateinit var serializerContext: SerializerContext
|
||||
|
||||
val sourceFileMap = SourceFileMap()
|
||||
|
||||
data class SerializerContext(
|
||||
val serializerExtension: KonanSerializerExtension,
|
||||
val topSerializer: KonanDescriptorSerializer,
|
||||
@@ -44,7 +45,7 @@ internal class KonanSerializationUtil(val context: Context, private val metadata
|
||||
)
|
||||
|
||||
private fun createNewContext(): SerializerContext {
|
||||
val extension = KonanSerializerExtension(context, metadataVersion)
|
||||
val extension = KonanSerializerExtension(context, metadataVersion, sourceFileMap)
|
||||
return SerializerContext(
|
||||
extension,
|
||||
KonanDescriptorSerializer.createTopLevel(context, extension)
|
||||
@@ -213,7 +214,8 @@ internal class KonanSerializationUtil(val context: Context, private val metadata
|
||||
val fragmentNames = mutableListOf<String>()
|
||||
|
||||
getPackagesFqNames(moduleDescriptor).forEach iteration@{ packageFqName ->
|
||||
val packageProtos = serializePackage(packageFqName, moduleDescriptor)
|
||||
val packageProtos =
|
||||
serializePackage(packageFqName, moduleDescriptor)
|
||||
if (packageProtos.isEmpty()) return@iteration
|
||||
|
||||
val packageFqNameStr = packageFqName.asString()
|
||||
@@ -223,7 +225,13 @@ internal class KonanSerializationUtil(val context: Context, private val metadata
|
||||
}
|
||||
fragments.add(packageProtos.map { it.toByteArray() })
|
||||
fragmentNames.add(packageFqNameStr)
|
||||
|
||||
}
|
||||
|
||||
sourceFileMap.filesAndClear().map { it.name ?: "" }.forEach {
|
||||
libraryProto.addFile(it)
|
||||
}
|
||||
|
||||
val libraryAsByteArray = libraryProto.build().toByteArray()
|
||||
return LinkData(libraryAsByteArray, fragments, fragmentNames)
|
||||
}
|
||||
|
||||
+6
-4
@@ -16,9 +16,11 @@ import org.jetbrains.kotlin.metadata.serialization.MutableVersionRequirementTabl
|
||||
import org.jetbrains.kotlin.serialization.KonanDescriptorSerializer
|
||||
import org.jetbrains.kotlin.serialization.KotlinSerializerExtensionBase
|
||||
import org.jetbrains.kotlin.serialization.konan.KonanSerializerProtocol
|
||||
import org.jetbrains.kotlin.serialization.konan.SourceFileMap
|
||||
import org.jetbrains.kotlin.types.KotlinType
|
||||
|
||||
internal class KonanSerializerExtension(val context: Context, override val metadataVersion: BinaryVersion) :
|
||||
internal class KonanSerializerExtension(val context: Context, override val metadataVersion: BinaryVersion,
|
||||
val sourceFileMap: SourceFileMap) :
|
||||
KotlinSerializerExtensionBase(KonanSerializerProtocol), IrAwareExtension {
|
||||
|
||||
val inlineDescriptorTable = DescriptorTable(context.irBuiltIns)
|
||||
@@ -28,7 +30,7 @@ internal class KonanSerializerExtension(val context: Context, override val metad
|
||||
override fun serializeType(type: KotlinType, proto: ProtoBuf.Type.Builder) {
|
||||
// TODO: For debugging purpose we store the textual
|
||||
// representation of serialized types.
|
||||
// To be removed for release 1.0.
|
||||
// To be removed.
|
||||
proto.setExtension(KonanProtoBuf.typeText, type.toString())
|
||||
|
||||
super.serializeType(type, proto)
|
||||
@@ -60,7 +62,7 @@ internal class KonanSerializerExtension(val context: Context, override val metad
|
||||
}
|
||||
|
||||
override fun serializeFunction(descriptor: FunctionDescriptor, proto: ProtoBuf.Function.Builder) {
|
||||
|
||||
proto.setExtension(KonanProtoBuf.functionFile, sourceFileMap.assign(descriptor.source.containingFile))
|
||||
super.serializeFunction(descriptor, proto)
|
||||
}
|
||||
|
||||
@@ -69,7 +71,7 @@ internal class KonanSerializerExtension(val context: Context, override val metad
|
||||
if (variable != null) {
|
||||
proto.setExtension(KonanProtoBuf.usedAsVariable, true)
|
||||
}
|
||||
|
||||
proto.setExtension(KonanProtoBuf.propertyFile, sourceFileMap.assign(descriptor.source.containingFile))
|
||||
proto.setExtension(KonanProtoBuf.hasBackingField,
|
||||
context.ir.propertiesWithBackingFields.contains(descriptor))
|
||||
|
||||
|
||||
@@ -32,6 +32,7 @@ extend Constructor {
|
||||
extend Function {
|
||||
repeated Annotation function_annotation = 170;
|
||||
optional InlineIrBody inline_ir_body = 171;
|
||||
optional int32 function_file = 172;
|
||||
}
|
||||
|
||||
extend Property {
|
||||
@@ -41,6 +42,7 @@ extend Property {
|
||||
optional Annotation.Argument.Value compile_time_value = 173;
|
||||
optional InlineIrBody inline_getter_ir_body = 174;
|
||||
optional InlineIrBody inline_setter_ir_body = 175;
|
||||
optional int32 property_file = 176;
|
||||
}
|
||||
|
||||
extend EnumEntry {
|
||||
@@ -95,5 +97,6 @@ message LinkDataLibrary {
|
||||
required string module_name = 1;
|
||||
repeated string package_fragment_name = 2;
|
||||
repeated string empty_package = 3;
|
||||
repeated string file = 4;
|
||||
}
|
||||
|
||||
|
||||
+2
-3
@@ -2,11 +2,10 @@ package org.jetbrains.kotlin.konan.library.resolver.impl
|
||||
|
||||
import org.jetbrains.kotlin.konan.library.KonanLibrary
|
||||
import org.jetbrains.kotlin.konan.library.resolver.KonanResolvedLibrary
|
||||
import org.jetbrains.kotlin.serialization.konan.SourceFileMap
|
||||
import org.jetbrains.kotlin.serialization.konan.parseModuleHeader
|
||||
|
||||
internal class KonanResolvedLibraryImpl(
|
||||
override val library: KonanLibrary
|
||||
): KonanResolvedLibrary {
|
||||
internal class KonanResolvedLibraryImpl(override val library: KonanLibrary): KonanResolvedLibrary {
|
||||
|
||||
private val _resolvedDependencies = mutableListOf<KonanResolvedLibrary>()
|
||||
private val _emptyPackages by lazy { parseModuleHeader(library.moduleHeaderData).emptyPackageList }
|
||||
|
||||
+22
@@ -1,8 +1,15 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license
|
||||
* that can be found in the LICENSE file.
|
||||
*/
|
||||
package org.jetbrains.kotlin.serialization.konan
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.SourceFile
|
||||
import org.jetbrains.kotlin.konan.library.KonanLibrary
|
||||
import org.jetbrains.kotlin.konan.library.resolver.KonanResolvedLibrary
|
||||
import org.jetbrains.kotlin.konan.library.resolver.PackageAccessedHandler
|
||||
import org.jetbrains.kotlin.konan.library.resolver.impl.KonanResolvedLibraryImpl
|
||||
import org.jetbrains.kotlin.metadata.deserialization.NameResolverImpl
|
||||
import org.jetbrains.kotlin.metadata.konan.KonanProtoBuf
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
@@ -14,6 +21,17 @@ import org.jetbrains.kotlin.serialization.deserialization.getClassId
|
||||
import org.jetbrains.kotlin.serialization.deserialization.getName
|
||||
import org.jetbrains.kotlin.storage.StorageManager
|
||||
|
||||
|
||||
private val KonanLibrary.fileSources: SourceFileMap get() {
|
||||
val result = SourceFileMap()
|
||||
val proto = parseModuleHeader(moduleHeaderData)
|
||||
proto.fileList.forEachIndexed { index, it ->
|
||||
result.provide(it, index, this)
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
|
||||
class KonanPackageFragment(
|
||||
fqName: FqName,
|
||||
private val library: KonanLibrary,
|
||||
@@ -23,6 +41,10 @@ class KonanPackageFragment(
|
||||
partName: String
|
||||
) : DeserializedPackageFragment(fqName, storageManager, module) {
|
||||
|
||||
val sourceFileMap: SourceFileMap by lazy {
|
||||
library.fileSources
|
||||
}
|
||||
|
||||
lateinit var components: DeserializationComponents
|
||||
|
||||
override fun initialize(components: DeserializationComponents) {
|
||||
|
||||
+55
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license
|
||||
* that can be found in the LICENSE file.
|
||||
*/
|
||||
package org.jetbrains.kotlin.serialization.konan
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.SourceFile
|
||||
import org.jetbrains.kotlin.konan.library.KonanLibrary
|
||||
import org.jetbrains.kotlin.konan.library.resolver.KonanResolvedLibrary
|
||||
import org.jetbrains.kotlin.serialization.deserialization.DeserializedPackageFragment
|
||||
|
||||
private class DeserializedSourceFile(
|
||||
val name_: String, val index: Int, val library: KonanLibrary) : SourceFile {
|
||||
override fun getName(): String? = name_
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
return other is DeserializedSourceFile && library == other.library && index == other.index
|
||||
}
|
||||
|
||||
override fun hashCode(): Int {
|
||||
return library.hashCode() xor index
|
||||
}
|
||||
}
|
||||
|
||||
class SourceFileMap {
|
||||
private val sourceToIndex = mutableMapOf<SourceFile, Int>()
|
||||
private val indexToSource = mutableMapOf<Int, SourceFile>()
|
||||
|
||||
fun assign(file: SourceFile): Int {
|
||||
return sourceToIndex.getOrPut(file) {
|
||||
sourceToIndex.size
|
||||
}
|
||||
}
|
||||
|
||||
fun provide(fileName: String, index: Int, library: KonanLibrary) {
|
||||
assert(indexToSource[index] == null)
|
||||
indexToSource[index] = DeserializedSourceFile(fileName, index, library)
|
||||
}
|
||||
|
||||
fun sourceFile(index: Int): SourceFile =
|
||||
indexToSource[index] ?: throw Error("Unknown file for $index")
|
||||
|
||||
fun filesAndClear() =
|
||||
sourceToIndex.keys.sortedBy {
|
||||
sourceToIndex[it]
|
||||
}.also{
|
||||
clear()
|
||||
}
|
||||
|
||||
|
||||
fun clear() {
|
||||
sourceToIndex.clear()
|
||||
indexToSource.clear()
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user