diff --git a/core/descriptors/src/org/jetbrains/kotlin/builtins/builtInsPackageFragmentProvider.kt b/core/descriptors/src/org/jetbrains/kotlin/builtins/builtInsPackageFragmentProvider.kt index 8fa7821cc02..082b2e1dbd5 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/builtins/builtInsPackageFragmentProvider.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/builtins/builtInsPackageFragmentProvider.kt @@ -57,7 +57,7 @@ public fun createBuiltInPackageFragmentProvider( localClassResolver.setDeserializationComponents(components) for (packageFragment in packageFragments) { - packageFragment.setDeserializationComponents(components) + packageFragment.components = components } return provider diff --git a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/DeserializedPackageFragment.kt b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/DeserializedPackageFragment.kt index 4322b188b2a..f300c494582 100644 --- a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/DeserializedPackageFragment.kt +++ b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/DeserializedPackageFragment.kt @@ -22,12 +22,13 @@ import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.serialization.ProtoBuf import org.jetbrains.kotlin.serialization.SerializedResourcePaths +import org.jetbrains.kotlin.serialization.builtins.BuiltInsProtoBuf import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedPackageMemberScope import org.jetbrains.kotlin.storage.StorageManager import org.jetbrains.kotlin.storage.getValue +import java.io.DataInputStream import java.io.InputStream import javax.inject.Inject -import kotlin.properties.Delegates public abstract class DeserializedPackageFragment( fqName: FqName, @@ -37,21 +38,51 @@ public abstract class DeserializedPackageFragment( private val loadResource: (path: String) -> InputStream? ) : PackageFragmentDescriptorImpl(module, fqName) { - val nameResolver = NameResolverImpl.read(loadResourceSure(serializedResourcePaths.getStringTableFilePath(fqName))) + val builtinsMessage = serializedResourcePaths.getBuiltInsFilePath(fqName)?.let(loadResource)?.let { stream -> + val dataInput = DataInputStream(stream) + val version = (1..dataInput.readInt()).map { dataInput.readInt() } - protected var components: DeserializationComponents by Delegates.notNull() + // TODO: check version correctly + if (!(version.size == 3 && version.let { + val (major, minor, patch) = it + major == 1 && minor == 0 && patch == 0 + })) { + throw UnsupportedOperationException( + "Kotlin built-in definition format version is not supported: expected 1.0.0, actual ${version.joinToString(".")}" + ) + } - // component dependency cycle - @Inject - public fun setDeserializationComponents(components: DeserializationComponents) { - this.components = components + BuiltInsProtoBuf.BuiltIns.parseFrom(stream, serializedResourcePaths.extensionRegistry) } + val nameResolver = + builtinsMessage?.let { NameResolverImpl(it.strings, it.qualifiedNames) } ?: + NameResolverImpl.read(loadResourceSure(serializedResourcePaths.getStringTableFilePath(fqName))) + + val classIdToProto = builtinsMessage?.let { builtins -> + builtins.classList.toMapBy { klass -> + nameResolver.getClassId(klass.fqName) + } + } + + // component dependency cycle + @set:Inject + lateinit var components: DeserializationComponents + internal val deserializedMemberScope by storageManager.createLazyValue { - val packageStream = loadResourceSure(serializedResourcePaths.getPackageFilePath(fqName)) - val packageProto = ProtoBuf.Package.parseFrom(packageStream, serializedResourcePaths.extensionRegistry) - DeserializedPackageMemberScope(this, packageProto, nameResolver, packagePartSource = null, components = components, - classNames = { loadClassNames(packageProto) }) + builtinsMessage?.let { builtins -> + DeserializedPackageMemberScope( + this, builtins.`package`, nameResolver, packagePartSource = null, components = components, + classNames = { classIdToProto!!.keys.filter { classId -> !classId.isNestedClass }.map { it.shortClassName } } + ) + } ?: run { + val packageStream = loadResourceSure(serializedResourcePaths.getPackageFilePath(fqName)) + val packageProto = ProtoBuf.Package.parseFrom(packageStream, serializedResourcePaths.extensionRegistry) + DeserializedPackageMemberScope( + this, packageProto, nameResolver, packagePartSource = null, components = components, + classNames = { loadClassNames(packageProto) } + ) + } } override fun getMemberScope() = deserializedMemberScope diff --git a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/NameResolverImpl.kt b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/NameResolverImpl.kt index c625a1569c2..ad72e2a971d 100644 --- a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/NameResolverImpl.kt +++ b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/NameResolverImpl.kt @@ -24,7 +24,7 @@ import org.jetbrains.kotlin.serialization.ProtoBuf.QualifiedNameTable.QualifiedN import java.io.InputStream import java.util.* -class NameResolverImpl private constructor( +class NameResolverImpl( private val strings: ProtoBuf.StringTable, private val qualifiedNames: ProtoBuf.QualifiedNameTable ) : NameResolver { diff --git a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/ResourceLoadingClassDataFinder.kt b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/ResourceLoadingClassDataFinder.kt index b8e09f042b0..5a89620e58c 100644 --- a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/ResourceLoadingClassDataFinder.kt +++ b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/ResourceLoadingClassDataFinder.kt @@ -24,21 +24,20 @@ import org.jetbrains.kotlin.serialization.ProtoBuf import org.jetbrains.kotlin.serialization.SerializedResourcePaths import java.io.InputStream -public open class ResourceLoadingClassDataFinder( +class ResourceLoadingClassDataFinder( private val packageFragmentProvider: PackageFragmentProvider, private val serializedResourcePaths: SerializedResourcePaths, private val loadResource: (path: String) -> InputStream? ) : ClassDataFinder { override fun findClassData(classId: ClassId): ClassDataWithSource? { - val packageFragment = packageFragmentProvider.getPackageFragments(classId.getPackageFqName()).singleOrNull() + val packageFragment = packageFragmentProvider.getPackageFragments(classId.packageFqName).singleOrNull() as? DeserializedPackageFragment ?: return null - val stream = loadResource(serializedResourcePaths.getClassMetadataPath(classId)) ?: return null + val classProto = packageFragment.classIdToProto?.get(classId) ?: run { + val stream = loadResource(serializedResourcePaths.getClassMetadataPath(classId)) ?: return null + ProtoBuf.Class.parseFrom(stream, serializedResourcePaths.extensionRegistry) + } - val classData = ClassData( - packageFragment.nameResolver, - ProtoBuf.Class.parseFrom(stream, serializedResourcePaths.extensionRegistry) - ) - return ClassDataWithSource(classData) + return ClassDataWithSource(ClassData(packageFragment.nameResolver, classProto)) } } diff --git a/js/js.serializer/src/org/jetbrains/kotlin/serialization/js/kotlinJavascriptPackageFragmentProvider.kt b/js/js.serializer/src/org/jetbrains/kotlin/serialization/js/kotlinJavascriptPackageFragmentProvider.kt index 9aac688673f..1b769096e13 100644 --- a/js/js.serializer/src/org/jetbrains/kotlin/serialization/js/kotlinJavascriptPackageFragmentProvider.kt +++ b/js/js.serializer/src/org/jetbrains/kotlin/serialization/js/kotlinJavascriptPackageFragmentProvider.kt @@ -54,7 +54,7 @@ public fun createKotlinJavascriptPackageFragmentProvider( localClassResolver.setDeserializationComponents(components) for (packageFragment in packageFragments) { - packageFragment.setDeserializationComponents(components) + packageFragment.components = components } return provider