[FIR] Fix mapping of java annotation arguments when parameter is array
#KT-65933 Fixed
This commit is contained in:
committed by
Space Team
parent
6479b15e46
commit
4780bb90e7
@@ -58,15 +58,14 @@ val JavaClass.classKind: ClassKind
|
||||
fun JavaClass.hasMetadataAnnotation(): Boolean =
|
||||
annotations.any { it.isResolvedTo(JvmAnnotationNames.METADATA_FQ_NAME) }
|
||||
|
||||
internal fun Any?.createConstantOrError(session: FirSession, expectedTypeRef: FirTypeRef? = null): FirExpression {
|
||||
val coneType = expectedTypeRef?.coneTypeOrNull
|
||||
val value = if (this is Int && coneType != null) {
|
||||
internal fun Any?.createConstantOrError(session: FirSession, expectedConeType: ConeKotlinType? = null): FirExpression {
|
||||
val value = if (this is Int && expectedConeType != null) {
|
||||
// special case for Java literals in annotation default values:
|
||||
// literal value is always integer, but an expected parameter type can be any other number type
|
||||
when {
|
||||
coneType.isByte -> this.toByte()
|
||||
coneType.isShort -> this.toShort()
|
||||
coneType.isLong -> this.toLong()
|
||||
expectedConeType.isByte -> this.toByte()
|
||||
expectedConeType.isShort -> this.toShort()
|
||||
expectedConeType.isLong -> this.toLong()
|
||||
else -> this
|
||||
}
|
||||
} else this
|
||||
|
||||
@@ -44,6 +44,7 @@ import org.jetbrains.kotlin.toKtPsiSourceElement
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.firstIsInstanceOrNull
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.ifNotEmpty
|
||||
import java.util.*
|
||||
import kotlin.math.exp
|
||||
|
||||
internal fun Iterable<JavaAnnotation>.convertAnnotationsToFir(
|
||||
session: FirSession,
|
||||
@@ -103,21 +104,18 @@ internal fun JavaValueParameter.toFirValueParameter(
|
||||
internal fun JavaAnnotationArgument.toFirExpression(
|
||||
session: FirSession, javaTypeParameterStack: JavaTypeParameterStack, expectedTypeRef: FirTypeRef?
|
||||
): FirExpression {
|
||||
return when (this) {
|
||||
val expectedConeType = expectedTypeRef?.toConeKotlinTypeProbablyFlexible(session, javaTypeParameterStack)
|
||||
val expectedArrayElementTypeIfArray = expectedConeType?.lowerBoundIfFlexible()?.arrayElementType() ?: expectedConeType
|
||||
val argument = when (this) {
|
||||
is JavaLiteralAnnotationArgument -> value.createConstantOrError(
|
||||
session,
|
||||
expectedTypeRef?.resolveIfJavaType(session, javaTypeParameterStack)
|
||||
expectedArrayElementTypeIfArray
|
||||
)
|
||||
is JavaArrayAnnotationArgument -> buildArrayLiteral {
|
||||
val argumentTypeRef = expectedTypeRef?.let {
|
||||
val type = if (it is FirJavaTypeRef) {
|
||||
it.toConeKotlinTypeProbablyFlexible(session, javaTypeParameterStack)
|
||||
} else {
|
||||
it.coneType
|
||||
}
|
||||
coneTypeOrNull = type
|
||||
val argumentTypeRef = expectedConeType?.let {
|
||||
coneTypeOrNull = it
|
||||
buildResolvedTypeRef {
|
||||
this.type = type.lowerBoundIfFlexible().arrayElementType()
|
||||
this.type = it.lowerBoundIfFlexible().arrayElementType()
|
||||
?: ConeErrorType(ConeSimpleDiagnostic("expected type is not array type"))
|
||||
}
|
||||
}
|
||||
@@ -131,7 +129,7 @@ internal fun JavaAnnotationArgument.toFirExpression(
|
||||
// a static import. In this case, the parameter default initializer will not have its type set, which isn't usually an
|
||||
// issue except in edge cases like KT-47702 where we do need to evaluate the default values of annotations.
|
||||
// As a fallback, we use the expected type which should be the type of the enum.
|
||||
classId = requireNotNull(enumClassId ?: expectedTypeRef?.coneTypeOrNull?.lowerBoundIfFlexible()?.classId),
|
||||
classId = requireNotNull(enumClassId ?: expectedArrayElementTypeIfArray?.lowerBoundIfFlexible()?.classId),
|
||||
entryName = entryName
|
||||
)
|
||||
is JavaClassObjectAnnotationArgument -> buildGetClassCall {
|
||||
@@ -152,6 +150,17 @@ internal fun JavaAnnotationArgument.toFirExpression(
|
||||
diagnostic = ConeSimpleDiagnostic("Unknown JavaAnnotationArgument: ${this::class.java}", DiagnosticKind.Java)
|
||||
}
|
||||
}
|
||||
|
||||
return if (expectedConeType?.lowerBoundIfFlexible()?.isArrayOrPrimitiveArray == true && argument !is FirArrayLiteral) {
|
||||
buildArrayLiteral {
|
||||
coneTypeOrNull = expectedConeType
|
||||
argumentList = buildArgumentList {
|
||||
arguments += argument
|
||||
}
|
||||
}
|
||||
} else {
|
||||
argument
|
||||
}
|
||||
}
|
||||
|
||||
private val JAVA_RETENTION_TO_KOTLIN: Map<String, AnnotationRetention> = mapOf(
|
||||
|
||||
Reference in New Issue
Block a user