KT-8530 Synthetic properties doesn't work with smart casts
#KT-8530 Fixed
This commit is contained in:
+26
-10
@@ -36,7 +36,7 @@ import org.jetbrains.kotlin.types.typeUtil.isUnit
|
||||
import org.jetbrains.kotlin.types.typeUtil.makeNotNullable
|
||||
import org.jetbrains.kotlin.utils.addIfNotNull
|
||||
import java.beans.Introspector
|
||||
import java.util.ArrayList
|
||||
import java.util.*
|
||||
|
||||
interface SyntheticJavaPropertyDescriptor : PropertyDescriptor {
|
||||
val getMethod: FunctionDescriptor
|
||||
@@ -52,7 +52,7 @@ interface SyntheticJavaPropertyDescriptor : PropertyDescriptor {
|
||||
val owner = getterOrSetter.getContainingDeclaration()
|
||||
if (owner !is JavaClassDescriptor) return null
|
||||
|
||||
return resolutionScope.getSyntheticExtensionProperties(owner.getDefaultType())
|
||||
return resolutionScope.getSyntheticExtensionProperties(listOf(owner.getDefaultType()))
|
||||
.filterIsInstance<SyntheticJavaPropertyDescriptor>()
|
||||
.firstOrNull { getterOrSetter == it.getMethod || getterOrSetter == it.setMethod }
|
||||
}
|
||||
@@ -136,11 +136,22 @@ class JavaSyntheticExtensionsScope(storageManager: StorageManager) : JetScope by
|
||||
&& descriptor.getVisibility() == Visibilities.PUBLIC
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor> {
|
||||
return collectSyntheticPropertiesByName(null, receiverType.makeNotNullable(), name) ?: emptyList()
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor> {
|
||||
var result: SmartList<PropertyDescriptor>? = null
|
||||
val processedTypes: MutableSet<JetType>? = if (receiverTypes.size() > 1) HashSet<JetType>() else null
|
||||
receiverTypes.forEach {
|
||||
result = collectSyntheticPropertiesByName(result, it.makeNotNullable(), name, processedTypes)
|
||||
}
|
||||
return when {
|
||||
result == null -> emptyList()
|
||||
result!!.size() > 1 -> result!!.toSet()
|
||||
else -> result!!
|
||||
}
|
||||
}
|
||||
|
||||
private fun collectSyntheticPropertiesByName(result: SmartList<PropertyDescriptor>?, type: JetType, name: Name): SmartList<PropertyDescriptor>? {
|
||||
private fun collectSyntheticPropertiesByName(result: SmartList<PropertyDescriptor>?, type: JetType, name: Name, processedTypes: MutableSet<JetType>?): SmartList<PropertyDescriptor>? {
|
||||
if (processedTypes != null && !processedTypes.add(type)) return result
|
||||
|
||||
@suppress("NAME_SHADOWING")
|
||||
var result = result
|
||||
|
||||
@@ -150,18 +161,23 @@ class JavaSyntheticExtensionsScope(storageManager: StorageManager) : JetScope by
|
||||
result = result.add(syntheticPropertyInClass(Triple(classifier, type, name)))
|
||||
}
|
||||
|
||||
typeConstructor.getSupertypes().forEach { result = collectSyntheticPropertiesByName(result, it, name) }
|
||||
typeConstructor.getSupertypes().forEach { result = collectSyntheticPropertiesByName(result, it, name, processedTypes) }
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor> {
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor> {
|
||||
val result = ArrayList<PropertyDescriptor>()
|
||||
result.collectSyntheticProperties(receiverType.makeNotNullable())
|
||||
val processedTypes = HashSet<JetType>()
|
||||
receiverTypes.forEach {
|
||||
result.collectSyntheticProperties(it.makeNotNullable(), processedTypes)
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
private fun MutableList<PropertyDescriptor>.collectSyntheticProperties(type: JetType) {
|
||||
private fun MutableList<PropertyDescriptor>.collectSyntheticProperties(type: JetType, processedTypes: MutableSet<JetType>) {
|
||||
if (!processedTypes.add(type)) return
|
||||
|
||||
val typeConstructor = type.getConstructor()
|
||||
val classifier = typeConstructor.getDeclarationDescriptor()
|
||||
if (classifier is JavaClassDescriptor) {
|
||||
@@ -173,7 +189,7 @@ class JavaSyntheticExtensionsScope(storageManager: StorageManager) : JetScope by
|
||||
}
|
||||
}
|
||||
|
||||
typeConstructor.getSupertypes().forEach { collectSyntheticProperties(it) }
|
||||
typeConstructor.getSupertypes().forEach { collectSyntheticProperties(it, processedTypes) }
|
||||
}
|
||||
|
||||
private fun SmartList<PropertyDescriptor>?.add(property: PropertyDescriptor?): SmartList<PropertyDescriptor>? {
|
||||
|
||||
@@ -53,12 +53,12 @@ class AllUnderImportsScope : JetScope {
|
||||
return scopes.flatMap { it.getFunctions(name) }
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor> {
|
||||
return scopes.flatMap { it.getSyntheticExtensionProperties(receiverType, name) }
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor> {
|
||||
return scopes.flatMap { it.getSyntheticExtensionProperties(receiverTypes, name) }
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor> {
|
||||
return scopes.flatMap { it.getSyntheticExtensionProperties(receiverType) }
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor> {
|
||||
return scopes.flatMap { it.getSyntheticExtensionProperties(receiverTypes) }
|
||||
}
|
||||
|
||||
override fun getPackage(name: Name): PackageViewDescriptor? = null // packages are not imported by all under imports
|
||||
|
||||
+8
-8
@@ -39,7 +39,7 @@ public trait CallableDescriptorCollector<D : CallableDescriptor> {
|
||||
|
||||
public fun getStaticMembersByName(receiver: JetType, name: Name, bindingTrace: BindingTrace): Collection<D>
|
||||
|
||||
public fun getExtensionsByName(scope: JetScope, name: Name, receiver: JetType, bindingTrace: BindingTrace): Collection<D>
|
||||
public fun getExtensionsByName(scope: JetScope, name: Name, receiverTypes: Collection<JetType>, bindingTrace: BindingTrace): Collection<D>
|
||||
}
|
||||
|
||||
private fun <D : CallableDescriptor> CallableDescriptorCollector<D>.withDefaultFilter() = filtered { !LibrarySourceHacks.shouldSkip(it) }
|
||||
@@ -97,7 +97,7 @@ private object FunctionCollector : CallableDescriptorCollector<FunctionDescripto
|
||||
return getConstructors(receiver.getMemberScope(), name, { isStaticNestedClass(it) })
|
||||
}
|
||||
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiver: JetType, bindingTrace: BindingTrace): Collection<FunctionDescriptor> {
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiverTypes: Collection<JetType>, bindingTrace: BindingTrace): Collection<FunctionDescriptor> {
|
||||
val functions = scope.getFunctions(name)
|
||||
val (extensions, nonExtensions) = functions.partition { it.getExtensionReceiverParameter() != null }
|
||||
|
||||
@@ -151,9 +151,9 @@ private object VariableCollector : CallableDescriptorCollector<VariableDescripto
|
||||
return listOf()
|
||||
}
|
||||
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiver: JetType, bindingTrace: BindingTrace): Collection<VariableDescriptor> {
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiverTypes: Collection<JetType>, bindingTrace: BindingTrace): Collection<VariableDescriptor> {
|
||||
// property may have an extension function type, we check the applicability later to avoid an early computing of deferred types
|
||||
return (listOf(scope.getLocalVariable(name)) + scope.getProperties(name) + scope.getSyntheticExtensionProperties(receiver, name)).filterNotNull()
|
||||
return (listOf(scope.getLocalVariable(name)) + scope.getProperties(name) + scope.getSyntheticExtensionProperties(receiverTypes, name)).filterNotNull()
|
||||
}
|
||||
|
||||
override fun toString() = "VARIABLES"
|
||||
@@ -175,8 +175,8 @@ private object PropertyCollector : CallableDescriptorCollector<VariableDescripto
|
||||
return filterProperties(VARIABLES_COLLECTOR.getStaticMembersByName(receiver, name, bindingTrace))
|
||||
}
|
||||
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiver: JetType, bindingTrace: BindingTrace): Collection<VariableDescriptor> {
|
||||
return filterProperties(VARIABLES_COLLECTOR.getExtensionsByName(scope, name, receiver, bindingTrace))
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiverTypes: Collection<JetType>, bindingTrace: BindingTrace): Collection<VariableDescriptor> {
|
||||
return filterProperties(VARIABLES_COLLECTOR.getExtensionsByName(scope, name, receiverTypes, bindingTrace))
|
||||
}
|
||||
|
||||
override fun toString() = "PROPERTIES"
|
||||
@@ -197,8 +197,8 @@ private fun <D : CallableDescriptor> CallableDescriptorCollector<D>.filtered(fil
|
||||
return delegate.getStaticMembersByName(receiver, name, bindingTrace).filter(filter)
|
||||
}
|
||||
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiver: JetType, bindingTrace: BindingTrace): Collection<D> {
|
||||
return delegate.getExtensionsByName(scope, name, receiver, bindingTrace).filter(filter)
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiverTypes: Collection<JetType>, bindingTrace: BindingTrace): Collection<D> {
|
||||
return delegate.getExtensionsByName(scope, name, receiverTypes, bindingTrace).filter(filter)
|
||||
}
|
||||
|
||||
override fun toString(): String {
|
||||
|
||||
@@ -18,9 +18,9 @@ package org.jetbrains.kotlin.resolve.calls.tasks
|
||||
|
||||
import com.google.common.collect.Lists
|
||||
import com.google.common.collect.Sets
|
||||
import org.jetbrains.kotlin.progress.ProgressIndicatorAndCompilationCanceledStatus
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.progress.ProgressIndicatorAndCompilationCanceledStatus
|
||||
import org.jetbrains.kotlin.psi.Call
|
||||
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
||||
import org.jetbrains.kotlin.resolve.calls.callResolverUtil.isOrOverridesSynthesized
|
||||
@@ -41,6 +41,7 @@ import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue
|
||||
import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue.NO_RECEIVER
|
||||
import org.jetbrains.kotlin.storage.StorageManager
|
||||
import org.jetbrains.kotlin.types.ErrorUtils
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.types.checker.JetTypeChecker
|
||||
import org.jetbrains.kotlin.types.expressions.ExpressionTypingUtils
|
||||
import org.jetbrains.kotlin.types.isDynamic
|
||||
@@ -119,8 +120,9 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
}
|
||||
val implicitReceivers = Sets.newLinkedHashSet<ReceiverValue>(JetScopeUtils.getImplicitReceiversHierarchyValues(c.scope))
|
||||
if (receiver.exists()) {
|
||||
addCandidatesForExplicitReceiver(receiver, implicitReceivers, c, isExplicit = true)
|
||||
addMembers(receiver, c, staticMembers = true, isExplicit = true)
|
||||
val receiverTypes = SmartCastUtils.getSmartCastVariants(receiver, c.context)
|
||||
addCandidatesForExplicitReceiver(receiver, receiverTypes, implicitReceivers, c, isExplicit = true)
|
||||
addMembers(receiver, receiverTypes, c, staticMembers = true, isExplicit = true)
|
||||
return
|
||||
}
|
||||
addCandidatesForNoReceiver(implicitReceivers, c)
|
||||
@@ -128,22 +130,24 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
|
||||
private fun <D : CallableDescriptor, F : D> addCandidatesForExplicitReceiver(
|
||||
explicitReceiver: ReceiverValue,
|
||||
explicitReceiverTypes: Collection<JetType>,
|
||||
implicitReceivers: Collection<ReceiverValue>,
|
||||
c: TaskPrioritizerContext<D, F>,
|
||||
isExplicit: Boolean
|
||||
) {
|
||||
addMembers(explicitReceiver, c, staticMembers = false, isExplicit = isExplicit)
|
||||
addMembers(explicitReceiver, explicitReceiverTypes, c, staticMembers = false, isExplicit = isExplicit)
|
||||
|
||||
if (explicitReceiver.getType().isDynamic()) {
|
||||
addCandidatesForDynamicReceiver(explicitReceiver, implicitReceivers, c, isExplicit)
|
||||
addCandidatesForDynamicReceiver(explicitReceiver, explicitReceiverTypes, implicitReceivers, c, isExplicit)
|
||||
}
|
||||
else {
|
||||
addExtensionCandidates(explicitReceiver, implicitReceivers, c, isExplicit)
|
||||
addExtensionCandidates(explicitReceiver, explicitReceiverTypes, implicitReceivers, c, isExplicit)
|
||||
}
|
||||
}
|
||||
|
||||
private fun <D : CallableDescriptor, F : D> addExtensionCandidates(
|
||||
explicitReceiver: ReceiverValue,
|
||||
explicitReceiverTypes: Collection<JetType>,
|
||||
implicitReceivers: Collection<ReceiverValue>,
|
||||
c: TaskPrioritizerContext<D, F>,
|
||||
isExplicit: Boolean
|
||||
@@ -154,6 +158,7 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
addMemberExtensionCandidates(
|
||||
implicitReceiver,
|
||||
explicitReceiver,
|
||||
explicitReceiverTypes,
|
||||
callableDescriptorCollector,
|
||||
c,
|
||||
createKind(EXTENSION_RECEIVER, isExplicit)
|
||||
@@ -164,7 +169,7 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
convertWithImpliedThis(
|
||||
c.scope,
|
||||
explicitReceiver,
|
||||
callableDescriptorCollector.getExtensionsByName(c.scope, c.name, explicitReceiver.getType(), c.context.trace),
|
||||
callableDescriptorCollector.getExtensionsByName(c.scope, c.name, explicitReceiverTypes, c.context.trace),
|
||||
createKind(EXTENSION_RECEIVER, isExplicit),
|
||||
c.context.call
|
||||
)
|
||||
@@ -174,15 +179,15 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
|
||||
private fun <D : CallableDescriptor, F : D> addMembers(
|
||||
explicitReceiver: ReceiverValue,
|
||||
explicitReceiverTypes: Collection<JetType>,
|
||||
c: TaskPrioritizerContext<D, F>,
|
||||
staticMembers: Boolean,
|
||||
isExplicit: Boolean
|
||||
) {
|
||||
for (callableDescriptorCollector in c.callableDescriptorCollectors) {
|
||||
c.result.addCandidates {
|
||||
val variantsForExplicitReceiver = SmartCastUtils.getSmartCastVariants(explicitReceiver, c.context)
|
||||
val members = Lists.newArrayList<ResolutionCandidate<D>>()
|
||||
for (type in variantsForExplicitReceiver) {
|
||||
for (type in explicitReceiverTypes) {
|
||||
val membersForThisVariant = if (staticMembers) {
|
||||
callableDescriptorCollector.getStaticMembersByName(type, c.name, c.context.trace)
|
||||
}
|
||||
@@ -205,12 +210,13 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
|
||||
private fun <D : CallableDescriptor, F : D> addCandidatesForDynamicReceiver(
|
||||
explicitReceiver: ReceiverValue,
|
||||
explicitReceiverTypes: Collection<JetType>,
|
||||
implicitReceivers: Collection<ReceiverValue>,
|
||||
c: TaskPrioritizerContext<D, F>,
|
||||
isExplicit: Boolean
|
||||
) {
|
||||
val onlyDynamicReceivers = c.replaceCollectors(c.callableDescriptorCollectors.onlyDynamicReceivers<D>())
|
||||
addExtensionCandidates(explicitReceiver, implicitReceivers, onlyDynamicReceivers, isExplicit)
|
||||
addExtensionCandidates(explicitReceiver, explicitReceiverTypes, implicitReceivers, onlyDynamicReceivers, isExplicit)
|
||||
|
||||
c.result.addCandidates {
|
||||
val dynamicScope = DynamicCallableDescriptors.createDynamicDescriptorScope(c.context.call, c.scope.getContainingDeclaration())
|
||||
@@ -231,13 +237,14 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
private fun <D : CallableDescriptor, F : D> addMemberExtensionCandidates(
|
||||
dispatchReceiver: ReceiverValue,
|
||||
receiverParameter: ReceiverValue,
|
||||
receiverParameterTypes: Collection<JetType>,
|
||||
callableDescriptorCollector: CallableDescriptorCollector<D>,
|
||||
c: TaskPrioritizerContext<D, F>,
|
||||
receiverKind: ExplicitReceiverKind
|
||||
) {
|
||||
c.result.addCandidates {
|
||||
val memberExtensions =
|
||||
callableDescriptorCollector.getExtensionsByName(dispatchReceiver.getType().getMemberScope(), c.name, receiverParameter.getType(), c.context.trace)
|
||||
callableDescriptorCollector.getExtensionsByName(dispatchReceiver.getType().getMemberScope(), c.name, receiverParameterTypes, c.context.trace)
|
||||
convertWithReceivers(memberExtensions, dispatchReceiver, receiverParameter, receiverKind, c.context.call)
|
||||
}
|
||||
}
|
||||
@@ -269,17 +276,19 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
//locals
|
||||
c.result.addCandidates(localsList)
|
||||
|
||||
val implicitReceiversWithTypes = implicitReceivers.map { it to SmartCastUtils.getSmartCastVariants(it, c.context) }
|
||||
|
||||
//try all implicit receivers as explicit
|
||||
for (implicitReceiver in implicitReceivers) {
|
||||
addCandidatesForExplicitReceiver(implicitReceiver, implicitReceivers, c, isExplicit = false)
|
||||
for ((implicitReceiver, implicitReceiverTypes) in implicitReceiversWithTypes) {
|
||||
addCandidatesForExplicitReceiver(implicitReceiver, implicitReceiverTypes, implicitReceivers, c, isExplicit = false)
|
||||
}
|
||||
|
||||
//nonlocals
|
||||
c.result.addCandidates(nonlocalsList)
|
||||
|
||||
//static (only for better error reporting)
|
||||
for (implicitReceiver in implicitReceivers) {
|
||||
addMembers(implicitReceiver, c, staticMembers = true, isExplicit = false)
|
||||
for ((implicitReceiver, implicitReceiverTypes) in implicitReceiversWithTypes) {
|
||||
addMembers(implicitReceiver, implicitReceiverTypes, c, staticMembers = true, isExplicit = false)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -297,7 +306,8 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
|
||||
// (1) a.foo + foo.invoke()
|
||||
if (!explicitReceiver.exists()) {
|
||||
addCandidatesForExplicitReceiver(variableReceiver, implicitReceivers, c, isExplicit = true)
|
||||
val variableReceiverTypes = SmartCastUtils.getSmartCastVariants(variableReceiver, c.context)
|
||||
addCandidatesForExplicitReceiver(variableReceiver, variableReceiverTypes, implicitReceivers, c, isExplicit = true)
|
||||
}
|
||||
|
||||
// (2) foo + a.invoke()
|
||||
@@ -323,8 +333,9 @@ public class TaskPrioritizer(private val storageManager: StorageManager) {
|
||||
c: TaskPrioritizerContext<D, F>,
|
||||
receiverKind: ExplicitReceiverKind
|
||||
) {
|
||||
val receiverParameterTypes = SmartCastUtils.getSmartCastVariants(receiverParameter, c.context)
|
||||
for (callableDescriptorCollector in c.callableDescriptorCollectors) {
|
||||
addMemberExtensionCandidates(dispatchReceiver, receiverParameter, callableDescriptorCollector, c, receiverKind)
|
||||
addMemberExtensionCandidates(dispatchReceiver, receiverParameter, receiverParameterTypes, callableDescriptorCollector, c, receiverKind)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -223,8 +223,8 @@ public fun DeclarationDescriptor.isDynamic(): Boolean {
|
||||
}
|
||||
|
||||
class CollectorForDynamicReceivers<D: CallableDescriptor>(val delegate: CallableDescriptorCollector<D>) : CallableDescriptorCollector<D> by delegate {
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiver: JetType, bindingTrace: BindingTrace): Collection<D> {
|
||||
return delegate.getExtensionsByName(scope, name, receiver, bindingTrace).filter {
|
||||
override fun getExtensionsByName(scope: JetScope, name: Name, receiverTypes: Collection<JetType>, bindingTrace: BindingTrace): Collection<D> {
|
||||
return delegate.getExtensionsByName(scope, name, receiverTypes, bindingTrace).filter {
|
||||
it.getExtensionReceiverParameter()?.getType()?.isDynamic() ?: false
|
||||
}
|
||||
}
|
||||
|
||||
@@ -258,18 +258,18 @@ class LazyImportScope(
|
||||
return importResolver.collectFromImports(name, LookupMode.EVERYTHING) { scope, name -> scope.getFunctions(name) }
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor> {
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor> {
|
||||
if (filteringKind == FilteringKind.INVISIBLE_CLASSES) return listOf()
|
||||
return importResolver.collectFromImports(name, LookupMode.EVERYTHING) { scope, name -> scope.getSyntheticExtensionProperties(receiverType, name) }
|
||||
return importResolver.collectFromImports(name, LookupMode.EVERYTHING) { scope, name -> scope.getSyntheticExtensionProperties(receiverTypes, name) }
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor> {
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor> {
|
||||
// we do not perform any filtering by visibility here because all descriptors from both visible/invisible filter scopes are to be added anyway
|
||||
if (filteringKind == FilteringKind.INVISIBLE_CLASSES) return listOf()
|
||||
|
||||
return importResolver.storageManager.compute {
|
||||
importResolver.indexedImports.imports.flatMapTo(LinkedHashSet<PropertyDescriptor>()) { import ->
|
||||
importResolver.getImportScope(import, LookupMode.EVERYTHING).getSyntheticExtensionProperties(receiverType)
|
||||
importResolver.getImportScope(import, LookupMode.EVERYTHING).getSyntheticExtensionProperties(receiverTypes)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,28 @@
|
||||
// FILE: KotlinFile.kt
|
||||
fun foo(o: JavaInterface2): Int {
|
||||
if (o is JavaClass) {
|
||||
<!DEBUG_INFO_SMARTCAST!>o<!>.something++
|
||||
return <!DEBUG_INFO_SMARTCAST!>o<!>.x + o.something2
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
// FILE: JavaClass.java
|
||||
public abstract class JavaClass extends BaseClass implements JavaInterface {
|
||||
public int getSomething() { return 1; }
|
||||
public void setSomething(int value) { }
|
||||
}
|
||||
|
||||
// FILE: BaseClass.java
|
||||
public abstract class BaseClass implements JavaInterface {
|
||||
}
|
||||
|
||||
// FILE: JavaInterface.java
|
||||
public interface JavaInterface {
|
||||
int getX();
|
||||
}
|
||||
|
||||
// FILE: JavaInterface2.java
|
||||
public interface JavaInterface2 {
|
||||
int getSomething2();
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
package
|
||||
|
||||
public /*synthesized*/ fun JavaInterface(/*0*/ function: () -> kotlin.Int): JavaInterface
|
||||
public /*synthesized*/ fun JavaInterface2(/*0*/ function: () -> kotlin.Int): JavaInterface2
|
||||
internal fun foo(/*0*/ o: JavaInterface2): kotlin.Int
|
||||
|
||||
public abstract class BaseClass : JavaInterface {
|
||||
public constructor BaseClass()
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public abstract override /*1*/ /*fake_override*/ fun getX(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public abstract class JavaClass : BaseClass, JavaInterface {
|
||||
public constructor JavaClass()
|
||||
public open override /*2*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open fun getSomething(): kotlin.Int
|
||||
public abstract override /*2*/ /*fake_override*/ fun getX(): kotlin.Int
|
||||
public open override /*2*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open fun setSomething(/*0*/ value: kotlin.Int): kotlin.Unit
|
||||
public open override /*2*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface JavaInterface {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public abstract fun getX(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface JavaInterface2 {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public abstract fun getSomething2(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
+23
@@ -0,0 +1,23 @@
|
||||
// FILE: KotlinFile.kt
|
||||
fun Any.foo(): Int {
|
||||
if (this is JavaClass) {
|
||||
something++
|
||||
return x
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
// FILE: JavaClass.java
|
||||
public abstract class JavaClass extends BaseClass implements JavaInterface {
|
||||
public int getSomething() { return 1; }
|
||||
public void setSomething(int value) { }
|
||||
}
|
||||
|
||||
// FILE: BaseClass.java
|
||||
public abstract class BaseClass implements JavaInterface {
|
||||
}
|
||||
|
||||
// FILE: JavaInterface.java
|
||||
public interface JavaInterface {
|
||||
int getX();
|
||||
}
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
package
|
||||
|
||||
public /*synthesized*/ fun JavaInterface(/*0*/ function: () -> kotlin.Int): JavaInterface
|
||||
internal fun kotlin.Any.foo(): kotlin.Int
|
||||
|
||||
public abstract class BaseClass : JavaInterface {
|
||||
public constructor BaseClass()
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public abstract override /*1*/ /*fake_override*/ fun getX(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public abstract class JavaClass : BaseClass, JavaInterface {
|
||||
public constructor JavaClass()
|
||||
public open override /*2*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open fun getSomething(): kotlin.Int
|
||||
public abstract override /*2*/ /*fake_override*/ fun getX(): kotlin.Int
|
||||
public open override /*2*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open fun setSomething(/*0*/ value: kotlin.Int): kotlin.Unit
|
||||
public open override /*2*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public interface JavaInterface {
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public abstract fun getX(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
@@ -14093,6 +14093,18 @@ public class JetDiagnosticsTestGenerated extends AbstractJetDiagnosticsTest {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/syntheticExtensions/SetterOnly.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("SmartCast.kt")
|
||||
public void testSmartCast() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/syntheticExtensions/SmartCast.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("SmartCastImplicitReceiver.kt")
|
||||
public void testSmartCastImplicitReceiver() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/syntheticExtensions/SmartCastImplicitReceiver.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
}
|
||||
|
||||
@TestMetadata("compiler/testData/diagnostics/tests/thisAndSuper")
|
||||
|
||||
@@ -47,12 +47,12 @@ public abstract class AbstractScopeAdapter : JetScope {
|
||||
return workerScope.getProperties(name)
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor> {
|
||||
return workerScope.getSyntheticExtensionProperties(receiverType, name)
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor> {
|
||||
return workerScope.getSyntheticExtensionProperties(receiverTypes, name)
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor> {
|
||||
return workerScope.getSyntheticExtensionProperties(receiverType)
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor> {
|
||||
return workerScope.getSyntheticExtensionProperties(receiverTypes)
|
||||
}
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? {
|
||||
|
||||
@@ -65,11 +65,11 @@ public open class ChainedScope(
|
||||
override fun getFunctions(name: Name): Collection<FunctionDescriptor>
|
||||
= getFromAllScopes { it.getFunctions(name) }
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor>
|
||||
= getFromAllScopes { it.getSyntheticExtensionProperties(receiverType, name) }
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor>
|
||||
= getFromAllScopes { it.getSyntheticExtensionProperties(receiverTypes, name) }
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor>
|
||||
= getFromAllScopes { it.getSyntheticExtensionProperties(receiverType) }
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor>
|
||||
= getFromAllScopes { it.getSyntheticExtensionProperties(receiverTypes) }
|
||||
|
||||
override fun getImplicitReceiversHierarchy(): List<ReceiverParameterDescriptor> {
|
||||
if (implicitReceiverHierarchy == null) {
|
||||
|
||||
@@ -37,9 +37,9 @@ public class FilteringScope(private val workerScope: JetScope, private val predi
|
||||
|
||||
override fun getProperties(name: Name) = workerScope.getProperties(name).filter(predicate)
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor> = workerScope.getSyntheticExtensionProperties(receiverType, name).filter(predicate)
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor> = workerScope.getSyntheticExtensionProperties(receiverTypes, name).filter(predicate)
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor> = workerScope.getSyntheticExtensionProperties(receiverType).filter(predicate)
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor> = workerScope.getSyntheticExtensionProperties(receiverTypes).filter(predicate)
|
||||
|
||||
override fun getLocalVariable(name: Name) = filterDescriptor(workerScope.getLocalVariable(name))
|
||||
|
||||
|
||||
@@ -35,9 +35,9 @@ public trait JetScope {
|
||||
|
||||
public fun getFunctions(name: Name): Collection<FunctionDescriptor>
|
||||
|
||||
public fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor>
|
||||
public fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor>
|
||||
|
||||
public fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor>
|
||||
public fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor>
|
||||
|
||||
public fun getContainingDeclaration(): DeclarationDescriptor
|
||||
|
||||
|
||||
@@ -32,9 +32,9 @@ public abstract class JetScopeImpl : JetScope {
|
||||
|
||||
override fun getFunctions(name: Name): Collection<FunctionDescriptor> = setOf()
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor> = listOf()
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor> = listOf()
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor> = listOf()
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor> = listOf()
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name): Collection<DeclarationDescriptor> = listOf()
|
||||
|
||||
|
||||
@@ -70,9 +70,9 @@ public class SubstitutingScope(private val workerScope: JetScope, private val su
|
||||
|
||||
override fun getFunctions(name: Name) = substitute(workerScope.getFunctions(name))
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<PropertyDescriptor> = substitute(workerScope.getSyntheticExtensionProperties(receiverType, name))
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>, name: Name): Collection<PropertyDescriptor> = substitute(workerScope.getSyntheticExtensionProperties(receiverTypes, name))
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<PropertyDescriptor> = substitute(workerScope.getSyntheticExtensionProperties(receiverType))
|
||||
override fun getSyntheticExtensionProperties(receiverTypes: Collection<JetType>): Collection<PropertyDescriptor> = substitute(workerScope.getSyntheticExtensionProperties(receiverTypes))
|
||||
|
||||
override fun getPackage(name: Name) = workerScope.getPackage(name)
|
||||
|
||||
|
||||
@@ -94,14 +94,14 @@ public class ErrorUtils {
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<PropertyDescriptor> getSyntheticExtensionProperties(
|
||||
@NotNull JetType receiverType, @NotNull Name name
|
||||
@NotNull Collection<? extends JetType> receiverTypes, @NotNull Name name
|
||||
) {
|
||||
return ERROR_PROPERTY_GROUP;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<PropertyDescriptor> getSyntheticExtensionProperties(@NotNull JetType receiverType) {
|
||||
public Collection<PropertyDescriptor> getSyntheticExtensionProperties(@NotNull Collection<? extends JetType> receiverTypes) {
|
||||
return ERROR_PROPERTY_GROUP;
|
||||
}
|
||||
|
||||
@@ -210,14 +210,14 @@ public class ErrorUtils {
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<PropertyDescriptor> getSyntheticExtensionProperties(
|
||||
@NotNull JetType receiverType, @NotNull Name name
|
||||
@NotNull Collection<? extends JetType> receiverTypes, @NotNull Name name
|
||||
) {
|
||||
throw new IllegalStateException();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<PropertyDescriptor> getSyntheticExtensionProperties(@NotNull JetType receiverType) {
|
||||
public Collection<PropertyDescriptor> getSyntheticExtensionProperties(@NotNull Collection<? extends JetType> receiverTypes) {
|
||||
throw new IllegalStateException();
|
||||
}
|
||||
|
||||
|
||||
+8
-6
@@ -167,7 +167,9 @@ public class ReferenceVariantsHelper(
|
||||
val memberFilter = kindFilter exclude DescriptorKindExclude.Extensions
|
||||
val containingDeclaration = resolutionScope.getContainingDeclaration()
|
||||
|
||||
for (receiverType in SmartCastUtils.getSmartCastVariantsWithLessSpecificExcluded(receiverValue, context, containingDeclaration, dataFlowInfo)) {
|
||||
val receiverTypes = SmartCastUtils.getSmartCastVariantsWithLessSpecificExcluded(receiverValue, context, containingDeclaration, dataFlowInfo)
|
||||
|
||||
for (receiverType in receiverTypes) {
|
||||
val members = receiverType.getMemberScope().getDescriptorsFiltered(DescriptorKindFilter.ALL, nameFilter) // filter by kind later because of constructors
|
||||
for (member in members) {
|
||||
if (member is ClassDescriptor) {
|
||||
@@ -179,12 +181,12 @@ public class ReferenceVariantsHelper(
|
||||
this.add(member)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!kindFilter.excludes.contains(DescriptorKindExclude.Extensions)) {
|
||||
for (extension in resolutionScope.getSyntheticExtensionProperties(receiverType)) {
|
||||
if (nameFilter(extension.getName()) && kindFilter.accepts(extension)) {
|
||||
addAll(extension.substituteExtensionIfCallable(receiverValue, callType, context, dataFlowInfo, containingDeclaration))
|
||||
}
|
||||
if (!kindFilter.excludes.contains(DescriptorKindExclude.Extensions)) {
|
||||
for (extension in resolutionScope.getSyntheticExtensionProperties(receiverTypes)) {
|
||||
if (nameFilter(extension.getName()) && kindFilter.accepts(extension)) {
|
||||
addAll(extension.substituteExtensionIfCallable(receiverValue, callType, context, dataFlowInfo, containingDeclaration))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user