forked from OSchip/llvm-project
[RISCV] Allow call pseudoinstruction to be used to call a function name that coincides with a register name
Previously `call zero`, `call f0` etc would fail. This leads to compilation failures if building programs that define functions with those names and using -save-temps. llvm-svn: 330846
This commit is contained in:
parent
39d61944df
commit
cd8688a4c2
|
@ -65,7 +65,7 @@ class RISCVAsmParser : public MCTargetAsmParser {
|
|||
OperandMatchResultTy parseMemOpBaseReg(OperandVector &Operands);
|
||||
OperandMatchResultTy parseOperandWithModifier(OperandVector &Operands);
|
||||
|
||||
bool parseOperand(OperandVector &Operands);
|
||||
bool parseOperand(OperandVector &Operands, bool ForceImmediate);
|
||||
|
||||
public:
|
||||
enum RISCVMatchResultTy {
|
||||
|
@ -881,12 +881,15 @@ RISCVAsmParser::parseMemOpBaseReg(OperandVector &Operands) {
|
|||
return MatchOperand_Success;
|
||||
}
|
||||
|
||||
/// Looks at a token type and creates the relevant operand
|
||||
/// from this information, adding to Operands.
|
||||
/// If operand was parsed, returns false, else true.
|
||||
bool RISCVAsmParser::parseOperand(OperandVector &Operands) {
|
||||
// Attempt to parse token as register
|
||||
if (parseRegister(Operands, true) == MatchOperand_Success)
|
||||
/// Looks at a token type and creates the relevant operand from this
|
||||
/// information, adding to Operands. If operand was parsed, returns false, else
|
||||
/// true. If ForceImmediate is true, no attempt will be made to parse the
|
||||
/// operand as a register, which is needed for pseudoinstructions such as
|
||||
/// call.
|
||||
bool RISCVAsmParser::parseOperand(OperandVector &Operands,
|
||||
bool ForceImmediate) {
|
||||
// Attempt to parse token as register, unless ForceImmediate.
|
||||
if (!ForceImmediate && parseRegister(Operands, true) == MatchOperand_Success)
|
||||
return false;
|
||||
|
||||
// Attempt to parse token as an immediate
|
||||
|
@ -913,7 +916,7 @@ bool RISCVAsmParser::ParseInstruction(ParseInstructionInfo &Info,
|
|||
return false;
|
||||
|
||||
// Parse first operand
|
||||
if (parseOperand(Operands))
|
||||
if (parseOperand(Operands, Name == "call"))
|
||||
return true;
|
||||
|
||||
// Parse until end of statement, consuming commas between operands
|
||||
|
@ -922,7 +925,7 @@ bool RISCVAsmParser::ParseInstruction(ParseInstructionInfo &Info,
|
|||
getLexer().Lex();
|
||||
|
||||
// Parse next operand
|
||||
if (parseOperand(Operands))
|
||||
if (parseOperand(Operands, false))
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -17,3 +17,23 @@ call bar
|
|||
# INSTR: auipc ra, 0
|
||||
# INSTR: jalr ra
|
||||
# FIXUP: fixup A - offset: 0, value: bar, kind:
|
||||
|
||||
# Ensure that calls to functions whose names coincide with register names work.
|
||||
|
||||
call zero
|
||||
# RELOC: R_RISCV_CALL zero 0x0
|
||||
# INSTR: auipc ra, 0
|
||||
# INSTR: jalr ra
|
||||
# FIXUP: fixup A - offset: 0, value: zero, kind:
|
||||
|
||||
call f1
|
||||
# RELOC: R_RISCV_CALL f1 0x0
|
||||
# INSTR: auipc ra, 0
|
||||
# INSTR: jalr ra
|
||||
# FIXUP: fixup A - offset: 0, value: f1, kind:
|
||||
|
||||
call ra
|
||||
# RELOC: R_RISCV_CALL ra 0x0
|
||||
# INSTR: auipc ra, 0
|
||||
# INSTR: jalr ra
|
||||
# FIXUP: fixup A - offset: 0, value: ra, kind:
|
||||
|
|
Loading…
Reference in New Issue