-
Notifications
You must be signed in to change notification settings - Fork 13.4k
[RISCV] Add symbol parsing support for XAndesPerf branch and gp-related instructions #137748
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
@llvm/pr-subscribers-llvm-binary-utilities @llvm/pr-subscribers-mc Author: Jim Lin (tclin914) ChangesThis patch adds support for parsing symbols in the XAndesPerf branch immediate and gp-related instructions. The branch immediate instructions use Patch is 30.69 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/137748.diff 16 Files Affected:
diff --git a/llvm/include/llvm/BinaryFormat/ELFRelocs/RISCV_nonstandard.def b/llvm/include/llvm/BinaryFormat/ELFRelocs/RISCV_nonstandard.def
index 7ae3d3f205772..7437533d5041b 100644
--- a/llvm/include/llvm/BinaryFormat/ELFRelocs/RISCV_nonstandard.def
+++ b/llvm/include/llvm/BinaryFormat/ELFRelocs/RISCV_nonstandard.def
@@ -26,3 +26,14 @@ ELF_RISCV_NONSTANDARD_RELOC(QUALCOMM, R_RISCV_QC_ABS20_U, 192)
ELF_RISCV_NONSTANDARD_RELOC(QUALCOMM, R_RISCV_QC_E_BRANCH, 193)
ELF_RISCV_NONSTANDARD_RELOC(QUALCOMM, R_RISCV_QC_E_32, 194)
ELF_RISCV_NONSTANDARD_RELOC(QUALCOMM, R_RISCV_QC_E_JUMP_PLT, 195)
+
+// Andes Nonstandard Relocations
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_BRANCH_10, 241)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_18S0_I, 246)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S1_I, 247)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S2_I, 248)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S3_I, 249)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_18S0_S, 250)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S1_S, 251)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S2_S, 252)
+ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S3_S, 253)
diff --git a/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp b/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp
index 9bc4734815364..fa11268bec835 100644
--- a/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp
+++ b/llvm/lib/Target/RISCV/AsmParser/RISCVAsmParser.cpp
@@ -533,14 +533,14 @@ struct RISCVOperand final : public MCParsedAsmOperand {
}
// True if operand is a symbol with no modifiers, or a constant with no
- // modifiers and isShiftedInt<N-1, 1>(Op).
- template <int N> bool isBareSimmNLsb0() const {
+ // modifiers and isShiftedInt<N-K, K>(Op).
+ template <int N, int K> bool isBareSimmNLsbK() const {
if (!isImm())
return false;
int64_t Imm;
if (evaluateConstantImm(getImm(), Imm))
- return isShiftedInt<N - 1, 1>(fixImmediateForRV32(Imm, isRV64Imm()));
+ return isShiftedInt<N - K, K>(fixImmediateForRV32(Imm, isRV64Imm()));
RISCVMCExpr::Specifier VK = RISCVMCExpr::VK_None;
return RISCVAsmParser::classifySymbolRef(getImm(), VK) &&
@@ -852,10 +852,6 @@ struct RISCVOperand final : public MCParsedAsmOperand {
return SignExtend64<32>(Imm);
}
- bool isSImm11Lsb0() const {
- return isSImmPred([](int64_t Imm) { return isShiftedInt<10, 1>(Imm); });
- }
-
bool isSImm12() const {
if (!isImm())
return false;
@@ -948,22 +944,6 @@ struct RISCVOperand final : public MCParsedAsmOperand {
[](int64_t Imm) { return Imm != INT64_MIN && isInt<5>(Imm - 1); });
}
- bool isSImm18() const {
- return isSImmPred([](int64_t Imm) { return isInt<18>(Imm); });
- }
-
- bool isSImm18Lsb0() const {
- return isSImmPred([](int64_t Imm) { return isShiftedInt<17, 1>(Imm); });
- }
-
- bool isSImm19Lsb00() const {
- return isSImmPred([](int64_t Imm) { return isShiftedInt<17, 2>(Imm); });
- }
-
- bool isSImm20Lsb000() const {
- return isSImmPred([](int64_t Imm) { return isShiftedInt<17, 3>(Imm); });
- }
-
bool isSImm32Lsb0() const {
return isSImmPred([](int64_t Imm) { return isShiftedInt<31, 1>(Imm); });
}
@@ -1535,7 +1515,7 @@ bool RISCVAsmParser::matchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
case Match_InvalidSImm11:
return generateImmOutOfRangeError(Operands, ErrorInfo, -(1 << 10),
(1 << 10) - 1);
- case Match_InvalidSImm11Lsb0:
+ case Match_InvalidBareSImm11Lsb0:
return generateImmOutOfRangeError(
Operands, ErrorInfo, -(1 << 10), (1 << 10) - 2,
"immediate must be a multiple of 2 bytes in the range");
@@ -1611,18 +1591,18 @@ bool RISCVAsmParser::matchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
(1 << 4),
"immediate must be in the range");
}
- case Match_InvalidSImm18:
+ case Match_InvalidBareSImm18:
return generateImmOutOfRangeError(Operands, ErrorInfo, -(1 << 17),
(1 << 17) - 1);
- case Match_InvalidSImm18Lsb0:
+ case Match_InvalidBareSImm18Lsb0:
return generateImmOutOfRangeError(
Operands, ErrorInfo, -(1 << 17), (1 << 17) - 2,
"immediate must be a multiple of 2 bytes in the range");
- case Match_InvalidSImm19Lsb00:
+ case Match_InvalidBareSImm19Lsb00:
return generateImmOutOfRangeError(
Operands, ErrorInfo, -(1 << 18), (1 << 18) - 4,
"immediate must be a multiple of 4 bytes in the range");
- case Match_InvalidSImm20Lsb000:
+ case Match_InvalidBareSImm20Lsb000:
return generateImmOutOfRangeError(
Operands, ErrorInfo, -(1 << 19), (1 << 19) - 8,
"immediate must be a multiple of 8 bytes in the range");
diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp
index d8cfeb07e52b6..43a93e64aee6e 100644
--- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp
+++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp
@@ -88,6 +88,9 @@ MCFixupKindInfo RISCVAsmBackend::getFixupKindInfo(MCFixupKind Kind) const {
{"fixup_riscv_qc_e_32", 16, 32, 0},
{"fixup_riscv_qc_abs20_u", 12, 20, 0},
{"fixup_riscv_qc_e_jump_plt", 0, 48, MCFixupKindInfo::FKF_IsPCRel},
+
+ // Andes fixups
+ {"fixup_riscv_nds_branch_10", 0, 32, MCFixupKindInfo::FKF_IsPCRel},
};
static_assert((std::size(Infos)) == RISCV::NumTargetFixupKinds,
"Not all fixup kinds added to Infos array");
@@ -568,6 +571,21 @@ static uint64_t adjustFixupValue(const MCFixup &Fixup, uint64_t Value,
(Bit15_13 << 17) | (Bit4_1 << 8) | (Bit11 << 7);
return Value;
}
+ case RISCV::fixup_riscv_nds_branch_10: {
+ if (!isInt<11>(Value))
+ Ctx.reportError(Fixup.getLoc(), "fixup value out of range");
+ if (Value & 0x1)
+ Ctx.reportError(Fixup.getLoc(), "fixup value must be 2-byte aligned");
+ // Need to extract imm[10], imm[9:5], imm[4:1] from the 11-bit Value.
+ unsigned Sbit = (Value >> 10) & 0x1;
+ unsigned Hi5 = (Value >> 5) & 0x1f;
+ unsigned Lo4 = (Value >> 1) & 0xf;
+ // Inst{31} = Sbit;
+ // Inst{29-25} = Hi5;
+ // Inst{11-8} = Lo4;
+ Value = (Sbit << 31) | (Hi5 << 25) | (Lo4 << 8);
+ return Value;
+ }
}
}
diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h
index 6ef94fb5e93da..545bfea66ea8f 100644
--- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h
+++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVBaseInfo.h
@@ -56,12 +56,21 @@ enum {
InstFormatQC_EB = 24,
InstFormatQC_EJ = 25,
InstFormatQC_ES = 26,
- InstFormatOther = 31,
-
- InstFormatMask = 31,
+ InstFormatNDS_BRANCH_10 = 27,
+ InstFormatNDS_GPREL_18S0_I = 28,
+ InstFormatNDS_GPREL_17S1_I = 29,
+ InstFormatNDS_GPREL_17S2_I = 30,
+ InstFormatNDS_GPREL_17S3_I = 31,
+ InstFormatNDS_GPREL_18S0_S = 32,
+ InstFormatNDS_GPREL_17S1_S = 33,
+ InstFormatNDS_GPREL_17S2_S = 34,
+ InstFormatNDS_GPREL_17S3_S = 35,
+ InstFormatOther = 63,
+
+ InstFormatMask = 63,
InstFormatShift = 0,
- ConstraintShift = InstFormatShift + 5,
+ ConstraintShift = InstFormatShift + 6,
VS2Constraint = 0b001 << ConstraintShift,
VS1Constraint = 0b010 << ConstraintShift,
VMConstraint = 0b100 << ConstraintShift,
diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFObjectWriter.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFObjectWriter.cpp
index 35e75489794f7..ed6bbc9fa9a6a 100644
--- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFObjectWriter.cpp
+++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVELFObjectWriter.cpp
@@ -108,6 +108,8 @@ unsigned RISCVELFObjectWriter::getRelocType(MCContext &Ctx,
return ELF::R_RISCV_QC_E_BRANCH;
case RISCV::fixup_riscv_qc_e_jump_plt:
return ELF::R_RISCV_QC_E_JUMP_PLT;
+ case RISCV::fixup_riscv_nds_branch_10:
+ return ELF::R_RISCV_NDS_BRANCH_10;
}
}
diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVFixupKinds.h b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVFixupKinds.h
index 80fbed8d10f99..0bdb35e2c573b 100644
--- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVFixupKinds.h
+++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVFixupKinds.h
@@ -56,6 +56,10 @@ enum Fixups {
// 32-bit fixup for symbol references in the 48-bit qc.j/qc.jal instructions
fixup_riscv_qc_e_jump_plt,
+ // Andes specific fixups
+ // 10-bit fixup for symbol references in the xandesperf branch instruction
+ fixup_riscv_nds_branch_10,
+
// Used as a sentinel, must be the last
fixup_riscv_invalid,
NumTargetFixupKinds = fixup_riscv_invalid - FirstTargetFixupKind
diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp
index 7486618782e6c..dec98e1028124 100644
--- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp
+++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp
@@ -677,6 +677,24 @@ uint64_t RISCVMCCodeEmitter::getImmOpValue(const MCInst &MI, unsigned OpNo,
FixupKind = RISCV::fixup_riscv_qc_e_32;
} else if (MIFrm == RISCVII::InstFormatQC_EJ) {
FixupKind = RISCV::fixup_riscv_qc_e_jump_plt;
+ } else if (MIFrm == RISCVII::InstFormatNDS_BRANCH_10) {
+ FixupKind = RISCV::fixup_riscv_nds_branch_10;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_18S0_I) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_18S0_I;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_17S1_I) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_17S1_I;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_17S2_I) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_17S2_I;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_17S3_I) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_17S3_I;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_18S0_S) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_18S0_S;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_17S1_S) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_17S1_S;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_17S2_S) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_17S2_S;
+ } else if (MIFrm == RISCVII::InstFormatNDS_GPREL_17S3_S) {
+ FixupKind = ELF::R_RISCV_NDS_GPREL_17S3_S;
}
}
diff --git a/llvm/lib/Target/RISCV/RISCVInstrFormats.td b/llvm/lib/Target/RISCV/RISCVInstrFormats.td
index 8d56637d8b281..fd125e6f4bdbe 100644
--- a/llvm/lib/Target/RISCV/RISCVInstrFormats.td
+++ b/llvm/lib/Target/RISCV/RISCVInstrFormats.td
@@ -27,37 +27,46 @@
// Format specifies the encoding used by the instruction. This is used by
// RISCVMCCodeEmitter to determine which form of fixup to use. These
// definitions must be kept in-sync with RISCVBaseInfo.h.
-class InstFormat<bits<5> val> {
- bits<5> Value = val;
-}
-def InstFormatPseudo : InstFormat<0>;
-def InstFormatR : InstFormat<1>;
-def InstFormatR4 : InstFormat<2>;
-def InstFormatI : InstFormat<3>;
-def InstFormatS : InstFormat<4>;
-def InstFormatB : InstFormat<5>;
-def InstFormatU : InstFormat<6>;
-def InstFormatJ : InstFormat<7>;
-def InstFormatCR : InstFormat<8>;
-def InstFormatCI : InstFormat<9>;
-def InstFormatCSS : InstFormat<10>;
-def InstFormatCIW : InstFormat<11>;
-def InstFormatCL : InstFormat<12>;
-def InstFormatCS : InstFormat<13>;
-def InstFormatCA : InstFormat<14>;
-def InstFormatCB : InstFormat<15>;
-def InstFormatCJ : InstFormat<16>;
-def InstFormatCU : InstFormat<17>;
-def InstFormatCLB : InstFormat<18>;
-def InstFormatCLH : InstFormat<19>;
-def InstFormatCSB : InstFormat<20>;
-def InstFormatCSH : InstFormat<21>;
-def InstFormatQC_EAI : InstFormat<22>;
-def InstFormatQC_EI : InstFormat<23>;
-def InstFormatQC_EB : InstFormat<24>;
-def InstFormatQC_EJ : InstFormat<25>;
-def InstFormatQC_ES : InstFormat<26>;
-def InstFormatOther : InstFormat<31>;
+class InstFormat<bits<6> val> {
+ bits<6> Value = val;
+}
+def InstFormatPseudo : InstFormat<0>;
+def InstFormatR : InstFormat<1>;
+def InstFormatR4 : InstFormat<2>;
+def InstFormatI : InstFormat<3>;
+def InstFormatS : InstFormat<4>;
+def InstFormatB : InstFormat<5>;
+def InstFormatU : InstFormat<6>;
+def InstFormatJ : InstFormat<7>;
+def InstFormatCR : InstFormat<8>;
+def InstFormatCI : InstFormat<9>;
+def InstFormatCSS : InstFormat<10>;
+def InstFormatCIW : InstFormat<11>;
+def InstFormatCL : InstFormat<12>;
+def InstFormatCS : InstFormat<13>;
+def InstFormatCA : InstFormat<14>;
+def InstFormatCB : InstFormat<15>;
+def InstFormatCJ : InstFormat<16>;
+def InstFormatCU : InstFormat<17>;
+def InstFormatCLB : InstFormat<18>;
+def InstFormatCLH : InstFormat<19>;
+def InstFormatCSB : InstFormat<20>;
+def InstFormatCSH : InstFormat<21>;
+def InstFormatQC_EAI : InstFormat<22>;
+def InstFormatQC_EI : InstFormat<23>;
+def InstFormatQC_EB : InstFormat<24>;
+def InstFormatQC_EJ : InstFormat<25>;
+def InstFormatQC_ES : InstFormat<26>;
+def InstFormatNDS_BRANCH_10 : InstFormat<27>;
+def InstFormatNDS_GPREL_18S0_I : InstFormat<28>;
+def InstFormatNDS_GPREL_17S1_I : InstFormat<29>;
+def InstFormatNDS_GPREL_17S2_I : InstFormat<30>;
+def InstFormatNDS_GPREL_17S3_I : InstFormat<31>;
+def InstFormatNDS_GPREL_18S0_S : InstFormat<32>;
+def InstFormatNDS_GPREL_17S1_S : InstFormat<33>;
+def InstFormatNDS_GPREL_17S2_S : InstFormat<34>;
+def InstFormatNDS_GPREL_17S3_S : InstFormat<35>;
+def InstFormatOther : InstFormat<63>;
class RISCVVConstraint<bits<3> val> {
@@ -190,42 +199,42 @@ class RVInstCommon<dag outs, dag ins, string opcodestr, string argstr,
let AsmString = opcodestr # !if(!empty(argstr), "", "\t" # argstr);
let Pattern = pattern;
- let TSFlags{4-0} = format.Value;
+ let TSFlags{5-0} = format.Value;
// Defaults
RISCVVConstraint RVVConstraint = NoConstraint;
- let TSFlags{7-5} = RVVConstraint.Value;
+ let TSFlags{8-6} = RVVConstraint.Value;
bits<3> VLMul = 0;
- let TSFlags{10-8} = VLMul;
+ let TSFlags{11-9} = VLMul;
bit IsTiedPseudo = 0;
- let TSFlags{11} = IsTiedPseudo;
+ let TSFlags{12} = IsTiedPseudo;
bit HasSEWOp = 0;
- let TSFlags{12} = HasSEWOp;
+ let TSFlags{13} = HasSEWOp;
bit HasVLOp = 0;
- let TSFlags{13} = HasVLOp;
+ let TSFlags{14} = HasVLOp;
bit HasVecPolicyOp = 0;
- let TSFlags{14} = HasVecPolicyOp;
+ let TSFlags{15} = HasVecPolicyOp;
bit IsRVVWideningReduction = 0;
- let TSFlags{15} = IsRVVWideningReduction;
+ let TSFlags{16} = IsRVVWideningReduction;
bit UsesMaskPolicy = 0;
- let TSFlags{16} = UsesMaskPolicy;
+ let TSFlags{17} = UsesMaskPolicy;
// Indicates that the result can be considered sign extended from bit 31. Some
// instructions with this flag aren't W instructions, but are either sign
// extended from a smaller size, always outputs a small integer, or put zeros
// in bits 63:31. Used by the SExtWRemoval pass.
bit IsSignExtendingOpW = 0;
- let TSFlags{17} = IsSignExtendingOpW;
+ let TSFlags{18} = IsSignExtendingOpW;
bit HasRoundModeOp = 0;
- let TSFlags{18} = HasRoundModeOp;
+ let TSFlags{19} = HasRoundModeOp;
// This is only valid when HasRoundModeOp is set to 1. HasRoundModeOp is set
// to 1 for vector fixed-point or floating-point intrinsics. This bit is
@@ -233,7 +242,7 @@ class RVInstCommon<dag outs, dag ins, string opcodestr, string argstr,
// fixed-point / floating-point instructions and emit appropriate read/write
// to the correct CSR.
bit UsesVXRM = 0;
- let TSFlags{19} = UsesVXRM;
+ let TSFlags{20} = UsesVXRM;
// Indicates whether these instructions can partially overlap between source
// registers and destination registers according to the vector spec.
@@ -242,19 +251,19 @@ class RVInstCommon<dag outs, dag ins, string opcodestr, string argstr,
// 2 -> narrowing case
// 3 -> widening case
bits<2> TargetOverlapConstraintType = 0;
- let TSFlags{21-20} = TargetOverlapConstraintType;
+ let TSFlags{22-21} = TargetOverlapConstraintType;
// Most vector instructions are elementwise, but some may depend on the value
// of VL (e.g. vslide1down.vx), and others may depend on the VL and mask
// (e.g. vredsum.vs, viota.m). Mark these instructions so that peepholes avoid
// changing their VL and/or mask.
EltDeps ElementsDependOn = EltDepsNone;
- let TSFlags{22} = ElementsDependOn.VL;
- let TSFlags{23} = ElementsDependOn.Mask;
+ let TSFlags{23} = ElementsDependOn.VL;
+ let TSFlags{24} = ElementsDependOn.Mask;
// Indicates the EEW of a vector instruction's destination operand.
EEW DestEEW = EEWSEWx1;
- let TSFlags{25-24} = DestEEW.Value;
+ let TSFlags{26-25} = DestEEW.Value;
}
class RVInst<dag outs, dag ins, string opcodestr, string argstr,
diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfo.td b/llvm/lib/Target/RISCV/RISCVInstrInfo.td
index 7cd36aa46efbe..1dccc6d07c78f 100644
--- a/llvm/lib/Target/RISCV/RISCVInstrInfo.td
+++ b/llvm/lib/Target/RISCV/RISCVInstrInfo.td
@@ -161,9 +161,24 @@ class UImmAsmOperand<int width, string suffix = "">
: ImmAsmOperand<"U", width, suffix> {
}
+class BareSImmNAsmOperand<int width>
+ : ImmAsmOperand<"BareS", width, ""> {
+ let PredicateMethod = "isBareSimmN<" # width # ">";
+}
+
class BareSImmNLsb0AsmOperand<int width>
: ImmAsmOperand<"BareS", width, "Lsb0"> {
- let PredicateMethod = "isBareSimmNLsb0<" # width # ">";
+ let PredicateMethod = "isBareSimmNLsbK<" # width # ", 1>";
+}
+
+class BareSImmNLsb00AsmOperand<int width>
+ : ImmAsmOperand<"BareS", width, "Lsb00"> {
+ let PredicateMethod = "isBareSimmNLsbK<" # width # ", 2>";
+}
+
+class BareSImmNLsb000AsmOperand<int width>
+ : ImmAsmOperand<"BareS", width, "Lsb000"> {
+ let PredicateMethod = "isBareSimmNLsbK<" # width # ", 3>";
}
class RISCVOp<ValueType vt = XLenVT> : Operand<vt> {
diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td b/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td
index 2ec768435259c..60fbeff5ab116 100644
--- a/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td
+++ b/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td
@@ -15,40 +15,40 @@
//===----------------------------------------------------------------------===//
// A 11-bit signed immediate where the least significant bit is zero.
-def simm11_lsb0 : Operand<OtherVT> {
- let ParserMatchClass = SImmAsmOperand<11, "Lsb0">;
+def bare_simm11_lsb0 : Operand<OtherVT> {
+ let ParserMatchClass = BareSImmNLsb0AsmOperand<11>;
let PrintMethod = "printBranchOperand";
let EncoderMethod = "getImmOpValueAsrN<1>";
let DecoderMethod = "decodeSImmOperandAndLslN<11, 1>";
let MCOperandPredicate = [{
int64_t Imm;
- if (!MCOp.evaluateAsConstantImm(Imm))
- return false;
- return isShiftedInt<10, 1>(Imm);
+ if (MCOp.evaluateAsConstantImm(Imm))
+ return isShiftedInt<10, 1>(Imm);
+ return MCOp.isBareSymbolRef();
}];
let OperandType = "OPERAND_PCREL";
}
-def simm18 : Operand<XLenVT> {
- let ParserMatchClass = SImmAsmOperand<18>;
+def bare_simm18 : Operand<XLenVT> {
+ let ParserMatchClass = BareSImmNAsmOperand<18>;
let EncoderMethod = "getImmOpValue";
let DecoderMethod = "decodeSImmOperand<18>";
}
-def simm18_lsb0 : Operand<XLenVT> {
- let ParserMatchClass = SImmAsmOperand<18, "Lsb0">;
+def bare_simm18_lsb0 : Operand<XLenVT> {
+ let ParserMatchClass = BareSImmNLsb0AsmOperand<18>;
let EncoderMethod = "getImmOpValueAsrN<1>";
let DecoderMethod = "decodeSImmOperandAndLslN<18, 1>";
}
-def simm19_lsb00 : Operand<XLenVT> {
- let ParserMatchClass = SImmAsmOperand<19, "Lsb00">;
+def bare_simm19_lsb00 : Operand<XLenVT> {
+ let ParserMatchClass = BareSImmNLsb00AsmOperand<19>;
let EncoderMethod = "getImmOpValueAsrN<2>";
let DecoderMethod = "decodeSImmOperandAndLslN<19, 2>";
}
-def simm20_lsb000 : Operand<XLenVT> {
- let ParserMatchClass = SImmAsmOperand<20, "Lsb000">;
+def bare_simm20_lsb000 : Operand<XLenVT> {
+ let ParserMatchClass = BareSImmNLsb000AsmOperand<20>;
let EncoderMethod = "getImmOpVal...
[truncated]
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks broadly good to me, but without referring to a specification, this is hard to verify :)
// Andes Nonstandard Relocations | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_BRANCH_10, 241) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_18S0_I, 246) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S1_I, 247) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S2_I, 248) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S3_I, 249) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_18S0_S, 250) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S1_S, 251) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S2_S, 252) | ||
ELF_RISCV_NONSTANDARD_RELOC(ANDES, R_RISCV_NDS_GPREL_17S3_S, 253) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is there non-llvm documentation for these relocations and the instructions/formats they apply to?
Separately, I am thinking of refactoring this file as with these changes, ELD (an external user) will break: https://github.com/qualcomm/eld/blob/b3197fa1e54b470d36d8bdff7a10b469287caa3a/lib/Target/RISCV/RISCVRelocationInternal.h#L70 - this is because I didn't do a good job originally to predict this, rather than a problem you have caused with these changes.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I will ask our guys to release such a document for these relocations.
This patch adds support for parsing symbols in the XAndesPerf branch immediate and gp-related instructions. The branch immediate instructions use
R_RISCV_NDS_BRANCH_10
relocation. The gp-related instructions useR_RISCV_NDS_GPREL_*
relocations to allow linker to calculate the offset from gp to the symbol.