1; Test the use of TEST UNDER MASK for 32-bit operations. 2; 3; RUN: llc < %s -mtriple=s390x-linux-gnu -mcpu=z196 | FileCheck %s 4 5@g = global i32 0 6 7; Check the lowest useful TMLL value. 8define void @f1(i32 %a) { 9; CHECK-LABEL: f1: 10; CHECK: tmll %r2, 1 11; CHECK: ber %r14 12; CHECK: br %r14 13entry: 14 %and = and i32 %a, 1 15 %cmp = icmp eq i32 %and, 0 16 br i1 %cmp, label %exit, label %store 17 18store: 19 store i32 1, i32 *@g 20 br label %exit 21 22exit: 23 ret void 24} 25 26; Check the high end of the TMLL range. 27define void @f2(i32 %a) { 28; CHECK-LABEL: f2: 29; CHECK: tmll %r2, 65535 30; CHECK: bner %r14 31; CHECK: br %r14 32entry: 33 %and = and i32 %a, 65535 34 %cmp = icmp ne i32 %and, 0 35 br i1 %cmp, label %exit, label %store 36 37store: 38 store i32 1, i32 *@g 39 br label %exit 40 41exit: 42 ret void 43} 44 45; Check the lowest useful TMLH value, which is the next value up. 46define void @f3(i32 %a) { 47; CHECK-LABEL: f3: 48; CHECK: tmlh %r2, 1 49; CHECK: bner %r14 50; CHECK: br %r14 51entry: 52 %and = and i32 %a, 65536 53 %cmp = icmp ne i32 %and, 0 54 br i1 %cmp, label %exit, label %store 55 56store: 57 store i32 1, i32 *@g 58 br label %exit 59 60exit: 61 ret void 62} 63 64; Check the next value up again, which cannot use TM. 65define void @f4(i32 %a) { 66; CHECK-LABEL: f4: 67; CHECK-NOT: {{tm[lh].}} 68; CHECK: br %r14 69entry: 70 %and = and i32 %a, 4294901759 71 %cmp = icmp eq i32 %and, 0 72 br i1 %cmp, label %exit, label %store 73 74store: 75 store i32 1, i32 *@g 76 br label %exit 77 78exit: 79 ret void 80} 81 82; Check the high end of the TMLH range. 83define void @f5(i32 %a) { 84; CHECK-LABEL: f5: 85; CHECK: tmlh %r2, 65535 86; CHECK: ber %r14 87; CHECK: br %r14 88entry: 89 %and = and i32 %a, 4294901760 90 %cmp = icmp eq i32 %and, 0 91 br i1 %cmp, label %exit, label %store 92 93store: 94 store i32 1, i32 *@g 95 br label %exit 96 97exit: 98 ret void 99} 100 101; Check that we can use TMLL for LT comparisons that are equivalent to 102; an equality comparison with zero. 103define void @f6(i32 %a) { 104; CHECK-LABEL: f6: 105; CHECK: tmll %r2, 240 106; CHECK: ber %r14 107; CHECK: br %r14 108entry: 109 %and = and i32 %a, 240 110 %cmp = icmp slt i32 %and, 16 111 br i1 %cmp, label %exit, label %store 112 113store: 114 store i32 1, i32 *@g 115 br label %exit 116 117exit: 118 ret void 119} 120 121; ...same again with LE. 122define void @f7(i32 %a) { 123; CHECK-LABEL: f7: 124; CHECK: tmll %r2, 240 125; CHECK: ber %r14 126; CHECK: br %r14 127entry: 128 %and = and i32 %a, 240 129 %cmp = icmp sle i32 %and, 15 130 br i1 %cmp, label %exit, label %store 131 132store: 133 store i32 1, i32 *@g 134 br label %exit 135 136exit: 137 ret void 138} 139 140; Check that we can use TMLL for GE comparisons that are equivalent to 141; an inequality comparison with zero. 142define void @f8(i32 %a) { 143; CHECK-LABEL: f8: 144; CHECK: tmll %r2, 240 145; CHECK: bner %r14 146; CHECK: br %r14 147entry: 148 %and = and i32 %a, 240 149 %cmp = icmp uge i32 %and, 16 150 br i1 %cmp, label %exit, label %store 151 152store: 153 store i32 1, i32 *@g 154 br label %exit 155 156exit: 157 ret void 158} 159 160; ...same again with GT. 161define void @f9(i32 %a) { 162; CHECK-LABEL: f9: 163; CHECK: tmll %r2, 240 164; CHECK: bner %r14 165; CHECK: br %r14 166entry: 167 %and = and i32 %a, 240 168 %cmp = icmp ugt i32 %and, 15 169 br i1 %cmp, label %exit, label %store 170 171store: 172 store i32 1, i32 *@g 173 br label %exit 174 175exit: 176 ret void 177} 178 179; Check that we can use TMLL for LT comparisons that effectively 180; test whether the top bit is clear. 181define void @f10(i32 %a) { 182; CHECK-LABEL: f10: 183; CHECK: tmll %r2, 35 184; CHECK: bler %r14 185; CHECK: br %r14 186entry: 187 %and = and i32 %a, 35 188 %cmp = icmp ult i32 %and, 8 189 br i1 %cmp, label %exit, label %store 190 191store: 192 store i32 1, i32 *@g 193 br label %exit 194 195exit: 196 ret void 197} 198 199; ...same again with LE. 200define void @f11(i32 %a) { 201; CHECK-LABEL: f11: 202; CHECK: tmll %r2, 35 203; CHECK: bler %r14 204; CHECK: br %r14 205entry: 206 %and = and i32 %a, 35 207 %cmp = icmp ule i32 %and, 31 208 br i1 %cmp, label %exit, label %store 209 210store: 211 store i32 1, i32 *@g 212 br label %exit 213 214exit: 215 ret void 216} 217 218; Check that we can use TMLL for GE comparisons that effectively test 219; whether the top bit is set. 220define void @f12(i32 %a) { 221; CHECK-LABEL: f12: 222; CHECK: tmll %r2, 140 223; CHECK: bnler %r14 224; CHECK: br %r14 225entry: 226 %and = and i32 %a, 140 227 %cmp = icmp uge i32 %and, 128 228 br i1 %cmp, label %exit, label %store 229 230store: 231 store i32 1, i32 *@g 232 br label %exit 233 234exit: 235 ret void 236} 237 238; ...same again for GT. 239define void @f13(i32 %a) { 240; CHECK-LABEL: f13: 241; CHECK: tmll %r2, 140 242; CHECK: bnler %r14 243; CHECK: br %r14 244entry: 245 %and = and i32 %a, 140 246 %cmp = icmp ugt i32 %and, 126 247 br i1 %cmp, label %exit, label %store 248 249store: 250 store i32 1, i32 *@g 251 br label %exit 252 253exit: 254 ret void 255} 256 257; Check that we can use TMLL for equality comparisons with the mask. 258define void @f14(i32 %a) { 259; CHECK-LABEL: f14: 260; CHECK: tmll %r2, 101 261; CHECK: bor %r14 262; CHECK: br %r14 263entry: 264 %and = and i32 %a, 101 265 %cmp = icmp eq i32 %and, 101 266 br i1 %cmp, label %exit, label %store 267 268store: 269 store i32 1, i32 *@g 270 br label %exit 271 272exit: 273 ret void 274} 275 276; Check that we can use TMLL for inequality comparisons with the mask. 277define void @f15(i32 %a) { 278; CHECK-LABEL: f15: 279; CHECK: tmll %r2, 65519 280; CHECK: bnor %r14 281; CHECK: br %r14 282entry: 283 %and = and i32 %a, 65519 284 %cmp = icmp ne i32 %and, 65519 285 br i1 %cmp, label %exit, label %store 286 287store: 288 store i32 1, i32 *@g 289 br label %exit 290 291exit: 292 ret void 293} 294 295; Check that we can use TMLL for LT comparisons that are equivalent 296; to inequality comparisons with the mask. 297define void @f16(i32 %a) { 298; CHECK-LABEL: f16: 299; CHECK: tmll %r2, 130 300; CHECK: bnor %r14 301; CHECK: br %r14 302entry: 303 %and = and i32 %a, 130 304 %cmp = icmp ult i32 %and, 129 305 br i1 %cmp, label %exit, label %store 306 307store: 308 store i32 1, i32 *@g 309 br label %exit 310 311exit: 312 ret void 313} 314 315; ...same again with LE. 316define void @f17(i32 %a) { 317; CHECK-LABEL: f17: 318; CHECK: tmll %r2, 130 319; CHECK: bnor %r14 320; CHECK: br %r14 321entry: 322 %and = and i32 %a, 130 323 %cmp = icmp ule i32 %and, 128 324 br i1 %cmp, label %exit, label %store 325 326store: 327 store i32 1, i32 *@g 328 br label %exit 329 330exit: 331 ret void 332} 333 334; Check that we can use TMLL for GE comparisons that are equivalent 335; to equality comparisons with the mask. 336define void @f18(i32 %a) { 337; CHECK-LABEL: f18: 338; CHECK: tmll %r2, 194 339; CHECK: bor %r14 340; CHECK: br %r14 341entry: 342 %and = and i32 %a, 194 343 %cmp = icmp uge i32 %and, 193 344 br i1 %cmp, label %exit, label %store 345 346store: 347 store i32 1, i32 *@g 348 br label %exit 349 350exit: 351 ret void 352} 353 354; ...same again for GT. 355define void @f19(i32 %a) { 356; CHECK-LABEL: f19: 357; CHECK: tmll %r2, 194 358; CHECK: bor %r14 359; CHECK: br %r14 360entry: 361 %and = and i32 %a, 194 362 %cmp = icmp ugt i32 %and, 192 363 br i1 %cmp, label %exit, label %store 364 365store: 366 store i32 1, i32 *@g 367 br label %exit 368 369exit: 370 ret void 371} 372 373; Check that we can use TMLL for equality comparisons for the low bit 374; when the mask has two bits. 375define void @f20(i32 %a) { 376; CHECK-LABEL: f20: 377; CHECK: tmll %r2, 20 378; CHECK: blr %r14 379; CHECK: br %r14 380entry: 381 %and = and i32 %a, 20 382 %cmp = icmp eq i32 %and, 4 383 br i1 %cmp, label %exit, label %store 384 385store: 386 store i32 1, i32 *@g 387 br label %exit 388 389exit: 390 ret void 391} 392 393; Check that we can use TMLL for inequality comparisons for the low bit 394; when the mask has two bits. 395define void @f21(i32 %a) { 396; CHECK-LABEL: f21: 397; CHECK: tmll %r2, 20 398; CHECK: bnlr %r14 399; CHECK: br %r14 400entry: 401 %and = and i32 %a, 20 402 %cmp = icmp ne i32 %and, 4 403 br i1 %cmp, label %exit, label %store 404 405store: 406 store i32 1, i32 *@g 407 br label %exit 408 409exit: 410 ret void 411} 412 413; Check that we can use TMLL for equality comparisons for the high bit 414; when the mask has two bits. 415define void @f22(i32 %a) { 416; CHECK-LABEL: f22: 417; CHECK: tmll %r2, 20 418; CHECK: bhr %r14 419; CHECK: br %r14 420entry: 421 %and = and i32 %a, 20 422 %cmp = icmp eq i32 %and, 16 423 br i1 %cmp, label %exit, label %store 424 425store: 426 store i32 1, i32 *@g 427 br label %exit 428 429exit: 430 ret void 431} 432 433; Check that we can use TMLL for inequality comparisons for the high bit 434; when the mask has two bits. 435define void @f23(i32 %a) { 436; CHECK-LABEL: f23: 437; CHECK: tmll %r2, 20 438; CHECK: bnhr %r14 439; CHECK: br %r14 440entry: 441 %and = and i32 %a, 20 442 %cmp = icmp ne i32 %and, 16 443 br i1 %cmp, label %exit, label %store 444 445store: 446 store i32 1, i32 *@g 447 br label %exit 448 449exit: 450 ret void 451} 452 453; Check that we can fold an SHL into a TMxx mask. 454define void @f24(i32 %a) { 455; CHECK-LABEL: f24: 456; CHECK: tmll %r2, 255 457; CHECK: bner %r14 458; CHECK: br %r14 459entry: 460 %shl = shl i32 %a, 12 461 %and = and i32 %shl, 1044480 462 %cmp = icmp ne i32 %and, 0 463 br i1 %cmp, label %exit, label %store 464 465store: 466 store i32 1, i32 *@g 467 br label %exit 468 469exit: 470 ret void 471} 472 473; Check that we can fold an SHR into a TMxx mask. 474define void @f25(i32 %a) { 475; CHECK-LABEL: f25: 476; CHECK: tmlh %r2, 512 477; CHECK: bner %r14 478; CHECK: br %r14 479entry: 480 %shr = lshr i32 %a, 25 481 %and = and i32 %shr, 1 482 %cmp = icmp ne i32 %and, 0 483 br i1 %cmp, label %exit, label %store 484 485store: 486 store i32 1, i32 *@g 487 br label %exit 488 489exit: 490 ret void 491} 492