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 import jdk.incubator.code.CodeReflection; 25 import java.util.function.Supplier; 26 27 28 /* 29 * @test 30 * @summary Smoke test for code reflection with null constants. 31 * @modules jdk.incubator.code 32 * @enablePreview 33 * @build NullTest 34 * @build CodeReflectionTester 35 * @run main CodeReflectionTester NullTest 36 */ 37 38 public class NullTest { 39 40 @CodeReflection 41 @IR(""" 42 func @"test1" (%0 : NullTest)void -> { 43 %1 : java.lang.String = constant @null; 44 %2 : Var<java.lang.String> = var %1 @"s"; 45 return; 46 }; 47 """) 48 void test1() { 49 String s = null; 50 } 51 52 @CodeReflection 53 @IR(""" 54 func @"test2" (%0 : NullTest)void -> { 55 %1 : java.lang.Object = constant @null; 56 %2 : java.lang.String = cast %1 @"java.lang.String"; 57 %3 : Var<java.lang.String> = var %2 @"s"; 58 return; 59 }; 60 """) 61 void test2() { 62 String s = (String)null; 63 } 64 65 @CodeReflection 66 @IR(""" 67 func @"test3" (%0 : NullTest, %1 : boolean)java.lang.String -> { 68 %2 : Var<boolean> = var %1 @"cond"; 69 %3 : java.lang.String = java.cexpression 70 ^cond()boolean -> { 71 %4 : boolean = var.load %2; 72 yield %4; 73 } 74 ^truepart()java.lang.String -> { 75 %5 : java.lang.String = constant @null; 76 yield %5; 77 } 78 ^falsepart()java.lang.String -> { 79 %6 : java.lang.String = constant @""; 80 yield %6; 81 }; 82 return %3; 83 }; 84 """) 85 String test3(boolean cond) { 86 return cond ? null : ""; 87 } 88 89 @CodeReflection 90 @IR(""" 91 func @"test4" (%0 : NullTest, %1 : boolean)java.lang.String -> { 92 %2 : Var<boolean> = var %1 @"cond"; 93 %3 : java.lang.String = java.cexpression 94 ^cond()boolean -> { 95 %4 : boolean = var.load %2; 96 yield %4; 97 } 98 ^truepart()java.lang.String -> { 99 %5 : java.lang.String = constant @""; 100 yield %5; 101 } 102 ^falsepart()java.lang.String -> { 103 %6 : java.lang.String = constant @null; 104 yield %6; 105 }; 106 return %3; 107 }; 108 """) 109 String test4(boolean cond) { 110 return cond ? "" : null; 111 } 112 113 @CodeReflection 114 @IR(""" 115 func @"test5" (%0 : NullTest, %1 : boolean)java.lang.String -> { 116 %2 : Var<boolean> = var %1 @"cond"; 117 %3 : java.lang.String = java.cexpression 118 ^cond()boolean -> { 119 %4 : boolean = var.load %2; 120 yield %4; 121 } 122 ^truepart()java.lang.String -> { 123 %5 : java.lang.String = constant @null; 124 yield %5; 125 } 126 ^falsepart()java.lang.String -> { 127 %6 : java.lang.String = constant @null; 128 yield %6; 129 }; 130 return %3; 131 }; 132 """) 133 String test5(boolean cond) { 134 return cond ? null : null; 135 } 136 137 @CodeReflection 138 @IR(""" 139 func @"test6" (%0 : NullTest, %1 : boolean)java.lang.String -> { 140 %2 : Var<boolean> = var %1 @"cond"; 141 %3 : java.lang.Object = java.cexpression 142 ^cond()boolean -> { 143 %4 : boolean = var.load %2; 144 yield %4; 145 } 146 ^truepart()java.lang.Object -> { 147 %5 : java.lang.Object = constant @null; 148 yield %5; 149 } 150 ^falsepart()java.lang.Object -> { 151 %6 : java.lang.Object = constant @null; 152 yield %6; 153 }; 154 %7 : java.lang.String = cast %3 @"java.lang.String"; 155 return %7; 156 }; 157 """) 158 String test6(boolean cond) { 159 return (String)(cond ? null : null); 160 } 161 162 @CodeReflection 163 @IR(""" 164 func @"test7" (%0 : NullTest, %1 : int)java.lang.String -> { 165 %2 : Var<int> = var %1 @"cond"; 166 %3 : int = var.load %2; 167 %4 : java.lang.String = java.switch.expression %3 168 ^constantCaseLabel(%5 : int)boolean -> { 169 %6 : int = constant @"1"; 170 %7 : boolean = eq %5 %6; 171 yield %7; 172 } 173 ()java.lang.String -> { 174 %8 : java.lang.String = constant @""; 175 yield %8; 176 } 177 ^defaultCaseLabel()boolean -> { 178 %9 : boolean = constant @"true"; 179 yield %9; 180 } 181 ()java.lang.String -> { 182 %9 : java.lang.String = constant @null; 183 yield %9; 184 }; 185 return %4; 186 }; 187 """) 188 String test7(int cond) { 189 return switch(cond) { 190 case 1 -> ""; 191 default -> null; 192 }; 193 } 194 195 @CodeReflection 196 @IR(""" 197 func @"test8" (%0 : NullTest, %1 : int)java.lang.String -> { 198 %2 : Var<int> = var %1 @"cond"; 199 %3 : int = var.load %2; 200 %4 : java.lang.String = java.switch.expression %3 201 ^constantCaseLabel(%5 : int)boolean -> { 202 %6 : int = constant @"1"; 203 %7 : boolean = eq %5 %6; 204 yield %7; 205 } 206 ()java.lang.String -> { 207 %8 : java.lang.String = constant @null; 208 yield %8; 209 } 210 ^defaultCaseLabel()boolean -> { 211 %9 : boolean = constant @"true"; 212 yield %9; 213 } 214 ()java.lang.String -> { 215 %9 : java.lang.String = constant @""; 216 yield %9; 217 }; 218 return %4; 219 }; 220 """) 221 String test8(int cond) { 222 return switch(cond) { 223 case 1 -> null; 224 default -> ""; 225 }; 226 } 227 228 @CodeReflection 229 @IR(""" 230 func @"test9" (%0 : NullTest, %1 : int)java.lang.String -> { 231 %2 : Var<int> = var %1 @"cond"; 232 %3 : int = var.load %2; 233 %4 : java.lang.String = java.switch.expression %3 234 ^constantCaseLabel(%5 : int)boolean -> { 235 %6 : int = constant @"1"; 236 %7 : boolean = eq %5 %6; 237 yield %7; 238 } 239 ()java.lang.String -> { 240 %8 : java.lang.String = constant @null; 241 yield %8; 242 } 243 ^defaultCaseLabel()boolean -> { 244 %9 : boolean = constant @"true"; 245 yield %9; 246 } 247 ()java.lang.String -> { 248 %9 : java.lang.String = constant @null; 249 yield %9; 250 }; 251 return %4; 252 }; 253 """) 254 String test9(int cond) { 255 return switch(cond) { 256 case 1 -> null; 257 default -> null; 258 }; 259 } 260 261 @CodeReflection 262 @IR(""" 263 func @"test10" (%0 : NullTest, %1 : int)java.lang.String -> { 264 %2 : Var<int> = var %1 @"cond"; 265 %3 : int = var.load %2; 266 %4 : java.lang.Object = java.switch.expression %3 267 ^constantCaseLabel(%5 : int)boolean -> { 268 %6 : int = constant @"1"; 269 %7 : boolean = eq %5 %6; 270 yield %7; 271 } 272 ()java.lang.Object -> { 273 %8 : java.lang.Object = constant @null; 274 yield %8; 275 } 276 ^defaultCaseLabel()boolean -> { 277 %9 : boolean = constant @"true"; 278 yield %9; 279 } 280 ()java.lang.Object -> { 281 %9 : java.lang.Object = constant @null; 282 yield %9; 283 }; 284 %10 : java.lang.String = cast %4 @"java.lang.String"; 285 return %10; 286 }; 287 """) 288 String test10(int cond) { 289 return (String)switch(cond) { 290 case 1 -> null; 291 default -> null; 292 }; 293 } 294 295 @CodeReflection 296 @IR(""" 297 func @"test11" (%0 : NullTest, %1 : int)java.lang.String -> { 298 %2 : Var<int> = var %1 @"cond"; 299 %3 : int = var.load %2; 300 %4 : java.lang.String = java.switch.expression %3 301 ^constantCaseLabel(%5 : int)boolean -> { 302 %6 : int = constant @"1"; 303 %7 : boolean = eq %5 %6; 304 yield %7; 305 } 306 ()java.lang.String -> { 307 %8 : java.lang.String = constant @""; 308 java.yield %8; 309 } 310 ^defaultCaseLabel()boolean -> { 311 %9 : boolean = constant @"true"; 312 yield %9; 313 } 314 ()java.lang.String -> { 315 %9 : java.lang.String = constant @null; 316 java.yield %9; 317 }; 318 return %4; 319 }; 320 """) 321 String test11(int cond) { 322 return switch(cond) { 323 case 1 -> { yield ""; } 324 default -> { yield null; } 325 }; 326 } 327 328 @CodeReflection 329 @IR(""" 330 func @"test12" (%0 : NullTest, %1 : int)java.lang.String -> { 331 %2 : Var<int> = var %1 @"cond"; 332 %3 : int = var.load %2; 333 %4 : java.lang.String = java.switch.expression %3 334 ^constantCaseLabel(%5 : int)boolean -> { 335 %6 : int = constant @"1"; 336 %7 : boolean = eq %5 %6; 337 yield %7; 338 } 339 ()java.lang.String -> { 340 %8 : java.lang.String = constant @null; 341 java.yield %8; 342 } 343 ^defaultCaseLabel()boolean -> { 344 %9 : boolean = constant @"true"; 345 yield %9; 346 } 347 ()java.lang.String -> { 348 %9 : java.lang.String = constant @""; 349 java.yield %9; 350 }; 351 return %4; 352 }; 353 """) 354 String test12(int cond) { 355 return switch(cond) { 356 case 1 -> { yield null; } 357 default -> { yield ""; } 358 }; 359 } 360 361 @CodeReflection 362 @IR(""" 363 func @"test13" (%0 : NullTest, %1 : int)java.lang.String -> { 364 %2 : Var<int> = var %1 @"cond"; 365 %3 : int = var.load %2; 366 %4 : java.lang.String = java.switch.expression %3 367 ^constantCaseLabel(%5 : int)boolean -> { 368 %6 : int = constant @"1"; 369 %7 : boolean = eq %5 %6; 370 yield %7; 371 } 372 ()java.lang.String -> { 373 %8 : java.lang.String = constant @null; 374 java.yield %8; 375 } 376 ^defaultCaseLabel()boolean -> { 377 %9 : boolean = constant @"true"; 378 yield %9; 379 } 380 ()java.lang.String -> { 381 %9 : java.lang.String = constant @null; 382 java.yield %9; 383 }; 384 return %4; 385 }; 386 """) 387 String test13(int cond) { 388 return switch(cond) { 389 case 1 -> { yield null; } 390 default -> { yield null; } 391 }; 392 } 393 394 @CodeReflection 395 @IR(""" 396 func @"test14" (%0 : NullTest, %1 : int)java.lang.String -> { 397 %2 : Var<int> = var %1 @"cond"; 398 %3 : int = var.load %2; 399 %4 : java.lang.Object = java.switch.expression %3 400 ^constantCaseLabel(%5 : int)boolean -> { 401 %6 : int = constant @"1"; 402 %7 : boolean = eq %5 %6; 403 yield %7; 404 } 405 ()java.lang.Object -> { 406 %8 : java.lang.Object = constant @null; 407 java.yield %8; 408 } 409 ^defaultCaseLabel()boolean -> { 410 %9 : boolean = constant @"true"; 411 yield %9; 412 } 413 ()java.lang.Object -> { 414 %9 : java.lang.Object = constant @null; 415 java.yield %9; 416 }; 417 %10 : java.lang.String = cast %4 @"java.lang.String"; 418 return %10; 419 }; 420 """) 421 String test14(int cond) { 422 return (String)switch(cond) { 423 case 1 -> { yield null; } 424 default -> { yield null; } 425 }; 426 } 427 428 @CodeReflection 429 @IR(""" 430 func @"test15" (%0 : NullTest)java.util.function.Supplier<java.lang.String> -> { 431 %1 : java.util.function.Supplier<java.lang.String> = lambda ()java.lang.String -> { 432 %2 : java.lang.String = constant @null; 433 return %2; 434 }; 435 return %1; 436 }; 437 """) 438 Supplier<String> test15() { 439 return () -> null; 440 } 441 442 static void m(String s, String... ss) { } 443 444 @CodeReflection 445 @IR(""" 446 func @"test16" (%0 : NullTest)void -> { 447 %1 : java.lang.String = constant @null; 448 invoke %1 @invoke.kind="STATIC" @invoke.varargs="true" @"NullTest::m(java.lang.String, java.lang.String[])void"; 449 return; 450 }; 451 """) 452 void test16() { 453 m(null); 454 } 455 456 @CodeReflection 457 @IR(""" 458 func @"test17" (%0 : NullTest)void -> { 459 %1 : java.lang.String = constant @null; 460 %2 : java.lang.String[] = constant @null; 461 invoke %1 %2 @invoke.kind="STATIC" @invoke.varargs="false" @"NullTest::m(java.lang.String, java.lang.String[])void"; 462 return; 463 }; 464 """) 465 void test17() { 466 m(null, null); 467 } 468 469 @CodeReflection 470 @IR(""" 471 func @"test18" (%0 : NullTest)void -> { 472 %1 : java.lang.String = constant @null; 473 %2 : java.lang.String = constant @null; 474 %3 : java.lang.String = constant @null; 475 invoke %1 %2 %3 @invoke.kind="STATIC" @invoke.varargs="true" @"NullTest::m(java.lang.String, java.lang.String[])void"; 476 return; 477 }; 478 """) 479 void test18() { 480 m(null, null, null); 481 } 482 483 static class Box { 484 Box(String s, String... ss) { } 485 } 486 487 @CodeReflection 488 @IR(""" 489 func @"test19" (%0 : NullTest)void -> { 490 %1 : java.lang.String = constant @null; 491 %2 : NullTest$Box = new %1 @"func<NullTest$Box, java.lang.String, java.lang.String[]>"; 492 return; 493 }; 494 """) 495 void test19() { 496 new Box(null); 497 } 498 499 @CodeReflection 500 @IR(""" 501 func @"test20" (%0 : NullTest)void -> { 502 %1 : java.lang.String = constant @null; 503 %2 : java.lang.String[] = constant @null; 504 %3 : NullTest$Box = new %1 %2 @"func<NullTest$Box, java.lang.String, java.lang.String[]>"; 505 return; 506 }; 507 """) 508 void test20() { 509 new Box(null, null); 510 } 511 512 @CodeReflection 513 @IR(""" 514 func @"test21" (%0 : NullTest)void -> { 515 %1 : java.lang.String = constant @null; 516 %2 : java.lang.String = constant @null; 517 %3 : java.lang.String = constant @null; 518 %4 : NullTest$Box = new %1 %2 %3 @"func<NullTest$Box, java.lang.String, java.lang.String[]>"; 519 return; 520 }; 521 """) 522 void test21() { 523 new Box(null, null, null); 524 } 525 }