aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp')
-rw-r--r--llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp182
1 files changed, 92 insertions, 90 deletions
diff --git a/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp b/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp
index dad91c6a969e..ec6f4e2ae216 100644
--- a/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp
+++ b/llvm/lib/Target/ARM/AsmParser/ARMAsmParser.cpp
@@ -11,7 +11,7 @@
#include "MCTargetDesc/ARMAddressingModes.h"
#include "MCTargetDesc/ARMBaseInfo.h"
#include "MCTargetDesc/ARMInstPrinter.h"
-#include "MCTargetDesc/ARMMCExpr.h"
+#include "MCTargetDesc/ARMMCAsmInfo.h"
#include "MCTargetDesc/ARMMCTargetDesc.h"
#include "TargetInfo/ARMTargetInfo.h"
#include "Utils/ARMBaseInfo.h"
@@ -31,7 +31,7 @@
#include "llvm/MC/MCInst.h"
#include "llvm/MC/MCInstrDesc.h"
#include "llvm/MC/MCInstrInfo.h"
-#include "llvm/MC/MCParser/MCAsmLexer.h"
+#include "llvm/MC/MCParser/AsmLexer.h"
#include "llvm/MC/MCParser/MCAsmParser.h"
#include "llvm/MC/MCParser/MCAsmParserExtension.h"
#include "llvm/MC/MCParser/MCAsmParserUtils.h"
@@ -55,7 +55,6 @@
#include "llvm/Support/raw_ostream.h"
#include "llvm/TargetParser/SubtargetFeature.h"
#include "llvm/TargetParser/TargetParser.h"
-#include "llvm/TargetParser/Triple.h"
#include <algorithm>
#include <cassert>
#include <cstddef>
@@ -288,6 +287,10 @@ class ARMAsmParser : public MCTargetAsmParser {
SmallVector<MCInst, 4> PendingConditionalInsts;
+ void onEndOfFile() override {
+ flushPendingInstructions(getParser().getStreamer());
+ }
+
void flushPendingInstructions(MCStreamer &Out) override {
if (!inImplicitITBlock()) {
assert(PendingConditionalInsts.size() == 0);
@@ -451,7 +454,7 @@ class ARMAsmParser : public MCTargetAsmParser {
bool parseMemory(OperandVector &);
bool parseOperand(OperandVector &, StringRef Mnemonic);
bool parseImmExpr(int64_t &Out);
- bool parsePrefix(ARMMCExpr::VariantKind &RefKind);
+ bool parsePrefix(ARM::Specifier &);
bool parseMemRegOffsetShift(ARM_AM::ShiftOpc &ShiftType,
unsigned &ShiftAmount);
bool parseLiteralValues(unsigned Size, SMLoc L);
@@ -745,9 +748,6 @@ public:
void ReportNearMisses(SmallVectorImpl<NearMissInfo> &NearMisses, SMLoc IDLoc,
OperandVector &Operands);
- MCSymbolRefExpr::VariantKind
- getVariantKindForName(StringRef Name) const override;
-
void doBeforeLabelEmit(MCSymbol *Symbol, SMLoc IDLoc) override;
void onLabelParsed(MCSymbol *Symbol) override;
@@ -1326,9 +1326,9 @@ public:
if (isImm() && !isa<MCConstantExpr>(getImm())) {
// We want to avoid matching :upper16: and :lower16: as we want these
// expressions to match in isImm0_65535Expr()
- const ARMMCExpr *ARM16Expr = dyn_cast<ARMMCExpr>(getImm());
- return (!ARM16Expr || (ARM16Expr->getKind() != ARMMCExpr::VK_ARM_HI16 &&
- ARM16Expr->getKind() != ARMMCExpr::VK_ARM_LO16));
+ auto *ARM16Expr = dyn_cast<MCSpecifierExpr>(getImm());
+ return (!ARM16Expr || (ARM16Expr->getSpecifier() != ARM::S_HI16 &&
+ ARM16Expr->getSpecifier() != ARM::S_LO16));
}
if (!isImm()) return false;
const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
@@ -3629,7 +3629,7 @@ public:
Inst.addOperand(MCOperand::createImm(Imm == 48 ? 1 : 0));
}
- void print(raw_ostream &OS) const override;
+ void print(raw_ostream &OS, const MCAsmInfo &MAI) const override;
static std::unique_ptr<ARMOperand> CreateITMask(unsigned Mask, SMLoc S,
ARMAsmParser &Parser) {
@@ -3979,7 +3979,7 @@ public:
} // end anonymous namespace.
-void ARMOperand::print(raw_ostream &OS) const {
+void ARMOperand::print(raw_ostream &OS, const MCAsmInfo &MAI) const {
auto RegName = [](MCRegister Reg) {
if (Reg)
return ARMInstPrinter::getRegisterName(Reg);
@@ -4024,7 +4024,7 @@ void ARMOperand::print(raw_ostream &OS) const {
OS << "<banked reg: " << getBankedReg() << ">";
break;
case k_Immediate:
- OS << *getImm();
+ MAI.printExpr(OS, *getImm());
break;
case k_MemBarrierOpt:
OS << "<ARM_MB::" << MemBOptToString(getMemBarrierOpt(), false) << ">";
@@ -4039,8 +4039,10 @@ void ARMOperand::print(raw_ostream &OS) const {
OS << "<memory";
if (Memory.BaseRegNum)
OS << " base:" << RegName(Memory.BaseRegNum);
- if (Memory.OffsetImm)
- OS << " offset-imm:" << *Memory.OffsetImm;
+ if (Memory.OffsetImm) {
+ OS << " offset-imm:";
+ MAI.printExpr(OS, *Memory.OffsetImm);
+ }
if (Memory.OffsetRegNum)
OS << " offset-reg:" << (Memory.isNegative ? "-" : "")
<< RegName(Memory.OffsetRegNum);
@@ -4094,7 +4096,8 @@ void ARMOperand::print(raw_ostream &OS) const {
<< ModImm.Rot << ")>";
break;
case k_ConstantPoolImmediate:
- OS << "<constant_pool_imm #" << *getConstantPoolImm();
+ OS << "<constant_pool_imm #";
+ MAI.printExpr(OS, *getConstantPoolImm());
break;
case k_BitfieldDescriptor:
OS << "<bitfield " << "lsb: " << Bitfield.LSB
@@ -5523,7 +5526,7 @@ ParseStatus ARMAsmParser::parseRotImm(OperandVector &Operands) {
ParseStatus ARMAsmParser::parseModImm(OperandVector &Operands) {
MCAsmParser &Parser = getParser();
- MCAsmLexer &Lexer = getLexer();
+ AsmLexer &Lexer = getLexer();
int64_t Imm1, Imm2;
SMLoc S = Parser.getTok().getLoc();
@@ -6424,16 +6427,16 @@ bool ARMAsmParser::parseOperand(OperandVector &Operands, StringRef Mnemonic) {
// ":upper8_15:", expression prefixes
// FIXME: Check it's an expression prefix,
// e.g. (FOO - :lower16:BAR) isn't legal.
- ARMMCExpr::VariantKind RefKind;
- if (parsePrefix(RefKind))
+ ARM::Specifier Spec;
+ if (parsePrefix(Spec))
return true;
const MCExpr *SubExprVal;
if (getParser().parseExpression(SubExprVal))
return true;
- const MCExpr *ExprVal = ARMMCExpr::create(RefKind, SubExprVal,
- getContext());
+ const auto *ExprVal =
+ MCSpecifierExpr::create(SubExprVal, Spec, getContext(), S);
E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
Operands.push_back(ARMOperand::CreateImm(ExprVal, S, E, *this));
return false;
@@ -6472,9 +6475,9 @@ bool ARMAsmParser::parseImmExpr(int64_t &Out) {
// parsePrefix - Parse ARM 16-bit relocations expression prefixes, i.e.
// :lower16: and :upper16: and Thumb 8-bit relocation expression prefixes, i.e.
// :upper8_15:, :upper0_7:, :lower8_15: and :lower0_7:
-bool ARMAsmParser::parsePrefix(ARMMCExpr::VariantKind &RefKind) {
+bool ARMAsmParser::parsePrefix(ARM::Specifier &Spec) {
MCAsmParser &Parser = getParser();
- RefKind = ARMMCExpr::VK_ARM_None;
+ Spec = ARM::S_None;
// consume an optional '#' (GNU compatibility)
if (getLexer().is(AsmToken::Hash))
@@ -6496,15 +6499,15 @@ bool ARMAsmParser::parsePrefix(ARMMCExpr::VariantKind &RefKind) {
};
static const struct PrefixEntry {
const char *Spelling;
- ARMMCExpr::VariantKind VariantKind;
+ ARM::Specifier Spec;
uint8_t SupportedFormats;
} PrefixEntries[] = {
- {"upper16", ARMMCExpr::VK_ARM_HI16, COFF | ELF | MACHO},
- {"lower16", ARMMCExpr::VK_ARM_LO16, COFF | ELF | MACHO},
- {"upper8_15", ARMMCExpr::VK_ARM_HI_8_15, ELF},
- {"upper0_7", ARMMCExpr::VK_ARM_HI_0_7, ELF},
- {"lower8_15", ARMMCExpr::VK_ARM_LO_8_15, ELF},
- {"lower0_7", ARMMCExpr::VK_ARM_LO_0_7, ELF},
+ {"upper16", ARM::S_HI16, COFF | ELF | MACHO},
+ {"lower16", ARM::S_LO16, COFF | ELF | MACHO},
+ {"upper8_15", ARM::S_HI_8_15, ELF},
+ {"upper0_7", ARM::S_HI_0_7, ELF},
+ {"lower8_15", ARM::S_LO_8_15, ELF},
+ {"lower0_7", ARM::S_LO_0_7, ELF},
};
StringRef IDVal = Parser.getTok().getIdentifier();
@@ -6546,7 +6549,7 @@ bool ARMAsmParser::parsePrefix(ARMMCExpr::VariantKind &RefKind) {
return true;
}
- RefKind = Prefix->VariantKind;
+ Spec = Prefix->Spec;
Parser.Lex();
if (getLexer().isNot(AsmToken::Colon)) {
@@ -6880,11 +6883,11 @@ static bool isThumbI8Relocation(MCParsedAsmOperand &MCOp) {
const MCExpr *E = dyn_cast<MCExpr>(Op.getImm());
if (!E)
return false;
- const ARMMCExpr *ARM16Expr = dyn_cast<ARMMCExpr>(E);
- if (ARM16Expr && (ARM16Expr->getKind() == ARMMCExpr::VK_ARM_HI_8_15 ||
- ARM16Expr->getKind() == ARMMCExpr::VK_ARM_HI_0_7 ||
- ARM16Expr->getKind() == ARMMCExpr::VK_ARM_LO_8_15 ||
- ARM16Expr->getKind() == ARMMCExpr::VK_ARM_LO_0_7))
+ auto *ARM16Expr = dyn_cast<MCSpecifierExpr>(E);
+ if (ARM16Expr && (ARM16Expr->getSpecifier() == ARM::S_HI_8_15 ||
+ ARM16Expr->getSpecifier() == ARM::S_HI_0_7 ||
+ ARM16Expr->getSpecifier() == ARM::S_LO_8_15 ||
+ ARM16Expr->getSpecifier() == ARM::S_LO_0_7))
return true;
return false;
}
@@ -6982,7 +6985,7 @@ void ARMAsmParser::fixupGNULDRDAlias(StringRef Mnemonic,
}
if (Op2.getReg() == ARM::PC)
return;
- unsigned PairedReg = GPR.getRegister(RtEncoding + 1);
+ MCRegister PairedReg = GPR.getRegister(RtEncoding + 1);
if (!PairedReg || PairedReg == ARM::PC ||
(PairedReg == ARM::SP && !hasV8Ops()))
return;
@@ -8287,9 +8290,9 @@ bool ARMAsmParser::validateInstruction(MCInst &Inst,
if (CE) break;
const MCExpr *E = dyn_cast<MCExpr>(Op.getImm());
if (!E) break;
- const ARMMCExpr *ARM16Expr = dyn_cast<ARMMCExpr>(E);
- if (!ARM16Expr || (ARM16Expr->getKind() != ARMMCExpr::VK_ARM_HI16 &&
- ARM16Expr->getKind() != ARMMCExpr::VK_ARM_LO16))
+ auto *ARM16Expr = dyn_cast<MCSpecifierExpr>(E);
+ if (!ARM16Expr || (ARM16Expr->getSpecifier() != ARM::S_HI16 &&
+ ARM16Expr->getSpecifier() != ARM::S_LO16))
return Error(
Op.getStartLoc(),
"immediate expression for mov requires :lower16: or :upper16");
@@ -8652,6 +8655,37 @@ bool ARMAsmParser::validateInstruction(MCInst &Inst,
"coprocessor must be configured as GCP");
break;
}
+
+ case ARM::VTOSHH:
+ case ARM::VTOUHH:
+ case ARM::VTOSLH:
+ case ARM::VTOULH:
+ case ARM::VTOSHS:
+ case ARM::VTOUHS:
+ case ARM::VTOSLS:
+ case ARM::VTOULS:
+ case ARM::VTOSHD:
+ case ARM::VTOUHD:
+ case ARM::VTOSLD:
+ case ARM::VTOULD:
+ case ARM::VSHTOH:
+ case ARM::VUHTOH:
+ case ARM::VSLTOH:
+ case ARM::VULTOH:
+ case ARM::VSHTOS:
+ case ARM::VUHTOS:
+ case ARM::VSLTOS:
+ case ARM::VULTOS:
+ case ARM::VSHTOD:
+ case ARM::VUHTOD:
+ case ARM::VSLTOD:
+ case ARM::VULTOD: {
+ if (Operands[MnemonicOpsEndInd]->getReg() !=
+ Operands[MnemonicOpsEndInd + 1]->getReg())
+ return Error(Operands[MnemonicOpsEndInd]->getStartLoc(),
+ "source and destination registers must be the same");
+ break;
+ }
}
return false;
@@ -9034,7 +9068,6 @@ bool ARMAsmParser::processInstruction(MCInst &Inst,
Out.emitLabel(Dot);
const MCExpr *OpExpr = Inst.getOperand(2).getExpr();
const MCExpr *InstPC = MCSymbolRefExpr::create(Dot,
- MCSymbolRefExpr::VK_None,
getContext());
const MCExpr *Const8 = MCConstantExpr::create(8, getContext());
const MCExpr *ReadPC = MCBinaryExpr::createAdd(InstPC, Const8,
@@ -11624,7 +11657,7 @@ bool ARMAsmParser::parseDirectiveThumb(SMLoc L) {
if (!isThumb())
SwitchMode();
- getParser().getStreamer().emitAssemblerFlag(MCAF_Code16);
+ getTargetStreamer().emitCode16();
getParser().getStreamer().emitCodeAlignment(Align(2), &getSTI(), 0);
return false;
}
@@ -11637,42 +11670,11 @@ bool ARMAsmParser::parseDirectiveARM(SMLoc L) {
if (isThumb())
SwitchMode();
- getParser().getStreamer().emitAssemblerFlag(MCAF_Code32);
+ getTargetStreamer().emitCode32();
getParser().getStreamer().emitCodeAlignment(Align(4), &getSTI(), 0);
return false;
}
-MCSymbolRefExpr::VariantKind
-ARMAsmParser::getVariantKindForName(StringRef Name) const {
- return StringSwitch<MCSymbolRefExpr::VariantKind>(Name.lower())
- .Case("funcdesc", MCSymbolRefExpr::VK_FUNCDESC)
- .Case("got", MCSymbolRefExpr::VK_GOT)
- .Case("got_prel", MCSymbolRefExpr::VK_ARM_GOT_PREL)
- .Case("gotfuncdesc", MCSymbolRefExpr::VK_GOTFUNCDESC)
- .Case("gotoff", MCSymbolRefExpr::VK_GOTOFF)
- .Case("gotofffuncdesc", MCSymbolRefExpr::VK_GOTOFFFUNCDESC)
- .Case("gottpoff", MCSymbolRefExpr::VK_GOTTPOFF)
- .Case("gottpoff_fdpic", MCSymbolRefExpr::VK_GOTTPOFF_FDPIC)
- .Case("imgrel", MCSymbolRefExpr::VK_COFF_IMGREL32)
- .Case("none", MCSymbolRefExpr::VK_ARM_NONE)
- .Case("plt", MCSymbolRefExpr::VK_PLT)
- .Case("prel31", MCSymbolRefExpr::VK_ARM_PREL31)
- .Case("sbrel", MCSymbolRefExpr::VK_ARM_SBREL)
- .Case("secrel32", MCSymbolRefExpr::VK_SECREL)
- .Case("target1", MCSymbolRefExpr::VK_ARM_TARGET1)
- .Case("target2", MCSymbolRefExpr::VK_ARM_TARGET2)
- .Case("tlscall", MCSymbolRefExpr::VK_TLSCALL)
- .Case("tlsdesc", MCSymbolRefExpr::VK_TLSDESC)
- .Case("tlsgd", MCSymbolRefExpr::VK_TLSGD)
- .Case("tlsgd_fdpic", MCSymbolRefExpr::VK_TLSGD_FDPIC)
- .Case("tlsld", MCSymbolRefExpr::VK_TLSLD)
- .Case("tlsldm", MCSymbolRefExpr::VK_TLSLDM)
- .Case("tlsldm_fdpic", MCSymbolRefExpr::VK_TLSLDM_FDPIC)
- .Case("tlsldo", MCSymbolRefExpr::VK_ARM_TLSLDO)
- .Case("tpoff", MCSymbolRefExpr::VK_TPOFF)
- .Default(MCSymbolRefExpr::VK_Invalid);
-}
-
void ARMAsmParser::doBeforeLabelEmit(MCSymbol *Symbol, SMLoc IDLoc) {
// We need to flush the current implicit IT block on a label, because it is
// not legal to branch into an IT block.
@@ -11681,7 +11683,7 @@ void ARMAsmParser::doBeforeLabelEmit(MCSymbol *Symbol, SMLoc IDLoc) {
void ARMAsmParser::onLabelParsed(MCSymbol *Symbol) {
if (NextSymbolIsThumb) {
- getParser().getStreamer().emitThumbFunc(Symbol);
+ getTargetStreamer().emitThumbFunc(Symbol);
NextSymbolIsThumb = false;
}
}
@@ -11701,7 +11703,7 @@ bool ARMAsmParser::parseDirectiveThumbFunc(SMLoc L) {
Parser.getTok().is(AsmToken::String)) {
MCSymbol *Func = getParser().getContext().getOrCreateSymbol(
Parser.getTok().getIdentifier());
- getParser().getStreamer().emitThumbFunc(Func);
+ getTargetStreamer().emitThumbFunc(Func);
Parser.Lex();
if (parseEOL())
return true;
@@ -11716,7 +11718,7 @@ bool ARMAsmParser::parseDirectiveThumbFunc(SMLoc L) {
if (!isThumb())
SwitchMode();
- getParser().getStreamer().emitAssemblerFlag(MCAF_Code16);
+ getTargetStreamer().emitCode16();
NextSymbolIsThumb = true;
return false;
@@ -11769,14 +11771,14 @@ bool ARMAsmParser::parseDirectiveCode(SMLoc L) {
if (!isThumb())
SwitchMode();
- getParser().getStreamer().emitAssemblerFlag(MCAF_Code16);
+ getTargetStreamer().emitCode16();
} else {
if (!hasARM())
return Error(L, "target does not support ARM mode");
if (isThumb())
SwitchMode();
- getParser().getStreamer().emitAssemblerFlag(MCAF_Code32);
+ getTargetStreamer().emitCode32();
}
return false;
@@ -11789,9 +11791,8 @@ bool ARMAsmParser::parseDirectiveReq(StringRef Name, SMLoc L) {
Parser.Lex(); // Eat the '.req' token.
MCRegister Reg;
SMLoc SRegLoc, ERegLoc;
- if (check(parseRegister(Reg, SRegLoc, ERegLoc), SRegLoc,
- "register name expected") ||
- parseEOL())
+ const bool parseResult = parseRegister(Reg, SRegLoc, ERegLoc);
+ if (check(parseResult, SRegLoc, "register name expected") || parseEOL())
return true;
if (RegisterReqs.insert(std::make_pair(Name, Reg)).first->second != Reg)
@@ -11825,8 +11826,10 @@ void ARMAsmParser::FixModeAfterArchChange(bool WasThumb, SMLoc Loc) {
SwitchMode();
} else {
// Mode switch forced, because the new arch doesn't support the old mode.
- getParser().getStreamer().emitAssemblerFlag(isThumb() ? MCAF_Code16
- : MCAF_Code32);
+ if (isThumb())
+ getTargetStreamer().emitCode16();
+ else
+ getTargetStreamer().emitCode32();
// Warn about the implcit mode switch. GAS does not switch modes here,
// but instead stays in the old mode, reporting an error on any following
// instructions as the mode does not exist on the target.
@@ -11847,7 +11850,6 @@ bool ARMAsmParser::parseDirectiveArch(SMLoc L) {
return Error(L, "Unknown arch name");
bool WasThumb = isThumb();
- Triple T;
MCSubtargetInfo &STI = copySTI();
STI.setDefaultFeatures("", /*TuneCPU*/ "",
("+" + ARM::getArchName(ID)).str());
@@ -12437,9 +12439,9 @@ bool ARMAsmParser::parseDirectiveTLSDescSeq(SMLoc L) {
if (getLexer().isNot(AsmToken::Identifier))
return TokError("expected variable after '.tlsdescseq' directive");
- const MCSymbolRefExpr *SRE =
- MCSymbolRefExpr::create(Parser.getTok().getIdentifier(),
- MCSymbolRefExpr::VK_ARM_TLSDESCSEQ, getContext());
+ auto *Sym = getContext().getOrCreateSymbol(Parser.getTok().getIdentifier());
+ const auto *SRE =
+ MCSymbolRefExpr::create(Sym, ARM::S_TLSDESCSEQ, getContext());
Lex();
if (parseEOL())
@@ -12723,7 +12725,7 @@ bool ARMAsmParser::parseDirectiveSEHCustom(SMLoc L) {
}
/// Force static initialization.
-extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeARMAsmParser() {
+extern "C" LLVM_ABI LLVM_EXTERNAL_VISIBILITY void LLVMInitializeARMAsmParser() {
RegisterMCAsmParser<ARMAsmParser> X(getTheARMLETarget());
RegisterMCAsmParser<ARMAsmParser> Y(getTheARMBETarget());
RegisterMCAsmParser<ARMAsmParser> A(getTheThumbLETarget());
@@ -12971,7 +12973,7 @@ bool ARMAsmParser::enableArchExtFeature(StringRef Name, SMLoc &ExtLoc) {
{ARM::AEK_CRYPTO,
{Feature_HasV8Bit},
{ARM::FeatureCrypto, ARM::FeatureNEON, ARM::FeatureFPARMv8}},
- {(ARM::AEK_DSP | ARM::AEK_SIMD | ARM::AEK_FP),
+ {(ARM::AEK_DSP | ARM::AEK_MVE | ARM::AEK_FP),
{Feature_HasV8_1MMainlineBit},
{ARM::HasMVEFloatOps}},
{ARM::AEK_FP,