[FIR] Remove jvm-specific annotations from common compiler code

^KT-54596 Fixed
This commit is contained in:
Nikolay Lunyak
2023-08-10 15:44:52 +03:00
committed by Space Team
parent f7a2da8f82
commit 986f1624ec
48 changed files with 405 additions and 268 deletions
@@ -12,7 +12,12 @@ import org.jetbrains.kotlin.analysis.api.annotations.KtNamedAnnotationValue
import org.jetbrains.kotlin.analysis.api.fir.annotations.mapAnnotationParameters
import org.jetbrains.kotlin.analysis.api.fir.evaluate.FirAnnotationValueConverter
import org.jetbrains.kotlin.analysis.api.symbols.KtSymbol
import org.jetbrains.kotlin.builtins.StandardNames
import org.jetbrains.kotlin.descriptors.annotations.AnnotationUseSiteTarget
import org.jetbrains.kotlin.fir.FirAnnotationContainer
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.declarations.getAnnotationsByClassId
import org.jetbrains.kotlin.fir.declarations.getStringArgument
import org.jetbrains.kotlin.fir.declarations.toAnnotationClassId
import org.jetbrains.kotlin.fir.diagnostics.ConeDiagnostic
import org.jetbrains.kotlin.fir.diagnostics.ConeStubDiagnostic
@@ -31,6 +36,7 @@ import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeDiagnosticWithSymbol
import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeHiddenCandidateError
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirNamedFunctionSymbol
import org.jetbrains.kotlin.name.JvmNames
import org.jetbrains.kotlin.psi.KtCallElement
import org.jetbrains.kotlin.util.OperatorNameConventions
@@ -116,3 +122,11 @@ internal fun FirAnnotation.toKtAnnotationInfo(
*/
internal val FirResolvedQualifier.isImplicitDispatchReceiver: Boolean
get() = source?.kind == KtFakeSourceElementKind.ImplicitReceiver
fun FirAnnotationContainer.getJvmNameFromAnnotation(session: FirSession, target: AnnotationUseSiteTarget? = null): String? {
val annotationCalls = getAnnotationsByClassId(JvmNames.Annotations.JvmName, session)
return annotationCalls.firstNotNullOfOrNull { call ->
call.getStringArgument(StandardNames.NAME)
?.takeIf { target == null || call.useSiteTarget == target }
}
}
@@ -5,12 +5,7 @@
package org.jetbrains.kotlin.analysis.api.fir.annotations
import org.jetbrains.kotlin.analysis.api.annotations.AnnotationUseSiteTargetFilter
import org.jetbrains.kotlin.analysis.api.annotations.KtAnnotationApplicationInfo
import org.jetbrains.kotlin.analysis.api.annotations.KtAnnotationApplicationWithArgumentsInfo
import org.jetbrains.kotlin.analysis.api.annotations.KtArrayAnnotationValue
import org.jetbrains.kotlin.analysis.api.annotations.KtEnumEntryAnnotationValue
import org.jetbrains.kotlin.analysis.api.annotations.KtNamedAnnotationValue
import org.jetbrains.kotlin.analysis.api.annotations.*
import org.jetbrains.kotlin.analysis.api.fir.toKtAnnotationApplication
import org.jetbrains.kotlin.analysis.api.fir.toKtAnnotationInfo
import org.jetbrains.kotlin.analysis.utils.errors.withClassEntry
@@ -18,23 +13,15 @@ import org.jetbrains.kotlin.descriptors.annotations.KotlinTarget
import org.jetbrains.kotlin.fir.FirAnnotationContainer
import org.jetbrains.kotlin.fir.FirSession
import org.jetbrains.kotlin.fir.containingClassLookupTag
import org.jetbrains.kotlin.fir.declarations.FirResolvePhase
import org.jetbrains.kotlin.fir.declarations.resolvePhase
import org.jetbrains.kotlin.fir.declarations.resolved
import org.jetbrains.kotlin.fir.declarations.toAnnotationClassId
import org.jetbrains.kotlin.fir.declarations.toAnnotationClassIdSafe
import org.jetbrains.kotlin.fir.declarations.*
import org.jetbrains.kotlin.fir.expressions.*
import org.jetbrains.kotlin.fir.references.toResolvedCallableSymbol
import org.jetbrains.kotlin.fir.resolve.transformers.plugin.CompilerRequiredAnnotationsHelper
import org.jetbrains.kotlin.fir.symbols.FirBasedSymbol
import org.jetbrains.kotlin.fir.symbols.resolvedAnnotationsWithArguments
import org.jetbrains.kotlin.fir.symbols.resolvedAnnotationsWithClassIds
import org.jetbrains.kotlin.fir.symbols.resolvedCompilerRequiredAnnotations
import org.jetbrains.kotlin.fir.utils.exceptions.withFirEntry
import org.jetbrains.kotlin.name.CallableId
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.name.StandardClassIds
import org.jetbrains.kotlin.name.*
import org.jetbrains.kotlin.utils.addToStdlib.ifNotEmpty
import org.jetbrains.kotlin.utils.exceptions.checkWithAttachment
import java.lang.annotation.ElementType
@@ -65,7 +52,7 @@ internal fun annotationsByClassId(
.mapIndexedToAnnotationApplication(useSiteTargetFilter, useSiteSession, classId) { index, annotation ->
annotation.asKtAnnotationApplicationForTargetAnnotation(useSiteSession, index)
}
} else if (classId == StandardClassIds.Annotations.Java.Target && firSymbol.fir.resolvePhase < FirResolvePhase.ANNOTATIONS_ARGUMENTS_MAPPING) {
} else if (classId == JvmNames.Annotations.Java.Target && firSymbol.fir.resolvePhase < FirResolvePhase.ANNOTATIONS_ARGUMENTS_MAPPING) {
annotationContainer.resolvedAnnotationsWithClassIds(firSymbol)
.mapIndexedToAnnotationApplication(useSiteTargetFilter, useSiteSession, classId) { index, annotation ->
annotation.asKtAnnotationApplicationForJavaTargetAnnotation(useSiteSession, index)
@@ -140,7 +127,7 @@ private fun FirAnnotation.asKtAnnotationApplicationForJavaTargetAnnotation(
): KtAnnotationApplicationWithArgumentsInfo = asKtAnnotationApplicationForAnnotationWithEnumArgument(
useSiteSession = useSiteSession,
index = index,
expectedEnumClassId = StandardClassIds.Annotations.Java.ElementType,
expectedEnumClassId = JvmNames.Annotations.Java.ElementType,
annotationParameterName = StandardClassIds.Annotations.ParameterNames.value,
nameMapper = { ElementType.values().firstOrNull { enumValue -> enumValue.name == it }?.name },
)
@@ -193,7 +180,7 @@ internal fun hasAnnotation(
useSiteSession: FirSession,
annotationContainer: FirAnnotationContainer = firSymbol.fir,
): Boolean {
return if (firSymbol.isFromCompilerRequiredAnnotationsPhase(classId)) {
return if (firSymbol.isFromCompilerRequiredAnnotationsPhase(classId, useSiteSession)) {
// this loop by index is required to avoid possible ConcurrentModificationException
val annotations = annotationContainer.resolvedCompilerRequiredAnnotations(firSymbol)
for (index in annotations.indices) {
@@ -211,5 +198,7 @@ internal fun hasAnnotation(
}
}
private fun FirBasedSymbol<*>.isFromCompilerRequiredAnnotationsPhase(classId: ClassId): Boolean =
fir.resolvePhase < FirResolvePhase.TYPES && classId in CompilerRequiredAnnotationsHelper.REQUIRED_ANNOTATIONS
private fun FirBasedSymbol<*>.isFromCompilerRequiredAnnotationsPhase(classId: ClassId, session: FirSession): Boolean {
val requiredAnnotations = session.annotationPlatformSupport.requiredAnnotations
return fir.resolvePhase < FirResolvePhase.TYPES && classId in requiredAnnotations
}
@@ -7,6 +7,7 @@ package org.jetbrains.kotlin.analysis.api.fir.components
import org.jetbrains.kotlin.analysis.api.components.KtSymbolInfoProvider
import org.jetbrains.kotlin.analysis.api.fir.KtFirAnalysisSession
import org.jetbrains.kotlin.analysis.api.fir.getJvmNameFromAnnotation
import org.jetbrains.kotlin.analysis.api.fir.symbols.*
import org.jetbrains.kotlin.analysis.api.lifetime.KtLifetimeToken
import org.jetbrains.kotlin.analysis.api.symbols.KtClassOrObjectSymbol
@@ -23,6 +24,7 @@ import org.jetbrains.kotlin.fir.languageVersionSettings
import org.jetbrains.kotlin.fir.symbols.impl.FirBackingFieldSymbol
import org.jetbrains.kotlin.fir.symbols.impl.FirPropertySymbol
import org.jetbrains.kotlin.load.java.JvmAbi
import org.jetbrains.kotlin.name.JvmNames
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.name.StandardClassIds
import org.jetbrains.kotlin.resolve.deprecation.DeprecationInfo
@@ -61,6 +63,7 @@ internal class KtFirSymbolInfoProvider(
// Check the simple names of the Java annotations. While presence of such an annotation name does not prove deprecation, it is a
// necessary condition for it. Type aliases are not a problem here: Java code cannot access Kotlin type aliases. (Currently,
// deprecation annotation type aliases do not work in Kotlin, either, but this might change in the future.)
val deprecationAnnotationSimpleNames = analysisSession.useSiteSession.annotationPlatformSupport.deprecationAnnotationsSimpleNames
return annotationSimpleNames.any { it != null && it in deprecationAnnotationSimpleNames }
}
@@ -127,7 +130,7 @@ internal class KtFirSymbolInfoProvider(
}
private fun getJvmName(property: FirProperty, isSetter: Boolean): Name {
if (property.backingField?.symbol?.hasAnnotation(StandardClassIds.Annotations.JvmField, analysisSession.useSiteSession) == true) {
if (property.backingField?.symbol?.hasAnnotation(JvmNames.Annotations.JvmField, analysisSession.useSiteSession) == true) {
return property.name
}
return Name.identifier(getJvmNameAsString(property, isSetter))
@@ -19,12 +19,11 @@ import org.jetbrains.kotlin.fir.declarations.utils.getExplicitBackingField
import org.jetbrains.kotlin.fir.expressions.*
import org.jetbrains.kotlin.fir.expressions.impl.FirLazyDelegatedConstructorCall
import org.jetbrains.kotlin.fir.extensions.registeredPluginAnnotations
import org.jetbrains.kotlin.fir.resolve.transformers.plugin.CompilerRequiredAnnotationsHelper
import org.jetbrains.kotlin.fir.declarations.annotationPlatformSupport
import org.jetbrains.kotlin.fir.scopes.kotlinScopeProvider
import org.jetbrains.kotlin.fir.types.*
import org.jetbrains.kotlin.fir.visitors.FirTransformer
import org.jetbrains.kotlin.fir.visitors.transformSingle
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.psi.*
internal object FirLazyBodiesCalculator {
@@ -319,15 +318,12 @@ private abstract class FirLazyAnnotationTransformer : FirTransformer<FirLazyAnno
return element
}
private val COMPILER_ANNOTATION_NAMES: Set<Name> = CompilerRequiredAnnotationsHelper.REQUIRED_ANNOTATIONS
.mapTo(mutableSetOf()) { it.shortClassName }
private fun canBeCompilerAnnotation(annotationCall: FirAnnotationCall, session: FirSession): Boolean {
val annotationTypeRef = annotationCall.annotationTypeRef
if (annotationTypeRef !is FirUserTypeRef) return false
if (session.registeredPluginAnnotations.annotations.isNotEmpty()) return true
val name = annotationTypeRef.qualifier.last().name
return name in COMPILER_ANNOTATION_NAMES
return name in session.annotationPlatformSupport.requiredAnnotationsShortClassNames
}
override fun transformResolvedTypeRef(resolvedTypeRef: FirResolvedTypeRef, data: FirLazyAnnotationTransformerData): FirTypeRef {
@@ -33,6 +33,7 @@ import org.jetbrains.kotlin.fir.symbols.lazyResolveToPhase
import org.jetbrains.kotlin.fir.types.FirUserTypeRef
import org.jetbrains.kotlin.analysis.low.level.api.fir.util.forEachDependentDeclaration
import org.jetbrains.kotlin.analysis.low.level.api.fir.util.isScriptDependentDeclaration
import org.jetbrains.kotlin.fir.declarations.annotationPlatformSupport
internal object LLFirCompilerAnnotationsLazyResolver : LLFirLazyResolver(FirResolvePhase.COMPILER_REQUIRED_ANNOTATIONS) {
override fun resolve(
@@ -197,8 +198,9 @@ private class LLFirCompilerRequiredAnnotationsTargetResolver(
fun balanceAnnotations(target: FirElementWithResolveState) {
if (target !is FirProperty) return
val backingField = target.backingField ?: return
val updatedAnnotations = transformer.annotationTransformer.extractBackingFieldAnnotationsFromProperty(
val updatedAnnotations = transformer.session.annotationPlatformSupport.extractBackingFieldAnnotationsFromProperty(
target,
transformer.session,
annotationMap[target].orEmpty(),
annotationMap[backingField].orEmpty(),
) ?: return
@@ -14,6 +14,7 @@ import org.jetbrains.kotlin.builtins.StandardNames
import org.jetbrains.kotlin.load.java.JvmAbi
import org.jetbrains.kotlin.load.java.JvmAnnotationNames
import org.jetbrains.kotlin.name.CallableId
import org.jetbrains.kotlin.name.JvmNames
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.name.StandardClassIds
import java.lang.annotation.ElementType
@@ -143,7 +144,7 @@ private fun javaRetentionArguments(kotlinRetentionName: String?): List<KtNamedAn
name = StandardNames.DEFAULT_VALUE_PARAMETER,
expression = KtEnumEntryAnnotationValue(
callableId = CallableId(
StandardClassIds.Annotations.Java.RetentionPolicy,
JvmNames.Annotations.Java.RetentionPolicy,
Name.identifier(retentionMapping(kotlinRetentionName ?: AnnotationRetention.RUNTIME.name)),
),
sourcePsi = null,
@@ -226,7 +227,7 @@ private fun SymbolLightJavaAnnotation.computeTargetJavaAnnotationArguments(): Li
values = javaTargetNames.map {
KtEnumEntryAnnotationValue(
callableId = CallableId(
classId = StandardClassIds.Annotations.Java.ElementType,
classId = JvmNames.Annotations.Java.ElementType,
callableName = Name.identifier(it),
),
sourcePsi = null,
@@ -9,6 +9,7 @@ import com.intellij.psi.PsiAnnotation
import com.intellij.psi.PsiModifierList
import org.jetbrains.kotlin.light.classes.symbol.toArrayIfNotEmptyOrDefault
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.JvmNames
import org.jetbrains.kotlin.name.StandardClassIds
import org.jetbrains.kotlin.utils.SmartList
import java.util.concurrent.atomic.AtomicReferenceFieldUpdater
@@ -95,7 +96,7 @@ internal class GranularAnnotationsBox(
* @see org.jetbrains.kotlin.fir.resolve.transformers.plugin.CompilerRequiredAnnotationsHelper
*/
private val specialAnnotationsListWithSafeArgumentsResolve: Map<String, ClassId> = listOf(
StandardClassIds.Annotations.JvmRecord,
JvmNames.Annotations.JvmRecord,
).associateBy { it.asFqNameString() }
/**
@@ -22,6 +22,7 @@ import org.jetbrains.kotlin.builtins.StandardNames
import org.jetbrains.kotlin.descriptors.annotations.AnnotationUseSiteTarget
import org.jetbrains.kotlin.light.classes.symbol.classes.SymbolLightClassBase
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.JvmNames
import org.jetbrains.kotlin.name.JvmNames.JVM_OVERLOADS_CLASS_ID
import org.jetbrains.kotlin.name.JvmNames.JVM_SYNTHETIC_ANNOTATION_CLASS_ID
import org.jetbrains.kotlin.name.StandardClassIds
@@ -52,7 +53,7 @@ internal fun KtAnnotatedSymbol.hasJvmSyntheticAnnotation(
internal fun KtAnnotatedSymbol.getJvmNameFromAnnotation(
useSiteTargetFilter: AnnotationUseSiteTargetFilter = AnyAnnotationUseSiteTargetFilter,
): String? {
val annotation = findAnnotation(StandardClassIds.Annotations.JvmName, useSiteTargetFilter)
val annotation = findAnnotation(JvmNames.Annotations.JvmName, useSiteTargetFilter)
return annotation?.let {
(it.arguments.firstOrNull()?.expression as? KtConstantAnnotationValue)?.constantValue?.value as? String
}
@@ -70,7 +71,7 @@ internal fun KtAnnotatedSymbol.isHiddenOrSynthetic(
useSiteTargetFilter: AnnotationUseSiteTargetFilter = annotationUseSiteTarget.toFilter(),
) = isHiddenByDeprecation(this, annotationUseSiteTarget) || hasJvmSyntheticAnnotation(useSiteTargetFilter)
internal fun KtAnnotatedSymbol.hasJvmFieldAnnotation(): Boolean = hasAnnotation(StandardClassIds.Annotations.JvmField)
internal fun KtAnnotatedSymbol.hasJvmFieldAnnotation(): Boolean = hasAnnotation(JvmNames.Annotations.JvmField)
internal fun KtAnnotatedSymbol.hasPublishedApiAnnotation(
useSiteTargetFilter: AnnotationUseSiteTargetFilter = AnyAnnotationUseSiteTargetFilter,
@@ -84,7 +85,7 @@ internal fun KtAnnotatedSymbol.hasJvmOverloadsAnnotation(): Boolean = hasAnnotat
internal fun KtAnnotatedSymbol.hasJvmStaticAnnotation(
useSiteTargetFilter: AnnotationUseSiteTargetFilter = AnyAnnotationUseSiteTargetFilter,
): Boolean = hasAnnotation(StandardClassIds.Annotations.JvmStatic, useSiteTargetFilter)
): Boolean = hasAnnotation(JvmNames.Annotations.JvmStatic, useSiteTargetFilter)
internal fun KtAnnotatedSymbol.hasInlineOnlyAnnotation(): Boolean = hasAnnotation(StandardClassIds.Annotations.InlineOnly)
@@ -109,7 +110,7 @@ internal fun KtAnnotatedSymbol.computeThrowsList(
builder.addReference(java.lang.NullPointerException::class.qualifiedName)
}
val annoApp = findAnnotation(StandardClassIds.Annotations.Throws, useSiteTargetFilter) ?: return
val annoApp = findAnnotation(JvmNames.Annotations.Throws, useSiteTargetFilter) ?: return
fun handleAnnotationValue(annotationValue: KtAnnotationValue) = when (annotationValue) {
is KtArrayAnnotationValue -> {
@@ -49,6 +49,7 @@ import org.jetbrains.kotlin.light.classes.symbol.isJvmField
import org.jetbrains.kotlin.light.classes.symbol.mapType
import org.jetbrains.kotlin.light.classes.symbol.methods.*
import org.jetbrains.kotlin.load.java.JvmAbi
import org.jetbrains.kotlin.name.JvmNames
import org.jetbrains.kotlin.name.StandardClassIds
import org.jetbrains.kotlin.psi.*
import org.jetbrains.kotlin.psi.psiUtil.containingClass
@@ -565,7 +566,7 @@ internal fun KtSymbolWithMembers.createInnerClasses(
if (containingClass is SymbolLightClassForAnnotationClass &&
this is KtNamedClassOrObjectSymbol &&
hasAnnotation(StandardClassIds.Annotations.Repeatable) &&
!hasAnnotation(StandardClassIds.Annotations.Java.Repeatable)
!hasAnnotation(JvmNames.Annotations.Java.Repeatable)
) {
result.add(SymbolLightClassForRepeatableAnnotationContainer(containingClass))
}