Fix for KT-11964: No TABLESWITCH in when on enum bytecode if enum constant is imported

#KT-11964 Fixed
This commit is contained in:
Michael Bogdanov
2016-06-26 19:13:23 +03:00
parent 81ec18e1fc
commit 3b419e8ba3
10 changed files with 31 additions and 8 deletions
@@ -161,6 +161,7 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor {
KotlinTypeInfo typeInfo = callExpressionResolver.getSimpleNameExpressionTypeInfo(expression, null, null, context);
checkNull(expression, context, typeInfo.getType());
components.constantExpressionEvaluator.evaluateExpression(expression, context.trace, context.expectedType);
return components.dataFlowAnalyzer.checkType(typeInfo, expression, context); // TODO : Extensions to this
}
@@ -0,0 +1,13 @@
import Color.RED
enum class Color { RED, GREEN, BLUE }
fun fifth(arg: Color) = when (arg) {
RED -> 1
Color.GREEN -> 2
Color.BLUE -> 3
}
// 1 TABLESWITCH
// 0 LOOKUPSWITCH
+1 -1
View File
@@ -26,7 +26,7 @@ fun test() {
when (x) {
<!INCOMPATIBLE_TYPES!>s<!> -> <!UNUSED_EXPRESSION!>1<!>
<!INCOMPATIBLE_TYPES!>""<!> -> <!UNUSED_EXPRESSION!>1<!>
<!INCOMPATIBLE_TYPES, DUPLICATE_LABEL_IN_WHEN!>""<!> -> <!UNUSED_EXPRESSION!>1<!>
x -> <!UNUSED_EXPRESSION!>1<!>
1 -> <!UNUSED_EXPRESSION!>1<!>
}
@@ -1429,6 +1429,12 @@ public class BytecodeTextTestGenerated extends AbstractBytecodeTextTest {
doTest(fileName);
}
@TestMetadata("importedEnumEntry.kt")
public void testImportedEnumEntry() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/bytecodeText/whenEnumOptimization/importedEnumEntry.kt");
doTest(fileName);
}
@TestMetadata("manyWhensWithinClass.kt")
public void testManyWhensWithinClass() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/bytecodeText/whenEnumOptimization/manyWhensWithinClass.kt");
@@ -16,6 +16,7 @@ Cleaning output files:
out/production/module/GetRandomEnumEntryKt.class
out/production/module/META-INF/module.kotlin_module
out/production/module/UseEnumImplicitlyKt.class
out/production/module/UseKt$WhenMappings.class
out/production/module/UseKt.class
End of files
Compiling files:
@@ -16,6 +16,7 @@ Cleaning output files:
out/production/module/GetRandomEnumEntryKt.class
out/production/module/META-INF/module.kotlin_module
out/production/module/UseEnumImplicitlyKt.class
out/production/module/UseKt$WhenMappings.class
out/production/module/UseKt.class
End of files
Compiling files:
@@ -13,6 +13,7 @@ End of files
Cleaning output files:
out/production/module/META-INF/module.kotlin_module
out/production/module/UseKt$WhenMappings.class
out/production/module/UseKt.class
End of files
Compiling files:
@@ -10,6 +10,7 @@ Compiling files:
End of files
Cleaning output files:
out/production/module/META-INF/module.kotlin_module
out/production/module/UseKt$WhenMappings.class
out/production/module/UseKt.class
End of files
Compiling files:
+1 -2
View File
@@ -12,10 +12,9 @@ class TestAlarm {
alarmManager.setRepeating(AlarmManager.ELAPSED_REALTIME, 5000, // ERROR
<warning descr="Value will be forced up to 60000 as of Android 5.1; don't rely on this to be exact">OtherClass.MY_INTERVAL</warning>, null); // ERROR
// Check value flow analysis, currently unsupported
val interval = 10;
val interval2 = 2L * interval;
alarmManager.setRepeating(AlarmManager.ELAPSED_REALTIME, 5000, interval2, null); // ERROR
alarmManager.setRepeating(AlarmManager.ELAPSED_REALTIME, 5000, <warning descr="Value will be forced up to 60000 as of Android 5.1; don't rely on this to be exact">interval2</warning>, null); // ERROR
}
private object OtherClass {
+5 -5
View File
@@ -26,8 +26,8 @@ class LogTest {
}
fun checkWrongTag(tag: String) {
if (Log.isLoggable(<error descr="Mismatched tags: the `d()` and `isLoggable()` calls typically should pass the same tag: `null` versus `null` (Conflicting tag)">TAG1</error>, Log.DEBUG)) {
Log.d(<error descr="Mismatched tags: the `d()` and `isLoggable()` calls typically should pass the same tag: `null` versus `null`">TAG2</error>, "message") // warn: mismatched tags!
if (Log.isLoggable(<error descr="Mismatched tags: the `d()` and `isLoggable()` calls typically should pass the same tag: `MyTag1` versus `MyTag2` (Conflicting tag)">TAG1</error>, Log.DEBUG)) {
Log.d(<error descr="Mismatched tags: the `d()` and `isLoggable()` calls typically should pass the same tag: `MyTag1` versus `MyTag2`">TAG2</error>, "message") // warn: mismatched tags!
}
if (Log.isLoggable("<error descr="Mismatched tags: the `d()` and `isLoggable()` calls typically should pass the same tag: `my_tag` versus `other_tag` (Conflicting tag)">my_tag</error>", Log.DEBUG)) {
Log.d("<error descr="Mismatched tags: the `d()` and `isLoggable()` calls typically should pass the same tag: `my_tag` versus `other_tag`">other_tag</error>", "message") // warn: mismatched tags!
@@ -50,12 +50,12 @@ class LogTest {
Log.d(TAG1, "message") // ok: short
Log.d(TAG22, "message") // ok: short
Log.d(TAG23, "message") // ok: threshold
Log.d(TAG24, "message") // error: too long
Log.d(LONG_TAG, "message") // error: way too long
Log.<error descr="The logging tag can be at most 23 characters, was 24 (123456789012345678901234)">d(TAG24, "message")</error> // error: too long
Log.<error descr="The logging tag can be at most 23 characters, was 39 (MyReallyReallyReallyReallyReallyLongTag)">d(LONG_TAG, "message")</error> // error: way too long
// Locally defined variable tags
val LOCAL_TAG = "MyReallyReallyReallyReallyReallyLongTag"
Log.d(LOCAL_TAG, "message") // error: too long
Log.<error descr="The logging tag can be at most 23 characters, was 39 (MyReallyReallyReallyReallyReallyLongTag)">d(LOCAL_TAG, "message")</error> // error: too long
// Concatenated tags
Log.<error descr="The logging tag can be at most 23 characters, was 28 (1234567890123456789012MyTag1)">d(TAG22 + TAG1, "message")</error> // error: too long