forked from OSchip/llvm-project
[ARM] Move MVE opcode helper functions to ARMBaseInstrInfo. NFC.
In ARMLowOverheadLoops.cpp, MVETailPredication.cpp, and MVEVPTBlock.cpp we have quite a few helper functions all looking at the opcodes of MVE instructions. This moves all these utility functions to ARMBaseInstrInfo. Diferential Revision: https://reviews.llvm.org/D71426
This commit is contained in:
parent
959ed0e294
commit
049f9672d8
|
@ -488,6 +488,27 @@ bool isUncondBranchOpcode(int Opc) {
|
||||||
return Opc == ARM::B || Opc == ARM::tB || Opc == ARM::t2B;
|
return Opc == ARM::B || Opc == ARM::tB || Opc == ARM::t2B;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// This table shows the VPT instruction variants, i.e. the different
|
||||||
|
// mask field encodings, see also B5.6. Predication/conditional execution in
|
||||||
|
// the ArmARM.
|
||||||
|
enum VPTMaskValue {
|
||||||
|
T = 8, // 0b1000
|
||||||
|
TT = 4, // 0b0100
|
||||||
|
TE = 12, // 0b1100
|
||||||
|
TTT = 2, // 0b0010
|
||||||
|
TTE = 6, // 0b0110
|
||||||
|
TEE = 10, // 0b1010
|
||||||
|
TET = 14, // 0b1110
|
||||||
|
TTTT = 1, // 0b0001
|
||||||
|
TTTE = 3, // 0b0011
|
||||||
|
TTEE = 5, // 0b0101
|
||||||
|
TTET = 7, // 0b0111
|
||||||
|
TEEE = 9, // 0b1001
|
||||||
|
TEET = 11, // 0b1011
|
||||||
|
TETT = 13, // 0b1101
|
||||||
|
TETE = 15 // 0b1111
|
||||||
|
};
|
||||||
|
|
||||||
static inline bool isVPTOpcode(int Opc) {
|
static inline bool isVPTOpcode(int Opc) {
|
||||||
return Opc == ARM::MVE_VPTv16i8 || Opc == ARM::MVE_VPTv16u8 ||
|
return Opc == ARM::MVE_VPTv16i8 || Opc == ARM::MVE_VPTv16u8 ||
|
||||||
Opc == ARM::MVE_VPTv16s8 || Opc == ARM::MVE_VPTv8i16 ||
|
Opc == ARM::MVE_VPTv16s8 || Opc == ARM::MVE_VPTv8i16 ||
|
||||||
|
@ -503,6 +524,97 @@ static inline bool isVPTOpcode(int Opc) {
|
||||||
Opc == ARM::MVE_VPST;
|
Opc == ARM::MVE_VPST;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline
|
||||||
|
unsigned VCMPOpcodeToVPT(unsigned Opcode) {
|
||||||
|
switch (Opcode) {
|
||||||
|
default:
|
||||||
|
return 0;
|
||||||
|
case ARM::MVE_VCMPf32:
|
||||||
|
return ARM::MVE_VPTv4f32;
|
||||||
|
case ARM::MVE_VCMPf16:
|
||||||
|
return ARM::MVE_VPTv8f16;
|
||||||
|
case ARM::MVE_VCMPi8:
|
||||||
|
return ARM::MVE_VPTv16i8;
|
||||||
|
case ARM::MVE_VCMPi16:
|
||||||
|
return ARM::MVE_VPTv8i16;
|
||||||
|
case ARM::MVE_VCMPi32:
|
||||||
|
return ARM::MVE_VPTv4i32;
|
||||||
|
case ARM::MVE_VCMPu8:
|
||||||
|
return ARM::MVE_VPTv16u8;
|
||||||
|
case ARM::MVE_VCMPu16:
|
||||||
|
return ARM::MVE_VPTv8u16;
|
||||||
|
case ARM::MVE_VCMPu32:
|
||||||
|
return ARM::MVE_VPTv4u32;
|
||||||
|
case ARM::MVE_VCMPs8:
|
||||||
|
return ARM::MVE_VPTv16s8;
|
||||||
|
case ARM::MVE_VCMPs16:
|
||||||
|
return ARM::MVE_VPTv8s16;
|
||||||
|
case ARM::MVE_VCMPs32:
|
||||||
|
return ARM::MVE_VPTv4s32;
|
||||||
|
|
||||||
|
case ARM::MVE_VCMPf32r:
|
||||||
|
return ARM::MVE_VPTv4f32r;
|
||||||
|
case ARM::MVE_VCMPf16r:
|
||||||
|
return ARM::MVE_VPTv8f16r;
|
||||||
|
case ARM::MVE_VCMPi8r:
|
||||||
|
return ARM::MVE_VPTv16i8r;
|
||||||
|
case ARM::MVE_VCMPi16r:
|
||||||
|
return ARM::MVE_VPTv8i16r;
|
||||||
|
case ARM::MVE_VCMPi32r:
|
||||||
|
return ARM::MVE_VPTv4i32r;
|
||||||
|
case ARM::MVE_VCMPu8r:
|
||||||
|
return ARM::MVE_VPTv16u8r;
|
||||||
|
case ARM::MVE_VCMPu16r:
|
||||||
|
return ARM::MVE_VPTv8u16r;
|
||||||
|
case ARM::MVE_VCMPu32r:
|
||||||
|
return ARM::MVE_VPTv4u32r;
|
||||||
|
case ARM::MVE_VCMPs8r:
|
||||||
|
return ARM::MVE_VPTv16s8r;
|
||||||
|
case ARM::MVE_VCMPs16r:
|
||||||
|
return ARM::MVE_VPTv8s16r;
|
||||||
|
case ARM::MVE_VCMPs32r:
|
||||||
|
return ARM::MVE_VPTv4s32r;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline
|
||||||
|
unsigned VCTPOpcodeToLSTP(unsigned Opcode, bool IsDoLoop) {
|
||||||
|
switch (Opcode) {
|
||||||
|
default:
|
||||||
|
llvm_unreachable("unhandled vctp opcode");
|
||||||
|
break;
|
||||||
|
case ARM::MVE_VCTP8:
|
||||||
|
return IsDoLoop ? ARM::MVE_DLSTP_8 : ARM::MVE_WLSTP_8;
|
||||||
|
case ARM::MVE_VCTP16:
|
||||||
|
return IsDoLoop ? ARM::MVE_DLSTP_16 : ARM::MVE_WLSTP_16;
|
||||||
|
case ARM::MVE_VCTP32:
|
||||||
|
return IsDoLoop ? ARM::MVE_DLSTP_32 : ARM::MVE_WLSTP_32;
|
||||||
|
case ARM::MVE_VCTP64:
|
||||||
|
return IsDoLoop ? ARM::MVE_DLSTP_64 : ARM::MVE_WLSTP_64;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline
|
||||||
|
bool isVCTP(MachineInstr *MI) {
|
||||||
|
switch (MI->getOpcode()) {
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
case ARM::MVE_VCTP8:
|
||||||
|
case ARM::MVE_VCTP16:
|
||||||
|
case ARM::MVE_VCTP32:
|
||||||
|
case ARM::MVE_VCTP64:
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline
|
||||||
|
bool isLoopStart(MachineInstr &MI) {
|
||||||
|
return MI.getOpcode() == ARM::t2DoLoopStart ||
|
||||||
|
MI.getOpcode() == ARM::t2WhileLoopStart;
|
||||||
|
}
|
||||||
|
|
||||||
static inline
|
static inline
|
||||||
bool isCondBranchOpcode(int Opc) {
|
bool isCondBranchOpcode(int Opc) {
|
||||||
return Opc == ARM::Bcc || Opc == ARM::tBcc || Opc == ARM::t2Bcc;
|
return Opc == ARM::Bcc || Opc == ARM::tBcc || Opc == ARM::t2Bcc;
|
||||||
|
|
|
@ -130,20 +130,7 @@ namespace {
|
||||||
if (!IsTailPredicationLegal())
|
if (!IsTailPredicationLegal())
|
||||||
return IsDo ? ARM::t2DLS : ARM::t2WLS;
|
return IsDo ? ARM::t2DLS : ARM::t2WLS;
|
||||||
|
|
||||||
switch (VCTP->getOpcode()) {
|
return VCTPOpcodeToLSTP(VCTP->getOpcode(), IsDo);
|
||||||
default:
|
|
||||||
llvm_unreachable("unhandled vctp opcode");
|
|
||||||
break;
|
|
||||||
case ARM::MVE_VCTP8:
|
|
||||||
return IsDo ? ARM::MVE_DLSTP_8 : ARM::MVE_WLSTP_8;
|
|
||||||
case ARM::MVE_VCTP16:
|
|
||||||
return IsDo ? ARM::MVE_DLSTP_16 : ARM::MVE_WLSTP_16;
|
|
||||||
case ARM::MVE_VCTP32:
|
|
||||||
return IsDo ? ARM::MVE_DLSTP_32 : ARM::MVE_WLSTP_32;
|
|
||||||
case ARM::MVE_VCTP64:
|
|
||||||
return IsDo ? ARM::MVE_DLSTP_64 : ARM::MVE_WLSTP_64;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void dump() const {
|
void dump() const {
|
||||||
|
@ -218,24 +205,6 @@ char ARMLowOverheadLoops::ID = 0;
|
||||||
INITIALIZE_PASS(ARMLowOverheadLoops, DEBUG_TYPE, ARM_LOW_OVERHEAD_LOOPS_NAME,
|
INITIALIZE_PASS(ARMLowOverheadLoops, DEBUG_TYPE, ARM_LOW_OVERHEAD_LOOPS_NAME,
|
||||||
false, false)
|
false, false)
|
||||||
|
|
||||||
static bool IsLoopStart(MachineInstr &MI) {
|
|
||||||
return MI.getOpcode() == ARM::t2DoLoopStart ||
|
|
||||||
MI.getOpcode() == ARM::t2WhileLoopStart;
|
|
||||||
}
|
|
||||||
|
|
||||||
static bool IsVCTP(MachineInstr *MI) {
|
|
||||||
switch (MI->getOpcode()) {
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
case ARM::MVE_VCTP8:
|
|
||||||
case ARM::MVE_VCTP16:
|
|
||||||
case ARM::MVE_VCTP32:
|
|
||||||
case ARM::MVE_VCTP64:
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
MachineInstr *LowOverheadLoop::IsSafeToDefineLR(ReachingDefAnalysis *RDA) {
|
MachineInstr *LowOverheadLoop::IsSafeToDefineLR(ReachingDefAnalysis *RDA) {
|
||||||
// We can define LR because LR already contains the same value.
|
// We can define LR because LR already contains the same value.
|
||||||
if (Start->getOperand(0).getReg() == ARM::LR)
|
if (Start->getOperand(0).getReg() == ARM::LR)
|
||||||
|
@ -423,7 +392,7 @@ bool ARMLowOverheadLoops::ProcessLoop(MachineLoop *ML) {
|
||||||
std::function<MachineInstr*(MachineBasicBlock*)> SearchForStart =
|
std::function<MachineInstr*(MachineBasicBlock*)> SearchForStart =
|
||||||
[&SearchForStart](MachineBasicBlock *MBB) -> MachineInstr* {
|
[&SearchForStart](MachineBasicBlock *MBB) -> MachineInstr* {
|
||||||
for (auto &MI : *MBB) {
|
for (auto &MI : *MBB) {
|
||||||
if (IsLoopStart(MI))
|
if (isLoopStart(MI))
|
||||||
return &MI;
|
return &MI;
|
||||||
}
|
}
|
||||||
if (MBB->pred_size() == 1)
|
if (MBB->pred_size() == 1)
|
||||||
|
@ -451,9 +420,9 @@ bool ARMLowOverheadLoops::ProcessLoop(MachineLoop *ML) {
|
||||||
LoLoop.Dec = &MI;
|
LoLoop.Dec = &MI;
|
||||||
else if (MI.getOpcode() == ARM::t2LoopEnd)
|
else if (MI.getOpcode() == ARM::t2LoopEnd)
|
||||||
LoLoop.End = &MI;
|
LoLoop.End = &MI;
|
||||||
else if (IsLoopStart(MI))
|
else if (isLoopStart(MI))
|
||||||
LoLoop.Start = &MI;
|
LoLoop.Start = &MI;
|
||||||
else if (IsVCTP(&MI))
|
else if (isVCTP(&MI))
|
||||||
LoLoop.addVCTP(&MI);
|
LoLoop.addVCTP(&MI);
|
||||||
else if (MI.getDesc().isCall()) {
|
else if (MI.getDesc().isCall()) {
|
||||||
// TODO: Though the call will require LE to execute again, does this
|
// TODO: Though the call will require LE to execute again, does this
|
||||||
|
@ -789,7 +758,7 @@ bool ARMLowOverheadLoops::RevertNonLoops() {
|
||||||
SmallVector<MachineInstr*, 4> Ends;
|
SmallVector<MachineInstr*, 4> Ends;
|
||||||
|
|
||||||
for (auto &I : MBB) {
|
for (auto &I : MBB) {
|
||||||
if (IsLoopStart(I))
|
if (isLoopStart(I))
|
||||||
Starts.push_back(&I);
|
Starts.push_back(&I);
|
||||||
else if (I.getOpcode() == ARM::t2LoopDec)
|
else if (I.getOpcode() == ARM::t2LoopDec)
|
||||||
Decs.push_back(&I);
|
Decs.push_back(&I);
|
||||||
|
|
|
@ -63,77 +63,6 @@ namespace {
|
||||||
|
|
||||||
INITIALIZE_PASS(MVEVPTBlock, DEBUG_TYPE, "ARM MVE VPT block pass", false, false)
|
INITIALIZE_PASS(MVEVPTBlock, DEBUG_TYPE, "ARM MVE VPT block pass", false, false)
|
||||||
|
|
||||||
enum VPTMaskValue {
|
|
||||||
T = 8, // 0b1000
|
|
||||||
TT = 4, // 0b0100
|
|
||||||
TE = 12, // 0b1100
|
|
||||||
TTT = 2, // 0b0010
|
|
||||||
TTE = 6, // 0b0110
|
|
||||||
TEE = 10, // 0b1010
|
|
||||||
TET = 14, // 0b1110
|
|
||||||
TTTT = 1, // 0b0001
|
|
||||||
TTTE = 3, // 0b0011
|
|
||||||
TTEE = 5, // 0b0101
|
|
||||||
TTET = 7, // 0b0111
|
|
||||||
TEEE = 9, // 0b1001
|
|
||||||
TEET = 11, // 0b1011
|
|
||||||
TETT = 13, // 0b1101
|
|
||||||
TETE = 15 // 0b1111
|
|
||||||
};
|
|
||||||
|
|
||||||
static unsigned VCMPOpcodeToVPT(unsigned Opcode) {
|
|
||||||
switch (Opcode) {
|
|
||||||
case ARM::MVE_VCMPf32:
|
|
||||||
return ARM::MVE_VPTv4f32;
|
|
||||||
case ARM::MVE_VCMPf16:
|
|
||||||
return ARM::MVE_VPTv8f16;
|
|
||||||
case ARM::MVE_VCMPi8:
|
|
||||||
return ARM::MVE_VPTv16i8;
|
|
||||||
case ARM::MVE_VCMPi16:
|
|
||||||
return ARM::MVE_VPTv8i16;
|
|
||||||
case ARM::MVE_VCMPi32:
|
|
||||||
return ARM::MVE_VPTv4i32;
|
|
||||||
case ARM::MVE_VCMPu8:
|
|
||||||
return ARM::MVE_VPTv16u8;
|
|
||||||
case ARM::MVE_VCMPu16:
|
|
||||||
return ARM::MVE_VPTv8u16;
|
|
||||||
case ARM::MVE_VCMPu32:
|
|
||||||
return ARM::MVE_VPTv4u32;
|
|
||||||
case ARM::MVE_VCMPs8:
|
|
||||||
return ARM::MVE_VPTv16s8;
|
|
||||||
case ARM::MVE_VCMPs16:
|
|
||||||
return ARM::MVE_VPTv8s16;
|
|
||||||
case ARM::MVE_VCMPs32:
|
|
||||||
return ARM::MVE_VPTv4s32;
|
|
||||||
|
|
||||||
case ARM::MVE_VCMPf32r:
|
|
||||||
return ARM::MVE_VPTv4f32r;
|
|
||||||
case ARM::MVE_VCMPf16r:
|
|
||||||
return ARM::MVE_VPTv8f16r;
|
|
||||||
case ARM::MVE_VCMPi8r:
|
|
||||||
return ARM::MVE_VPTv16i8r;
|
|
||||||
case ARM::MVE_VCMPi16r:
|
|
||||||
return ARM::MVE_VPTv8i16r;
|
|
||||||
case ARM::MVE_VCMPi32r:
|
|
||||||
return ARM::MVE_VPTv4i32r;
|
|
||||||
case ARM::MVE_VCMPu8r:
|
|
||||||
return ARM::MVE_VPTv16u8r;
|
|
||||||
case ARM::MVE_VCMPu16r:
|
|
||||||
return ARM::MVE_VPTv8u16r;
|
|
||||||
case ARM::MVE_VCMPu32r:
|
|
||||||
return ARM::MVE_VPTv4u32r;
|
|
||||||
case ARM::MVE_VCMPs8r:
|
|
||||||
return ARM::MVE_VPTv16s8r;
|
|
||||||
case ARM::MVE_VCMPs16r:
|
|
||||||
return ARM::MVE_VPTv8s16r;
|
|
||||||
case ARM::MVE_VCMPs32r:
|
|
||||||
return ARM::MVE_VPTv4s32r;
|
|
||||||
|
|
||||||
default:
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static MachineInstr *findVCMPToFoldIntoVPST(MachineBasicBlock::iterator MI,
|
static MachineInstr *findVCMPToFoldIntoVPST(MachineBasicBlock::iterator MI,
|
||||||
const TargetRegisterInfo *TRI,
|
const TargetRegisterInfo *TRI,
|
||||||
unsigned &NewOpcode) {
|
unsigned &NewOpcode) {
|
||||||
|
|
Loading…
Reference in New Issue