KT-13780 No completion and assertion error in log

#KT-13780 Fixed
This commit is contained in:
Valentin Kipyatkov
2016-10-07 17:52:29 +03:00
parent 09a3741eb9
commit 7b12dd498f
20 changed files with 94 additions and 24 deletions
@@ -27,12 +27,10 @@ import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
import org.jetbrains.kotlin.incremental.components.NoLookupLocation import org.jetbrains.kotlin.incremental.components.NoLookupLocation
import org.jetbrains.kotlin.load.java.JvmAbi import org.jetbrains.kotlin.load.java.JvmAbi
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.psi.KtElement import org.jetbrains.kotlin.psi.KtElement
import org.jetbrains.kotlin.resolve.DescriptorFactory import org.jetbrains.kotlin.resolve.DescriptorFactory
import org.jetbrains.kotlin.resolve.DescriptorUtils import org.jetbrains.kotlin.resolve.DescriptorUtils
import org.jetbrains.kotlin.resolve.PropertyImportedFromObject import org.jetbrains.kotlin.resolve.PropertyImportedFromObject
import org.jetbrains.kotlin.resolve.descriptorUtil.builtIns
import org.jetbrains.kotlin.resolve.descriptorUtil.getSuperClassNotAny import org.jetbrains.kotlin.resolve.descriptorUtil.getSuperClassNotAny
import org.jetbrains.kotlin.resolve.jvm.AsmTypes.* import org.jetbrains.kotlin.resolve.jvm.AsmTypes.*
import org.jetbrains.kotlin.resolve.jvm.diagnostics.JvmDeclarationOrigin import org.jetbrains.kotlin.resolve.jvm.diagnostics.JvmDeclarationOrigin
@@ -224,7 +222,7 @@ class PropertyReferenceCodegen(
@JvmStatic @JvmStatic
fun createFakeOpenDescriptor(getFunction: FunctionDescriptor, classDescriptor: ClassDescriptor): FunctionDescriptor { fun createFakeOpenDescriptor(getFunction: FunctionDescriptor, classDescriptor: ClassDescriptor): FunctionDescriptor {
val copy = getFunction.original.copy(classDescriptor, Modality.OPEN, getFunction.visibility, getFunction.kind, false) val copy = getFunction.original.copy(classDescriptor, Modality.OPEN, getFunction.visibility, getFunction.kind, false)
return copy.substitute(ANY_SUBSTITUTOR) return copy.substitute(ANY_SUBSTITUTOR)!!
} }
@JvmStatic @JvmStatic
@@ -364,7 +364,7 @@ class JavaSyntheticPropertiesScope(storageManager: StorageManager, private val l
} }
val classParametersSubstitutor = TypeSubstitutor.create(substitutionMap) val classParametersSubstitutor = TypeSubstitutor.create(substitutionMap)
descriptor.getMethod = getMethod.substitute(classParametersSubstitutor) descriptor.getMethod = getMethod.substitute(classParametersSubstitutor) ?: return null
descriptor.setMethod = setMethod?.substitute(classParametersSubstitutor) descriptor.setMethod = setMethod?.substitute(classParametersSubstitutor)
return descriptor return descriptor
} }
@@ -181,7 +181,7 @@ class SamAdapterFunctionsScope(
TypeConstructorSubstitution.createByConstructorsMap( TypeConstructorSubstitution.createByConstructorsMap(
substitutionMap, configuration.substitution.approximateCapturedTypes()).buildSubstitutor() substitutionMap, configuration.substitution.approximateCapturedTypes()).buildSubstitutor()
descriptor.baseDescriptorForSynthetic = original.baseDescriptorForSynthetic.substitute(sourceFunctionSubstitutor) descriptor.baseDescriptorForSynthetic = original.baseDescriptorForSynthetic.substitute(sourceFunctionSubstitutor) ?: return null
return descriptor return descriptor
} }
@@ -31,7 +31,7 @@ class FunctionImportedFromObject(functionFromObject: FunctionDescriptor) :
ImportedFromObjectCallableDescriptor<FunctionDescriptor>(functionFromObject) { ImportedFromObjectCallableDescriptor<FunctionDescriptor>(functionFromObject) {
override fun getDispatchReceiverParameter(): ReceiverParameterDescriptor? = null override fun getDispatchReceiverParameter(): ReceiverParameterDescriptor? = null
override fun substitute(substitutor: TypeSubstitutor) = callableFromObject.substitute(substitutor).wrap() override fun substitute(substitutor: TypeSubstitutor) = callableFromObject.substitute(substitutor)?.wrap()
private val _original by lazy { private val _original by lazy {
functionFromObject.original.wrap() functionFromObject.original.wrap()
@@ -53,7 +53,7 @@ fun createSynthesizedInvokes(functions: Collection<FunctionDescriptor>): Collect
fakeOverride fakeOverride
} }
result.add(synthesized.substitute(TypeSubstitutor.create(invoke.getDispatchReceiverParameter()!!.type))) result.add(synthesized.substitute(TypeSubstitutor.create(invoke.getDispatchReceiverParameter()!!.type)) ?: continue)
} }
return result return result
@@ -24,7 +24,7 @@ interface ClassConstructorDescriptor : ConstructorDescriptor {
override fun getOriginal(): ClassConstructorDescriptor override fun getOriginal(): ClassConstructorDescriptor
override fun substitute(substitutor: TypeSubstitutor): ClassConstructorDescriptor override fun substitute(substitutor: TypeSubstitutor): ClassConstructorDescriptor?
override fun copy( override fun copy(
newOwner: DeclarationDescriptor, newOwner: DeclarationDescriptor,
@@ -17,6 +17,7 @@
package org.jetbrains.kotlin.descriptors; package org.jetbrains.kotlin.descriptors;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.name.Name; import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.types.KotlinType; import org.jetbrains.kotlin.types.KotlinType;
import org.jetbrains.kotlin.types.TypeSubstitutor; import org.jetbrains.kotlin.types.TypeSubstitutor;
@@ -43,7 +44,7 @@ public interface ConstructorDescriptor extends FunctionDescriptor {
@Override @Override
ConstructorDescriptor getOriginal(); ConstructorDescriptor getOriginal();
@NotNull @Nullable
@Override @Override
ConstructorDescriptor substitute(@NotNull TypeSubstitutor substitutor); ConstructorDescriptor substitute(@NotNull TypeSubstitutor substitutor);
@@ -19,7 +19,6 @@ package org.jetbrains.kotlin.descriptors;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.descriptors.annotations.Annotations; import org.jetbrains.kotlin.descriptors.annotations.Annotations;
import org.jetbrains.kotlin.descriptors.impl.FunctionDescriptorImpl;
import org.jetbrains.kotlin.name.Name; import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.types.KotlinType; import org.jetbrains.kotlin.types.KotlinType;
import org.jetbrains.kotlin.types.TypeSubstitution; import org.jetbrains.kotlin.types.TypeSubstitution;
@@ -37,7 +36,7 @@ public interface FunctionDescriptor extends CallableMemberDescriptor {
@Override @Override
FunctionDescriptor getOriginal(); FunctionDescriptor getOriginal();
@NotNull @Nullable
@Override @Override
FunctionDescriptor substitute(@NotNull TypeSubstitutor substitutor); FunctionDescriptor substitute(@NotNull TypeSubstitutor substitutor);
@@ -106,7 +106,7 @@ public class ClassConstructorDescriptorImpl extends FunctionDescriptorImpl imple
return (ClassConstructorDescriptor) super.getOriginal(); return (ClassConstructorDescriptor) super.getOriginal();
} }
@NotNull @Nullable
@Override @Override
public ClassConstructorDescriptor substitute(@NotNull TypeSubstitutor originalSubstitutor) { public ClassConstructorDescriptor substitute(@NotNull TypeSubstitutor originalSubstitutor) {
return (ClassConstructorDescriptor) super.substitute(originalSubstitutor); return (ClassConstructorDescriptor) super.substitute(originalSubstitutor);
@@ -153,7 +153,7 @@ class LookupElementFactory(
//TODO: order for them //TODO: order for them
val fuzzyParameterType = parameterType.toFuzzyType(descriptor.typeParameters) val fuzzyParameterType = parameterType.toFuzzyType(descriptor.typeParameters)
for ((variable, substitutor) in contextVariablesProvider.functionTypeVariables(fuzzyParameterType)) { for ((variable, substitutor) in contextVariablesProvider.functionTypeVariables(fuzzyParameterType)) {
val substitutedDescriptor = descriptor.substitute(substitutor) val substitutedDescriptor = descriptor.substitute(substitutor) ?: continue
add(createFunctionCallElementWithArguments(substitutedDescriptor, variable.name.render(), useReceiverTypes)) add(createFunctionCallElementWithArguments(substitutedDescriptor, variable.name.render(), useReceiverTypes))
} }
} }
@@ -210,7 +210,7 @@ class TypeInstantiationItems(
1 -> { 1 -> {
val constructor = visibleConstructors.single() val constructor = visibleConstructors.single()
val substitutor = TypeSubstitutor.create(fuzzyType.presentationType()) val substitutor = TypeSubstitutor.create(fuzzyType.presentationType())
val substitutedConstructor = constructor.substitute(substitutor) val substitutedConstructor = constructor.substitute(substitutor) ?: constructor // render original signature if failed to substitute
BasicLookupElementFactory.SHORT_NAMES_RENDERER.renderFunctionParameters(substitutedConstructor) BasicLookupElementFactory.SHORT_NAMES_RENDERER.renderFunctionParameters(substitutedConstructor)
} }
+9
View File
@@ -0,0 +1,9 @@
class ResolvedCall<out D>(val candidateDescriptor: D)
fun test(myResolvedCall: ResolvedCall<String>) {
bar(my<caret>)
}
fun bar(foo: ResolvedCall<*>) {}
// EXIST: myResolvedCall
@@ -0,0 +1,9 @@
class ResolvedCall<out D>(val candidateDescriptor: D)
fun test(myResolvedCall: ResolvedCall<Any>) {
bar(my<caret>)
}
fun bar(foo: ResolvedCall<out CharSequence>) {}
// EXIST: myResolvedCall
@@ -0,0 +1,9 @@
class X<D>()
fun test() {
bar(<caret>)
}
fun bar(foo: X<*>) {}
// EXIST: { lookupString:"X", itemText:"X", tailText:"() (<root>)" }
@@ -0,0 +1,9 @@
class X<D>(d: D)
fun test() {
bar(<caret>)
}
fun bar(foo: X<*>) {}
// EXIST: { lookupString:"X", itemText:"X", tailText:"(d: D) (<root>)" }
@@ -493,6 +493,18 @@ public class JSBasicCompletionTestGenerated extends AbstractJSBasicCompletionTes
doTest(fileName); doTest(fileName);
} }
@TestMetadata("KT13780.kt")
public void testKT13780() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/KT13780.kt");
doTest(fileName);
}
@TestMetadata("KT13780_1.kt")
public void testKT13780_1() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/KT13780_1.kt");
doTest(fileName);
}
@TestMetadata("LocalMultideclarationValues.kt") @TestMetadata("LocalMultideclarationValues.kt")
public void testLocalMultideclarationValues() throws Exception { public void testLocalMultideclarationValues() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/LocalMultideclarationValues.kt"); String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/LocalMultideclarationValues.kt");
@@ -493,6 +493,18 @@ public class JvmBasicCompletionTestGenerated extends AbstractJvmBasicCompletionT
doTest(fileName); doTest(fileName);
} }
@TestMetadata("KT13780.kt")
public void testKT13780() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/KT13780.kt");
doTest(fileName);
}
@TestMetadata("KT13780_1.kt")
public void testKT13780_1() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/KT13780_1.kt");
doTest(fileName);
}
@TestMetadata("LocalMultideclarationValues.kt") @TestMetadata("LocalMultideclarationValues.kt")
public void testLocalMultideclarationValues() throws Exception { public void testLocalMultideclarationValues() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/LocalMultideclarationValues.kt"); String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/LocalMultideclarationValues.kt");
@@ -874,6 +874,18 @@ public class JvmSmartCompletionTestGenerated extends AbstractJvmSmartCompletionT
doTest(fileName); doTest(fileName);
} }
@TestMetadata("StarProjection1.kt")
public void testStarProjection1() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/smart/constructor/StarProjection1.kt");
doTest(fileName);
}
@TestMetadata("StarProjection2.kt")
public void testStarProjection2() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/smart/constructor/StarProjection2.kt");
doTest(fileName);
}
@TestMetadata("WithParameters.kt") @TestMetadata("WithParameters.kt")
public void testWithParameters() throws Exception { public void testWithParameters() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/smart/constructor/WithParameters.kt"); String fileName = KotlinTestUtils.navigationMetadata("idea/idea-completion/testData/smart/constructor/WithParameters.kt");
@@ -29,6 +29,7 @@ import org.jetbrains.kotlin.types.TypeSubstitutor
import org.jetbrains.kotlin.types.typeUtil.TypeNullability import org.jetbrains.kotlin.types.typeUtil.TypeNullability
import org.jetbrains.kotlin.util.OperatorNameConventions import org.jetbrains.kotlin.util.OperatorNameConventions
import org.jetbrains.kotlin.util.isValidOperator import org.jetbrains.kotlin.util.isValidOperator
import org.jetbrains.kotlin.utils.addIfNotNull
import java.util.* import java.util.*
abstract class TypesWithOperatorDetector( abstract class TypesWithOperatorDetector(
@@ -70,7 +71,7 @@ abstract class TypesWithOperatorDetector(
} }
val substitutor = checkIsSuitableByType(function, freeParameters) ?: continue val substitutor = checkIsSuitableByType(function, freeParameters) ?: continue
add(function.substitute(substitutor)) addIfNotNull(function.substitute(substitutor))
} }
return this return this
} }
@@ -90,18 +91,17 @@ abstract class TypesWithOperatorDetector(
if (type.nullability() != TypeNullability.NULLABLE) { if (type.nullability() != TypeNullability.NULLABLE) {
for (memberFunction in type.type.memberScope.getContributedFunctions(name, NoLookupLocation.FROM_IDE)) { for (memberFunction in type.type.memberScope.getContributedFunctions(name, NoLookupLocation.FROM_IDE)) {
if (memberFunction.isValidOperator()) { if (memberFunction.isValidOperator()) {
checkIsSuitableByType(memberFunction, type.freeParameters)?.let { substitutor -> val substitutor = checkIsSuitableByType(memberFunction, type.freeParameters) ?: continue
return Pair(memberFunction.substitute(substitutor), substitutor) val substituted = memberFunction.substitute(substitutor) ?: continue
} return substituted to substitutor
} }
} }
} }
for (operator in extensionOperators) { for (operator in extensionOperators) {
val substitutor = type.checkIsSubtypeOf(operator.fuzzyExtensionReceiverType()!!) val substitutor = type.checkIsSubtypeOf(operator.fuzzyExtensionReceiverType()!!) ?: continue
if (substitutor != null) { val substituted = operator.substitute(substitutor) ?: continue
return Pair(operator.substitute(substitutor), substitutor) return substituted to substitutor
}
} }
return null return null
@@ -29,11 +29,11 @@ import org.jetbrains.kotlin.diagnostics.Diagnostic
import org.jetbrains.kotlin.idea.caches.resolve.analyze import org.jetbrains.kotlin.idea.caches.resolve.analyze
import org.jetbrains.kotlin.idea.caches.resolve.getResolutionFacade import org.jetbrains.kotlin.idea.caches.resolve.getResolutionFacade
import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptor import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptor
import org.jetbrains.kotlin.idea.core.ShortenReferences
import org.jetbrains.kotlin.idea.core.isVisible import org.jetbrains.kotlin.idea.core.isVisible
import org.jetbrains.kotlin.idea.core.moveCaret import org.jetbrains.kotlin.idea.core.moveCaret
import org.jetbrains.kotlin.idea.core.replaced import org.jetbrains.kotlin.idea.core.replaced
import org.jetbrains.kotlin.idea.util.IdeDescriptorRenderers import org.jetbrains.kotlin.idea.util.IdeDescriptorRenderers
import org.jetbrains.kotlin.idea.core.ShortenReferences
import org.jetbrains.kotlin.psi.* import org.jetbrains.kotlin.psi.*
import org.jetbrains.kotlin.psi.psiUtil.endOffset import org.jetbrains.kotlin.psi.psiUtil.endOffset
import org.jetbrains.kotlin.renderer.DescriptorRenderer import org.jetbrains.kotlin.renderer.DescriptorRenderer
@@ -72,7 +72,7 @@ object SuperClassNotInitialized : KotlinIntentionActionsFactory() {
val substitutedConstructors = constructors val substitutedConstructors = constructors
.filter { it.valueParameters.isNotEmpty() } .filter { it.valueParameters.isNotEmpty() }
.map { it.substitute(substitutor) } .mapNotNull { it.substitute(substitutor) }
if (substitutedConstructors.isNotEmpty()) { if (substitutedConstructors.isNotEmpty()) {
val parameterTypes: List<List<KotlinType>> = substitutedConstructors.map { val parameterTypes: List<List<KotlinType>> = substitutedConstructors.map {