Improved kotlin decompiler range indexes
Fixed #KT-30628
This commit is contained in:
@@ -57,10 +57,7 @@ object MapPsiToAsmDesc {
|
||||
append(typeDesc(it.type))
|
||||
}
|
||||
append(")")
|
||||
psiMethod.returnType?.let {
|
||||
append(typeDesc(it))
|
||||
}
|
||||
?: return unknownSignature() // TODO: support constructors, there seems to be additional logic in java that doesn't work correctly for compiled kotlin
|
||||
append(psiMethod.returnType?.let { typeDesc(it) } ?: "V")
|
||||
}
|
||||
|
||||
private fun unknownSignature() = ""
|
||||
|
||||
@@ -64,6 +64,7 @@ import org.jetbrains.kotlin.idea.debugger.test.AbstractFileRankingTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToDecompiledLibraryTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTestWithJS
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateJavaToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractClsStubBuilderTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractLoadJavaClsStubTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.textBuilder.AbstractCommonDecompiledTextFromJsMetadataTest
|
||||
@@ -332,6 +333,10 @@ fun main(args: Array<String>) {
|
||||
model("decompiler/navigation/usercode")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateJavaToLibrarySourceTest>(annotations = listOf(muteExtraSuffix(".libsrc"))) {
|
||||
model("decompiler/navigation/userJavaCode", pattern = "^(.+)\\.java$")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateToLibrarySourceTestWithJS>(annotations = listOf(muteExtraSuffix(".libsrcjs"))) {
|
||||
model("decompiler/navigation/usercode", testClassName = "UsercodeWithJSModule")
|
||||
}
|
||||
|
||||
@@ -70,6 +70,7 @@ import org.jetbrains.kotlin.idea.debugger.test.AbstractFileRankingTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToDecompiledLibraryTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTestWithJS
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateJavaToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractClsStubBuilderTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractLoadJavaClsStubTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.textBuilder.AbstractCommonDecompiledTextFromJsMetadataTest
|
||||
@@ -318,6 +319,10 @@ fun main(args: Array<String>) {
|
||||
model("decompiler/navigation/usercode")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateJavaToLibrarySourceTest>(annotations = listOf(muteExtraSuffix(".libsrc"))) {
|
||||
model("decompiler/navigation/userJavaCode", pattern = "^(.+)\\.java$")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateToLibrarySourceTestWithJS>(annotations = listOf(muteExtraSuffix(".libsrcjs"))) {
|
||||
model("decompiler/navigation/usercode", testClassName ="UsercodeWithJSModule")
|
||||
}
|
||||
|
||||
@@ -70,6 +70,7 @@ import org.jetbrains.kotlin.idea.debugger.test.AbstractFileRankingTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToDecompiledLibraryTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTestWithJS
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateJavaToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractClsStubBuilderTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractLoadJavaClsStubTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.textBuilder.AbstractCommonDecompiledTextFromJsMetadataTest
|
||||
@@ -318,6 +319,10 @@ fun main(args: Array<String>) {
|
||||
model("decompiler/navigation/usercode")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateJavaToLibrarySourceTest>(annotations = listOf(muteExtraSuffix(".libsrc"))) {
|
||||
model("decompiler/navigation/userJavaCode", pattern = "^(.+)\\.java$")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateToLibrarySourceTestWithJS>(annotations = listOf(muteExtraSuffix(".libsrcjs"))) {
|
||||
model("decompiler/navigation/usercode", testClassName ="UsercodeWithJSModule")
|
||||
}
|
||||
|
||||
@@ -70,6 +70,7 @@ import org.jetbrains.kotlin.idea.debugger.test.AbstractFileRankingTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToDecompiledLibraryTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateToLibrarySourceTestWithJS
|
||||
import org.jetbrains.kotlin.idea.decompiler.navigation.AbstractNavigateJavaToLibrarySourceTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractClsStubBuilderTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.stubBuilder.AbstractLoadJavaClsStubTest
|
||||
import org.jetbrains.kotlin.idea.decompiler.textBuilder.AbstractCommonDecompiledTextFromJsMetadataTest
|
||||
@@ -318,6 +319,10 @@ fun main(args: Array<String>) {
|
||||
model("decompiler/navigation/usercode")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateJavaToLibrarySourceTest>(annotations = listOf(muteExtraSuffix(".libsrc"))) {
|
||||
model("decompiler/navigation/userJavaCode", pattern = "^(.+)\\.java$")
|
||||
}
|
||||
|
||||
testClass<AbstractNavigateToLibrarySourceTestWithJS>(annotations = listOf(muteExtraSuffix(".libsrcjs"))) {
|
||||
model("decompiler/navigation/usercode", testClassName ="UsercodeWithJSModule")
|
||||
}
|
||||
|
||||
+115
-37
@@ -1,17 +1,6 @@
|
||||
/*
|
||||
* 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.
|
||||
* Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.idea.caches.lightClasses
|
||||
@@ -20,6 +9,8 @@ import com.intellij.psi.PsiElement
|
||||
import com.intellij.psi.PsiField
|
||||
import com.intellij.psi.PsiMember
|
||||
import com.intellij.psi.PsiMethod
|
||||
import com.intellij.psi.impl.compiled.SignatureParsing
|
||||
import com.intellij.util.cls.ClsFormatException
|
||||
import org.jetbrains.kotlin.asJava.builder.LightMemberOrigin
|
||||
import org.jetbrains.kotlin.asJava.classes.lazyPub
|
||||
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||
@@ -36,12 +27,18 @@ import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.psi.KtClassOrObject
|
||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||
import org.jetbrains.kotlin.psi.KtDeclarationContainer
|
||||
import org.jetbrains.kotlin.resolve.calls.components.hasDefaultValue
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.classId
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.isExtension
|
||||
import org.jetbrains.kotlin.resolve.jvm.JvmClassName
|
||||
import org.jetbrains.kotlin.resolve.jvm.annotations.findJvmOverloadsAnnotation
|
||||
import org.jetbrains.kotlin.resolve.jvm.diagnostics.JvmDeclarationOriginKind
|
||||
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.type.MapPsiToAsmDesc
|
||||
import java.text.CharacterIterator
|
||||
import java.text.StringCharacterIterator
|
||||
|
||||
interface LightMemberOriginForCompiledElement<T : PsiMember> : LightMemberOrigin {
|
||||
val member: T
|
||||
@@ -98,7 +95,8 @@ data class LightMemberOriginForCompiledMethod(val psiMethod: PsiMethod, val file
|
||||
|
||||
override val originalElement: KtDeclaration? by lazyPub {
|
||||
val desc = MapPsiToAsmDesc.methodDesc(psiMethod)
|
||||
val signature = MemberSignature.fromMethodNameAndDesc(psiMethod.name, desc)
|
||||
val name = if (psiMethod.isConstructor) "<init>" else psiMethod.name
|
||||
val signature = MemberSignature.fromMethodNameAndDesc(name, desc)
|
||||
findDeclarationInCompiledFile(file, psiMethod, signature)
|
||||
}
|
||||
}
|
||||
@@ -148,58 +146,138 @@ private fun ClassDescriptor.relativeClassName(): List<Name> {
|
||||
return classId!!.relativeClassName.pathSegments().drop(1)
|
||||
}
|
||||
|
||||
private fun excludeParametersFromDescriptor(descriptor: String, omittedParameters: List<Int>): String? {
|
||||
|
||||
fun tryParseParametersAndReturnType(): Pair<List<String>, String>? {
|
||||
val iterator = StringCharacterIterator(descriptor)
|
||||
|
||||
fun parseTypeString(): String? {
|
||||
val begin = iterator.index
|
||||
try {
|
||||
SignatureParsing.parseTypeString(iterator) { it }
|
||||
} catch (e: ClsFormatException) {
|
||||
return null
|
||||
}
|
||||
val end = iterator.index
|
||||
return descriptor.substring(begin, end)
|
||||
}
|
||||
|
||||
if (iterator.current() != '(') return null
|
||||
iterator.next()
|
||||
|
||||
if (iterator.current() == ')') {
|
||||
iterator.next()
|
||||
val returnType = parseTypeString() ?: return null
|
||||
return emptyList<String>() to returnType
|
||||
}
|
||||
|
||||
val parameterTypes = mutableListOf<String>()
|
||||
while (iterator.current() != ')' && iterator.current() != CharacterIterator.DONE) {
|
||||
parameterTypes += parseTypeString() ?: return null
|
||||
}
|
||||
|
||||
if (iterator.current() != ')') return null
|
||||
iterator.next()
|
||||
|
||||
val returnType = parseTypeString() ?: return null
|
||||
return parameterTypes to returnType
|
||||
}
|
||||
|
||||
val (parameterTypes, returnType) = tryParseParametersAndReturnType() ?: return null
|
||||
|
||||
val parametersList = parameterTypes
|
||||
.filterIndexed { index, _ -> index !in omittedParameters }
|
||||
.joinToString("")
|
||||
|
||||
return "($parametersList)$returnType"
|
||||
}
|
||||
|
||||
private fun ClassDescriptor.desc(): String = "L" + JvmClassName.byClassId(classId!!).internalName + ";"
|
||||
|
||||
private object ByJvmSignatureIndexer : DecompiledTextIndexer<ClassNameAndSignature> {
|
||||
override fun indexDescriptor(descriptor: DeclarationDescriptor): Collection<ClassNameAndSignature> {
|
||||
val signatures = arrayListOf<ClassNameAndSignature>()
|
||||
|
||||
fun save(id: List<Name>, signature: MemberSignature) {
|
||||
signatures.add(ClassNameAndSignature(id, signature))
|
||||
}
|
||||
|
||||
if (descriptor is ClassDescriptor) {
|
||||
@Suppress("NON_EXHAUSTIVE_WHEN")
|
||||
when (descriptor.kind) {
|
||||
fun ClassDescriptor.apply() {
|
||||
when (kind) {
|
||||
ClassKind.ENUM_ENTRY -> {
|
||||
val enumClass = descriptor.containingDeclaration as ClassDescriptor
|
||||
val signature = MemberSignature.fromFieldNameAndDesc(descriptor.name.asString(), enumClass.desc())
|
||||
val enumClass = containingDeclaration as ClassDescriptor
|
||||
val signature = MemberSignature.fromFieldNameAndDesc(name.asString(), enumClass.desc())
|
||||
save(enumClass.relativeClassName(), signature)
|
||||
}
|
||||
ClassKind.OBJECT -> {
|
||||
val instanceFieldSignature = MemberSignature.fromFieldNameAndDesc(JvmAbi.INSTANCE_FIELD, descriptor.desc())
|
||||
save(descriptor.relativeClassName(), instanceFieldSignature)
|
||||
if (descriptor.isCompanionObject) {
|
||||
val signature = MemberSignature.fromFieldNameAndDesc(descriptor.name.asString(), descriptor.desc())
|
||||
save((descriptor.containingDeclaration as? ClassDescriptor)?.relativeClassName().orEmpty(), signature)
|
||||
val instanceFieldSignature = MemberSignature.fromFieldNameAndDesc(JvmAbi.INSTANCE_FIELD, desc())
|
||||
save(relativeClassName(), instanceFieldSignature)
|
||||
if (isCompanionObject) {
|
||||
val signature = MemberSignature.fromFieldNameAndDesc(name.asString(), desc())
|
||||
save((containingDeclaration as? ClassDescriptor)?.relativeClassName().orEmpty(), signature)
|
||||
}
|
||||
}
|
||||
else -> {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun DeserializedClassConstructorDescriptor.apply() {
|
||||
JvmProtoBufUtil.getJvmConstructorSignature(proto, nameResolver, typeTable)?.let {
|
||||
val id = (containingDeclaration as? ClassDescriptor)?.relativeClassName().orEmpty()
|
||||
val signature = MemberSignature.fromJvmMemberSignature(it)
|
||||
save(id, signature)
|
||||
}
|
||||
}
|
||||
|
||||
fun DeserializedSimpleFunctionDescriptor.apply() {
|
||||
JvmProtoBufUtil.getJvmMethodSignature(proto, nameResolver, typeTable)?.let {
|
||||
val id = (containingDeclaration as? ClassDescriptor)?.relativeClassName().orEmpty()
|
||||
|
||||
val signature = MemberSignature.fromJvmMemberSignature(it)
|
||||
save(id, signature)
|
||||
|
||||
if (findJvmOverloadsAnnotation() == null) return
|
||||
|
||||
val extensionShift = if (isExtension) 1 else 0
|
||||
|
||||
val omittedList = mutableListOf<Int>()
|
||||
valueParameters.asReversed().forEach { parameter ->
|
||||
if (parameter.hasDefaultValue()) {
|
||||
omittedList.add(parameter.index + extensionShift)
|
||||
val newDescriptor = excludeParametersFromDescriptor(it.desc, omittedList)
|
||||
if (newDescriptor != null) {
|
||||
val overloadedSignature = MemberSignature.fromMethodNameAndDesc(it.name, newDescriptor)
|
||||
save(id, overloadedSignature)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (descriptor is DeserializedSimpleFunctionDescriptor) {
|
||||
JvmProtoBufUtil.getJvmMethodSignature(descriptor.proto, descriptor.nameResolver, descriptor.typeTable)?.let { it ->
|
||||
val signature = MemberSignature.fromJvmMemberSignature(it)
|
||||
save((descriptor.containingDeclaration as? ClassDescriptor)?.relativeClassName().orEmpty(), signature)
|
||||
}
|
||||
}
|
||||
if (descriptor is DeserializedPropertyDescriptor) {
|
||||
val proto = descriptor.proto
|
||||
val className = (descriptor.containingDeclaration as? ClassDescriptor)?.relativeClassName().orEmpty()
|
||||
fun DeserializedPropertyDescriptor.apply() {
|
||||
val className = (containingDeclaration as? ClassDescriptor)?.relativeClassName().orEmpty()
|
||||
val signature = proto.getExtensionOrNull(JvmProtoBuf.propertySignature)
|
||||
if (signature != null) {
|
||||
val fieldSignature = JvmProtoBufUtil.getJvmFieldSignature(proto, descriptor.nameResolver, descriptor.typeTable)
|
||||
val fieldSignature = JvmProtoBufUtil.getJvmFieldSignature(proto, nameResolver, typeTable)
|
||||
if (fieldSignature != null) {
|
||||
save(className, MemberSignature.fromJvmMemberSignature(fieldSignature))
|
||||
}
|
||||
if (signature.hasGetter()) {
|
||||
save(className, MemberSignature.fromMethod(descriptor.nameResolver, signature.getter))
|
||||
save(className, MemberSignature.fromMethod(nameResolver, signature.getter))
|
||||
}
|
||||
if (signature.hasSetter()) {
|
||||
save(className, MemberSignature.fromMethod(descriptor.nameResolver, signature.setter))
|
||||
save(className, MemberSignature.fromMethod(nameResolver, signature.setter))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
when (descriptor) {
|
||||
is ClassDescriptor -> descriptor.apply()
|
||||
is DeserializedClassConstructorDescriptor -> descriptor.apply()
|
||||
is DeserializedSimpleFunctionDescriptor -> descriptor.apply()
|
||||
is DeserializedPropertyDescriptor -> descriptor.apply()
|
||||
}
|
||||
|
||||
return signatures
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
package testData.libraries
|
||||
|
||||
class SomeClassWithConstructors(private val arg: String) {
|
||||
constructor(x: Int) : this("Hello")
|
||||
fun check() {
|
||||
TODO()
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
package testData.libraries
|
||||
|
||||
@JvmOverloads
|
||||
fun <T> String.overloadedFun(vararg specs: String, allowExisting: Boolean = false, x: Int, y: Int = 2, z: T): String {
|
||||
TODO()
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
package testData.libraries
|
||||
|
||||
@JvmName("renamedFun")
|
||||
fun funToRename(x: Int) {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
import testData.libraries.*;
|
||||
|
||||
class TestClassAndConstructors {
|
||||
void foo() {
|
||||
|
||||
SomeClassWithConstructors inst = new SomeClassWithConstructors("arg");
|
||||
|
||||
SomeClassWithConstructors inst2 = new SomeClassWithConstructors(2);
|
||||
}
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
Actual data differs from file content: ClassAndConstuctors.source.expected expected:< [SomeClassWithConstructors.class
|
||||
public final class <1><2><3><4>SomeClassWithConstructors public constructor(arg: kotlin.String)] {
|
||||
> but was:< [classAndConstructors.kt
|
||||
class <1><2><3><4>SomeClassWithConstructors(private val arg: String) ] {
|
||||
>
|
||||
+2
@@ -0,0 +1,2 @@
|
||||
SomeClassWithConstructors.class
|
||||
public final class <1><2><3><4>SomeClassWithConstructors public constructor(arg: kotlin.String) {
|
||||
@@ -0,0 +1,11 @@
|
||||
import testData.libraries.*;
|
||||
|
||||
class TestOverload {
|
||||
void foo() {
|
||||
OverloadedFunKt.overloadedFun("", null, 2, null);
|
||||
|
||||
OverloadedFunKt.overloadedFun("", null, true, 2, null);
|
||||
|
||||
OverloadedFunKt.overloadedFun("", null, true, 2, 3, null);
|
||||
}
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
Actual data differs from file content: OverloadedFun.source.expected expected:<...d from a class file
|
||||
[// Implementation of methods is not available
|
||||
|
||||
package testData.libraries
|
||||
|
||||
@kotlin.jvm.JvmOverloads public fun <T> kotlin.String.<2><4><6>overloadedFun(vararg specs: kotlin.String, allowExisting: kotlin.Boolean /* = compiled code */, x: kotlin.Int, y: kotlin.Int /* = compiled code */, z: T): kotlin.String { /* compiled code */ }]
|
||||
> but was:<...d from a class file
|
||||
[ overloadedFun.kt
|
||||
fun <T> String.<2><4><6>overloadedFun(vararg specs: String, allowExisting: Boolean = false, x: Int, y: Int = 2, z: T): String {]
|
||||
>
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
OverloadedFunKt.class
|
||||
<1><3><5>// IntelliJ API Decompiler stub source generated from a class file
|
||||
// Implementation of methods is not available
|
||||
|
||||
package testData.libraries
|
||||
|
||||
@kotlin.jvm.JvmOverloads public fun <T> kotlin.String.<2><4><6>overloadedFun(vararg specs: kotlin.String, allowExisting: kotlin.Boolean /* = compiled code */, x: kotlin.Int, y: kotlin.Int /* = compiled code */, z: T): kotlin.String { /* compiled code */ }
|
||||
@@ -0,0 +1,7 @@
|
||||
import testData.libraries.*;
|
||||
|
||||
class TestRenamedElements {
|
||||
void foo() {
|
||||
RenamedElementsKt.renamedFun(2);
|
||||
}
|
||||
}
|
||||
+12
@@ -0,0 +1,12 @@
|
||||
Actual data differs from file content: RenamedElements.source.expected expected:<[RenamedElementsKt.class
|
||||
<1>// IntelliJ API Decompiler stub source generated from a class file
|
||||
// Implementation of methods is not available
|
||||
|
||||
package testData.libraries
|
||||
|
||||
@kotlin.jvm.JvmName public fun <2>funToRename(x: kotlin.Int): kotlin.Unit { /* compiled code */ }]
|
||||
> but was:<[ RenamedElementsKt.class
|
||||
<1>// IntelliJ API Decompiler stub source generated from a class file
|
||||
renamedElements.kt
|
||||
fun <2>funToRename(x: Int) {]
|
||||
>
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
RenamedElementsKt.class
|
||||
<1>// IntelliJ API Decompiler stub source generated from a class file
|
||||
// Implementation of methods is not available
|
||||
|
||||
package testData.libraries
|
||||
|
||||
@kotlin.jvm.JvmName public fun <2>funToRename(x: kotlin.Int): kotlin.Unit { /* compiled code */ }
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
Actual data differs from file content: LibraryNestedClassSecondaryConstructorUsages.results.txt expected:<...3 class Y(): A.T()
|
||||
[[LibraryNestedClassSecondaryConstructorUsages.1.java] New instance creation 14 A.T a = new A.T();
|
||||
[LibraryNestedClassSecondaryConstructorUsages.1.java] Unclassified usage 10 super();
|
||||
[LibraryNestedClassSecondaryConstructorUsages.1.java] Unclassified usage 6 public J() {
|
||||
[library.kt] New instance creation 64 val tt = A.T()
|
||||
[library.kt] Supertype 40 class VV(): A.T()
|
||||
]> but was:<...3 class Y(): A.T()
|
||||
[[library.kt] New instance creation 64 val tt = A.T()
|
||||
[library.kt] Supertype 40 class VV(): A.T()]>
|
||||
+2
-2
@@ -1,6 +1,6 @@
|
||||
package usages
|
||||
package usages;
|
||||
|
||||
import library.*
|
||||
import library.*;
|
||||
|
||||
class J extends A.T {
|
||||
public J() {
|
||||
|
||||
+3
@@ -1,4 +1,7 @@
|
||||
[LibraryNestedClassSecondaryConstructorUsages.0.kt] New instance creation 16 val a: A.T = A.T()
|
||||
[LibraryNestedClassSecondaryConstructorUsages.0.kt] Supertype 13 class Y(): A.T()
|
||||
[LibraryNestedClassSecondaryConstructorUsages.1.java] New instance creation 14 A.T a = new A.T();
|
||||
[LibraryNestedClassSecondaryConstructorUsages.1.java] Unclassified usage 10 super();
|
||||
[LibraryNestedClassSecondaryConstructorUsages.1.java] Unclassified usage 6 public J() {
|
||||
[library.kt] New instance creation 64 val tt = A.T()
|
||||
[library.kt] Supertype 40 class VV(): A.T()
|
||||
|
||||
idea/testData/findUsages/libraryUsages/kotlinLibrary/LibrarySecondaryConstructorUsages.0.kt.fail.192
Vendored
+6
@@ -0,0 +1,6 @@
|
||||
Actual data differs from file content: LibrarySecondaryConstructorUsages.results.txt expected:<... 13 class Y(): A()
|
||||
[[LibrarySecondaryConstructorUsages.1.java] New instance creation 14 A a = new A();
|
||||
[LibrarySecondaryConstructorUsages.1.java] Unclassified usage 10 super();
|
||||
[LibrarySecondaryConstructorUsages.1.java] Unclassified usage 6 public J() {
|
||||
[]library.kt] New inst...> but was:<... 13 class Y(): A()
|
||||
[[]library.kt] New inst...>
|
||||
Vendored
+2
-2
@@ -1,6 +1,6 @@
|
||||
package usages
|
||||
package usages;
|
||||
|
||||
import library.*
|
||||
import library.*;
|
||||
|
||||
class J extends A {
|
||||
public J() {
|
||||
|
||||
Vendored
+4
-1
@@ -1,4 +1,7 @@
|
||||
[LibrarySecondaryConstructorUsages.0.kt] New instance creation 16 val a: A = A()
|
||||
[LibrarySecondaryConstructorUsages.0.kt] Supertype 13 class Y(): A()
|
||||
[LibrarySecondaryConstructorUsages.1.java] New instance creation 14 A a = new A();
|
||||
[LibrarySecondaryConstructorUsages.1.java] Unclassified usage 10 super();
|
||||
[LibrarySecondaryConstructorUsages.1.java] Unclassified usage 6 public J() {
|
||||
[library.kt] New instance creation 58 val aa = A()
|
||||
[library.kt] Supertype 39 class CC(): A() {
|
||||
[library.kt] Supertype 39 class CC(): A() {
|
||||
+20
-8
@@ -5,8 +5,7 @@
|
||||
|
||||
package org.jetbrains.kotlin.idea.decompiler.navigation
|
||||
|
||||
import com.intellij.psi.PsiElement
|
||||
import com.intellij.psi.PsiFile
|
||||
import com.intellij.psi.*
|
||||
import com.intellij.psi.impl.source.resolve.reference.impl.PsiMultiReference
|
||||
import junit.framework.TestCase
|
||||
import org.jetbrains.kotlin.idea.navigation.NavigationTestUtils
|
||||
@@ -22,7 +21,8 @@ abstract class AbstractNavigateToLibraryTest : KotlinLightCodeInsightFixtureTest
|
||||
|
||||
protected fun doTest(path: String) {
|
||||
myFixture.configureByFile(fileName())
|
||||
NavigationChecker.checkAnnotatedCode(file, File(path.replace(".kt", expectedFileExt)))
|
||||
val pathOfExpect = path.replace(Regex("\\.kt|\\.java"), expectedFileExt)
|
||||
NavigationChecker.checkAnnotatedCode(file, File(pathOfExpect))
|
||||
}
|
||||
|
||||
override fun tearDown() {
|
||||
@@ -55,6 +55,18 @@ abstract class AbstractNavigateToLibrarySourceTest : AbstractNavigateToLibraryTe
|
||||
}
|
||||
}
|
||||
|
||||
abstract class AbstractNavigateJavaToLibrarySourceTest : AbstractNavigateToLibraryTest() {
|
||||
override val expectedFileExt: String get() = ".source.expected"
|
||||
|
||||
override fun getProjectDescriptor(): KotlinLightProjectDescriptor = PROJECT_DESCRIPTOR
|
||||
|
||||
protected companion object {
|
||||
val PROJECT_DESCRIPTOR = SdkAndMockLibraryProjectDescriptor(
|
||||
PluginTestCaseBase.getTestDataPathBase() + "/decompiler/navigation/fromJavaSource", true
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
abstract class AbstractNavigateToLibrarySourceTestWithJS : AbstractNavigateToLibrarySourceTest() {
|
||||
override fun getProjectDescriptor(): KotlinLightProjectDescriptor = KotlinMultiModuleProjectDescriptor(
|
||||
"AbstractNavigateToLibrarySourceTestWithJS",
|
||||
@@ -74,13 +86,13 @@ class NavigationChecker(val file: PsiFile, val referenceTargetChecker: (PsiEleme
|
||||
target!!.navigationElement
|
||||
}
|
||||
|
||||
private fun collectInterestingReferences(): Collection<KtReference> {
|
||||
val referenceContainersToReferences = LinkedHashMap<PsiElement, KtReference>()
|
||||
private fun collectInterestingReferences(): Collection<PsiReference> {
|
||||
val referenceContainersToReferences = LinkedHashMap<PsiElement, PsiReference>()
|
||||
for (offset in 0 until file.textLength) {
|
||||
val refs = when (val ref = file.findReferenceAt(offset)) {
|
||||
is KtReference -> listOf(ref)
|
||||
is KtReference, is PsiReferenceExpression, is PsiJavaCodeReferenceElement -> listOf(ref)
|
||||
is PsiMultiReference -> ref.references.filterIsInstance<KtReference>()
|
||||
else -> emptyList<KtReference>()
|
||||
else -> emptyList()
|
||||
}
|
||||
|
||||
refs.forEach { referenceContainersToReferences.addReference(it) }
|
||||
@@ -88,7 +100,7 @@ class NavigationChecker(val file: PsiFile, val referenceTargetChecker: (PsiEleme
|
||||
return referenceContainersToReferences.values
|
||||
}
|
||||
|
||||
private fun MutableMap<PsiElement, KtReference>.addReference(ref: KtReference) {
|
||||
private fun MutableMap<PsiElement, PsiReference>.addReference(ref: PsiReference) {
|
||||
if (containsKey(ref.element)) return
|
||||
val target = ref.resolve() ?: return
|
||||
|
||||
|
||||
+47
@@ -0,0 +1,47 @@
|
||||
/*
|
||||
* Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.idea.decompiler.navigation;
|
||||
|
||||
import com.intellij.testFramework.TestDataPath;
|
||||
import org.jetbrains.kotlin.test.JUnit3RunnerWithInners;
|
||||
import org.jetbrains.kotlin.test.KotlinTestUtils;
|
||||
import org.jetbrains.kotlin.test.MuteExtraSuffix;
|
||||
import org.jetbrains.kotlin.test.TestMetadata;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
/** This class is generated by {@link org.jetbrains.kotlin.generators.tests.TestsPackage}. DO NOT MODIFY MANUALLY */
|
||||
@SuppressWarnings("all")
|
||||
@TestMetadata("idea/testData/decompiler/navigation/userJavaCode")
|
||||
@TestDataPath("$PROJECT_ROOT")
|
||||
@MuteExtraSuffix(".libsrc")
|
||||
@RunWith(JUnit3RunnerWithInners.class)
|
||||
public class NavigateJavaToLibrarySourceTestGenerated extends AbstractNavigateJavaToLibrarySourceTest {
|
||||
private void runTest(String testDataFilePath) throws Exception {
|
||||
KotlinTestUtils.runTest(this::doTest, this, testDataFilePath);
|
||||
}
|
||||
|
||||
public void testAllFilesPresentInUserJavaCode() throws Exception {
|
||||
KotlinTestUtils.assertAllTestsPresentByMetadataWithExcluded(this.getClass(), new File("idea/testData/decompiler/navigation/userJavaCode"), Pattern.compile("^(.+)\\.java$"), null, true);
|
||||
}
|
||||
|
||||
@TestMetadata("ClassAndConstuctors.java")
|
||||
public void testClassAndConstuctors() throws Exception {
|
||||
runTest("idea/testData/decompiler/navigation/userJavaCode/ClassAndConstuctors.java");
|
||||
}
|
||||
|
||||
@TestMetadata("OverloadedFun.java")
|
||||
public void testOverloadedFun() throws Exception {
|
||||
runTest("idea/testData/decompiler/navigation/userJavaCode/OverloadedFun.java");
|
||||
}
|
||||
|
||||
@TestMetadata("RenamedElements.java")
|
||||
public void testRenamedElements() throws Exception {
|
||||
runTest("idea/testData/decompiler/navigation/userJavaCode/RenamedElements.java");
|
||||
}
|
||||
}
|
||||
@@ -19,4 +19,9 @@ org.jetbrains.kotlin.idea.completion.test.JvmBasicCompletionTestGenerated.Java.S
|
||||
org.jetbrains.kotlin.idea.completion.test.JvmBasicCompletionTestGenerated.Java.SyntheticExtensions.testSmartCast2, KT-32919
|
||||
org.jetbrains.kotlin.idea.completion.test.JvmBasicCompletionTestGenerated.Java.SyntheticExtensions.testSyntheticExtensions1, KT-32919
|
||||
org.jetbrains.kotlin.idea.completion.test.weighers.BasicCompletionWeigherTestGenerated.testPreferFromJdk, KT-35709 Class from JDK is not prioritized
|
||||
org.jetbrains.kotlin.idea.quickfix.QuickFixMultiFileTestGenerated.AutoImports.testAmbiguousNamePreferFromJdk, KT-35709 Class from JDK is not prioritized
|
||||
org.jetbrains.kotlin.idea.quickfix.QuickFixMultiFileTestGenerated.AutoImports.testAmbiguousNamePreferFromJdk, KT-35709 Class from JDK is not prioritized
|
||||
org.jetbrains.kotlin.findUsages.KotlinFindUsagesWithLibraryTestGenerated.KotlinLibrary.testLibrarySecondaryConstructorUsages, KT-34542, FAIL
|
||||
org.jetbrains.kotlin.findUsages.KotlinFindUsagesWithLibraryTestGenerated.KotlinLibrary.testLibraryNestedClassSecondaryConstructorUsages, KT-34542, FAIL
|
||||
org.jetbrains.kotlin.idea.decompiler.navigation.NavigateJavaToLibrarySourceTestGenerated.testClassAndConstuctors, KT-34542, FAIL
|
||||
org.jetbrains.kotlin.idea.decompiler.navigation.NavigateJavaToLibrarySourceTestGenerated.testOverloadedFun, KT-34542, FAIL
|
||||
org.jetbrains.kotlin.idea.decompiler.navigation.NavigateJavaToLibrarySourceTestGenerated.testRenamedElements, KT-34542, FAIL
|
||||
Reference in New Issue
Block a user