1*795d594fSAndroid Build Coastguard Worker /* 2*795d594fSAndroid Build Coastguard Worker * Copyright (C) 2014 The Android Open Source Project 3*795d594fSAndroid Build Coastguard Worker * 4*795d594fSAndroid Build Coastguard Worker * Licensed under the Apache License, Version 2.0 (the "License"); 5*795d594fSAndroid Build Coastguard Worker * you may not use this file except in compliance with the License. 6*795d594fSAndroid Build Coastguard Worker * You may obtain a copy of the License at 7*795d594fSAndroid Build Coastguard Worker * 8*795d594fSAndroid Build Coastguard Worker * http://www.apache.org/licenses/LICENSE-2.0 9*795d594fSAndroid Build Coastguard Worker * 10*795d594fSAndroid Build Coastguard Worker * Unless required by applicable law or agreed to in writing, software 11*795d594fSAndroid Build Coastguard Worker * distributed under the License is distributed on an "AS IS" BASIS, 12*795d594fSAndroid Build Coastguard Worker * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13*795d594fSAndroid Build Coastguard Worker * See the License for the specific language governing permissions and 14*795d594fSAndroid Build Coastguard Worker * limitations under the License. 15*795d594fSAndroid Build Coastguard Worker */ 16*795d594fSAndroid Build Coastguard Worker 17*795d594fSAndroid Build Coastguard Worker public class Main { 18*795d594fSAndroid Build Coastguard Worker 19*795d594fSAndroid Build Coastguard Worker /// CHECK-START: void Main.InlineVoid() inliner (before) 20*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const42:i\d+>> IntConstant 42 21*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: InvokeStaticOrDirect 22*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: InvokeStaticOrDirect [<<Const42>>{{(,[ij]\d+)?}}] 23*795d594fSAndroid Build Coastguard Worker 24*795d594fSAndroid Build Coastguard Worker /// CHECK-START: void Main.InlineVoid() inliner (after) 25*795d594fSAndroid Build Coastguard Worker /// CHECK-NOT: InvokeStaticOrDirect 26*795d594fSAndroid Build Coastguard Worker InlineVoid()27*795d594fSAndroid Build Coastguard Worker public static void InlineVoid() { 28*795d594fSAndroid Build Coastguard Worker returnVoid(); 29*795d594fSAndroid Build Coastguard Worker returnVoidWithOneParameter(42); 30*795d594fSAndroid Build Coastguard Worker } 31*795d594fSAndroid Build Coastguard Worker 32*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineParameter(int) inliner (before) 33*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Param:i\d+>> ParameterValue 34*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:i\d+>> InvokeStaticOrDirect [<<Param>>{{(,[ij]\d+)?}}] 35*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 36*795d594fSAndroid Build Coastguard Worker 37*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineParameter(int) inliner (after) 38*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Param:i\d+>> ParameterValue 39*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Param>>] 40*795d594fSAndroid Build Coastguard Worker InlineParameter(int a)41*795d594fSAndroid Build Coastguard Worker public static int InlineParameter(int a) { 42*795d594fSAndroid Build Coastguard Worker return returnParameter(a); 43*795d594fSAndroid Build Coastguard Worker } 44*795d594fSAndroid Build Coastguard Worker 45*795d594fSAndroid Build Coastguard Worker /// CHECK-START: long Main.InlineWideParameter(long) inliner (before) 46*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Param:j\d+>> ParameterValue 47*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:j\d+>> InvokeStaticOrDirect [<<Param>>{{(,[ij]\d+)?}}] 48*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 49*795d594fSAndroid Build Coastguard Worker 50*795d594fSAndroid Build Coastguard Worker /// CHECK-START: long Main.InlineWideParameter(long) inliner (after) 51*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Param:j\d+>> ParameterValue 52*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Param>>] 53*795d594fSAndroid Build Coastguard Worker InlineWideParameter(long a)54*795d594fSAndroid Build Coastguard Worker public static long InlineWideParameter(long a) { 55*795d594fSAndroid Build Coastguard Worker return returnWideParameter(a); 56*795d594fSAndroid Build Coastguard Worker } 57*795d594fSAndroid Build Coastguard Worker 58*795d594fSAndroid Build Coastguard Worker /// CHECK-START: java.lang.Object Main.InlineReferenceParameter(java.lang.Object) inliner (before) 59*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Param:l\d+>> ParameterValue 60*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:l\d+>> InvokeStaticOrDirect [<<Param>>{{(,[ij]\d+)?}}] 61*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 62*795d594fSAndroid Build Coastguard Worker 63*795d594fSAndroid Build Coastguard Worker /// CHECK-START: java.lang.Object Main.InlineReferenceParameter(java.lang.Object) inliner (after) 64*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Param:l\d+>> ParameterValue 65*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Param>>] 66*795d594fSAndroid Build Coastguard Worker InlineReferenceParameter(Object o)67*795d594fSAndroid Build Coastguard Worker public static Object InlineReferenceParameter(Object o) { 68*795d594fSAndroid Build Coastguard Worker return returnReferenceParameter(o); 69*795d594fSAndroid Build Coastguard Worker } 70*795d594fSAndroid Build Coastguard Worker 71*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineInt() inliner (before) 72*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:i\d+>> InvokeStaticOrDirect 73*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 74*795d594fSAndroid Build Coastguard Worker 75*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineInt() inliner (after) 76*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const4:i\d+>> IntConstant 4 77*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Const4>>] 78*795d594fSAndroid Build Coastguard Worker InlineInt()79*795d594fSAndroid Build Coastguard Worker public static int InlineInt() { 80*795d594fSAndroid Build Coastguard Worker return returnInt(); 81*795d594fSAndroid Build Coastguard Worker } 82*795d594fSAndroid Build Coastguard Worker 83*795d594fSAndroid Build Coastguard Worker /// CHECK-START: long Main.InlineWide() inliner (before) 84*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:j\d+>> InvokeStaticOrDirect 85*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 86*795d594fSAndroid Build Coastguard Worker 87*795d594fSAndroid Build Coastguard Worker /// CHECK-START: long Main.InlineWide() inliner (after) 88*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const8:j\d+>> LongConstant 8 89*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Const8>>] 90*795d594fSAndroid Build Coastguard Worker InlineWide()91*795d594fSAndroid Build Coastguard Worker public static long InlineWide() { 92*795d594fSAndroid Build Coastguard Worker return returnWide(); 93*795d594fSAndroid Build Coastguard Worker } 94*795d594fSAndroid Build Coastguard Worker 95*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineAdd() inliner (before) 96*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const3:i\d+>> IntConstant 3 97*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const5:i\d+>> IntConstant 5 98*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:i\d+>> InvokeStaticOrDirect 99*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 100*795d594fSAndroid Build Coastguard Worker 101*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineAdd() inliner (after) 102*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const8:i\d+>> IntConstant 8 103*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Const8>>] 104*795d594fSAndroid Build Coastguard Worker InlineAdd()105*795d594fSAndroid Build Coastguard Worker public static int InlineAdd() { 106*795d594fSAndroid Build Coastguard Worker return returnAdd(3, 5); 107*795d594fSAndroid Build Coastguard Worker } 108*795d594fSAndroid Build Coastguard Worker 109*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineFieldAccess() inliner (before) 110*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<After:i\d+>> InvokeStaticOrDirect 111*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<After>>] 112*795d594fSAndroid Build Coastguard Worker 113*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineFieldAccess() inliner (after) 114*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const1:i\d+>> IntConstant 1 115*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Before:i\d+>> StaticFieldGet 116*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<After:i\d+>> Add [<<Before>>,<<Const1>>] 117*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: StaticFieldSet [{{l\d+}},<<After>>] 118*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<After>>] 119*795d594fSAndroid Build Coastguard Worker 120*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineFieldAccess() inliner (after) 121*795d594fSAndroid Build Coastguard Worker /// CHECK-NOT: InvokeStaticOrDirect 122*795d594fSAndroid Build Coastguard Worker InlineFieldAccess()123*795d594fSAndroid Build Coastguard Worker public static int InlineFieldAccess() { 124*795d594fSAndroid Build Coastguard Worker return incCounter(); 125*795d594fSAndroid Build Coastguard Worker } 126*795d594fSAndroid Build Coastguard Worker 127*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineWithControlFlow(boolean) inliner (before) 128*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const1:i\d+>> IntConstant 1 129*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const3:i\d+>> IntConstant 3 130*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const5:i\d+>> IntConstant 5 131*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Add:i\d+>> InvokeStaticOrDirect [<<Const1>>,<<Const3>>{{(,[ij]\d+)?}}] 132*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Sub:i\d+>> InvokeStaticOrDirect [<<Const5>>,<<Const3>>{{(,[ij]\d+)?}}] 133*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Add>>,<<Sub>>] 134*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Phi>>] 135*795d594fSAndroid Build Coastguard Worker 136*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlineWithControlFlow(boolean) inliner (after) 137*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const4:i\d+>> IntConstant 4 138*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const2:i\d+>> IntConstant 2 139*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Const4>>,<<Const2>>] 140*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Phi>>] 141*795d594fSAndroid Build Coastguard Worker InlineWithControlFlow(boolean cond)142*795d594fSAndroid Build Coastguard Worker public static int InlineWithControlFlow(boolean cond) { 143*795d594fSAndroid Build Coastguard Worker int x, const1, const3, const5; 144*795d594fSAndroid Build Coastguard Worker const1 = 1; 145*795d594fSAndroid Build Coastguard Worker const3 = 3; 146*795d594fSAndroid Build Coastguard Worker const5 = 5; 147*795d594fSAndroid Build Coastguard Worker if (cond) { 148*795d594fSAndroid Build Coastguard Worker x = returnAdd(const1, const3); 149*795d594fSAndroid Build Coastguard Worker } else { 150*795d594fSAndroid Build Coastguard Worker x = returnSub(const5, const3); 151*795d594fSAndroid Build Coastguard Worker } 152*795d594fSAndroid Build Coastguard Worker return x; 153*795d594fSAndroid Build Coastguard Worker } 154*795d594fSAndroid Build Coastguard Worker 155*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.returnAbs(int) builder (after) 156*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:i\d+>> Abs 157*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 158*795d594fSAndroid Build Coastguard Worker returnAbs(int i)159*795d594fSAndroid Build Coastguard Worker private static int returnAbs(int i) { 160*795d594fSAndroid Build Coastguard Worker return Math.abs(i); 161*795d594fSAndroid Build Coastguard Worker } 162*795d594fSAndroid Build Coastguard Worker 163*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlinedIntrinsicsAreStillIntrinsic() inliner (before) 164*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<ConstMinus1:i\d+>> IntConstant -1 165*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Result:i\d+>> InvokeStaticOrDirect 166*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Result>>] 167*795d594fSAndroid Build Coastguard Worker 168*795d594fSAndroid Build Coastguard Worker // 169*795d594fSAndroid Build Coastguard Worker // Intrinsic directly simplified into Abs and evaluated! 170*795d594fSAndroid Build Coastguard Worker // 171*795d594fSAndroid Build Coastguard Worker /// CHECK-START: int Main.InlinedIntrinsicsAreStillIntrinsic() inliner (after) 172*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: <<Const1:i\d+>> IntConstant 1 173*795d594fSAndroid Build Coastguard Worker /// CHECK-DAG: Return [<<Const1>>] 174*795d594fSAndroid Build Coastguard Worker InlinedIntrinsicsAreStillIntrinsic()175*795d594fSAndroid Build Coastguard Worker public static int InlinedIntrinsicsAreStillIntrinsic() { 176*795d594fSAndroid Build Coastguard Worker return returnAbs(-1); 177*795d594fSAndroid Build Coastguard Worker } 178*795d594fSAndroid Build Coastguard Worker returnVoid()179*795d594fSAndroid Build Coastguard Worker private static void returnVoid() { 180*795d594fSAndroid Build Coastguard Worker return; 181*795d594fSAndroid Build Coastguard Worker } 182*795d594fSAndroid Build Coastguard Worker returnVoidWithOneParameter(int a)183*795d594fSAndroid Build Coastguard Worker private static void returnVoidWithOneParameter(int a) { 184*795d594fSAndroid Build Coastguard Worker return; 185*795d594fSAndroid Build Coastguard Worker } 186*795d594fSAndroid Build Coastguard Worker returnParameter(int a)187*795d594fSAndroid Build Coastguard Worker private static int returnParameter(int a) { 188*795d594fSAndroid Build Coastguard Worker return a; 189*795d594fSAndroid Build Coastguard Worker } 190*795d594fSAndroid Build Coastguard Worker returnWideParameter(long a)191*795d594fSAndroid Build Coastguard Worker private static long returnWideParameter(long a) { 192*795d594fSAndroid Build Coastguard Worker return a; 193*795d594fSAndroid Build Coastguard Worker } 194*795d594fSAndroid Build Coastguard Worker returnReferenceParameter(Object o)195*795d594fSAndroid Build Coastguard Worker private static Object returnReferenceParameter(Object o) { 196*795d594fSAndroid Build Coastguard Worker return o; 197*795d594fSAndroid Build Coastguard Worker } 198*795d594fSAndroid Build Coastguard Worker returnInt()199*795d594fSAndroid Build Coastguard Worker private static int returnInt() { 200*795d594fSAndroid Build Coastguard Worker return 4; 201*795d594fSAndroid Build Coastguard Worker } 202*795d594fSAndroid Build Coastguard Worker returnWide()203*795d594fSAndroid Build Coastguard Worker private static long returnWide() { 204*795d594fSAndroid Build Coastguard Worker return 8L; 205*795d594fSAndroid Build Coastguard Worker } 206*795d594fSAndroid Build Coastguard Worker returnAdd(int a, int b)207*795d594fSAndroid Build Coastguard Worker private static int returnAdd(int a, int b) { 208*795d594fSAndroid Build Coastguard Worker return a + b; 209*795d594fSAndroid Build Coastguard Worker } 210*795d594fSAndroid Build Coastguard Worker returnSub(int a, int b)211*795d594fSAndroid Build Coastguard Worker private static int returnSub(int a, int b) { 212*795d594fSAndroid Build Coastguard Worker return a - b; 213*795d594fSAndroid Build Coastguard Worker } 214*795d594fSAndroid Build Coastguard Worker 215*795d594fSAndroid Build Coastguard Worker private static int counter = 42; 216*795d594fSAndroid Build Coastguard Worker incCounter()217*795d594fSAndroid Build Coastguard Worker private static int incCounter() { 218*795d594fSAndroid Build Coastguard Worker return ++counter; 219*795d594fSAndroid Build Coastguard Worker } 220*795d594fSAndroid Build Coastguard Worker main(String[] args)221*795d594fSAndroid Build Coastguard Worker public static void main(String[] args) { 222*795d594fSAndroid Build Coastguard Worker InlineVoid(); 223*795d594fSAndroid Build Coastguard Worker 224*795d594fSAndroid Build Coastguard Worker if (InlineInt() != 4) { 225*795d594fSAndroid Build Coastguard Worker throw new Error(); 226*795d594fSAndroid Build Coastguard Worker } 227*795d594fSAndroid Build Coastguard Worker 228*795d594fSAndroid Build Coastguard Worker if (InlineWide() != 8L) { 229*795d594fSAndroid Build Coastguard Worker throw new Error(); 230*795d594fSAndroid Build Coastguard Worker } 231*795d594fSAndroid Build Coastguard Worker 232*795d594fSAndroid Build Coastguard Worker if (InlineParameter(42) != 42) { 233*795d594fSAndroid Build Coastguard Worker throw new Error(); 234*795d594fSAndroid Build Coastguard Worker } 235*795d594fSAndroid Build Coastguard Worker 236*795d594fSAndroid Build Coastguard Worker if (InlineWideParameter(0x100000001L) != 0x100000001L) { 237*795d594fSAndroid Build Coastguard Worker throw new Error(); 238*795d594fSAndroid Build Coastguard Worker } 239*795d594fSAndroid Build Coastguard Worker 240*795d594fSAndroid Build Coastguard Worker if (InlineReferenceParameter(Main.class) != Main.class) { 241*795d594fSAndroid Build Coastguard Worker throw new Error(); 242*795d594fSAndroid Build Coastguard Worker } 243*795d594fSAndroid Build Coastguard Worker 244*795d594fSAndroid Build Coastguard Worker if (InlineAdd() != 8) { 245*795d594fSAndroid Build Coastguard Worker throw new Error(); 246*795d594fSAndroid Build Coastguard Worker } 247*795d594fSAndroid Build Coastguard Worker 248*795d594fSAndroid Build Coastguard Worker if (InlineFieldAccess() != 43 || InlineFieldAccess() != 44) { 249*795d594fSAndroid Build Coastguard Worker throw new Error(); 250*795d594fSAndroid Build Coastguard Worker } 251*795d594fSAndroid Build Coastguard Worker 252*795d594fSAndroid Build Coastguard Worker if (InlineWithControlFlow(true) != 4) { 253*795d594fSAndroid Build Coastguard Worker throw new Error(); 254*795d594fSAndroid Build Coastguard Worker } 255*795d594fSAndroid Build Coastguard Worker 256*795d594fSAndroid Build Coastguard Worker if (InlineWithControlFlow(false) != 2) { 257*795d594fSAndroid Build Coastguard Worker throw new Error(); 258*795d594fSAndroid Build Coastguard Worker } 259*795d594fSAndroid Build Coastguard Worker 260*795d594fSAndroid Build Coastguard Worker if (InlinedIntrinsicsAreStillIntrinsic() != 1) { 261*795d594fSAndroid Build Coastguard Worker throw new Error(); 262*795d594fSAndroid Build Coastguard Worker } 263*795d594fSAndroid Build Coastguard Worker 264*795d594fSAndroid Build Coastguard Worker if (returnAbs(-1) != 1) { 265*795d594fSAndroid Build Coastguard Worker throw new Error(); 266*795d594fSAndroid Build Coastguard Worker } 267*795d594fSAndroid Build Coastguard Worker } 268*795d594fSAndroid Build Coastguard Worker } 269