diff options
Diffstat (limited to 'llvm/test/CodeGen/PowerPC')
-rw-r--r-- | llvm/test/CodeGen/PowerPC/ppc64-P9-mod.ll | 263 |
1 files changed, 263 insertions, 0 deletions
diff --git a/llvm/test/CodeGen/PowerPC/ppc64-P9-mod.ll b/llvm/test/CodeGen/PowerPC/ppc64-P9-mod.ll new file mode 100644 index 00000000000..46e347becbb --- /dev/null +++ b/llvm/test/CodeGen/PowerPC/ppc64-P9-mod.ll @@ -0,0 +1,263 @@ +; RUN: llc < %s -mtriple=powerpc64le-unknown-linux-gnu -mcpu=pwr9 -verify-machineinstrs | FileCheck %s +; RUN: llc < %s -mtriple=powerpc64-unknown-linux-gnu -mcpu=pwr9 -verify-machineinstrs | FileCheck %s +; RUN: llc < %s -mtriple=powerpc64le-unknown-linux-gnu -mcpu=pwr8 | FileCheck %s -check-prefix=CHECK-PWR8 -implicit-check-not mod[us][wd] + +@mod_resultsw = common local_unnamed_addr global i32 0, align 4 +@mod_resultud = common local_unnamed_addr global i64 0, align 8 +@div_resultsw = common local_unnamed_addr global i32 0, align 4 +@mod_resultuw = common local_unnamed_addr global i32 0, align 4 +@div_resultuw = common local_unnamed_addr global i32 0, align 4 +@div_resultsd = common local_unnamed_addr global i64 0, align 8 +@mod_resultsd = common local_unnamed_addr global i64 0, align 8 +@div_resultud = common local_unnamed_addr global i64 0, align 8 + +; Function Attrs: norecurse nounwind +define void @modulo_sw(i32 signext %a, i32 signext %b) local_unnamed_addr { +entry: + %rem = srem i32 %a, %b + store i32 %rem, i32* @mod_resultsw, align 4 + ret void +; CHECK-LABEL: modulo_sw +; CHECK: modsw {{[0-9]+}}, 3, 4 +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_sw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind readnone +define zeroext i32 @modulo_uw(i32 zeroext %a, i32 zeroext %b) local_unnamed_addr { +entry: + %rem = urem i32 %a, %b + ret i32 %rem +; CHECK-LABEL: modulo_uw +; CHECK: moduw {{[0-9]+}}, 3, 4 +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_uw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind readnone +define i64 @modulo_sd(i64 %a, i64 %b) local_unnamed_addr { +entry: + %rem = srem i64 %a, %b + ret i64 %rem +; CHECK-LABEL: modulo_sd +; CHECK: modsd {{[0-9]+}}, 3, 4 +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_sd +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +define void @modulo_ud(i64 %a, i64 %b) local_unnamed_addr { +entry: + %rem = urem i64 %a, %b + store i64 %rem, i64* @mod_resultud, align 8 + ret void +; CHECK-LABEL: modulo_ud +; CHECK: modud {{[0-9]+}}, 3, 4 +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_ud +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +define void @modulo_div_sw(i32 signext %a, i32 signext %b) local_unnamed_addr { +entry: + %rem = srem i32 %a, %b + store i32 %rem, i32* @mod_resultsw, align 4 + %div = sdiv i32 %a, %b + store i32 %div, i32* @div_resultsw, align 4 + ret void +; CHECK-LABEL: modulo_div_sw +; CHECK-NOT: modsw +; CHECK: div +; CHECK-NOT: modsw +; CHECK: mull +; CHECK-NOT: modsw +; CHECK: sub +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_div_sw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +define void @modulo_div_abc_sw(i32 signext %a, i32 signext %b, i32 signext %c) local_unnamed_addr { +entry: + %rem = srem i32 %a, %c + store i32 %rem, i32* @mod_resultsw, align 4 + %div = sdiv i32 %b, %c + store i32 %div, i32* @div_resultsw, align 4 + ret void +; CHECK-LABEL: modulo_div_abc_sw +; CHECK: modsw {{[0-9]+}}, 3, 5 +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_div_abc_sw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +define void @modulo_div_uw(i32 zeroext %a, i32 zeroext %b) local_unnamed_addr { +entry: + %rem = urem i32 %a, %b + store i32 %rem, i32* @mod_resultuw, align 4 + %div = udiv i32 %a, %b + store i32 %div, i32* @div_resultuw, align 4 + ret void +; CHECK-LABEL: modulo_div_uw +; CHECK-NOT: modsw +; CHECK: div +; CHECK-NOT: modsw +; CHECK: mull +; CHECK-NOT: modsw +; CHECK: sub +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_div_uw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +define void @modulo_div_swuw(i32 signext %a, i32 signext %b) local_unnamed_addr { +entry: + %rem = srem i32 %a, %b + store i32 %rem, i32* @mod_resultsw, align 4 + %div = udiv i32 %a, %b + store i32 %div, i32* @div_resultsw, align 4 + ret void +; CHECK-LABEL: modulo_div_swuw +; CHECK: modsw {{[0-9]+}}, 3, 4 +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_div_swuw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +define void @modulo_div_udsd(i64 %a, i64 %b) local_unnamed_addr { +entry: + %rem = urem i64 %a, %b + store i64 %rem, i64* @mod_resultud, align 8 + %div = sdiv i64 %a, %b + store i64 %div, i64* @div_resultsd, align 8 + ret void +; CHECK-LABEL: modulo_div_udsd +; CHECK: modud {{[0-9]+}}, 3, 4 +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_div_udsd +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +define void @modulo_const32_sw(i32 signext %a) local_unnamed_addr { +entry: + %rem = srem i32 %a, 32 + store i32 %rem, i32* @mod_resultsw, align 4 + ret void +; CHECK-LABEL: modulo_const32_sw +; CHECK-NOT: modsw +; CHECK: srawi +; CHECK-NOT: modsw +; CHECK: addze +; CHECK-NOT: modsw +; CHECK: slwi +; CHECK-NOT: modsw +; CHECK: subf +; CHECK-NOT: modsw +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_const32_sw +; CHECK-PWR8: srawi +; CHECK-PWR8: addze +; CHECK-PWR8: slwi +; CHECK-PWR8: subf +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind readnone +define signext i32 @modulo_const3_sw(i32 signext %a) local_unnamed_addr { +entry: + %rem = srem i32 %a, 3 + ret i32 %rem +; CHECK-LABEL: modulo_const3_sw +; CHECK-NOT: modsw +; CHECK: mull +; CHECK-NOT: modsw +; CHECK: sub +; CHECK-NOT: modsw +; CHECK: blr +; CHECK-PWR8-LABEL: modulo_const3_sw +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind readnone +define signext i32 @const2_modulo_sw(i32 signext %a) local_unnamed_addr { +entry: + %rem = srem i32 2, %a + ret i32 %rem +; CHECK-LABEL: const2_modulo_sw +; CHECK: modsw {{[0-9]+}}, {{[0-9]+}}, 3 +; CHECK: blr +; CHECK-PWR8-LABEL: const2_modulo_sw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + +; Function Attrs: norecurse nounwind +; FIXME On power 9 this test will still produce modsw because the divide is in +; a different block than the remainder. Due to the nature of the SDAG we cannot +; see the div in the other block. +define void @blocks_modulo_div_sw(i32 signext %a, i32 signext %b, i32 signext %c) local_unnamed_addr { +entry: + %div = sdiv i32 %a, %b + store i32 %div, i32* @div_resultsw, align 4 + %cmp = icmp sgt i32 %c, 0 + br i1 %cmp, label %if.then, label %if.end + +if.then: ; preds = %entry + %rem = srem i32 %a, %b + store i32 %rem, i32* @mod_resultsw, align 4 + br label %if.end + +if.end: ; preds = %if.then, %entry + ret void +; CHECK-LABEL: blocks_modulo_div_sw +; CHECK: div +; CHECK: modsw {{[0-9]+}}, 3, 4 +; CHECK: blr +; CHECK-PWR8-LABEL: blocks_modulo_div_sw +; CHECK-PWR8: div +; CHECK-PWR8: mull +; CHECK-PWR8: sub +; CHECK-PWR8: blr +} + + |