Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rollback custom constant value evaluator #2096

Merged
merged 1 commit into from
Sep 11, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -37,16 +37,11 @@ import org.jetbrains.kotlin.analysis.api.annotations.KaAnnotated
import org.jetbrains.kotlin.analysis.api.annotations.KaAnnotation
import org.jetbrains.kotlin.analysis.api.annotations.KaAnnotationValue
import org.jetbrains.kotlin.analysis.api.components.KaSubstitutorBuilder
import org.jetbrains.kotlin.analysis.api.fir.KaSymbolByFirBuilder
import org.jetbrains.kotlin.analysis.api.fir.evaluate.FirAnnotationValueConverter
import org.jetbrains.kotlin.analysis.api.fir.symbols.KaFirSymbol
import org.jetbrains.kotlin.analysis.api.fir.symbols.KaFirValueParameterSymbol
import org.jetbrains.kotlin.analysis.api.fir.types.KaFirFunctionType
import org.jetbrains.kotlin.analysis.api.fir.types.KaFirType
import org.jetbrains.kotlin.analysis.api.impl.base.annotations.KaAnnotationImpl
import org.jetbrains.kotlin.analysis.api.impl.base.annotations.KaArrayAnnotationValueImpl
import org.jetbrains.kotlin.analysis.api.impl.base.annotations.KaClassLiteralAnnotationValueImpl
import org.jetbrains.kotlin.analysis.api.impl.base.annotations.KaNestedAnnotationAnnotationValueImpl
import org.jetbrains.kotlin.analysis.api.impl.base.types.KaBaseStarTypeProjection
import org.jetbrains.kotlin.analysis.api.impl.base.types.KaBaseTypeArgumentWithVariance
import org.jetbrains.kotlin.analysis.api.platform.lifetime.KotlinAlwaysAccessibleLifetimeToken
Expand All @@ -62,15 +57,9 @@ import org.jetbrains.kotlin.codegen.state.md5base64
import org.jetbrains.kotlin.fir.analysis.checkers.getContainingClassSymbol
import org.jetbrains.kotlin.fir.declarations.FirRegularClass
import org.jetbrains.kotlin.fir.declarations.FirResolvePhase
import org.jetbrains.kotlin.fir.declarations.getTargetType
import org.jetbrains.kotlin.fir.declarations.utils.moduleName
import org.jetbrains.kotlin.fir.expressions.FirAnnotation
import org.jetbrains.kotlin.fir.expressions.FirArrayLiteral
import org.jetbrains.kotlin.fir.expressions.FirExpression
import org.jetbrains.kotlin.fir.expressions.FirGetClassCall
import org.jetbrains.kotlin.fir.java.JavaTypeParameterStack
import org.jetbrains.kotlin.fir.java.toFirExpression
import org.jetbrains.kotlin.fir.resolve.fullyExpandedType
import org.jetbrains.kotlin.fir.symbols.SymbolInternals
import org.jetbrains.kotlin.fir.symbols.lazyResolveToPhase
import org.jetbrains.kotlin.fir.types.*
Expand Down Expand Up @@ -551,48 +540,6 @@ internal fun KaAnnotationValue.toValue(): Any? = when (this) {

@OptIn(SymbolInternals::class, KaImplementationDetail::class, KaExperimentalApi::class)
internal fun KaValueParameterSymbol.getDefaultValue(): KaAnnotationValue? {
fun FirExpression.toValue(builder: KaSymbolByFirBuilder): KaAnnotationValue? {
if (this is FirAnnotation) {
val classId = ClassId.fromString(
(annotationTypeRef.coneType as? ConeLookupTagBasedType)?.lookupTag.toString()
)
return KaNestedAnnotationAnnotationValueImpl(
KaAnnotationImpl(
JavaToKotlinClassMap.mapJavaToKotlinIncludingClassMapping(
classId.asSingleFqName()
) ?: classId,
null,
null,
lazyOf(emptyList()),
null,
KotlinAlwaysAccessibleLifetimeToken(ResolverAAImpl.ktModule.project)
),
KotlinAlwaysAccessibleLifetimeToken(ResolverAAImpl.ktModule.project)
)
}
if (this is FirArrayLiteral) {
return KaArrayAnnotationValueImpl(argumentList.arguments.mapNotNull { it.toValue(builder) }, null, token)
}
return if (this is FirGetClassCall) {
var coneType = this.getTargetType()?.fullyExpandedType(builder.rootSession)
// FirAnnotationValueConverter expects fir type, while the type parsed from libraries are modeled
// as flexible type, for it to be used in argument of KClass values, it needs to be unwrapped.
if (coneType is ConeFlexibleType) {
coneType = coneType.lowerBound
}

if (coneType is ConeClassLikeType && coneType !is ConeErrorType) {
val classId = JavaToKotlinClassMap
.mapJavaToKotlinIncludingClassMapping(coneType.lookupTag.classId.asSingleFqName())
val type = builder.typeBuilder.buildKtType(coneType).convertToKotlinType()
KaClassLiteralAnnotationValueImpl(type, classId, null, token)
} else {
null
}
} else {
FirAnnotationValueConverter.toConstantValue(this, builder)
}
}
return this.psi.let { psiElement ->
when (psiElement) {
is KtParameter -> analyze {
Expand Down Expand Up @@ -645,7 +592,7 @@ internal fun KaValueParameterSymbol.getDefaultValue(): KaAnnotationValue? {
// will produce empty array for array type values and `null` for the rest of value types.
val expression = (defaultValue ?: JavaUnknownAnnotationArgumentImpl(null))
.toFirExpression(firSession, JavaTypeParameterStack.EMPTY, expectedTypeRef, null)
expression.toValue(symbolBuilder)
FirAnnotationValueConverter.toConstantValue(expression, symbolBuilder)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,10 @@
// [warning1, warning 2]
// Sub: [i:42]
// TestJavaLib: OtherAnnotation
// TestNestedAnnotationDefaults: def
// TestNestedAnnotationDefaults: hij
// TestNestedAnnotationDefaults: def
// TestNestedAnnotationDefaults: hij
// END
// MODULE: module1
// FILE: placeholder.kt
Expand Down Expand Up @@ -71,6 +75,9 @@ public @interface JavaAnnotationWithDefaults {
OtherAnnotation otherAnnotationVal() default @OtherAnnotation("def");
}

// FILE: KotlinAnnotationWithDefaults.kt
annotation class KotlinAnnotationWithDefaults(val otherAnnotation: OtherAnnotation = OtherAnnotation("hij"))

// MODULE: main(module1)
// FILE: Test.java
@MyAnnotation(stringParam = "2") class MyClass implements MyInterface {}
Expand Down Expand Up @@ -137,3 +144,18 @@ class Sub implements @B(a = @A(i = 42)) Parent {}
// FILE: TestJavaLib.java
@JavaAnnotationWithDefaults
class TestJavaLib {}

// FILE: JavaAnnotationWithDefaultsInSource.java
public @interface JavaAnnotationWithDefaultsInSource {
OtherAnnotation otherAnnotationVal() default @OtherAnnotation("def");
}

// FILE: KotlinAnnotationWithDefaults.kt
annotation class KotlinAnnotationWithDefaultsInSource(val otherAnnotation: OtherAnnotation = OtherAnnotation("hij"))

// FILE: KotlinClient.kt
@JavaAnnotationWithDefaultsInSource
@KotlinAnnotationWithDefaultsInSource
@JavaAnnotationWithDefaults
@KotlinAnnotationWithDefaults
class TestNestedAnnotationDefaults
22 changes: 22 additions & 0 deletions kotlin-analysis-api/testData/annotationValue/annotationValue_kt.kt
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,10 @@
// Cls: argToA: b
// Cls: argToB: 42
// TestJavaLib: OtherAnnotation
// TestNestedAnnotationDefaults: def
// TestNestedAnnotationDefaults: hij
// TestNestedAnnotationDefaults: def
// TestNestedAnnotationDefaults: hij
// END
// MODULE: module1
// FILE: placeholder.kt
Expand Down Expand Up @@ -72,6 +76,9 @@ public @interface JavaAnnotationWithDefaults {
OtherAnnotation otherAnnotationVal() default @OtherAnnotation("def");
}

// FILE: KotlinAnnotationWithDefaults.kt
annotation class KotlinAnnotationWithDefaults(val otherAnnotation: OtherAnnotation = OtherAnnotation("hij"))

// MODULE: main(module1)
// FILE: a.kt

Expand Down Expand Up @@ -150,3 +157,18 @@ class Sub : @B(a = A(i = 42)) Parent
// FILE: TestJavaLib.kt
@JavaAnnotationWithDefaults
class TestJavaLib

// FILE: JavaAnnotationWithDefaultsInSource.java
public @interface JavaAnnotationWithDefaultsInSource {
OtherAnnotation otherAnnotationVal() default @OtherAnnotation("def");
}

// FILE: KotlinAnnotationWithDefaultsInSource.kt
annotation class KotlinAnnotationWithDefaultsInSource(val otherAnnotation: OtherAnnotation = OtherAnnotation("hij"))

// FILE: TestNestedAnnotationDefaults.java
@JavaAnnotationWithDefaultsInSource
@KotlinAnnotationWithDefaultsInSource
@JavaAnnotationWithDefaults
@KotlinAnnotationWithDefaults
class TestNestedAnnotationDefaults {}
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
// TEST PROCESSOR: DefaultKClassValueProcessor
// EXPECTED:
// java.lang.String
// kotlin.String
// kotlin.String
// kotlin.String
// java.lang.String
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Given annotation class ExampleAnnotation(val value: kotlin.reflect.KClass<*> = java.lang.String::class), I think the old expected values are wrong.

// kotlin.Int
// END
// MODULE: lib1
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,13 @@ class AnnotationArgumentProcessor : AbstractTestProcessor() {
}
}

resolver.getClassDeclarationByName("TestNestedAnnotationDefaults")?.let { cls ->
cls.annotations.forEach { annotation ->
val annotationArg = annotation.arguments.single().value as KSAnnotation
results.add("${cls.simpleName.asString()}: ${annotationArg.arguments.single().value}")
}
}

return emptyList()
}

Expand Down
Loading