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