Use TypeSystemCommonBackendContext in KotlinTypeMapper.writeGenericArguments
This commit is contained in:
@@ -352,26 +352,9 @@ class KotlinTypeMapper @JvmOverloads constructor(
|
||||
parameters: List<TypeParameterDescriptor>,
|
||||
mode: TypeMappingMode
|
||||
) {
|
||||
for ((parameter, argument) in parameters.zip(arguments)) {
|
||||
if (argument.isStarProjection ||
|
||||
// In<Nothing, Foo> == In<*, Foo> -> In<?, Foo>
|
||||
KotlinBuiltIns.isNothing(argument.type) && parameter.variance === Variance.IN_VARIANCE
|
||||
) {
|
||||
signatureVisitor.writeUnboundedWildcard()
|
||||
} else {
|
||||
val argumentMode = mode.updateArgumentModeFromAnnotations(argument.type)
|
||||
val projectionKind = getVarianceForWildcard(parameter, argument, argumentMode)
|
||||
|
||||
signatureVisitor.writeTypeArgument(projectionKind)
|
||||
|
||||
mapType(
|
||||
argument.type, signatureVisitor,
|
||||
argumentMode.toGenericArgumentMode(
|
||||
getEffectiveVariance(parameter.variance, argument.projectionKind)
|
||||
)
|
||||
)
|
||||
|
||||
signatureVisitor.writeTypeArgumentEnd()
|
||||
with(SimpleClassicTypeSystemContext) {
|
||||
writeGenericArguments(signatureVisitor, arguments, parameters, mode) { type, sw, mode ->
|
||||
mapType(type as KotlinType, sw, mode)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1502,6 +1485,37 @@ class KotlinTypeMapper @JvmOverloads constructor(
|
||||
return Variance.OUT_VARIANCE
|
||||
}
|
||||
|
||||
fun TypeSystemCommonBackendContext.writeGenericArguments(
|
||||
signatureVisitor: JvmSignatureWriter,
|
||||
arguments: List<TypeArgumentMarker>,
|
||||
parameters: List<TypeParameterMarker>,
|
||||
mode: TypeMappingMode,
|
||||
mapType: (KotlinTypeMarker, JvmSignatureWriter, TypeMappingMode) -> Type
|
||||
) {
|
||||
for ((parameter, argument) in parameters.zip(arguments)) {
|
||||
if (argument.isStarProjection() ||
|
||||
// In<Nothing, Foo> == In<*, Foo> -> In<?, Foo>
|
||||
argument.getType().isNothing() && parameter.getVariance() == TypeVariance.IN
|
||||
) {
|
||||
signatureVisitor.writeUnboundedWildcard()
|
||||
} else {
|
||||
val argumentMode = mode.updateArgumentModeFromAnnotations(argument.getType(), this)
|
||||
val projectionKind = getVarianceForWildcard(parameter, argument, argumentMode)
|
||||
|
||||
signatureVisitor.writeTypeArgument(projectionKind)
|
||||
|
||||
mapType(
|
||||
argument.getType(), signatureVisitor,
|
||||
argumentMode.toGenericArgumentMode(
|
||||
getEffectiveVariance(parameter.getVariance().convertVariance(), argument.getVariance().convertVariance())
|
||||
)
|
||||
)
|
||||
|
||||
signatureVisitor.writeTypeArgumentEnd()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//NB: similar platform agnostic code in DescriptorUtils.unwrapFakeOverride
|
||||
private fun findSuperDeclaration(descriptor: FunctionDescriptor, isSuperCall: Boolean): FunctionDescriptor {
|
||||
var current = descriptor
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
|
||||
@file:JvmName("TypeMappingUtil")
|
||||
|
||||
package org.jetbrains.kotlin.codegen.state
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.CallableDescriptor
|
||||
@@ -32,6 +33,7 @@ import org.jetbrains.kotlin.resolve.isInlineClassType
|
||||
import org.jetbrains.kotlin.types.KotlinType
|
||||
import org.jetbrains.kotlin.types.TypeSystemCommonBackendContext
|
||||
import org.jetbrains.kotlin.types.Variance
|
||||
import org.jetbrains.kotlin.types.checker.SimpleClassicTypeSystemContext
|
||||
import org.jetbrains.kotlin.types.checker.convertVariance
|
||||
import org.jetbrains.kotlin.types.getEffectiveVariance
|
||||
import org.jetbrains.kotlin.types.model.KotlinTypeMarker
|
||||
@@ -82,8 +84,10 @@ private val METHODS_WITH_DECLARATION_SITE_WILDCARDS = setOf(
|
||||
BUILTIN_NAMES.mutableMap.child("putAll")
|
||||
)
|
||||
|
||||
fun TypeMappingMode.updateArgumentModeFromAnnotations(type: KotlinType): TypeMappingMode {
|
||||
type.suppressWildcardsMode()?.let {
|
||||
fun TypeMappingMode.updateArgumentModeFromAnnotations(
|
||||
type: KotlinTypeMarker, typeSystem: TypeSystemCommonBackendContext
|
||||
): TypeMappingMode {
|
||||
type.suppressWildcardsMode(typeSystem)?.let {
|
||||
return TypeMappingMode.createWithConstantDeclarationSiteWildcardsMode(
|
||||
skipDeclarationSiteWildcards = it,
|
||||
isForAnnotationParameter = isForAnnotationParameter,
|
||||
@@ -91,12 +95,12 @@ fun TypeMappingMode.updateArgumentModeFromAnnotations(type: KotlinType): TypeMap
|
||||
)
|
||||
}
|
||||
|
||||
if (type.annotations.hasAnnotation(JVM_WILDCARD_ANNOTATION_FQ_NAME)) {
|
||||
if (with(typeSystem) { type.hasAnnotation(JVM_WILDCARD_ANNOTATION_FQ_NAME) }) {
|
||||
return TypeMappingMode.createWithConstantDeclarationSiteWildcardsMode(
|
||||
skipDeclarationSiteWildcards = false,
|
||||
isForAnnotationParameter = isForAnnotationParameter,
|
||||
fallbackMode = this,
|
||||
needInlineClassWrapping = needInlineClassWrapping
|
||||
skipDeclarationSiteWildcards = false,
|
||||
isForAnnotationParameter = isForAnnotationParameter,
|
||||
fallbackMode = this,
|
||||
needInlineClassWrapping = needInlineClassWrapping
|
||||
)
|
||||
}
|
||||
|
||||
@@ -108,7 +112,7 @@ internal fun extractTypeMappingModeFromAnnotation(
|
||||
outerType: KotlinType,
|
||||
isForAnnotationParameter: Boolean
|
||||
): TypeMappingMode? =
|
||||
(outerType.suppressWildcardsMode() ?: callableDescriptor?.suppressWildcardsMode())?.let {
|
||||
(outerType.suppressWildcardsMode(SimpleClassicTypeSystemContext) ?: callableDescriptor?.suppressWildcardsMode())?.let {
|
||||
if (outerType.arguments.isNotEmpty())
|
||||
TypeMappingMode.createWithConstantDeclarationSiteWildcardsMode(
|
||||
skipDeclarationSiteWildcards = it,
|
||||
@@ -122,14 +126,17 @@ internal fun extractTypeMappingModeFromAnnotation(
|
||||
private fun DeclarationDescriptor.suppressWildcardsMode(): Boolean? =
|
||||
parentsWithSelf.mapNotNull {
|
||||
it.annotations.findAnnotation(JVM_SUPPRESS_WILDCARDS_ANNOTATION_FQ_NAME)
|
||||
}.firstOrNull().suppressWildcardsMode()
|
||||
}.firstOrNull()?.suppressWildcardsMode()
|
||||
|
||||
private fun KotlinType.suppressWildcardsMode(): Boolean? =
|
||||
annotations.findAnnotation(JVM_SUPPRESS_WILDCARDS_ANNOTATION_FQ_NAME).suppressWildcardsMode()
|
||||
private fun KotlinTypeMarker.suppressWildcardsMode(typeSystem: TypeSystemCommonBackendContext): Boolean? =
|
||||
with(typeSystem) {
|
||||
if (hasAnnotation(JVM_SUPPRESS_WILDCARDS_ANNOTATION_FQ_NAME))
|
||||
getAnnotationFirstArgumentValue(JVM_SUPPRESS_WILDCARDS_ANNOTATION_FQ_NAME) as? Boolean ?: true
|
||||
else null
|
||||
}
|
||||
|
||||
private fun AnnotationDescriptor?.suppressWildcardsMode(): Boolean? {
|
||||
return (this ?: return null).allValueArguments.values.firstOrNull()?.value as? Boolean ?: true
|
||||
}
|
||||
private fun AnnotationDescriptor.suppressWildcardsMode(): Boolean? =
|
||||
allValueArguments.values.firstOrNull()?.value as? Boolean ?: true
|
||||
|
||||
val JVM_SUPPRESS_WILDCARDS_ANNOTATION_FQ_NAME = FqName("kotlin.jvm.JvmSuppressWildcards")
|
||||
val JVM_WILDCARD_ANNOTATION_FQ_NAME = FqName("kotlin.jvm.JvmWildcard")
|
||||
|
||||
@@ -5,9 +5,23 @@
|
||||
|
||||
package org.jetbrains.kotlin.types
|
||||
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.types.model.KotlinTypeMarker
|
||||
import org.jetbrains.kotlin.types.model.TypeConstructorMarker
|
||||
import org.jetbrains.kotlin.types.model.TypeSystemContext
|
||||
|
||||
interface TypeSystemCommonBackendContext : TypeSystemContext {
|
||||
fun TypeConstructorMarker.isFinalClassOrEnumEntryOrAnnotationClassConstructor(): Boolean
|
||||
|
||||
fun KotlinTypeMarker.hasAnnotation(fqName: FqName): Boolean
|
||||
|
||||
/**
|
||||
* @return value of the first argument of the annotation with the given [fqName], if the annotation is present and
|
||||
* the argument is of a primitive type or a String, or null otherwise.
|
||||
*
|
||||
* Note that this method returns null if no arguments are provided, even if the corresponding annotation parameter has a default value.
|
||||
*
|
||||
* TODO: provide a more granular & elaborate API here to reduce confusion
|
||||
*/
|
||||
fun KotlinTypeMarker.getAnnotationFirstArgumentValue(fqName: FqName): Any?
|
||||
}
|
||||
|
||||
@@ -10,6 +10,7 @@ import org.jetbrains.kotlin.builtins.KotlinBuiltIns.FQ_NAMES
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.annotations.Annotations
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.resolve.calls.inference.CapturedType
|
||||
import org.jetbrains.kotlin.resolve.constants.IntegerLiteralTypeConstructor
|
||||
import org.jetbrains.kotlin.resolve.descriptorUtil.hasExactAnnotation
|
||||
@@ -485,6 +486,15 @@ interface ClassicTypeSystemContext : TypeSystemInferenceExtensionContext, TypeSy
|
||||
return this is NewCapturedTypeConstructor
|
||||
}
|
||||
|
||||
override fun KotlinTypeMarker.hasAnnotation(fqName: FqName): Boolean {
|
||||
require(this is KotlinType, this::errorMessage)
|
||||
return annotations.hasAnnotation(fqName)
|
||||
}
|
||||
|
||||
override fun KotlinTypeMarker.getAnnotationFirstArgumentValue(fqName: FqName): Any? {
|
||||
require(this is KotlinType, this::errorMessage)
|
||||
return annotations.findAnnotation(fqName)?.allValueArguments?.values?.firstOrNull()?.value
|
||||
}
|
||||
}
|
||||
|
||||
fun TypeVariance.convertVariance(): Variance {
|
||||
|
||||
+2
-1
@@ -33,6 +33,7 @@ import org.jetbrains.kotlin.psi.*
|
||||
import org.jetbrains.kotlin.resolve.BindingContext
|
||||
import org.jetbrains.kotlin.resolve.source.getPsi
|
||||
import org.jetbrains.kotlin.types.*
|
||||
import org.jetbrains.kotlin.types.checker.SimpleClassicTypeSystemContext
|
||||
|
||||
private typealias SubstitutionMap = Map<String, Pair<KtTypeParameter, KtTypeProjection>>
|
||||
|
||||
@@ -145,7 +146,7 @@ class ErrorTypeCorrector(
|
||||
RETURN_TYPE -> TypeMappingMode.getOptimalModeForReturnType(kotlinType, false)
|
||||
METHOD_PARAMETER_TYPE -> TypeMappingMode.getOptimalModeForValueParameter(kotlinType)
|
||||
SUPER_TYPE -> TypeMappingMode.SUPER_TYPE
|
||||
}.updateArgumentModeFromAnnotations(kotlinType)
|
||||
}.updateArgumentModeFromAnnotations(kotlinType, SimpleClassicTypeSystemContext)
|
||||
|
||||
val typeParameters = (target as? ClassifierDescriptor)?.typeConstructor?.parameters
|
||||
return treeMaker.TypeApply(baseExpression, mapJListIndexed(arguments) { index, projection ->
|
||||
|
||||
Reference in New Issue
Block a user