diff options
author | Diana Picus <diana.picus@linaro.org> | 2016-07-18 06:48:25 +0000 |
---|---|---|
committer | Diana Picus <diana.picus@linaro.org> | 2016-07-18 06:48:25 +0000 |
commit | 774d157a5d1a2a03d7d6c724b987588b5c3bb279 (patch) | |
tree | 1c1edcffbbe6e6caa5c27805e41bbea3b42ab87b /llvm/lib/Target/ARM/ARMFastISel.cpp | |
parent | 197228927a84a15e7ca9d30ddc37113078239501 (diff) | |
download | bcm5719-llvm-774d157a5d1a2a03d7d6c724b987588b5c3bb279.tar.gz bcm5719-llvm-774d157a5d1a2a03d7d6c724b987588b5c3bb279.zip |
[ARM] Honour ABI for rem under -O0 for EABI, GNUEABI, Android and Musl
At higher optimization levels, we generate the libcall for DIVREM_Ix, which is
fine: aeabi_{u|i}divmod. At -O0 we generate the one for REM_Ix, which is the
default {u}mod{q|h|s|d}i3.
This commit makes sure that we don't generate REM_Ix calls for ABIs that
don't support them (i.e. where we need to use DIVREM_Ix instead). This is
achieved by bailing out of FastISel, which can't handle non-double multi-reg
returns, and letting the legalization infrastructure expand the REM_Ix calls.
It also updates the divmod-eabi.ll test to run under -O0 as well, and adds some
Windows checks to it to make sure we don't break things for it.
Fixes PR27068
Differential Revision: https://reviews.llvm.org/D21926
llvm-svn: 275773
Diffstat (limited to 'llvm/lib/Target/ARM/ARMFastISel.cpp')
-rw-r--r-- | llvm/lib/Target/ARM/ARMFastISel.cpp | 7 |
1 files changed, 7 insertions, 0 deletions
diff --git a/llvm/lib/Target/ARM/ARMFastISel.cpp b/llvm/lib/Target/ARM/ARMFastISel.cpp index 0f11ac9a3a0..13724da5d4f 100644 --- a/llvm/lib/Target/ARM/ARMFastISel.cpp +++ b/llvm/lib/Target/ARM/ARMFastISel.cpp @@ -1718,6 +1718,13 @@ bool ARMFastISel::SelectRem(const Instruction *I, bool isSigned) { if (!isTypeLegal(Ty, VT)) return false; + // Many ABIs do not provide a libcall for standalone remainder, so we need to + // use divrem (see the RTABI 4.3.1). Since FastISel can't handle non-double + // multi-reg returns, we'll have to bail out. + if (!TLI.hasStandaloneRem(VT)) { + return false; + } + RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL; if (VT == MVT::i8) LC = isSigned ? RTLIB::SREM_I8 : RTLIB::UREM_I8; |