1 /*
  2  * Copyright (c) 2024, Oracle and/or its affiliates. All rights reserved.
  3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  4  *
  5  * This code is free software; you can redistribute it and/or modify it
  6  * under the terms of the GNU General Public License version 2 only, as
  7  * published by the Free Software Foundation.
  8  *
  9  * This code is distributed in the hope that it will be useful, but WITHOUT
 10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 12  * version 2 for more details (a copy is included in the LICENSE file that
 13  * accompanied this code).
 14  *
 15  * You should have received a copy of the GNU General Public License version
 16  * 2 along with this work; if not, write to the Free Software Foundation,
 17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 18  *
 19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 20  * or visit www.oracle.com if you need additional information or have any
 21  * questions.
 22  */
 23 
 24 /*
 25  * @test
 26  * @summary Smoke test for code reflection with binary operations.
 27  * @modules jdk.incubator.code
 28  * @build BinopTest
 29  * @build CodeReflectionTester
 30  * @run main CodeReflectionTester BinopTest
 31  */
 32 
 33 import jdk.incubator.code.CodeReflection;
 34 
 35 public class BinopTest {
 36 
 37     @CodeReflection
 38     @IR("""
 39             func @"test" (%0 : BinopTest)int -> {
 40                 %1 : int = constant @"5";
 41                 %2 : int = constant @"2";
 42                 %3 : int = constant @"4";
 43                 %4 : int = mul %2 %3;
 44                 %5 : int = add %1 %4;
 45                 %6 : int = constant @"3";
 46                 %7 : int = sub %5 %6;
 47                 return %7;
 48             };
 49             """)
 50     int test() {
 51         return 5 + 2 * 4 - 3;
 52     }
 53 
 54     @CodeReflection
 55     @IR("""
 56             func @"test2" (%0 : BinopTest)int -> {
 57                 %1 : int = constant @"1";
 58                 %2 : int = constant @"2";
 59                 %3 : int = constant @"3";
 60                 %4 : int = constant @"4";
 61                 %5 : int = add %3 %4;
 62                 %6 : int = add %2 %5;
 63                 %7 : int = add %1 %6;
 64                 return %7;
 65             };
 66             """)
 67     int test2() {
 68         return 1 + (2 + (3 + 4));
 69     }
 70 
 71     @CodeReflection
 72     @IR("""
 73             func @"test3" (%0 : BinopTest)int -> {
 74                 %1 : int = constant @"1";
 75                 %2 : int = constant @"2";
 76                 %3 : int = add %1 %2;
 77                 %4 : int = constant @"3";
 78                 %5 : int = add %3 %4;
 79                 %6 : int = constant @"4";
 80                 %7 : int = add %5 %6;
 81                 return %7;
 82             };
 83             """)
 84     int test3() {
 85         return ((1 + 2) + 3) + 4;
 86     }
 87 
 88     @CodeReflection
 89     @IR("""
 90             func @"test4" (%0 : BinopTest, %1 : int)int -> {
 91                 %2 : Var<int> = var %1 @"i";
 92                 %3 : int = var.load %2;
 93                 %4 : int = constant @"1";
 94                 %5 : int = add %3 %4;
 95                 var.store %2 %5;
 96                 %6 : int = var.load %2;
 97                 %7 : int = constant @"1";
 98                 %8 : int = mul %6 %7;
 99                 var.store %2 %8;
100                 %9 : int = add %5 %8;
101                 %10 : int = var.load %2;
102                 %11 : int = constant @"1";
103                 %12 : int = div %10 %11;
104                 var.store %2 %12;
105                 %13 : int = add %9 %12;
106                 %14 : int = var.load %2;
107                 %15 : int = constant @"1";
108                 %16 : int = sub %14 %15;
109                 var.store %2 %16;
110                 %17 : int = add %13 %16;
111                 %18 : int = var.load %2;
112                 %19 : int = constant @"1";
113                 %20 : int = mod %18 %19;
114                 var.store %2 %20;
115                 %21 : int = add %17 %20;
116                 return %21;
117             };
118             """)
119     int test4(int i) {
120         return (i += 1) + (i *= 1) + (i /= 1) + (i -= 1) + (i %= 1);
121     }
122 
123     @CodeReflection
124     @IR("""
125             func @"test5" (%0 : BinopTest, %1 : int)boolean -> {
126                 %2 : Var<int> = var %1 @"i";
127                 %3 : int = var.load %2;
128                 %4 : int = constant @"0";
129                 %5 : boolean = eq %3 %4;
130                 %6 : boolean = not %5;
131                 return %6;
132             };
133             """)
134     boolean test5(int i) {
135         return !(i == 0);
136     }
137 
138     @CodeReflection
139     @IR("""
140             func @"test6" (%0 : BinopTest)int -> {
141                 %1 : int = constant @"5";
142                 %2 : int = constant @"2";
143                 %3 : int = mod %1 %2;
144                 return %3;
145             };
146             """)
147     int test6() {
148         return 5 % 2;
149     }
150 
151     @CodeReflection
152     @IR("""
153             func @"test7" (%0 : BinopTest, %1 : double)void -> {
154                 %2 : Var<double> = var %1 @"d";
155                 %3 : double = var.load %2;
156                 %4 : int = constant @"1";
157                 %5 : double = conv %4;
158                 %6 : double = add %3 %5;
159                 var.store %2 %6;
160                 %7 : long = constant @"1";
161                 %8 : double = conv %7;
162                 %9 : double = var.load %2;
163                 %10 : double = add %8 %9;
164                 var.store %2 %10;
165                 %11 : double = var.load %2;
166                 %12 : long = constant @"1";
167                 %13 : double = conv %12;
168                 %14 : double = sub %11 %13;
169                 var.store %2 %14;
170                 %15 : int = constant @"1";
171                 %16 : double = conv %15;
172                 %17 : double = var.load %2;
173                 %18 : double = sub %16 %17;
174                 var.store %2 %18;
175                 %19 : double = var.load %2;
176                 %20 : int = constant @"1";
177                 %21 : double = conv %20;
178                 %22 : double = mul %19 %21;
179                 var.store %2 %22;
180                 %23 : long = constant @"1";
181                 %24 : double = conv %23;
182                 %25 : double = var.load %2;
183                 %26 : double = mul %24 %25;
184                 var.store %2 %26;
185                 %27 : double = var.load %2;
186                 %28 : long = constant @"1";
187                 %29 : double = conv %28;
188                 %30 : double = div %27 %29;
189                 var.store %2 %30;
190                 %31 : int = constant @"1";
191                 %32 : double = conv %31;
192                 %33 : double = var.load %2;
193                 %34 : double = div %32 %33;
194                 var.store %2 %34;
195                 %35 : double = var.load %2;
196                 %36 : int = constant @"1";
197                 %37 : double = conv %36;
198                 %38 : double = mod %35 %37;
199                 var.store %2 %38;
200                 %39 : long = constant @"1";
201                 %40 : double = conv %39;
202                 %41 : double = var.load %2;
203                 %42 : double = mod %40 %41;
204                 var.store %2 %42;
205                 %43 : int = constant @"-1";
206                 %44 : double = conv %43;
207                 var.store %2 %44;
208                 return;
209             };
210             """)
211     void test7(double d) {
212         d = d + 1;
213         d = 1L + d;
214 
215         d = d - 1L;
216         d = 1 - d;
217 
218         d = d * 1;
219         d = 1L * d;
220 
221         d = d / 1L;
222         d = 1 / d;
223 
224         d = d % 1;
225         d = 1L % d;
226 
227         d = -1;
228     }
229 
230     @CodeReflection
231     @IR("""
232             func @"test8" (%0 : BinopTest, %1 : double)void -> {
233                 %2 : Var<double> = var %1 @"d";
234                 %3 : double = var.load %2;
235                 %4 : int = constant @"1";
236                 %5 : double = conv %4;
237                 %6 : double = add %3 %5;
238                 var.store %2 %6;
239                 %7 : double = var.load %2;
240                 %8 : long = constant @"1";
241                 %9 : double = conv %8;
242                 %10 : double = sub %7 %9;
243                 var.store %2 %10;
244                 %11 : double = var.load %2;
245                 %12 : int = constant @"1";
246                 %13 : double = conv %12;
247                 %14 : double = mul %11 %13;
248                 var.store %2 %14;
249                 %15 : double = var.load %2;
250                 %16 : long = constant @"1";
251                 %17 : double = conv %16;
252                 %18 : double = div %15 %17;
253                 var.store %2 %18;
254                 %19 : double = var.load %2;
255                 %20 : int = constant @"1";
256                 %21 : double = conv %20;
257                 %22 : double = mod %19 %21;
258                 var.store %2 %22;
259                 return;
260             };
261             """)
262     void test8(double d) {
263         d += 1;
264 
265         d -= 1L;
266 
267         d *= 1;
268 
269         d /= 1L;
270 
271         d %= 1;
272     }
273 
274     @CodeReflection
275     @IR("""
276             func @"test9" (%0 : BinopTest, %1 : byte, %2 : byte, %3 : short)void -> {
277                 %4 : Var<byte> = var %1 @"a";
278                 %5 : Var<byte> = var %2 @"b";
279                 %6 : Var<short> = var %3 @"s";
280                 %7 : byte = var.load %4;
281                 %8 : byte = var.load %5;
282                 %9 : byte = add %7 %8;
283                 var.store %4 %9;
284                 %10 : byte = var.load %4;
285                 %11 : short = var.load %6;
286                 %12 : byte = conv %11;
287                 %13 : byte = div %10 %12;
288                 var.store %4 %13;
289                 %14 : byte = var.load %4;
290                 %15 : double = constant @"3.5";
291                 %16 : byte = conv %15;
292                 %17 : byte = mul %14 %16;
293                 var.store %4 %17;
294                 %18 : byte = var.load %4;
295                 %19 : byte = var.load %5;
296                 %20 : byte = lshl %18 %19;
297                 var.store %4 %20;
298                 %21 : byte = var.load %4;
299                 %22 : int = constant @"1";
300                 %23 : byte = conv %22;
301                 %24 : byte = ashr %21 %23;
302                 var.store %4 %24;
303                 %25 : byte = var.load %4;
304                 %26 : long = constant @"1";
305                 %27 : byte = conv %26;
306                 %28 : byte = ashr %25 %27;
307                 var.store %4 %28;
308                 return;
309             };
310             """)
311     void test9(byte a, byte b, short s) {
312         a += b;
313 
314         a /= s;
315 
316         a *= 3.5d;
317 
318         a <<= b;
319 
320         a >>= 1;
321 
322         a >>= 1L;
323     }
324 }