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