Cache declared/non-declared static/non-static KClass members

Making KClassImpl.Data, its superclass and ReflectProperties public was
required because they are accessed from other package in KClasses.kt
This commit is contained in:
Alexander Udalov
2016-08-17 17:57:12 +03:00
parent f292ca3dad
commit 6a97dc5f2c
5 changed files with 66 additions and 55 deletions
@@ -70,10 +70,7 @@ val KClass<*>.defaultType: KType
* Does not include members declared in supertypes. * Does not include members declared in supertypes.
*/ */
val KClass<*>.declaredMembers: Collection<KCallable<*>> val KClass<*>.declaredMembers: Collection<KCallable<*>>
get() = with(this as KClassImpl) { get() = (this as KClassImpl).data().declaredMembers.toList()
(getMembers(memberScope, declaredOnly = true) +
getMembers(staticScope, declaredOnly = true)).toList()
}
/** /**
* Returns all functions declared in this class, including all non-static methods declared in the class * Returns all functions declared in this class, including all non-static methods declared in the class
@@ -86,8 +83,7 @@ val KClass<*>.functions: Collection<KFunction<*>>
* Returns static functions declared in this class. * Returns static functions declared in this class.
*/ */
val KClass<*>.staticFunctions: Collection<KFunction<*>> val KClass<*>.staticFunctions: Collection<KFunction<*>>
get() = (this as KClassImpl) get() = (this as KClassImpl).data().allStaticMembers
.getMembers(staticScope, declaredOnly = false)
.filterIsInstance<KFunction<*>>() .filterIsInstance<KFunction<*>>()
.toList() .toList()
@@ -95,8 +91,7 @@ val KClass<*>.staticFunctions: Collection<KFunction<*>>
* Returns non-extension non-static functions declared in this class and all of its superclasses. * Returns non-extension non-static functions declared in this class and all of its superclasses.
*/ */
val KClass<*>.memberFunctions: Collection<KFunction<*>> val KClass<*>.memberFunctions: Collection<KFunction<*>>
get() = (this as KClassImpl) get() = (this as KClassImpl).data().allNonStaticMembers
.getMembers(memberScope, declaredOnly = false)
.filterNotExtensions() .filterNotExtensions()
.filterIsInstance<KFunction<*>>() .filterIsInstance<KFunction<*>>()
.toList() .toList()
@@ -105,8 +100,7 @@ val KClass<*>.memberFunctions: Collection<KFunction<*>>
* Returns extension functions declared in this class and all of its superclasses. * Returns extension functions declared in this class and all of its superclasses.
*/ */
val KClass<*>.memberExtensionFunctions: Collection<KFunction<*>> val KClass<*>.memberExtensionFunctions: Collection<KFunction<*>>
get() = (this as KClassImpl) get() = (this as KClassImpl).data().allNonStaticMembers
.getMembers(memberScope, declaredOnly = false)
.filterExtensions() .filterExtensions()
.filterIsInstance<KFunction<*>>() .filterIsInstance<KFunction<*>>()
.toList() .toList()
@@ -117,9 +111,7 @@ val KClass<*>.memberExtensionFunctions: Collection<KFunction<*>>
* declared in the class and the superclasses, as well as static methods declared in the class. * declared in the class and the superclasses, as well as static methods declared in the class.
*/ */
val KClass<*>.declaredFunctions: Collection<KFunction<*>> val KClass<*>.declaredFunctions: Collection<KFunction<*>>
get() = (this as KClassImpl) get() = (this as KClassImpl).data().declaredMembers
.getMembers(memberScope, declaredOnly = true)
.plus(getMembers(staticScope, declaredOnly = true))
.filterIsInstance<KFunction<*>>() .filterIsInstance<KFunction<*>>()
.toList() .toList()
@@ -127,8 +119,7 @@ val KClass<*>.declaredFunctions: Collection<KFunction<*>>
* Returns non-extension non-static functions declared in this class. * Returns non-extension non-static functions declared in this class.
*/ */
val KClass<*>.declaredMemberFunctions: Collection<KFunction<*>> val KClass<*>.declaredMemberFunctions: Collection<KFunction<*>>
get() = (this as KClassImpl) get() = (this as KClassImpl).data().declaredNonStaticMembers
.getMembers(memberScope, declaredOnly = true)
.filterNotExtensions() .filterNotExtensions()
.filterIsInstance<KFunction<*>>() .filterIsInstance<KFunction<*>>()
.toList() .toList()
@@ -137,8 +128,7 @@ val KClass<*>.declaredMemberFunctions: Collection<KFunction<*>>
* Returns extension functions declared in this class. * Returns extension functions declared in this class.
*/ */
val KClass<*>.declaredMemberExtensionFunctions: Collection<KFunction<*>> val KClass<*>.declaredMemberExtensionFunctions: Collection<KFunction<*>>
get() = (this as KClassImpl) get() = (this as KClassImpl).data().declaredNonStaticMembers
.getMembers(memberScope, declaredOnly = true)
.filterExtensions() .filterExtensions()
.filterIsInstance<KFunction<*>>() .filterIsInstance<KFunction<*>>()
.toList() .toList()
@@ -148,8 +138,7 @@ val KClass<*>.declaredMemberExtensionFunctions: Collection<KFunction<*>>
* Only properties representing static fields of Java classes are considered static. * Only properties representing static fields of Java classes are considered static.
*/ */
val KClass<*>.staticProperties: Collection<KProperty0<*>> val KClass<*>.staticProperties: Collection<KProperty0<*>>
get() = (this as KClassImpl) get() = (this as KClassImpl).data().allStaticMembers
.getMembers(staticScope, declaredOnly = false)
.filterNotExtensions() .filterNotExtensions()
.filterIsInstance<KProperty0<*>>() .filterIsInstance<KProperty0<*>>()
.toList() .toList()
@@ -158,8 +147,7 @@ val KClass<*>.staticProperties: Collection<KProperty0<*>>
* Returns non-extension properties declared in this class and all of its superclasses. * Returns non-extension properties declared in this class and all of its superclasses.
*/ */
val <T : Any> KClass<T>.memberProperties: Collection<KProperty1<T, *>> val <T : Any> KClass<T>.memberProperties: Collection<KProperty1<T, *>>
get() = (this as KClassImpl<T>) get() = (this as KClassImpl<T>).data().allNonStaticMembers
.getMembers(memberScope, declaredOnly = false)
.filterNotExtensions() .filterNotExtensions()
.filterIsInstance<KProperty1<T, *>>() .filterIsInstance<KProperty1<T, *>>()
.toList() .toList()
@@ -168,8 +156,7 @@ val <T : Any> KClass<T>.memberProperties: Collection<KProperty1<T, *>>
* Returns extension properties declared in this class and all of its superclasses. * Returns extension properties declared in this class and all of its superclasses.
*/ */
val <T : Any> KClass<T>.memberExtensionProperties: Collection<KProperty2<T, *, *>> val <T : Any> KClass<T>.memberExtensionProperties: Collection<KProperty2<T, *, *>>
get() = (this as KClassImpl<T>) get() = (this as KClassImpl<T>).data().allNonStaticMembers
.getMembers(memberScope, declaredOnly = false)
.filterExtensions() .filterExtensions()
.filterIsInstance<KProperty2<T, *, *>>() .filterIsInstance<KProperty2<T, *, *>>()
.toList() .toList()
@@ -178,8 +165,7 @@ val <T : Any> KClass<T>.memberExtensionProperties: Collection<KProperty2<T, *, *
* Returns non-extension properties declared in this class. * Returns non-extension properties declared in this class.
*/ */
val <T : Any> KClass<T>.declaredMemberProperties: Collection<KProperty1<T, *>> val <T : Any> KClass<T>.declaredMemberProperties: Collection<KProperty1<T, *>>
get() = (this as KClassImpl<T>) get() = (this as KClassImpl<T>).data().declaredNonStaticMembers
.getMembers(memberScope, declaredOnly = true)
.filterNotExtensions() .filterNotExtensions()
.filterIsInstance<KProperty1<T, *>>() .filterIsInstance<KProperty1<T, *>>()
.toList() .toList()
@@ -188,8 +174,7 @@ val <T : Any> KClass<T>.declaredMemberProperties: Collection<KProperty1<T, *>>
* Returns extension properties declared in this class. * Returns extension properties declared in this class.
*/ */
val <T : Any> KClass<T>.declaredMemberExtensionProperties: Collection<KProperty2<T, *, *>> val <T : Any> KClass<T>.declaredMemberExtensionProperties: Collection<KProperty2<T, *, *>>
get() = (this as KClassImpl<T>) get() = (this as KClassImpl<T>).data().declaredNonStaticMembers
.getMembers(memberScope, declaredOnly = true)
.filterExtensions() .filterExtensions()
.filterIsInstance<KProperty2<T, *, *>>() .filterIsInstance<KProperty2<T, *, *>>()
.toList() .toList()
@@ -32,10 +32,12 @@ import org.jetbrains.kotlin.resolve.scopes.MemberScope
import org.jetbrains.kotlin.serialization.deserialization.findClassAcrossModuleDependencies import org.jetbrains.kotlin.serialization.deserialization.findClassAcrossModuleDependencies
import kotlin.jvm.internal.TypeIntrinsics import kotlin.jvm.internal.TypeIntrinsics
import kotlin.reflect.* import kotlin.reflect.*
import kotlin.reflect.jvm.internal.KDeclarationContainerImpl.MemberBelonginess.DECLARED
import kotlin.reflect.jvm.internal.KDeclarationContainerImpl.MemberBelonginess.INHERITED
internal class KClassImpl<T : Any>(override val jClass: Class<T>) : internal class KClassImpl<T : Any>(override val jClass: Class<T>) :
KDeclarationContainerImpl(), KClass<T>, KClassifierImpl, KAnnotatedElementImpl { KDeclarationContainerImpl(), KClass<T>, KClassifierImpl, KAnnotatedElementImpl {
private inner class Data : KDeclarationContainerImpl.Data() { inner class Data : KDeclarationContainerImpl.Data() {
val descriptor: ClassDescriptor by ReflectProperties.lazySoft { val descriptor: ClassDescriptor by ReflectProperties.lazySoft {
val classId = classId val classId = classId
val moduleData = data().moduleData val moduleData = data().moduleData
@@ -60,9 +62,26 @@ internal class KClassImpl<T : Any>(override val jClass: Class<T>) :
} }
field.get(null) as T field.get(null) as T
} }
val declaredNonStaticMembers: Sequence<KCallableImpl<*>>
by ReflectProperties.lazySoft { getMembers(memberScope, DECLARED) }
val declaredStaticMembers: Sequence<KCallableImpl<*>>
by ReflectProperties.lazySoft { getMembers(staticScope, DECLARED) }
val inheritedNonStaticMembers: Sequence<KCallableImpl<*>>
by ReflectProperties.lazySoft { getMembers(memberScope, INHERITED) }
val inheritedStaticMembers: Sequence<KCallableImpl<*>>
by ReflectProperties.lazySoft { getMembers(staticScope, INHERITED) }
val allNonStaticMembers: Sequence<KCallableImpl<*>> get() = declaredNonStaticMembers + inheritedNonStaticMembers
val allStaticMembers: Sequence<KCallableImpl<*>> get() = declaredStaticMembers + inheritedStaticMembers
val declaredMembers: Sequence<KCallableImpl<*>> get() = declaredNonStaticMembers + declaredStaticMembers
val allMembers: Collection<KCallable<*>> by ReflectProperties.lazySoft {
(allNonStaticMembers + allStaticMembers).toList()
}
} }
private val data = ReflectProperties.lazy { Data() } val data = ReflectProperties.lazy { Data() }
override val descriptor: ClassDescriptor get() = data().descriptor override val descriptor: ClassDescriptor get() = data().descriptor
@@ -74,8 +93,7 @@ internal class KClassImpl<T : Any>(override val jClass: Class<T>) :
internal val staticScope: MemberScope get() = descriptor.staticScope internal val staticScope: MemberScope get() = descriptor.staticScope
override val members: Collection<KCallable<*>> override val members: Collection<KCallable<*>> get() = data().allMembers
get() = (getMembers(memberScope, declaredOnly = false) + getMembers(staticScope, declaredOnly = false)).toList()
override val constructorDescriptors: Collection<ConstructorDescriptor> override val constructorDescriptors: Collection<ConstructorDescriptor>
get() { get() {
@@ -31,7 +31,7 @@ import kotlin.jvm.internal.ClassBasedDeclarationContainer
import kotlin.reflect.KotlinReflectionInternalError import kotlin.reflect.KotlinReflectionInternalError
internal abstract class KDeclarationContainerImpl : ClassBasedDeclarationContainer { internal abstract class KDeclarationContainerImpl : ClassBasedDeclarationContainer {
protected abstract inner class Data { abstract inner class Data {
// This is stored here on a soft reference to prevent GC from destroying the weak reference to it in the moduleByClassLoader cache // This is stored here on a soft reference to prevent GC from destroying the weak reference to it in the moduleByClassLoader cache
val moduleData: RuntimeModuleData by ReflectProperties.lazySoft { val moduleData: RuntimeModuleData by ReflectProperties.lazySoft {
jClass.getOrCreateModule() jClass.getOrCreateModule()
@@ -47,33 +47,37 @@ internal abstract class KDeclarationContainerImpl : ClassBasedDeclarationContain
abstract fun getFunctions(name: Name): Collection<FunctionDescriptor> abstract fun getFunctions(name: Name): Collection<FunctionDescriptor>
fun getMembers(scope: MemberScope, declaredOnly: Boolean): Sequence<KCallableImpl<*>> { protected fun getMembers(scope: MemberScope, belonginess: MemberBelonginess): Sequence<KCallableImpl<*>> {
val visitor = object : DeclarationDescriptorVisitorEmptyBodies<KCallableImpl<*>?, Unit>() { val visitor = object : DeclarationDescriptorVisitorEmptyBodies<KCallableImpl<*>, Unit>() {
private fun skipCallable(descriptor: CallableMemberDescriptor): Boolean = override fun visitPropertyDescriptor(descriptor: PropertyDescriptor, data: Unit): KCallableImpl<*> =
declaredOnly && !descriptor.kind.isReal createProperty(descriptor)
override fun visitPropertyDescriptor(descriptor: PropertyDescriptor, data: Unit): KCallableImpl<*>? { override fun visitFunctionDescriptor(descriptor: FunctionDescriptor, data: Unit): KCallableImpl<*> =
return if (skipCallable(descriptor)) null else createProperty(descriptor) KFunctionImpl(this@KDeclarationContainerImpl, descriptor)
}
override fun visitFunctionDescriptor(descriptor: FunctionDescriptor, data: Unit): KCallableImpl<*>? { override fun visitConstructorDescriptor(descriptor: ConstructorDescriptor, data: Unit): KCallableImpl<*> =
return if (skipCallable(descriptor)) null else KFunctionImpl(this@KDeclarationContainerImpl, descriptor) throw IllegalStateException("No constructors should appear in this scope: $descriptor")
}
override fun visitConstructorDescriptor(descriptor: ConstructorDescriptor, data: Unit): KCallableImpl<*>? {
throw IllegalStateException("No constructors should appear in this scope: $descriptor")
}
} }
return scope.getContributedDescriptors().asSequence() return scope.getContributedDescriptors().asSequence()
.filter { descriptor -> .filter { descriptor ->
descriptor !is MemberDescriptor || descriptor.visibility != Visibilities.INVISIBLE_FAKE descriptor is CallableMemberDescriptor &&
descriptor.visibility != Visibilities.INVISIBLE_FAKE &&
belonginess.accept(descriptor)
} }
.mapNotNull { descriptor -> .mapNotNull { descriptor ->
descriptor.accept(visitor, Unit) descriptor.accept(visitor, Unit)
} }
} }
protected enum class MemberBelonginess {
DECLARED,
INHERITED;
fun accept(member: CallableMemberDescriptor): Boolean =
member.kind.isReal == (this == DECLARED)
}
private fun createProperty(descriptor: PropertyDescriptor): KPropertyImpl<*> { private fun createProperty(descriptor: PropertyDescriptor): KPropertyImpl<*> {
val receiverCount = (descriptor.dispatchReceiverParameter?.let { 1 } ?: 0) + val receiverCount = (descriptor.dispatchReceiverParameter?.let { 1 } ?: 0) +
(descriptor.extensionReceiverParameter?.let { 1 } ?: 0) (descriptor.extensionReceiverParameter?.let { 1 } ?: 0)
@@ -26,6 +26,7 @@ import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.scopes.MemberScope import org.jetbrains.kotlin.resolve.scopes.MemberScope
import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedCallableMemberDescriptor import org.jetbrains.kotlin.serialization.deserialization.descriptors.DeserializedCallableMemberDescriptor
import kotlin.reflect.KCallable import kotlin.reflect.KCallable
import kotlin.reflect.jvm.internal.KDeclarationContainerImpl.MemberBelonginess.DECLARED
internal class KPackageImpl(override val jClass: Class<*>, val moduleName: String) : KDeclarationContainerImpl() { internal class KPackageImpl(override val jClass: Class<*>, val moduleName: String) : KDeclarationContainerImpl() {
private inner class Data : KDeclarationContainerImpl.Data() { private inner class Data : KDeclarationContainerImpl.Data() {
@@ -48,6 +49,15 @@ internal class KPackageImpl(override val jClass: Class<*>, val moduleName: Strin
jClass jClass
} }
} }
val members: Collection<KCallableImpl<*>> by ReflectProperties.lazySoft {
getMembers(scope, DECLARED).filter { member ->
val callableDescriptor = member.descriptor as DeserializedCallableMemberDescriptor
val packageFragment = callableDescriptor.containingDeclaration as PackageFragmentDescriptor
val source = (packageFragment as? LazyJavaPackageFragment)?.source as? KotlinJvmBinaryPackageSourceElement
(source?.getContainingBinaryClass(callableDescriptor) as? ReflectKotlinClass)?.klass == jClass
}.toList()
}
} }
private val data = ReflectProperties.lazy { Data() } private val data = ReflectProperties.lazy { Data() }
@@ -56,13 +66,7 @@ internal class KPackageImpl(override val jClass: Class<*>, val moduleName: Strin
private val scope: MemberScope get() = data().descriptor.memberScope private val scope: MemberScope get() = data().descriptor.memberScope
override val members: Collection<KCallable<*>> override val members: Collection<KCallable<*>> get() = data().members
get() = getMembers(scope, declaredOnly = false).filter { member ->
val callableDescriptor = member.descriptor as DeserializedCallableMemberDescriptor
val packageFragment = callableDescriptor.containingDeclaration as PackageFragmentDescriptor
val source = (packageFragment as? LazyJavaPackageFragment)?.source as? KotlinJvmBinaryPackageSourceElement
(source?.getContainingBinaryClass(callableDescriptor) as? ReflectKotlinClass)?.klass == jClass
}.toList()
override val constructorDescriptors: Collection<ConstructorDescriptor> override val constructorDescriptors: Collection<ConstructorDescriptor>
get() = emptyList() get() = emptyList()
@@ -23,7 +23,7 @@ import org.jetbrains.annotations.Nullable;
import java.lang.ref.SoftReference; import java.lang.ref.SoftReference;
import java.lang.ref.WeakReference; import java.lang.ref.WeakReference;
/* package */ class ReflectProperties { public class ReflectProperties {
public static abstract class Val<T> { public static abstract class Val<T> {
private static final Object NULL_VALUE = new Object() {}; private static final Object NULL_VALUE = new Object() {};