diff --git a/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirIdePredicateBasedProvider.kt b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirIdePredicateBasedProvider.kt
index e48a0ffbc2e..8df0ed22446 100644
--- a/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirIdePredicateBasedProvider.kt
+++ b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/providers/LLFirIdePredicateBasedProvider.kt
@@ -134,7 +134,7 @@ internal class LLFirIdePredicateBasedProvider(
override fun visitMetaAnnotatedWith(predicate: AbstractPredicate.MetaAnnotatedWith
, data: FirDeclaration): Boolean {
return data.annotations.any { annotation ->
- annotation.markedWithMetaAnnotation(session, data, predicate.metaAnnotations)
+ annotation.markedWithMetaAnnotation(session, data, predicate.metaAnnotations, predicate.includeItself)
}
}
diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/extensions/FirPredicateBasedProviderImpl.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/extensions/FirPredicateBasedProviderImpl.kt
index 3e416d6c030..9d950b2aa03 100644
--- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/extensions/FirPredicateBasedProviderImpl.kt
+++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/extensions/FirPredicateBasedProviderImpl.kt
@@ -140,7 +140,7 @@ class FirPredicateBasedProviderImpl(private val session: FirSession) : FirPredic
override fun visitMetaAnnotatedWith(predicate: AbstractPredicate.MetaAnnotatedWith
, data: FirDeclaration): Boolean {
return data.annotations.any { annotation ->
- annotation.markedWithMetaAnnotation(session, data, predicate.metaAnnotations)
+ annotation.markedWithMetaAnnotation(session, data, predicate.metaAnnotations, predicate.includeItself)
}
}
@@ -190,23 +190,25 @@ class FirPredicateBasedProviderImpl(private val session: FirSession) : FirPredic
fun FirAnnotation.markedWithMetaAnnotation(
session: FirSession,
containingDeclaration: FirDeclaration,
- metaAnnotations: Set
+ metaAnnotations: Set,
+ includeItself: Boolean
): Boolean {
containingDeclaration.symbol.lazyResolveToPhase(FirResolvePhase.COMPILER_REQUIRED_ANNOTATIONS)
return annotationTypeRef.coneTypeSafe()
?.toRegularClassSymbol(session)
- .markedWithMetaAnnotationImpl(session, metaAnnotations, mutableSetOf())
+ .markedWithMetaAnnotationImpl(session, metaAnnotations, includeItself, mutableSetOf())
}
fun FirRegularClassSymbol?.markedWithMetaAnnotationImpl(
session: FirSession,
metaAnnotations: Set,
+ includeItself: Boolean,
visited: MutableSet
): Boolean {
if (this == null) return false
if (!visited.add(this)) return false
- if (this.classId.asSingleFqName() in metaAnnotations) return true
+ if (this.classId.asSingleFqName() in metaAnnotations) return includeItself
return this.resolvedCompilerAnnotationsWithClassIds
.mapNotNull { it.annotationTypeRef.coneTypeSafe()?.toRegularClassSymbol(session) }
- .any { it.markedWithMetaAnnotationImpl(session, metaAnnotations, visited) }
+ .any { it.markedWithMetaAnnotationImpl(session, metaAnnotations, includeItself = true, visited) }
}
diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/plugin/AbstractFirSpecificAnnotationResolveTransformer.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/plugin/AbstractFirSpecificAnnotationResolveTransformer.kt
index 1eb21973c3e..be3a44214c6 100644
--- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/plugin/AbstractFirSpecificAnnotationResolveTransformer.kt
+++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/plugin/AbstractFirSpecificAnnotationResolveTransformer.kt
@@ -144,7 +144,7 @@ internal abstract class AbstractFirSpecificAnnotationResolveTransformer(
}
private fun ConeKotlinType.markedWithMetaAnnotation(session: FirSession, metaAnnotations: Set): Boolean {
- return toRegularClassSymbol(session).markedWithMetaAnnotationImpl(session, metaAnnotations, mutableSetOf())
+ return toRegularClassSymbol(session).markedWithMetaAnnotationImpl(session, metaAnnotations, includeItself = true, mutableSetOf())
}
diff --git a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/AbstractPredicate.kt b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/AbstractPredicate.kt
index add10e3d263..42f03eae325 100644
--- a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/AbstractPredicate.kt
+++ b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/AbstractPredicate.kt
@@ -169,8 +169,13 @@ sealed interface AbstractPredicate> {
/**
* Matches declarations, which are annotated with annotations which are annotated with [metaAnnotations]
+ *
+ * [includeItself] flag determines if declaration, annotated with meta-annotation itself will
+ * be considered as matching to predicate
+ *
* Relation "annotation with meta annotation" is transitive. E.g. in snippet below some declaration will
- * be matched with predicate MetaAnnotatedWith("Ann") if it is annotated with `@Ann`, `@Some` or `@Other`
+ * be matched with predicate MetaAnnotatedWith("Ann") if it is annotated with `@Ann` (if [includeItself] set to true),
+ * `@Some` or `@Other`
*
* @Ann
* annotation class Some
@@ -200,6 +205,8 @@ sealed interface AbstractPredicate
> {
* and can not be used for global lookup
*/
sealed interface MetaAnnotatedWith
> : AbstractPredicate
{
+ val includeItself: Boolean
+
override fun accept(visitor: PredicateVisitor, data: D): R {
return visitor.visitMetaAnnotatedWith(this, data)
}
diff --git a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/DeclarationPredicate.kt b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/DeclarationPredicate.kt
index 5871e39492f..1daaa8d3cef 100644
--- a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/DeclarationPredicate.kt
+++ b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/extensions/predicate/DeclarationPredicate.kt
@@ -91,7 +91,8 @@ sealed class DeclarationPredicate : AbstractPredicate {
// ------------------------------------ MetaAnnotated ------------------------------------
class MetaAnnotatedWith(
- override val metaAnnotations: Set
+ override val metaAnnotations: Set,
+ override val includeItself: Boolean
) : DeclarationPredicate(), AbstractPredicate.MetaAnnotatedWith {
init {
require(metaAnnotations.isNotEmpty()) {
@@ -122,7 +123,8 @@ sealed class DeclarationPredicate : AbstractPredicate {
override fun annotatedOrUnder(vararg annotations: AnnotationFqn): DeclarationPredicate =
annotated(*annotations) or ancestorAnnotated(*annotations)
- fun metaAnnotated(vararg metaAnnotations: AnnotationFqn): DeclarationPredicate = MetaAnnotatedWith(metaAnnotations.toSet())
+ fun metaAnnotated(vararg metaAnnotations: AnnotationFqn, includeItself: Boolean): DeclarationPredicate =
+ MetaAnnotatedWith(metaAnnotations.toSet(), includeItself)
// ------------------- collections -------------------
override fun annotated(annotations: Collection): DeclarationPredicate = AnnotatedWith(annotations.toSet())
@@ -137,7 +139,8 @@ sealed class DeclarationPredicate : AbstractPredicate {
override fun annotatedOrUnder(annotations: Collection): DeclarationPredicate =
annotated(annotations) or ancestorAnnotated(annotations)
- fun metaAnnotated(metaAnnotations: Collection): DeclarationPredicate = MetaAnnotatedWith(metaAnnotations.toSet())
+ fun metaAnnotated(metaAnnotations: Collection, includeItself: Boolean): DeclarationPredicate =
+ MetaAnnotatedWith(metaAnnotations.toSet(), includeItself)
}
companion object {
diff --git a/plugins/allopen/allopen.k2/src/org/jetbrains/kotlin/allopen/fir/FirAllOpenStatusTransformer.kt b/plugins/allopen/allopen.k2/src/org/jetbrains/kotlin/allopen/fir/FirAllOpenStatusTransformer.kt
index f5202413630..c90e8151ffe 100644
--- a/plugins/allopen/allopen.k2/src/org/jetbrains/kotlin/allopen/fir/FirAllOpenStatusTransformer.kt
+++ b/plugins/allopen/allopen.k2/src/org/jetbrains/kotlin/allopen/fir/FirAllOpenStatusTransformer.kt
@@ -57,7 +57,7 @@ class FirAllOpenPredicateMatcher(
override val predicate = DeclarationPredicate.create {
val annotationFqNames = allOpenAnnotationFqNames.map { FqName(it) }
- annotated(annotationFqNames) or metaAnnotated(annotationFqNames)
+ annotated(annotationFqNames) or metaAnnotated(annotationFqNames, includeItself = true)
}
}
diff --git a/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/AllOpenStatusTransformer.kt b/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/AllOpenStatusTransformer.kt
index a2fd9e4e809..8fc0cc13817 100644
--- a/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/AllOpenStatusTransformer.kt
+++ b/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/AllOpenStatusTransformer.kt
@@ -20,7 +20,7 @@ class AllOpenStatusTransformer(session: FirSession) : FirStatusTransformerExtens
companion object {
private val ALL_OPEN = FqName("org.jetbrains.kotlin.fir.plugin.AllOpen")
private val PREDICATE = DeclarationPredicate.create {
- annotatedOrUnder(ALL_OPEN) or metaAnnotated(ALL_OPEN)
+ annotatedOrUnder(ALL_OPEN) or metaAnnotated(ALL_OPEN, includeItself = true)
}
}
diff --git a/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/SomeAdditionalSupertypeGenerator.kt b/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/SomeAdditionalSupertypeGenerator.kt
index a65130bcb27..77809189c16 100644
--- a/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/SomeAdditionalSupertypeGenerator.kt
+++ b/plugins/fir-plugin-prototype/src/org/jetbrains/kotlin/fir/plugin/SomeAdditionalSupertypeGenerator.kt
@@ -31,7 +31,7 @@ class SomeAdditionalSupertypeGenerator(session: FirSession) : FirSupertypeGenera
companion object {
private val myInterfaceClassId = ClassId(FqName("foo"), Name.identifier("MyInterface"))
private val PREDICATE = DeclarationPredicate.create {
- annotated("MyInterfaceSupertype".fqn()) or metaAnnotated("MetaSupertype".fqn())
+ annotated("MyInterfaceSupertype".fqn()) or metaAnnotated("MetaSupertype".fqn(), includeItself = false)
}
}
diff --git a/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.fir.txt b/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.fir.txt
index 83946e67168..ae8417f85f4 100644
--- a/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.fir.txt
+++ b/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.fir.txt
@@ -24,14 +24,14 @@ FILE: main.kt
}
}
- @R|org/jetbrains/kotlin/fir/plugin/MetaSupertype|() public final class Zero : R|kotlin/Any|, R|foo/MyInterface| {
+ @R|org/jetbrains/kotlin/fir/plugin/MetaSupertype|() public final class Zero : R|kotlin/Any| {
public constructor(): R|foo/Zero| {
super()
}
}
public final fun test(a: R|foo/Zero|, b: R|foo/First|, c: R|foo/Second|, d: R|foo/Third|): R|kotlin/Unit| {
- R|/a|.R|foo/MyInterface.foo|()
+ R|/a|.#()
R|/b|.R|foo/MyInterface.foo|()
R|/c|.R|foo/MyInterface.foo|()
R|/d|.R|foo/MyInterface.foo|()
diff --git a/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.kt b/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.kt
index a243326eaf8..f6ade31946d 100644
--- a/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.kt
+++ b/plugins/fir-plugin-prototype/testData/diagnostics/supertypes/metaAnnotationOrder.kt
@@ -21,7 +21,7 @@ class First
class Zero
fun test(a: Zero, b: First, c: Second, d: Third) {
- a.foo()
+ a.foo() // should be an error, because meta predicate has inludeItself = false
b.foo()
c.foo()
d.foo()
diff --git a/plugins/kotlinx-serialization/kotlinx-serialization.k2/src/org/jetbrains/kotlinx/serialization/compiler/fir/FirSerializationPredicates.kt b/plugins/kotlinx-serialization/kotlinx-serialization.k2/src/org/jetbrains/kotlinx/serialization/compiler/fir/FirSerializationPredicates.kt
index 12472398125..08742b84d13 100644
--- a/plugins/kotlinx-serialization/kotlinx-serialization.k2/src/org/jetbrains/kotlinx/serialization/compiler/fir/FirSerializationPredicates.kt
+++ b/plugins/kotlinx-serialization/kotlinx-serialization.k2/src/org/jetbrains/kotlinx/serialization/compiler/fir/FirSerializationPredicates.kt
@@ -13,9 +13,10 @@ object FirSerializationPredicates {
annotated(setOf(SerializationAnnotations.serializerAnnotationFqName)) // @Serializer(for=...)
}
internal val hasMetaAnnotation = DeclarationPredicate.create {
- metaAnnotated(SerializationAnnotations.metaSerializableAnnotationFqName)
+ metaAnnotated(SerializationAnnotations.metaSerializableAnnotationFqName, includeItself = false)
}
internal val annotatedWithSerializableOrMeta = DeclarationPredicate.create {
- annotated(setOf(SerializationAnnotations.serializableAnnotationFqName)) or metaAnnotated(SerializationAnnotations.metaSerializableAnnotationFqName)
+ annotated(setOf(SerializationAnnotations.serializableAnnotationFqName)) or
+ metaAnnotated(SerializationAnnotations.metaSerializableAnnotationFqName, includeItself = false)
}
}
diff --git a/plugins/noarg/noarg.k2/src/org/jetbrains/kotlin/noarg/fir/NoArgAnnotationNameProvider.kt b/plugins/noarg/noarg.k2/src/org/jetbrains/kotlin/noarg/fir/NoArgAnnotationNameProvider.kt
index dc8c3375115..28d0e78dbf8 100644
--- a/plugins/noarg/noarg.k2/src/org/jetbrains/kotlin/noarg/fir/NoArgAnnotationNameProvider.kt
+++ b/plugins/noarg/noarg.k2/src/org/jetbrains/kotlin/noarg/fir/NoArgAnnotationNameProvider.kt
@@ -22,7 +22,7 @@ class FirNoArgPredicateMatcher(
override val predicate = DeclarationPredicate.create {
val annotationFqNames = noArgAnnotationFqNames.map { FqName(it) }
- annotated(annotationFqNames) or metaAnnotated(annotationFqNames)
+ annotated(annotationFqNames) or metaAnnotated(annotationFqNames, includeItself = true)
}
}