Retaining annotations on Java array types

This commit is contained in:
Andrey Breslav
2015-02-04 19:21:55 +03:00
parent fc3cd20456
commit 1d4109aec1
7 changed files with 78 additions and 23 deletions
@@ -24,11 +24,11 @@ fun test() {
val platformJ = J.staticJ
platformNN[0]
platformN[0]
<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>[0]
platformJ[0]
platformNN[0] = 1
platformN[0] = 1
<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>[0] = 1
platformJ[0] = 1
}
@@ -0,0 +1,34 @@
// FILE: p/J.java
package p;
import org.jetbrains.annotations.*;
public class J {
@NotNull
public static int[] staticNN;
@Nullable
public static int[] staticN;
public static int[] staticJ;
}
// FILE: k.kt
import p.*
fun test() {
// @NotNull platform type
val platformNN = J.staticNN
// @Nullable platform type
val platformN = J.staticN
// platform type with no annotation
val platformJ = J.staticJ
platformNN[0]
<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>[0]
platformJ[0]
platformNN[0] = 1
<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>[0] = 1
platformJ[0] = 1
}
@@ -0,0 +1,3 @@
package
internal fun test(): kotlin.Unit
@@ -8634,6 +8634,12 @@ public class JetDiagnosticsTestGenerated extends AbstractJetDiagnosticsTest {
doTest(fileName);
}
@TestMetadata("primitiveArray.kt")
public void testPrimitiveArray() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/primitiveArray.kt");
doTest(fileName);
}
@TestMetadata("throw.kt")
public void testThrow() throws Exception {
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/throw.kt");
@@ -41,11 +41,9 @@ class LazyJavaAnnotations(
return annotationDescriptors(jAnnotation)
}
[suppress("UNCHECKED_CAST")] // any iterator can be cast to MutableIterator
override fun iterator(): MutableIterator<AnnotationDescriptor>
= annotationOwner.getAnnotations().stream().map { annotationDescriptors(it) }.filterNotNull().iterator() as MutableIterator
override fun iterator() = annotationOwner.getAnnotations().stream().map { annotationDescriptors(it) }.filterNotNull().iterator()
override fun isEmpty() = iterator().hasNext()
override fun isEmpty() = !iterator().hasNext()
}
fun LazyJavaResolverContext.resolveAnnotations(annotationsOwner: JavaAnnotationOwner): Annotations
@@ -36,6 +36,7 @@ import org.jetbrains.kotlin.load.java.lazy.types.JavaTypeFlexibility.*
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.load.java.JvmAnnotationNames
import kotlin.platform.platformStatic
import org.jetbrains.kotlin.types.typeUtil.replaceAnnotations
class LazyJavaTypeResolver(
private val c: LazyJavaResolverContext,
@@ -63,27 +64,29 @@ class LazyJavaTypeResolver(
}
public fun transformArrayType(arrayType: JavaArrayType, attr: JavaTypeAttributes, isVararg: Boolean = false): JetType {
val javaComponentType = arrayType.getComponentType()
if (javaComponentType is JavaPrimitiveType) {
val jetType = JavaToKotlinClassMap.INSTANCE.mapPrimitiveKotlinClass("[" + javaComponentType.getCanonicalText())
if (jetType != null) {
return if (PLATFORM_TYPES && attr.allowFlexible)
FlexibleJavaClassifierTypeCapabilities.create(jetType, TypeUtils.makeNullable(jetType))
else TypeUtils.makeNullableAsSpecified(jetType, !attr.isMarkedNotNull)
return run { (): JetType ->
val javaComponentType = arrayType.getComponentType()
if (javaComponentType is JavaPrimitiveType) {
val jetType = JavaToKotlinClassMap.INSTANCE.mapPrimitiveKotlinClass("[" + javaComponentType.getCanonicalText())
if (jetType != null) {
return@run if (PLATFORM_TYPES && attr.allowFlexible)
FlexibleJavaClassifierTypeCapabilities.create(jetType, TypeUtils.makeNullable(jetType))
else TypeUtils.makeNullableAsSpecified(jetType, !attr.isMarkedNotNull)
}
}
}
val componentType = transformJavaType(javaComponentType, TYPE_ARGUMENT.toAttributes(attr.allowFlexible))
val componentType = transformJavaType(javaComponentType, TYPE_ARGUMENT.toAttributes(attr.allowFlexible))
if (PLATFORM_TYPES && attr.allowFlexible) {
return FlexibleJavaClassifierTypeCapabilities.create(
KotlinBuiltIns.getInstance().getArrayType(INVARIANT, componentType),
TypeUtils.makeNullable(KotlinBuiltIns.getInstance().getArrayType(OUT_VARIANCE, componentType)))
}
if (PLATFORM_TYPES && attr.allowFlexible) {
return@run FlexibleJavaClassifierTypeCapabilities.create(
KotlinBuiltIns.getInstance().getArrayType(INVARIANT, componentType),
TypeUtils.makeNullable(KotlinBuiltIns.getInstance().getArrayType(OUT_VARIANCE, componentType)))
}
val projectionKind = if (attr.howThisTypeIsUsed == MEMBER_SIGNATURE_CONTRAVARIANT || isVararg) OUT_VARIANCE else INVARIANT
val result = KotlinBuiltIns.getInstance().getArrayType(projectionKind, componentType)
return TypeUtils.makeNullableAsSpecified(result, !attr.isMarkedNotNull)
val projectionKind = if (attr.howThisTypeIsUsed == MEMBER_SIGNATURE_CONTRAVARIANT || isVararg) OUT_VARIANCE else INVARIANT
val result = KotlinBuiltIns.getInstance().getArrayType(projectionKind, componentType)
return@run TypeUtils.makeNullableAsSpecified(result, !attr.isMarkedNotNull)
}.replaceAnnotations(attr.annotations)
}
private class LazyStarProjection(
@@ -30,6 +30,8 @@ import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.types.isDynamic
import org.jetbrains.kotlin.types.TypeProjection
import org.jetbrains.kotlin.types.TypeProjectionImpl
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.types.DelegatingType
fun JetType.getContainedTypeParameters(): Collection<TypeParameterDescriptor> {
val declarationDescriptor = getConstructor().getDeclarationDescriptor()
@@ -72,4 +74,13 @@ fun TypeProjection.substitute(doSubstitute: (JetType) -> JetType): TypeProjectio
return if (isStarProjection())
this
else TypeProjectionImpl(getProjectionKind(), doSubstitute(getType()))
}
fun JetType.replaceAnnotations(newAnnotations: Annotations): JetType {
if (newAnnotations.isEmpty()) return this
return object : DelegatingType() {
override fun getDelegate() = this@replaceAnnotations
override fun getAnnotations() = newAnnotations
}
}