brintos

brintos / llvm-project-archived public Read only

0
0
Text · 10.8 KiB · ad6aa79 Raw
330 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 32; Test 64-bit addition in which the second operand is variable.3;4; RUN: llc < %s -mtriple=s390x-linux-gnu | FileCheck %s5 6declare i64 @foo()7 8; Check ALGR.9define zeroext i1 @f1(i64 %dummy, i64 %a, i64 %b, ptr %res) {10; CHECK-LABEL: f1:11; CHECK:       # %bb.0:12; CHECK-NEXT:    algr %r3, %r413; CHECK-NEXT:    ipm %r014; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 3515; CHECK-NEXT:    stg %r3, 0(%r5)16; CHECK-NEXT:    br %r1417  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)18  %val = extractvalue {i64, i1} %t, 019  %obit = extractvalue {i64, i1} %t, 120  store i64 %val, ptr %res21  ret i1 %obit22}23 24; Check using the overflow result for a branch.25define void @f2(i64 %dummy, i64 %a, i64 %b, ptr %res) {26; CHECK-LABEL: f2:27; CHECK:       # %bb.0:28; CHECK-NEXT:    algr %r3, %r429; CHECK-NEXT:    stg %r3, 0(%r5)30; CHECK-NEXT:    jgnle foo@PLT31; CHECK-NEXT:  .LBB1_1: # %exit32; CHECK-NEXT:    br %r1433  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)34  %val = extractvalue {i64, i1} %t, 035  %obit = extractvalue {i64, i1} %t, 136  store i64 %val, ptr %res37  br i1 %obit, label %call, label %exit38 39call:40  tail call i64 @foo()41  br label %exit42 43exit:44  ret void45}46 47; ... and the same with the inverted direction.48define void @f3(i64 %dummy, i64 %a, i64 %b, ptr %res) {49; CHECK-LABEL: f3:50; CHECK:       # %bb.0:51; CHECK-NEXT:    algr %r3, %r452; CHECK-NEXT:    stg %r3, 0(%r5)53; CHECK-NEXT:    jgle foo@PLT54; CHECK-NEXT:  .LBB2_1: # %exit55; CHECK-NEXT:    br %r1456  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)57  %val = extractvalue {i64, i1} %t, 058  %obit = extractvalue {i64, i1} %t, 159  store i64 %val, ptr %res60  br i1 %obit, label %exit, label %call61 62call:63  tail call i64 @foo()64  br label %exit65 66exit:67  ret void68}69 70; Check ALG with no displacement.71define zeroext i1 @f4(i64 %dummy, i64 %a, ptr %src, ptr %res) {72; CHECK-LABEL: f4:73; CHECK:       # %bb.0:74; CHECK-NEXT:    alg %r3, 0(%r4)75; CHECK-NEXT:    ipm %r076; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 3577; CHECK-NEXT:    stg %r3, 0(%r5)78; CHECK-NEXT:    br %r1479  %b = load i64, ptr %src80  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)81  %val = extractvalue {i64, i1} %t, 082  %obit = extractvalue {i64, i1} %t, 183  store i64 %val, ptr %res84  ret i1 %obit85}86 87; Check the high end of the aligned ALG range.88define zeroext i1 @f5(i64 %dummy, i64 %a, ptr %src, ptr %res) {89; CHECK-LABEL: f5:90; CHECK:       # %bb.0:91; CHECK-NEXT:    alg %r3, 524280(%r4)92; CHECK-NEXT:    ipm %r093; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 3594; CHECK-NEXT:    stg %r3, 0(%r5)95; CHECK-NEXT:    br %r1496  %ptr = getelementptr i64, ptr %src, i64 6553597  %b = load i64, ptr %ptr98  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)99  %val = extractvalue {i64, i1} %t, 0100  %obit = extractvalue {i64, i1} %t, 1101  store i64 %val, ptr %res102  ret i1 %obit103}104 105; Check the next doubleword up, which needs separate address logic.106; Other sequences besides this one would be OK.107define zeroext i1 @f6(i64 %dummy, i64 %a, ptr %src, ptr %res) {108; CHECK-LABEL: f6:109; CHECK:       # %bb.0:110; CHECK-NEXT:    agfi %r4, 524288111; CHECK-NEXT:    alg %r3, 0(%r4)112; CHECK-NEXT:    ipm %r0113; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 35114; CHECK-NEXT:    stg %r3, 0(%r5)115; CHECK-NEXT:    br %r14116  %ptr = getelementptr i64, ptr %src, i64 65536117  %b = load i64, ptr %ptr118  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)119  %val = extractvalue {i64, i1} %t, 0120  %obit = extractvalue {i64, i1} %t, 1121  store i64 %val, ptr %res122  ret i1 %obit123}124 125; Check the high end of the negative aligned ALG range.126define zeroext i1 @f7(i64 %dummy, i64 %a, ptr %src, ptr %res) {127; CHECK-LABEL: f7:128; CHECK:       # %bb.0:129; CHECK-NEXT:    alg %r3, -8(%r4)130; CHECK-NEXT:    ipm %r0131; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 35132; CHECK-NEXT:    stg %r3, 0(%r5)133; CHECK-NEXT:    br %r14134  %ptr = getelementptr i64, ptr %src, i64 -1135  %b = load i64, ptr %ptr136  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)137  %val = extractvalue {i64, i1} %t, 0138  %obit = extractvalue {i64, i1} %t, 1139  store i64 %val, ptr %res140  ret i1 %obit141}142 143; Check the low end of the ALG range.144define zeroext i1 @f8(i64 %dummy, i64 %a, ptr %src, ptr %res) {145; CHECK-LABEL: f8:146; CHECK:       # %bb.0:147; CHECK-NEXT:    alg %r3, -524288(%r4)148; CHECK-NEXT:    ipm %r0149; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 35150; CHECK-NEXT:    stg %r3, 0(%r5)151; CHECK-NEXT:    br %r14152  %ptr = getelementptr i64, ptr %src, i64 -65536153  %b = load i64, ptr %ptr154  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)155  %val = extractvalue {i64, i1} %t, 0156  %obit = extractvalue {i64, i1} %t, 1157  store i64 %val, ptr %res158  ret i1 %obit159}160 161; Check the next doubleword down, which needs separate address logic.162; Other sequences besides this one would be OK.163define zeroext i1 @f9(i64 %dummy, i64 %a, ptr %src, ptr %res) {164; CHECK-LABEL: f9:165; CHECK:       # %bb.0:166; CHECK-NEXT:    agfi %r4, -524296167; CHECK-NEXT:    alg %r3, 0(%r4)168; CHECK-NEXT:    ipm %r0169; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 35170; CHECK-NEXT:    stg %r3, 0(%r5)171; CHECK-NEXT:    br %r14172  %ptr = getelementptr i64, ptr %src, i64 -65537173  %b = load i64, ptr %ptr174  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)175  %val = extractvalue {i64, i1} %t, 0176  %obit = extractvalue {i64, i1} %t, 1177  store i64 %val, ptr %res178  ret i1 %obit179}180 181; Check that ALG allows an index.182define zeroext i1 @f10(i64 %src, i64 %index, i64 %a, ptr %res) {183; CHECK-LABEL: f10:184; CHECK:       # %bb.0:185; CHECK-NEXT:    alg %r4, 524280(%r3,%r2)186; CHECK-NEXT:    ipm %r0187; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 35188; CHECK-NEXT:    stg %r4, 0(%r5)189; CHECK-NEXT:    br %r14190  %add1 = add i64 %src, %index191  %add2 = add i64 %add1, 524280192  %ptr = inttoptr i64 %add2 to ptr193  %b = load i64, ptr %ptr194  %t = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %a, i64 %b)195  %val = extractvalue {i64, i1} %t, 0196  %obit = extractvalue {i64, i1} %t, 1197  store i64 %val, ptr %res198  ret i1 %obit199}200 201; Check that additions of spilled values can use ALG rather than ALGR.202define zeroext i1 @f11(ptr %ptr0) {203; CHECK-LABEL: f11:204; CHECK:       # %bb.0:205; CHECK-NEXT:    stmg %r6, %r15, 48(%r15)206; CHECK-NEXT:    .cfi_offset %r6, -112207; CHECK-NEXT:    .cfi_offset %r7, -104208; CHECK-NEXT:    .cfi_offset %r8, -96209; CHECK-NEXT:    .cfi_offset %r9, -88210; CHECK-NEXT:    .cfi_offset %r10, -80211; CHECK-NEXT:    .cfi_offset %r11, -72212; CHECK-NEXT:    .cfi_offset %r12, -64213; CHECK-NEXT:    .cfi_offset %r13, -56214; CHECK-NEXT:    .cfi_offset %r14, -48215; CHECK-NEXT:    .cfi_offset %r15, -40216; CHECK-NEXT:    aghi %r15, -176217; CHECK-NEXT:    .cfi_def_cfa_offset 336218; CHECK-NEXT:    lg %r7, 0(%r2)219; CHECK-NEXT:    lg %r6, 16(%r2)220; CHECK-NEXT:    lg %r13, 32(%r2)221; CHECK-NEXT:    lg %r12, 48(%r2)222; CHECK-NEXT:    lg %r8, 64(%r2)223; CHECK-NEXT:    lg %r9, 80(%r2)224; CHECK-NEXT:    lg %r10, 96(%r2)225; CHECK-NEXT:    lg %r11, 112(%r2)226; CHECK-NEXT:    mvc 160(8,%r15), 128(%r2) # 8-byte Folded Spill227; CHECK-NEXT:    mvc 168(8,%r15), 144(%r2) # 8-byte Folded Spill228; CHECK-NEXT:    brasl %r14, foo@PLT229; CHECK-NEXT:    algr %r2, %r7230; CHECK-NEXT:    ipm %r0231; CHECK-NEXT:    risbg %r0, %r0, 63, 191, 35232; CHECK-NEXT:    algr %r2, %r6233; CHECK-NEXT:    ipm %r1234; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35235; CHECK-NEXT:    algr %r2, %r13236; CHECK-NEXT:    ipm %r1237; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35238; CHECK-NEXT:    algr %r2, %r12239; CHECK-NEXT:    ipm %r1240; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35241; CHECK-NEXT:    algr %r2, %r8242; CHECK-NEXT:    ipm %r1243; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35244; CHECK-NEXT:    algr %r2, %r9245; CHECK-NEXT:    ipm %r1246; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35247; CHECK-NEXT:    algr %r2, %r10248; CHECK-NEXT:    ipm %r1249; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35250; CHECK-NEXT:    algr %r2, %r11251; CHECK-NEXT:    ipm %r1252; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35253; CHECK-NEXT:    alg %r2, 160(%r15) # 8-byte Folded Reload254; CHECK-NEXT:    ipm %r1255; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35256; CHECK-NEXT:    alg %r2, 168(%r15) # 8-byte Folded Reload257; CHECK-NEXT:    ipm %r1258; CHECK-NEXT:    rosbg %r0, %r1, 63, 63, 35259; CHECK-NEXT:    risbg %r2, %r0, 63, 191, 0260; CHECK-NEXT:    lmg %r6, %r15, 224(%r15)261; CHECK-NEXT:    br %r14262  %ptr1 = getelementptr i64, ptr %ptr0, i64 2263  %ptr2 = getelementptr i64, ptr %ptr0, i64 4264  %ptr3 = getelementptr i64, ptr %ptr0, i64 6265  %ptr4 = getelementptr i64, ptr %ptr0, i64 8266  %ptr5 = getelementptr i64, ptr %ptr0, i64 10267  %ptr6 = getelementptr i64, ptr %ptr0, i64 12268  %ptr7 = getelementptr i64, ptr %ptr0, i64 14269  %ptr8 = getelementptr i64, ptr %ptr0, i64 16270  %ptr9 = getelementptr i64, ptr %ptr0, i64 18271 272  %val0 = load i64, ptr %ptr0273  %val1 = load i64, ptr %ptr1274  %val2 = load i64, ptr %ptr2275  %val3 = load i64, ptr %ptr3276  %val4 = load i64, ptr %ptr4277  %val5 = load i64, ptr %ptr5278  %val6 = load i64, ptr %ptr6279  %val7 = load i64, ptr %ptr7280  %val8 = load i64, ptr %ptr8281  %val9 = load i64, ptr %ptr9282 283  %ret = call i64 @foo()284 285  %t0 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %ret, i64 %val0)286  %add0 = extractvalue {i64, i1} %t0, 0287  %obit0 = extractvalue {i64, i1} %t0, 1288  %t1 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add0, i64 %val1)289  %add1 = extractvalue {i64, i1} %t1, 0290  %obit1 = extractvalue {i64, i1} %t1, 1291  %res1 = or i1 %obit0, %obit1292  %t2 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add1, i64 %val2)293  %add2 = extractvalue {i64, i1} %t2, 0294  %obit2 = extractvalue {i64, i1} %t2, 1295  %res2 = or i1 %res1, %obit2296  %t3 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add2, i64 %val3)297  %add3 = extractvalue {i64, i1} %t3, 0298  %obit3 = extractvalue {i64, i1} %t3, 1299  %res3 = or i1 %res2, %obit3300  %t4 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add3, i64 %val4)301  %add4 = extractvalue {i64, i1} %t4, 0302  %obit4 = extractvalue {i64, i1} %t4, 1303  %res4 = or i1 %res3, %obit4304  %t5 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add4, i64 %val5)305  %add5 = extractvalue {i64, i1} %t5, 0306  %obit5 = extractvalue {i64, i1} %t5, 1307  %res5 = or i1 %res4, %obit5308  %t6 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add5, i64 %val6)309  %add6 = extractvalue {i64, i1} %t6, 0310  %obit6 = extractvalue {i64, i1} %t6, 1311  %res6 = or i1 %res5, %obit6312  %t7 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add6, i64 %val7)313  %add7 = extractvalue {i64, i1} %t7, 0314  %obit7 = extractvalue {i64, i1} %t7, 1315  %res7 = or i1 %res6, %obit7316  %t8 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add7, i64 %val8)317  %add8 = extractvalue {i64, i1} %t8, 0318  %obit8 = extractvalue {i64, i1} %t8, 1319  %res8 = or i1 %res7, %obit8320  %t9 = call {i64, i1} @llvm.uadd.with.overflow.i64(i64 %add8, i64 %val9)321  %add9 = extractvalue {i64, i1} %t9, 0322  %obit9 = extractvalue {i64, i1} %t9, 1323  %res9 = or i1 %res8, %obit9324 325  ret i1 %res9326}327 328declare {i64, i1} @llvm.uadd.with.overflow.i64(i64, i64) nounwind readnone329 330