Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
330 changes: 325 additions & 5 deletions llvm/lib/Target/AArch64/AArch64FrameLowering.cpp

Large diffs are not rendered by default.

16 changes: 15 additions & 1 deletion llvm/lib/Target/AArch64/AArch64InstrInfo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ static cl::opt<unsigned>
AArch64InstrInfo::AArch64InstrInfo(const AArch64Subtarget &STI)
: AArch64GenInstrInfo(AArch64::ADJCALLSTACKDOWN, AArch64::ADJCALLSTACKUP,
AArch64::CATCHRET),
RI(STI.getTargetTriple()), Subtarget(STI) {}
RI(STI.getTargetTriple(), STI.getHwMode()), Subtarget(STI) {}

/// GetInstSize - Return the number of bytes of code the specified
/// instruction may be. This returns the maximum number of bytes.
Expand Down Expand Up @@ -2438,6 +2438,8 @@ unsigned AArch64InstrInfo::getLoadStoreImmIdx(unsigned Opc) {
case AArch64::STZ2Gi:
case AArch64::STZGi:
case AArch64::TAGPstack:
case AArch64::SPILL_PPR_TO_ZPR_SLOT_PSEUDO:
case AArch64::FILL_PPR_FROM_ZPR_SLOT_PSEUDO:
return 2;
case AArch64::LD1B_D_IMM:
case AArch64::LD1B_H_IMM:
Expand Down Expand Up @@ -4223,6 +4225,8 @@ bool AArch64InstrInfo::getMemOpInfo(unsigned Opcode, TypeSize &Scale,
MinOffset = -256;
MaxOffset = 254;
break;
case AArch64::SPILL_PPR_TO_ZPR_SLOT_PSEUDO:
case AArch64::FILL_PPR_FROM_ZPR_SLOT_PSEUDO:
case AArch64::LDR_ZXI:
case AArch64::STR_ZXI:
Scale = TypeSize::getScalable(16);
Expand Down Expand Up @@ -5355,6 +5359,11 @@ void AArch64InstrInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
"Unexpected register store without SVE store instructions");
Opc = AArch64::STR_ZXI;
StackID = TargetStackID::ScalableVector;
} else if (AArch64::PPRRegClass.hasSubClassEq(RC)) {
assert(Subtarget.isSVEorStreamingSVEAvailable() &&
"Unexpected predicate store without SVE store instructions");
Opc = AArch64::SPILL_PPR_TO_ZPR_SLOT_PSEUDO;
StackID = TargetStackID::ScalableVector;
}
break;
case 24:
Expand Down Expand Up @@ -5527,6 +5536,11 @@ void AArch64InstrInfo::loadRegFromStackSlot(
"Unexpected register load without SVE load instructions");
Opc = AArch64::LDR_ZXI;
StackID = TargetStackID::ScalableVector;
} else if (AArch64::PPRRegClass.hasSubClassEq(RC)) {
assert(Subtarget.isSVEorStreamingSVEAvailable() &&
"Unexpected predicate load without SVE load instructions");
Opc = AArch64::FILL_PPR_FROM_ZPR_SLOT_PSEUDO;
StackID = TargetStackID::ScalableVector;
}
break;
case 24:
Expand Down
4 changes: 2 additions & 2 deletions llvm/lib/Target/AArch64/AArch64RegisterInfo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,8 @@ using namespace llvm;
#define GET_REGINFO_TARGET_DESC
#include "AArch64GenRegisterInfo.inc"

