[llvm] [AArch64][llvm] Implement HINT instructions as aliases (NFCI) (PR #206383)
Jonathan Thackray via llvm-commits
llvm-commits at lists.llvm.org
Sun Jun 28 18:01:24 PDT 2026
https://github.com/jthackray created https://github.com/llvm/llvm-project/pull/206383
Implement some `HINT`-space encodings as aliases of `HINT`
instead of dedicated instructions. Re-implement these isns:
* bti
* psb
* stshh
* stcph
* shuh
* tsb
Parse aliases explicitly in `AArch64AsmParser::parseHintAlias()` as they
have custom operands. Remove the (now unused) `PSB`, `BTI`, `CMH`, `PHint`
and `TSB` tablegen defs, operand classes, parser hooks and printer helpers.
Also, tighten the BTI check in the parser. The old bitmask matched non-BTI
`HINT` immediates such as `shuh/stcph`; use an exact BTI HINT encoding
check instead (`isHintSpaceBTI()`)
Add additional MC coverage for HINT aliases. The only intended functional
change is a diagnostic tweak for invalid `tsb csync` operands, which now
uses the common `HINT` alias error message codepath:
```
-//CHECK-ERROR: error: 'csync' operand expected
+//CHECK-ERROR: error: invalid operand for instruction
```
Apart from this, no other test code was modified; only new tests added.
>From 0f0ae39d34669efcdab03af6d987afc20fc5fcb4 Mon Sep 17 00:00:00 2001
From: Jonathan Thackray <jonathan.thackray at arm.com>
Date: Mon, 29 Jun 2026 01:57:57 +0100
Subject: [PATCH] [AArch64][llvm] Implement HINT instructions as aliases (NFCI)
Implement some `HINT`-space encodings as aliases of `HINT`
instead of dedicated instructions. Re-implement these isns:
* bti
* psb
* stshh
* stcph
* shuh
* tsb
Parse aliases explicitly in `AArch64AsmParser::parseHintAlias()` as they
have custom operands. Remove the (now unused) `PSB`, `BTI`, `CMH`, `PHint`
and `TSB` tablegen defs, operand classes, parser hooks and printer helpers.
Also, tighten the BTI check in the parser. The old bitmask matched non-BTI
`HINT` immediates such as `shuh/stcph`; use an exact BTI HINT encoding
check instead (`isHintSpaceBTI()`)
Add additional MC coverage for HINT aliases. The only intended functional
change is a diagnostic tweak for invalid `tsb csync` operands, which now
uses the common `HINT` alias error message codepath:
```
-//CHECK-ERROR: error: 'csync' operand expected
+//CHECK-ERROR: error: invalid operand for instruction
```
Apart from this, no other test code was modified; only new tests added.
---
llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp | 3 +-
.../lib/Target/AArch64/AArch64InstrFormats.td | 103 ----
llvm/lib/Target/AArch64/AArch64InstrInfo.td | 45 +-
.../Target/AArch64/AArch64SystemOperands.td | 152 ------
.../AArch64/AsmParser/AArch64AsmParser.cpp | 465 +++++++-----------
.../MCTargetDesc/AArch64InstPrinter.cpp | 55 +--
.../AArch64/MCTargetDesc/AArch64InstPrinter.h | 11 -
.../Target/AArch64/Utils/AArch64BaseInfo.cpp | 35 --
.../Target/AArch64/Utils/AArch64BaseInfo.h | 57 +--
.../AArch64/armv8.2a-statistical-profiling.s | 3 +
llvm/test/MC/AArch64/armv8.4a-trace-error.s | 6 +-
llvm/test/MC/AArch64/armv8.4a-trace.s | 2 +
llvm/test/MC/AArch64/armv8.5a-bti.s | 3 +
.../AArch64/armv9.6a-pcdphint-diagnostics.s | 19 +
llvm/test/MC/AArch64/armv9.6a-pcdphint.s | 10 +-
llvm/test/MC/AArch64/armv9.7a-memsys.s | 14 +-
llvm/test/MC/AArch64/basic-a64-instructions.s | 14 +-
llvm/test/MC/AArch64/ras-extension.s | 3 +
llvm/test/MC/AArch64/speculation-barriers.s | 2 +
19 files changed, 285 insertions(+), 717 deletions(-)
create mode 100644 llvm/test/MC/AArch64/armv9.6a-pcdphint-diagnostics.s
diff --git a/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp b/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
index 156c12c5ab8dd..6468f047532a5 100644
--- a/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
+++ b/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
@@ -3202,8 +3202,7 @@ void AArch64AsmPrinter::emitInstruction(const MachineInstr *MI) {
if (CurrentPatchableFunctionEntrySym &&
CurrentPatchableFunctionEntrySym == CurrentFnBegin &&
MI == &MF->front().front()) {
- int64_t Imm = MI->getOperand(0).getImm();
- if ((Imm & 32) && (Imm & 6)) {
+ if (AArch64BTIHint::isHintSpaceBTI(MI->getOperand(0).getImm())) {
MCInst Inst;
MCInstLowering.Lower(MI, Inst);
EmitToStreamer(*OutStreamer, Inst);
diff --git a/llvm/lib/Target/AArch64/AArch64InstrFormats.td b/llvm/lib/Target/AArch64/AArch64InstrFormats.td
index daf53c99988b0..c84f1c4a66ac3 100644
--- a/llvm/lib/Target/AArch64/AArch64InstrFormats.td
+++ b/llvm/lib/Target/AArch64/AArch64InstrFormats.td
@@ -1861,29 +1861,6 @@ let mayStore = 1, mayLoad = 1, hasSideEffects = 1 in
let Inst{11-5} = imm;
}
-def PHintInstOperand : AsmOperandClass {
- let Name = "PHint";
- let ParserMethod = "tryParsePHintInstOperand";
-}
-
-def phint_op : Operand<i32> {
- let ParserMatchClass = PHintInstOperand;
- let PrintMethod = "printPHintOp";
- let OperandType = "OPERAND_IMMEDIATE";
- let MIOperandInfo = (ops i32imm: $policy);
- let DecoderMethod = "DecodeUImm<3>";
-}
-
-class STSHHI
- : SimpleSystemI<0, (ins phint_op:$policy), "stshh", "\t$policy", []>,
- Sched<[WriteHint]> {
- bits<1> policy;
- let Inst{20-12} = 0b000110010;
- let Inst{11-8} = 0b0110;
- let Inst{7-6} = 0b00;
- let Inst{5} = policy;
-}
-
// System instructions taking a single literal operand which encodes into
// CRm. op2 differentiates the opcodes.
def BarrierAsmOperand : AsmOperandClass {
@@ -1952,55 +1929,6 @@ def msr_sysreg_op : Operand<i32> {
let OperandType = "OPERAND_IMMEDIATE";
}
-def PSBHintOperand : AsmOperandClass {
- let Name = "PSBHint";
- let ParserMethod = "tryParsePSBHint";
-}
-def psbhint_op : Operand<i32> {
- let ParserMatchClass = PSBHintOperand;
- let PrintMethod = "printPSBHintOp";
- let MCOperandPredicate = [{
- // Check, if operand is valid, to fix exhaustive aliasing in disassembly.
- // "psb" is an alias to "hint" only for certain values of CRm:Op2 fields.
- if (!MCOp.isImm())
- return false;
- return AArch64PSBHint::lookupPSBByEncoding(MCOp.getImm()) != nullptr;
- }];
- let OperandType = "OPERAND_IMMEDIATE";
-}
-
-def BTIHintOperand : AsmOperandClass {
- let Name = "BTIHint";
- let ParserMethod = "tryParseBTIHint";
-}
-def btihint_op : Operand<i32> {
- let ParserMatchClass = BTIHintOperand;
- let PrintMethod = "printBTIHintOp";
- let MCOperandPredicate = [{
- // "bti" is an alias to "hint" only for certain values of CRm:Op2 fields.
- if (!MCOp.isImm())
- return false;
- return AArch64BTIHint::lookupBTIByEncoding(MCOp.getImm() ^ 32) != nullptr;
- }];
- let OperandType = "OPERAND_IMMEDIATE";
-}
-
-def CMHPriorityHintOperand : AsmOperandClass {
- let Name = "CMHPriorityHint";
- let ParserMethod = "tryParseCMHPriorityHint";
-}
-
-def CMHPriorityHint_op : Operand<i32> {
- let ParserMatchClass = CMHPriorityHintOperand;
- let PrintMethod = "printCMHPriorityHintOp";
- let MCOperandPredicate = [{
- if (!MCOp.isImm())
- return false;
- return AArch64CMHPriorityHint::lookupCMHPriorityHintByEncoding(MCOp.getImm()) != nullptr;
- }];
- let OperandType = "OPERAND_IMMEDIATE";
-}
-
def TIndexHintOperand : AsmOperandClass {
let Name = "TIndexHint";
let ParserMethod = "tryParseTIndexHint";
@@ -13600,37 +13528,6 @@ multiclass SIMDThreeSameVectorFP8MatrixMul<string asm, SDPatternOperator OpNode>
}
}
-//----------------------------------------------------------------------------
-// Contention Management Hints - FEAT_CMH
-//----------------------------------------------------------------------------
-
-class SHUHInst<string asm> : I<
- (outs),
- (ins CMHPriorityHint_op:$priority),
- asm, "\t$priority", "", []>, Sched<[]> {
- bits<1> priority;
- let Inst{31-12} = 0b11010101000000110010;
- let Inst{11-8} = 0b0110;
- let Inst{7-6} = 0b01;
- let Inst{5} = priority;
- let Inst{4-0} = 0b11111;
-}
-
-multiclass SHUH<string asm> {
- def NAME : SHUHInst<asm>;
- def : InstAlias<asm, (!cast<Instruction>(NAME) 0), 1>;
-}
-
-class STCPHInst<string asm> : I<
- (outs),
- (ins),
- asm, "", "", []>, Sched<[]> {
- let Inst{31-12} = 0b11010101000000110010;
- let Inst{11-8} = 0b0110;
- let Inst{7-5} = 0b100;
- let Inst{4-0} = 0b11111;
-}
-
//---
// Permission Overlays Extension 2 (FEAT_S1POE2)
//---
diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.td b/llvm/lib/Target/AArch64/AArch64InstrInfo.td
index fc7aea5a4d5f5..e3bc8da02f153 100644
--- a/llvm/lib/Target/AArch64/AArch64InstrInfo.td
+++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.td
@@ -1552,13 +1552,13 @@ let hasSideEffects = 1, isCodeGenOnly = 1, isTerminator = 1, isBarrier = 1 in {
//===----------------------------------------------------------------------===//
def HINT : HintI<"hint">;
-def : InstAlias<"yield",(HINT 0b001)>;
-def : InstAlias<"wfe", (HINT 0b010)>;
-def : InstAlias<"wfi", (HINT 0b011)>;
-def : InstAlias<"sev", (HINT 0b100)>;
-def : InstAlias<"sevl", (HINT 0b101)>;
-def : InstAlias<"dgh", (HINT 0b110)>;
-def : InstAlias<"esb", (HINT 0b10000)>, Requires<[HasRAS]>;
+def : InstAlias<"yield",(HINT 1)>;
+def : InstAlias<"wfe", (HINT 2)>;
+def : InstAlias<"wfi", (HINT 3)>;
+def : InstAlias<"sev", (HINT 4)>;
+def : InstAlias<"sevl", (HINT 5)>;
+def : InstAlias<"dgh", (HINT 6)>;
+def : InstAlias<"esb", (HINT 16)>, Requires<[HasRAS]>;
def : InstAlias<"csdb", (HINT 20)>;
let CRm = 0b0000, hasSideEffects = 0 in
@@ -1566,20 +1566,30 @@ def NOP : SystemNoOperands<0b000, "hint\t#0">;
def : InstAlias<"nop", (NOP)>;
-def STSHH: STSHHI;
+def : InstAlias<"stshh keep", (HINT 48), 1>;
+def : InstAlias<"stshh strm", (HINT 49), 1>;
+def : InstAlias<"shuh", (HINT 50), 1>;
+def : InstAlias<"shuh ph", (HINT 51), 1>;
+def : InstAlias<"stcph", (HINT 52), 1>;
// In order to be able to write readable assembly, LLVM should accept assembly
// inputs that use Branch Target Identification mnemonics, even with BTI disabled.
// However, in order to be compatible with other assemblers (e.g. GAS), LLVM
// should not emit these mnemonics unless BTI is enabled.
def : InstAlias<"bti", (HINT 32), 0>;
-def : InstAlias<"bti $op", (HINT btihint_op:$op), 0>;
+def : InstAlias<"bti r", (HINT 32), 0>;
+def : InstAlias<"bti c", (HINT 34), 0>;
+def : InstAlias<"bti j", (HINT 36), 0>;
+def : InstAlias<"bti jc", (HINT 38), 0>;
def : InstAlias<"bti r", (HINT 32)>, Requires<[HasBTIE]>;
def : InstAlias<"bti", (HINT 32)>, Requires<[HasBTI]>;
-def : InstAlias<"bti $op", (HINT btihint_op:$op)>, Requires<[HasBTI]>;
+def : InstAlias<"bti c", (HINT 34)>, Requires<[HasBTI]>;
+def : InstAlias<"bti j", (HINT 36)>, Requires<[HasBTI]>;
+def : InstAlias<"bti jc", (HINT 38)>, Requires<[HasBTI]>;
// v8.2a Statistical Profiling extension
-def : InstAlias<"psb $op", (HINT psbhint_op:$op)>, Requires<[HasSPE]>;
+def : InstAlias<"psb csync", (HINT 17), 1>, Requires<[HasSPE]>;
+def : InstAlias<"tsb csync", (HINT 18), 1>, Requires<[HasTRACEV8_4]>;
// As far as LLVM is concerned this writes to the system's exclusive monitors.
let mayLoad = 1, mayStore = 1 in
@@ -1597,12 +1607,6 @@ def DSB : CRmSystemI<barrier_op, 0b100, "dsb",
def ISB : CRmSystemI<barrier_op, 0b110, "isb",
[(int_aarch64_isb (i32 imm32_0_15:$CRm))]>;
-def TSB : CRmSystemI<barrier_op, 0b010, "tsb", []> {
- let CRm = 0b0010;
- let Inst{12} = 0;
- let Predicates = [HasTRACEV8_4];
-}
-
def DSBnXS : CRmSystemI<barrier_nxs_op, 0b001, "dsb"> {
let CRm{1-0} = 0b11;
let Inst{9-8} = 0b10;
@@ -11931,13 +11935,6 @@ let Predicates = [HasF16F32MM] in
let Uses = [FPMR, FPCR] in
defm FMMLA : SIMDThreeSameVectorFP8MatrixMul<"fmmla", int_aarch64_neon_fmmla>;
-//===----------------------------------------------------------------------===//
-// Contention Management Hints (FEAT_CMH)
-//===----------------------------------------------------------------------===//
-
-defm SHUH : SHUH<"shuh">; // Shared Update Hint instruction
-def STCPH : STCPHInst<"stcph">; // Store Concurrent Priority Hint instruction
-
//===----------------------------------------------------------------------===//
// Permission Overlays Extension 2 (FEAT_S1POE2)
//===----------------------------------------------------------------------===//
diff --git a/llvm/lib/Target/AArch64/AArch64SystemOperands.td b/llvm/lib/Target/AArch64/AArch64SystemOperands.td
index bcd1786a0e9ea..971b57fb490f7 100644
--- a/llvm/lib/Target/AArch64/AArch64SystemOperands.td
+++ b/llvm/lib/Target/AArch64/AArch64SystemOperands.td
@@ -337,39 +337,6 @@ def lookupISBByName : SearchIndex {
def : ISB<"sy", 0xf>;
-//===----------------------------------------------------------------------===//
-// TSB (Trace synchronization barrier) instruction options.
-//===----------------------------------------------------------------------===//
-
-class TSB<string name, bits<4> encoding> {
- string Name = name;
- bits<4> Encoding;
- let Encoding = encoding;
-
- code Requires = [{ {AArch64::FeatureTRACEV8_4} }];
-}
-
-def TSBValues : GenericEnum {
- let FilterClass = "TSB";
- let NameField = "Name";
- let ValueField = "Encoding";
-}
-
-def TSBsList : GenericTable {
- let FilterClass = "TSB";
- let Fields = ["Name", "Encoding", "Requires"];
-
- let PrimaryKey = ["Encoding"];
- let PrimaryKeyName = "lookupTSBByEncoding";
-}
-
-def lookupTSBByName : SearchIndex {
- let Table = TSBsList;
- let Key = ["Name"];
-}
-
-def : TSB<"csync", 2>;
-
//===----------------------------------------------------------------------===//
// PRFM (prefetch) instruction options.
//===----------------------------------------------------------------------===//
@@ -749,87 +716,6 @@ def : SVCR<"SVCRZA", 0b010>;
def : SVCR<"SVCRSMZA", 0b011>;
}
-//===----------------------------------------------------------------------===//
-// PSB instruction options.
-//===----------------------------------------------------------------------===//
-
-class PSB<string name, bits<5> encoding> {
- string Name = name;
- bits<5> Encoding;
- let Encoding = encoding;
-}
-
-def PSBValues : GenericEnum {
- let FilterClass = "PSB";
- let NameField = "Name";
- let ValueField = "Encoding";
-}
-
-def PSBsList : GenericTable {
- let FilterClass = "PSB";
- let Fields = ["Name", "Encoding"];
-
- let PrimaryKey = ["Encoding"];
- let PrimaryKeyName = "lookupPSBByEncoding";
-}
-
-def lookupPSBByName : SearchIndex {
- let Table = PSBsList;
- let Key = ["Name"];
-}
-
-def : PSB<"csync", 0x11>;
-
-//===----------------------------------------------------------------------===//
-// BTI instruction options.
-//===----------------------------------------------------------------------===//
-
-class BTI<string name, bits<3> encoding> {
- string Name = name;
- bits<3> Encoding;
- let Encoding = encoding;
-}
-
-def BTIValues : GenericEnum {
- let FilterClass = "BTI";
- let NameField = "Name";
- let ValueField = "Encoding";
-}
-
-def BTIsList : GenericTable {
- let FilterClass = "BTI";
- let Fields = ["Name", "Encoding"];
-
- let PrimaryKey = ["Encoding"];
- let PrimaryKeyName = "lookupBTIByEncoding";
-}
-
-def lookupBTIByName : SearchIndex {
- let Table = BTIsList;
- let Key = ["Name"];
-}
-
-def : BTI<"r", 0b000>;
-def : BTI<"c", 0b010>;
-def : BTI<"j", 0b100>;
-def : BTI<"jc", 0b110>;
-
-//===----------------------------------------------------------------------===//
-// CMHPriority instruction options.
-//===----------------------------------------------------------------------===//
-
-class CMHPriorityHint<string name, bits<1> encoding> : SearchableTable {
- let SearchableFields = ["Name", "Encoding"];
- let EnumValueField = "Encoding";
-
- string Name = name;
- bits<1> Encoding;
- let Encoding = encoding;
-}
-
-def : CMHPriorityHint<"ph", 0b1>;
-
-
//===----------------------------------------------------------------------===//
// TIndex instruction options.
//===----------------------------------------------------------------------===//
@@ -2446,44 +2332,6 @@ def : RWSysReg<"ACTLRMASK_EL2", 0b11, 0b100, 0b0001, 0b0100, 0b001>;
def : RWSysReg<"ACTLRMASK_EL12", 0b11, 0b101, 0b0001, 0b0100, 0b001>;
def : RWSysReg<"ACTLRALIAS_EL1", 0b11, 0b000, 0b0001, 0b0100, 0b101>;
-//===----------------------------------------------------------------------===//
-// v9.6a PCDPHINT instruction options.
-//===----------------------------------------------------------------------===//
-
-class PHint<bits<2> op0, bits<3> op1, bits<4> crn, bits<4> crm,
- bits<3> op2, string name> {
- string Name = name;
- bits<16> Encoding;
- let Encoding{15-14} = op0;
- let Encoding{13-11} = op1;
- let Encoding{10-7} = crn;
- let Encoding{6-3} = crm;
- let Encoding{2-0} = op2;
- code Requires = [{ {} }];
-}
-
-def PHintValues : GenericEnum {
- let FilterClass = "PHint";
- let NameField = "Name";
- let ValueField = "Encoding";
-}
-
-def PHintsList : GenericTable {
- let FilterClass = "PHint";
- let Fields = ["Name", "Encoding", "Requires"];
-
- let PrimaryKey = ["Encoding"];
- let PrimaryKeyName = "lookupPHintByEncoding";
-}
-
-def lookupPHintByName : SearchIndex {
- let Table = PHintsList;
- let Key = ["Name"];
-}
-
-def KEEP : PHint<0b00, 0b000, 0b0000, 0b0000, 0b000, "keep">;
-def STRM : PHint<0b00, 0b000, 0b0000, 0b0000, 0b001, "strm">;
-
// v9.6a Realm management extension enhancements
def : RWSysReg<"GPCBW_EL3", 0b11, 0b110, 0b0010, 0b0001, 0b101>;
diff --git a/llvm/lib/Target/AArch64/AsmParser/AArch64AsmParser.cpp b/llvm/lib/Target/AArch64/AsmParser/AArch64AsmParser.cpp
index b3fda2fe849fa..d9107f031d52f 100644
--- a/llvm/lib/Target/AArch64/AsmParser/AArch64AsmParser.cpp
+++ b/llvm/lib/Target/AArch64/AsmParser/AArch64AsmParser.cpp
@@ -162,6 +162,7 @@ class AArch64AsmParser : public MCTargetAsmParser {
bool parseSysAlias(StringRef Name, SMLoc NameLoc, OperandVector &Operands);
bool parseSyslAlias(StringRef Name, SMLoc NameLoc, OperandVector &Operands);
bool parseSyspAlias(StringRef Name, SMLoc NameLoc, OperandVector &Operands);
+ bool parseHintAlias(StringRef Name, SMLoc NameLoc, OperandVector &Operands);
void createSysAlias(uint16_t Encoding, OperandVector &Operands, SMLoc S);
AArch64CC::CondCode parseCondCodeString(StringRef Cond,
std::string &Suggestion);
@@ -267,9 +268,6 @@ class AArch64AsmParser : public MCTargetAsmParser {
template <bool IsSVEPrefetch = false>
ParseStatus tryParsePrefetch(OperandVector &Operands);
ParseStatus tryParseRPRFMOperand(OperandVector &Operands);
- ParseStatus tryParsePSBHint(OperandVector &Operands);
- ParseStatus tryParseBTIHint(OperandVector &Operands);
- ParseStatus tryParseCMHPriorityHint(OperandVector &Operands);
ParseStatus tryParseTIndexHint(OperandVector &Operands);
ParseStatus tryParseAdrpLabel(OperandVector &Operands);
ParseStatus tryParseAdrLabel(OperandVector &Operands);
@@ -300,7 +298,24 @@ class AArch64AsmParser : public MCTargetAsmParser {
ParseStatus tryParseGPR64x8(OperandVector &Operands);
ParseStatus tryParseImmRange(OperandVector &Operands);
template <int> ParseStatus tryParseAdjImm0_63(OperandVector &Operands);
- ParseStatus tryParsePHintInstOperand(OperandVector &Operands);
+ template <typename LookupFn, typename CreateFn>
+ ParseStatus tryParseNamedHintOperand(OperandVector &Operands,
+ LookupFn LookupByName,
+ CreateFn CreateOperand) {
+ SMLoc S = getLoc();
+ const AsmToken &Tok = getTok();
+ if (Tok.isNot(AsmToken::Identifier))
+ return TokError("invalid operand for instruction");
+
+ auto Entry = LookupByName(Tok.getString());
+ if (!Entry)
+ return TokError("invalid operand for instruction");
+
+ Operands.push_back(
+ CreateOperand(Entry->Encoding, Tok.getString(), S, getContext()));
+ Lex(); // Eat identifier token.
+ return ParseStatus::Success;
+ }
public:
enum AArch64MatchResultTy {
@@ -372,10 +387,6 @@ class AArch64Operand : public MCParsedAsmOperand {
k_ShiftExtend,
k_FPImm,
k_Barrier,
- k_PSBHint,
- k_PHint,
- k_BTIHint,
- k_CMHPriorityHint,
k_TIndexHint,
} Kind;
@@ -491,31 +502,12 @@ class AArch64Operand : public MCParsedAsmOperand {
unsigned Val;
};
- struct PSBHintOp {
- const char *Data;
- unsigned Length;
- unsigned Val;
- };
- struct PHintOp {
- const char *Data;
- unsigned Length;
- unsigned Val;
- };
- struct BTIHintOp {
- const char *Data;
- unsigned Length;
- unsigned Val;
- };
- struct CMHPriorityHintOp {
- const char *Data;
- unsigned Length;
- unsigned Val;
- };
- struct TIndexHintOp {
+ struct NamedHintOp {
const char *Data;
unsigned Length;
unsigned Val;
};
+ using TIndexHintOp = NamedHintOp;
struct SVCROp {
const char *Data;
@@ -524,28 +516,24 @@ class AArch64Operand : public MCParsedAsmOperand {
};
union {
- struct TokOp Tok;
- struct RegOp Reg;
- struct MatrixRegOp MatrixReg;
- struct MatrixTileListOp MatrixTileList;
- struct VectorListOp VectorList;
- struct VectorIndexOp VectorIndex;
- struct ImmOp Imm;
- struct ShiftedImmOp ShiftedImm;
- struct ImmRangeOp ImmRange;
- struct CondCodeOp CondCode;
- struct FPImmOp FPImm;
- struct BarrierOp Barrier;
- struct SysRegOp SysReg;
- struct SysCRImmOp SysCRImm;
- struct PrefetchOp Prefetch;
- struct PSBHintOp PSBHint;
- struct PHintOp PHint;
- struct BTIHintOp BTIHint;
- struct CMHPriorityHintOp CMHPriorityHint;
- struct TIndexHintOp TIndexHint;
- struct ShiftExtendOp ShiftExtend;
- struct SVCROp SVCR;
+ TokOp Tok;
+ RegOp Reg;
+ MatrixRegOp MatrixReg;
+ MatrixTileListOp MatrixTileList;
+ VectorListOp VectorList;
+ VectorIndexOp VectorIndex;
+ ImmOp Imm;
+ ShiftedImmOp ShiftedImm;
+ ImmRangeOp ImmRange;
+ CondCodeOp CondCode;
+ FPImmOp FPImm;
+ BarrierOp Barrier;
+ SysRegOp SysReg;
+ SysCRImmOp SysCRImm;
+ PrefetchOp Prefetch;
+ TIndexHintOp TIndexHint;
+ ShiftExtendOp ShiftExtend;
+ SVCROp SVCR;
};
// Keep the MCContext around as the MCExprs may need manipulated during
@@ -605,18 +593,6 @@ class AArch64Operand : public MCParsedAsmOperand {
case k_Prefetch:
Prefetch = o.Prefetch;
break;
- case k_PSBHint:
- PSBHint = o.PSBHint;
- break;
- case k_PHint:
- PHint = o.PHint;
- break;
- case k_BTIHint:
- BTIHint = o.BTIHint;
- break;
- case k_CMHPriorityHint:
- CMHPriorityHint = o.CMHPriorityHint;
- break;
case k_TIndexHint:
TIndexHint = o.TIndexHint;
break;
@@ -764,46 +740,6 @@ class AArch64Operand : public MCParsedAsmOperand {
return Prefetch.Val;
}
- unsigned getPSBHint() const {
- assert(Kind == k_PSBHint && "Invalid access!");
- return PSBHint.Val;
- }
-
- unsigned getPHint() const {
- assert(Kind == k_PHint && "Invalid access!");
- return PHint.Val;
- }
-
- StringRef getPSBHintName() const {
- assert(Kind == k_PSBHint && "Invalid access!");
- return StringRef(PSBHint.Data, PSBHint.Length);
- }
-
- StringRef getPHintName() const {
- assert(Kind == k_PHint && "Invalid access!");
- return StringRef(PHint.Data, PHint.Length);
- }
-
- unsigned getBTIHint() const {
- assert(Kind == k_BTIHint && "Invalid access!");
- return BTIHint.Val;
- }
-
- StringRef getBTIHintName() const {
- assert(Kind == k_BTIHint && "Invalid access!");
- return StringRef(BTIHint.Data, BTIHint.Length);
- }
-
- unsigned getCMHPriorityHint() const {
- assert(Kind == k_CMHPriorityHint && "Invalid access!");
- return CMHPriorityHint.Val;
- }
-
- StringRef getCMHPriorityHintName() const {
- assert(Kind == k_CMHPriorityHint && "Invalid access!");
- return StringRef(CMHPriorityHint.Data, CMHPriorityHint.Length);
- }
-
unsigned getTIndexHint() const {
assert(Kind == k_TIndexHint && "Invalid access!");
return TIndexHint.Val;
@@ -1553,10 +1489,6 @@ class AArch64Operand : public MCParsedAsmOperand {
}
bool isSysCR() const { return Kind == k_SysCR; }
bool isPrefetch() const { return Kind == k_Prefetch; }
- bool isPSBHint() const { return Kind == k_PSBHint; }
- bool isPHint() const { return Kind == k_PHint; }
- bool isBTIHint() const { return Kind == k_BTIHint; }
- bool isCMHPriorityHint() const { return Kind == k_CMHPriorityHint; }
bool isTIndexHint() const { return Kind == k_TIndexHint; }
bool isShiftExtend() const { return Kind == k_ShiftExtend; }
bool isShifter() const {
@@ -2229,26 +2161,6 @@ class AArch64Operand : public MCParsedAsmOperand {
Inst.addOperand(MCOperand::createImm(getPrefetch()));
}
- void addPSBHintOperands(MCInst &Inst, unsigned N) const {
- assert(N == 1 && "Invalid number of operands!");
- Inst.addOperand(MCOperand::createImm(getPSBHint()));
- }
-
- void addPHintOperands(MCInst &Inst, unsigned N) const {
- assert(N == 1 && "Invalid number of operands!");
- Inst.addOperand(MCOperand::createImm(getPHint()));
- }
-
- void addBTIHintOperands(MCInst &Inst, unsigned N) const {
- assert(N == 1 && "Invalid number of operands!");
- Inst.addOperand(MCOperand::createImm(getBTIHint()));
- }
-
- void addCMHPriorityHintOperands(MCInst &Inst, unsigned N) const {
- assert(N == 1 && "Invalid number of operands!");
- Inst.addOperand(MCOperand::createImm(getCMHPriorityHint()));
- }
-
void addTIndexHintOperands(MCInst &Inst, unsigned N) const {
assert(N == 1 && "Invalid number of operands!");
Inst.addOperand(MCOperand::createImm(getTIndexHint()));
@@ -2542,12 +2454,20 @@ class AArch64Operand : public MCParsedAsmOperand {
return Op;
}
+ struct IdentityHintEncoding {
+ unsigned operator()(unsigned Val) const { return Val; }
+ };
+
+ template <KindTy Kind, NamedHintOp AArch64Operand::*Member,
+ typename Encode = IdentityHintEncoding>
static std::unique_ptr<AArch64Operand>
- CreatePHintInst(unsigned Val, StringRef Str, SMLoc S, MCContext &Ctx) {
- auto Op = std::make_unique<AArch64Operand>(k_PHint, Ctx);
- Op->PHint.Val = Val;
- Op->PHint.Data = Str.data();
- Op->PHint.Length = Str.size();
+ CreateNamedHintOperand(unsigned Val, StringRef Str, SMLoc S, MCContext &Ctx,
+ Encode EncodeVal = {}) {
+ auto Op = std::make_unique<AArch64Operand>(Kind, Ctx);
+ auto &Hint = Op.get()->*Member;
+ Hint.Val = EncodeVal(Val);
+ Hint.Data = Str.data();
+ Hint.Length = Str.size();
Op->StartLoc = S;
Op->EndLoc = S;
return Op;
@@ -2568,45 +2488,8 @@ class AArch64Operand : public MCParsedAsmOperand {
MCContext &Ctx) {
auto Op = std::make_unique<AArch64Operand>(k_Prefetch, Ctx);
Op->Prefetch.Val = Val;
- Op->Barrier.Data = Str.data();
- Op->Barrier.Length = Str.size();
- Op->StartLoc = S;
- Op->EndLoc = S;
- return Op;
- }
-
- static std::unique_ptr<AArch64Operand> CreatePSBHint(unsigned Val,
- StringRef Str,
- SMLoc S,
- MCContext &Ctx) {
- auto Op = std::make_unique<AArch64Operand>(k_PSBHint, Ctx);
- Op->PSBHint.Val = Val;
- Op->PSBHint.Data = Str.data();
- Op->PSBHint.Length = Str.size();
- Op->StartLoc = S;
- Op->EndLoc = S;
- return Op;
- }
-
- static std::unique_ptr<AArch64Operand> CreateBTIHint(unsigned Val,
- StringRef Str,
- SMLoc S,
- MCContext &Ctx) {
- auto Op = std::make_unique<AArch64Operand>(k_BTIHint, Ctx);
- Op->BTIHint.Val = Val | 32;
- Op->BTIHint.Data = Str.data();
- Op->BTIHint.Length = Str.size();
- Op->StartLoc = S;
- Op->EndLoc = S;
- return Op;
- }
-
- static std::unique_ptr<AArch64Operand>
- CreateCMHPriorityHint(unsigned Val, StringRef Str, SMLoc S, MCContext &Ctx) {
- auto Op = std::make_unique<AArch64Operand>(k_CMHPriorityHint, Ctx);
- Op->CMHPriorityHint.Val = Val;
- Op->CMHPriorityHint.Data = Str.data();
- Op->CMHPriorityHint.Length = Str.size();
+ Op->Prefetch.Data = Str.data();
+ Op->Prefetch.Length = Str.size();
Op->StartLoc = S;
Op->EndLoc = S;
return Op;
@@ -2614,13 +2497,8 @@ class AArch64Operand : public MCParsedAsmOperand {
static std::unique_ptr<AArch64Operand>
CreateTIndexHint(unsigned Val, StringRef Str, SMLoc S, MCContext &Ctx) {
- auto Op = std::make_unique<AArch64Operand>(k_TIndexHint, Ctx);
- Op->TIndexHint.Val = Val;
- Op->TIndexHint.Data = Str.data();
- Op->TIndexHint.Length = Str.size();
- Op->StartLoc = S;
- Op->EndLoc = S;
- return Op;
+ return CreateNamedHintOperand<k_TIndexHint, &AArch64Operand::TIndexHint>(
+ Val, Str, S, Ctx);
}
static std::unique_ptr<AArch64Operand>
@@ -2724,18 +2602,6 @@ void AArch64Operand::print(raw_ostream &OS, const MCAsmInfo &MAI) const {
OS << "<prfop invalid #" << getPrefetch() << ">";
break;
}
- case k_PSBHint:
- OS << getPSBHintName();
- break;
- case k_PHint:
- OS << getPHintName();
- break;
- case k_BTIHint:
- OS << getBTIHintName();
- break;
- case k_CMHPriorityHint:
- OS << getCMHPriorityHintName();
- break;
case k_TIndexHint:
OS << getTIndexHintName();
break;
@@ -3297,23 +3163,6 @@ ParseStatus AArch64AsmParser::tryParsePrefetch(OperandVector &Operands) {
return ParseStatus::Success;
}
-/// tryParsePSBHint - Try to parse a PSB operand, mapped to Hint command
-ParseStatus AArch64AsmParser::tryParsePSBHint(OperandVector &Operands) {
- SMLoc S = getLoc();
- const AsmToken &Tok = getTok();
- if (Tok.isNot(AsmToken::Identifier))
- return TokError("invalid operand for instruction");
-
- auto PSB = AArch64PSBHint::lookupPSBByName(Tok.getString());
- if (!PSB)
- return TokError("invalid operand for instruction");
-
- Operands.push_back(AArch64Operand::CreatePSBHint(
- PSB->Encoding, Tok.getString(), S, getContext()));
- Lex(); // Eat identifier token.
- return ParseStatus::Success;
-}
-
ParseStatus AArch64AsmParser::tryParseSyspXzrPair(OperandVector &Operands) {
SMLoc StartLoc = getLoc();
@@ -3347,56 +3196,11 @@ ParseStatus AArch64AsmParser::tryParseSyspXzrPair(OperandVector &Operands) {
return ParseStatus::Success;
}
-/// tryParseBTIHint - Try to parse a BTI operand, mapped to Hint command
-ParseStatus AArch64AsmParser::tryParseBTIHint(OperandVector &Operands) {
- SMLoc S = getLoc();
- const AsmToken &Tok = getTok();
- if (Tok.isNot(AsmToken::Identifier))
- return TokError("invalid operand for instruction");
-
- auto BTI = AArch64BTIHint::lookupBTIByName(Tok.getString());
- if (!BTI)
- return TokError("invalid operand for instruction");
-
- Operands.push_back(AArch64Operand::CreateBTIHint(
- BTI->Encoding, Tok.getString(), S, getContext()));
- Lex(); // Eat identifier token.
- return ParseStatus::Success;
-}
-
-/// tryParseCMHPriorityHint - Try to parse a CMHPriority operand
-ParseStatus AArch64AsmParser::tryParseCMHPriorityHint(OperandVector &Operands) {
- SMLoc S = getLoc();
- const AsmToken &Tok = getTok();
- if (Tok.isNot(AsmToken::Identifier))
- return TokError("invalid operand for instruction");
-
- auto CMHPriority =
- AArch64CMHPriorityHint::lookupCMHPriorityHintByName(Tok.getString());
- if (!CMHPriority)
- return TokError("invalid operand for instruction");
-
- Operands.push_back(AArch64Operand::CreateCMHPriorityHint(
- CMHPriority->Encoding, Tok.getString(), S, getContext()));
- Lex(); // Eat identifier token.
- return ParseStatus::Success;
-}
-
/// tryParseTIndexHint - Try to parse a TIndex operand
ParseStatus AArch64AsmParser::tryParseTIndexHint(OperandVector &Operands) {
- SMLoc S = getLoc();
- const AsmToken &Tok = getTok();
- if (Tok.isNot(AsmToken::Identifier))
- return TokError("invalid operand for instruction");
-
- auto TIndex = AArch64TIndexHint::lookupTIndexByName(Tok.getString());
- if (!TIndex)
- return TokError("invalid operand for instruction");
-
- Operands.push_back(AArch64Operand::CreateTIndexHint(
- TIndex->Encoding, Tok.getString(), S, getContext()));
- Lex(); // Eat identifier token.
- return ParseStatus::Success;
+ return tryParseNamedHintOperand(Operands,
+ AArch64TIndexHint::lookupTIndexByName,
+ AArch64Operand::CreateTIndexHint);
}
/// tryParseAdrpLabel - Parse and validate a source label for the ADRP
@@ -4291,12 +4095,127 @@ bool AArch64AsmParser::parseSyspAlias(StringRef Name, SMLoc NameLoc,
return false;
}
+/// parseHintAlias - Some named HINT encodings have aliases. Parse them
+/// specially so that we create a HINT MCInst.
+bool AArch64AsmParser::parseHintAlias(StringRef Name, SMLoc NameLoc,
+ OperandVector &Operands) {
+ if (Name.contains('.'))
+ return TokError("invalid operand");
+
+ enum class HintAliasKind { Invalid, BTI, PSB, SHUH, STCPH, STSHH, TSB };
+ HintAliasKind Kind = StringSwitch<HintAliasKind>(Name)
+ .Case("bti", HintAliasKind::BTI)
+ .Case("psb", HintAliasKind::PSB)
+ .Case("shuh", HintAliasKind::SHUH)
+ .Case("stcph", HintAliasKind::STCPH)
+ .Case("stshh", HintAliasKind::STSHH)
+ .Case("tsb", HintAliasKind::TSB)
+ .Default(HintAliasKind::Invalid);
+ if (Kind == HintAliasKind::Invalid)
+ llvm_unreachable("unknown HINT alias");
+
+ Mnemonic = Name;
+ Operands.push_back(
+ AArch64Operand::CreateToken("hint", NameLoc, getContext()));
+
+ const AsmToken &Tok = getTok();
+ SMLoc S = Tok.getLoc();
+ unsigned Imm;
+
+ switch (Kind) {
+ case HintAliasKind::Invalid:
+ llvm_unreachable("unknown HINT alias");
+ case HintAliasKind::STCPH:
+ Imm = 52;
+ break;
+ case HintAliasKind::BTI:
+ if (Tok.is(AsmToken::EndOfStatement)) {
+ Imm = 32;
+ } else if (Tok.is(AsmToken::Identifier)) {
+ StringRef Op = Tok.getString();
+ if (Op == "r")
+ Imm = 32;
+ else if (Op == "c")
+ Imm = 34;
+ else if (Op == "j")
+ Imm = 36;
+ else if (Op == "jc")
+ Imm = 38;
+ else
+ return TokError("invalid operand for instruction");
+ Lex(); // Eat operand.
+ } else {
+ return TokError("invalid operand for instruction");
+ }
+ break;
+ case HintAliasKind::SHUH:
+ if (Tok.is(AsmToken::EndOfStatement)) {
+ Imm = 50;
+ } else if (Tok.is(AsmToken::Identifier) && Tok.getString() == "ph") {
+ Imm = 51;
+ Lex(); // Eat operand.
+ } else {
+ return TokError("invalid operand for instruction");
+ }
+ break;
+ case HintAliasKind::PSB:
+ case HintAliasKind::STSHH:
+ case HintAliasKind::TSB: {
+ if ((Kind == HintAliasKind::PSB || Kind == HintAliasKind::TSB) &&
+ Tok.is(AsmToken::EndOfStatement))
+ return Error(NameLoc, "too few operands for instruction");
+
+ if (Tok.isNot(AsmToken::Identifier)) {
+ return TokError("invalid operand for instruction");
+ }
+
+ StringRef Op = Tok.getString();
+ switch (Kind) {
+ case HintAliasKind::STSHH:
+ if (Op == "keep")
+ Imm = 48;
+ else if (Op == "strm")
+ Imm = 49;
+ else
+ return TokError("invalid operand for instruction");
+ break;
+ case HintAliasKind::PSB:
+ if (Op != "csync")
+ return TokError("invalid operand for instruction");
+ if (!getSTI().hasFeature(AArch64::FeatureAll) &&
+ !getSTI().hasFeature(AArch64::FeatureSPE))
+ return TokError("instruction requires: spe");
+ Imm = 17;
+ break;
+ case HintAliasKind::TSB:
+ if (Op != "csync")
+ return TokError("invalid operand for instruction");
+ if (!getSTI().hasFeature(AArch64::FeatureAll) &&
+ !getSTI().hasFeature(AArch64::FeatureTRACEV8_4))
+ return TokError("instruction requires: tracev8.4");
+ Imm = 18;
+ break;
+ default:
+ llvm_unreachable("unexpected HINT alias kind");
+ }
+ Lex(); // Eat operand.
+ break;
+ }
+ }
+
+ Operands.push_back(AArch64Operand::CreateImm(
+ MCConstantExpr::create(Imm, getContext()), S, getLoc(), getContext()));
+
+ if (parseToken(AsmToken::EndOfStatement, "unexpected token in argument list"))
+ return true;
+
+ return false;
+}
+
ParseStatus AArch64AsmParser::tryParseBarrierOperand(OperandVector &Operands) {
MCAsmParser &Parser = getParser();
const AsmToken &Tok = getTok();
- if (Mnemonic == "tsb" && Tok.isNot(AsmToken::Identifier))
- return TokError("'csync' operand expected");
if (parseOptionalToken(AsmToken::Hash) || Tok.is(AsmToken::Integer)) {
// Immediate operand.
const MCExpr *ImmVal;
@@ -4328,15 +4247,11 @@ ParseStatus AArch64AsmParser::tryParseBarrierOperand(OperandVector &Operands) {
return TokError("invalid operand for instruction");
StringRef Operand = Tok.getString();
- auto TSB = AArch64TSB::lookupTSBByName(Operand);
auto DB = AArch64DB::lookupDBByName(Operand);
// The only valid named option for ISB is 'sy'
if (Mnemonic == "isb" && (!DB || DB->Encoding != AArch64DB::sy))
return TokError("'sy' or #imm operand expected");
- // The only valid named option for TSB is 'csync'
- if (Mnemonic == "tsb" && (!TSB || TSB->Encoding != AArch64TSB::csync))
- return TokError("'csync' operand expected");
- if (!DB && !TSB) {
+ if (!DB) {
if (Mnemonic == "dsb") {
// This case is a no match here, but it might be matched by the nXS
// variant.
@@ -4346,8 +4261,8 @@ ParseStatus AArch64AsmParser::tryParseBarrierOperand(OperandVector &Operands) {
}
Operands.push_back(AArch64Operand::CreateBarrier(
- DB ? DB->Encoding : TSB->Encoding, Tok.getString(), getLoc(),
- getContext(), false /*hasnXSModifier*/));
+ DB->Encoding, Tok.getString(), getLoc(), getContext(),
+ false /*hasnXSModifier*/));
Lex(); // Consume the option
return ParseStatus::Success;
@@ -4434,23 +4349,6 @@ ParseStatus AArch64AsmParser::tryParseSysReg(OperandVector &Operands) {
return ParseStatus::Success;
}
-ParseStatus
-AArch64AsmParser::tryParsePHintInstOperand(OperandVector &Operands) {
- SMLoc S = getLoc();
- const AsmToken &Tok = getTok();
- if (Tok.isNot(AsmToken::Identifier))
- return TokError("invalid operand for instruction");
-
- auto PH = AArch64PHint::lookupPHintByName(Tok.getString());
- if (!PH)
- return TokError("invalid operand for instruction");
-
- Operands.push_back(AArch64Operand::CreatePHintInst(
- PH->Encoding, Tok.getString(), S, getContext()));
- Lex(); // Eat identifier token.
- return ParseStatus::Success;
-}
-
/// tryParseNeonVectorRegister - Parse a vector register operand.
bool AArch64AsmParser::tryParseNeonVectorRegister(OperandVector &Operands) {
if (getTok().isNot(AsmToken::Identifier))
@@ -5522,6 +5420,11 @@ bool AArch64AsmParser::parseInstruction(ParseInstructionInfo &Info,
if (Head == "tlbip")
return parseSyspAlias(Head, NameLoc, Operands);
+ // These mnemonics are aliases for HINT instructions.
+ if (Head == "bti" || Head == "stshh" || Head == "psb" || Head == "tsb" ||
+ Head == "shuh" || Head == "stcph")
+ return parseHintAlias(Name, NameLoc, Operands);
+
Operands.push_back(AArch64Operand::CreateToken(Head, NameLoc, getContext()));
Mnemonic = Head;
diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.cpp b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.cpp
index 2783b559c8f5c..b6cb621685ba0 100644
--- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.cpp
+++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.cpp
@@ -1571,50 +1571,15 @@ void AArch64InstPrinter::printPrefetchOp(const MCInst *MI, unsigned OpNum,
markup(O, Markup::Immediate) << '#' << formatImm(prfop);
}
-void AArch64InstPrinter::printPSBHintOp(const MCInst *MI, unsigned OpNum,
- const MCSubtargetInfo &STI,
- raw_ostream &O) {
- unsigned psbhintop = MI->getOperand(OpNum).getImm();
- auto PSB = AArch64PSBHint::lookupPSBByEncoding(psbhintop);
- if (PSB)
- O << AArch64PSBHint::getPSBStr(PSB->Name);
- else
- markup(O, Markup::Immediate) << '#' << formatImm(psbhintop);
-}
-
-void AArch64InstPrinter::printBTIHintOp(const MCInst *MI, unsigned OpNum,
- const MCSubtargetInfo &STI,
- raw_ostream &O) {
- unsigned btihintop = MI->getOperand(OpNum).getImm() ^ 32;
- auto BTI = AArch64BTIHint::lookupBTIByEncoding(btihintop);
- if (BTI)
- O << AArch64BTIHint::getBTIStr(BTI->Name);
- else
- markup(O, Markup::Immediate) << '#' << formatImm(btihintop);
-}
-
-void AArch64InstPrinter::printCMHPriorityHintOp(const MCInst *MI,
- unsigned OpNum,
- const MCSubtargetInfo &STI,
- raw_ostream &O) {
- unsigned priorityhint_op = MI->getOperand(OpNum).getImm();
- auto PHint =
- AArch64CMHPriorityHint::lookupCMHPriorityHintByEncoding(priorityhint_op);
- if (PHint)
- O << AArch64CMHPriorityHint::getCMHPriorityHintStr(PHint->Name);
- else
- markup(O, Markup::Immediate) << '#' << formatImm(priorityhint_op);
-}
-
void AArch64InstPrinter::printTIndexHintOp(const MCInst *MI, unsigned OpNum,
const MCSubtargetInfo &STI,
raw_ostream &O) {
- unsigned tindexhintop = MI->getOperand(OpNum).getImm();
- auto TIndex = AArch64TIndexHint::lookupTIndexByEncoding(tindexhintop);
+ unsigned TIndexHintOp = MI->getOperand(OpNum).getImm();
+ auto TIndex = AArch64TIndexHint::lookupTIndexByEncoding(TIndexHintOp);
if (TIndex)
O << AArch64TIndexHint::getTIndexStr(TIndex->Name);
else
- markup(O, Markup::Immediate) << '#' << formatImm(tindexhintop);
+ markup(O, Markup::Immediate) << '#' << formatImm(TIndexHintOp);
}
void AArch64InstPrinter::printFPImmOperand(const MCInst *MI, unsigned OpNum,
@@ -1966,9 +1931,6 @@ void AArch64InstPrinter::printBarrierOption(const MCInst *MI, unsigned OpNo,
if (Opcode == AArch64::ISB) {
auto ISB = AArch64ISB::lookupISBByEncoding(Val);
Name = ISB ? AArch64ISB::getISBStr(ISB->Name) : "";
- } else if (Opcode == AArch64::TSB) {
- auto TSB = AArch64TSB::lookupTSBByEncoding(Val);
- Name = TSB ? AArch64TSB::getTSBStr(TSB->Name) : "";
} else {
auto DB = AArch64DB::lookupDBByEncoding(Val);
Name = DB ? AArch64DB::getDBStr(DB->Name) : "";
@@ -2261,14 +2223,3 @@ void AArch64InstPrinter::printSyspXzrPair(const MCInst *MI, unsigned OpNum,
"MC representation of SyspXzrPair should be XZR");
O << getRegisterName(Reg) << ", " << getRegisterName(Reg);
}
-
-void AArch64InstPrinter::printPHintOp(const MCInst *MI, unsigned OpNum,
- const MCSubtargetInfo &STI,
- raw_ostream &O) {
- unsigned Op = MI->getOperand(OpNum).getImm();
- auto PH = AArch64PHint::lookupPHintByEncoding(Op);
- if (PH)
- O << AArch64PHint::getPHintStr(PH->Name);
- else
- markup(O, Markup::Immediate) << '#' << formatImm(Op);
-}
diff --git a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.h b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.h
index 3f7a3b4b0667b..bea14c14ae1f6 100644
--- a/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.h
+++ b/llvm/lib/Target/AArch64/MCTargetDesc/AArch64InstPrinter.h
@@ -147,15 +147,6 @@ class AArch64InstPrinter : public MCInstPrinter {
void printRPRFMOperand(const MCInst *MI, unsigned OpNum,
const MCSubtargetInfo &STI, raw_ostream &O);
- void printPSBHintOp(const MCInst *MI, unsigned OpNum,
- const MCSubtargetInfo &STI, raw_ostream &O);
-
- void printBTIHintOp(const MCInst *MI, unsigned OpNum,
- const MCSubtargetInfo &STI, raw_ostream &O);
-
- void printCMHPriorityHintOp(const MCInst *MI, unsigned OpNum,
- const MCSubtargetInfo &STI, raw_ostream &O);
-
void printTIndexHintOp(const MCInst *MI, unsigned OpNum,
const MCSubtargetInfo &STI, raw_ostream &O);
@@ -245,8 +236,6 @@ class AArch64InstPrinter : public MCInstPrinter {
template <unsigned ImmIs0, unsigned ImmIs1>
void printExactFPImm(const MCInst *MI, unsigned OpNum,
const MCSubtargetInfo &STI, raw_ostream &O);
- void printPHintOp(const MCInst *MI, unsigned OpNum,
- const MCSubtargetInfo &STI, raw_ostream &O);
};
class AArch64AppleInstPrinter : public AArch64InstPrinter {
diff --git a/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.cpp b/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.cpp
index c2fccc91cfec9..9d94703ef2c8f 100644
--- a/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.cpp
+++ b/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.cpp
@@ -59,13 +59,6 @@ namespace llvm {
}
}
-namespace llvm {
- namespace AArch64TSB {
-#define GET_TSBsList_IMPL
-#include "AArch64GenSystemOperands.inc"
- }
-}
-
namespace llvm {
namespace AArch64PRFM {
#define GET_PRFMsList_IMPL
@@ -117,34 +110,6 @@ namespace llvm {
}
}
-namespace llvm {
- namespace AArch64PSBHint {
-#define GET_PSBsList_IMPL
-#include "AArch64GenSystemOperands.inc"
- }
-}
-
-namespace llvm {
-namespace AArch64PHint {
-#define GET_PHintsList_IMPL
-#include "AArch64GenSystemOperands.inc"
-} // namespace AArch64PHint
-} // namespace llvm
-
-namespace llvm {
- namespace AArch64BTIHint {
-#define GET_BTIsList_IMPL
-#include "AArch64GenSystemOperands.inc"
- }
-}
-
-namespace llvm {
-namespace AArch64CMHPriorityHint {
-#define GET_CMHPRIORITYHINT_IMPL
-#include "AArch64GenSystemOperands.inc"
-} // namespace AArch64CMHPriorityHint
-} // namespace llvm
-
namespace llvm {
namespace AArch64TIndexHint {
#define GET_TINDEX_IMPL
diff --git a/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.h b/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.h
index bd7faa42449b7..562ed6a901e4a 100644
--- a/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.h
+++ b/llvm/lib/Target/AArch64/Utils/AArch64BaseInfo.h
@@ -546,15 +546,6 @@ namespace AArch64ISB {
#include "AArch64GenSystemOperands.inc"
}
-namespace AArch64TSB {
- struct TSB : SysAlias {
- using SysAlias::SysAlias;
- };
-#define GET_TSBValues_DECL
-#define GET_TSBsList_DECL
-#include "AArch64GenSystemOperands.inc"
-}
-
namespace AArch64PRFM {
struct PRFM : SysAlias {
using SysAlias::SysAlias;
@@ -705,51 +696,15 @@ namespace AArch64PState {
#include "AArch64GenSystemOperands.inc"
}
-namespace AArch64PSBHint {
- struct PSB : SysAlias {
- using SysAlias::SysAlias;
- };
-#define GET_PSBValues_DECL
-#define GET_PSBsList_DECL
-#include "AArch64GenSystemOperands.inc"
-}
-
-namespace AArch64PHint {
-struct PHint {
- StringTable::Offset Name;
- unsigned Encoding;
- FeatureBitset FeaturesRequired;
-
- bool haveFeatures(FeatureBitset ActiveFeatures) const {
- return ActiveFeatures[llvm::AArch64::FeatureAll] ||
- (FeaturesRequired & ActiveFeatures) == FeaturesRequired;
- }
-};
-
-#define GET_PHintValues_DECL
-#define GET_PHintsList_DECL
-#include "AArch64GenSystemOperands.inc"
-
-const PHint *lookupPHintByName(StringRef);
-const PHint *lookupPHintByEncoding(uint16_t);
-} // namespace AArch64PHint
-
namespace AArch64BTIHint {
- struct BTI : SysAlias {
- using SysAlias::SysAlias;
- };
-#define GET_BTIValues_DECL
-#define GET_BTIsList_DECL
-#include "AArch64GenSystemOperands.inc"
+inline static bool isBTIEncoding(int64_t Enc) {
+ return Enc == 0 || Enc == 2 || Enc == 4 || Enc == 6;
}
-namespace AArch64CMHPriorityHint {
-struct CMHPriorityHint : SysAlias {
- using SysAlias::SysAlias;
-};
-#define GET_CMHPRIORITYHINT_DECL
-#include "AArch64GenSystemOperands.inc"
-} // namespace AArch64CMHPriorityHint
+inline static bool isHintSpaceBTI(int64_t Imm) {
+ return Imm >= 32 && Imm < 64 && isBTIEncoding(Imm - 32);
+}
+} // namespace AArch64BTIHint
namespace AArch64TIndexHint {
struct TIndex : SysAlias {
diff --git a/llvm/test/MC/AArch64/armv8.2a-statistical-profiling.s b/llvm/test/MC/AArch64/armv8.2a-statistical-profiling.s
index 25fff6ac56ae9..006e24d4f8255 100644
--- a/llvm/test/MC/AArch64/armv8.2a-statistical-profiling.s
+++ b/llvm/test/MC/AArch64/armv8.2a-statistical-profiling.s
@@ -9,6 +9,9 @@
// NO_SPE_OUT-NOT: mrs
// NO_SPE_OUT-NOT: psb
+ hint #17
+// CHECK: psb csync // encoding: [0x3f,0x22,0x03,0xd5]
+
psb csync
// CHECK: psb csync // encoding: [0x3f,0x22,0x03,0xd5]
// NO_SPE: instruction requires: spe
diff --git a/llvm/test/MC/AArch64/armv8.4a-trace-error.s b/llvm/test/MC/AArch64/armv8.4a-trace-error.s
index 99b61280a3180..ec166c715b0ea 100644
--- a/llvm/test/MC/AArch64/armv8.4a-trace-error.s
+++ b/llvm/test/MC/AArch64/armv8.4a-trace-error.s
@@ -12,12 +12,12 @@ tsb 0
//CHECK-ERROR: error: too few operands for instruction
//CHECK-ERROR: tsb
//CHECK-ERROR: ^
-//CHECK-ERROR: error: 'csync' operand expected
+//CHECK-ERROR: error: invalid operand for instruction
//CHECK-ERROR: tsb foo
//CHECK-ERROR: ^
-//CHECK-ERROR: error: 'csync' operand expected
+//CHECK-ERROR: error: invalid operand for instruction
//CHECK-ERROR: tsb #0
//CHECK-ERROR: ^
-//CHECK-ERROR: error: 'csync' operand expected
+//CHECK-ERROR: error: invalid operand for instruction
//CHECK-ERROR: tsb 0
//CHECK-ERROR: ^
diff --git a/llvm/test/MC/AArch64/armv8.4a-trace.s b/llvm/test/MC/AArch64/armv8.4a-trace.s
index a7ce371a0a0b6..0351e20f3fd66 100644
--- a/llvm/test/MC/AArch64/armv8.4a-trace.s
+++ b/llvm/test/MC/AArch64/armv8.4a-trace.s
@@ -22,6 +22,7 @@ mrs x0, TRFCR_EL1
mrs x0, TRFCR_EL2
mrs x0, TRFCR_EL12
+hint #18
tsb csync
//CHECK: msr TRFCR_EL1, x0 // encoding: [0x20,0x12,0x18,0xd5]
@@ -33,6 +34,7 @@ tsb csync
//CHECK: mrs x0, TRFCR_EL12 // encoding: [0x20,0x12,0x3d,0xd5]
//CHECK: tsb csync // encoding: [0x5f,0x22,0x03,0xd5]
+//CHECK-NEXT: tsb csync // encoding: [0x5f,0x22,0x03,0xd5]
//CHECK-ERROR: error: expected writable system register or pstate
//CHECK-ERROR: msr TRFCR_EL1, x0
diff --git a/llvm/test/MC/AArch64/armv8.5a-bti.s b/llvm/test/MC/AArch64/armv8.5a-bti.s
index e0585f7613fcc..e806d5ad03ca8 100644
--- a/llvm/test/MC/AArch64/armv8.5a-bti.s
+++ b/llvm/test/MC/AArch64/armv8.5a-bti.s
@@ -3,15 +3,18 @@
// RUN: llvm-mc -triple aarch64-none-linux-gnu -show-encoding -mattr=-bti < %s | FileCheck %s --check-prefix=NOBTI
bti
+bti r
bti c
bti j
bti jc
+// CHECK: bti // encoding: [0x1f,0x24,0x03,0xd5]
// CHECK: bti // encoding: [0x1f,0x24,0x03,0xd5]
// CHECK: bti c // encoding: [0x5f,0x24,0x03,0xd5]
// CHECK: bti j // encoding: [0x9f,0x24,0x03,0xd5]
// CHECK: bti jc // encoding: [0xdf,0x24,0x03,0xd5]
+// NOBTI: hint #32 // encoding: [0x1f,0x24,0x03,0xd5]
// NOBTI: hint #32 // encoding: [0x1f,0x24,0x03,0xd5]
// NOBTI: hint #34 // encoding: [0x5f,0x24,0x03,0xd5]
// NOBTI: hint #36 // encoding: [0x9f,0x24,0x03,0xd5]
diff --git a/llvm/test/MC/AArch64/armv9.6a-pcdphint-diagnostics.s b/llvm/test/MC/AArch64/armv9.6a-pcdphint-diagnostics.s
new file mode 100644
index 0000000000000..9e2b67a81459e
--- /dev/null
+++ b/llvm/test/MC/AArch64/armv9.6a-pcdphint-diagnostics.s
@@ -0,0 +1,19 @@
+// RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 | FileCheck %s
+
+stshh
+stshh foo
+stshh #0
+stshh 0
+
+// CHECK: error: invalid operand for instruction
+// CHECK-NEXT: stshh
+// CHECK-NEXT: ^
+// CHECK: error: invalid operand for instruction
+// CHECK-NEXT: stshh foo
+// CHECK-NEXT: ^
+// CHECK: error: invalid operand for instruction
+// CHECK-NEXT: stshh #0
+// CHECK-NEXT: ^
+// CHECK: error: invalid operand for instruction
+// CHECK-NEXT: stshh 0
+// CHECK-NEXT: ^
diff --git a/llvm/test/MC/AArch64/armv9.6a-pcdphint.s b/llvm/test/MC/AArch64/armv9.6a-pcdphint.s
index 46fe8981d1ebf..e6bf5cf680cf7 100644
--- a/llvm/test/MC/AArch64/armv9.6a-pcdphint.s
+++ b/llvm/test/MC/AArch64/armv9.6a-pcdphint.s
@@ -6,7 +6,15 @@
// RUN: llvm-mc -triple=aarch64 -show-encoding < %s \
// RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \
// RUN: | llvm-mc -triple=aarch64 -disassemble -show-encoding \
-// RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST
+// RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST,CHECK-HINT-ALIAS
+
+hint #48
+// CHECK-HINT-ALIAS: stshh keep
+// CHECK-ENCODING: encoding: [0x1f,0x26,0x03,0xd5]
+
+hint #49
+// CHECK-HINT-ALIAS-NEXT: stshh strm
+// CHECK-ENCODING: encoding: [0x3f,0x26,0x03,0xd5]
stshh keep
// CHECK-INST: stshh keep
diff --git a/llvm/test/MC/AArch64/armv9.7a-memsys.s b/llvm/test/MC/AArch64/armv9.7a-memsys.s
index ce3ac9bc7e8ee..11a75c2007b4d 100644
--- a/llvm/test/MC/AArch64/armv9.7a-memsys.s
+++ b/llvm/test/MC/AArch64/armv9.7a-memsys.s
@@ -10,10 +10,22 @@
// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+lscp < %s \
// RUN: | sed '/.text/d' | sed 's/.*encoding: //g' \
// RUN: | llvm-mc -triple=aarch64 -mattr=+lscp -disassemble -show-encoding \
-// RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST
+// RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST,CHECK-HINT-ALIAS
// Armv9.7-A Contention Management Hints (FEAT_CMH).
+hint #50
+// CHECK-HINT-ALIAS: shuh
+// CHECK-ENCODING: encoding: [0x5f,0x26,0x03,0xd5]
+
+hint #51
+// CHECK-HINT-ALIAS-NEXT: shuh ph
+// CHECK-ENCODING: encoding: [0x7f,0x26,0x03,0xd5]
+
+hint #52
+// CHECK-HINT-ALIAS-NEXT: stcph
+// CHECK-ENCODING: encoding: [0x9f,0x26,0x03,0xd5]
+
shuh
// CHECK-INST: shuh
// CHECK-ENCODING: encoding: [0x5f,0x26,0x03,0xd5]
diff --git a/llvm/test/MC/AArch64/basic-a64-instructions.s b/llvm/test/MC/AArch64/basic-a64-instructions.s
index 093c09c67bacb..fad6dc796cc2a 100644
--- a/llvm/test/MC/AArch64/basic-a64-instructions.s
+++ b/llvm/test/MC/AArch64/basic-a64-instructions.s
@@ -3460,9 +3460,21 @@ _func:
//------------------------------------------------------------------------------
hint #0
+ hint #1
+ hint #2
+ hint #3
+ hint #4
+ hint #5
+ hint #6
hint #127
// CHECK: nop // encoding: [0x1f,0x20,0x03,0xd5]
-// CHECK: hint #{{127|0x7f}} // encoding: [0xff,0x2f,0x03,0xd5]
+// CHECK-NEXT: yield // encoding: [0x3f,0x20,0x03,0xd5]
+// CHECK-NEXT: wfe // encoding: [0x5f,0x20,0x03,0xd5]
+// CHECK-NEXT: wfi // encoding: [0x7f,0x20,0x03,0xd5]
+// CHECK-NEXT: sev // encoding: [0x9f,0x20,0x03,0xd5]
+// CHECK-NEXT: sevl // encoding: [0xbf,0x20,0x03,0xd5]
+// CHECK-NEXT: dgh // encoding: [0xdf,0x20,0x03,0xd5]
+// CHECK-NEXT: hint #{{127|0x7f}} // encoding: [0xff,0x2f,0x03,0xd5]
nop
yield
diff --git a/llvm/test/MC/AArch64/ras-extension.s b/llvm/test/MC/AArch64/ras-extension.s
index 2400add87cdde..53cc26ee1ea31 100644
--- a/llvm/test/MC/AArch64/ras-extension.s
+++ b/llvm/test/MC/AArch64/ras-extension.s
@@ -5,6 +5,9 @@
// RUN: llvm-mc -triple aarch64-none-linux-gnu -show-encoding -mcpu=cortex-r82 < %s | FileCheck %s
// RUN: llvm-mc -triple aarch64-none-linux-gnu -show-encoding -mattr=+v8r < %s | FileCheck %s
+ hint #16
+// CHECK: esb // encoding: [0x1f,0x22,0x03,0xd5]
+
esb
// CHECK: esb // encoding: [0x1f,0x22,0x03,0xd5]
diff --git a/llvm/test/MC/AArch64/speculation-barriers.s b/llvm/test/MC/AArch64/speculation-barriers.s
index 0ab3fe7923efa..7c80d96227166 100644
--- a/llvm/test/MC/AArch64/speculation-barriers.s
+++ b/llvm/test/MC/AArch64/speculation-barriers.s
@@ -1,9 +1,11 @@
// RUN: llvm-mc -triple aarch64-none-linux-gnu -show-encoding < %s | FileCheck %s
+hint #20
csdb
ssbb
pssbb
+// CHECK: csdb // encoding: [0x9f,0x22,0x03,0xd5]
// CHECK: csdb // encoding: [0x9f,0x22,0x03,0xd5]
// CHECK: ssbb // encoding: [0x9f,0x30,0x03,0xd5]
// CHECK: pssbb // encoding: [0x9f,0x34,0x03,0xd5]
More information about the llvm-commits
mailing list