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