AArch64RegisterInfo::AArch64RegisterInfo(const Triple &TT)
: AArch64GenRegisterInfo(AArch64::LR), TT(TT) {
AArch64RegisterInfo::AArch64RegisterInfo(const Triple &TT, unsigned HwMode)
: AArch64GenRegisterInfo(AArch64::LR, 0, 0, 0, HwMode), TT(TT) {
AArch64_MC::initLLVMToCVRegMapping(this);
}

Expand Down
2 changes: 1 addition & 1 deletion llvm/lib/Target/AArch64/AArch64RegisterInfo.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ class AArch64RegisterInfo final : public AArch64GenRegisterInfo {
const Triple &TT;

public:
AArch64RegisterInfo(const Triple &TT);
AArch64RegisterInfo(const Triple &TT, unsigned HwMode);

// FIXME: This should be tablegen'd like getDwarfRegNum is
int getSEHRegNum(unsigned i) const {
Expand Down
11 changes: 10 additions & 1 deletion llvm/lib/Target/AArch64/AArch64RegisterInfo.td
Original file line number Diff line number Diff line change
Expand Up @@ -979,10 +979,19 @@ class ZPRRegOp <string Suffix, AsmOperandClass C, ElementSizeEnum Size,
//******************************************************************************

// SVE predicate register classes.

// Note: This hardware mode is enabled in AArch64Subtarget::getHwModeSet()
// (without the use of the table-gen'd predicates).
def SMEWithZPRPredicateSpills : HwMode<"", [Predicate<"false">]>;

def PPRSpillFillRI : RegInfoByHwMode<
[DefaultMode, SMEWithZPRPredicateSpills],
[RegInfo<16,16,16>, RegInfo<16,128,128>]>;

class PPRClass<int firstreg, int lastreg, int step = 1> : RegisterClass<"AArch64",
[ nxv16i1, nxv8i1, nxv4i1, nxv2i1, nxv1i1 ], 16,
(sequence "P%u", firstreg, lastreg, step)> {
let Size = 16;
let RegInfos = PPRSpillFillRI;
}

def PPR : PPRClass<0, 15> {
Expand Down
19 changes: 19 additions & 0 deletions llvm/lib/Target/AArch64/AArch64Subtarget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,11 @@ static cl::alias AArch64StreamingStackHazardSize(
cl::desc("alias for -aarch64-streaming-hazard-size"),
cl::aliasopt(AArch64StreamingHazardSize));

static cl::opt<bool> EnableZPRPredicateSpills(
"aarch64-enable-zpr-predicate-spills", cl::init(false), cl::Hidden,
cl::desc(
"Enables spilling/reloading SVE predicates as data vectors (ZPRs)"));

// Subreg liveness tracking is disabled by default for now until all issues
// are ironed out. This option allows the feature to be used in tests.
static cl::opt<bool>
Expand Down Expand Up @@ -405,6 +410,20 @@ AArch64Subtarget::AArch64Subtarget(const Triple &TT, StringRef CPU,
EnableSubregLiveness = EnableSubregLivenessTracking.getValue();
}

unsigned AArch64Subtarget::getHwModeSet() const {
AArch64HwModeBits Modes = AArch64HwModeBits::DefaultMode;

// Use a special hardware mode in streaming[-compatible] functions with
// aarch64-enable-zpr-predicate-spills. This changes the spill size (and
// alignment) for the predicate register class.
if (EnableZPRPredicateSpills.getValue() &&
(isStreaming() || isStreamingCompatible())) {
Modes |= AArch64HwModeBits::SMEWithZPRPredicateSpills;
}

return to_underlying(Modes);
}

const CallLowering *AArch64Subtarget::getCallLowering() const {
return CallLoweringInfo.get();
}
Expand Down
2 changes: 2 additions & 0 deletions llvm/lib/Target/AArch64/AArch64Subtarget.h
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,8 @@ class AArch64Subtarget final : public AArch64GenSubtargetInfo {
bool IsStreaming = false, bool IsStreamingCompatible = false,
bool HasMinSize = false);

virtual unsigned getHwModeSet() const override;

// Getters for SubtargetFeatures defined in tablegen
#define GET_SUBTARGETINFO_MACRO(ATTRIBUTE, DEFAULT, GETTER) \
bool GETTER() const { return ATTRIBUTE; }
Expand Down
14 changes: 14 additions & 0 deletions llvm/lib/Target/AArch64/SMEInstrFormats.td
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,20 @@ def FORM_TRANSPOSED_REG_TUPLE_X4_PSEUDO :
let hasPostISelHook = 1;
}

def SPILL_PPR_TO_ZPR_SLOT_PSEUDO :
Pseudo<(outs), (ins PPRorPNRAny:$Pt, GPR64sp:$Rn, simm9:$imm9), []>, Sched<[]>
{
let mayStore = 1;
let hasSideEffects = 0;
}

def FILL_PPR_FROM_ZPR_SLOT_PSEUDO :
Pseudo<(outs PPRorPNRAny:$Pt), (ins GPR64sp:$Rn, simm9:$imm9), []>, Sched<[]>
{
let mayLoad = 1;
let hasSideEffects = 0;
}

def SDTZALoadStore : SDTypeProfile<0, 3, [SDTCisInt<0>, SDTCisPtrTy<1>, SDTCisInt<2>]>;
def AArch64SMELdr : SDNode<"AArch64ISD::SME_ZA_LDR", SDTZALoadStore,
[SDNPHasChain, SDNPSideEffect, SDNPMayLoad]>;
Expand Down
Loading
Loading