From d4825cf4f0f8737c95c00f3b38ee264e229fa2fe Mon Sep 17 00:00:00 2001 From: Alexander Udalov Date: Thu, 20 Aug 2015 16:27:09 -0700 Subject: [PATCH] Support KParameter.kind: instance, extension receiver, or value --- .../reflection/parameters/kinds.kt | 18 +++++++++++++++++ ...lackBoxWithStdlibCodegenTestGenerated.java | 6 ++++++ .../builtins/src/kotlin/reflect/KParameter.kt | 20 +++++++++++++++++++ .../reflect/jvm/internal/KCallableImpl.kt | 6 +++--- .../reflect/jvm/internal/KParameterImpl.kt | 1 + 5 files changed, 48 insertions(+), 3 deletions(-) create mode 100644 compiler/testData/codegen/boxWithStdlib/reflection/parameters/kinds.kt diff --git a/compiler/testData/codegen/boxWithStdlib/reflection/parameters/kinds.kt b/compiler/testData/codegen/boxWithStdlib/reflection/parameters/kinds.kt new file mode 100644 index 00000000000..a6d7b05f6d0 --- /dev/null +++ b/compiler/testData/codegen/boxWithStdlib/reflection/parameters/kinds.kt @@ -0,0 +1,18 @@ +import kotlin.reflect.* +import kotlin.reflect.KParameter.Kind.* +import kotlin.test.assertEquals + +class A { + fun Int.foo(x: String) {} + + inner class Inner(s: String) {} +} + +fun box(): String { + val foo = A::class.memberExtensionFunctions.single() + + assertEquals(listOf(INSTANCE, EXTENSION_RECEIVER, VALUE), foo.parameters.map { it.kind }) + assertEquals(listOf(INSTANCE, VALUE), A::Inner.parameters.map { it.kind }) + + return "OK" +} diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxWithStdlibCodegenTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxWithStdlibCodegenTestGenerated.java index d351566b3cd..df0c4a237ce 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxWithStdlibCodegenTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/generated/BlackBoxWithStdlibCodegenTestGenerated.java @@ -3597,6 +3597,12 @@ public class BlackBoxWithStdlibCodegenTestGenerated extends AbstractBlackBoxCode doTestWithStdlib(fileName); } + @TestMetadata("kinds.kt") + public void testKinds() throws Exception { + String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/boxWithStdlib/reflection/parameters/kinds.kt"); + doTestWithStdlib(fileName); + } + @TestMetadata("propertySetter.kt") public void testPropertySetter() throws Exception { String fileName = JetTestUtils.navigationMetadata("compiler/testData/codegen/boxWithStdlib/reflection/parameters/propertySetter.kt"); diff --git a/core/builtins/src/kotlin/reflect/KParameter.kt b/core/builtins/src/kotlin/reflect/KParameter.kt index f2c5e32eb57..4ff91222d43 100644 --- a/core/builtins/src/kotlin/reflect/KParameter.kt +++ b/core/builtins/src/kotlin/reflect/KParameter.kt @@ -40,4 +40,24 @@ public interface KParameter : KAnnotatedElement { * not the individual element. */ public val type: KType + + /** + * Kind of this parameter. + */ + public val kind: Kind + + /** + * Kind represents a particular position of the parameter declaration in the source code, + * such as an instance, an extension receiver parameter or a value parameter. + */ + public enum class Kind { + /** Instance required to make a call to the member, or an outer class instance for an inner class constructor. */ + INSTANCE, + + /** Extension receiver of an extension function or property. */ + EXTENSION_RECEIVER, + + /** Ordinary named value parameter. */ + VALUE, + } } diff --git a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KCallableImpl.kt b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KCallableImpl.kt index 03d121bb512..5340abd1ae3 100644 --- a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KCallableImpl.kt +++ b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KCallableImpl.kt @@ -36,15 +36,15 @@ interface KCallableImpl : KCallable, KAnnotatedElementImpl { var index = 0 if (descriptor.dispatchReceiverParameter != null) { - result.add(KParameterImpl(this, index++) { descriptor.dispatchReceiverParameter!! }) + result.add(KParameterImpl(this, index++, KParameter.Kind.INSTANCE) { descriptor.dispatchReceiverParameter!! }) } if (descriptor.extensionReceiverParameter != null) { - result.add(KParameterImpl(this, index++) { descriptor.extensionReceiverParameter!! }) + result.add(KParameterImpl(this, index++, KParameter.Kind.EXTENSION_RECEIVER) { descriptor.extensionReceiverParameter!! }) } for (i in descriptor.valueParameters.indices) { - result.add(KParameterImpl(this, index++) { descriptor.valueParameters[i] }) + result.add(KParameterImpl(this, index++, KParameter.Kind.VALUE) { descriptor.valueParameters[i] }) } result.trimToSize() diff --git a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KParameterImpl.kt b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KParameterImpl.kt index d8062b114f8..62611238249 100644 --- a/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KParameterImpl.kt +++ b/core/reflection.jvm/src/kotlin/reflect/jvm/internal/KParameterImpl.kt @@ -25,6 +25,7 @@ import kotlin.reflect.KType class KParameterImpl( val callable: KCallableImpl<*>, override val index: Int, + override val kind: KParameter.Kind, computeDescriptor: () -> ParameterDescriptor ) : KParameter, KAnnotatedElementImpl { private val descriptor: ParameterDescriptor by ReflectProperties.lazySoft(computeDescriptor)