[FE 1.0] Report errors on cycles in annotation parameter types
^KT-47932 ^KT-50753 Fixed
This commit is contained in:
committed by
teamcity
parent
139a800ff7
commit
e9ac24dc33
+12
@@ -1169,6 +1169,18 @@ public class DiagnosisCompilerTestFE10TestdataTestGenerated extends AbstractDiag
|
|||||||
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_after.kt")
|
||||||
|
public void testCycleInParameters_after() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_after.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_before.kt")
|
||||||
|
public void testCycleInParameters_before() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_before.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("DanglingMixed.kt")
|
@TestMetadata("DanglingMixed.kt")
|
||||||
public void testDanglingMixed() throws Exception {
|
public void testDanglingMixed() throws Exception {
|
||||||
|
|||||||
+12
@@ -1169,6 +1169,18 @@ public class FirOldFrontendDiagnosticsTestGenerated extends AbstractFirDiagnosti
|
|||||||
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_after.kt")
|
||||||
|
public void testCycleInParameters_after() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_after.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_before.kt")
|
||||||
|
public void testCycleInParameters_before() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_before.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("DanglingMixed.kt")
|
@TestMetadata("DanglingMixed.kt")
|
||||||
public void testDanglingMixed() throws Exception {
|
public void testDanglingMixed() throws Exception {
|
||||||
|
|||||||
+12
@@ -1169,6 +1169,18 @@ public class FirOldFrontendDiagnosticsWithLightTreeTestGenerated extends Abstrac
|
|||||||
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_after.kt")
|
||||||
|
public void testCycleInParameters_after() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_after.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_before.kt")
|
||||||
|
public void testCycleInParameters_before() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_before.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("DanglingMixed.kt")
|
@TestMetadata("DanglingMixed.kt")
|
||||||
public void testDanglingMixed() throws Exception {
|
public void testDanglingMixed() throws Exception {
|
||||||
|
|||||||
@@ -300,6 +300,7 @@ public interface Errors {
|
|||||||
DiagnosticFactory0<KtAnnotatedExpression> ANNOTATIONS_ON_BLOCK_LEVEL_EXPRESSION_ON_THE_SAME_LINE = DiagnosticFactory0.create(WARNING);
|
DiagnosticFactory0<KtAnnotatedExpression> ANNOTATIONS_ON_BLOCK_LEVEL_EXPRESSION_ON_THE_SAME_LINE = DiagnosticFactory0.create(WARNING);
|
||||||
DiagnosticFactory0<KtAnnotationEntry> ANNOTATION_USED_AS_ANNOTATION_ARGUMENT = DiagnosticFactory0.create(ERROR);
|
DiagnosticFactory0<KtAnnotationEntry> ANNOTATION_USED_AS_ANNOTATION_ARGUMENT = DiagnosticFactory0.create(ERROR);
|
||||||
DiagnosticFactory0<KtExpression> ANNOTATION_ARGUMENT_IS_NON_CONST = DiagnosticFactory0.create(WARNING);
|
DiagnosticFactory0<KtExpression> ANNOTATION_ARGUMENT_IS_NON_CONST = DiagnosticFactory0.create(WARNING);
|
||||||
|
DiagnosticFactoryForDeprecation0<KtParameter> CYCLE_IN_ANNOTATION_PARAMETER = DiagnosticFactoryForDeprecation0.create(LanguageFeature.ProhibitCyclesInAnnotations);
|
||||||
|
|
||||||
DiagnosticFactoryForDeprecation0<PsiElement> RESTRICTED_RETENTION_FOR_EXPRESSION_ANNOTATION =
|
DiagnosticFactoryForDeprecation0<PsiElement> RESTRICTED_RETENTION_FOR_EXPRESSION_ANNOTATION =
|
||||||
DiagnosticFactoryForDeprecation0.create(LanguageFeature.RestrictRetentionForExpressionAnnotations);
|
DiagnosticFactoryForDeprecation0.create(LanguageFeature.RestrictRetentionForExpressionAnnotations);
|
||||||
|
|||||||
+1
@@ -1001,6 +1001,7 @@ public class DefaultErrorMessages {
|
|||||||
|
|
||||||
MAP.put(ANNOTATION_USED_AS_ANNOTATION_ARGUMENT, "An annotation can't be used as the annotations argument");
|
MAP.put(ANNOTATION_USED_AS_ANNOTATION_ARGUMENT, "An annotation can't be used as the annotations argument");
|
||||||
MAP.put(ANNOTATION_ARGUMENT_IS_NON_CONST, "An annotation argument must be a compile-time constant");
|
MAP.put(ANNOTATION_ARGUMENT_IS_NON_CONST, "An annotation argument must be a compile-time constant");
|
||||||
|
MAP.put(CYCLE_IN_ANNOTATION_PARAMETER, "Type of this parameter is cyclic");
|
||||||
|
|
||||||
MAP.put(RESTRICTED_RETENTION_FOR_EXPRESSION_ANNOTATION,
|
MAP.put(RESTRICTED_RETENTION_FOR_EXPRESSION_ANNOTATION,
|
||||||
"Expression annotations with retention other than SOURCE are prohibited");
|
"Expression annotations with retention other than SOURCE are prohibited");
|
||||||
|
|||||||
@@ -49,6 +49,7 @@ private val DEFAULT_DECLARATION_CHECKERS = listOf(
|
|||||||
EnumCompanionInEnumConstructorCallChecker,
|
EnumCompanionInEnumConstructorCallChecker,
|
||||||
ContextualDeclarationChecker,
|
ContextualDeclarationChecker,
|
||||||
ValueParameterUsageInDefaultArgumentChecker,
|
ValueParameterUsageInDefaultArgumentChecker,
|
||||||
|
CyclicAnnotationsChecker,
|
||||||
)
|
)
|
||||||
|
|
||||||
private val DEFAULT_CALL_CHECKERS = listOf(
|
private val DEFAULT_CALL_CHECKERS = listOf(
|
||||||
|
|||||||
+86
@@ -0,0 +1,86 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||||
|
* 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.resolve.checkers
|
||||||
|
|
||||||
|
import org.jetbrains.kotlin.builtins.ReflectionTypes
|
||||||
|
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||||
|
import org.jetbrains.kotlin.descriptors.ClassKind
|
||||||
|
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||||
|
import org.jetbrains.kotlin.descriptors.ValueParameterDescriptor
|
||||||
|
import org.jetbrains.kotlin.diagnostics.Errors.CYCLE_IN_ANNOTATION_PARAMETER
|
||||||
|
import org.jetbrains.kotlin.psi.KtClass
|
||||||
|
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||||
|
import org.jetbrains.kotlin.types.UnwrappedType
|
||||||
|
|
||||||
|
object CyclicAnnotationsChecker : DeclarationChecker {
|
||||||
|
override fun check(declaration: KtDeclaration, descriptor: DeclarationDescriptor, context: DeclarationCheckerContext) {
|
||||||
|
if (
|
||||||
|
declaration !is KtClass || !declaration.isAnnotation() ||
|
||||||
|
descriptor !is ClassDescriptor || descriptor.kind != ClassKind.ANNOTATION_CLASS
|
||||||
|
) return
|
||||||
|
|
||||||
|
val primaryConstructor = declaration.primaryConstructor ?: return
|
||||||
|
val primaryConstructorDescriptor = descriptor.unsubstitutedPrimaryConstructor ?: return
|
||||||
|
|
||||||
|
val checker = Checker(descriptor)
|
||||||
|
|
||||||
|
for ((parameter, parameterDescriptor) in primaryConstructor.valueParameters.zip(primaryConstructorDescriptor.valueParameters)) {
|
||||||
|
if (checker.parameterHasCycle(descriptor, parameterDescriptor)) {
|
||||||
|
context.trace.report(CYCLE_IN_ANNOTATION_PARAMETER.on(context.languageVersionSettings, parameter))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private class Checker(val targetAnnotation: ClassDescriptor) {
|
||||||
|
private val visitedAnnotationDescriptors = mutableSetOf(targetAnnotation)
|
||||||
|
private val annotationDescriptorsWithCycle = mutableSetOf(targetAnnotation)
|
||||||
|
|
||||||
|
fun annotationHasCycle(annotationDescriptor: ClassDescriptor): Boolean {
|
||||||
|
val constructorDescriptor = annotationDescriptor.unsubstitutedPrimaryConstructor ?: return false
|
||||||
|
|
||||||
|
for (parameterDescriptor in constructorDescriptor.valueParameters) {
|
||||||
|
if (parameterHasCycle(annotationDescriptor, parameterDescriptor)) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
fun parameterHasCycle(ownedAnnotation: ClassDescriptor, parameterDescriptor: ValueParameterDescriptor): Boolean {
|
||||||
|
val returnType = parameterDescriptor.returnType?.unwrap() ?: return false
|
||||||
|
return when {
|
||||||
|
returnType.arguments.isNotEmpty() && !ReflectionTypes.isKClassType(returnType) -> {
|
||||||
|
for (argument in returnType.arguments) {
|
||||||
|
if (!argument.isStarProjection) {
|
||||||
|
if (typeHasCycle(ownedAnnotation, argument.type.unwrap())) return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
false
|
||||||
|
}
|
||||||
|
else -> typeHasCycle(ownedAnnotation, returnType)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun typeHasCycle(ownedAnnotation: ClassDescriptor, type: UnwrappedType): Boolean {
|
||||||
|
val referencedAnnotationDescriptor = (type.constructor.declarationDescriptor as? ClassDescriptor)
|
||||||
|
?.takeIf { it.kind == ClassKind.ANNOTATION_CLASS }
|
||||||
|
?: return false
|
||||||
|
if (!visitedAnnotationDescriptors.add(referencedAnnotationDescriptor)) {
|
||||||
|
return (referencedAnnotationDescriptor in annotationDescriptorsWithCycle).also {
|
||||||
|
if (it) {
|
||||||
|
annotationDescriptorsWithCycle += ownedAnnotation
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (referencedAnnotationDescriptor == targetAnnotation) {
|
||||||
|
annotationDescriptorsWithCycle += ownedAnnotation
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
return annotationHasCycle(referencedAnnotationDescriptor)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
+15
@@ -0,0 +1,15 @@
|
|||||||
|
// WITH_REFLECT
|
||||||
|
// LANGUAGE: +ProhibitCyclesInAnnotations
|
||||||
|
// ISSUE: KT-47932
|
||||||
|
|
||||||
|
import kotlin.reflect.KClass
|
||||||
|
|
||||||
|
annotation class X(val value: X) // error
|
||||||
|
annotation class Y(val value: Array<Y>) // error
|
||||||
|
|
||||||
|
annotation class Z1(val a: Z2, val b: Z2) // error
|
||||||
|
annotation class Z2(val value: Z1) // error
|
||||||
|
|
||||||
|
annotation class A(val x: KClass<A>) // OK
|
||||||
|
annotation class B(val x: KClass<B>) // OK
|
||||||
|
annotation class C(val b: B) // OK
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
// WITH_REFLECT
|
||||||
|
// LANGUAGE: +ProhibitCyclesInAnnotations
|
||||||
|
// ISSUE: KT-47932
|
||||||
|
|
||||||
|
import kotlin.reflect.KClass
|
||||||
|
|
||||||
|
annotation class X(<!CYCLE_IN_ANNOTATION_PARAMETER_ERROR!>val value: X<!>) // error
|
||||||
|
annotation class Y(<!CYCLE_IN_ANNOTATION_PARAMETER_ERROR!>val value: Array<Y><!>) // error
|
||||||
|
|
||||||
|
annotation class Z1(<!CYCLE_IN_ANNOTATION_PARAMETER_ERROR!>val a: Z2<!>, <!CYCLE_IN_ANNOTATION_PARAMETER_ERROR!>val b: Z2<!>) // error
|
||||||
|
annotation class Z2(<!CYCLE_IN_ANNOTATION_PARAMETER_ERROR!>val value: Z1<!>) // error
|
||||||
|
|
||||||
|
annotation class A(val x: KClass<A>) // OK
|
||||||
|
annotation class B(val x: KClass<B>) // OK
|
||||||
|
annotation class C(val b: B) // OK
|
||||||
@@ -0,0 +1,58 @@
|
|||||||
|
package
|
||||||
|
|
||||||
|
public final annotation class A : kotlin.Annotation {
|
||||||
|
public constructor A(/*0*/ x: kotlin.reflect.KClass<A>)
|
||||||
|
public final val x: kotlin.reflect.KClass<A>
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class B : kotlin.Annotation {
|
||||||
|
public constructor B(/*0*/ x: kotlin.reflect.KClass<B>)
|
||||||
|
public final val x: kotlin.reflect.KClass<B>
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class C : kotlin.Annotation {
|
||||||
|
public constructor C(/*0*/ b: B)
|
||||||
|
public final val b: B
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class X : kotlin.Annotation {
|
||||||
|
public constructor X(/*0*/ value: X)
|
||||||
|
public final val value: X
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class Y : kotlin.Annotation {
|
||||||
|
public constructor Y(/*0*/ value: kotlin.Array<Y>)
|
||||||
|
public final val value: kotlin.Array<Y>
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class Z1 : kotlin.Annotation {
|
||||||
|
public constructor Z1(/*0*/ a: Z2, /*1*/ b: Z2)
|
||||||
|
public final val a: Z2
|
||||||
|
public final val b: Z2
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class Z2 : kotlin.Annotation {
|
||||||
|
public constructor Z2(/*0*/ value: Z1)
|
||||||
|
public final val value: Z1
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
+15
@@ -0,0 +1,15 @@
|
|||||||
|
// WITH_REFLECT
|
||||||
|
// LANGUAGE: -ProhibitCyclesInAnnotations
|
||||||
|
// ISSUE: KT-47932
|
||||||
|
|
||||||
|
import kotlin.reflect.KClass
|
||||||
|
|
||||||
|
annotation class X(val value: X) // error
|
||||||
|
annotation class Y(val value: Array<Y>) // error
|
||||||
|
|
||||||
|
annotation class Z1(val a: Z2, val b: Z2) // error
|
||||||
|
annotation class Z2(val value: Z1) // error
|
||||||
|
|
||||||
|
annotation class A(val x: KClass<A>) // OK
|
||||||
|
annotation class B(val x: KClass<B>) // OK
|
||||||
|
annotation class C(val b: B) // OK
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
// WITH_REFLECT
|
||||||
|
// LANGUAGE: -ProhibitCyclesInAnnotations
|
||||||
|
// ISSUE: KT-47932
|
||||||
|
|
||||||
|
import kotlin.reflect.KClass
|
||||||
|
|
||||||
|
annotation class X(<!CYCLE_IN_ANNOTATION_PARAMETER_WARNING!>val value: X<!>) // error
|
||||||
|
annotation class Y(<!CYCLE_IN_ANNOTATION_PARAMETER_WARNING!>val value: Array<Y><!>) // error
|
||||||
|
|
||||||
|
annotation class Z1(<!CYCLE_IN_ANNOTATION_PARAMETER_WARNING!>val a: Z2<!>, <!CYCLE_IN_ANNOTATION_PARAMETER_WARNING!>val b: Z2<!>) // error
|
||||||
|
annotation class Z2(<!CYCLE_IN_ANNOTATION_PARAMETER_WARNING!>val value: Z1<!>) // error
|
||||||
|
|
||||||
|
annotation class A(val x: KClass<A>) // OK
|
||||||
|
annotation class B(val x: KClass<B>) // OK
|
||||||
|
annotation class C(val b: B) // OK
|
||||||
@@ -0,0 +1,59 @@
|
|||||||
|
package
|
||||||
|
|
||||||
|
public final annotation class A : kotlin.Annotation {
|
||||||
|
public constructor A(/*0*/ x: kotlin.reflect.KClass<A>)
|
||||||
|
public final val x: kotlin.reflect.KClass<A>
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class B : kotlin.Annotation {
|
||||||
|
public constructor B(/*0*/ x: kotlin.reflect.KClass<B>)
|
||||||
|
public final val x: kotlin.reflect.KClass<B>
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class C : kotlin.Annotation {
|
||||||
|
public constructor C(/*0*/ b: B)
|
||||||
|
public final val b: B
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class X : kotlin.Annotation {
|
||||||
|
public constructor X(/*0*/ value: X)
|
||||||
|
public final val value: X
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class Y : kotlin.Annotation {
|
||||||
|
public constructor Y(/*0*/ value: kotlin.Array<Y>)
|
||||||
|
public final val value: kotlin.Array<Y>
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class Z1 : kotlin.Annotation {
|
||||||
|
public constructor Z1(/*0*/ a: Z2, /*1*/ b: Z2)
|
||||||
|
public final val a: Z2
|
||||||
|
public final val b: Z2
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
|
public final annotation class Z2 : kotlin.Annotation {
|
||||||
|
public constructor Z2(/*0*/ value: Z1)
|
||||||
|
public final val value: Z1
|
||||||
|
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||||
|
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||||
|
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||||
|
}
|
||||||
|
|
||||||
Generated
+12
@@ -1169,6 +1169,18 @@ public class DiagnosticTestGenerated extends AbstractDiagnosticTest {
|
|||||||
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
runTest("compiler/testData/diagnostics/tests/annotations/ConstructorCallAllowed.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_after.kt")
|
||||||
|
public void testCycleInParameters_after() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_after.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@TestMetadata("cycleInParameters_before.kt")
|
||||||
|
public void testCycleInParameters_before() throws Exception {
|
||||||
|
runTest("compiler/testData/diagnostics/tests/annotations/cycleInParameters_before.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@TestMetadata("DanglingInScript.kts")
|
@TestMetadata("DanglingInScript.kts")
|
||||||
public void testDanglingInScript() throws Exception {
|
public void testDanglingInScript() throws Exception {
|
||||||
|
|||||||
@@ -259,6 +259,7 @@ enum class LanguageFeature(
|
|||||||
ProhibitIllegalValueParameterUsageInDefaultArguments(KOTLIN_1_9, kind = BUG_FIX), // KT-25694
|
ProhibitIllegalValueParameterUsageInDefaultArguments(KOTLIN_1_9, kind = BUG_FIX), // KT-25694
|
||||||
ProhibitConstructorCallOnFunctionalSupertype(KOTLIN_1_9, kind = BUG_FIX), // KT-46344
|
ProhibitConstructorCallOnFunctionalSupertype(KOTLIN_1_9, kind = BUG_FIX), // KT-46344
|
||||||
ProhibitArrayLiteralsInCompanionOfAnnotation(KOTLIN_1_9, kind = BUG_FIX), // KT-39041
|
ProhibitArrayLiteralsInCompanionOfAnnotation(KOTLIN_1_9, kind = BUG_FIX), // KT-39041
|
||||||
|
ProhibitCyclesInAnnotations(KOTLIN_1_9, kind = BUG_FIX), // KT-49110
|
||||||
|
|
||||||
// Temporarily disabled, see KT-27084/KT-22379
|
// Temporarily disabled, see KT-27084/KT-22379
|
||||||
SoundSmartcastFromLoopConditionForLoopAssignedVariables(sinceVersion = null, kind = BUG_FIX),
|
SoundSmartcastFromLoopConditionForLoopAssignedVariables(sinceVersion = null, kind = BUG_FIX),
|
||||||
|
|||||||
@@ -17,7 +17,9 @@ import org.jetbrains.kotlin.incremental.components.NoLookupLocation
|
|||||||
import org.jetbrains.kotlin.name.ClassId
|
import org.jetbrains.kotlin.name.ClassId
|
||||||
import org.jetbrains.kotlin.name.FqNameUnsafe
|
import org.jetbrains.kotlin.name.FqNameUnsafe
|
||||||
import org.jetbrains.kotlin.name.Name
|
import org.jetbrains.kotlin.name.Name
|
||||||
|
import org.jetbrains.kotlin.name.StandardClassIds
|
||||||
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
import org.jetbrains.kotlin.resolve.DescriptorUtils
|
||||||
|
import org.jetbrains.kotlin.resolve.descriptorUtil.classId
|
||||||
import org.jetbrains.kotlin.resolve.scopes.MemberScope
|
import org.jetbrains.kotlin.resolve.scopes.MemberScope
|
||||||
import org.jetbrains.kotlin.types.*
|
import org.jetbrains.kotlin.types.*
|
||||||
import org.jetbrains.kotlin.util.capitalizeDecapitalize.capitalizeAsciiOnly
|
import org.jetbrains.kotlin.util.capitalizeDecapitalize.capitalizeAsciiOnly
|
||||||
@@ -99,6 +101,11 @@ class ReflectionTypes(module: ModuleDescriptor, private val notFoundClasses: Not
|
|||||||
return containingPackage != null && containingPackage.fqName == KOTLIN_REFLECT_FQ_NAME
|
return containingPackage != null && containingPackage.fqName == KOTLIN_REFLECT_FQ_NAME
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun isKClassType(type: KotlinType): Boolean {
|
||||||
|
val descriptor = type.unwrap().constructor.declarationDescriptor ?: return false
|
||||||
|
return descriptor.classId == StandardClassIds.KClass
|
||||||
|
}
|
||||||
|
|
||||||
fun isCallableType(type: KotlinType): Boolean =
|
fun isCallableType(type: KotlinType): Boolean =
|
||||||
type.isFunctionTypeOrSubtype || type.isSuspendFunctionTypeOrSubtype || isKCallableType(type)
|
type.isFunctionTypeOrSubtype || type.isSuspendFunctionTypeOrSubtype || isKCallableType(type)
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user