diff --git a/compiler/frontend/src/org/jetbrains/kotlin/psi/synthetics/SyntheticClassOrObjectDescriptor.kt b/compiler/frontend/src/org/jetbrains/kotlin/psi/synthetics/SyntheticClassOrObjectDescriptor.kt index dd20f2e8001..2b08cde5dfa 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/psi/synthetics/SyntheticClassOrObjectDescriptor.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/psi/synthetics/SyntheticClassOrObjectDescriptor.kt @@ -29,6 +29,7 @@ import org.jetbrains.kotlin.storage.StorageManager import org.jetbrains.kotlin.types.AbstractClassTypeConstructor import org.jetbrains.kotlin.types.KotlinType import org.jetbrains.kotlin.types.TypeConstructor +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner /* * This class introduces all attributes that are needed for synthetic classes/object so far. @@ -88,7 +89,7 @@ class SyntheticClassOrObjectDescriptor( override fun getConstructors() = listOf(_unsubstitutedPrimaryConstructor()) + secondaryConstructors override fun getDeclaredTypeParameters() = typeParameters override fun getStaticScope() = MemberScope.Empty - override fun getUnsubstitutedMemberScope() = unsubstitutedMemberScope + override fun getUnsubstitutedMemberScope(kotlinTypeRefiner: KotlinTypeRefiner) = unsubstitutedMemberScope override fun getSealedSubclasses() = emptyList() init { diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassDescriptor.java b/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassDescriptor.java index 06513e7087f..56e4c6d7283 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassDescriptor.java +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassDescriptor.java @@ -48,6 +48,7 @@ import org.jetbrains.kotlin.storage.NotNullLazyValue; import org.jetbrains.kotlin.storage.NullableLazyValue; import org.jetbrains.kotlin.storage.StorageManager; import org.jetbrains.kotlin.types.*; +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner; import java.util.ArrayList; import java.util.Collection; @@ -91,7 +92,7 @@ public class LazyClassDescriptor extends ClassDescriptorBase implements ClassDes private final NullableLazyValue companionObjectDescriptor; private final MemoizedFunctionToNotNull extraCompanionObjectDescriptors; - private final LazyClassMemberScope unsubstitutedMemberScope; + private final ScopesHolderForClass scopesHolderForClass; private final MemberScope staticScope; private final NullableLazyValue forceResolveAllContents; @@ -127,7 +128,7 @@ public class LazyClassDescriptor extends ClassDescriptorBase implements ClassDes StorageManager storageManager = c.getStorageManager(); - this.unsubstitutedMemberScope = createMemberScope(c, this.declarationProvider); + this.scopesHolderForClass = createMemberScope(c, this.declarationProvider); this.kind = classLikeInfo.getClassKind(); this.staticScope = kind == ClassKind.ENUM_CLASS ? new StaticScopeForKotlinEnum(storageManager, this) : MemberScope.Empty.INSTANCE; @@ -308,17 +309,22 @@ public class LazyClassDescriptor extends ClassDescriptorBase implements ClassDes // NOTE: Called from constructor! @NotNull - protected LazyClassMemberScope createMemberScope( + protected ScopesHolderForClass createMemberScope( @NotNull LazyClassContext c, @NotNull ClassMemberDeclarationProvider declarationProvider ) { - return new LazyClassMemberScope(c, declarationProvider, this, c.getTrace()); + return ScopesHolderForClass.Companion.create( + this, + c.getStorageManager(), + c.getKotlinTypeChecker().getKotlinTypeRefiner(), + kotlinTypeRefiner -> new LazyClassMemberScope(c, declarationProvider, this, c.getTrace(), kotlinTypeRefiner) + ); } @NotNull @Override - public MemberScope getUnsubstitutedMemberScope() { - return unsubstitutedMemberScope; + public MemberScope getUnsubstitutedMemberScope(@NotNull KotlinTypeRefiner kotlinTypeRefiner) { + return scopesHolderForClass.getScope(kotlinTypeRefiner); } @NotNull @@ -367,7 +373,7 @@ public class LazyClassDescriptor extends ClassDescriptorBase implements ClassDes @SuppressWarnings("unchecked") public Collection getDeclaredCallableMembers() { return (Collection) CollectionsKt.filter( - DescriptorUtils.getAllDescriptors(unsubstitutedMemberScope), + DescriptorUtils.getAllDescriptors(getUnsubstitutedMemberScope()), descriptor -> descriptor instanceof CallableMemberDescriptor && ((CallableMemberDescriptor) descriptor).getKind() != CallableMemberDescriptor.Kind.FAKE_OVERRIDE ); @@ -382,12 +388,12 @@ public class LazyClassDescriptor extends ClassDescriptorBase implements ClassDes @NotNull @Override public Collection getConstructors() { - return unsubstitutedMemberScope.getConstructors(); + return ((LazyClassMemberScope) getUnsubstitutedMemberScope()).getConstructors(); } @Override public ClassConstructorDescriptor getUnsubstitutedPrimaryConstructor() { - return unsubstitutedMemberScope.getPrimaryConstructor(); + return ((LazyClassMemberScope) getUnsubstitutedMemberScope()).getPrimaryConstructor(); } @NotNull diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassMemberScope.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassMemberScope.kt index 3d0fe63e311..c6d89ee41d9 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassMemberScope.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/lazy/descriptors/LazyClassMemberScope.kt @@ -40,14 +40,18 @@ import org.jetbrains.kotlin.resolve.scopes.LexicalScope import org.jetbrains.kotlin.resolve.scopes.MemberScope import org.jetbrains.kotlin.storage.NotNullLazyValue import org.jetbrains.kotlin.storage.NullableLazyValue +import org.jetbrains.kotlin.storage.getValue import org.jetbrains.kotlin.types.KotlinType +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner +import org.jetbrains.kotlin.types.refinement.TypeRefinement import java.util.* open class LazyClassMemberScope( c: LazyClassContext, declarationProvider: ClassMemberDeclarationProvider, thisClass: ClassDescriptorWithResolutionScopes, - trace: BindingTrace + trace: BindingTrace, + private val kotlinTypeRefiner: KotlinTypeRefiner = c.kotlinTypeChecker.kotlinTypeRefiner ) : AbstractLazyMemberScope(c, declarationProvider, thisClass, trace) { private val descriptorsFromDeclaredElements = storageManager.createLazyValue { diff --git a/core/descriptors/src/org/jetbrains/kotlin/builtins/functions/FunctionClassDescriptor.kt b/core/descriptors/src/org/jetbrains/kotlin/builtins/functions/FunctionClassDescriptor.kt index f479cfcbdb9..ee9853c09a1 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/builtins/functions/FunctionClassDescriptor.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/builtins/functions/FunctionClassDescriptor.kt @@ -18,6 +18,7 @@ import org.jetbrains.kotlin.resolve.DescriptorUtils.COROUTINES_PACKAGE_FQ_NAME_R import org.jetbrains.kotlin.resolve.scopes.MemberScope import org.jetbrains.kotlin.storage.StorageManager import org.jetbrains.kotlin.types.* +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner import java.util.* /** @@ -82,7 +83,7 @@ class FunctionClassDescriptor( override fun getTypeConstructor(): TypeConstructor = typeConstructor - override fun getUnsubstitutedMemberScope() = memberScope + override fun getUnsubstitutedMemberScope(kotlinTypeRefiner: KotlinTypeRefiner) = memberScope override fun getCompanionObjectDescriptor() = null override fun getConstructors() = emptyList() diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/NotFoundClasses.kt b/core/descriptors/src/org/jetbrains/kotlin/descriptors/NotFoundClasses.kt index 2148fec45a0..5a52f6ab1d1 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/descriptors/NotFoundClasses.kt +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/NotFoundClasses.kt @@ -17,6 +17,7 @@ import org.jetbrains.kotlin.resolve.scopes.MemberScope import org.jetbrains.kotlin.storage.StorageManager import org.jetbrains.kotlin.types.ClassTypeConstructorImpl import org.jetbrains.kotlin.types.Variance +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner class NotFoundClasses(private val storageManager: StorageManager, private val module: ModuleDescriptor) { /** @@ -73,7 +74,7 @@ class NotFoundClasses(private val storageManager: StorageManager, private val mo override fun isExternal() = false override val annotations: Annotations get() = Annotations.EMPTY - override fun getUnsubstitutedMemberScope() = MemberScope.Empty + override fun getUnsubstitutedMemberScope(kotlinTypeRefiner: KotlinTypeRefiner) = MemberScope.Empty override fun getStaticScope() = MemberScope.Empty override fun getConstructors(): Collection = emptySet() override fun getUnsubstitutedPrimaryConstructor(): ClassConstructorDescriptor? = null diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/ScopesHolderForClass.kt b/core/descriptors/src/org/jetbrains/kotlin/descriptors/ScopesHolderForClass.kt new file mode 100644 index 00000000000..c6b31d25355 --- /dev/null +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/ScopesHolderForClass.kt @@ -0,0 +1,56 @@ +/* + * Copyright 2010-2019 JetBrains s.r.o. 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.descriptors + +import org.jetbrains.kotlin.resolve.descriptorUtil.module +import org.jetbrains.kotlin.resolve.scopes.MemberScope +import org.jetbrains.kotlin.storage.StorageManager +import org.jetbrains.kotlin.storage.getValue +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner +import org.jetbrains.kotlin.types.refinement.TypeRefinement + +class ScopesHolderForClass private constructor( + private val classDescriptor: ClassDescriptor, + storageManager: StorageManager, + private val scopeFactory: (KotlinTypeRefiner) -> T, + private val kotlinTypeRefinerForOwnerModule: KotlinTypeRefiner +) { + private val scopeForOwnerModule by storageManager.createLazyValue { + scopeFactory(kotlinTypeRefinerForOwnerModule) + } + + @UseExperimental(TypeRefinement::class) + fun getScope(kotlinTypeRefiner: KotlinTypeRefiner): T { + /* + * That check doesn't break anything, because scopeForOwnerModule _will_ anyway refine supertypes from module of + * class descriptor. + * + * Without that fastpass there is problem wit recursion types such that: + * + * interface A> + * + * interface B : B + * + * In this case (without check) we start compute default type of class descriptor B, go to isRefinementNeededForTypeConstructor, + * ask for supertypes of B, see A, ask default type of class B and fail with recursion problem + */ + if (!kotlinTypeRefiner.isRefinementNeededForModule(classDescriptor.module)) return scopeForOwnerModule + + if (!kotlinTypeRefiner.isRefinementNeededForTypeConstructor(classDescriptor.typeConstructor)) return scopeForOwnerModule + return kotlinTypeRefiner.getOrPutScopeForClass(classDescriptor) { scopeFactory(kotlinTypeRefiner) } + } + + companion object { + fun create( + classDescriptor: ClassDescriptor, + storageManager: StorageManager, + kotlinTypeRefinerForOwnerModule: KotlinTypeRefiner, + scopeFactory: (KotlinTypeRefiner) -> T + ): ScopesHolderForClass { + return ScopesHolderForClass(classDescriptor, storageManager, scopeFactory, kotlinTypeRefinerForOwnerModule) + } + } +} diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/AbstractClassDescriptor.java b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/AbstractClassDescriptor.java index 59d62742da0..a1812029037 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/AbstractClassDescriptor.java +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/AbstractClassDescriptor.java @@ -18,20 +18,21 @@ package org.jetbrains.kotlin.descriptors.impl; import kotlin.jvm.functions.Function0; import org.jetbrains.annotations.NotNull; -import org.jetbrains.kotlin.descriptors.ClassDescriptor; -import org.jetbrains.kotlin.descriptors.DeclarationDescriptorVisitor; -import org.jetbrains.kotlin.descriptors.ReceiverParameterDescriptor; +import org.jetbrains.kotlin.descriptors.*; import org.jetbrains.kotlin.name.Name; +import org.jetbrains.kotlin.resolve.DescriptorUtils; +import org.jetbrains.kotlin.resolve.descriptorUtil.DescriptorUtilsKt; import org.jetbrains.kotlin.resolve.scopes.InnerClassesScopeWrapper; import org.jetbrains.kotlin.resolve.scopes.MemberScope; import org.jetbrains.kotlin.resolve.scopes.SubstitutingScope; import org.jetbrains.kotlin.storage.NotNullLazyValue; import org.jetbrains.kotlin.storage.StorageManager; import org.jetbrains.kotlin.types.*; +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner; import java.util.List; -public abstract class AbstractClassDescriptor implements ClassDescriptor { +public abstract class AbstractClassDescriptor extends ModuleAwareClassDescriptor { private final Name name; protected final NotNullLazyValue defaultType; private final NotNullLazyValue unsubstitutedInnerClassesScope; @@ -85,23 +86,41 @@ public abstract class AbstractClassDescriptor implements ClassDescriptor { @NotNull @Override - public MemberScope getMemberScope(@NotNull List typeArguments) { + public MemberScope getMemberScope(@NotNull List typeArguments, @NotNull KotlinTypeRefiner kotlinTypeRefiner) { assert typeArguments.size() == getTypeConstructor().getParameters().size() : "Illegal number of type arguments: expected " + getTypeConstructor().getParameters().size() + " but was " + typeArguments.size() + " for " + getTypeConstructor() + " " + getTypeConstructor().getParameters(); - if (typeArguments.isEmpty()) return getUnsubstitutedMemberScope(); + if (typeArguments.isEmpty()) return getUnsubstitutedMemberScope(kotlinTypeRefiner); TypeSubstitutor substitutor = TypeConstructorSubstitution.create(getTypeConstructor(), typeArguments).buildSubstitutor(); - return new SubstitutingScope(getUnsubstitutedMemberScope(), substitutor); + return new SubstitutingScope(getUnsubstitutedMemberScope(kotlinTypeRefiner), substitutor); + } + + @NotNull + @Override + public MemberScope getMemberScope(@NotNull TypeSubstitution typeSubstitution, @NotNull KotlinTypeRefiner kotlinTypeRefiner) { + if (typeSubstitution.isEmpty()) return getUnsubstitutedMemberScope(kotlinTypeRefiner); + + TypeSubstitutor substitutor = TypeSubstitutor.create(typeSubstitution); + return new SubstitutingScope(getUnsubstitutedMemberScope(kotlinTypeRefiner), substitutor); + } + + @NotNull + @Override + public MemberScope getMemberScope(@NotNull List typeArguments) { + return getMemberScope(typeArguments, DescriptorUtilsKt.getKotlinTypeRefiner(DescriptorUtils.getContainingModule(this))); } @NotNull @Override public MemberScope getMemberScope(@NotNull TypeSubstitution typeSubstitution) { - if (typeSubstitution.isEmpty()) return getUnsubstitutedMemberScope(); + return getMemberScope(typeSubstitution, DescriptorUtilsKt.getKotlinTypeRefiner(DescriptorUtils.getContainingModule(this))); + } - TypeSubstitutor substitutor = TypeSubstitutor.create(typeSubstitution); - return new SubstitutingScope(getUnsubstitutedMemberScope(), substitutor); + @NotNull + @Override + public MemberScope getUnsubstitutedMemberScope() { + return getUnsubstitutedMemberScope(DescriptorUtilsKt.getKotlinTypeRefiner(DescriptorUtils.getContainingModule(this))); } @NotNull diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/ClassDescriptorImpl.java b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/ClassDescriptorImpl.java index 18ecd13197a..a0cc195df4a 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/ClassDescriptorImpl.java +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/ClassDescriptorImpl.java @@ -16,6 +16,7 @@ import org.jetbrains.kotlin.storage.StorageManager; import org.jetbrains.kotlin.types.ClassTypeConstructorImpl; import org.jetbrains.kotlin.types.KotlinType; import org.jetbrains.kotlin.types.TypeConstructor; +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner; import java.util.Collection; import java.util.Collections; @@ -79,7 +80,7 @@ public class ClassDescriptorImpl extends ClassDescriptorBase { @NotNull @Override - public MemberScope getUnsubstitutedMemberScope() { + public MemberScope getUnsubstitutedMemberScope(@NotNull KotlinTypeRefiner kotlinTypeRefiner) { return unsubstitutedMemberScope; } diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/EnumEntrySyntheticClassDescriptor.java b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/EnumEntrySyntheticClassDescriptor.java index f7ee014dde5..f12108b9dac 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/EnumEntrySyntheticClassDescriptor.java +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/EnumEntrySyntheticClassDescriptor.java @@ -25,6 +25,7 @@ import org.jetbrains.kotlin.storage.StorageManager; import org.jetbrains.kotlin.types.ClassTypeConstructorImpl; import org.jetbrains.kotlin.types.KotlinType; import org.jetbrains.kotlin.types.TypeConstructor; +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner; import org.jetbrains.kotlin.utils.Printer; import java.util.*; @@ -76,7 +77,7 @@ public class EnumEntrySyntheticClassDescriptor extends ClassDescriptorBase { @NotNull @Override - public MemberScope getUnsubstitutedMemberScope() { + public MemberScope getUnsubstitutedMemberScope(@NotNull KotlinTypeRefiner kotlinTypeRefiner) { return scope; } diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/LazySubstitutingClassDescriptor.java b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/LazySubstitutingClassDescriptor.java index aa45dbbaa04..2e61b652896 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/LazySubstitutingClassDescriptor.java +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/LazySubstitutingClassDescriptor.java @@ -12,24 +12,27 @@ import org.jetbrains.annotations.Nullable; import org.jetbrains.kotlin.descriptors.*; import org.jetbrains.kotlin.descriptors.annotations.Annotations; import org.jetbrains.kotlin.name.Name; +import org.jetbrains.kotlin.resolve.DescriptorUtils; +import org.jetbrains.kotlin.resolve.descriptorUtil.DescriptorUtilsKt; import org.jetbrains.kotlin.resolve.scopes.MemberScope; import org.jetbrains.kotlin.resolve.scopes.SubstitutingScope; import org.jetbrains.kotlin.storage.LockBasedStorageManager; import org.jetbrains.kotlin.types.*; +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner; import java.util.ArrayList; import java.util.Collection; import java.util.List; -public class LazySubstitutingClassDescriptor implements ClassDescriptor { - private final ClassDescriptor original; +public class LazySubstitutingClassDescriptor extends ModuleAwareClassDescriptor { + private final ModuleAwareClassDescriptor original; private final TypeSubstitutor originalSubstitutor; private TypeSubstitutor newSubstitutor; private List typeConstructorParameters; private List declaredTypeParameters; private TypeConstructor typeConstructor; - public LazySubstitutingClassDescriptor(ClassDescriptor descriptor, TypeSubstitutor substitutor) { + public LazySubstitutingClassDescriptor(ModuleAwareClassDescriptor descriptor, TypeSubstitutor substitutor) { this.original = descriptor; this.originalSubstitutor = substitutor; } @@ -82,28 +85,46 @@ public class LazySubstitutingClassDescriptor implements ClassDescriptor { @NotNull @Override - public MemberScope getMemberScope(@NotNull List typeArguments) { - MemberScope memberScope = original.getMemberScope(typeArguments); + public MemberScope getMemberScope(@NotNull List typeArguments, @NotNull KotlinTypeRefiner kotlinTypeRefiner) { + MemberScope memberScope = original.getMemberScope(typeArguments, kotlinTypeRefiner); if (originalSubstitutor.isEmpty()) { return memberScope; } return new SubstitutingScope(memberScope, getSubstitutor()); } + @NotNull + @Override + public MemberScope getMemberScope(@NotNull TypeSubstitution typeSubstitution, @NotNull KotlinTypeRefiner kotlinTypeRefiner) { + MemberScope memberScope = original.getMemberScope(typeSubstitution, kotlinTypeRefiner); + if (originalSubstitutor.isEmpty()) { + return memberScope; + } + return new SubstitutingScope(memberScope, getSubstitutor()); + } + + @NotNull + @Override + public MemberScope getMemberScope(@NotNull List typeArguments) { + return getMemberScope(typeArguments, DescriptorUtilsKt.getKotlinTypeRefiner(DescriptorUtils.getContainingModule(this))); + } + @NotNull @Override public MemberScope getMemberScope(@NotNull TypeSubstitution typeSubstitution) { - MemberScope memberScope = original.getMemberScope(typeSubstitution); - if (originalSubstitutor.isEmpty()) { - return memberScope; - } - return new SubstitutingScope(memberScope, getSubstitutor()); + return getMemberScope(typeSubstitution, DescriptorUtilsKt.getKotlinTypeRefiner(DescriptorUtils.getContainingModule(this))); } @NotNull @Override public MemberScope getUnsubstitutedMemberScope() { - MemberScope memberScope = original.getUnsubstitutedMemberScope(); + return getUnsubstitutedMemberScope(DescriptorUtilsKt.getKotlinTypeRefiner(DescriptorUtils.getContainingModule(original))); + } + + @NotNull + @Override + public MemberScope getUnsubstitutedMemberScope(@NotNull KotlinTypeRefiner kotlinTypeRefiner) { + MemberScope memberScope = original.getUnsubstitutedMemberScope(kotlinTypeRefiner); if (originalSubstitutor.isEmpty()) { return memberScope; } diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/ModuleAwareClassDescriptor.kt b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/ModuleAwareClassDescriptor.kt new file mode 100644 index 00000000000..7df140ca4a4 --- /dev/null +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/ModuleAwareClassDescriptor.kt @@ -0,0 +1,45 @@ +/* + * Copyright 2010-2019 JetBrains s.r.o. 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.descriptors.impl + +import org.jetbrains.kotlin.descriptors.ClassDescriptor +import org.jetbrains.kotlin.descriptors.ModuleDescriptor +import org.jetbrains.kotlin.descriptors.impl.ModuleAwareClassDescriptor.Companion.getRefinedMemberScopeIfPossible +import org.jetbrains.kotlin.descriptors.impl.ModuleAwareClassDescriptor.Companion.getRefinedUnsubstitutedMemberScopeIfPossible +import org.jetbrains.kotlin.resolve.scopes.MemberScope +import org.jetbrains.kotlin.types.TypeProjection +import org.jetbrains.kotlin.types.TypeSubstitution +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner + +abstract class ModuleAwareClassDescriptor : ClassDescriptor { + protected abstract fun getUnsubstitutedMemberScope(kotlinTypeRefiner: KotlinTypeRefiner): MemberScope + protected abstract fun getMemberScope(typeSubstitution: TypeSubstitution, kotlinTypeRefiner: KotlinTypeRefiner): MemberScope + protected abstract fun getMemberScope(typeArguments: List, kotlinTypeRefiner: KotlinTypeRefiner): MemberScope + + companion object { + internal fun ClassDescriptor.getRefinedUnsubstitutedMemberScopeIfPossible( + kotlinTypeRefiner: KotlinTypeRefiner + ): MemberScope = + (this as? ModuleAwareClassDescriptor)?.getUnsubstitutedMemberScope(kotlinTypeRefiner) ?: this.unsubstitutedMemberScope + + internal fun ClassDescriptor.getRefinedMemberScopeIfPossible( + typeSubstitution: TypeSubstitution, + kotlinTypeRefiner: KotlinTypeRefiner + ): MemberScope = + (this as? ModuleAwareClassDescriptor)?.getMemberScope(typeSubstitution, kotlinTypeRefiner) ?: this.getMemberScope( + typeSubstitution + ) + } +} + +fun ClassDescriptor.getRefinedUnsubstitutedMemberScopeIfPossible( + kotlinTypeRefiner: KotlinTypeRefiner +): MemberScope = getRefinedUnsubstitutedMemberScopeIfPossible(kotlinTypeRefiner) + +fun ClassDescriptor.getRefinedMemberScopeIfPossible( + typeSubstitution: TypeSubstitution, + kotlinTypeRefiner: KotlinTypeRefiner +): MemberScope = getRefinedMemberScopeIfPossible(typeSubstitution, kotlinTypeRefiner) diff --git a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/MutableClassDescriptor.java b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/MutableClassDescriptor.java index 532c2f216c4..5884475ee1b 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/MutableClassDescriptor.java +++ b/core/descriptors/src/org/jetbrains/kotlin/descriptors/impl/MutableClassDescriptor.java @@ -13,6 +13,7 @@ import org.jetbrains.kotlin.name.Name; import org.jetbrains.kotlin.resolve.scopes.MemberScope; import org.jetbrains.kotlin.storage.StorageManager; import org.jetbrains.kotlin.types.*; +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner; import java.util.*; @@ -162,7 +163,7 @@ public class MutableClassDescriptor extends ClassDescriptorBase { @Override @NotNull - public MemberScope getUnsubstitutedMemberScope() { + public MemberScope getUnsubstitutedMemberScope(@NotNull KotlinTypeRefiner kotlinTypeRefiner) { return MemberScope.Empty.INSTANCE; // used for getDefaultType } diff --git a/core/descriptors/src/org/jetbrains/kotlin/types/ErrorUtils.java b/core/descriptors/src/org/jetbrains/kotlin/types/ErrorUtils.java index c2c2183a869..ec66fbc6f06 100644 --- a/core/descriptors/src/org/jetbrains/kotlin/types/ErrorUtils.java +++ b/core/descriptors/src/org/jetbrains/kotlin/types/ErrorUtils.java @@ -35,7 +35,9 @@ import org.jetbrains.kotlin.resolve.descriptorUtil.DescriptorUtilsKt; import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter; import org.jetbrains.kotlin.resolve.scopes.MemberScope; import org.jetbrains.kotlin.storage.LockBasedStorageManager; +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner; import org.jetbrains.kotlin.types.error.ErrorSimpleFunctionDescriptorImpl; +import org.jetbrains.kotlin.types.refinement.TypeRefinement; import org.jetbrains.kotlin.utils.Printer; import java.util.Collection; @@ -372,13 +374,13 @@ public class ErrorUtils { @NotNull @Override - public MemberScope getMemberScope(@NotNull List typeArguments) { + public MemberScope getMemberScope(@NotNull List typeArguments, @NotNull KotlinTypeRefiner kotlinTypeRefiner) { return createErrorScope("Error scope for class " + getName() + " with arguments: " + typeArguments); } @NotNull @Override - public MemberScope getMemberScope(@NotNull TypeSubstitution typeSubstitution) { + public MemberScope getMemberScope(@NotNull TypeSubstitution typeSubstitution, @NotNull KotlinTypeRefiner kotlinTypeRefiner) { return createErrorScope("Error scope for class " + getName() + " with arguments: " + typeSubstitution); } } diff --git a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/descriptors/DeserializedClassDescriptor.kt b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/descriptors/DeserializedClassDescriptor.kt index 772946a73ac..be3d7e34718 100644 --- a/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/descriptors/DeserializedClassDescriptor.kt +++ b/core/deserialization/src/org/jetbrains/kotlin/serialization/deserialization/descriptors/DeserializedClassDescriptor.kt @@ -27,6 +27,8 @@ import org.jetbrains.kotlin.serialization.deserialization.* import org.jetbrains.kotlin.types.AbstractClassTypeConstructor import org.jetbrains.kotlin.types.KotlinType import org.jetbrains.kotlin.types.TypeConstructor +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner +import org.jetbrains.kotlin.types.refinement.TypeRefinement import java.util.* class DeserializedClassDescriptor( @@ -52,7 +54,11 @@ class DeserializedClassDescriptor( private val staticScope = if (kind == ClassKind.ENUM_CLASS) StaticScopeForKotlinEnum(c.storageManager, this) else MemberScope.Empty private val typeConstructor = DeserializedClassTypeConstructor() - private val memberScope = DeserializedClassMemberScope() + + private val memberScopeHolder = + ScopesHolderForClass.create(this, c.storageManager, c.components.kotlinTypeChecker.kotlinTypeRefiner, this::DeserializedClassMemberScope) + + private val memberScope get() = memberScopeHolder.getScope(c.components.kotlinTypeChecker.kotlinTypeRefiner) private val enumEntries = if (kind == ClassKind.ENUM_CLASS) EnumEntryClassDescriptors() else null private val containingDeclaration = outerContext.containingDeclaration @@ -98,7 +104,8 @@ class DeserializedClassDescriptor( override fun isExternal() = Flags.IS_EXTERNAL_CLASS.get(classProto.flags) - override fun getUnsubstitutedMemberScope(): MemberScope = memberScope + override fun getUnsubstitutedMemberScope(kotlinTypeRefiner: KotlinTypeRefiner): MemberScope = + memberScopeHolder.getScope(kotlinTypeRefiner) override fun getStaticScope() = staticScope @@ -200,7 +207,7 @@ class DeserializedClassDescriptor( get() = SupertypeLoopChecker.EMPTY } - private inner class DeserializedClassMemberScope : DeserializedMemberScope( + private inner class DeserializedClassMemberScope(private val kotlinTypeRefiner: KotlinTypeRefiner) : DeserializedMemberScope( c, classProto.functionList, classProto.propertyList, classProto.typeAliasList, classProto.nestedClassNameList.map(c.nameResolver::getName).let { { it } } // workaround KT-13454 ) { diff --git a/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/LazyScriptDescriptor.kt b/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/LazyScriptDescriptor.kt index 303cb5f7dc0..7694ba43318 100644 --- a/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/LazyScriptDescriptor.kt +++ b/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/LazyScriptDescriptor.kt @@ -29,6 +29,7 @@ import org.jetbrains.kotlin.resolve.lazy.ResolveSession import org.jetbrains.kotlin.resolve.lazy.data.KtScriptInfo import org.jetbrains.kotlin.resolve.lazy.declarations.ClassMemberDeclarationProvider import org.jetbrains.kotlin.resolve.lazy.descriptors.LazyClassDescriptor +import org.jetbrains.kotlin.resolve.lazy.descriptors.LazyClassMemberScope import org.jetbrains.kotlin.resolve.scopes.LexicalScope import org.jetbrains.kotlin.resolve.scopes.LexicalScopeImpl import org.jetbrains.kotlin.resolve.scopes.LexicalScopeKind @@ -144,14 +145,19 @@ class LazyScriptDescriptor( override fun accept(visitor: DeclarationDescriptorVisitor, data: D): R = visitor.visitScriptDescriptor(this, data) - override fun createMemberScope(c: LazyClassContext, declarationProvider: ClassMemberDeclarationProvider): LazyScriptClassMemberScope = - LazyScriptClassMemberScope( - // Must be a ResolveSession for scripts - c as ResolveSession, - declarationProvider, - this, - c.trace - ) + override fun createMemberScope( + c: LazyClassContext, + declarationProvider: ClassMemberDeclarationProvider + ): ScopesHolderForClass = + ScopesHolderForClass.create(this, c.storageManager, c.kotlinTypeChecker.kotlinTypeRefiner) { + LazyScriptClassMemberScope( + // Must be a ResolveSession for scripts + c as ResolveSession, + declarationProvider, + this, + c.trace + ) + } override fun getUnsubstitutedPrimaryConstructor() = super.getUnsubstitutedPrimaryConstructor()!! diff --git a/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/ScriptProvidedPropertiesDescriptor.kt b/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/ScriptProvidedPropertiesDescriptor.kt index a3fbe8f7ecd..d5af8149958 100644 --- a/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/ScriptProvidedPropertiesDescriptor.kt +++ b/plugins/scripting/scripting-compiler-impl/src/org/jetbrains/kotlin/scripting/resolve/ScriptProvidedPropertiesDescriptor.kt @@ -14,6 +14,7 @@ import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter import org.jetbrains.kotlin.resolve.scopes.MemberScope import org.jetbrains.kotlin.resolve.scopes.MemberScopeImpl import org.jetbrains.kotlin.storage.LockBasedStorageManager +import org.jetbrains.kotlin.types.checker.KotlinTypeRefiner import org.jetbrains.kotlin.utils.Printer import kotlin.script.experimental.api.ScriptCompilationConfiguration import kotlin.script.experimental.api.providedProperties @@ -42,7 +43,7 @@ class ScriptProvidedPropertiesDescriptor(script: LazyScriptDescriptor) : ) } - override fun getUnsubstitutedMemberScope(): MemberScope = memberScope() + override fun getUnsubstitutedMemberScope(kotlinTypeRefiner: KotlinTypeRefiner): MemberScope = memberScope() val properties: () -> List = script.resolveSession.storageManager.createLazyValue { script.scriptCompilationConfiguration()[ScriptCompilationConfiguration.providedProperties].orEmpty().mapNotNull { (name, type) -> @@ -76,4 +77,4 @@ class ScriptProvidedPropertiesDescriptor(script: LazyScriptDescriptor) : p.println("Scope of script provided properties: $scriptId") } } -} \ No newline at end of file +}