diff options
| author | Jiangning Liu <jiangning.liu@arm.com> | 2012-08-02 08:13:13 +0000 |
|---|---|---|
| committer | Jiangning Liu <jiangning.liu@arm.com> | 2012-08-02 08:13:13 +0000 |
| commit | 1fb27eccf5b7eabde9678d84411eb1df8a693683 (patch) | |
| tree | 8d53d92a72109753456e6edb1b3886f8704441e7 /lib/Target/ARM/AsmParser | |
| parent | ac89c0ddfdcf22a7bdaec3dd7e5de5f30ffcaf43 (diff) | |
| download | external_llvm-1fb27eccf5b7eabde9678d84411eb1df8a693683.zip external_llvm-1fb27eccf5b7eabde9678d84411eb1df8a693683.tar.gz external_llvm-1fb27eccf5b7eabde9678d84411eb1df8a693683.tar.bz2 | |
Fix #13241, a bug around shift immediate operand for ARM instruction ADR.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@161159 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Target/ARM/AsmParser')
| -rw-r--r-- | lib/Target/ARM/AsmParser/ARMAsmParser.cpp | 23 |
1 files changed, 23 insertions, 0 deletions
diff --git a/lib/Target/ARM/AsmParser/ARMAsmParser.cpp b/lib/Target/ARM/AsmParser/ARMAsmParser.cpp index 4497720..6fe6356 100644 --- a/lib/Target/ARM/AsmParser/ARMAsmParser.cpp +++ b/lib/Target/ARM/AsmParser/ARMAsmParser.cpp @@ -796,6 +796,13 @@ public: int64_t Value = CE->getValue(); return Value > 0 && Value <= 32; } + bool isAdrLabel() const { + // If we have an immediate that's not a constant, treat it as a label + // reference needing a fixup. If it is a constant, but it can't fit + // into shift immediate encoding, we reject it. + if (isImm() && !isa<MCConstantExpr>(getImm())) return true; + else return (isARMSOImm() || isARMSOImmNeg()); + } bool isARMSOImm() const { if (!isImm()) return false; const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); @@ -1644,6 +1651,22 @@ public: Inst.addOperand(MCOperand::CreateImm(Imm)); } + void addAdrLabelOperands(MCInst &Inst, unsigned N) const { + assert(N == 1 && "Invalid number of operands!"); + assert(isImm() && "Not an immediate!"); + + // If we have an immediate that's not a constant, treat it as a label + // reference needing a fixup. + if (!isa<MCConstantExpr>(getImm())) { + Inst.addOperand(MCOperand::CreateExpr(getImm())); + return; + } + + const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); + int Val = CE->getValue(); + Inst.addOperand(MCOperand::CreateImm(Val)); + } + void addAlignedMemoryOperands(MCInst &Inst, unsigned N) const { assert(N == 2 && "Invalid number of operands!"); Inst.addOperand(MCOperand::CreateReg(Memory.BaseRegNum)); |
