Basic Java nullability warnings implemented
#KT-6723 In Progress
This commit is contained in:
+39
-1
@@ -42,10 +42,21 @@ import org.jetbrains.kotlin.load.kotlin.nativeDeclarations.NativeFunChecker
|
||||
import org.jetbrains.kotlin.psi.JetPropertyAccessor
|
||||
import org.jetbrains.kotlin.descriptors.MemberDescriptor
|
||||
import org.jetbrains.kotlin.resolve.jvm.calls.checkers.NeedSyntheticChecker
|
||||
import org.jetbrains.kotlin.resolve.calls.checkers.AdditionalTypeChecker
|
||||
import org.jetbrains.kotlin.psi.JetExpression
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.resolve.calls.context.ResolutionContext
|
||||
import org.jetbrains.kotlin.types.TypeUtils
|
||||
import org.jetbrains.kotlin.load.java.lazy.types.isMarkedNullable
|
||||
import org.jetbrains.kotlin.load.java.lazy.types.isMarkedNotNull
|
||||
import org.jetbrains.kotlin.types.isFlexible
|
||||
import org.jetbrains.kotlin.resolve.calls.smartcasts.DataFlowValueFactory
|
||||
import org.jetbrains.kotlin.resolve.jvm.diagnostics.ErrorsJvm.NullabilityInformationSource
|
||||
|
||||
public object KotlinJvmCheckerProvider : AdditionalCheckerProvider(
|
||||
annotationCheckers = listOf(PlatformStaticAnnotationChecker(), LocalFunInlineChecker(), ReifiedTypeParameterAnnotationChecker(), NativeFunChecker()),
|
||||
additionalCallCheckers = listOf(NeedSyntheticChecker())
|
||||
additionalCallCheckers = listOf(NeedSyntheticChecker()),
|
||||
additionalTypeCheckers = listOf(JavaNullabilityWarningsChecker())
|
||||
)
|
||||
|
||||
public class LocalFunInlineChecker : AnnotationChecker {
|
||||
@@ -127,3 +138,30 @@ private fun checkTypeParameterDescriptorsAreNotReified(
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
public class JavaNullabilityWarningsChecker : AdditionalTypeChecker {
|
||||
private fun JetType.mayBeNull(): NullabilityInformationSource? {
|
||||
if (!isFlexible() && TypeUtils.isNullableType(this)) return NullabilityInformationSource.KOTLIN
|
||||
if (getAnnotations().isMarkedNullable()) return NullabilityInformationSource.JAVA
|
||||
return null
|
||||
}
|
||||
|
||||
private fun JetType.mustNotBeNull(): NullabilityInformationSource? {
|
||||
if (!isFlexible() && !TypeUtils.isNullableType(this)) return NullabilityInformationSource.KOTLIN
|
||||
if (getAnnotations().isMarkedNotNull()) return NullabilityInformationSource.JAVA
|
||||
return null
|
||||
}
|
||||
|
||||
override fun checkType(expression: JetExpression, expressionType: JetType, c: ResolutionContext<*>) {
|
||||
if (TypeUtils.noExpectedType(c.expectedType)) return
|
||||
|
||||
val expectedMustNotBeNull = c.expectedType.mustNotBeNull()
|
||||
val actualNullabilityInKotlin = c.dataFlowInfo.getNullability(DataFlowValueFactory.createDataFlowValue(expression, expressionType, c.trace.getBindingContext()))
|
||||
val actualMayBeNull = if (!actualNullabilityInKotlin.canBeNull()) null else expressionType.mayBeNull()
|
||||
|
||||
if (expectedMustNotBeNull != null && actualMayBeNull != null) {
|
||||
c.trace.report(ErrorsJvm.NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS.on(expression, expectedMustNotBeNull, actualMayBeNull))
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
+4
@@ -20,6 +20,7 @@ import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor;
|
||||
import org.jetbrains.kotlin.diagnostics.rendering.DefaultErrorMessages;
|
||||
import org.jetbrains.kotlin.diagnostics.rendering.DiagnosticFactoryToRendererMap;
|
||||
import org.jetbrains.kotlin.diagnostics.rendering.Renderers;
|
||||
import org.jetbrains.kotlin.renderer.DescriptorRenderer;
|
||||
import org.jetbrains.kotlin.renderer.Renderer;
|
||||
|
||||
@@ -51,6 +52,9 @@ public class DefaultErrorMessagesJvm implements DefaultErrorMessages.Extension {
|
||||
MAP.put(ErrorsJvm.NATIVE_DECLARATION_CANNOT_HAVE_BODY, "Native declaration can not have a body");
|
||||
MAP.put(ErrorsJvm.NATIVE_DECLARATION_IN_TRAIT, "Members of traits can not be native");
|
||||
MAP.put(ErrorsJvm.NATIVE_DECLARATION_CANNOT_BE_INLINED, "Members of traits can not be inlined");
|
||||
|
||||
MAP.put(ErrorsJvm.NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS,
|
||||
"Expected type does not accept nulls in {0}, but the value may be null in {1}", Renderers.TO_STRING, Renderers.TO_STRING);
|
||||
}
|
||||
|
||||
|
||||
|
||||
+23
@@ -17,14 +17,18 @@
|
||||
package org.jetbrains.kotlin.resolve.jvm.diagnostics;
|
||||
|
||||
import com.intellij.psi.PsiElement;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor;
|
||||
import org.jetbrains.kotlin.diagnostics.DiagnosticFactory0;
|
||||
import org.jetbrains.kotlin.diagnostics.DiagnosticFactory1;
|
||||
import org.jetbrains.kotlin.diagnostics.DiagnosticFactory2;
|
||||
import org.jetbrains.kotlin.diagnostics.Errors;
|
||||
import org.jetbrains.kotlin.psi.JetDeclaration;
|
||||
import org.jetbrains.kotlin.psi.JetExpression;
|
||||
|
||||
import static org.jetbrains.kotlin.diagnostics.PositioningStrategies.*;
|
||||
import static org.jetbrains.kotlin.diagnostics.Severity.ERROR;
|
||||
import static org.jetbrains.kotlin.diagnostics.Severity.WARNING;
|
||||
|
||||
public interface ErrorsJvm {
|
||||
DiagnosticFactory1<PsiElement, ConflictingJvmDeclarationsData> CONFLICTING_JVM_DECLARATIONS =
|
||||
@@ -42,6 +46,25 @@ public interface ErrorsJvm {
|
||||
DiagnosticFactory0<JetDeclaration> NATIVE_DECLARATION_IN_TRAIT = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
DiagnosticFactory0<JetDeclaration> NATIVE_DECLARATION_CANNOT_BE_INLINED = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
|
||||
|
||||
enum NullabilityInformationSource {
|
||||
KOTLIN {
|
||||
@NotNull
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Kotlin";
|
||||
}
|
||||
},
|
||||
JAVA {
|
||||
@NotNull
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Java";
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
DiagnosticFactory2<JetExpression, NullabilityInformationSource, NullabilityInformationSource> NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS = DiagnosticFactory2.create(WARNING);
|
||||
|
||||
@SuppressWarnings("UnusedDeclaration")
|
||||
Object _initializer = new Object() {
|
||||
{
|
||||
|
||||
@@ -23,11 +23,12 @@ private val DEFAULT_TYPE_CHECKERS = listOf(TypeApproximator())
|
||||
|
||||
public abstract class AdditionalCheckerProvider(
|
||||
public val annotationCheckers: List<AnnotationChecker>,
|
||||
additionalCallCheckers: List<CallChecker>
|
||||
additionalCallCheckers: List<CallChecker>,
|
||||
additionalTypeCheckers: List<AdditionalTypeChecker>
|
||||
) {
|
||||
|
||||
public val callCheckers: List<CallChecker> = DEFAULT_CALL_CHECKERS + additionalCallCheckers
|
||||
public val additionalTypeCheckers: List<AdditionalTypeChecker> = DEFAULT_TYPE_CHECKERS
|
||||
public val additionalTypeCheckers: List<AdditionalTypeChecker> = DEFAULT_TYPE_CHECKERS + additionalTypeCheckers
|
||||
|
||||
public object DefaultProvider : AdditionalCheckerProvider(listOf(), listOf()) {}
|
||||
public object DefaultProvider : AdditionalCheckerProvider(listOf(), listOf(), listOf()) {}
|
||||
}
|
||||
|
||||
@@ -1,29 +1,29 @@
|
||||
import java.sql.DriverManager
|
||||
|
||||
fun getConnection(url: String?) {
|
||||
DriverManager.getConnection(url)
|
||||
DriverManager.getConnection(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>url<!>)
|
||||
DriverManager.getConnection(url!!) : java.sql.Connection
|
||||
}
|
||||
|
||||
fun getConnection(url: String?, props: java.util.Properties?) {
|
||||
DriverManager.getConnection(url, props)
|
||||
DriverManager.getConnection(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>url<!>, props)
|
||||
DriverManager.getConnection(url!!, props) : java.sql.Connection
|
||||
}
|
||||
|
||||
fun getConnection(url: String?, user: String?, password: String?) {
|
||||
DriverManager.getConnection(url, user!!, password!!)
|
||||
DriverManager.getConnection(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>url<!>, user!!, password!!)
|
||||
DriverManager.getConnection(url!!, user, password<!UNNECESSARY_NOT_NULL_ASSERTION!>!!<!>)
|
||||
DriverManager.getConnection(url<!UNNECESSARY_NOT_NULL_ASSERTION!>!!<!>, user<!UNNECESSARY_NOT_NULL_ASSERTION!>!!<!>, password)
|
||||
DriverManager.getConnection(url<!UNNECESSARY_NOT_NULL_ASSERTION!>!!<!>, user<!UNNECESSARY_NOT_NULL_ASSERTION!>!!<!>, password<!UNNECESSARY_NOT_NULL_ASSERTION!>!!<!>) : java.sql.Connection
|
||||
}
|
||||
|
||||
fun getDriver(url: String?) {
|
||||
DriverManager.getDriver(url)
|
||||
DriverManager.getDriver(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>url<!>)
|
||||
DriverManager.getDriver(url!!) : java.sql.Driver
|
||||
}
|
||||
|
||||
fun registerDriver(driver: java.sql.Driver?) {
|
||||
DriverManager.registerDriver(driver)
|
||||
DriverManager.registerDriver(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>driver<!>)
|
||||
DriverManager.registerDriver(driver!!)
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
fun executeQuery(statement: java.sql.Statement, cmd: String?) {
|
||||
statement.executeQuery(cmd)
|
||||
statement.executeQuery(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>cmd<!>)
|
||||
statement.executeQuery(cmd!!) : java.sql.ResultSet
|
||||
}
|
||||
|
||||
@@ -8,6 +8,6 @@ fun executeQuery(statement: java.sql.PreparedStatement) {
|
||||
}
|
||||
|
||||
fun executeUpdate(statement: java.sql.Statement, cmd: String?) {
|
||||
statement.executeUpdate(cmd)
|
||||
statement.executeUpdate(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>cmd<!>)
|
||||
statement.executeUpdate(cmd!!)
|
||||
}
|
||||
@@ -0,0 +1,58 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static Integer staticNN;
|
||||
@Nullable
|
||||
public static Integer staticN;
|
||||
public static Integer staticJ;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
fun test() {
|
||||
// @NotNull platform type
|
||||
var platformNN = J.staticNN
|
||||
// @Nullable platform type
|
||||
var platformN = J.staticN
|
||||
// platform type with no annotation
|
||||
var platformJ = J.staticJ
|
||||
|
||||
+platformNN
|
||||
+platformN
|
||||
+platformJ
|
||||
|
||||
++platformNN
|
||||
++platformN
|
||||
++platformJ
|
||||
|
||||
platformNN++
|
||||
platformN++
|
||||
platformJ++
|
||||
|
||||
1 + platformNN
|
||||
1 + <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>
|
||||
1 + platformJ
|
||||
|
||||
platformNN + 1
|
||||
platformN + 1
|
||||
platformJ + 1
|
||||
|
||||
1 plus platformNN
|
||||
1 plus <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>
|
||||
1 plus platformJ
|
||||
|
||||
platformNN plus 1
|
||||
platformN plus 1
|
||||
platformJ plus 1
|
||||
|
||||
platformNN += 1
|
||||
platformN += 1
|
||||
platformJ += 1
|
||||
}
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,34 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static Integer[] staticNN;
|
||||
@Nullable
|
||||
public static Integer[] staticN;
|
||||
public static Integer[] 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]
|
||||
platformN[0]
|
||||
platformJ[0]
|
||||
|
||||
platformNN[0] = 1
|
||||
platformN[0] = 1
|
||||
platformJ[0] = 1
|
||||
}
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,29 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
public static J staticJ;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
var v: J = J()
|
||||
var n: J? = J()
|
||||
|
||||
fun test() {
|
||||
v = J.staticNN
|
||||
v = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>J.staticN<!>
|
||||
v = J.staticJ
|
||||
|
||||
n = J.staticNN
|
||||
n = J.staticN
|
||||
n = J.staticJ
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package
|
||||
|
||||
internal var n: p.J?
|
||||
internal var v: p.J
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,50 @@
|
||||
// !DIAGNOSTICS: -UNUSED_EXPRESSION
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static Boolean staticNN;
|
||||
@Nullable
|
||||
public static Boolean staticN;
|
||||
public static Boolean 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
|
||||
|
||||
if (platformNN) {}
|
||||
if (<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>) {}
|
||||
if (platformJ) {}
|
||||
|
||||
while (platformNN) {}
|
||||
while (<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>) {}
|
||||
while (platformJ) {}
|
||||
|
||||
do {} while (platformNN)
|
||||
do {} while (<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>)
|
||||
do {} while (platformJ)
|
||||
|
||||
platformNN && false
|
||||
<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!> && false
|
||||
platformJ && false
|
||||
|
||||
platformNN || false
|
||||
<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!> || false
|
||||
platformJ || false
|
||||
|
||||
!platformNN
|
||||
!<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>
|
||||
!platformJ
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,34 @@
|
||||
// !DIAGNOSTICS: -UNUSED_PARAMETER
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
fun test() {
|
||||
val n = J.staticN
|
||||
foo(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>n<!>)
|
||||
J.staticNN = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>n<!>
|
||||
if (n != null) {
|
||||
foo(n)
|
||||
J.staticNN = n
|
||||
}
|
||||
|
||||
val x: J? = null
|
||||
J.staticNN = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>x<!>
|
||||
if (x != null) {
|
||||
J.staticNN = x
|
||||
}
|
||||
}
|
||||
|
||||
fun foo(j: J) {}
|
||||
@@ -0,0 +1,4 @@
|
||||
package
|
||||
|
||||
internal fun foo(/*0*/ j: p.J): kotlin.Unit
|
||||
internal fun test(): kotlin.Unit
|
||||
+30
@@ -0,0 +1,30 @@
|
||||
// !DIAGNOSTICS: -UNUSED_PARAMETER
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
public static J 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
|
||||
|
||||
fun foo(p: J = platformNN, p1: J = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>, p2: J = platformJ) {}
|
||||
|
||||
fun foo1(p: J? = platformNN, p1: J? = platformN, p2: J? = platformJ) {}
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
+26
@@ -0,0 +1,26 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
|
||||
public interface DP {
|
||||
String get(Object a, Object b);
|
||||
String set(Object a, Object b, Object c);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static DP staticNN;
|
||||
@Nullable
|
||||
public static DP staticN;
|
||||
public static DP staticJ;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
var A by J.staticNN
|
||||
var B by J.staticN
|
||||
var C by J.staticJ
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
package
|
||||
|
||||
internal var A: kotlin.String!
|
||||
internal var B: kotlin.String!
|
||||
internal var C: kotlin.String!
|
||||
@@ -0,0 +1,21 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
import java.util.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static List<String> staticNN;
|
||||
@Nullable
|
||||
public static List<String> staticN;
|
||||
public static List<String> staticJ;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
class A : List<String> by J.staticNN
|
||||
class B : List<String> by <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>J.staticN<!>
|
||||
class C : List<String> by J.staticJ
|
||||
@@ -0,0 +1,55 @@
|
||||
package
|
||||
|
||||
internal final class A : kotlin.List<kotlin.String> {
|
||||
public constructor A()
|
||||
public open override /*1*/ /*delegation*/ fun contains(/*0*/ o: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun containsAll(/*0*/ c: kotlin.Collection<kotlin.Any?>): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun get(/*0*/ index: kotlin.Int): kotlin.String
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun indexOf(/*0*/ o: kotlin.Any?): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun isEmpty(): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun iterator(): kotlin.Iterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun lastIndexOf(/*0*/ o: kotlin.Any?): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun listIterator(): kotlin.ListIterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun listIterator(/*0*/ index: kotlin.Int): kotlin.ListIterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun size(): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun subList(/*0*/ fromIndex: kotlin.Int, /*1*/ toIndex: kotlin.Int): kotlin.List<kotlin.String>
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
internal final class B : kotlin.List<kotlin.String> {
|
||||
public constructor B()
|
||||
public open override /*1*/ /*delegation*/ fun contains(/*0*/ o: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun containsAll(/*0*/ c: kotlin.Collection<kotlin.Any?>): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun get(/*0*/ index: kotlin.Int): kotlin.String
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun indexOf(/*0*/ o: kotlin.Any?): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun isEmpty(): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun iterator(): kotlin.Iterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun lastIndexOf(/*0*/ o: kotlin.Any?): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun listIterator(): kotlin.ListIterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun listIterator(/*0*/ index: kotlin.Int): kotlin.ListIterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun size(): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun subList(/*0*/ fromIndex: kotlin.Int, /*1*/ toIndex: kotlin.Int): kotlin.List<kotlin.String>
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
internal final class C : kotlin.List<kotlin.String> {
|
||||
public constructor C()
|
||||
public open override /*1*/ /*delegation*/ fun contains(/*0*/ o: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun containsAll(/*0*/ c: kotlin.Collection<kotlin.Any?>): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun get(/*0*/ index: kotlin.Int): kotlin.String
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun indexOf(/*0*/ o: kotlin.Any?): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun isEmpty(): kotlin.Boolean
|
||||
public open override /*1*/ /*delegation*/ fun iterator(): kotlin.Iterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun lastIndexOf(/*0*/ o: kotlin.Any?): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun listIterator(): kotlin.ListIterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun listIterator(/*0*/ index: kotlin.Int): kotlin.ListIterator<kotlin.String>
|
||||
public open override /*1*/ /*delegation*/ fun size(): kotlin.Int
|
||||
public open override /*1*/ /*delegation*/ fun subList(/*0*/ fromIndex: kotlin.Int, /*1*/ toIndex: kotlin.Int): kotlin.List<kotlin.String>
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
public static J 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.foo()
|
||||
platformN.foo()
|
||||
platformJ.foo()
|
||||
|
||||
platformNN.bar()
|
||||
platformN.bar()
|
||||
platformJ.bar()
|
||||
}
|
||||
|
||||
fun J.foo() {}
|
||||
fun J?.bar() {}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
internal fun p.J?.bar(): kotlin.Unit
|
||||
internal fun p.J.foo(): kotlin.Unit
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
public static J staticJ;
|
||||
|
||||
public void foo() {}
|
||||
}
|
||||
|
||||
// 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.foo()
|
||||
platformN.foo()
|
||||
platformJ.foo()
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,33 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
public static J 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 : J
|
||||
<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!> : J
|
||||
platformJ : J
|
||||
|
||||
platformNN : J?
|
||||
platformN : J?
|
||||
platformJ : J?
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,31 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
import java.util.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static List<String> staticNN;
|
||||
@Nullable
|
||||
public static List<String> staticN;
|
||||
public static List<String> 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
|
||||
|
||||
for (x in platformNN) {}
|
||||
for (x in platformN) {}
|
||||
for (x in platformJ) {}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
+30
@@ -0,0 +1,30 @@
|
||||
// !DIAGNOSTICS: -UNUSED_PARAMETER
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
public static J staticJ;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
fun test() {
|
||||
foo(J.staticNN)
|
||||
foo(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>J.staticN<!>)
|
||||
foo(J.staticJ)
|
||||
|
||||
bar(J.staticNN)
|
||||
bar(J.staticN)
|
||||
bar(J.staticJ)
|
||||
}
|
||||
|
||||
fun foo(j: J) {}
|
||||
fun bar(j: J?) {}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
package
|
||||
|
||||
internal fun bar(/*0*/ j: p.J?): kotlin.Unit
|
||||
internal fun foo(/*0*/ j: p.J): kotlin.Unit
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,27 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
public interface Invoke {
|
||||
void invoke();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static Invoke staticNN;
|
||||
@Nullable
|
||||
public static Invoke staticN;
|
||||
public static Invoke staticJ;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
fun test() {
|
||||
J.staticNN()
|
||||
J.staticN()
|
||||
J.staticJ()
|
||||
}
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
// !DIAGNOSTICS: -UNUSED_VARIABLE
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
public interface Multi {
|
||||
String component1();
|
||||
String component2();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static Multi staticNN;
|
||||
@Nullable
|
||||
public static Multi staticN;
|
||||
public static Multi 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
|
||||
|
||||
val (a1, b1) = platformNN
|
||||
val (a2, b2) = platformN
|
||||
val (a3, b3) = platformJ
|
||||
}
|
||||
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
@@ -0,0 +1,92 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static J staticNN;
|
||||
@Nullable
|
||||
public static J staticN;
|
||||
public static J staticJ;
|
||||
|
||||
public static void staticSet(@NotNull J nn, @Nullable J n, J j) {}
|
||||
|
||||
public J(@NotNull J nn, @Nullable J n, J j) {}
|
||||
public J() {}
|
||||
|
||||
@NotNull
|
||||
public J nn;
|
||||
@Nullable
|
||||
public J n;
|
||||
public J j;
|
||||
|
||||
public void set(@NotNull J nn, @Nullable J n, J j) {}
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
fun test(n: J?, nn: J) {
|
||||
// @NotNull platform type
|
||||
val platformNN = J.staticNN
|
||||
// @Nullable platform type
|
||||
val platformN = J.staticN
|
||||
// platform type with no annotation
|
||||
val platformJ = J.staticJ
|
||||
|
||||
J.staticNN = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>n<!>
|
||||
J.staticNN = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>
|
||||
J.staticNN = nn
|
||||
J.staticNN = platformNN
|
||||
J.staticNN = platformJ
|
||||
|
||||
J.staticN = n
|
||||
J.staticN = platformN
|
||||
J.staticN = nn
|
||||
J.staticN = platformNN
|
||||
J.staticN = platformJ
|
||||
|
||||
J.staticJ = n
|
||||
J.staticJ = platformN
|
||||
J.staticJ = nn
|
||||
J.staticJ = platformNN
|
||||
J.staticJ = platformJ
|
||||
|
||||
J.staticSet(nn, nn, nn)
|
||||
J.staticSet(platformNN, platformNN, platformNN)
|
||||
J.staticSet(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>n<!>, n, n)
|
||||
J.staticSet(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>, platformN, platformN)
|
||||
J.staticSet(platformJ, platformJ, platformJ)
|
||||
|
||||
J().nn = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>n<!>
|
||||
J().nn = <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>
|
||||
J().nn = nn
|
||||
J().nn = platformNN
|
||||
J().nn = platformJ
|
||||
|
||||
J().n = n
|
||||
J().n = platformN
|
||||
J().n = nn
|
||||
J().n = platformNN
|
||||
J().n = platformJ
|
||||
|
||||
J().j = n
|
||||
J().j = platformN
|
||||
J().j = nn
|
||||
J().j = platformNN
|
||||
J().j = platformJ
|
||||
|
||||
J().set(nn, nn, nn)
|
||||
J().set(platformNN, platformNN, platformNN)
|
||||
J().set(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>n<!>, n, n)
|
||||
J().set(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>, platformN, platformN)
|
||||
J().set(platformJ, platformJ, platformJ)
|
||||
|
||||
J(nn, nn, nn)
|
||||
J(platformNN, platformNN, platformNN)
|
||||
J(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>n<!>, n, n)
|
||||
J(<!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>platformN<!>, platformN, platformN)
|
||||
J(platformJ, platformJ, platformJ)
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
internal fun test(/*0*/ n: p.J?, /*1*/ nn: p.J): kotlin.Unit
|
||||
@@ -0,0 +1,28 @@
|
||||
// FILE: p/J.java
|
||||
package p;
|
||||
|
||||
import org.jetbrains.annotations.*;
|
||||
|
||||
public class J {
|
||||
@NotNull
|
||||
public static Exception staticNN;
|
||||
@Nullable
|
||||
public static Exception staticN;
|
||||
public static Exception staticJ;
|
||||
}
|
||||
|
||||
// FILE: k.kt
|
||||
|
||||
import p.*
|
||||
|
||||
fun test() {
|
||||
throw J.staticNN
|
||||
}
|
||||
|
||||
fun test1() {
|
||||
throw <!NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS!>J.staticN<!>
|
||||
}
|
||||
|
||||
fun test2() {
|
||||
throw J.staticJ
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package
|
||||
|
||||
internal fun test(): kotlin.Unit
|
||||
internal fun test1(): kotlin.Unit
|
||||
internal fun test2(): kotlin.Unit
|
||||
@@ -8262,7 +8262,7 @@ public class JetDiagnosticsTestGenerated extends AbstractJetDiagnosticsTest {
|
||||
|
||||
@TestMetadata("compiler/testData/diagnostics/tests/platformTypes")
|
||||
@TestDataPath("$PROJECT_ROOT")
|
||||
@InnerTestClasses({PlatformTypes.CommonSupertype.class, PlatformTypes.Intersection.class, PlatformTypes.MethodCall.class})
|
||||
@InnerTestClasses({PlatformTypes.CommonSupertype.class, PlatformTypes.Intersection.class, PlatformTypes.MethodCall.class, PlatformTypes.NullabilityWarnings.class})
|
||||
@RunWith(JUnit3RunnerWithInners.class)
|
||||
public static class PlatformTypes extends AbstractJetDiagnosticsTest {
|
||||
public void testAllFilesPresentInPlatformTypes() throws Exception {
|
||||
@@ -8529,6 +8529,117 @@ public class JetDiagnosticsTestGenerated extends AbstractJetDiagnosticsTest {
|
||||
doTest(fileName);
|
||||
}
|
||||
}
|
||||
|
||||
@TestMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings")
|
||||
@TestDataPath("$PROJECT_ROOT")
|
||||
@RunWith(JUnit3RunnerWithInners.class)
|
||||
public static class NullabilityWarnings extends AbstractJetDiagnosticsTest {
|
||||
public void testAllFilesPresentInNullabilityWarnings() throws Exception {
|
||||
JetTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings"), Pattern.compile("^(.+)\\.kt$"), true);
|
||||
}
|
||||
|
||||
@TestMetadata("arithmetic.kt")
|
||||
public void testArithmetic() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/arithmetic.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("array.kt")
|
||||
public void testArray() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/array.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("assignToVar.kt")
|
||||
public void testAssignToVar() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/assignToVar.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("conditions.kt")
|
||||
public void testConditions() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/conditions.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("dataFlowInfo.kt")
|
||||
public void testDataFlowInfo() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/dataFlowInfo.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("defaultParameters.kt")
|
||||
public void testDefaultParameters() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/defaultParameters.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("delegatedProperties.kt")
|
||||
public void testDelegatedProperties() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/delegatedProperties.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("delegation.kt")
|
||||
public void testDelegation() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/delegation.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("derefenceExtension.kt")
|
||||
public void testDerefenceExtension() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/derefenceExtension.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("derefenceMember.kt")
|
||||
public void testDerefenceMember() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/derefenceMember.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("expectedType.kt")
|
||||
public void testExpectedType() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/expectedType.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("for.kt")
|
||||
public void testFor() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/for.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("functionArguments.kt")
|
||||
public void testFunctionArguments() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/functionArguments.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("invoke.kt")
|
||||
public void testInvoke() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/invoke.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("multiDeclaration.kt")
|
||||
public void testMultiDeclaration() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/multiDeclaration.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("passToJava.kt")
|
||||
public void testPassToJava() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/passToJava.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("throw.kt")
|
||||
public void testThrow() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("compiler/testData/diagnostics/tests/platformTypes/nullabilityWarnings/throw.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@TestMetadata("compiler/testData/diagnostics/tests/recovery")
|
||||
|
||||
+2
-1
@@ -362,7 +362,8 @@ class LazyJavaTypeAttributes(
|
||||
|
||||
private fun Annotations.isMarkedReadOnly() = findAnnotation(JvmAnnotationNames.JETBRAINS_READONLY_ANNOTATION) != null
|
||||
private fun Annotations.isMarkedMutable() = findAnnotation(JvmAnnotationNames.JETBRAINS_MUTABLE_ANNOTATION) != null
|
||||
private fun Annotations.isMarkedNotNull() = findAnnotation(JvmAnnotationNames.JETBRAINS_NOT_NULL_ANNOTATION) != null
|
||||
internal fun Annotations.isMarkedNotNull() = findAnnotation(JvmAnnotationNames.JETBRAINS_NOT_NULL_ANNOTATION) != null
|
||||
internal fun Annotations.isMarkedNullable() = findAnnotation(JvmAnnotationNames.JETBRAINS_NULLABLE_ANNOTATION) != null
|
||||
|
||||
fun TypeUsage.toAttributes(allowFlexible: Boolean = true) = object : JavaTypeAttributes {
|
||||
override val howThisTypeIsUsed: TypeUsage = this@toAttributes
|
||||
|
||||
@@ -35,7 +35,8 @@ import org.jetbrains.kotlin.resolve.calls.checkers.CallChecker
|
||||
|
||||
public object KotlinJsCheckerProvider : AdditionalCheckerProvider(
|
||||
annotationCheckers = listOf(NativeInvokeChecker(), NativeGetterChecker(), NativeSetterChecker()),
|
||||
additionalCallCheckers = listOf()
|
||||
additionalCallCheckers = listOf(),
|
||||
additionalTypeCheckers = listOf()
|
||||
)
|
||||
|
||||
private abstract class AbstractNativeAnnotationsChecker(private val requiredAnnotation: PredefinedAnnotation) : AnnotationChecker {
|
||||
|
||||
@@ -120,4 +120,23 @@ Constructs in question: anything that provides an expected type, i.e.
|
||||
- all kinds of calls (foo, foo(), x[], x foo y, x + y, x++, x += 3, for loop, multi-declarations, invoke-convention, ...)
|
||||
- explicit expected type (foo: Bar)
|
||||
- for booleans: if (foo), foo || bar, foo && bar (!foo is a call)
|
||||
- argument of throw
|
||||
- argument of throw
|
||||
|
||||
## Warnings on nullability misuse
|
||||
|
||||
A type loaded from Java is said to *bare* a `@Nullable`/`@NotNull` annotation when
|
||||
- it's a return type a method so annotated;
|
||||
- it's a type of a field or a parameter so annotated;
|
||||
- it's a so annotated type (Java 8 and later).
|
||||
|
||||
A value is `@Nullable`/`@NotNull` when its type bares such an annotation.
|
||||
|
||||
Inside this section, a value is *nullable*/*not-null* when
|
||||
- it's `@Nullable`/`@NotNull`, or
|
||||
- it's type in Kotlin when refined with data flow info is nullable/not-null.
|
||||
|
||||
The compiler issues warnings specific to `@Nullable`/`@NotNull` in the following situations:
|
||||
- a `@Nullable` value is assigned to a not-null location (including passing parameters and receivers to functions/properties);
|
||||
- a nullable value is assigned to a `@NotNull` location;
|
||||
- a `@NotNull` value is dereferenced with a safe call (`?.`), used in `!!` or on the left-hand side of an elvis operator `?:`;
|
||||
- a `@NotNull` value is compared with `null` through `==`, `!=`, `===` or `!==`
|
||||
Reference in New Issue
Block a user