aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib
diff options
context:
space:
mode:
authorJob Noorman <jnoorman@igalia.com>2023-07-28 10:27:32 +0200
committerJob Noorman <jnoorman@igalia.com>2023-07-28 10:42:05 +0200
commitafb2e9f44c13101c7b22c99e080b0beb0cd5b01e (patch)
treef93545cb35e0dfe9da76581e2d29339ec9c4f44f /llvm/lib
parente76304d05e56f593a45fd54115e2d1d30a329a11 (diff)
downloadllvm-afb2e9f44c13101c7b22c99e080b0beb0cd5b01e.zip
llvm-afb2e9f44c13101c7b22c99e080b0beb0cd5b01e.tar.gz
llvm-afb2e9f44c13101c7b22c99e080b0beb0cd5b01e.tar.bz2
[RISCV][MC] Add CLI option to disable branch relaxation
D154958 enables branch relaxation for unresolved symbols. This has an interesting consequence for some LLD tests: branch relocations are tested by using branches to undefined symbols and defining them, with different values, on the LLD command line. These tests broke and there doesn't seem to be an easy workaround: as far as I can tell, there is no way to convince llvm-mc to emit a branch relocation to an undefined symbol without branch relaxation kicking in. This patch proposes to add a flag, `-riscv-asm-relax-branches=0`, to do just that. The main purpose for this flag is for testing but it might be seen as a first step to some kind of "strict" or WYSIWYG mode (i.e., what you give to the assembler is exactly what comes out). The need for this has been mentioned in, for example, D108961. However, I suspect there will be a lot of discussion around what exactly such a strict mode would look like. Therefore, I gated this feature behind a CLI flag instead of adding a new target feature. Reviewed By: asb, MaskRay Differential Revision: https://reviews.llvm.org/D155953
Diffstat (limited to 'llvm/lib')
-rw-r--r--llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp11
1 files changed, 11 insertions, 0 deletions
diff --git a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp
index 1b890fb..6a46fff 100644
--- a/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp
+++ b/llvm/lib/Target/RISCV/MCTargetDesc/RISCVAsmBackend.cpp
@@ -19,6 +19,7 @@
#include "llvm/MC/MCObjectWriter.h"
#include "llvm/MC/MCSymbol.h"
#include "llvm/MC/MCValue.h"
+#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Endian.h"
#include "llvm/Support/EndianStream.h"
#include "llvm/Support/ErrorHandling.h"
@@ -27,6 +28,9 @@
using namespace llvm;
+static cl::opt<bool> RelaxBranches("riscv-asm-relax-branches", cl::init(true),
+ cl::Hidden);
+
std::optional<MCFixupKind> RISCVAsmBackend::getFixupKind(StringRef Name) const {
if (STI.getTargetTriple().isOSBinFormatELF()) {
unsigned Type;
@@ -144,6 +148,9 @@ bool RISCVAsmBackend::fixupNeedsRelaxationAdvanced(const MCFixup &Fixup,
const MCRelaxableFragment *DF,
const MCAsmLayout &Layout,
const bool WasForced) const {
+ if (!RelaxBranches)
+ return false;
+
int64_t Offset = int64_t(Value);
unsigned Kind = Fixup.getTargetKind();
@@ -483,6 +490,8 @@ static uint64_t adjustFixupValue(const MCFixup &Fixup, uint64_t Value,
return UpperImm | ((LowerImm << 20) << 32);
}
case RISCV::fixup_riscv_rvc_jump: {
+ if (!isInt<12>(Value))
+ Ctx.reportError(Fixup.getLoc(), "fixup value out of range");
// Need to produce offset[11|4|9:8|10|6|7|3:1|5] from the 11-bit Value.
unsigned Bit11 = (Value >> 11) & 0x1;
unsigned Bit4 = (Value >> 4) & 0x1;
@@ -497,6 +506,8 @@ static uint64_t adjustFixupValue(const MCFixup &Fixup, uint64_t Value,
return Value;
}
case RISCV::fixup_riscv_rvc_branch: {
+ if (!isInt<9>(Value))
+ Ctx.reportError(Fixup.getLoc(), "fixup value out of range");
// Need to produce offset[8|4:3], [reg 3 bit], offset[7:6|2:1|5]
unsigned Bit8 = (Value >> 8) & 0x1;
unsigned Bit7_6 = (Value >> 6) & 0x3;