1 /* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 public class Main { 18 main(String[] args)19 public static void main(String[] args) {} 20 public static int foo = 42; 21 22 // Primitive array initialization is trivial for purposes of the ClinitCheck. It cannot 23 // leak instances of erroneous classes or initialize subclasses of erroneous classes. 24 public static int[] array1 = new int[] { 1, 2, 3 }; 25 public static int[] array2; 26 static { 27 int[] a = new int[4]; 28 a[0] = 42; 29 array2 = a; 30 } 31 32 /// CHECK-START: void Main.inlinedMethod() builder (after) 33 /// CHECK: ClinitCheck 34 35 /// CHECK-START: void Main.inlinedMethod() inliner (after) 36 /// CHECK: ClinitCheck 37 /// CHECK-NOT: ClinitCheck 38 /// CHECK-NOT: InvokeStaticOrDirect inlinedMethod()39 public void inlinedMethod() { 40 SubSub.bar(); 41 } 42 } 43 44 class Sub extends Main { 45 /// CHECK-START: void Sub.invokeSuperClass() builder (after) 46 /// CHECK-NOT: ClinitCheck invokeSuperClass()47 public void invokeSuperClass() { 48 // No Class initialization check as Main.<clinit> is trivial. b/62478025 49 int a = Main.foo; 50 } 51 52 /// CHECK-START: void Sub.invokeItself() builder (after) 53 /// CHECK-NOT: ClinitCheck invokeItself()54 public void invokeItself() { 55 // No Class initialization check as Sub.<clinit> and Main.<clinit> are trivial. b/62478025 56 int a = foo; 57 } 58 59 /// CHECK-START: void Sub.invokeSubClass() builder (after) 60 /// CHECK: ClinitCheck invokeSubClass()61 public void invokeSubClass() { 62 int a = SubSub.foo; 63 } 64 65 public static int foo = 42; 66 } 67 68 class SubSub { bar()69 public static void bar() { 70 int a = Main.foo; 71 } 72 public static int foo = 42; 73 } 74 75 class NonTrivial { 76 public static int staticFoo = 42; 77 public int instanceFoo; 78 79 static { 80 System.out.println("NonTrivial.<clinit>"); 81 } 82 83 /// CHECK-START: void NonTrivial.<init>() builder (after) 84 /// CHECK-NOT: ClinitCheck 85 86 /// CHECK-START: void NonTrivial.<init>() builder (after) 87 /// CHECK: StaticFieldGet NonTrivial()88 public NonTrivial() { 89 // ClinitCheck is eliminated because this is a constructor and therefore the 90 // corresponding new-instance in the caller must have performed the check. 91 instanceFoo = staticFoo; 92 } 93 } 94