forked from OSchip/llvm-project
[M68k][GloballSel] RegBankSelect implementation
Implementation of RegBankSelect for the M68k backend. Differential Revision: https://reviews.llvm.org/D107542
This commit is contained in:
parent
a353edb8d6
commit
7bdce6bcbd
|
@ -11,7 +11,8 @@
|
|||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "M68kRegisterBankInfo.h"
|
||||
#include "MCTargetDesc/M68kMCTargetDesc.h"
|
||||
#include "M68kInstrInfo.h" // For the register classes
|
||||
#include "M68kSubtarget.h"
|
||||
#include "llvm/CodeGen/GlobalISel/RegisterBank.h"
|
||||
#include "llvm/CodeGen/GlobalISel/RegisterBankInfo.h"
|
||||
#include "llvm/CodeGen/MachineRegisterInfo.h"
|
||||
|
@ -19,9 +20,86 @@
|
|||
|
||||
#define GET_TARGET_REGBANK_IMPL
|
||||
#include "M68kGenRegisterBank.inc"
|
||||
#undef GET_TARGET_REGBANK_IMPL
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
// FIXME: TableGen this.
|
||||
// If it grows too much and TableGen still isn't ready to do the job, extract it
|
||||
// into an M68kGenRegisterBankInfo.def (similar to AArch64).
|
||||
namespace llvm {
|
||||
namespace M68k {
|
||||
enum PartialMappingIdx {
|
||||
PMI_GPR,
|
||||
PMI_Min = PMI_GPR,
|
||||
};
|
||||
|
||||
RegisterBankInfo::PartialMapping PartMappings[]{
|
||||
// GPR Partial Mapping
|
||||
{0, 32, GPRRegBank},
|
||||
};
|
||||
|
||||
enum ValueMappingIdx {
|
||||
InvalidIdx = 0,
|
||||
GPR3OpsIdx = 1,
|
||||
};
|
||||
|
||||
RegisterBankInfo::ValueMapping ValueMappings[] = {
|
||||
// invalid
|
||||
{nullptr, 0},
|
||||
// 3 operands in GPRs
|
||||
{&PartMappings[PMI_GPR - PMI_Min], 1},
|
||||
{&PartMappings[PMI_GPR - PMI_Min], 1},
|
||||
{&PartMappings[PMI_GPR - PMI_Min], 1},
|
||||
|
||||
};
|
||||
} // end namespace M68k
|
||||
} // end namespace llvm
|
||||
|
||||
M68kRegisterBankInfo::M68kRegisterBankInfo(const TargetRegisterInfo &TRI)
|
||||
: M68kGenRegisterBankInfo() {}
|
||||
|
||||
const RegisterBank &
|
||||
M68kRegisterBankInfo::getRegBankFromRegClass(const TargetRegisterClass &RC,
|
||||
LLT) const {
|
||||
return getRegBank(M68k::GPRRegBankID);
|
||||
}
|
||||
|
||||
const RegisterBankInfo::InstructionMapping &
|
||||
M68kRegisterBankInfo::getInstrMapping(const MachineInstr &MI) const {
|
||||
auto Opc = MI.getOpcode();
|
||||
|
||||
if (!isPreISelGenericOpcode(Opc)) {
|
||||
const InstructionMapping &Mapping = getInstrMappingImpl(MI);
|
||||
if (Mapping.isValid())
|
||||
return Mapping;
|
||||
}
|
||||
|
||||
using namespace TargetOpcode;
|
||||
|
||||
unsigned NumOperands = MI.getNumOperands();
|
||||
const ValueMapping *OperandsMapping = &M68k::ValueMappings[M68k::GPR3OpsIdx];
|
||||
|
||||
switch (Opc) {
|
||||
case G_ADD:
|
||||
case G_SUB:
|
||||
case G_MUL:
|
||||
case G_SDIV:
|
||||
case G_UDIV:
|
||||
case G_LOAD:
|
||||
case G_STORE: {
|
||||
OperandsMapping = &M68k::ValueMappings[M68k::GPR3OpsIdx];
|
||||
break;
|
||||
}
|
||||
|
||||
case G_CONSTANT:
|
||||
case G_FRAME_INDEX:
|
||||
OperandsMapping =
|
||||
getOperandsMapping({&M68k::ValueMappings[M68k::GPR3OpsIdx], nullptr});
|
||||
break;
|
||||
default:
|
||||
return getInvalidInstructionMapping();
|
||||
}
|
||||
|
||||
return getInstructionMapping(DefaultMappingID, /*Cost=*/1, OperandsMapping,
|
||||
NumOperands);
|
||||
}
|
||||
|
|
|
@ -34,6 +34,12 @@ protected:
|
|||
class M68kRegisterBankInfo final : public M68kGenRegisterBankInfo {
|
||||
public:
|
||||
M68kRegisterBankInfo(const TargetRegisterInfo &TRI);
|
||||
|
||||
const RegisterBank &getRegBankFromRegClass(const TargetRegisterClass &RC,
|
||||
LLT) const override;
|
||||
|
||||
const InstructionMapping &
|
||||
getInstrMapping(const MachineInstr &MI) const override;
|
||||
};
|
||||
} // end namespace llvm
|
||||
#endif
|
||||
|
|
|
@ -12,4 +12,4 @@
|
|||
//===----------------------------------------------------------------------===//
|
||||
|
||||
/// General Purpose Registers. Here we define a register bank with name AnyGPR
|
||||
def GPRRegBank : RegisterBank<"AnyGPR", [DR8]>;
|
||||
def GPRRegBank : RegisterBank<"AnyGPR", [XR32]>;
|
||||
|
|
|
@ -0,0 +1,29 @@
|
|||
; RUN: llc -mtriple=m68k -global-isel -stop-after=regbankselect < %s | FileCheck %s
|
||||
|
||||
define i32 @test_add(i32 %x, i32 %y) {
|
||||
; CHECK-LABEL: name: test_add
|
||||
; CHECK: bb.1 (%ir-block.0):
|
||||
; CHECK: [[G_F_I1:%[0-9]+]]:anygpr(p0) = G_FRAME_INDEX
|
||||
; CHECK: [[G_LOAD1:%[0-9]+]]:anygpr(s32) = G_LOAD [[G_F_I1]](p0)
|
||||
; CHECK: [[G_F_I2:%[0-9]+]]:anygpr(p0) = G_FRAME_INDEX
|
||||
; CHECK: [[G_LOAD2:%[0-9]+]]:anygpr(s32) = G_LOAD [[G_F_I2]](p0)
|
||||
; CHECK: [[G_ADD1:%[0-9]+]]:anygpr(s32) = G_ADD [[G_LOAD1]], [[G_LOAD2]]
|
||||
; CHECK: $d0 = COPY [[G_ADD1]](s32)
|
||||
; CHECK: RTS implicit $d0
|
||||
%sum = add i32 %x, %y
|
||||
ret i32 %sum
|
||||
}
|
||||
|
||||
define i32 @test_sub(i32 %x, i32 %y) {
|
||||
; CHECK-LABEL: name: test_sub
|
||||
; CHECK: bb.1 (%ir-block.0):
|
||||
; CHECK: [[G_F_I1:%[0-9]+]]:anygpr(p0) = G_FRAME_INDEX
|
||||
; CHECK: [[G_LOAD1:%[0-9]+]]:anygpr(s32) = G_LOAD [[G_F_I1]](p0)
|
||||
; CHECK: [[G_F_I2:%[0-9]+]]:anygpr(p0) = G_FRAME_INDEX
|
||||
; CHECK: [[G_LOAD2:%[0-9]+]]:anygpr(s32) = G_LOAD [[G_F_I2]](p0)
|
||||
; CHECK: [[G_SUB1:%[0-9]+]]:anygpr(s32) = G_SUB [[G_LOAD1]], [[G_LOAD2]]
|
||||
; CHECK: $d0 = COPY [[G_SUB1]](s32)
|
||||
; CHECK: RTS implicit $d0
|
||||
%diff = sub i32 %x, %y
|
||||
ret i32 %diff
|
||||
}
|
Loading…
Reference in New Issue