mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2025-02-04 19:26:30 +00:00
GlobalISel: legalize frem to a libcall on AArch64.
llvm-svn: 279988
This commit is contained in:
parent
05f74b5dbe
commit
34bd451acc
@ -88,9 +88,9 @@ class CallLowering {
|
||||
/// needs to be passed.
|
||||
///
|
||||
/// \return true if the lowering succeeded, false otherwise.
|
||||
virtual bool lowerCall(MachineIRBuilder &MIRBuilder, MachineOperand &Callee,
|
||||
ArrayRef<MVT> ResTys, ArrayRef<unsigned> ResRegs,
|
||||
ArrayRef<MVT> ArgTys,
|
||||
virtual bool lowerCall(MachineIRBuilder &MIRBuilder,
|
||||
const MachineOperand &Callee, ArrayRef<MVT> ResTys,
|
||||
ArrayRef<unsigned> ResRegs, ArrayRef<MVT> ArgTys,
|
||||
ArrayRef<unsigned> ArgRegs) const {
|
||||
return false;
|
||||
}
|
||||
|
@ -61,6 +61,9 @@ public:
|
||||
LegalizeResult legalizeInstr(MachineInstr &MI,
|
||||
const MachineLegalizer &Legalizer);
|
||||
|
||||
/// Legalize an instruction by emiting a runtime library call instead.
|
||||
LegalizeResult libcall(MachineInstr &MI);
|
||||
|
||||
/// Legalize an instruction by reducing the width of the underlying scalar
|
||||
/// type.
|
||||
LegalizeResult narrowScalar(MachineInstr &MI, unsigned TypeIdx, LLT NarrowTy);
|
||||
|
@ -14,10 +14,12 @@
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/CodeGen/GlobalISel/MachineLegalizeHelper.h"
|
||||
#include "llvm/CodeGen/GlobalISel/CallLowering.h"
|
||||
#include "llvm/CodeGen/GlobalISel/MachineLegalizer.h"
|
||||
#include "llvm/CodeGen/MachineRegisterInfo.h"
|
||||
#include "llvm/Support/Debug.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
#include "llvm/Target/TargetLowering.h"
|
||||
#include "llvm/Target/TargetSubtargetInfo.h"
|
||||
|
||||
#include <sstream>
|
||||
@ -38,6 +40,8 @@ MachineLegalizeHelper::legalizeInstrStep(MachineInstr &MI,
|
||||
switch (std::get<0>(Action)) {
|
||||
case MachineLegalizer::Legal:
|
||||
return AlreadyLegal;
|
||||
case MachineLegalizer::Libcall:
|
||||
return libcall(MI);
|
||||
case MachineLegalizer::NarrowScalar:
|
||||
return narrowScalar(MI, std::get<1>(Action), std::get<2>(Action));
|
||||
case MachineLegalizer::WidenScalar:
|
||||
@ -89,6 +93,30 @@ void MachineLegalizeHelper::extractParts(unsigned Reg, LLT Ty, int NumParts,
|
||||
LLT::scalar(Ty.getSizeInBits() * NumParts), Reg);
|
||||
}
|
||||
|
||||
MachineLegalizeHelper::LegalizeResult
|
||||
MachineLegalizeHelper::libcall(MachineInstr &MI) {
|
||||
unsigned Size = MI.getType().getSizeInBits();
|
||||
MIRBuilder.setInstr(MI);
|
||||
|
||||
switch (MI.getOpcode()) {
|
||||
default:
|
||||
return UnableToLegalize;
|
||||
case TargetOpcode::G_FREM: {
|
||||
MVT Ty = MVT::getFloatingPointVT(MI.getType().getSizeInBits());
|
||||
auto &CLI = *MIRBuilder.getMF().getSubtarget().getCallLowering();
|
||||
auto &TLI = *MIRBuilder.getMF().getSubtarget().getTargetLowering();
|
||||
const char *Name =
|
||||
TLI.getLibcallName(Size == 64 ? RTLIB::REM_F64 : RTLIB::REM_F32);
|
||||
|
||||
CLI.lowerCall(MIRBuilder, MachineOperand::CreateES(Name), Ty,
|
||||
MI.getOperand(0).getReg(), {Ty, Ty},
|
||||
{MI.getOperand(1).getReg(), MI.getOperand(2).getReg()});
|
||||
MI.eraseFromParent();
|
||||
return Legalized;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
MachineLegalizeHelper::LegalizeResult
|
||||
MachineLegalizeHelper::narrowScalar(MachineInstr &MI, unsigned TypeIdx,
|
||||
LLT NarrowTy) {
|
||||
|
@ -127,6 +127,7 @@ LLT MachineLegalizer::findLegalType(const InstrAspect &Aspect,
|
||||
llvm_unreachable("Cannot find legal type");
|
||||
case Legal:
|
||||
case Lower:
|
||||
case Libcall:
|
||||
return Aspect.Type;
|
||||
case NarrowScalar: {
|
||||
return findLegalType(Aspect,
|
||||
|
@ -131,7 +131,7 @@ bool AArch64CallLowering::lowerFormalArguments(
|
||||
}
|
||||
|
||||
bool AArch64CallLowering::lowerCall(MachineIRBuilder &MIRBuilder,
|
||||
MachineOperand &Callee,
|
||||
const MachineOperand &Callee,
|
||||
ArrayRef<MVT> ResTys,
|
||||
ArrayRef<unsigned> ResRegs,
|
||||
ArrayRef<MVT> ArgTys,
|
||||
|
@ -34,7 +34,7 @@ class AArch64CallLowering: public CallLowering {
|
||||
const Function::ArgumentListType &Args,
|
||||
ArrayRef<unsigned> VRegs) const override;
|
||||
|
||||
bool lowerCall(MachineIRBuilder &MIRBuilder, MachineOperand &Callee,
|
||||
bool lowerCall(MachineIRBuilder &MIRBuilder, const MachineOperand &Callee,
|
||||
ArrayRef<MVT> ResTys, ArrayRef<unsigned> ResRegs,
|
||||
ArrayRef<MVT> ArgTys,
|
||||
ArrayRef<unsigned> ArgRegs) const override;
|
||||
|
@ -66,6 +66,9 @@ AArch64MachineLegalizer::AArch64MachineLegalizer() {
|
||||
for (auto Ty : {s32, s64})
|
||||
setAction({BinOp, Ty}, Legal);
|
||||
|
||||
setAction({G_FREM, s32}, Libcall);
|
||||
setAction({G_FREM, s64}, Libcall);
|
||||
|
||||
for (auto MemOp : {G_LOAD, G_STORE}) {
|
||||
for (auto Ty : {s8, s16, s32, s64})
|
||||
setAction({MemOp, Ty}, Legal);
|
||||
|
@ -21,6 +21,8 @@ registers:
|
||||
- { id: 6, class: _ }
|
||||
- { id: 7, class: _ }
|
||||
- { id: 8, class: _ }
|
||||
- { id: 9, class: _ }
|
||||
- { id: 10, class: _ }
|
||||
body: |
|
||||
bb.0.entry:
|
||||
liveins: %x0, %x1, %x2, %x3
|
||||
@ -49,4 +51,16 @@ body: |
|
||||
%7(8) = G_TRUNC { s8, s64 } %1
|
||||
%8(8) = G_SREM s8 %6, %7
|
||||
|
||||
; CHECK: %d0 = COPY %0
|
||||
; CHECK: %d1 = COPY %1
|
||||
; CHECK: BL $fmod, csr_aarch64_aapcs, implicit-def %lr, implicit %sp, implicit %d0, implicit %d1, implicit-def %d0
|
||||
; CHECK: %9(64) = COPY %d0
|
||||
%9(64) = G_FREM s64 %0, %1
|
||||
|
||||
; CHECK: %s0 = COPY %3
|
||||
; CHECK: %s1 = COPY %4
|
||||
; CHECK: BL $fmodf, csr_aarch64_aapcs, implicit-def %lr, implicit %sp, implicit %s0, implicit %s1, implicit-def %s0
|
||||
; CHECK: %10(32) = COPY %s0
|
||||
%10(32) = G_FREM s32 %3, %4
|
||||
|
||||
...
|
||||
|
Loading…
x
Reference in New Issue
Block a user