Add some data flow analysis tests on when
This commit is contained in:
committed by
Dmitry Petrov
parent
ae929d0f08
commit
148d03e365
+37
@@ -0,0 +1,37 @@
|
||||
// !LANGUAGE: +VariableDeclarationInWhenSubject
|
||||
// !DIAGNOSTICS: -UNUSED_VARIABLE
|
||||
|
||||
fun getBoolean() = true
|
||||
|
||||
fun testSafeCaptureVarInInitializer() {
|
||||
var x: Int? = 42
|
||||
x!!
|
||||
<!DEBUG_INFO_SMARTCAST!>x<!>.inc()
|
||||
|
||||
val s = when (val y = run { x = 42; 32 }) {
|
||||
0 -> {
|
||||
<!SMARTCAST_IMPOSSIBLE!>x<!>.inc() // TODO fix smart casts for captured variables
|
||||
"0"
|
||||
}
|
||||
else -> "!= 0"
|
||||
}
|
||||
|
||||
<!SMARTCAST_IMPOSSIBLE!>x<!>.inc() // TODO fix smart casts for captured variables
|
||||
}
|
||||
|
||||
|
||||
fun testUnsafeCaptureVarInInitializer() {
|
||||
var x: Int? = 42
|
||||
x!!
|
||||
<!DEBUG_INFO_SMARTCAST!>x<!>.inc()
|
||||
|
||||
val s = when (val y = run { x = null; 32 }) {
|
||||
0 -> {
|
||||
<!SMARTCAST_IMPOSSIBLE!>x<!>.inc() // NB smart cast should be impossible
|
||||
"0"
|
||||
}
|
||||
else -> "!= 0"
|
||||
}
|
||||
|
||||
<!SMARTCAST_IMPOSSIBLE!>x<!>.inc() // NB smart cast should be impossible
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
package
|
||||
|
||||
public fun getBoolean(): kotlin.Boolean
|
||||
public fun testSafeCaptureVarInInitializer(): kotlin.Unit
|
||||
public fun testUnsafeCaptureVarInInitializer(): kotlin.Unit
|
||||
+43
@@ -0,0 +1,43 @@
|
||||
// !LANGUAGE: +VariableDeclarationInWhenSubject
|
||||
// !DIAGNOSTICS: -UNUSED_VARIABLE
|
||||
|
||||
|
||||
fun testJumpOutInElvis(x: Int?) {
|
||||
loop@ while (true) {
|
||||
val y = when (val z = x ?: break@loop) {
|
||||
0 -> "0"
|
||||
else -> "not 0"
|
||||
}
|
||||
|
||||
<!DEBUG_INFO_SMARTCAST!>x<!>.inc()
|
||||
}
|
||||
|
||||
x<!UNSAFE_CALL!>.<!>inc()
|
||||
}
|
||||
|
||||
fun testJumpOutInElvisLikeIf(x: Int?) {
|
||||
loop@ while (true) {
|
||||
val y = when (val z = if (x == null) break@loop else <!DEBUG_INFO_SMARTCAST!>x<!>) {
|
||||
0 -> "0"
|
||||
else -> "not 0"
|
||||
}
|
||||
<!DEBUG_INFO_SMARTCAST!>x<!>.inc()
|
||||
}
|
||||
|
||||
x<!UNSAFE_CALL!>.<!>inc()
|
||||
}
|
||||
|
||||
|
||||
fun getBoolean() = true
|
||||
|
||||
fun testJumpOutInIf(x: Int?) {
|
||||
loop@ while (true) {
|
||||
val y = when (val z = if (getBoolean()) { x!!; break@loop } else x) {
|
||||
0 -> "0"
|
||||
else -> "not 0"
|
||||
}
|
||||
x<!UNSAFE_CALL!>.<!>inc()
|
||||
}
|
||||
|
||||
x<!UNSAFE_CALL!>.<!>inc() // Actually, safe, but it's OK if it's error
|
||||
}
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
package
|
||||
|
||||
public fun getBoolean(): kotlin.Boolean
|
||||
public fun testJumpOutInElvis(/*0*/ x: kotlin.Int?): kotlin.Unit
|
||||
public fun testJumpOutInElvisLikeIf(/*0*/ x: kotlin.Int?): kotlin.Unit
|
||||
public fun testJumpOutInIf(/*0*/ x: kotlin.Int?): kotlin.Unit
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
// !LANGUAGE: +VariableDeclarationInWhenSubject
|
||||
// !DIAGNOSTICS: -UNUSED_VARIABLE -UNUSED_PARAMETER
|
||||
|
||||
|
||||
fun testNoSubjectVariableName(x: Int?) {
|
||||
val y = when (val<!SYNTAX!><!> = 42) {
|
||||
0 -> "0"
|
||||
else -> "not 0"
|
||||
}
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
package
|
||||
|
||||
public fun testNoSubjectVariableName(/*0*/ x: kotlin.Int?): kotlin.Unit
|
||||
+23
@@ -0,0 +1,23 @@
|
||||
// !LANGUAGE: +VariableDeclarationInWhenSubject
|
||||
// !DIAGNOSTICS: -UNUSED_VARIABLE
|
||||
|
||||
enum class E { FIRST, SECOND }
|
||||
|
||||
fun testSmartcastToEnumInSubjectInitializer(e: E?) {
|
||||
val x = <!NO_ELSE_IN_WHEN!>when<!> (val ne = e!!) { // TODO fix
|
||||
E.FIRST -> "f"
|
||||
E.SECOND -> "s"
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
sealed class Either
|
||||
class Left : Either()
|
||||
class Right : Either()
|
||||
|
||||
fun testSmartcastToSealedInSubjectInitializer(x: Any?) {
|
||||
val y = <!NO_ELSE_IN_WHEN!>when<!> (val either = x as Either) { // TODO fix
|
||||
is Left -> "L"
|
||||
is Right -> "R"
|
||||
}
|
||||
}
|
||||
+46
@@ -0,0 +1,46 @@
|
||||
package
|
||||
|
||||
public fun testSmartcastToEnumInSubjectInitializer(/*0*/ e: E?): kotlin.Unit
|
||||
public fun testSmartcastToSealedInSubjectInitializer(/*0*/ x: kotlin.Any?): kotlin.Unit
|
||||
|
||||
public final enum class E : kotlin.Enum<E> {
|
||||
enum entry FIRST
|
||||
|
||||
enum entry SECOND
|
||||
|
||||
private constructor E()
|
||||
public final override /*1*/ /*fake_override*/ val name: kotlin.String
|
||||
public final override /*1*/ /*fake_override*/ val ordinal: kotlin.Int
|
||||
protected final override /*1*/ /*fake_override*/ fun clone(): kotlin.Any
|
||||
public final override /*1*/ /*fake_override*/ fun compareTo(/*0*/ other: E): kotlin.Int
|
||||
public final override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
protected/*protected and package*/ final override /*1*/ /*fake_override*/ /*isHiddenForResolutionEverywhereBesideSupercalls*/ fun finalize(): kotlin.Unit
|
||||
public final override /*1*/ /*fake_override*/ /*isHiddenForResolutionEverywhereBesideSupercalls*/ fun getDeclaringClass(): java.lang.Class<E!>!
|
||||
public final override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
|
||||
// Static members
|
||||
public final /*synthesized*/ fun valueOf(/*0*/ value: kotlin.String): E
|
||||
public final /*synthesized*/ fun values(): kotlin.Array<E>
|
||||
}
|
||||
|
||||
public sealed class Either {
|
||||
private constructor Either()
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public final class Left : Either {
|
||||
public constructor Left()
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
|
||||
public final class Right : Either {
|
||||
public constructor Right()
|
||||
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
|
||||
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
|
||||
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
|
||||
}
|
||||
@@ -22470,16 +22470,31 @@ public class DiagnosticsTestGenerated extends AbstractDiagnosticsTest {
|
||||
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/diagnostics/tests/when/withSubjectVariable"), Pattern.compile("^(.+)\\.kt$"), TargetBackend.ANY, true);
|
||||
}
|
||||
|
||||
@TestMetadata("capturingInInitializer.kt")
|
||||
public void testCapturingInInitializer() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/capturingInInitializer.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("invisibleOutsideOfWhen.kt")
|
||||
public void testInvisibleOutsideOfWhen() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/invisibleOutsideOfWhen.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("jumpoutInInitializer.kt")
|
||||
public void testJumpoutInInitializer() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/jumpoutInInitializer.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("nestedWhenWithSubject.kt")
|
||||
public void testNestedWhenWithSubject() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/nestedWhenWithSubject.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("noSubjectVariableName.kt")
|
||||
public void testNoSubjectVariableName() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/noSubjectVariableName.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("reassignmentToWhenSubjectVariable.kt")
|
||||
public void testReassignmentToWhenSubjectVariable() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/reassignmentToWhenSubjectVariable.kt");
|
||||
@@ -22500,6 +22515,11 @@ public class DiagnosticsTestGenerated extends AbstractDiagnosticsTest {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/smartCastsOnSubjectVariable.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("smartcastToEnum.kt")
|
||||
public void testSmartcastToEnum() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/smartcastToEnum.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("subjectVariableInIsPattern.kt")
|
||||
public void testSubjectVariableInIsPattern() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/subjectVariableInIsPattern.kt");
|
||||
|
||||
Generated
+20
@@ -22470,16 +22470,31 @@ public class DiagnosticsUsingJavacTestGenerated extends AbstractDiagnosticsUsing
|
||||
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/diagnostics/tests/when/withSubjectVariable"), Pattern.compile("^(.+)\\.kt$"), TargetBackend.ANY, true);
|
||||
}
|
||||
|
||||
@TestMetadata("capturingInInitializer.kt")
|
||||
public void testCapturingInInitializer() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/capturingInInitializer.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("invisibleOutsideOfWhen.kt")
|
||||
public void testInvisibleOutsideOfWhen() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/invisibleOutsideOfWhen.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("jumpoutInInitializer.kt")
|
||||
public void testJumpoutInInitializer() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/jumpoutInInitializer.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("nestedWhenWithSubject.kt")
|
||||
public void testNestedWhenWithSubject() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/nestedWhenWithSubject.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("noSubjectVariableName.kt")
|
||||
public void testNoSubjectVariableName() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/noSubjectVariableName.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("reassignmentToWhenSubjectVariable.kt")
|
||||
public void testReassignmentToWhenSubjectVariable() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/reassignmentToWhenSubjectVariable.kt");
|
||||
@@ -22500,6 +22515,11 @@ public class DiagnosticsUsingJavacTestGenerated extends AbstractDiagnosticsUsing
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/smartCastsOnSubjectVariable.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("smartcastToEnum.kt")
|
||||
public void testSmartcastToEnum() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/smartcastToEnum.kt");
|
||||
}
|
||||
|
||||
@TestMetadata("subjectVariableInIsPattern.kt")
|
||||
public void testSubjectVariableInIsPattern() throws Exception {
|
||||
runTest("compiler/testData/diagnostics/tests/when/withSubjectVariable/subjectVariableInIsPattern.kt");
|
||||
|
||||
Reference in New Issue
Block a user