| // Test field initialization |
| // fields, initializers, static initializers, constructors. |
| |
| import org.checkerframework.checker.nullness.qual.*; |
| |
| interface FunctionInit<T extends @Nullable Object, R> { |
| R apply(T t); |
| } |
| |
| interface Consumer<T> { |
| void consume(T t); |
| } |
| |
| public class LambdaInit { |
| String f1; |
| String f2 = ""; |
| @Nullable String f3 = ""; |
| |
| String f1b; |
| FunctionInit<String, String> ff0 = |
| s -> { |
| // :: error: (dereference.of.nullable) |
| f1.toString(); |
| // :: error: (dereference.of.nullable) |
| f1b.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| return ""; |
| }; |
| // Test field value refinement after initializer. f1b should still be @Nullable in the lambda. |
| Object o1 = f1b = ""; |
| |
| String f4; |
| |
| { |
| f3 = ""; |
| f4 = ""; |
| FunctionInit<String, String> ff0 = |
| s -> { |
| // :: error: (dereference.of.nullable) |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| f4.toString(); |
| return ""; |
| }; |
| } |
| |
| String f5; |
| |
| @SuppressWarnings("initialization.fields.uninitialized") // f1 is not initialized |
| LambdaInit() { |
| f5 = ""; |
| FunctionInit<String, String> ff0 = |
| s -> { |
| // :: error: (dereference.of.nullable) |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| f5.toString(); |
| return ""; |
| }; |
| } |
| |
| // // This is a bug |
| // // Could probably be fixed with CommittmentTreeAnnotator::visitMethod |
| // // Or more likely, TypeFromTree::212 |
| // // AnnotatedTypeFactory::getImplicitReceiverType::1146(there is a todo...) |
| // Object o = new Object() { |
| // @Override |
| // public String toString() { |
| // f1.toString(); |
| // f2.toString(); |
| // return ""; |
| // } |
| // }; |
| // |
| |
| // Works! |
| void method() { |
| FunctionInit<String, String> ff0 = |
| s -> { |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| return ""; |
| }; |
| } |
| |
| // Test for nested |
| class Nested { |
| FunctionInit<String, String> ff0 = |
| s -> { |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| return ""; |
| }; |
| |
| String f4; |
| |
| { |
| f3 = ""; |
| f4 = ""; |
| FunctionInit<String, String> ff0 = |
| s -> { |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| f4.toString(); |
| return ""; |
| }; |
| } |
| |
| String f5; |
| |
| Nested() { |
| f5 = ""; |
| FunctionInit<String, String> ff0 = |
| s -> { |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| f5.toString(); |
| return ""; |
| }; |
| } |
| |
| void method() { |
| FunctionInit<String, String> ff0 = |
| s -> { |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| return ""; |
| }; |
| } |
| } |
| |
| // Test for nested in a lambda |
| Consumer<String> func = |
| s -> { |
| Consumer<String> ff0 = |
| s2 -> { |
| // :: error: (dereference.of.nullable) |
| f1.toString(); |
| f2.toString(); |
| // :: error: (dereference.of.nullable) |
| f3.toString(); |
| }; |
| }; |
| |
| // Tests for static initializers. |
| // :: error: (initialization.static.field.uninitialized) |
| static String sf1; |
| static String sf2 = ""; |
| static @Nullable String sf3 = ""; |
| static String sf1b; |
| static FunctionInit<String, String> sff0 = |
| s -> { |
| |
| // This is an issue with static initializers in general |
| // // :: error: (dereference.of.nullable) |
| sf1.toString(); |
| // This is an issue with static initializers in general |
| // // :: error: (dereference.of.nullable) |
| sf1b.toString(); |
| sf2.toString(); |
| // :: error: (dereference.of.nullable) |
| sf3.toString(); |
| return ""; |
| }; |
| // Test field value refinement after initializer. f1b should still be null. |
| static Object so1 = sf1b = ""; |
| |
| static String sf4; |
| |
| static { |
| sf3 = ""; |
| sf4 = ""; |
| FunctionInit<String, String> sff0 = |
| s -> { |
| |
| // This is an issue with static initializers in general |
| // // :: error: (dereference.of.nullable) |
| sf1.toString(); |
| sf2.toString(); |
| // :: error: (dereference.of.nullable) |
| sf3.toString(); |
| sf4.toString(); |
| return ""; |
| }; |
| } |
| } |