ARMAsmParser.cpp revision 4a5ffb399f841783c201c599b88d576757f1922e
1//===-- ARMAsmParser.cpp - Parse ARM assembly to MCInst instructions ------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9 10#include "ARM.h" 11#include "ARMBaseRegisterInfo.h" 12#include "ARMSubtarget.h" 13#include "MCTargetDesc/ARMAddressingModes.h" 14#include "MCTargetDesc/ARMMCExpr.h" 15#include "llvm/MC/MCParser/MCAsmLexer.h" 16#include "llvm/MC/MCParser/MCAsmParser.h" 17#include "llvm/MC/MCParser/MCParsedAsmOperand.h" 18#include "llvm/MC/MCAsmInfo.h" 19#include "llvm/MC/MCContext.h" 20#include "llvm/MC/MCStreamer.h" 21#include "llvm/MC/MCExpr.h" 22#include "llvm/MC/MCInst.h" 23#include "llvm/MC/MCSubtargetInfo.h" 24#include "llvm/Target/TargetRegistry.h" 25#include "llvm/Target/TargetAsmParser.h" 26#include "llvm/Support/SourceMgr.h" 27#include "llvm/Support/raw_ostream.h" 28#include "llvm/ADT/OwningPtr.h" 29#include "llvm/ADT/SmallVector.h" 30#include "llvm/ADT/StringExtras.h" 31#include "llvm/ADT/StringSwitch.h" 32#include "llvm/ADT/Twine.h" 33 34using namespace llvm; 35 36namespace { 37 38class ARMOperand; 39 40class ARMAsmParser : public TargetAsmParser { 41 MCSubtargetInfo &STI; 42 MCAsmParser &Parser; 43 44 MCAsmParser &getParser() const { return Parser; } 45 MCAsmLexer &getLexer() const { return Parser.getLexer(); } 46 47 void Warning(SMLoc L, const Twine &Msg) { Parser.Warning(L, Msg); } 48 bool Error(SMLoc L, const Twine &Msg) { return Parser.Error(L, Msg); } 49 50 int TryParseRegister(); 51 virtual bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc); 52 bool TryParseRegisterWithWriteBack(SmallVectorImpl<MCParsedAsmOperand*> &); 53 int TryParseShiftRegister(SmallVectorImpl<MCParsedAsmOperand*> &); 54 bool ParseRegisterList(SmallVectorImpl<MCParsedAsmOperand*> &); 55 bool ParseMemory(SmallVectorImpl<MCParsedAsmOperand*> &, 56 ARMII::AddrMode AddrMode); 57 bool ParseOperand(SmallVectorImpl<MCParsedAsmOperand*> &, StringRef Mnemonic); 58 bool ParsePrefix(ARMMCExpr::VariantKind &RefKind); 59 const MCExpr *ApplyPrefixToExpr(const MCExpr *E, 60 MCSymbolRefExpr::VariantKind Variant); 61 62 63 bool ParseMemoryOffsetReg(bool &Negative, 64 bool &OffsetRegShifted, 65 enum ARM_AM::ShiftOpc &ShiftType, 66 const MCExpr *&ShiftAmount, 67 const MCExpr *&Offset, 68 bool &OffsetIsReg, 69 int &OffsetRegNum, 70 SMLoc &E); 71 bool ParseShift(enum ARM_AM::ShiftOpc &St, 72 const MCExpr *&ShiftAmount, SMLoc &E); 73 bool ParseDirectiveWord(unsigned Size, SMLoc L); 74 bool ParseDirectiveThumb(SMLoc L); 75 bool ParseDirectiveThumbFunc(SMLoc L); 76 bool ParseDirectiveCode(SMLoc L); 77 bool ParseDirectiveSyntax(SMLoc L); 78 79 bool MatchAndEmitInstruction(SMLoc IDLoc, 80 SmallVectorImpl<MCParsedAsmOperand*> &Operands, 81 MCStreamer &Out); 82 StringRef SplitMnemonic(StringRef Mnemonic, unsigned &PredicationCode, 83 bool &CarrySetting, unsigned &ProcessorIMod); 84 void GetMnemonicAcceptInfo(StringRef Mnemonic, bool &CanAcceptCarrySet, 85 bool &CanAcceptPredicationCode); 86 87 bool isThumb() const { 88 // FIXME: Can tablegen auto-generate this? 89 return (STI.getFeatureBits() & ARM::ModeThumb) != 0; 90 } 91 bool isThumbOne() const { 92 return isThumb() && (STI.getFeatureBits() & ARM::FeatureThumb2) == 0; 93 } 94 void SwitchMode() { 95 unsigned FB = ComputeAvailableFeatures(STI.ToggleFeature(ARM::ModeThumb)); 96 setAvailableFeatures(FB); 97 } 98 99 /// @name Auto-generated Match Functions 100 /// { 101 102#define GET_ASSEMBLER_HEADER 103#include "ARMGenAsmMatcher.inc" 104 105 /// } 106 107 OperandMatchResultTy tryParseCoprocNumOperand( 108 SmallVectorImpl<MCParsedAsmOperand*>&); 109 OperandMatchResultTy tryParseCoprocRegOperand( 110 SmallVectorImpl<MCParsedAsmOperand*>&); 111 OperandMatchResultTy tryParseMemBarrierOptOperand( 112 SmallVectorImpl<MCParsedAsmOperand*>&); 113 OperandMatchResultTy tryParseProcIFlagsOperand( 114 SmallVectorImpl<MCParsedAsmOperand*>&); 115 OperandMatchResultTy tryParseMSRMaskOperand( 116 SmallVectorImpl<MCParsedAsmOperand*>&); 117 OperandMatchResultTy tryParseMemMode2Operand( 118 SmallVectorImpl<MCParsedAsmOperand*>&); 119 OperandMatchResultTy tryParseMemMode3Operand( 120 SmallVectorImpl<MCParsedAsmOperand*>&); 121 OperandMatchResultTy parsePKHImm(SmallVectorImpl<MCParsedAsmOperand*> &O, 122 StringRef Op, int Low, int High); 123 OperandMatchResultTy parsePKHLSLImm(SmallVectorImpl<MCParsedAsmOperand*> &O) { 124 return parsePKHImm(O, "lsl", 0, 31); 125 } 126 OperandMatchResultTy parsePKHASRImm(SmallVectorImpl<MCParsedAsmOperand*> &O) { 127 return parsePKHImm(O, "asr", 1, 32); 128 } 129 OperandMatchResultTy parseSetEndImm(SmallVectorImpl<MCParsedAsmOperand*>&); 130 131 // Asm Match Converter Methods 132 bool CvtLdWriteBackRegAddrMode2(MCInst &Inst, unsigned Opcode, 133 const SmallVectorImpl<MCParsedAsmOperand*> &); 134 bool CvtStWriteBackRegAddrMode2(MCInst &Inst, unsigned Opcode, 135 const SmallVectorImpl<MCParsedAsmOperand*> &); 136 bool CvtLdWriteBackRegAddrMode3(MCInst &Inst, unsigned Opcode, 137 const SmallVectorImpl<MCParsedAsmOperand*> &); 138 bool CvtStWriteBackRegAddrMode3(MCInst &Inst, unsigned Opcode, 139 const SmallVectorImpl<MCParsedAsmOperand*> &); 140 141public: 142 ARMAsmParser(MCSubtargetInfo &_STI, MCAsmParser &_Parser) 143 : TargetAsmParser(), STI(_STI), Parser(_Parser) { 144 MCAsmParserExtension::Initialize(_Parser); 145 146 // Initialize the set of available features. 147 setAvailableFeatures(ComputeAvailableFeatures(STI.getFeatureBits())); 148 } 149 150 virtual bool ParseInstruction(StringRef Name, SMLoc NameLoc, 151 SmallVectorImpl<MCParsedAsmOperand*> &Operands); 152 virtual bool ParseDirective(AsmToken DirectiveID); 153}; 154} // end anonymous namespace 155 156namespace { 157 158/// ARMOperand - Instances of this class represent a parsed ARM machine 159/// instruction. 160class ARMOperand : public MCParsedAsmOperand { 161 enum KindTy { 162 CondCode, 163 CCOut, 164 CoprocNum, 165 CoprocReg, 166 Immediate, 167 MemBarrierOpt, 168 Memory, 169 MSRMask, 170 ProcIFlags, 171 Register, 172 RegisterList, 173 DPRRegisterList, 174 SPRRegisterList, 175 ShiftedRegister, 176 ShiftedImmediate, 177 Shifter, 178 Token 179 } Kind; 180 181 SMLoc StartLoc, EndLoc; 182 SmallVector<unsigned, 8> Registers; 183 184 union { 185 struct { 186 ARMCC::CondCodes Val; 187 } CC; 188 189 struct { 190 ARM_MB::MemBOpt Val; 191 } MBOpt; 192 193 struct { 194 unsigned Val; 195 } Cop; 196 197 struct { 198 ARM_PROC::IFlags Val; 199 } IFlags; 200 201 struct { 202 unsigned Val; 203 } MMask; 204 205 struct { 206 const char *Data; 207 unsigned Length; 208 } Tok; 209 210 struct { 211 unsigned RegNum; 212 } Reg; 213 214 struct { 215 const MCExpr *Val; 216 } Imm; 217 218 /// Combined record for all forms of ARM address expressions. 219 struct { 220 ARMII::AddrMode AddrMode; 221 unsigned BaseRegNum; 222 union { 223 unsigned RegNum; ///< Offset register num, when OffsetIsReg. 224 const MCExpr *Value; ///< Offset value, when !OffsetIsReg. 225 } Offset; 226 const MCExpr *ShiftAmount; // used when OffsetRegShifted is true 227 enum ARM_AM::ShiftOpc ShiftType; // used when OffsetRegShifted is true 228 unsigned OffsetRegShifted : 1; // only used when OffsetIsReg is true 229 unsigned Preindexed : 1; 230 unsigned Postindexed : 1; 231 unsigned OffsetIsReg : 1; 232 unsigned Negative : 1; // only used when OffsetIsReg is true 233 unsigned Writeback : 1; 234 } Mem; 235 236 struct { 237 ARM_AM::ShiftOpc ShiftTy; 238 unsigned Imm; 239 } Shift; 240 struct { 241 ARM_AM::ShiftOpc ShiftTy; 242 unsigned SrcReg; 243 unsigned ShiftReg; 244 unsigned ShiftImm; 245 } ShiftedReg; 246 struct { 247 ARM_AM::ShiftOpc ShiftTy; 248 unsigned SrcReg; 249 unsigned ShiftImm; 250 } ShiftedImm; 251 }; 252 253 ARMOperand(KindTy K) : MCParsedAsmOperand(), Kind(K) {} 254public: 255 ARMOperand(const ARMOperand &o) : MCParsedAsmOperand() { 256 Kind = o.Kind; 257 StartLoc = o.StartLoc; 258 EndLoc = o.EndLoc; 259 switch (Kind) { 260 case CondCode: 261 CC = o.CC; 262 break; 263 case Token: 264 Tok = o.Tok; 265 break; 266 case CCOut: 267 case Register: 268 Reg = o.Reg; 269 break; 270 case RegisterList: 271 case DPRRegisterList: 272 case SPRRegisterList: 273 Registers = o.Registers; 274 break; 275 case CoprocNum: 276 case CoprocReg: 277 Cop = o.Cop; 278 break; 279 case Immediate: 280 Imm = o.Imm; 281 break; 282 case MemBarrierOpt: 283 MBOpt = o.MBOpt; 284 break; 285 case Memory: 286 Mem = o.Mem; 287 break; 288 case MSRMask: 289 MMask = o.MMask; 290 break; 291 case ProcIFlags: 292 IFlags = o.IFlags; 293 break; 294 case Shifter: 295 Shift = o.Shift; 296 break; 297 case ShiftedRegister: 298 ShiftedReg = o.ShiftedReg; 299 break; 300 case ShiftedImmediate: 301 ShiftedImm = o.ShiftedImm; 302 break; 303 } 304 } 305 306 /// getStartLoc - Get the location of the first token of this operand. 307 SMLoc getStartLoc() const { return StartLoc; } 308 /// getEndLoc - Get the location of the last token of this operand. 309 SMLoc getEndLoc() const { return EndLoc; } 310 311 ARMCC::CondCodes getCondCode() const { 312 assert(Kind == CondCode && "Invalid access!"); 313 return CC.Val; 314 } 315 316 unsigned getCoproc() const { 317 assert((Kind == CoprocNum || Kind == CoprocReg) && "Invalid access!"); 318 return Cop.Val; 319 } 320 321 StringRef getToken() const { 322 assert(Kind == Token && "Invalid access!"); 323 return StringRef(Tok.Data, Tok.Length); 324 } 325 326 unsigned getReg() const { 327 assert((Kind == Register || Kind == CCOut) && "Invalid access!"); 328 return Reg.RegNum; 329 } 330 331 const SmallVectorImpl<unsigned> &getRegList() const { 332 assert((Kind == RegisterList || Kind == DPRRegisterList || 333 Kind == SPRRegisterList) && "Invalid access!"); 334 return Registers; 335 } 336 337 const MCExpr *getImm() const { 338 assert(Kind == Immediate && "Invalid access!"); 339 return Imm.Val; 340 } 341 342 ARM_MB::MemBOpt getMemBarrierOpt() const { 343 assert(Kind == MemBarrierOpt && "Invalid access!"); 344 return MBOpt.Val; 345 } 346 347 ARM_PROC::IFlags getProcIFlags() const { 348 assert(Kind == ProcIFlags && "Invalid access!"); 349 return IFlags.Val; 350 } 351 352 unsigned getMSRMask() const { 353 assert(Kind == MSRMask && "Invalid access!"); 354 return MMask.Val; 355 } 356 357 /// @name Memory Operand Accessors 358 /// @{ 359 ARMII::AddrMode getMemAddrMode() const { 360 return Mem.AddrMode; 361 } 362 unsigned getMemBaseRegNum() const { 363 return Mem.BaseRegNum; 364 } 365 unsigned getMemOffsetRegNum() const { 366 assert(Mem.OffsetIsReg && "Invalid access!"); 367 return Mem.Offset.RegNum; 368 } 369 const MCExpr *getMemOffset() const { 370 assert(!Mem.OffsetIsReg && "Invalid access!"); 371 return Mem.Offset.Value; 372 } 373 unsigned getMemOffsetRegShifted() const { 374 assert(Mem.OffsetIsReg && "Invalid access!"); 375 return Mem.OffsetRegShifted; 376 } 377 const MCExpr *getMemShiftAmount() const { 378 assert(Mem.OffsetIsReg && Mem.OffsetRegShifted && "Invalid access!"); 379 return Mem.ShiftAmount; 380 } 381 enum ARM_AM::ShiftOpc getMemShiftType() const { 382 assert(Mem.OffsetIsReg && Mem.OffsetRegShifted && "Invalid access!"); 383 return Mem.ShiftType; 384 } 385 bool getMemPreindexed() const { return Mem.Preindexed; } 386 bool getMemPostindexed() const { return Mem.Postindexed; } 387 bool getMemOffsetIsReg() const { return Mem.OffsetIsReg; } 388 bool getMemNegative() const { return Mem.Negative; } 389 bool getMemWriteback() const { return Mem.Writeback; } 390 391 /// @} 392 393 bool isCoprocNum() const { return Kind == CoprocNum; } 394 bool isCoprocReg() const { return Kind == CoprocReg; } 395 bool isCondCode() const { return Kind == CondCode; } 396 bool isCCOut() const { return Kind == CCOut; } 397 bool isImm() const { return Kind == Immediate; } 398 bool isImm0_255() const { 399 if (Kind != Immediate) 400 return false; 401 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 402 if (!CE) return false; 403 int64_t Value = CE->getValue(); 404 return Value >= 0 && Value < 256; 405 } 406 bool isImm0_7() const { 407 if (Kind != Immediate) 408 return false; 409 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 410 if (!CE) return false; 411 int64_t Value = CE->getValue(); 412 return Value >= 0 && Value < 8; 413 } 414 bool isImm0_15() const { 415 if (Kind != Immediate) 416 return false; 417 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 418 if (!CE) return false; 419 int64_t Value = CE->getValue(); 420 return Value >= 0 && Value < 16; 421 } 422 bool isImm0_31() const { 423 if (Kind != Immediate) 424 return false; 425 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 426 if (!CE) return false; 427 int64_t Value = CE->getValue(); 428 return Value >= 0 && Value < 32; 429 } 430 bool isImm1_32() const { 431 if (Kind != Immediate) 432 return false; 433 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 434 if (!CE) return false; 435 int64_t Value = CE->getValue(); 436 return Value > 0 && Value < 33; 437 } 438 bool isImm0_65535() const { 439 if (Kind != Immediate) 440 return false; 441 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 442 if (!CE) return false; 443 int64_t Value = CE->getValue(); 444 return Value >= 0 && Value < 65536; 445 } 446 bool isImm0_65535Expr() const { 447 if (Kind != Immediate) 448 return false; 449 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 450 // If it's not a constant expression, it'll generate a fixup and be 451 // handled later. 452 if (!CE) return true; 453 int64_t Value = CE->getValue(); 454 return Value >= 0 && Value < 65536; 455 } 456 bool isPKHLSLImm() const { 457 if (Kind != Immediate) 458 return false; 459 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 460 if (!CE) return false; 461 int64_t Value = CE->getValue(); 462 return Value >= 0 && Value < 32; 463 } 464 bool isPKHASRImm() const { 465 if (Kind != Immediate) 466 return false; 467 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 468 if (!CE) return false; 469 int64_t Value = CE->getValue(); 470 return Value > 0 && Value <= 32; 471 } 472 bool isARMSOImm() const { 473 if (Kind != Immediate) 474 return false; 475 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 476 if (!CE) return false; 477 int64_t Value = CE->getValue(); 478 return ARM_AM::getSOImmVal(Value) != -1; 479 } 480 bool isT2SOImm() const { 481 if (Kind != Immediate) 482 return false; 483 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 484 if (!CE) return false; 485 int64_t Value = CE->getValue(); 486 return ARM_AM::getT2SOImmVal(Value) != -1; 487 } 488 bool isSetEndImm() const { 489 if (Kind != Immediate) 490 return false; 491 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 492 if (!CE) return false; 493 int64_t Value = CE->getValue(); 494 return Value == 1 || Value == 0; 495 } 496 bool isReg() const { return Kind == Register; } 497 bool isRegList() const { return Kind == RegisterList; } 498 bool isDPRRegList() const { return Kind == DPRRegisterList; } 499 bool isSPRRegList() const { return Kind == SPRRegisterList; } 500 bool isToken() const { return Kind == Token; } 501 bool isMemBarrierOpt() const { return Kind == MemBarrierOpt; } 502 bool isMemory() const { return Kind == Memory; } 503 bool isShifter() const { return Kind == Shifter; } 504 bool isShiftedReg() const { return Kind == ShiftedRegister; } 505 bool isShiftedImm() const { return Kind == ShiftedImmediate; } 506 bool isMemMode2() const { 507 if (getMemAddrMode() != ARMII::AddrMode2) 508 return false; 509 510 if (getMemOffsetIsReg()) 511 return true; 512 513 if (getMemNegative() && 514 !(getMemPostindexed() || getMemPreindexed())) 515 return false; 516 517 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 518 if (!CE) return false; 519 int64_t Value = CE->getValue(); 520 521 // The offset must be in the range 0-4095 (imm12). 522 if (Value > 4095 || Value < -4095) 523 return false; 524 525 return true; 526 } 527 bool isMemMode3() const { 528 if (getMemAddrMode() != ARMII::AddrMode3) 529 return false; 530 531 if (getMemOffsetIsReg()) { 532 if (getMemOffsetRegShifted()) 533 return false; // No shift with offset reg allowed 534 return true; 535 } 536 537 if (getMemNegative() && 538 !(getMemPostindexed() || getMemPreindexed())) 539 return false; 540 541 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 542 if (!CE) return false; 543 int64_t Value = CE->getValue(); 544 545 // The offset must be in the range 0-255 (imm8). 546 if (Value > 255 || Value < -255) 547 return false; 548 549 return true; 550 } 551 bool isMemMode5() const { 552 if (!isMemory() || getMemOffsetIsReg() || getMemWriteback() || 553 getMemNegative()) 554 return false; 555 556 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 557 if (!CE) return false; 558 559 // The offset must be a multiple of 4 in the range 0-1020. 560 int64_t Value = CE->getValue(); 561 return ((Value & 0x3) == 0 && Value <= 1020 && Value >= -1020); 562 } 563 bool isMemMode7() const { 564 if (!isMemory() || 565 getMemPreindexed() || 566 getMemPostindexed() || 567 getMemOffsetIsReg() || 568 getMemNegative() || 569 getMemWriteback()) 570 return false; 571 572 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 573 if (!CE) return false; 574 575 if (CE->getValue()) 576 return false; 577 578 return true; 579 } 580 bool isMemModeRegThumb() const { 581 if (!isMemory() || !getMemOffsetIsReg() || getMemWriteback()) 582 return false; 583 return true; 584 } 585 bool isMemModeImmThumb() const { 586 if (!isMemory() || getMemOffsetIsReg() || getMemWriteback()) 587 return false; 588 589 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 590 if (!CE) return false; 591 592 // The offset must be a multiple of 4 in the range 0-124. 593 uint64_t Value = CE->getValue(); 594 return ((Value & 0x3) == 0 && Value <= 124); 595 } 596 bool isMSRMask() const { return Kind == MSRMask; } 597 bool isProcIFlags() const { return Kind == ProcIFlags; } 598 599 void addExpr(MCInst &Inst, const MCExpr *Expr) const { 600 // Add as immediates when possible. Null MCExpr = 0. 601 if (Expr == 0) 602 Inst.addOperand(MCOperand::CreateImm(0)); 603 else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr)) 604 Inst.addOperand(MCOperand::CreateImm(CE->getValue())); 605 else 606 Inst.addOperand(MCOperand::CreateExpr(Expr)); 607 } 608 609 void addCondCodeOperands(MCInst &Inst, unsigned N) const { 610 assert(N == 2 && "Invalid number of operands!"); 611 Inst.addOperand(MCOperand::CreateImm(unsigned(getCondCode()))); 612 unsigned RegNum = getCondCode() == ARMCC::AL ? 0: ARM::CPSR; 613 Inst.addOperand(MCOperand::CreateReg(RegNum)); 614 } 615 616 void addCoprocNumOperands(MCInst &Inst, unsigned N) const { 617 assert(N == 1 && "Invalid number of operands!"); 618 Inst.addOperand(MCOperand::CreateImm(getCoproc())); 619 } 620 621 void addCoprocRegOperands(MCInst &Inst, unsigned N) const { 622 assert(N == 1 && "Invalid number of operands!"); 623 Inst.addOperand(MCOperand::CreateImm(getCoproc())); 624 } 625 626 void addCCOutOperands(MCInst &Inst, unsigned N) const { 627 assert(N == 1 && "Invalid number of operands!"); 628 Inst.addOperand(MCOperand::CreateReg(getReg())); 629 } 630 631 void addRegOperands(MCInst &Inst, unsigned N) const { 632 assert(N == 1 && "Invalid number of operands!"); 633 Inst.addOperand(MCOperand::CreateReg(getReg())); 634 } 635 636 void addShiftedRegOperands(MCInst &Inst, unsigned N) const { 637 assert(N == 3 && "Invalid number of operands!"); 638 assert(isShiftedReg() && "addShiftedRegOperands() on non ShiftedReg!"); 639 Inst.addOperand(MCOperand::CreateReg(ShiftedReg.SrcReg)); 640 Inst.addOperand(MCOperand::CreateReg(ShiftedReg.ShiftReg)); 641 Inst.addOperand(MCOperand::CreateImm( 642 ARM_AM::getSORegOpc(ShiftedReg.ShiftTy, ShiftedReg.ShiftImm))); 643 } 644 645 void addShiftedImmOperands(MCInst &Inst, unsigned N) const { 646 assert(N == 2 && "Invalid number of operands!"); 647 assert(isShiftedImm() && "addShiftedImmOperands() on non ShiftedImm!"); 648 Inst.addOperand(MCOperand::CreateReg(ShiftedImm.SrcReg)); 649 Inst.addOperand(MCOperand::CreateImm( 650 ARM_AM::getSORegOpc(ShiftedImm.ShiftTy, ShiftedImm.ShiftImm))); 651 } 652 653 654 void addShifterOperands(MCInst &Inst, unsigned N) const { 655 assert(N == 1 && "Invalid number of operands!"); 656 Inst.addOperand(MCOperand::CreateImm( 657 ARM_AM::getSORegOpc(Shift.ShiftTy, 0))); 658 } 659 660 void addRegListOperands(MCInst &Inst, unsigned N) const { 661 assert(N == 1 && "Invalid number of operands!"); 662 const SmallVectorImpl<unsigned> &RegList = getRegList(); 663 for (SmallVectorImpl<unsigned>::const_iterator 664 I = RegList.begin(), E = RegList.end(); I != E; ++I) 665 Inst.addOperand(MCOperand::CreateReg(*I)); 666 } 667 668 void addDPRRegListOperands(MCInst &Inst, unsigned N) const { 669 addRegListOperands(Inst, N); 670 } 671 672 void addSPRRegListOperands(MCInst &Inst, unsigned N) const { 673 addRegListOperands(Inst, N); 674 } 675 676 void addImmOperands(MCInst &Inst, unsigned N) const { 677 assert(N == 1 && "Invalid number of operands!"); 678 addExpr(Inst, getImm()); 679 } 680 681 void addImm0_255Operands(MCInst &Inst, unsigned N) const { 682 assert(N == 1 && "Invalid number of operands!"); 683 addExpr(Inst, getImm()); 684 } 685 686 void addImm0_7Operands(MCInst &Inst, unsigned N) const { 687 assert(N == 1 && "Invalid number of operands!"); 688 addExpr(Inst, getImm()); 689 } 690 691 void addImm0_15Operands(MCInst &Inst, unsigned N) const { 692 assert(N == 1 && "Invalid number of operands!"); 693 addExpr(Inst, getImm()); 694 } 695 696 void addImm0_31Operands(MCInst &Inst, unsigned N) const { 697 assert(N == 1 && "Invalid number of operands!"); 698 addExpr(Inst, getImm()); 699 } 700 701 void addImm1_32Operands(MCInst &Inst, unsigned N) const { 702 assert(N == 1 && "Invalid number of operands!"); 703 // The constant encodes as the immediate-1, and we store in the instruction 704 // the bits as encoded, so subtract off one here. 705 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 706 Inst.addOperand(MCOperand::CreateImm(CE->getValue() - 1)); 707 } 708 709 void addImm0_65535Operands(MCInst &Inst, unsigned N) const { 710 assert(N == 1 && "Invalid number of operands!"); 711 addExpr(Inst, getImm()); 712 } 713 714 void addImm0_65535ExprOperands(MCInst &Inst, unsigned N) const { 715 assert(N == 1 && "Invalid number of operands!"); 716 addExpr(Inst, getImm()); 717 } 718 719 void addPKHLSLImmOperands(MCInst &Inst, unsigned N) const { 720 assert(N == 1 && "Invalid number of operands!"); 721 addExpr(Inst, getImm()); 722 } 723 724 void addPKHASRImmOperands(MCInst &Inst, unsigned N) const { 725 assert(N == 1 && "Invalid number of operands!"); 726 // An ASR value of 32 encodes as 0, so that's how we want to add it to 727 // the instruction as well. 728 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm()); 729 int Val = CE->getValue(); 730 Inst.addOperand(MCOperand::CreateImm(Val == 32 ? 0 : Val)); 731 } 732 733 void addARMSOImmOperands(MCInst &Inst, unsigned N) const { 734 assert(N == 1 && "Invalid number of operands!"); 735 addExpr(Inst, getImm()); 736 } 737 738 void addT2SOImmOperands(MCInst &Inst, unsigned N) const { 739 assert(N == 1 && "Invalid number of operands!"); 740 addExpr(Inst, getImm()); 741 } 742 743 void addSetEndImmOperands(MCInst &Inst, unsigned N) const { 744 assert(N == 1 && "Invalid number of operands!"); 745 addExpr(Inst, getImm()); 746 } 747 748 void addMemBarrierOptOperands(MCInst &Inst, unsigned N) const { 749 assert(N == 1 && "Invalid number of operands!"); 750 Inst.addOperand(MCOperand::CreateImm(unsigned(getMemBarrierOpt()))); 751 } 752 753 void addMemMode7Operands(MCInst &Inst, unsigned N) const { 754 assert(N == 1 && isMemMode7() && "Invalid number of operands!"); 755 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 756 757 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 758 (void)CE; 759 assert((CE || CE->getValue() == 0) && 760 "No offset operand support in mode 7"); 761 } 762 763 void addMemMode2Operands(MCInst &Inst, unsigned N) const { 764 assert(isMemMode2() && "Invalid mode or number of operands!"); 765 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 766 unsigned IdxMode = (getMemPreindexed() | getMemPostindexed() << 1); 767 768 if (getMemOffsetIsReg()) { 769 Inst.addOperand(MCOperand::CreateReg(getMemOffsetRegNum())); 770 771 ARM_AM::AddrOpc AMOpc = getMemNegative() ? ARM_AM::sub : ARM_AM::add; 772 ARM_AM::ShiftOpc ShOpc = ARM_AM::no_shift; 773 int64_t ShiftAmount = 0; 774 775 if (getMemOffsetRegShifted()) { 776 ShOpc = getMemShiftType(); 777 const MCConstantExpr *CE = 778 dyn_cast<MCConstantExpr>(getMemShiftAmount()); 779 ShiftAmount = CE->getValue(); 780 } 781 782 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM2Opc(AMOpc, ShiftAmount, 783 ShOpc, IdxMode))); 784 return; 785 } 786 787 // Create a operand placeholder to always yield the same number of operands. 788 Inst.addOperand(MCOperand::CreateReg(0)); 789 790 // FIXME: #-0 is encoded differently than #0. Does the parser preserve 791 // the difference? 792 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 793 assert(CE && "Non-constant mode 2 offset operand!"); 794 int64_t Offset = CE->getValue(); 795 796 if (Offset >= 0) 797 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM2Opc(ARM_AM::add, 798 Offset, ARM_AM::no_shift, IdxMode))); 799 else 800 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM2Opc(ARM_AM::sub, 801 -Offset, ARM_AM::no_shift, IdxMode))); 802 } 803 804 void addMemMode3Operands(MCInst &Inst, unsigned N) const { 805 assert(isMemMode3() && "Invalid mode or number of operands!"); 806 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 807 unsigned IdxMode = (getMemPreindexed() | getMemPostindexed() << 1); 808 809 if (getMemOffsetIsReg()) { 810 Inst.addOperand(MCOperand::CreateReg(getMemOffsetRegNum())); 811 812 ARM_AM::AddrOpc AMOpc = getMemNegative() ? ARM_AM::sub : ARM_AM::add; 813 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM3Opc(AMOpc, 0, 814 IdxMode))); 815 return; 816 } 817 818 // Create a operand placeholder to always yield the same number of operands. 819 Inst.addOperand(MCOperand::CreateReg(0)); 820 821 // FIXME: #-0 is encoded differently than #0. Does the parser preserve 822 // the difference? 823 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 824 assert(CE && "Non-constant mode 3 offset operand!"); 825 int64_t Offset = CE->getValue(); 826 827 if (Offset >= 0) 828 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM3Opc(ARM_AM::add, 829 Offset, IdxMode))); 830 else 831 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM3Opc(ARM_AM::sub, 832 -Offset, IdxMode))); 833 } 834 835 void addMemMode5Operands(MCInst &Inst, unsigned N) const { 836 assert(N == 2 && isMemMode5() && "Invalid number of operands!"); 837 838 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 839 assert(!getMemOffsetIsReg() && "Invalid mode 5 operand"); 840 841 // FIXME: #-0 is encoded differently than #0. Does the parser preserve 842 // the difference? 843 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 844 assert(CE && "Non-constant mode 5 offset operand!"); 845 846 // The MCInst offset operand doesn't include the low two bits (like 847 // the instruction encoding). 848 int64_t Offset = CE->getValue() / 4; 849 if (Offset >= 0) 850 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM5Opc(ARM_AM::add, 851 Offset))); 852 else 853 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM5Opc(ARM_AM::sub, 854 -Offset))); 855 } 856 857 void addMemModeRegThumbOperands(MCInst &Inst, unsigned N) const { 858 assert(N == 2 && isMemModeRegThumb() && "Invalid number of operands!"); 859 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 860 Inst.addOperand(MCOperand::CreateReg(getMemOffsetRegNum())); 861 } 862 863 void addMemModeImmThumbOperands(MCInst &Inst, unsigned N) const { 864 assert(N == 2 && isMemModeImmThumb() && "Invalid number of operands!"); 865 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 866 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 867 assert(CE && "Non-constant mode offset operand!"); 868 Inst.addOperand(MCOperand::CreateImm(CE->getValue())); 869 } 870 871 void addMSRMaskOperands(MCInst &Inst, unsigned N) const { 872 assert(N == 1 && "Invalid number of operands!"); 873 Inst.addOperand(MCOperand::CreateImm(unsigned(getMSRMask()))); 874 } 875 876 void addProcIFlagsOperands(MCInst &Inst, unsigned N) const { 877 assert(N == 1 && "Invalid number of operands!"); 878 Inst.addOperand(MCOperand::CreateImm(unsigned(getProcIFlags()))); 879 } 880 881 virtual void print(raw_ostream &OS) const; 882 883 static ARMOperand *CreateCondCode(ARMCC::CondCodes CC, SMLoc S) { 884 ARMOperand *Op = new ARMOperand(CondCode); 885 Op->CC.Val = CC; 886 Op->StartLoc = S; 887 Op->EndLoc = S; 888 return Op; 889 } 890 891 static ARMOperand *CreateCoprocNum(unsigned CopVal, SMLoc S) { 892 ARMOperand *Op = new ARMOperand(CoprocNum); 893 Op->Cop.Val = CopVal; 894 Op->StartLoc = S; 895 Op->EndLoc = S; 896 return Op; 897 } 898 899 static ARMOperand *CreateCoprocReg(unsigned CopVal, SMLoc S) { 900 ARMOperand *Op = new ARMOperand(CoprocReg); 901 Op->Cop.Val = CopVal; 902 Op->StartLoc = S; 903 Op->EndLoc = S; 904 return Op; 905 } 906 907 static ARMOperand *CreateCCOut(unsigned RegNum, SMLoc S) { 908 ARMOperand *Op = new ARMOperand(CCOut); 909 Op->Reg.RegNum = RegNum; 910 Op->StartLoc = S; 911 Op->EndLoc = S; 912 return Op; 913 } 914 915 static ARMOperand *CreateToken(StringRef Str, SMLoc S) { 916 ARMOperand *Op = new ARMOperand(Token); 917 Op->Tok.Data = Str.data(); 918 Op->Tok.Length = Str.size(); 919 Op->StartLoc = S; 920 Op->EndLoc = S; 921 return Op; 922 } 923 924 static ARMOperand *CreateReg(unsigned RegNum, SMLoc S, SMLoc E) { 925 ARMOperand *Op = new ARMOperand(Register); 926 Op->Reg.RegNum = RegNum; 927 Op->StartLoc = S; 928 Op->EndLoc = E; 929 return Op; 930 } 931 932 static ARMOperand *CreateShiftedRegister(ARM_AM::ShiftOpc ShTy, 933 unsigned SrcReg, 934 unsigned ShiftReg, 935 unsigned ShiftImm, 936 SMLoc S, SMLoc E) { 937 ARMOperand *Op = new ARMOperand(ShiftedRegister); 938 Op->ShiftedReg.ShiftTy = ShTy; 939 Op->ShiftedReg.SrcReg = SrcReg; 940 Op->ShiftedReg.ShiftReg = ShiftReg; 941 Op->ShiftedReg.ShiftImm = ShiftImm; 942 Op->StartLoc = S; 943 Op->EndLoc = E; 944 return Op; 945 } 946 947 static ARMOperand *CreateShiftedImmediate(ARM_AM::ShiftOpc ShTy, 948 unsigned SrcReg, 949 unsigned ShiftImm, 950 SMLoc S, SMLoc E) { 951 ARMOperand *Op = new ARMOperand(ShiftedImmediate); 952 Op->ShiftedImm.ShiftTy = ShTy; 953 Op->ShiftedImm.SrcReg = SrcReg; 954 Op->ShiftedImm.ShiftImm = ShiftImm; 955 Op->StartLoc = S; 956 Op->EndLoc = E; 957 return Op; 958 } 959 960 static ARMOperand *CreateShifter(ARM_AM::ShiftOpc ShTy, 961 SMLoc S, SMLoc E) { 962 ARMOperand *Op = new ARMOperand(Shifter); 963 Op->Shift.ShiftTy = ShTy; 964 Op->StartLoc = S; 965 Op->EndLoc = E; 966 return Op; 967 } 968 969 static ARMOperand * 970 CreateRegList(const SmallVectorImpl<std::pair<unsigned, SMLoc> > &Regs, 971 SMLoc StartLoc, SMLoc EndLoc) { 972 KindTy Kind = RegisterList; 973 974 if (ARM::DPRRegClass.contains(Regs.front().first)) 975 Kind = DPRRegisterList; 976 else if (ARM::SPRRegClass.contains(Regs.front().first)) 977 Kind = SPRRegisterList; 978 979 ARMOperand *Op = new ARMOperand(Kind); 980 for (SmallVectorImpl<std::pair<unsigned, SMLoc> >::const_iterator 981 I = Regs.begin(), E = Regs.end(); I != E; ++I) 982 Op->Registers.push_back(I->first); 983 array_pod_sort(Op->Registers.begin(), Op->Registers.end()); 984 Op->StartLoc = StartLoc; 985 Op->EndLoc = EndLoc; 986 return Op; 987 } 988 989 static ARMOperand *CreateImm(const MCExpr *Val, SMLoc S, SMLoc E) { 990 ARMOperand *Op = new ARMOperand(Immediate); 991 Op->Imm.Val = Val; 992 Op->StartLoc = S; 993 Op->EndLoc = E; 994 return Op; 995 } 996 997 static ARMOperand *CreateMem(ARMII::AddrMode AddrMode, unsigned BaseRegNum, 998 bool OffsetIsReg, const MCExpr *Offset, 999 int OffsetRegNum, bool OffsetRegShifted, 1000 enum ARM_AM::ShiftOpc ShiftType, 1001 const MCExpr *ShiftAmount, bool Preindexed, 1002 bool Postindexed, bool Negative, bool Writeback, 1003 SMLoc S, SMLoc E) { 1004 assert((OffsetRegNum == -1 || OffsetIsReg) && 1005 "OffsetRegNum must imply OffsetIsReg!"); 1006 assert((!OffsetRegShifted || OffsetIsReg) && 1007 "OffsetRegShifted must imply OffsetIsReg!"); 1008 assert((Offset || OffsetIsReg) && 1009 "Offset must exists unless register offset is used!"); 1010 assert((!ShiftAmount || (OffsetIsReg && OffsetRegShifted)) && 1011 "Cannot have shift amount without shifted register offset!"); 1012 assert((!Offset || !OffsetIsReg) && 1013 "Cannot have expression offset and register offset!"); 1014 1015 ARMOperand *Op = new ARMOperand(Memory); 1016 Op->Mem.AddrMode = AddrMode; 1017 Op->Mem.BaseRegNum = BaseRegNum; 1018 Op->Mem.OffsetIsReg = OffsetIsReg; 1019 if (OffsetIsReg) 1020 Op->Mem.Offset.RegNum = OffsetRegNum; 1021 else 1022 Op->Mem.Offset.Value = Offset; 1023 Op->Mem.OffsetRegShifted = OffsetRegShifted; 1024 Op->Mem.ShiftType = ShiftType; 1025 Op->Mem.ShiftAmount = ShiftAmount; 1026 Op->Mem.Preindexed = Preindexed; 1027 Op->Mem.Postindexed = Postindexed; 1028 Op->Mem.Negative = Negative; 1029 Op->Mem.Writeback = Writeback; 1030 1031 Op->StartLoc = S; 1032 Op->EndLoc = E; 1033 return Op; 1034 } 1035 1036 static ARMOperand *CreateMemBarrierOpt(ARM_MB::MemBOpt Opt, SMLoc S) { 1037 ARMOperand *Op = new ARMOperand(MemBarrierOpt); 1038 Op->MBOpt.Val = Opt; 1039 Op->StartLoc = S; 1040 Op->EndLoc = S; 1041 return Op; 1042 } 1043 1044 static ARMOperand *CreateProcIFlags(ARM_PROC::IFlags IFlags, SMLoc S) { 1045 ARMOperand *Op = new ARMOperand(ProcIFlags); 1046 Op->IFlags.Val = IFlags; 1047 Op->StartLoc = S; 1048 Op->EndLoc = S; 1049 return Op; 1050 } 1051 1052 static ARMOperand *CreateMSRMask(unsigned MMask, SMLoc S) { 1053 ARMOperand *Op = new ARMOperand(MSRMask); 1054 Op->MMask.Val = MMask; 1055 Op->StartLoc = S; 1056 Op->EndLoc = S; 1057 return Op; 1058 } 1059}; 1060 1061} // end anonymous namespace. 1062 1063void ARMOperand::print(raw_ostream &OS) const { 1064 switch (Kind) { 1065 case CondCode: 1066 OS << "<ARMCC::" << ARMCondCodeToString(getCondCode()) << ">"; 1067 break; 1068 case CCOut: 1069 OS << "<ccout " << getReg() << ">"; 1070 break; 1071 case CoprocNum: 1072 OS << "<coprocessor number: " << getCoproc() << ">"; 1073 break; 1074 case CoprocReg: 1075 OS << "<coprocessor register: " << getCoproc() << ">"; 1076 break; 1077 case MSRMask: 1078 OS << "<mask: " << getMSRMask() << ">"; 1079 break; 1080 case Immediate: 1081 getImm()->print(OS); 1082 break; 1083 case MemBarrierOpt: 1084 OS << "<ARM_MB::" << MemBOptToString(getMemBarrierOpt()) << ">"; 1085 break; 1086 case Memory: 1087 OS << "<memory " 1088 << "am:" << ARMII::AddrModeToString(getMemAddrMode()) 1089 << " base:" << getMemBaseRegNum(); 1090 if (getMemOffsetIsReg()) { 1091 OS << " offset:<register " << getMemOffsetRegNum(); 1092 if (getMemOffsetRegShifted()) { 1093 OS << " offset-shift-type:" << getMemShiftType(); 1094 OS << " offset-shift-amount:" << *getMemShiftAmount(); 1095 } 1096 } else { 1097 OS << " offset:" << *getMemOffset(); 1098 } 1099 if (getMemOffsetIsReg()) 1100 OS << " (offset-is-reg)"; 1101 if (getMemPreindexed()) 1102 OS << " (pre-indexed)"; 1103 if (getMemPostindexed()) 1104 OS << " (post-indexed)"; 1105 if (getMemNegative()) 1106 OS << " (negative)"; 1107 if (getMemWriteback()) 1108 OS << " (writeback)"; 1109 OS << ">"; 1110 break; 1111 case ProcIFlags: { 1112 OS << "<ARM_PROC::"; 1113 unsigned IFlags = getProcIFlags(); 1114 for (int i=2; i >= 0; --i) 1115 if (IFlags & (1 << i)) 1116 OS << ARM_PROC::IFlagsToString(1 << i); 1117 OS << ">"; 1118 break; 1119 } 1120 case Register: 1121 OS << "<register " << getReg() << ">"; 1122 break; 1123 case Shifter: 1124 OS << "<shifter " << ARM_AM::getShiftOpcStr(Shift.ShiftTy) << ">"; 1125 break; 1126 case ShiftedRegister: 1127 OS << "<so_reg_reg " 1128 << ShiftedReg.SrcReg 1129 << ARM_AM::getShiftOpcStr(ARM_AM::getSORegShOp(ShiftedReg.ShiftImm)) 1130 << ", " << ShiftedReg.ShiftReg << ", " 1131 << ARM_AM::getSORegOffset(ShiftedReg.ShiftImm) 1132 << ">"; 1133 break; 1134 case ShiftedImmediate: 1135 OS << "<so_reg_imm " 1136 << ShiftedImm.SrcReg 1137 << ARM_AM::getShiftOpcStr(ARM_AM::getSORegShOp(ShiftedImm.ShiftImm)) 1138 << ", " << ARM_AM::getSORegOffset(ShiftedImm.ShiftImm) 1139 << ">"; 1140 break; 1141 case RegisterList: 1142 case DPRRegisterList: 1143 case SPRRegisterList: { 1144 OS << "<register_list "; 1145 1146 const SmallVectorImpl<unsigned> &RegList = getRegList(); 1147 for (SmallVectorImpl<unsigned>::const_iterator 1148 I = RegList.begin(), E = RegList.end(); I != E; ) { 1149 OS << *I; 1150 if (++I < E) OS << ", "; 1151 } 1152 1153 OS << ">"; 1154 break; 1155 } 1156 case Token: 1157 OS << "'" << getToken() << "'"; 1158 break; 1159 } 1160} 1161 1162/// @name Auto-generated Match Functions 1163/// { 1164 1165static unsigned MatchRegisterName(StringRef Name); 1166 1167/// } 1168 1169bool ARMAsmParser::ParseRegister(unsigned &RegNo, 1170 SMLoc &StartLoc, SMLoc &EndLoc) { 1171 RegNo = TryParseRegister(); 1172 1173 return (RegNo == (unsigned)-1); 1174} 1175 1176/// Try to parse a register name. The token must be an Identifier when called, 1177/// and if it is a register name the token is eaten and the register number is 1178/// returned. Otherwise return -1. 1179/// 1180int ARMAsmParser::TryParseRegister() { 1181 const AsmToken &Tok = Parser.getTok(); 1182 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 1183 1184 // FIXME: Validate register for the current architecture; we have to do 1185 // validation later, so maybe there is no need for this here. 1186 std::string upperCase = Tok.getString().str(); 1187 std::string lowerCase = LowercaseString(upperCase); 1188 unsigned RegNum = MatchRegisterName(lowerCase); 1189 if (!RegNum) { 1190 RegNum = StringSwitch<unsigned>(lowerCase) 1191 .Case("r13", ARM::SP) 1192 .Case("r14", ARM::LR) 1193 .Case("r15", ARM::PC) 1194 .Case("ip", ARM::R12) 1195 .Default(0); 1196 } 1197 if (!RegNum) return -1; 1198 1199 Parser.Lex(); // Eat identifier token. 1200 return RegNum; 1201} 1202 1203// Try to parse a shifter (e.g., "lsl <amt>"). On success, return 0. 1204// If a recoverable error occurs, return 1. If an irrecoverable error 1205// occurs, return -1. An irrecoverable error is one where tokens have been 1206// consumed in the process of trying to parse the shifter (i.e., when it is 1207// indeed a shifter operand, but malformed). 1208int ARMAsmParser::TryParseShiftRegister( 1209 SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1210 SMLoc S = Parser.getTok().getLoc(); 1211 const AsmToken &Tok = Parser.getTok(); 1212 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 1213 1214 std::string upperCase = Tok.getString().str(); 1215 std::string lowerCase = LowercaseString(upperCase); 1216 ARM_AM::ShiftOpc ShiftTy = StringSwitch<ARM_AM::ShiftOpc>(lowerCase) 1217 .Case("lsl", ARM_AM::lsl) 1218 .Case("lsr", ARM_AM::lsr) 1219 .Case("asr", ARM_AM::asr) 1220 .Case("ror", ARM_AM::ror) 1221 .Case("rrx", ARM_AM::rrx) 1222 .Default(ARM_AM::no_shift); 1223 1224 if (ShiftTy == ARM_AM::no_shift) 1225 return 1; 1226 1227 Parser.Lex(); // Eat the operator. 1228 1229 // The source register for the shift has already been added to the 1230 // operand list, so we need to pop it off and combine it into the shifted 1231 // register operand instead. 1232 OwningPtr<ARMOperand> PrevOp((ARMOperand*)Operands.pop_back_val()); 1233 if (!PrevOp->isReg()) 1234 return Error(PrevOp->getStartLoc(), "shift must be of a register"); 1235 int SrcReg = PrevOp->getReg(); 1236 int64_t Imm = 0; 1237 int ShiftReg = 0; 1238 if (ShiftTy == ARM_AM::rrx) { 1239 // RRX Doesn't have an explicit shift amount. The encoder expects 1240 // the shift register to be the same as the source register. Seems odd, 1241 // but OK. 1242 ShiftReg = SrcReg; 1243 } else { 1244 // Figure out if this is shifted by a constant or a register (for non-RRX). 1245 if (Parser.getTok().is(AsmToken::Hash)) { 1246 Parser.Lex(); // Eat hash. 1247 SMLoc ImmLoc = Parser.getTok().getLoc(); 1248 const MCExpr *ShiftExpr = 0; 1249 if (getParser().ParseExpression(ShiftExpr)) { 1250 Error(ImmLoc, "invalid immediate shift value"); 1251 return -1; 1252 } 1253 // The expression must be evaluatable as an immediate. 1254 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(ShiftExpr); 1255 if (!CE) { 1256 Error(ImmLoc, "invalid immediate shift value"); 1257 return -1; 1258 } 1259 // Range check the immediate. 1260 // lsl, ror: 0 <= imm <= 31 1261 // lsr, asr: 0 <= imm <= 32 1262 Imm = CE->getValue(); 1263 if (Imm < 0 || 1264 ((ShiftTy == ARM_AM::lsl || ShiftTy == ARM_AM::ror) && Imm > 31) || 1265 ((ShiftTy == ARM_AM::lsr || ShiftTy == ARM_AM::asr) && Imm > 32)) { 1266 Error(ImmLoc, "immediate shift value out of range"); 1267 return -1; 1268 } 1269 } else if (Parser.getTok().is(AsmToken::Identifier)) { 1270 ShiftReg = TryParseRegister(); 1271 SMLoc L = Parser.getTok().getLoc(); 1272 if (ShiftReg == -1) { 1273 Error (L, "expected immediate or register in shift operand"); 1274 return -1; 1275 } 1276 } else { 1277 Error (Parser.getTok().getLoc(), 1278 "expected immediate or register in shift operand"); 1279 return -1; 1280 } 1281 } 1282 1283 if (ShiftReg && ShiftTy != ARM_AM::rrx) 1284 Operands.push_back(ARMOperand::CreateShiftedRegister(ShiftTy, SrcReg, 1285 ShiftReg, Imm, 1286 S, Parser.getTok().getLoc())); 1287 else 1288 Operands.push_back(ARMOperand::CreateShiftedImmediate(ShiftTy, SrcReg, Imm, 1289 S, Parser.getTok().getLoc())); 1290 1291 return 0; 1292} 1293 1294 1295/// Try to parse a register name. The token must be an Identifier when called. 1296/// If it's a register, an AsmOperand is created. Another AsmOperand is created 1297/// if there is a "writeback". 'true' if it's not a register. 1298/// 1299/// TODO this is likely to change to allow different register types and or to 1300/// parse for a specific register type. 1301bool ARMAsmParser:: 1302TryParseRegisterWithWriteBack(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1303 SMLoc S = Parser.getTok().getLoc(); 1304 int RegNo = TryParseRegister(); 1305 if (RegNo == -1) 1306 return true; 1307 1308 Operands.push_back(ARMOperand::CreateReg(RegNo, S, Parser.getTok().getLoc())); 1309 1310 const AsmToken &ExclaimTok = Parser.getTok(); 1311 if (ExclaimTok.is(AsmToken::Exclaim)) { 1312 Operands.push_back(ARMOperand::CreateToken(ExclaimTok.getString(), 1313 ExclaimTok.getLoc())); 1314 Parser.Lex(); // Eat exclaim token 1315 } 1316 1317 return false; 1318} 1319 1320/// MatchCoprocessorOperandName - Try to parse an coprocessor related 1321/// instruction with a symbolic operand name. Example: "p1", "p7", "c3", 1322/// "c5", ... 1323static int MatchCoprocessorOperandName(StringRef Name, char CoprocOp) { 1324 // Use the same layout as the tablegen'erated register name matcher. Ugly, 1325 // but efficient. 1326 switch (Name.size()) { 1327 default: break; 1328 case 2: 1329 if (Name[0] != CoprocOp) 1330 return -1; 1331 switch (Name[1]) { 1332 default: return -1; 1333 case '0': return 0; 1334 case '1': return 1; 1335 case '2': return 2; 1336 case '3': return 3; 1337 case '4': return 4; 1338 case '5': return 5; 1339 case '6': return 6; 1340 case '7': return 7; 1341 case '8': return 8; 1342 case '9': return 9; 1343 } 1344 break; 1345 case 3: 1346 if (Name[0] != CoprocOp || Name[1] != '1') 1347 return -1; 1348 switch (Name[2]) { 1349 default: return -1; 1350 case '0': return 10; 1351 case '1': return 11; 1352 case '2': return 12; 1353 case '3': return 13; 1354 case '4': return 14; 1355 case '5': return 15; 1356 } 1357 break; 1358 } 1359 1360 return -1; 1361} 1362 1363/// tryParseCoprocNumOperand - Try to parse an coprocessor number operand. The 1364/// token must be an Identifier when called, and if it is a coprocessor 1365/// number, the token is eaten and the operand is added to the operand list. 1366ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1367tryParseCoprocNumOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1368 SMLoc S = Parser.getTok().getLoc(); 1369 const AsmToken &Tok = Parser.getTok(); 1370 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 1371 1372 int Num = MatchCoprocessorOperandName(Tok.getString(), 'p'); 1373 if (Num == -1) 1374 return MatchOperand_NoMatch; 1375 1376 Parser.Lex(); // Eat identifier token. 1377 Operands.push_back(ARMOperand::CreateCoprocNum(Num, S)); 1378 return MatchOperand_Success; 1379} 1380 1381/// tryParseCoprocRegOperand - Try to parse an coprocessor register operand. The 1382/// token must be an Identifier when called, and if it is a coprocessor 1383/// number, the token is eaten and the operand is added to the operand list. 1384ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1385tryParseCoprocRegOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1386 SMLoc S = Parser.getTok().getLoc(); 1387 const AsmToken &Tok = Parser.getTok(); 1388 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 1389 1390 int Reg = MatchCoprocessorOperandName(Tok.getString(), 'c'); 1391 if (Reg == -1) 1392 return MatchOperand_NoMatch; 1393 1394 Parser.Lex(); // Eat identifier token. 1395 Operands.push_back(ARMOperand::CreateCoprocReg(Reg, S)); 1396 return MatchOperand_Success; 1397} 1398 1399/// Parse a register list, return it if successful else return null. The first 1400/// token must be a '{' when called. 1401bool ARMAsmParser:: 1402ParseRegisterList(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1403 assert(Parser.getTok().is(AsmToken::LCurly) && 1404 "Token is not a Left Curly Brace"); 1405 SMLoc S = Parser.getTok().getLoc(); 1406 1407 // Read the rest of the registers in the list. 1408 unsigned PrevRegNum = 0; 1409 SmallVector<std::pair<unsigned, SMLoc>, 32> Registers; 1410 1411 do { 1412 bool IsRange = Parser.getTok().is(AsmToken::Minus); 1413 Parser.Lex(); // Eat non-identifier token. 1414 1415 const AsmToken &RegTok = Parser.getTok(); 1416 SMLoc RegLoc = RegTok.getLoc(); 1417 if (RegTok.isNot(AsmToken::Identifier)) { 1418 Error(RegLoc, "register expected"); 1419 return true; 1420 } 1421 1422 int RegNum = TryParseRegister(); 1423 if (RegNum == -1) { 1424 Error(RegLoc, "register expected"); 1425 return true; 1426 } 1427 1428 if (IsRange) { 1429 int Reg = PrevRegNum; 1430 do { 1431 ++Reg; 1432 Registers.push_back(std::make_pair(Reg, RegLoc)); 1433 } while (Reg != RegNum); 1434 } else { 1435 Registers.push_back(std::make_pair(RegNum, RegLoc)); 1436 } 1437 1438 PrevRegNum = RegNum; 1439 } while (Parser.getTok().is(AsmToken::Comma) || 1440 Parser.getTok().is(AsmToken::Minus)); 1441 1442 // Process the right curly brace of the list. 1443 const AsmToken &RCurlyTok = Parser.getTok(); 1444 if (RCurlyTok.isNot(AsmToken::RCurly)) { 1445 Error(RCurlyTok.getLoc(), "'}' expected"); 1446 return true; 1447 } 1448 1449 SMLoc E = RCurlyTok.getLoc(); 1450 Parser.Lex(); // Eat right curly brace token. 1451 1452 // Verify the register list. 1453 SmallVectorImpl<std::pair<unsigned, SMLoc> >::const_iterator 1454 RI = Registers.begin(), RE = Registers.end(); 1455 1456 unsigned HighRegNum = getARMRegisterNumbering(RI->first); 1457 bool EmittedWarning = false; 1458 1459 DenseMap<unsigned, bool> RegMap; 1460 RegMap[HighRegNum] = true; 1461 1462 for (++RI; RI != RE; ++RI) { 1463 const std::pair<unsigned, SMLoc> &RegInfo = *RI; 1464 unsigned Reg = getARMRegisterNumbering(RegInfo.first); 1465 1466 if (RegMap[Reg]) { 1467 Error(RegInfo.second, "register duplicated in register list"); 1468 return true; 1469 } 1470 1471 if (!EmittedWarning && Reg < HighRegNum) 1472 Warning(RegInfo.second, 1473 "register not in ascending order in register list"); 1474 1475 RegMap[Reg] = true; 1476 HighRegNum = std::max(Reg, HighRegNum); 1477 } 1478 1479 Operands.push_back(ARMOperand::CreateRegList(Registers, S, E)); 1480 return false; 1481} 1482 1483/// tryParseMemBarrierOptOperand - Try to parse DSB/DMB data barrier options. 1484ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1485tryParseMemBarrierOptOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1486 SMLoc S = Parser.getTok().getLoc(); 1487 const AsmToken &Tok = Parser.getTok(); 1488 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 1489 StringRef OptStr = Tok.getString(); 1490 1491 unsigned Opt = StringSwitch<unsigned>(OptStr.slice(0, OptStr.size())) 1492 .Case("sy", ARM_MB::SY) 1493 .Case("st", ARM_MB::ST) 1494 .Case("sh", ARM_MB::ISH) 1495 .Case("ish", ARM_MB::ISH) 1496 .Case("shst", ARM_MB::ISHST) 1497 .Case("ishst", ARM_MB::ISHST) 1498 .Case("nsh", ARM_MB::NSH) 1499 .Case("un", ARM_MB::NSH) 1500 .Case("nshst", ARM_MB::NSHST) 1501 .Case("unst", ARM_MB::NSHST) 1502 .Case("osh", ARM_MB::OSH) 1503 .Case("oshst", ARM_MB::OSHST) 1504 .Default(~0U); 1505 1506 if (Opt == ~0U) 1507 return MatchOperand_NoMatch; 1508 1509 Parser.Lex(); // Eat identifier token. 1510 Operands.push_back(ARMOperand::CreateMemBarrierOpt((ARM_MB::MemBOpt)Opt, S)); 1511 return MatchOperand_Success; 1512} 1513 1514/// tryParseProcIFlagsOperand - Try to parse iflags from CPS instruction. 1515ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1516tryParseProcIFlagsOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1517 SMLoc S = Parser.getTok().getLoc(); 1518 const AsmToken &Tok = Parser.getTok(); 1519 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 1520 StringRef IFlagsStr = Tok.getString(); 1521 1522 unsigned IFlags = 0; 1523 for (int i = 0, e = IFlagsStr.size(); i != e; ++i) { 1524 unsigned Flag = StringSwitch<unsigned>(IFlagsStr.substr(i, 1)) 1525 .Case("a", ARM_PROC::A) 1526 .Case("i", ARM_PROC::I) 1527 .Case("f", ARM_PROC::F) 1528 .Default(~0U); 1529 1530 // If some specific iflag is already set, it means that some letter is 1531 // present more than once, this is not acceptable. 1532 if (Flag == ~0U || (IFlags & Flag)) 1533 return MatchOperand_NoMatch; 1534 1535 IFlags |= Flag; 1536 } 1537 1538 Parser.Lex(); // Eat identifier token. 1539 Operands.push_back(ARMOperand::CreateProcIFlags((ARM_PROC::IFlags)IFlags, S)); 1540 return MatchOperand_Success; 1541} 1542 1543/// tryParseMSRMaskOperand - Try to parse mask flags from MSR instruction. 1544ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1545tryParseMSRMaskOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1546 SMLoc S = Parser.getTok().getLoc(); 1547 const AsmToken &Tok = Parser.getTok(); 1548 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 1549 StringRef Mask = Tok.getString(); 1550 1551 // Split spec_reg from flag, example: CPSR_sxf => "CPSR" and "sxf" 1552 size_t Start = 0, Next = Mask.find('_'); 1553 StringRef Flags = ""; 1554 std::string SpecReg = LowercaseString(Mask.slice(Start, Next)); 1555 if (Next != StringRef::npos) 1556 Flags = Mask.slice(Next+1, Mask.size()); 1557 1558 // FlagsVal contains the complete mask: 1559 // 3-0: Mask 1560 // 4: Special Reg (cpsr, apsr => 0; spsr => 1) 1561 unsigned FlagsVal = 0; 1562 1563 if (SpecReg == "apsr") { 1564 FlagsVal = StringSwitch<unsigned>(Flags) 1565 .Case("nzcvq", 0x8) // same as CPSR_f 1566 .Case("g", 0x4) // same as CPSR_s 1567 .Case("nzcvqg", 0xc) // same as CPSR_fs 1568 .Default(~0U); 1569 1570 if (FlagsVal == ~0U) { 1571 if (!Flags.empty()) 1572 return MatchOperand_NoMatch; 1573 else 1574 FlagsVal = 0; // No flag 1575 } 1576 } else if (SpecReg == "cpsr" || SpecReg == "spsr") { 1577 if (Flags == "all") // cpsr_all is an alias for cpsr_fc 1578 Flags = "fc"; 1579 for (int i = 0, e = Flags.size(); i != e; ++i) { 1580 unsigned Flag = StringSwitch<unsigned>(Flags.substr(i, 1)) 1581 .Case("c", 1) 1582 .Case("x", 2) 1583 .Case("s", 4) 1584 .Case("f", 8) 1585 .Default(~0U); 1586 1587 // If some specific flag is already set, it means that some letter is 1588 // present more than once, this is not acceptable. 1589 if (FlagsVal == ~0U || (FlagsVal & Flag)) 1590 return MatchOperand_NoMatch; 1591 FlagsVal |= Flag; 1592 } 1593 } else // No match for special register. 1594 return MatchOperand_NoMatch; 1595 1596 // Special register without flags are equivalent to "fc" flags. 1597 if (!FlagsVal) 1598 FlagsVal = 0x9; 1599 1600 // Bit 4: Special Reg (cpsr, apsr => 0; spsr => 1) 1601 if (SpecReg == "spsr") 1602 FlagsVal |= 16; 1603 1604 Parser.Lex(); // Eat identifier token. 1605 Operands.push_back(ARMOperand::CreateMSRMask(FlagsVal, S)); 1606 return MatchOperand_Success; 1607} 1608 1609/// tryParseMemMode2Operand - Try to parse memory addressing mode 2 operand. 1610ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1611tryParseMemMode2Operand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1612 assert(Parser.getTok().is(AsmToken::LBrac) && "Token is not a \"[\""); 1613 1614 if (ParseMemory(Operands, ARMII::AddrMode2)) 1615 return MatchOperand_NoMatch; 1616 1617 return MatchOperand_Success; 1618} 1619 1620/// tryParseMemMode3Operand - Try to parse memory addressing mode 3 operand. 1621ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1622tryParseMemMode3Operand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1623 assert(Parser.getTok().is(AsmToken::LBrac) && "Token is not a \"[\""); 1624 1625 if (ParseMemory(Operands, ARMII::AddrMode3)) 1626 return MatchOperand_NoMatch; 1627 1628 return MatchOperand_Success; 1629} 1630 1631ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1632parsePKHImm(SmallVectorImpl<MCParsedAsmOperand*> &Operands, StringRef Op, 1633 int Low, int High) { 1634 const AsmToken &Tok = Parser.getTok(); 1635 if (Tok.isNot(AsmToken::Identifier)) { 1636 Error(Parser.getTok().getLoc(), Op + " operand expected."); 1637 return MatchOperand_ParseFail; 1638 } 1639 StringRef ShiftName = Tok.getString(); 1640 std::string LowerOp = LowercaseString(Op); 1641 std::string UpperOp = UppercaseString(Op); 1642 if (ShiftName != LowerOp && ShiftName != UpperOp) { 1643 Error(Parser.getTok().getLoc(), Op + " operand expected."); 1644 return MatchOperand_ParseFail; 1645 } 1646 Parser.Lex(); // Eat shift type token. 1647 1648 // There must be a '#' and a shift amount. 1649 if (Parser.getTok().isNot(AsmToken::Hash)) { 1650 Error(Parser.getTok().getLoc(), "'#' expected"); 1651 return MatchOperand_ParseFail; 1652 } 1653 Parser.Lex(); // Eat hash token. 1654 1655 const MCExpr *ShiftAmount; 1656 SMLoc Loc = Parser.getTok().getLoc(); 1657 if (getParser().ParseExpression(ShiftAmount)) { 1658 Error(Loc, "illegal expression"); 1659 return MatchOperand_ParseFail; 1660 } 1661 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(ShiftAmount); 1662 if (!CE) { 1663 Error(Loc, "constant expression expected"); 1664 return MatchOperand_ParseFail; 1665 } 1666 int Val = CE->getValue(); 1667 if (Val < Low || Val > High) { 1668 Error(Loc, "immediate value out of range"); 1669 return MatchOperand_ParseFail; 1670 } 1671 1672 Operands.push_back(ARMOperand::CreateImm(CE, Loc, Parser.getTok().getLoc())); 1673 1674 return MatchOperand_Success; 1675} 1676 1677ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 1678parseSetEndImm(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1679 const AsmToken &Tok = Parser.getTok(); 1680 SMLoc S = Tok.getLoc(); 1681 if (Tok.isNot(AsmToken::Identifier)) { 1682 Error(Tok.getLoc(), "'be' or 'le' operand expected"); 1683 return MatchOperand_ParseFail; 1684 } 1685 int Val = StringSwitch<int>(Tok.getString()) 1686 .Case("be", 1) 1687 .Case("le", 0) 1688 .Default(-1); 1689 Parser.Lex(); // Eat the token. 1690 1691 if (Val == -1) { 1692 Error(Tok.getLoc(), "'be' or 'le' operand expected"); 1693 return MatchOperand_ParseFail; 1694 } 1695 Operands.push_back(ARMOperand::CreateImm(MCConstantExpr::Create(Val, 1696 getContext()), 1697 S, Parser.getTok().getLoc())); 1698 return MatchOperand_Success; 1699} 1700 1701/// CvtLdWriteBackRegAddrMode2 - Convert parsed operands to MCInst. 1702/// Needed here because the Asm Gen Matcher can't handle properly tied operands 1703/// when they refer multiple MIOperands inside a single one. 1704bool ARMAsmParser:: 1705CvtLdWriteBackRegAddrMode2(MCInst &Inst, unsigned Opcode, 1706 const SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1707 ((ARMOperand*)Operands[2])->addRegOperands(Inst, 1); 1708 1709 // Create a writeback register dummy placeholder. 1710 Inst.addOperand(MCOperand::CreateImm(0)); 1711 1712 ((ARMOperand*)Operands[3])->addMemMode2Operands(Inst, 3); 1713 ((ARMOperand*)Operands[1])->addCondCodeOperands(Inst, 2); 1714 return true; 1715} 1716 1717/// CvtStWriteBackRegAddrMode2 - Convert parsed operands to MCInst. 1718/// Needed here because the Asm Gen Matcher can't handle properly tied operands 1719/// when they refer multiple MIOperands inside a single one. 1720bool ARMAsmParser:: 1721CvtStWriteBackRegAddrMode2(MCInst &Inst, unsigned Opcode, 1722 const SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1723 // Create a writeback register dummy placeholder. 1724 Inst.addOperand(MCOperand::CreateImm(0)); 1725 ((ARMOperand*)Operands[2])->addRegOperands(Inst, 1); 1726 ((ARMOperand*)Operands[3])->addMemMode2Operands(Inst, 3); 1727 ((ARMOperand*)Operands[1])->addCondCodeOperands(Inst, 2); 1728 return true; 1729} 1730 1731/// CvtLdWriteBackRegAddrMode3 - Convert parsed operands to MCInst. 1732/// Needed here because the Asm Gen Matcher can't handle properly tied operands 1733/// when they refer multiple MIOperands inside a single one. 1734bool ARMAsmParser:: 1735CvtLdWriteBackRegAddrMode3(MCInst &Inst, unsigned Opcode, 1736 const SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1737 ((ARMOperand*)Operands[2])->addRegOperands(Inst, 1); 1738 1739 // Create a writeback register dummy placeholder. 1740 Inst.addOperand(MCOperand::CreateImm(0)); 1741 1742 ((ARMOperand*)Operands[3])->addMemMode3Operands(Inst, 3); 1743 ((ARMOperand*)Operands[1])->addCondCodeOperands(Inst, 2); 1744 return true; 1745} 1746 1747/// CvtStWriteBackRegAddrMode3 - Convert parsed operands to MCInst. 1748/// Needed here because the Asm Gen Matcher can't handle properly tied operands 1749/// when they refer multiple MIOperands inside a single one. 1750bool ARMAsmParser:: 1751CvtStWriteBackRegAddrMode3(MCInst &Inst, unsigned Opcode, 1752 const SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1753 // Create a writeback register dummy placeholder. 1754 Inst.addOperand(MCOperand::CreateImm(0)); 1755 ((ARMOperand*)Operands[2])->addRegOperands(Inst, 1); 1756 ((ARMOperand*)Operands[3])->addMemMode3Operands(Inst, 3); 1757 ((ARMOperand*)Operands[1])->addCondCodeOperands(Inst, 2); 1758 return true; 1759} 1760 1761/// Parse an ARM memory expression, return false if successful else return true 1762/// or an error. The first token must be a '[' when called. 1763/// 1764/// TODO Only preindexing and postindexing addressing are started, unindexed 1765/// with option, etc are still to do. 1766bool ARMAsmParser:: 1767ParseMemory(SmallVectorImpl<MCParsedAsmOperand*> &Operands, 1768 ARMII::AddrMode AddrMode = ARMII::AddrModeNone) { 1769 SMLoc S, E; 1770 assert(Parser.getTok().is(AsmToken::LBrac) && 1771 "Token is not a Left Bracket"); 1772 S = Parser.getTok().getLoc(); 1773 Parser.Lex(); // Eat left bracket token. 1774 1775 const AsmToken &BaseRegTok = Parser.getTok(); 1776 if (BaseRegTok.isNot(AsmToken::Identifier)) { 1777 Error(BaseRegTok.getLoc(), "register expected"); 1778 return true; 1779 } 1780 int BaseRegNum = TryParseRegister(); 1781 if (BaseRegNum == -1) { 1782 Error(BaseRegTok.getLoc(), "register expected"); 1783 return true; 1784 } 1785 1786 // The next token must either be a comma or a closing bracket. 1787 const AsmToken &Tok = Parser.getTok(); 1788 if (!Tok.is(AsmToken::Comma) && !Tok.is(AsmToken::RBrac)) 1789 return true; 1790 1791 bool Preindexed = false; 1792 bool Postindexed = false; 1793 bool OffsetIsReg = false; 1794 bool Negative = false; 1795 bool Writeback = false; 1796 ARMOperand *WBOp = 0; 1797 int OffsetRegNum = -1; 1798 bool OffsetRegShifted = false; 1799 enum ARM_AM::ShiftOpc ShiftType = ARM_AM::lsl; 1800 const MCExpr *ShiftAmount = 0; 1801 const MCExpr *Offset = 0; 1802 1803 // First look for preindexed address forms, that is after the "[Rn" we now 1804 // have to see if the next token is a comma. 1805 if (Tok.is(AsmToken::Comma)) { 1806 Preindexed = true; 1807 Parser.Lex(); // Eat comma token. 1808 1809 if (ParseMemoryOffsetReg(Negative, OffsetRegShifted, ShiftType, ShiftAmount, 1810 Offset, OffsetIsReg, OffsetRegNum, E)) 1811 return true; 1812 const AsmToken &RBracTok = Parser.getTok(); 1813 if (RBracTok.isNot(AsmToken::RBrac)) { 1814 Error(RBracTok.getLoc(), "']' expected"); 1815 return true; 1816 } 1817 E = RBracTok.getLoc(); 1818 Parser.Lex(); // Eat right bracket token. 1819 1820 const AsmToken &ExclaimTok = Parser.getTok(); 1821 if (ExclaimTok.is(AsmToken::Exclaim)) { 1822 // None of addrmode3 instruction uses "!" 1823 if (AddrMode == ARMII::AddrMode3) 1824 return true; 1825 1826 WBOp = ARMOperand::CreateToken(ExclaimTok.getString(), 1827 ExclaimTok.getLoc()); 1828 Writeback = true; 1829 Parser.Lex(); // Eat exclaim token 1830 } else { // In addressing mode 2, pre-indexed mode always end with "!" 1831 if (AddrMode == ARMII::AddrMode2) 1832 Preindexed = false; 1833 } 1834 } else { 1835 // The "[Rn" we have so far was not followed by a comma. 1836 1837 // If there's anything other than the right brace, this is a post indexing 1838 // addressing form. 1839 E = Tok.getLoc(); 1840 Parser.Lex(); // Eat right bracket token. 1841 1842 const AsmToken &NextTok = Parser.getTok(); 1843 1844 if (NextTok.isNot(AsmToken::EndOfStatement)) { 1845 Postindexed = true; 1846 Writeback = true; 1847 1848 if (NextTok.isNot(AsmToken::Comma)) { 1849 Error(NextTok.getLoc(), "',' expected"); 1850 return true; 1851 } 1852 1853 Parser.Lex(); // Eat comma token. 1854 1855 if (ParseMemoryOffsetReg(Negative, OffsetRegShifted, ShiftType, 1856 ShiftAmount, Offset, OffsetIsReg, OffsetRegNum, 1857 E)) 1858 return true; 1859 } 1860 } 1861 1862 // Force Offset to exist if used. 1863 if (!OffsetIsReg) { 1864 if (!Offset) 1865 Offset = MCConstantExpr::Create(0, getContext()); 1866 } else { 1867 if (AddrMode == ARMII::AddrMode3 && OffsetRegShifted) { 1868 Error(E, "shift amount not supported"); 1869 return true; 1870 } 1871 } 1872 1873 Operands.push_back(ARMOperand::CreateMem(AddrMode, BaseRegNum, OffsetIsReg, 1874 Offset, OffsetRegNum, OffsetRegShifted, 1875 ShiftType, ShiftAmount, Preindexed, 1876 Postindexed, Negative, Writeback, S, E)); 1877 if (WBOp) 1878 Operands.push_back(WBOp); 1879 1880 return false; 1881} 1882 1883/// Parse the offset of a memory operand after we have seen "[Rn," or "[Rn]," 1884/// we will parse the following (were +/- means that a plus or minus is 1885/// optional): 1886/// +/-Rm 1887/// +/-Rm, shift 1888/// #offset 1889/// we return false on success or an error otherwise. 1890bool ARMAsmParser::ParseMemoryOffsetReg(bool &Negative, 1891 bool &OffsetRegShifted, 1892 enum ARM_AM::ShiftOpc &ShiftType, 1893 const MCExpr *&ShiftAmount, 1894 const MCExpr *&Offset, 1895 bool &OffsetIsReg, 1896 int &OffsetRegNum, 1897 SMLoc &E) { 1898 Negative = false; 1899 OffsetRegShifted = false; 1900 OffsetIsReg = false; 1901 OffsetRegNum = -1; 1902 const AsmToken &NextTok = Parser.getTok(); 1903 E = NextTok.getLoc(); 1904 if (NextTok.is(AsmToken::Plus)) 1905 Parser.Lex(); // Eat plus token. 1906 else if (NextTok.is(AsmToken::Minus)) { 1907 Negative = true; 1908 Parser.Lex(); // Eat minus token 1909 } 1910 // See if there is a register following the "[Rn," or "[Rn]," we have so far. 1911 const AsmToken &OffsetRegTok = Parser.getTok(); 1912 if (OffsetRegTok.is(AsmToken::Identifier)) { 1913 SMLoc CurLoc = OffsetRegTok.getLoc(); 1914 OffsetRegNum = TryParseRegister(); 1915 if (OffsetRegNum != -1) { 1916 OffsetIsReg = true; 1917 E = CurLoc; 1918 } 1919 } 1920 1921 // If we parsed a register as the offset then there can be a shift after that. 1922 if (OffsetRegNum != -1) { 1923 // Look for a comma then a shift 1924 const AsmToken &Tok = Parser.getTok(); 1925 if (Tok.is(AsmToken::Comma)) { 1926 Parser.Lex(); // Eat comma token. 1927 1928 const AsmToken &Tok = Parser.getTok(); 1929 if (ParseShift(ShiftType, ShiftAmount, E)) 1930 return Error(Tok.getLoc(), "shift expected"); 1931 OffsetRegShifted = true; 1932 } 1933 } 1934 else { // the "[Rn," or "[Rn,]" we have so far was not followed by "Rm" 1935 // Look for #offset following the "[Rn," or "[Rn]," 1936 const AsmToken &HashTok = Parser.getTok(); 1937 if (HashTok.isNot(AsmToken::Hash)) 1938 return Error(HashTok.getLoc(), "'#' expected"); 1939 1940 Parser.Lex(); // Eat hash token. 1941 1942 if (getParser().ParseExpression(Offset)) 1943 return true; 1944 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 1945 } 1946 return false; 1947} 1948 1949/// ParseShift as one of these two: 1950/// ( lsl | lsr | asr | ror ) , # shift_amount 1951/// rrx 1952/// and returns true if it parses a shift otherwise it returns false. 1953bool ARMAsmParser::ParseShift(ARM_AM::ShiftOpc &St, 1954 const MCExpr *&ShiftAmount, SMLoc &E) { 1955 const AsmToken &Tok = Parser.getTok(); 1956 if (Tok.isNot(AsmToken::Identifier)) 1957 return true; 1958 StringRef ShiftName = Tok.getString(); 1959 if (ShiftName == "lsl" || ShiftName == "LSL") 1960 St = ARM_AM::lsl; 1961 else if (ShiftName == "lsr" || ShiftName == "LSR") 1962 St = ARM_AM::lsr; 1963 else if (ShiftName == "asr" || ShiftName == "ASR") 1964 St = ARM_AM::asr; 1965 else if (ShiftName == "ror" || ShiftName == "ROR") 1966 St = ARM_AM::ror; 1967 else if (ShiftName == "rrx" || ShiftName == "RRX") 1968 St = ARM_AM::rrx; 1969 else 1970 return true; 1971 Parser.Lex(); // Eat shift type token. 1972 1973 // Rrx stands alone. 1974 if (St == ARM_AM::rrx) 1975 return false; 1976 1977 // Otherwise, there must be a '#' and a shift amount. 1978 const AsmToken &HashTok = Parser.getTok(); 1979 if (HashTok.isNot(AsmToken::Hash)) 1980 return Error(HashTok.getLoc(), "'#' expected"); 1981 Parser.Lex(); // Eat hash token. 1982 1983 if (getParser().ParseExpression(ShiftAmount)) 1984 return true; 1985 1986 return false; 1987} 1988 1989/// Parse a arm instruction operand. For now this parses the operand regardless 1990/// of the mnemonic. 1991bool ARMAsmParser::ParseOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands, 1992 StringRef Mnemonic) { 1993 SMLoc S, E; 1994 1995 // Check if the current operand has a custom associated parser, if so, try to 1996 // custom parse the operand, or fallback to the general approach. 1997 OperandMatchResultTy ResTy = MatchOperandParserImpl(Operands, Mnemonic); 1998 if (ResTy == MatchOperand_Success) 1999 return false; 2000 // If there wasn't a custom match, try the generic matcher below. Otherwise, 2001 // there was a match, but an error occurred, in which case, just return that 2002 // the operand parsing failed. 2003 if (ResTy == MatchOperand_ParseFail) 2004 return true; 2005 2006 switch (getLexer().getKind()) { 2007 default: 2008 Error(Parser.getTok().getLoc(), "unexpected token in operand"); 2009 return true; 2010 case AsmToken::Identifier: { 2011 if (!TryParseRegisterWithWriteBack(Operands)) 2012 return false; 2013 int Res = TryParseShiftRegister(Operands); 2014 if (Res == 0) // success 2015 return false; 2016 else if (Res == -1) // irrecoverable error 2017 return true; 2018 2019 // Fall though for the Identifier case that is not a register or a 2020 // special name. 2021 } 2022 case AsmToken::Integer: // things like 1f and 2b as a branch targets 2023 case AsmToken::Dot: { // . as a branch target 2024 // This was not a register so parse other operands that start with an 2025 // identifier (like labels) as expressions and create them as immediates. 2026 const MCExpr *IdVal; 2027 S = Parser.getTok().getLoc(); 2028 if (getParser().ParseExpression(IdVal)) 2029 return true; 2030 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2031 Operands.push_back(ARMOperand::CreateImm(IdVal, S, E)); 2032 return false; 2033 } 2034 case AsmToken::LBrac: 2035 return ParseMemory(Operands); 2036 case AsmToken::LCurly: 2037 return ParseRegisterList(Operands); 2038 case AsmToken::Hash: 2039 // #42 -> immediate. 2040 // TODO: ":lower16:" and ":upper16:" modifiers after # before immediate 2041 S = Parser.getTok().getLoc(); 2042 Parser.Lex(); 2043 const MCExpr *ImmVal; 2044 if (getParser().ParseExpression(ImmVal)) 2045 return true; 2046 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2047 Operands.push_back(ARMOperand::CreateImm(ImmVal, S, E)); 2048 return false; 2049 case AsmToken::Colon: { 2050 // ":lower16:" and ":upper16:" expression prefixes 2051 // FIXME: Check it's an expression prefix, 2052 // e.g. (FOO - :lower16:BAR) isn't legal. 2053 ARMMCExpr::VariantKind RefKind; 2054 if (ParsePrefix(RefKind)) 2055 return true; 2056 2057 const MCExpr *SubExprVal; 2058 if (getParser().ParseExpression(SubExprVal)) 2059 return true; 2060 2061 const MCExpr *ExprVal = ARMMCExpr::Create(RefKind, SubExprVal, 2062 getContext()); 2063 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2064 Operands.push_back(ARMOperand::CreateImm(ExprVal, S, E)); 2065 return false; 2066 } 2067 } 2068} 2069 2070// ParsePrefix - Parse ARM 16-bit relocations expression prefix, i.e. 2071// :lower16: and :upper16:. 2072bool ARMAsmParser::ParsePrefix(ARMMCExpr::VariantKind &RefKind) { 2073 RefKind = ARMMCExpr::VK_ARM_None; 2074 2075 // :lower16: and :upper16: modifiers 2076 assert(getLexer().is(AsmToken::Colon) && "expected a :"); 2077 Parser.Lex(); // Eat ':' 2078 2079 if (getLexer().isNot(AsmToken::Identifier)) { 2080 Error(Parser.getTok().getLoc(), "expected prefix identifier in operand"); 2081 return true; 2082 } 2083 2084 StringRef IDVal = Parser.getTok().getIdentifier(); 2085 if (IDVal == "lower16") { 2086 RefKind = ARMMCExpr::VK_ARM_LO16; 2087 } else if (IDVal == "upper16") { 2088 RefKind = ARMMCExpr::VK_ARM_HI16; 2089 } else { 2090 Error(Parser.getTok().getLoc(), "unexpected prefix in operand"); 2091 return true; 2092 } 2093 Parser.Lex(); 2094 2095 if (getLexer().isNot(AsmToken::Colon)) { 2096 Error(Parser.getTok().getLoc(), "unexpected token after prefix"); 2097 return true; 2098 } 2099 Parser.Lex(); // Eat the last ':' 2100 return false; 2101} 2102 2103const MCExpr * 2104ARMAsmParser::ApplyPrefixToExpr(const MCExpr *E, 2105 MCSymbolRefExpr::VariantKind Variant) { 2106 // Recurse over the given expression, rebuilding it to apply the given variant 2107 // to the leftmost symbol. 2108 if (Variant == MCSymbolRefExpr::VK_None) 2109 return E; 2110 2111 switch (E->getKind()) { 2112 case MCExpr::Target: 2113 llvm_unreachable("Can't handle target expr yet"); 2114 case MCExpr::Constant: 2115 llvm_unreachable("Can't handle lower16/upper16 of constant yet"); 2116 2117 case MCExpr::SymbolRef: { 2118 const MCSymbolRefExpr *SRE = cast<MCSymbolRefExpr>(E); 2119 2120 if (SRE->getKind() != MCSymbolRefExpr::VK_None) 2121 return 0; 2122 2123 return MCSymbolRefExpr::Create(&SRE->getSymbol(), Variant, getContext()); 2124 } 2125 2126 case MCExpr::Unary: 2127 llvm_unreachable("Can't handle unary expressions yet"); 2128 2129 case MCExpr::Binary: { 2130 const MCBinaryExpr *BE = cast<MCBinaryExpr>(E); 2131 const MCExpr *LHS = ApplyPrefixToExpr(BE->getLHS(), Variant); 2132 const MCExpr *RHS = BE->getRHS(); 2133 if (!LHS) 2134 return 0; 2135 2136 return MCBinaryExpr::Create(BE->getOpcode(), LHS, RHS, getContext()); 2137 } 2138 } 2139 2140 assert(0 && "Invalid expression kind!"); 2141 return 0; 2142} 2143 2144/// \brief Given a mnemonic, split out possible predication code and carry 2145/// setting letters to form a canonical mnemonic and flags. 2146// 2147// FIXME: Would be nice to autogen this. 2148StringRef ARMAsmParser::SplitMnemonic(StringRef Mnemonic, 2149 unsigned &PredicationCode, 2150 bool &CarrySetting, 2151 unsigned &ProcessorIMod) { 2152 PredicationCode = ARMCC::AL; 2153 CarrySetting = false; 2154 ProcessorIMod = 0; 2155 2156 // Ignore some mnemonics we know aren't predicated forms. 2157 // 2158 // FIXME: Would be nice to autogen this. 2159 if ((Mnemonic == "movs" && isThumb()) || 2160 Mnemonic == "teq" || Mnemonic == "vceq" || Mnemonic == "svc" || 2161 Mnemonic == "mls" || Mnemonic == "smmls" || Mnemonic == "vcls" || 2162 Mnemonic == "vmls" || Mnemonic == "vnmls" || Mnemonic == "vacge" || 2163 Mnemonic == "vcge" || Mnemonic == "vclt" || Mnemonic == "vacgt" || 2164 Mnemonic == "vcgt" || Mnemonic == "vcle" || Mnemonic == "smlal" || 2165 Mnemonic == "umaal" || Mnemonic == "umlal" || Mnemonic == "vabal" || 2166 Mnemonic == "vmlal" || Mnemonic == "vpadal" || Mnemonic == "vqdmlal") 2167 return Mnemonic; 2168 2169 // First, split out any predication code. Ignore mnemonics we know aren't 2170 // predicated but do have a carry-set and so weren't caught above. 2171 if (Mnemonic != "adcs" && Mnemonic != "bics" && Mnemonic != "movs" && 2172 Mnemonic != "muls" && Mnemonic != "smlals" && Mnemonic != "smulls") { 2173 unsigned CC = StringSwitch<unsigned>(Mnemonic.substr(Mnemonic.size()-2)) 2174 .Case("eq", ARMCC::EQ) 2175 .Case("ne", ARMCC::NE) 2176 .Case("hs", ARMCC::HS) 2177 .Case("cs", ARMCC::HS) 2178 .Case("lo", ARMCC::LO) 2179 .Case("cc", ARMCC::LO) 2180 .Case("mi", ARMCC::MI) 2181 .Case("pl", ARMCC::PL) 2182 .Case("vs", ARMCC::VS) 2183 .Case("vc", ARMCC::VC) 2184 .Case("hi", ARMCC::HI) 2185 .Case("ls", ARMCC::LS) 2186 .Case("ge", ARMCC::GE) 2187 .Case("lt", ARMCC::LT) 2188 .Case("gt", ARMCC::GT) 2189 .Case("le", ARMCC::LE) 2190 .Case("al", ARMCC::AL) 2191 .Default(~0U); 2192 if (CC != ~0U) { 2193 Mnemonic = Mnemonic.slice(0, Mnemonic.size() - 2); 2194 PredicationCode = CC; 2195 } 2196 } 2197 2198 // Next, determine if we have a carry setting bit. We explicitly ignore all 2199 // the instructions we know end in 's'. 2200 if (Mnemonic.endswith("s") && 2201 !(Mnemonic == "asrs" || Mnemonic == "cps" || Mnemonic == "mls" || 2202 Mnemonic == "mrs" || Mnemonic == "smmls" || Mnemonic == "vabs" || 2203 Mnemonic == "vcls" || Mnemonic == "vmls" || Mnemonic == "vmrs" || 2204 Mnemonic == "vnmls" || Mnemonic == "vqabs" || Mnemonic == "vrecps" || 2205 Mnemonic == "vrsqrts" || (Mnemonic == "movs" && isThumb()))) { 2206 Mnemonic = Mnemonic.slice(0, Mnemonic.size() - 1); 2207 CarrySetting = true; 2208 } 2209 2210 // The "cps" instruction can have a interrupt mode operand which is glued into 2211 // the mnemonic. Check if this is the case, split it and parse the imod op 2212 if (Mnemonic.startswith("cps")) { 2213 // Split out any imod code. 2214 unsigned IMod = 2215 StringSwitch<unsigned>(Mnemonic.substr(Mnemonic.size()-2, 2)) 2216 .Case("ie", ARM_PROC::IE) 2217 .Case("id", ARM_PROC::ID) 2218 .Default(~0U); 2219 if (IMod != ~0U) { 2220 Mnemonic = Mnemonic.slice(0, Mnemonic.size()-2); 2221 ProcessorIMod = IMod; 2222 } 2223 } 2224 2225 return Mnemonic; 2226} 2227 2228/// \brief Given a canonical mnemonic, determine if the instruction ever allows 2229/// inclusion of carry set or predication code operands. 2230// 2231// FIXME: It would be nice to autogen this. 2232void ARMAsmParser:: 2233GetMnemonicAcceptInfo(StringRef Mnemonic, bool &CanAcceptCarrySet, 2234 bool &CanAcceptPredicationCode) { 2235 if (Mnemonic == "and" || Mnemonic == "lsl" || Mnemonic == "lsr" || 2236 Mnemonic == "rrx" || Mnemonic == "ror" || Mnemonic == "sub" || 2237 Mnemonic == "smull" || Mnemonic == "add" || Mnemonic == "adc" || 2238 Mnemonic == "mul" || Mnemonic == "bic" || Mnemonic == "asr" || 2239 Mnemonic == "umlal" || Mnemonic == "orr" || Mnemonic == "mvn" || 2240 Mnemonic == "rsb" || Mnemonic == "rsc" || Mnemonic == "orn" || 2241 Mnemonic == "sbc" || Mnemonic == "mla" || Mnemonic == "umull" || 2242 Mnemonic == "eor" || Mnemonic == "smlal" || 2243 (Mnemonic == "mov" && !isThumbOne())) { 2244 CanAcceptCarrySet = true; 2245 } else { 2246 CanAcceptCarrySet = false; 2247 } 2248 2249 if (Mnemonic == "cbnz" || Mnemonic == "setend" || Mnemonic == "dmb" || 2250 Mnemonic == "cps" || Mnemonic == "mcr2" || Mnemonic == "it" || 2251 Mnemonic == "mcrr2" || Mnemonic == "cbz" || Mnemonic == "cdp2" || 2252 Mnemonic == "trap" || Mnemonic == "mrc2" || Mnemonic == "mrrc2" || 2253 Mnemonic == "dsb" || Mnemonic == "isb" || Mnemonic == "clrex" || 2254 Mnemonic == "setend" || 2255 Mnemonic.startswith("cps") || (Mnemonic == "movs" && isThumb())) { 2256 CanAcceptPredicationCode = false; 2257 } else { 2258 CanAcceptPredicationCode = true; 2259 } 2260 2261 if (isThumb()) 2262 if (Mnemonic == "bkpt" || Mnemonic == "mcr" || Mnemonic == "mcrr" || 2263 Mnemonic == "mrc" || Mnemonic == "mrrc" || Mnemonic == "cdp") 2264 CanAcceptPredicationCode = false; 2265} 2266 2267/// Parse an arm instruction mnemonic followed by its operands. 2268bool ARMAsmParser::ParseInstruction(StringRef Name, SMLoc NameLoc, 2269 SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 2270 // Create the leading tokens for the mnemonic, split by '.' characters. 2271 size_t Start = 0, Next = Name.find('.'); 2272 StringRef Mnemonic = Name.slice(Start, Next); 2273 2274 // Split out the predication code and carry setting flag from the mnemonic. 2275 unsigned PredicationCode; 2276 unsigned ProcessorIMod; 2277 bool CarrySetting; 2278 Mnemonic = SplitMnemonic(Mnemonic, PredicationCode, CarrySetting, 2279 ProcessorIMod); 2280 2281 Operands.push_back(ARMOperand::CreateToken(Mnemonic, NameLoc)); 2282 2283 // FIXME: This is all a pretty gross hack. We should automatically handle 2284 // optional operands like this via tblgen. 2285 2286 // Next, add the CCOut and ConditionCode operands, if needed. 2287 // 2288 // For mnemonics which can ever incorporate a carry setting bit or predication 2289 // code, our matching model involves us always generating CCOut and 2290 // ConditionCode operands to match the mnemonic "as written" and then we let 2291 // the matcher deal with finding the right instruction or generating an 2292 // appropriate error. 2293 bool CanAcceptCarrySet, CanAcceptPredicationCode; 2294 GetMnemonicAcceptInfo(Mnemonic, CanAcceptCarrySet, CanAcceptPredicationCode); 2295 2296 // If we had a carry-set on an instruction that can't do that, issue an 2297 // error. 2298 if (!CanAcceptCarrySet && CarrySetting) { 2299 Parser.EatToEndOfStatement(); 2300 return Error(NameLoc, "instruction '" + Mnemonic + 2301 "' can not set flags, but 's' suffix specified"); 2302 } 2303 // If we had a predication code on an instruction that can't do that, issue an 2304 // error. 2305 if (!CanAcceptPredicationCode && PredicationCode != ARMCC::AL) { 2306 Parser.EatToEndOfStatement(); 2307 return Error(NameLoc, "instruction '" + Mnemonic + 2308 "' is not predicable, but condition code specified"); 2309 } 2310 2311 // Add the carry setting operand, if necessary. 2312 // 2313 // FIXME: It would be awesome if we could somehow invent a location such that 2314 // match errors on this operand would print a nice diagnostic about how the 2315 // 's' character in the mnemonic resulted in a CCOut operand. 2316 if (CanAcceptCarrySet) 2317 Operands.push_back(ARMOperand::CreateCCOut(CarrySetting ? ARM::CPSR : 0, 2318 NameLoc)); 2319 2320 // Add the predication code operand, if necessary. 2321 if (CanAcceptPredicationCode) { 2322 Operands.push_back(ARMOperand::CreateCondCode( 2323 ARMCC::CondCodes(PredicationCode), NameLoc)); 2324 } 2325 2326 // Add the processor imod operand, if necessary. 2327 if (ProcessorIMod) { 2328 Operands.push_back(ARMOperand::CreateImm( 2329 MCConstantExpr::Create(ProcessorIMod, getContext()), 2330 NameLoc, NameLoc)); 2331 } else { 2332 // This mnemonic can't ever accept a imod, but the user wrote 2333 // one (or misspelled another mnemonic). 2334 2335 // FIXME: Issue a nice error. 2336 } 2337 2338 // Add the remaining tokens in the mnemonic. 2339 while (Next != StringRef::npos) { 2340 Start = Next; 2341 Next = Name.find('.', Start + 1); 2342 StringRef ExtraToken = Name.slice(Start, Next); 2343 2344 Operands.push_back(ARMOperand::CreateToken(ExtraToken, NameLoc)); 2345 } 2346 2347 // Read the remaining operands. 2348 if (getLexer().isNot(AsmToken::EndOfStatement)) { 2349 // Read the first operand. 2350 if (ParseOperand(Operands, Mnemonic)) { 2351 Parser.EatToEndOfStatement(); 2352 return true; 2353 } 2354 2355 while (getLexer().is(AsmToken::Comma)) { 2356 Parser.Lex(); // Eat the comma. 2357 2358 // Parse and remember the operand. 2359 if (ParseOperand(Operands, Mnemonic)) { 2360 Parser.EatToEndOfStatement(); 2361 return true; 2362 } 2363 } 2364 } 2365 2366 if (getLexer().isNot(AsmToken::EndOfStatement)) { 2367 Parser.EatToEndOfStatement(); 2368 return TokError("unexpected token in argument list"); 2369 } 2370 2371 Parser.Lex(); // Consume the EndOfStatement 2372 2373 2374 // The 'mov' mnemonic is special. One variant has a cc_out operand, while 2375 // another does not. Specifically, the MOVW instruction does not. So we 2376 // special case it here and remove the defaulted (non-setting) cc_out 2377 // operand if that's the instruction we're trying to match. 2378 // 2379 // We do this post-processing of the explicit operands rather than just 2380 // conditionally adding the cc_out in the first place because we need 2381 // to check the type of the parsed immediate operand. 2382 if (Mnemonic == "mov" && Operands.size() > 4 && 2383 !static_cast<ARMOperand*>(Operands[4])->isARMSOImm() && 2384 static_cast<ARMOperand*>(Operands[4])->isImm0_65535Expr() && 2385 static_cast<ARMOperand*>(Operands[1])->getReg() == 0) { 2386 ARMOperand *Op = static_cast<ARMOperand*>(Operands[1]); 2387 Operands.erase(Operands.begin() + 1); 2388 delete Op; 2389 } 2390 2391 return false; 2392} 2393 2394bool ARMAsmParser:: 2395MatchAndEmitInstruction(SMLoc IDLoc, 2396 SmallVectorImpl<MCParsedAsmOperand*> &Operands, 2397 MCStreamer &Out) { 2398 MCInst Inst; 2399 unsigned ErrorInfo; 2400 MatchResultTy MatchResult; 2401 MatchResult = MatchInstructionImpl(Operands, Inst, ErrorInfo); 2402 switch (MatchResult) { 2403 case Match_Success: 2404 Out.EmitInstruction(Inst); 2405 return false; 2406 case Match_MissingFeature: 2407 Error(IDLoc, "instruction requires a CPU feature not currently enabled"); 2408 return true; 2409 case Match_InvalidOperand: { 2410 SMLoc ErrorLoc = IDLoc; 2411 if (ErrorInfo != ~0U) { 2412 if (ErrorInfo >= Operands.size()) 2413 return Error(IDLoc, "too few operands for instruction"); 2414 2415 ErrorLoc = ((ARMOperand*)Operands[ErrorInfo])->getStartLoc(); 2416 if (ErrorLoc == SMLoc()) ErrorLoc = IDLoc; 2417 } 2418 2419 return Error(ErrorLoc, "invalid operand for instruction"); 2420 } 2421 case Match_MnemonicFail: 2422 return Error(IDLoc, "unrecognized instruction mnemonic"); 2423 case Match_ConversionFail: 2424 return Error(IDLoc, "unable to convert operands to instruction"); 2425 } 2426 2427 llvm_unreachable("Implement any new match types added!"); 2428 return true; 2429} 2430 2431/// ParseDirective parses the arm specific directives 2432bool ARMAsmParser::ParseDirective(AsmToken DirectiveID) { 2433 StringRef IDVal = DirectiveID.getIdentifier(); 2434 if (IDVal == ".word") 2435 return ParseDirectiveWord(4, DirectiveID.getLoc()); 2436 else if (IDVal == ".thumb") 2437 return ParseDirectiveThumb(DirectiveID.getLoc()); 2438 else if (IDVal == ".thumb_func") 2439 return ParseDirectiveThumbFunc(DirectiveID.getLoc()); 2440 else if (IDVal == ".code") 2441 return ParseDirectiveCode(DirectiveID.getLoc()); 2442 else if (IDVal == ".syntax") 2443 return ParseDirectiveSyntax(DirectiveID.getLoc()); 2444 return true; 2445} 2446 2447/// ParseDirectiveWord 2448/// ::= .word [ expression (, expression)* ] 2449bool ARMAsmParser::ParseDirectiveWord(unsigned Size, SMLoc L) { 2450 if (getLexer().isNot(AsmToken::EndOfStatement)) { 2451 for (;;) { 2452 const MCExpr *Value; 2453 if (getParser().ParseExpression(Value)) 2454 return true; 2455 2456 getParser().getStreamer().EmitValue(Value, Size, 0/*addrspace*/); 2457 2458 if (getLexer().is(AsmToken::EndOfStatement)) 2459 break; 2460 2461 // FIXME: Improve diagnostic. 2462 if (getLexer().isNot(AsmToken::Comma)) 2463 return Error(L, "unexpected token in directive"); 2464 Parser.Lex(); 2465 } 2466 } 2467 2468 Parser.Lex(); 2469 return false; 2470} 2471 2472/// ParseDirectiveThumb 2473/// ::= .thumb 2474bool ARMAsmParser::ParseDirectiveThumb(SMLoc L) { 2475 if (getLexer().isNot(AsmToken::EndOfStatement)) 2476 return Error(L, "unexpected token in directive"); 2477 Parser.Lex(); 2478 2479 // TODO: set thumb mode 2480 // TODO: tell the MC streamer the mode 2481 // getParser().getStreamer().Emit???(); 2482 return false; 2483} 2484 2485/// ParseDirectiveThumbFunc 2486/// ::= .thumbfunc symbol_name 2487bool ARMAsmParser::ParseDirectiveThumbFunc(SMLoc L) { 2488 const MCAsmInfo &MAI = getParser().getStreamer().getContext().getAsmInfo(); 2489 bool isMachO = MAI.hasSubsectionsViaSymbols(); 2490 StringRef Name; 2491 2492 // Darwin asm has function name after .thumb_func direction 2493 // ELF doesn't 2494 if (isMachO) { 2495 const AsmToken &Tok = Parser.getTok(); 2496 if (Tok.isNot(AsmToken::Identifier) && Tok.isNot(AsmToken::String)) 2497 return Error(L, "unexpected token in .thumb_func directive"); 2498 Name = Tok.getString(); 2499 Parser.Lex(); // Consume the identifier token. 2500 } 2501 2502 if (getLexer().isNot(AsmToken::EndOfStatement)) 2503 return Error(L, "unexpected token in directive"); 2504 Parser.Lex(); 2505 2506 // FIXME: assuming function name will be the line following .thumb_func 2507 if (!isMachO) { 2508 Name = Parser.getTok().getString(); 2509 } 2510 2511 // Mark symbol as a thumb symbol. 2512 MCSymbol *Func = getParser().getContext().GetOrCreateSymbol(Name); 2513 getParser().getStreamer().EmitThumbFunc(Func); 2514 return false; 2515} 2516 2517/// ParseDirectiveSyntax 2518/// ::= .syntax unified | divided 2519bool ARMAsmParser::ParseDirectiveSyntax(SMLoc L) { 2520 const AsmToken &Tok = Parser.getTok(); 2521 if (Tok.isNot(AsmToken::Identifier)) 2522 return Error(L, "unexpected token in .syntax directive"); 2523 StringRef Mode = Tok.getString(); 2524 if (Mode == "unified" || Mode == "UNIFIED") 2525 Parser.Lex(); 2526 else if (Mode == "divided" || Mode == "DIVIDED") 2527 return Error(L, "'.syntax divided' arm asssembly not supported"); 2528 else 2529 return Error(L, "unrecognized syntax mode in .syntax directive"); 2530 2531 if (getLexer().isNot(AsmToken::EndOfStatement)) 2532 return Error(Parser.getTok().getLoc(), "unexpected token in directive"); 2533 Parser.Lex(); 2534 2535 // TODO tell the MC streamer the mode 2536 // getParser().getStreamer().Emit???(); 2537 return false; 2538} 2539 2540/// ParseDirectiveCode 2541/// ::= .code 16 | 32 2542bool ARMAsmParser::ParseDirectiveCode(SMLoc L) { 2543 const AsmToken &Tok = Parser.getTok(); 2544 if (Tok.isNot(AsmToken::Integer)) 2545 return Error(L, "unexpected token in .code directive"); 2546 int64_t Val = Parser.getTok().getIntVal(); 2547 if (Val == 16) 2548 Parser.Lex(); 2549 else if (Val == 32) 2550 Parser.Lex(); 2551 else 2552 return Error(L, "invalid operand to .code directive"); 2553 2554 if (getLexer().isNot(AsmToken::EndOfStatement)) 2555 return Error(Parser.getTok().getLoc(), "unexpected token in directive"); 2556 Parser.Lex(); 2557 2558 if (Val == 16) { 2559 if (!isThumb()) 2560 SwitchMode(); 2561 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code16); 2562 } else { 2563 if (isThumb()) 2564 SwitchMode(); 2565 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code32); 2566 } 2567 2568 return false; 2569} 2570 2571extern "C" void LLVMInitializeARMAsmLexer(); 2572 2573/// Force static initialization. 2574extern "C" void LLVMInitializeARMAsmParser() { 2575 RegisterAsmParser<ARMAsmParser> X(TheARMTarget); 2576 RegisterAsmParser<ARMAsmParser> Y(TheThumbTarget); 2577 LLVMInitializeARMAsmLexer(); 2578} 2579 2580#define GET_REGISTER_MATCHER 2581#define GET_MATCHER_IMPLEMENTATION 2582#include "ARMGenAsmMatcher.inc" 2583