Combine cls stub builders for built-ins and JS
This commit is contained in:
+4
-2
@@ -24,6 +24,7 @@ import org.jetbrains.kotlin.builtins.BuiltInsBinaryVersion
|
|||||||
import org.jetbrains.kotlin.idea.decompiler.common.FileWithMetadata
|
import org.jetbrains.kotlin.idea.decompiler.common.FileWithMetadata
|
||||||
import org.jetbrains.kotlin.idea.decompiler.common.KotlinMetadataDecompiler
|
import org.jetbrains.kotlin.idea.decompiler.common.KotlinMetadataDecompiler
|
||||||
import org.jetbrains.kotlin.name.ClassId
|
import org.jetbrains.kotlin.name.ClassId
|
||||||
|
import org.jetbrains.kotlin.psi.stubs.KotlinStubVersions
|
||||||
import org.jetbrains.kotlin.resolve.TargetPlatform
|
import org.jetbrains.kotlin.resolve.TargetPlatform
|
||||||
import org.jetbrains.kotlin.serialization.ProtoBuf
|
import org.jetbrains.kotlin.serialization.ProtoBuf
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.FlexibleTypeDeserializer
|
import org.jetbrains.kotlin.serialization.deserialization.FlexibleTypeDeserializer
|
||||||
@@ -31,8 +32,9 @@ import org.jetbrains.kotlin.serialization.deserialization.MetadataPackageFragmen
|
|||||||
import java.io.ByteArrayInputStream
|
import java.io.ByteArrayInputStream
|
||||||
|
|
||||||
class KotlinBuiltInDecompiler : KotlinMetadataDecompiler<BuiltInsBinaryVersion>(
|
class KotlinBuiltInDecompiler : KotlinMetadataDecompiler<BuiltInsBinaryVersion>(
|
||||||
KotlinBuiltInFileType, KotlinBuiltInStubBuilder(), TargetPlatform.Default, BuiltInSerializerProtocol,
|
KotlinBuiltInFileType, TargetPlatform.Default, BuiltInSerializerProtocol,
|
||||||
FlexibleTypeDeserializer.ThrowException, BuiltInsBinaryVersion.INSTANCE, BuiltInsBinaryVersion.INVALID_VERSION
|
FlexibleTypeDeserializer.ThrowException, BuiltInsBinaryVersion.INSTANCE, BuiltInsBinaryVersion.INVALID_VERSION,
|
||||||
|
KotlinStubVersions.BUILTIN_STUB_VERSION
|
||||||
) {
|
) {
|
||||||
override fun readFile(bytes: ByteArray, file: VirtualFile): FileWithMetadata? {
|
override fun readFile(bytes: ByteArray, file: VirtualFile): FileWithMetadata? {
|
||||||
return BuiltInDefinitionFile.read(bytes, file)
|
return BuiltInDefinitionFile.read(bytes, file)
|
||||||
|
|||||||
+4
-3
@@ -21,7 +21,6 @@ import com.intellij.openapi.vfs.VirtualFile
|
|||||||
import com.intellij.psi.FileViewProvider
|
import com.intellij.psi.FileViewProvider
|
||||||
import com.intellij.psi.PsiManager
|
import com.intellij.psi.PsiManager
|
||||||
import com.intellij.psi.compiled.ClassFileDecompilers
|
import com.intellij.psi.compiled.ClassFileDecompilers
|
||||||
import com.intellij.psi.compiled.ClsStubBuilder
|
|
||||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||||
import org.jetbrains.kotlin.idea.decompiler.KotlinDecompiledFileViewProvider
|
import org.jetbrains.kotlin.idea.decompiler.KotlinDecompiledFileViewProvider
|
||||||
import org.jetbrains.kotlin.idea.decompiler.KtDecompiledFile
|
import org.jetbrains.kotlin.idea.decompiler.KtDecompiledFile
|
||||||
@@ -41,13 +40,15 @@ import java.io.IOException
|
|||||||
|
|
||||||
abstract class KotlinMetadataDecompiler<out V : BinaryVersion>(
|
abstract class KotlinMetadataDecompiler<out V : BinaryVersion>(
|
||||||
private val fileType: FileType,
|
private val fileType: FileType,
|
||||||
private val stubBuilder: ClsStubBuilder,
|
|
||||||
private val targetPlatform: TargetPlatform,
|
private val targetPlatform: TargetPlatform,
|
||||||
private val serializerProtocol: SerializerExtensionProtocol,
|
private val serializerProtocol: SerializerExtensionProtocol,
|
||||||
private val flexibleTypeDeserializer: FlexibleTypeDeserializer,
|
private val flexibleTypeDeserializer: FlexibleTypeDeserializer,
|
||||||
private val expectedBinaryVersion: V,
|
private val expectedBinaryVersion: V,
|
||||||
private val invalidBinaryVersion: V
|
private val invalidBinaryVersion: V,
|
||||||
|
stubVersion: Int
|
||||||
) : ClassFileDecompilers.Full() {
|
) : ClassFileDecompilers.Full() {
|
||||||
|
private val stubBuilder = KotlinMetadataStubBuilder(stubVersion, fileType, serializerProtocol, this::readFile)
|
||||||
|
|
||||||
private val renderer = DescriptorRenderer.withOptions { defaultDecompilerRendererOptions() }
|
private val renderer = DescriptorRenderer.withOptions { defaultDecompilerRendererOptions() }
|
||||||
|
|
||||||
abstract fun readFile(bytes: ByteArray, file: VirtualFile): FileWithMetadata?
|
abstract fun readFile(bytes: ByteArray, file: VirtualFile): FileWithMetadata?
|
||||||
|
|||||||
+15
-11
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2010-2016 JetBrains s.r.o.
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -14,28 +14,32 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package org.jetbrains.kotlin.idea.decompiler.builtIns
|
package org.jetbrains.kotlin.idea.decompiler.common
|
||||||
|
|
||||||
|
import com.intellij.openapi.fileTypes.FileType
|
||||||
|
import com.intellij.openapi.vfs.VirtualFile
|
||||||
import com.intellij.psi.compiled.ClsStubBuilder
|
import com.intellij.psi.compiled.ClsStubBuilder
|
||||||
import com.intellij.psi.impl.compiled.ClassFileStubBuilder
|
import com.intellij.psi.impl.compiled.ClassFileStubBuilder
|
||||||
import com.intellij.psi.stubs.PsiFileStub
|
import com.intellij.psi.stubs.PsiFileStub
|
||||||
import com.intellij.util.indexing.FileContent
|
import com.intellij.util.indexing.FileContent
|
||||||
import org.jetbrains.kotlin.builtins.BuiltInSerializerProtocol
|
|
||||||
import org.jetbrains.kotlin.idea.decompiler.common.AnnotationLoaderForStubBuilderImpl
|
|
||||||
import org.jetbrains.kotlin.idea.decompiler.common.FileWithMetadata
|
|
||||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.*
|
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.*
|
||||||
import org.jetbrains.kotlin.psi.stubs.KotlinStubVersions
|
import org.jetbrains.kotlin.serialization.SerializerExtensionProtocol
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.ProtoBasedClassDataFinder
|
import org.jetbrains.kotlin.serialization.deserialization.ProtoBasedClassDataFinder
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.ProtoContainer
|
import org.jetbrains.kotlin.serialization.deserialization.ProtoContainer
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.TypeTable
|
import org.jetbrains.kotlin.serialization.deserialization.TypeTable
|
||||||
|
|
||||||
class KotlinBuiltInStubBuilder : ClsStubBuilder() {
|
open class KotlinMetadataStubBuilder(
|
||||||
override fun getStubVersion() = ClassFileStubBuilder.STUB_VERSION + KotlinStubVersions.BUILTIN_STUB_VERSION
|
private val version: Int,
|
||||||
|
private val fileType: FileType,
|
||||||
|
private val serializerProtocol: SerializerExtensionProtocol,
|
||||||
|
private val readFile: (ByteArray, VirtualFile) -> FileWithMetadata?
|
||||||
|
) : ClsStubBuilder() {
|
||||||
|
override fun getStubVersion() = ClassFileStubBuilder.STUB_VERSION + version
|
||||||
|
|
||||||
override fun buildFileStub(content: FileContent): PsiFileStub<*>? {
|
override fun buildFileStub(content: FileContent): PsiFileStub<*>? {
|
||||||
val virtualFile = content.file
|
val virtualFile = content.file
|
||||||
assert(virtualFile.fileType == KotlinBuiltInFileType) { "Unexpected file type ${virtualFile.fileType}" }
|
assert(virtualFile.fileType == fileType) { "Unexpected file type ${virtualFile.fileType}" }
|
||||||
val file = BuiltInDefinitionFile.read(content.content, virtualFile) ?: return null
|
val file = readFile(content.content, virtualFile) ?: return null
|
||||||
|
|
||||||
when (file) {
|
when (file) {
|
||||||
is FileWithMetadata.Incompatible -> {
|
is FileWithMetadata.Incompatible -> {
|
||||||
@@ -47,7 +51,7 @@ class KotlinBuiltInStubBuilder : ClsStubBuilder() {
|
|||||||
val nameResolver = file.nameResolver
|
val nameResolver = file.nameResolver
|
||||||
val components = ClsStubBuilderComponents(
|
val components = ClsStubBuilderComponents(
|
||||||
ProtoBasedClassDataFinder(file.proto, nameResolver),
|
ProtoBasedClassDataFinder(file.proto, nameResolver),
|
||||||
AnnotationLoaderForStubBuilderImpl(BuiltInSerializerProtocol),
|
AnnotationLoaderForStubBuilderImpl(serializerProtocol),
|
||||||
virtualFile
|
virtualFile
|
||||||
)
|
)
|
||||||
val context = components.createContext(nameResolver, packageFqName, TypeTable(packageProto.typeTable))
|
val context = components.createContext(nameResolver, packageFqName, TypeTable(packageProto.typeTable))
|
||||||
+12
-18
@@ -20,6 +20,7 @@ import com.intellij.openapi.vfs.VirtualFile
|
|||||||
import org.jetbrains.kotlin.idea.decompiler.common.FileWithMetadata
|
import org.jetbrains.kotlin.idea.decompiler.common.FileWithMetadata
|
||||||
import org.jetbrains.kotlin.idea.decompiler.common.KotlinMetadataDecompiler
|
import org.jetbrains.kotlin.idea.decompiler.common.KotlinMetadataDecompiler
|
||||||
import org.jetbrains.kotlin.js.resolve.JsPlatform
|
import org.jetbrains.kotlin.js.resolve.JsPlatform
|
||||||
|
import org.jetbrains.kotlin.psi.stubs.KotlinStubVersions
|
||||||
import org.jetbrains.kotlin.serialization.ProtoBuf
|
import org.jetbrains.kotlin.serialization.ProtoBuf
|
||||||
import org.jetbrains.kotlin.serialization.js.DynamicTypeDeserializer
|
import org.jetbrains.kotlin.serialization.js.DynamicTypeDeserializer
|
||||||
import org.jetbrains.kotlin.serialization.js.JsProtoBuf
|
import org.jetbrains.kotlin.serialization.js.JsProtoBuf
|
||||||
@@ -28,27 +29,20 @@ import org.jetbrains.kotlin.utils.JsMetadataVersion
|
|||||||
import java.io.ByteArrayInputStream
|
import java.io.ByteArrayInputStream
|
||||||
|
|
||||||
class KotlinJavaScriptMetaFileDecompiler : KotlinMetadataDecompiler<JsMetadataVersion>(
|
class KotlinJavaScriptMetaFileDecompiler : KotlinMetadataDecompiler<JsMetadataVersion>(
|
||||||
KotlinJavaScriptMetaFileType, KotlinJavaScriptStubBuilder(), JsPlatform, JsSerializerProtocol, DynamicTypeDeserializer,
|
KotlinJavaScriptMetaFileType, JsPlatform, JsSerializerProtocol, DynamicTypeDeserializer,
|
||||||
JsMetadataVersion.INSTANCE, JsMetadataVersion.INVALID_VERSION
|
JsMetadataVersion.INSTANCE, JsMetadataVersion.INVALID_VERSION, KotlinStubVersions.JS_STUB_VERSION
|
||||||
) {
|
) {
|
||||||
override fun readFile(bytes: ByteArray, file: VirtualFile): FileWithMetadata? {
|
override fun readFile(bytes: ByteArray, file: VirtualFile): FileWithMetadata? {
|
||||||
return KjsmFile.read(bytes)
|
val stream = ByteArrayInputStream(bytes)
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class KjsmFile(proto: ProtoBuf.PackageFragment) : FileWithMetadata.Compatible(proto, JsSerializerProtocol) {
|
val version = JsMetadataVersion.readFrom(stream)
|
||||||
companion object {
|
if (!version.isCompatible()) {
|
||||||
fun read(bytes: ByteArray): FileWithMetadata? {
|
return FileWithMetadata.Incompatible(version)
|
||||||
val stream = ByteArrayInputStream(bytes)
|
|
||||||
|
|
||||||
val version = JsMetadataVersion.readFrom(stream)
|
|
||||||
if (!version.isCompatible()) {
|
|
||||||
return FileWithMetadata.Incompatible(version)
|
|
||||||
}
|
|
||||||
|
|
||||||
JsProtoBuf.Header.parseDelimitedFrom(stream)
|
|
||||||
|
|
||||||
return KjsmFile(ProtoBuf.PackageFragment.parseFrom(stream, JsSerializerProtocol.extensionRegistry))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
JsProtoBuf.Header.parseDelimitedFrom(stream)
|
||||||
|
|
||||||
|
val proto = ProtoBuf.PackageFragment.parseFrom(stream, JsSerializerProtocol.extensionRegistry)
|
||||||
|
return FileWithMetadata.Compatible(proto, JsSerializerProtocol)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
-71
@@ -1,71 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2010-2016 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.idea.decompiler.js
|
|
||||||
|
|
||||||
import com.intellij.psi.compiled.ClsStubBuilder
|
|
||||||
import com.intellij.psi.impl.compiled.ClassFileStubBuilder
|
|
||||||
import com.intellij.psi.stubs.PsiFileStub
|
|
||||||
import com.intellij.util.indexing.FileContent
|
|
||||||
import org.jetbrains.kotlin.idea.decompiler.common.AnnotationLoaderForStubBuilderImpl
|
|
||||||
import org.jetbrains.kotlin.idea.decompiler.common.FileWithMetadata
|
|
||||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.*
|
|
||||||
import org.jetbrains.kotlin.psi.stubs.KotlinStubVersions
|
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.ProtoBasedClassDataFinder
|
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.ProtoContainer
|
|
||||||
import org.jetbrains.kotlin.serialization.deserialization.TypeTable
|
|
||||||
import org.jetbrains.kotlin.serialization.js.JsSerializerProtocol
|
|
||||||
|
|
||||||
// TODO: deduplicate code with KotlinBuiltInStubBuilder
|
|
||||||
class KotlinJavaScriptStubBuilder : ClsStubBuilder() {
|
|
||||||
override fun getStubVersion() = ClassFileStubBuilder.STUB_VERSION + KotlinStubVersions.JS_STUB_VERSION
|
|
||||||
|
|
||||||
override fun buildFileStub(content: FileContent): PsiFileStub<*>? {
|
|
||||||
val virtualFile = content.file
|
|
||||||
assert(virtualFile.fileType == KotlinJavaScriptMetaFileType) { "Unexpected file type ${virtualFile.fileType}" }
|
|
||||||
val file = KjsmFile.read(content.content) ?: return null
|
|
||||||
|
|
||||||
when (file) {
|
|
||||||
is FileWithMetadata.Incompatible -> {
|
|
||||||
return createIncompatibleAbiVersionFileStub()
|
|
||||||
}
|
|
||||||
is FileWithMetadata.Compatible -> {
|
|
||||||
val packageProto = file.proto.`package`
|
|
||||||
val packageFqName = file.packageFqName
|
|
||||||
val nameResolver = file.nameResolver
|
|
||||||
val components = ClsStubBuilderComponents(
|
|
||||||
ProtoBasedClassDataFinder(file.proto, nameResolver),
|
|
||||||
AnnotationLoaderForStubBuilderImpl(JsSerializerProtocol),
|
|
||||||
virtualFile
|
|
||||||
)
|
|
||||||
val context = components.createContext(nameResolver, packageFqName, TypeTable(packageProto.typeTable))
|
|
||||||
|
|
||||||
val fileStub = createFileStub(packageFqName, isScript = false)
|
|
||||||
createDeclarationsStubs(
|
|
||||||
fileStub, context,
|
|
||||||
ProtoContainer.Package(packageFqName, context.nameResolver, context.typeTable, source = null),
|
|
||||||
packageProto
|
|
||||||
)
|
|
||||||
for (classProto in file.classesToDecompile) {
|
|
||||||
createClassStub(
|
|
||||||
fileStub, classProto, nameResolver, nameResolver.getClassId(classProto.fqName), source = null, context = context
|
|
||||||
)
|
|
||||||
}
|
|
||||||
return fileStub
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
+3
-3
@@ -21,7 +21,7 @@ import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase
|
|||||||
import com.intellij.util.indexing.FileContentImpl
|
import com.intellij.util.indexing.FileContentImpl
|
||||||
import org.jetbrains.kotlin.builtins.BuiltInSerializerProtocol
|
import org.jetbrains.kotlin.builtins.BuiltInSerializerProtocol
|
||||||
import org.jetbrains.kotlin.builtins.BuiltInsBinaryVersion
|
import org.jetbrains.kotlin.builtins.BuiltInsBinaryVersion
|
||||||
import org.jetbrains.kotlin.idea.decompiler.builtIns.KotlinBuiltInStubBuilder
|
import org.jetbrains.kotlin.idea.decompiler.builtIns.KotlinBuiltInDecompiler
|
||||||
import org.jetbrains.kotlin.idea.test.KotlinWithJdkAndRuntimeLightProjectDescriptor
|
import org.jetbrains.kotlin.idea.test.KotlinWithJdkAndRuntimeLightProjectDescriptor
|
||||||
import org.jetbrains.kotlin.idea.test.PluginTestCaseBase
|
import org.jetbrains.kotlin.idea.test.PluginTestCaseBase
|
||||||
import org.jetbrains.kotlin.name.FqName
|
import org.jetbrains.kotlin.name.FqName
|
||||||
@@ -49,7 +49,7 @@ class BuiltInDecompilerTest : AbstractBuiltInDecompilerTest() {
|
|||||||
val dirInRuntime = findDir(packageFqName, project)
|
val dirInRuntime = findDir(packageFqName, project)
|
||||||
val kotlinBuiltInsVirtualFile = dirInRuntime.children.single { it.extension == BuiltInSerializerProtocol.BUILTINS_FILE_EXTENSION }
|
val kotlinBuiltInsVirtualFile = dirInRuntime.children.single { it.extension == BuiltInSerializerProtocol.BUILTINS_FILE_EXTENSION }
|
||||||
myFixture.configureFromExistingVirtualFile(kotlinBuiltInsVirtualFile)
|
myFixture.configureFromExistingVirtualFile(kotlinBuiltInsVirtualFile)
|
||||||
return KotlinBuiltInStubBuilder().buildFileStub(FileContentImpl.createByFile(kotlinBuiltInsVirtualFile))!!
|
return KotlinBuiltInDecompiler().stubBuilder.buildFileStub(FileContentImpl.createByFile(kotlinBuiltInsVirtualFile))!!
|
||||||
}
|
}
|
||||||
|
|
||||||
fun testBuiltInStubTreeEqualToStubTreeFromDecompiledText() {
|
fun testBuiltInStubTreeEqualToStubTreeFromDecompiledText() {
|
||||||
@@ -63,7 +63,7 @@ class BuiltInDecompilerForWrongAbiVersionTest : AbstractBuiltInDecompilerTest()
|
|||||||
|
|
||||||
override fun configureAndBuildFileStub(packageFqName: String): PsiFileStub<*> {
|
override fun configureAndBuildFileStub(packageFqName: String): PsiFileStub<*> {
|
||||||
myFixture.configureByFile(testDataPath + BuiltInSerializerProtocol.getBuiltInsFilePath(FqName(packageFqName)))
|
myFixture.configureByFile(testDataPath + BuiltInSerializerProtocol.getBuiltInsFilePath(FqName(packageFqName)))
|
||||||
return KotlinBuiltInStubBuilder().buildFileStub(FileContentImpl.createByFile(myFixture.file.virtualFile))!!
|
return KotlinBuiltInDecompiler().stubBuilder.buildFileStub(FileContentImpl.createByFile(myFixture.file.virtualFile))!!
|
||||||
}
|
}
|
||||||
|
|
||||||
fun testStubTreesEqualForIncompatibleAbiVersion() {
|
fun testStubTreesEqualForIncompatibleAbiVersion() {
|
||||||
|
|||||||
Reference in New Issue
Block a user