ARMAsmParser.cpp revision f922c47143d247cbae14b294a0bada139bcd35f6
1//===-- ARMAsmParser.cpp - Parse ARM assembly to MCInst instructions ------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9 10#include "ARM.h" 11#include "ARMAddressingModes.h" 12#include "ARMMCExpr.h" 13#include "ARMBaseRegisterInfo.h" 14#include "ARMSubtarget.h" 15#include "llvm/MC/MCParser/MCAsmLexer.h" 16#include "llvm/MC/MCParser/MCAsmParser.h" 17#include "llvm/MC/MCParser/MCParsedAsmOperand.h" 18#include "llvm/MC/MCContext.h" 19#include "llvm/MC/MCStreamer.h" 20#include "llvm/MC/MCExpr.h" 21#include "llvm/MC/MCInst.h" 22#include "llvm/Target/TargetRegistry.h" 23#include "llvm/Target/TargetAsmParser.h" 24#include "llvm/Support/SourceMgr.h" 25#include "llvm/Support/raw_ostream.h" 26#include "llvm/ADT/SmallVector.h" 27#include "llvm/ADT/StringExtras.h" 28#include "llvm/ADT/StringSwitch.h" 29#include "llvm/ADT/Twine.h" 30using namespace llvm; 31 32/// Shift types used for register controlled shifts in ARM memory addressing. 33enum ShiftType { 34 Lsl, 35 Lsr, 36 Asr, 37 Ror, 38 Rrx 39}; 40 41namespace { 42 43class ARMOperand; 44 45class ARMAsmParser : public TargetAsmParser { 46 MCAsmParser &Parser; 47 TargetMachine &TM; 48 49 MCAsmParser &getParser() const { return Parser; } 50 MCAsmLexer &getLexer() const { return Parser.getLexer(); } 51 52 void Warning(SMLoc L, const Twine &Msg) { Parser.Warning(L, Msg); } 53 bool Error(SMLoc L, const Twine &Msg) { return Parser.Error(L, Msg); } 54 55 int TryParseRegister(); 56 virtual bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc); 57 bool TryParseRegisterWithWriteBack(SmallVectorImpl<MCParsedAsmOperand*> &); 58 bool ParseRegisterList(SmallVectorImpl<MCParsedAsmOperand*> &); 59 bool ParseMemory(SmallVectorImpl<MCParsedAsmOperand*> &); 60 bool ParseOperand(SmallVectorImpl<MCParsedAsmOperand*> &, StringRef Mnemonic); 61 bool ParsePrefix(ARMMCExpr::VariantKind &RefKind); 62 const MCExpr *ApplyPrefixToExpr(const MCExpr *E, 63 MCSymbolRefExpr::VariantKind Variant); 64 65 66 bool ParseMemoryOffsetReg(bool &Negative, 67 bool &OffsetRegShifted, 68 enum ShiftType &ShiftType, 69 const MCExpr *&ShiftAmount, 70 const MCExpr *&Offset, 71 bool &OffsetIsReg, 72 int &OffsetRegNum, 73 SMLoc &E); 74 bool ParseShift(enum ShiftType &St, const MCExpr *&ShiftAmount, SMLoc &E); 75 bool ParseDirectiveWord(unsigned Size, SMLoc L); 76 bool ParseDirectiveThumb(SMLoc L); 77 bool ParseDirectiveThumbFunc(SMLoc L); 78 bool ParseDirectiveCode(SMLoc L); 79 bool ParseDirectiveSyntax(SMLoc L); 80 81 bool MatchAndEmitInstruction(SMLoc IDLoc, 82 SmallVectorImpl<MCParsedAsmOperand*> &Operands, 83 MCStreamer &Out); 84 void GetMnemonicAcceptInfo(StringRef Mnemonic, bool &CanAcceptCarrySet, 85 bool &CanAcceptPredicationCode); 86 87 /// @name Auto-generated Match Functions 88 /// { 89 90#define GET_ASSEMBLER_HEADER 91#include "ARMGenAsmMatcher.inc" 92 93 /// } 94 95 OperandMatchResultTy tryParseCoprocNumOperand( 96 SmallVectorImpl<MCParsedAsmOperand*>&); 97 OperandMatchResultTy tryParseCoprocRegOperand( 98 SmallVectorImpl<MCParsedAsmOperand*>&); 99 OperandMatchResultTy tryParseMemBarrierOptOperand( 100 SmallVectorImpl<MCParsedAsmOperand*> &); 101 102public: 103 ARMAsmParser(const Target &T, MCAsmParser &_Parser, TargetMachine &_TM) 104 : TargetAsmParser(T), Parser(_Parser), TM(_TM) { 105 // Initialize the set of available features. 106 setAvailableFeatures(ComputeAvailableFeatures( 107 &TM.getSubtarget<ARMSubtarget>())); 108 } 109 110 virtual bool ParseInstruction(StringRef Name, SMLoc NameLoc, 111 SmallVectorImpl<MCParsedAsmOperand*> &Operands); 112 virtual bool ParseDirective(AsmToken DirectiveID); 113}; 114} // end anonymous namespace 115 116namespace { 117 118/// ARMOperand - Instances of this class represent a parsed ARM machine 119/// instruction. 120class ARMOperand : public MCParsedAsmOperand { 121 enum KindTy { 122 CondCode, 123 CCOut, 124 CoprocNum, 125 CoprocReg, 126 Immediate, 127 MemBarrierOpt, 128 Memory, 129 Register, 130 RegisterList, 131 DPRRegisterList, 132 SPRRegisterList, 133 Token 134 } Kind; 135 136 SMLoc StartLoc, EndLoc; 137 SmallVector<unsigned, 8> Registers; 138 139 union { 140 struct { 141 ARMCC::CondCodes Val; 142 } CC; 143 144 struct { 145 ARM_MB::MemBOpt Val; 146 } MBOpt; 147 148 struct { 149 unsigned Val; 150 } Cop; 151 152 struct { 153 const char *Data; 154 unsigned Length; 155 } Tok; 156 157 struct { 158 unsigned RegNum; 159 } Reg; 160 161 struct { 162 const MCExpr *Val; 163 } Imm; 164 165 /// Combined record for all forms of ARM address expressions. 166 struct { 167 unsigned BaseRegNum; 168 union { 169 unsigned RegNum; ///< Offset register num, when OffsetIsReg. 170 const MCExpr *Value; ///< Offset value, when !OffsetIsReg. 171 } Offset; 172 const MCExpr *ShiftAmount; // used when OffsetRegShifted is true 173 enum ShiftType ShiftType; // used when OffsetRegShifted is true 174 unsigned OffsetRegShifted : 1; // only used when OffsetIsReg is true 175 unsigned Preindexed : 1; 176 unsigned Postindexed : 1; 177 unsigned OffsetIsReg : 1; 178 unsigned Negative : 1; // only used when OffsetIsReg is true 179 unsigned Writeback : 1; 180 } Mem; 181 }; 182 183 ARMOperand(KindTy K) : MCParsedAsmOperand(), Kind(K) {} 184public: 185 ARMOperand(const ARMOperand &o) : MCParsedAsmOperand() { 186 Kind = o.Kind; 187 StartLoc = o.StartLoc; 188 EndLoc = o.EndLoc; 189 switch (Kind) { 190 case CondCode: 191 CC = o.CC; 192 break; 193 case Token: 194 Tok = o.Tok; 195 break; 196 case CCOut: 197 case Register: 198 Reg = o.Reg; 199 break; 200 case RegisterList: 201 case DPRRegisterList: 202 case SPRRegisterList: 203 Registers = o.Registers; 204 break; 205 case CoprocNum: 206 case CoprocReg: 207 Cop = o.Cop; 208 break; 209 case Immediate: 210 Imm = o.Imm; 211 break; 212 case MemBarrierOpt: 213 MBOpt = o.MBOpt; 214 break; 215 case Memory: 216 Mem = o.Mem; 217 break; 218 } 219 } 220 221 /// getStartLoc - Get the location of the first token of this operand. 222 SMLoc getStartLoc() const { return StartLoc; } 223 /// getEndLoc - Get the location of the last token of this operand. 224 SMLoc getEndLoc() const { return EndLoc; } 225 226 ARMCC::CondCodes getCondCode() const { 227 assert(Kind == CondCode && "Invalid access!"); 228 return CC.Val; 229 } 230 231 unsigned getCoproc() const { 232 assert((Kind == CoprocNum || Kind == CoprocReg) && "Invalid access!"); 233 return Cop.Val; 234 } 235 236 StringRef getToken() const { 237 assert(Kind == Token && "Invalid access!"); 238 return StringRef(Tok.Data, Tok.Length); 239 } 240 241 unsigned getReg() const { 242 assert((Kind == Register || Kind == CCOut) && "Invalid access!"); 243 return Reg.RegNum; 244 } 245 246 const SmallVectorImpl<unsigned> &getRegList() const { 247 assert((Kind == RegisterList || Kind == DPRRegisterList || 248 Kind == SPRRegisterList) && "Invalid access!"); 249 return Registers; 250 } 251 252 const MCExpr *getImm() const { 253 assert(Kind == Immediate && "Invalid access!"); 254 return Imm.Val; 255 } 256 257 ARM_MB::MemBOpt getMemBarrierOpt() const { 258 assert(Kind == MemBarrierOpt && "Invalid access!"); 259 return MBOpt.Val; 260 } 261 262 /// @name Memory Operand Accessors 263 /// @{ 264 265 unsigned getMemBaseRegNum() const { 266 return Mem.BaseRegNum; 267 } 268 unsigned getMemOffsetRegNum() const { 269 assert(Mem.OffsetIsReg && "Invalid access!"); 270 return Mem.Offset.RegNum; 271 } 272 const MCExpr *getMemOffset() const { 273 assert(!Mem.OffsetIsReg && "Invalid access!"); 274 return Mem.Offset.Value; 275 } 276 unsigned getMemOffsetRegShifted() const { 277 assert(Mem.OffsetIsReg && "Invalid access!"); 278 return Mem.OffsetRegShifted; 279 } 280 const MCExpr *getMemShiftAmount() const { 281 assert(Mem.OffsetIsReg && Mem.OffsetRegShifted && "Invalid access!"); 282 return Mem.ShiftAmount; 283 } 284 enum ShiftType getMemShiftType() const { 285 assert(Mem.OffsetIsReg && Mem.OffsetRegShifted && "Invalid access!"); 286 return Mem.ShiftType; 287 } 288 bool getMemPreindexed() const { return Mem.Preindexed; } 289 bool getMemPostindexed() const { return Mem.Postindexed; } 290 bool getMemOffsetIsReg() const { return Mem.OffsetIsReg; } 291 bool getMemNegative() const { return Mem.Negative; } 292 bool getMemWriteback() const { return Mem.Writeback; } 293 294 /// @} 295 296 bool isCoprocNum() const { return Kind == CoprocNum; } 297 bool isCoprocReg() const { return Kind == CoprocReg; } 298 bool isCondCode() const { return Kind == CondCode; } 299 bool isCCOut() const { return Kind == CCOut; } 300 bool isImm() const { return Kind == Immediate; } 301 bool isReg() const { return Kind == Register; } 302 bool isRegList() const { return Kind == RegisterList; } 303 bool isDPRRegList() const { return Kind == DPRRegisterList; } 304 bool isSPRRegList() const { return Kind == SPRRegisterList; } 305 bool isToken() const { return Kind == Token; } 306 bool isMemBarrierOpt() const { return Kind == MemBarrierOpt; } 307 bool isMemory() const { return Kind == Memory; } 308 bool isMemMode5() const { 309 if (!isMemory() || getMemOffsetIsReg() || getMemWriteback() || 310 getMemNegative()) 311 return false; 312 313 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 314 if (!CE) return false; 315 316 // The offset must be a multiple of 4 in the range 0-1020. 317 int64_t Value = CE->getValue(); 318 return ((Value & 0x3) == 0 && Value <= 1020 && Value >= -1020); 319 } 320 bool isMemModeRegThumb() const { 321 if (!isMemory() || !getMemOffsetIsReg() || getMemWriteback()) 322 return false; 323 return true; 324 } 325 bool isMemModeImmThumb() const { 326 if (!isMemory() || getMemOffsetIsReg() || getMemWriteback()) 327 return false; 328 329 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 330 if (!CE) return false; 331 332 // The offset must be a multiple of 4 in the range 0-124. 333 uint64_t Value = CE->getValue(); 334 return ((Value & 0x3) == 0 && Value <= 124); 335 } 336 337 void addExpr(MCInst &Inst, const MCExpr *Expr) const { 338 // Add as immediates when possible. Null MCExpr = 0. 339 if (Expr == 0) 340 Inst.addOperand(MCOperand::CreateImm(0)); 341 else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr)) 342 Inst.addOperand(MCOperand::CreateImm(CE->getValue())); 343 else 344 Inst.addOperand(MCOperand::CreateExpr(Expr)); 345 } 346 347 void addCondCodeOperands(MCInst &Inst, unsigned N) const { 348 assert(N == 2 && "Invalid number of operands!"); 349 Inst.addOperand(MCOperand::CreateImm(unsigned(getCondCode()))); 350 unsigned RegNum = getCondCode() == ARMCC::AL ? 0: ARM::CPSR; 351 Inst.addOperand(MCOperand::CreateReg(RegNum)); 352 } 353 354 void addCoprocNumOperands(MCInst &Inst, unsigned N) const { 355 assert(N == 1 && "Invalid number of operands!"); 356 Inst.addOperand(MCOperand::CreateImm(getCoproc())); 357 } 358 359 void addCoprocRegOperands(MCInst &Inst, unsigned N) const { 360 assert(N == 1 && "Invalid number of operands!"); 361 Inst.addOperand(MCOperand::CreateImm(getCoproc())); 362 } 363 364 void addCCOutOperands(MCInst &Inst, unsigned N) const { 365 assert(N == 1 && "Invalid number of operands!"); 366 Inst.addOperand(MCOperand::CreateReg(getReg())); 367 } 368 369 void addRegOperands(MCInst &Inst, unsigned N) const { 370 assert(N == 1 && "Invalid number of operands!"); 371 Inst.addOperand(MCOperand::CreateReg(getReg())); 372 } 373 374 void addRegListOperands(MCInst &Inst, unsigned N) const { 375 assert(N == 1 && "Invalid number of operands!"); 376 const SmallVectorImpl<unsigned> &RegList = getRegList(); 377 for (SmallVectorImpl<unsigned>::const_iterator 378 I = RegList.begin(), E = RegList.end(); I != E; ++I) 379 Inst.addOperand(MCOperand::CreateReg(*I)); 380 } 381 382 void addDPRRegListOperands(MCInst &Inst, unsigned N) const { 383 addRegListOperands(Inst, N); 384 } 385 386 void addSPRRegListOperands(MCInst &Inst, unsigned N) const { 387 addRegListOperands(Inst, N); 388 } 389 390 void addImmOperands(MCInst &Inst, unsigned N) const { 391 assert(N == 1 && "Invalid number of operands!"); 392 addExpr(Inst, getImm()); 393 } 394 395 void addMemBarrierOptOperands(MCInst &Inst, unsigned N) const { 396 assert(N == 1 && "Invalid number of operands!"); 397 Inst.addOperand(MCOperand::CreateImm(unsigned(getMemBarrierOpt()))); 398 } 399 400 void addMemMode5Operands(MCInst &Inst, unsigned N) const { 401 assert(N == 2 && isMemMode5() && "Invalid number of operands!"); 402 403 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 404 assert(!getMemOffsetIsReg() && "Invalid mode 5 operand"); 405 406 // FIXME: #-0 is encoded differently than #0. Does the parser preserve 407 // the difference? 408 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 409 assert(CE && "Non-constant mode 5 offset operand!"); 410 411 // The MCInst offset operand doesn't include the low two bits (like 412 // the instruction encoding). 413 int64_t Offset = CE->getValue() / 4; 414 if (Offset >= 0) 415 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM5Opc(ARM_AM::add, 416 Offset))); 417 else 418 Inst.addOperand(MCOperand::CreateImm(ARM_AM::getAM5Opc(ARM_AM::sub, 419 -Offset))); 420 } 421 422 void addMemModeRegThumbOperands(MCInst &Inst, unsigned N) const { 423 assert(N == 2 && isMemModeRegThumb() && "Invalid number of operands!"); 424 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 425 Inst.addOperand(MCOperand::CreateReg(getMemOffsetRegNum())); 426 } 427 428 void addMemModeImmThumbOperands(MCInst &Inst, unsigned N) const { 429 assert(N == 2 && isMemModeImmThumb() && "Invalid number of operands!"); 430 Inst.addOperand(MCOperand::CreateReg(getMemBaseRegNum())); 431 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemOffset()); 432 assert(CE && "Non-constant mode offset operand!"); 433 Inst.addOperand(MCOperand::CreateImm(CE->getValue())); 434 } 435 436 virtual void dump(raw_ostream &OS) const; 437 438 static ARMOperand *CreateCondCode(ARMCC::CondCodes CC, SMLoc S) { 439 ARMOperand *Op = new ARMOperand(CondCode); 440 Op->CC.Val = CC; 441 Op->StartLoc = S; 442 Op->EndLoc = S; 443 return Op; 444 } 445 446 static ARMOperand *CreateCoprocNum(unsigned CopVal, SMLoc S) { 447 ARMOperand *Op = new ARMOperand(CoprocNum); 448 Op->Cop.Val = CopVal; 449 Op->StartLoc = S; 450 Op->EndLoc = S; 451 return Op; 452 } 453 454 static ARMOperand *CreateCoprocReg(unsigned CopVal, SMLoc S) { 455 ARMOperand *Op = new ARMOperand(CoprocReg); 456 Op->Cop.Val = CopVal; 457 Op->StartLoc = S; 458 Op->EndLoc = S; 459 return Op; 460 } 461 462 static ARMOperand *CreateCCOut(unsigned RegNum, SMLoc S) { 463 ARMOperand *Op = new ARMOperand(CCOut); 464 Op->Reg.RegNum = RegNum; 465 Op->StartLoc = S; 466 Op->EndLoc = S; 467 return Op; 468 } 469 470 static ARMOperand *CreateToken(StringRef Str, SMLoc S) { 471 ARMOperand *Op = new ARMOperand(Token); 472 Op->Tok.Data = Str.data(); 473 Op->Tok.Length = Str.size(); 474 Op->StartLoc = S; 475 Op->EndLoc = S; 476 return Op; 477 } 478 479 static ARMOperand *CreateReg(unsigned RegNum, SMLoc S, SMLoc E) { 480 ARMOperand *Op = new ARMOperand(Register); 481 Op->Reg.RegNum = RegNum; 482 Op->StartLoc = S; 483 Op->EndLoc = E; 484 return Op; 485 } 486 487 static ARMOperand * 488 CreateRegList(const SmallVectorImpl<std::pair<unsigned, SMLoc> > &Regs, 489 SMLoc StartLoc, SMLoc EndLoc) { 490 KindTy Kind = RegisterList; 491 492 if (ARM::DPRRegClass.contains(Regs.front().first)) 493 Kind = DPRRegisterList; 494 else if (ARM::SPRRegClass.contains(Regs.front().first)) 495 Kind = SPRRegisterList; 496 497 ARMOperand *Op = new ARMOperand(Kind); 498 for (SmallVectorImpl<std::pair<unsigned, SMLoc> >::const_iterator 499 I = Regs.begin(), E = Regs.end(); I != E; ++I) 500 Op->Registers.push_back(I->first); 501 array_pod_sort(Op->Registers.begin(), Op->Registers.end()); 502 Op->StartLoc = StartLoc; 503 Op->EndLoc = EndLoc; 504 return Op; 505 } 506 507 static ARMOperand *CreateImm(const MCExpr *Val, SMLoc S, SMLoc E) { 508 ARMOperand *Op = new ARMOperand(Immediate); 509 Op->Imm.Val = Val; 510 Op->StartLoc = S; 511 Op->EndLoc = E; 512 return Op; 513 } 514 515 static ARMOperand *CreateMem(unsigned BaseRegNum, bool OffsetIsReg, 516 const MCExpr *Offset, int OffsetRegNum, 517 bool OffsetRegShifted, enum ShiftType ShiftType, 518 const MCExpr *ShiftAmount, bool Preindexed, 519 bool Postindexed, bool Negative, bool Writeback, 520 SMLoc S, SMLoc E) { 521 assert((OffsetRegNum == -1 || OffsetIsReg) && 522 "OffsetRegNum must imply OffsetIsReg!"); 523 assert((!OffsetRegShifted || OffsetIsReg) && 524 "OffsetRegShifted must imply OffsetIsReg!"); 525 assert((Offset || OffsetIsReg) && 526 "Offset must exists unless register offset is used!"); 527 assert((!ShiftAmount || (OffsetIsReg && OffsetRegShifted)) && 528 "Cannot have shift amount without shifted register offset!"); 529 assert((!Offset || !OffsetIsReg) && 530 "Cannot have expression offset and register offset!"); 531 532 ARMOperand *Op = new ARMOperand(Memory); 533 Op->Mem.BaseRegNum = BaseRegNum; 534 Op->Mem.OffsetIsReg = OffsetIsReg; 535 if (OffsetIsReg) 536 Op->Mem.Offset.RegNum = OffsetRegNum; 537 else 538 Op->Mem.Offset.Value = Offset; 539 Op->Mem.OffsetRegShifted = OffsetRegShifted; 540 Op->Mem.ShiftType = ShiftType; 541 Op->Mem.ShiftAmount = ShiftAmount; 542 Op->Mem.Preindexed = Preindexed; 543 Op->Mem.Postindexed = Postindexed; 544 Op->Mem.Negative = Negative; 545 Op->Mem.Writeback = Writeback; 546 547 Op->StartLoc = S; 548 Op->EndLoc = E; 549 return Op; 550 } 551 552 static ARMOperand *CreateMemBarrierOpt(ARM_MB::MemBOpt Opt, SMLoc S) { 553 ARMOperand *Op = new ARMOperand(MemBarrierOpt); 554 Op->MBOpt.Val = Opt; 555 Op->StartLoc = S; 556 Op->EndLoc = S; 557 return Op; 558 } 559}; 560 561} // end anonymous namespace. 562 563void ARMOperand::dump(raw_ostream &OS) const { 564 switch (Kind) { 565 case CondCode: 566 OS << "<ARMCC::" << ARMCondCodeToString(getCondCode()) << ">"; 567 break; 568 case CCOut: 569 OS << "<ccout " << getReg() << ">"; 570 break; 571 case CoprocNum: 572 OS << "<coprocessor number: " << getCoproc() << ">"; 573 break; 574 case CoprocReg: 575 OS << "<coprocessor register: " << getCoproc() << ">"; 576 break; 577 case Immediate: 578 getImm()->print(OS); 579 break; 580 case MemBarrierOpt: 581 OS << "<ARM_MB::" << MemBOptToString(getMemBarrierOpt()) << ">"; 582 break; 583 case Memory: 584 OS << "<memory " 585 << "base:" << getMemBaseRegNum(); 586 if (getMemOffsetIsReg()) { 587 OS << " offset:<register " << getMemOffsetRegNum(); 588 if (getMemOffsetRegShifted()) { 589 OS << " offset-shift-type:" << getMemShiftType(); 590 OS << " offset-shift-amount:" << *getMemShiftAmount(); 591 } 592 } else { 593 OS << " offset:" << *getMemOffset(); 594 } 595 if (getMemOffsetIsReg()) 596 OS << " (offset-is-reg)"; 597 if (getMemPreindexed()) 598 OS << " (pre-indexed)"; 599 if (getMemPostindexed()) 600 OS << " (post-indexed)"; 601 if (getMemNegative()) 602 OS << " (negative)"; 603 if (getMemWriteback()) 604 OS << " (writeback)"; 605 OS << ">"; 606 break; 607 case Register: 608 OS << "<register " << getReg() << ">"; 609 break; 610 case RegisterList: 611 case DPRRegisterList: 612 case SPRRegisterList: { 613 OS << "<register_list "; 614 615 const SmallVectorImpl<unsigned> &RegList = getRegList(); 616 for (SmallVectorImpl<unsigned>::const_iterator 617 I = RegList.begin(), E = RegList.end(); I != E; ) { 618 OS << *I; 619 if (++I < E) OS << ", "; 620 } 621 622 OS << ">"; 623 break; 624 } 625 case Token: 626 OS << "'" << getToken() << "'"; 627 break; 628 } 629} 630 631/// @name Auto-generated Match Functions 632/// { 633 634static unsigned MatchRegisterName(StringRef Name); 635 636/// } 637 638bool ARMAsmParser::ParseRegister(unsigned &RegNo, 639 SMLoc &StartLoc, SMLoc &EndLoc) { 640 RegNo = TryParseRegister(); 641 642 return (RegNo == (unsigned)-1); 643} 644 645/// Try to parse a register name. The token must be an Identifier when called, 646/// and if it is a register name the token is eaten and the register number is 647/// returned. Otherwise return -1. 648/// 649int ARMAsmParser::TryParseRegister() { 650 const AsmToken &Tok = Parser.getTok(); 651 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 652 653 // FIXME: Validate register for the current architecture; we have to do 654 // validation later, so maybe there is no need for this here. 655 std::string upperCase = Tok.getString().str(); 656 std::string lowerCase = LowercaseString(upperCase); 657 unsigned RegNum = MatchRegisterName(lowerCase); 658 if (!RegNum) { 659 RegNum = StringSwitch<unsigned>(lowerCase) 660 .Case("r13", ARM::SP) 661 .Case("r14", ARM::LR) 662 .Case("r15", ARM::PC) 663 .Case("ip", ARM::R12) 664 .Default(0); 665 } 666 if (!RegNum) return -1; 667 668 Parser.Lex(); // Eat identifier token. 669 return RegNum; 670} 671 672/// Try to parse a register name. The token must be an Identifier when called. 673/// If it's a register, an AsmOperand is created. Another AsmOperand is created 674/// if there is a "writeback". 'true' if it's not a register. 675/// 676/// TODO this is likely to change to allow different register types and or to 677/// parse for a specific register type. 678bool ARMAsmParser:: 679TryParseRegisterWithWriteBack(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 680 SMLoc S = Parser.getTok().getLoc(); 681 int RegNo = TryParseRegister(); 682 if (RegNo == -1) 683 return true; 684 685 Operands.push_back(ARMOperand::CreateReg(RegNo, S, Parser.getTok().getLoc())); 686 687 const AsmToken &ExclaimTok = Parser.getTok(); 688 if (ExclaimTok.is(AsmToken::Exclaim)) { 689 Operands.push_back(ARMOperand::CreateToken(ExclaimTok.getString(), 690 ExclaimTok.getLoc())); 691 Parser.Lex(); // Eat exclaim token 692 } 693 694 return false; 695} 696 697/// MatchCoprocessorOperandName - Try to parse an coprocessor related 698/// instruction with a symbolic operand name. Example: "p1", "p7", "c3", 699/// "c5", ... 700static int MatchCoprocessorOperandName(StringRef Name, char CoprocOp) { 701 // Use the same layout as the tablegen'erated register name matcher. Ugly, 702 // but efficient. 703 switch (Name.size()) { 704 default: break; 705 case 2: 706 if (Name[0] != CoprocOp) 707 return -1; 708 switch (Name[1]) { 709 default: return -1; 710 case '0': return 0; 711 case '1': return 1; 712 case '2': return 2; 713 case '3': return 3; 714 case '4': return 4; 715 case '5': return 5; 716 case '6': return 6; 717 case '7': return 7; 718 case '8': return 8; 719 case '9': return 9; 720 } 721 break; 722 case 3: 723 if (Name[0] != CoprocOp || Name[1] != '1') 724 return -1; 725 switch (Name[2]) { 726 default: return -1; 727 case '0': return 10; 728 case '1': return 11; 729 case '2': return 12; 730 case '3': return 13; 731 case '4': return 14; 732 case '5': return 15; 733 } 734 break; 735 } 736 737 llvm_unreachable("Unhandled coprocessor operand string!"); 738 return -1; 739} 740 741/// tryParseCoprocNumOperand - Try to parse an coprocessor number operand. The 742/// token must be an Identifier when called, and if it is a coprocessor 743/// number, the token is eaten and the operand is added to the operand list. 744ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 745tryParseCoprocNumOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 746 SMLoc S = Parser.getTok().getLoc(); 747 const AsmToken &Tok = Parser.getTok(); 748 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 749 750 int Num = MatchCoprocessorOperandName(Tok.getString(), 'p'); 751 if (Num == -1) 752 return MatchOperand_NoMatch; 753 754 Parser.Lex(); // Eat identifier token. 755 Operands.push_back(ARMOperand::CreateCoprocNum(Num, S)); 756 return MatchOperand_Success; 757} 758 759/// tryParseCoprocRegOperand - Try to parse an coprocessor register operand. The 760/// token must be an Identifier when called, and if it is a coprocessor 761/// number, the token is eaten and the operand is added to the operand list. 762ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 763tryParseCoprocRegOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 764 SMLoc S = Parser.getTok().getLoc(); 765 const AsmToken &Tok = Parser.getTok(); 766 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 767 768 int Reg = MatchCoprocessorOperandName(Tok.getString(), 'c'); 769 if (Reg == -1) 770 return MatchOperand_NoMatch; 771 772 Parser.Lex(); // Eat identifier token. 773 Operands.push_back(ARMOperand::CreateCoprocReg(Reg, S)); 774 return MatchOperand_Success; 775} 776 777/// Parse a register list, return it if successful else return null. The first 778/// token must be a '{' when called. 779bool ARMAsmParser:: 780ParseRegisterList(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 781 assert(Parser.getTok().is(AsmToken::LCurly) && 782 "Token is not a Left Curly Brace"); 783 SMLoc S = Parser.getTok().getLoc(); 784 785 // Read the rest of the registers in the list. 786 unsigned PrevRegNum = 0; 787 SmallVector<std::pair<unsigned, SMLoc>, 32> Registers; 788 789 do { 790 bool IsRange = Parser.getTok().is(AsmToken::Minus); 791 Parser.Lex(); // Eat non-identifier token. 792 793 const AsmToken &RegTok = Parser.getTok(); 794 SMLoc RegLoc = RegTok.getLoc(); 795 if (RegTok.isNot(AsmToken::Identifier)) { 796 Error(RegLoc, "register expected"); 797 return true; 798 } 799 800 int RegNum = TryParseRegister(); 801 if (RegNum == -1) { 802 Error(RegLoc, "register expected"); 803 return true; 804 } 805 806 if (IsRange) { 807 int Reg = PrevRegNum; 808 do { 809 ++Reg; 810 Registers.push_back(std::make_pair(Reg, RegLoc)); 811 } while (Reg != RegNum); 812 } else { 813 Registers.push_back(std::make_pair(RegNum, RegLoc)); 814 } 815 816 PrevRegNum = RegNum; 817 } while (Parser.getTok().is(AsmToken::Comma) || 818 Parser.getTok().is(AsmToken::Minus)); 819 820 // Process the right curly brace of the list. 821 const AsmToken &RCurlyTok = Parser.getTok(); 822 if (RCurlyTok.isNot(AsmToken::RCurly)) { 823 Error(RCurlyTok.getLoc(), "'}' expected"); 824 return true; 825 } 826 827 SMLoc E = RCurlyTok.getLoc(); 828 Parser.Lex(); // Eat right curly brace token. 829 830 // Verify the register list. 831 SmallVectorImpl<std::pair<unsigned, SMLoc> >::const_iterator 832 RI = Registers.begin(), RE = Registers.end(); 833 834 unsigned HighRegNum = getARMRegisterNumbering(RI->first); 835 bool EmittedWarning = false; 836 837 DenseMap<unsigned, bool> RegMap; 838 RegMap[HighRegNum] = true; 839 840 for (++RI; RI != RE; ++RI) { 841 const std::pair<unsigned, SMLoc> &RegInfo = *RI; 842 unsigned Reg = getARMRegisterNumbering(RegInfo.first); 843 844 if (RegMap[Reg]) { 845 Error(RegInfo.second, "register duplicated in register list"); 846 return true; 847 } 848 849 if (!EmittedWarning && Reg < HighRegNum) 850 Warning(RegInfo.second, 851 "register not in ascending order in register list"); 852 853 RegMap[Reg] = true; 854 HighRegNum = std::max(Reg, HighRegNum); 855 } 856 857 Operands.push_back(ARMOperand::CreateRegList(Registers, S, E)); 858 return false; 859} 860 861/// tryParseMemBarrierOptOperand - Try to parse DSB/DMB data barrier options. 862ARMAsmParser::OperandMatchResultTy ARMAsmParser:: 863tryParseMemBarrierOptOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 864 SMLoc S = Parser.getTok().getLoc(); 865 const AsmToken &Tok = Parser.getTok(); 866 assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier"); 867 StringRef OptStr = Tok.getString(); 868 869 unsigned Opt = StringSwitch<unsigned>(OptStr.slice(0, OptStr.size())) 870 .Case("sy", ARM_MB::SY) 871 .Case("st", ARM_MB::ST) 872 .Case("ish", ARM_MB::ISH) 873 .Case("ishst", ARM_MB::ISHST) 874 .Case("nsh", ARM_MB::NSH) 875 .Case("nshst", ARM_MB::NSHST) 876 .Case("osh", ARM_MB::OSH) 877 .Case("oshst", ARM_MB::OSHST) 878 .Default(~0U); 879 880 if (Opt == ~0U) 881 return MatchOperand_NoMatch; 882 883 Parser.Lex(); // Eat identifier token. 884 Operands.push_back(ARMOperand::CreateMemBarrierOpt((ARM_MB::MemBOpt)Opt, S)); 885 return MatchOperand_Success; 886} 887 888/// Parse an ARM memory expression, return false if successful else return true 889/// or an error. The first token must be a '[' when called. 890/// 891/// TODO Only preindexing and postindexing addressing are started, unindexed 892/// with option, etc are still to do. 893bool ARMAsmParser:: 894ParseMemory(SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 895 SMLoc S, E; 896 assert(Parser.getTok().is(AsmToken::LBrac) && 897 "Token is not a Left Bracket"); 898 S = Parser.getTok().getLoc(); 899 Parser.Lex(); // Eat left bracket token. 900 901 const AsmToken &BaseRegTok = Parser.getTok(); 902 if (BaseRegTok.isNot(AsmToken::Identifier)) { 903 Error(BaseRegTok.getLoc(), "register expected"); 904 return true; 905 } 906 int BaseRegNum = TryParseRegister(); 907 if (BaseRegNum == -1) { 908 Error(BaseRegTok.getLoc(), "register expected"); 909 return true; 910 } 911 912 // The next token must either be a comma or a closing bracket. 913 const AsmToken &Tok = Parser.getTok(); 914 if (!Tok.is(AsmToken::Comma) && !Tok.is(AsmToken::RBrac)) 915 return true; 916 917 bool Preindexed = false; 918 bool Postindexed = false; 919 bool OffsetIsReg = false; 920 bool Negative = false; 921 bool Writeback = false; 922 ARMOperand *WBOp = 0; 923 int OffsetRegNum = -1; 924 bool OffsetRegShifted = false; 925 enum ShiftType ShiftType = Lsl; 926 const MCExpr *ShiftAmount = 0; 927 const MCExpr *Offset = 0; 928 929 // First look for preindexed address forms, that is after the "[Rn" we now 930 // have to see if the next token is a comma. 931 if (Tok.is(AsmToken::Comma)) { 932 Preindexed = true; 933 Parser.Lex(); // Eat comma token. 934 935 if (ParseMemoryOffsetReg(Negative, OffsetRegShifted, ShiftType, ShiftAmount, 936 Offset, OffsetIsReg, OffsetRegNum, E)) 937 return true; 938 const AsmToken &RBracTok = Parser.getTok(); 939 if (RBracTok.isNot(AsmToken::RBrac)) { 940 Error(RBracTok.getLoc(), "']' expected"); 941 return true; 942 } 943 E = RBracTok.getLoc(); 944 Parser.Lex(); // Eat right bracket token. 945 946 const AsmToken &ExclaimTok = Parser.getTok(); 947 if (ExclaimTok.is(AsmToken::Exclaim)) { 948 WBOp = ARMOperand::CreateToken(ExclaimTok.getString(), 949 ExclaimTok.getLoc()); 950 Writeback = true; 951 Parser.Lex(); // Eat exclaim token 952 } 953 } else { 954 // The "[Rn" we have so far was not followed by a comma. 955 956 // If there's anything other than the right brace, this is a post indexing 957 // addressing form. 958 E = Tok.getLoc(); 959 Parser.Lex(); // Eat right bracket token. 960 961 const AsmToken &NextTok = Parser.getTok(); 962 963 if (NextTok.isNot(AsmToken::EndOfStatement)) { 964 Postindexed = true; 965 Writeback = true; 966 967 if (NextTok.isNot(AsmToken::Comma)) { 968 Error(NextTok.getLoc(), "',' expected"); 969 return true; 970 } 971 972 Parser.Lex(); // Eat comma token. 973 974 if (ParseMemoryOffsetReg(Negative, OffsetRegShifted, ShiftType, 975 ShiftAmount, Offset, OffsetIsReg, OffsetRegNum, 976 E)) 977 return true; 978 } 979 } 980 981 // Force Offset to exist if used. 982 if (!OffsetIsReg) { 983 if (!Offset) 984 Offset = MCConstantExpr::Create(0, getContext()); 985 } 986 987 Operands.push_back(ARMOperand::CreateMem(BaseRegNum, OffsetIsReg, Offset, 988 OffsetRegNum, OffsetRegShifted, 989 ShiftType, ShiftAmount, Preindexed, 990 Postindexed, Negative, Writeback, 991 S, E)); 992 if (WBOp) 993 Operands.push_back(WBOp); 994 995 return false; 996} 997 998/// Parse the offset of a memory operand after we have seen "[Rn," or "[Rn]," 999/// we will parse the following (were +/- means that a plus or minus is 1000/// optional): 1001/// +/-Rm 1002/// +/-Rm, shift 1003/// #offset 1004/// we return false on success or an error otherwise. 1005bool ARMAsmParser::ParseMemoryOffsetReg(bool &Negative, 1006 bool &OffsetRegShifted, 1007 enum ShiftType &ShiftType, 1008 const MCExpr *&ShiftAmount, 1009 const MCExpr *&Offset, 1010 bool &OffsetIsReg, 1011 int &OffsetRegNum, 1012 SMLoc &E) { 1013 Negative = false; 1014 OffsetRegShifted = false; 1015 OffsetIsReg = false; 1016 OffsetRegNum = -1; 1017 const AsmToken &NextTok = Parser.getTok(); 1018 E = NextTok.getLoc(); 1019 if (NextTok.is(AsmToken::Plus)) 1020 Parser.Lex(); // Eat plus token. 1021 else if (NextTok.is(AsmToken::Minus)) { 1022 Negative = true; 1023 Parser.Lex(); // Eat minus token 1024 } 1025 // See if there is a register following the "[Rn," or "[Rn]," we have so far. 1026 const AsmToken &OffsetRegTok = Parser.getTok(); 1027 if (OffsetRegTok.is(AsmToken::Identifier)) { 1028 SMLoc CurLoc = OffsetRegTok.getLoc(); 1029 OffsetRegNum = TryParseRegister(); 1030 if (OffsetRegNum != -1) { 1031 OffsetIsReg = true; 1032 E = CurLoc; 1033 } 1034 } 1035 1036 // If we parsed a register as the offset then there can be a shift after that. 1037 if (OffsetRegNum != -1) { 1038 // Look for a comma then a shift 1039 const AsmToken &Tok = Parser.getTok(); 1040 if (Tok.is(AsmToken::Comma)) { 1041 Parser.Lex(); // Eat comma token. 1042 1043 const AsmToken &Tok = Parser.getTok(); 1044 if (ParseShift(ShiftType, ShiftAmount, E)) 1045 return Error(Tok.getLoc(), "shift expected"); 1046 OffsetRegShifted = true; 1047 } 1048 } 1049 else { // the "[Rn," or "[Rn,]" we have so far was not followed by "Rm" 1050 // Look for #offset following the "[Rn," or "[Rn]," 1051 const AsmToken &HashTok = Parser.getTok(); 1052 if (HashTok.isNot(AsmToken::Hash)) 1053 return Error(HashTok.getLoc(), "'#' expected"); 1054 1055 Parser.Lex(); // Eat hash token. 1056 1057 if (getParser().ParseExpression(Offset)) 1058 return true; 1059 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 1060 } 1061 return false; 1062} 1063 1064/// ParseShift as one of these two: 1065/// ( lsl | lsr | asr | ror ) , # shift_amount 1066/// rrx 1067/// and returns true if it parses a shift otherwise it returns false. 1068bool ARMAsmParser::ParseShift(ShiftType &St, const MCExpr *&ShiftAmount, 1069 SMLoc &E) { 1070 const AsmToken &Tok = Parser.getTok(); 1071 if (Tok.isNot(AsmToken::Identifier)) 1072 return true; 1073 StringRef ShiftName = Tok.getString(); 1074 if (ShiftName == "lsl" || ShiftName == "LSL") 1075 St = Lsl; 1076 else if (ShiftName == "lsr" || ShiftName == "LSR") 1077 St = Lsr; 1078 else if (ShiftName == "asr" || ShiftName == "ASR") 1079 St = Asr; 1080 else if (ShiftName == "ror" || ShiftName == "ROR") 1081 St = Ror; 1082 else if (ShiftName == "rrx" || ShiftName == "RRX") 1083 St = Rrx; 1084 else 1085 return true; 1086 Parser.Lex(); // Eat shift type token. 1087 1088 // Rrx stands alone. 1089 if (St == Rrx) 1090 return false; 1091 1092 // Otherwise, there must be a '#' and a shift amount. 1093 const AsmToken &HashTok = Parser.getTok(); 1094 if (HashTok.isNot(AsmToken::Hash)) 1095 return Error(HashTok.getLoc(), "'#' expected"); 1096 Parser.Lex(); // Eat hash token. 1097 1098 if (getParser().ParseExpression(ShiftAmount)) 1099 return true; 1100 1101 return false; 1102} 1103 1104/// Parse a arm instruction operand. For now this parses the operand regardless 1105/// of the mnemonic. 1106bool ARMAsmParser::ParseOperand(SmallVectorImpl<MCParsedAsmOperand*> &Operands, 1107 StringRef Mnemonic) { 1108 SMLoc S, E; 1109 1110 // Check if the current operand has a custom associated parser, if so, try to 1111 // custom parse the operand, or fallback to the general approach. 1112 OperandMatchResultTy ResTy = MatchOperandParserImpl(Operands, Mnemonic); 1113 if (ResTy == MatchOperand_Success) 1114 return false; 1115 // If there wasn't a custom match, try the generic matcher below. Otherwise, 1116 // there was a match, but an error occurred, in which case, just return that 1117 // the operand parsing failed. 1118 if (ResTy == MatchOperand_ParseFail) 1119 return true; 1120 1121 switch (getLexer().getKind()) { 1122 default: 1123 Error(Parser.getTok().getLoc(), "unexpected token in operand"); 1124 return true; 1125 case AsmToken::Identifier: 1126 if (!TryParseRegisterWithWriteBack(Operands)) 1127 return false; 1128 1129 // Fall though for the Identifier case that is not a register or a 1130 // special name. 1131 case AsmToken::Integer: // things like 1f and 2b as a branch targets 1132 case AsmToken::Dot: { // . as a branch target 1133 // This was not a register so parse other operands that start with an 1134 // identifier (like labels) as expressions and create them as immediates. 1135 const MCExpr *IdVal; 1136 S = Parser.getTok().getLoc(); 1137 if (getParser().ParseExpression(IdVal)) 1138 return true; 1139 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 1140 Operands.push_back(ARMOperand::CreateImm(IdVal, S, E)); 1141 return false; 1142 } 1143 case AsmToken::LBrac: 1144 return ParseMemory(Operands); 1145 case AsmToken::LCurly: 1146 return ParseRegisterList(Operands); 1147 case AsmToken::Hash: 1148 // #42 -> immediate. 1149 // TODO: ":lower16:" and ":upper16:" modifiers after # before immediate 1150 S = Parser.getTok().getLoc(); 1151 Parser.Lex(); 1152 const MCExpr *ImmVal; 1153 if (getParser().ParseExpression(ImmVal)) 1154 return true; 1155 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 1156 Operands.push_back(ARMOperand::CreateImm(ImmVal, S, E)); 1157 return false; 1158 case AsmToken::Colon: { 1159 // ":lower16:" and ":upper16:" expression prefixes 1160 // FIXME: Check it's an expression prefix, 1161 // e.g. (FOO - :lower16:BAR) isn't legal. 1162 ARMMCExpr::VariantKind RefKind; 1163 if (ParsePrefix(RefKind)) 1164 return true; 1165 1166 const MCExpr *SubExprVal; 1167 if (getParser().ParseExpression(SubExprVal)) 1168 return true; 1169 1170 const MCExpr *ExprVal = ARMMCExpr::Create(RefKind, SubExprVal, 1171 getContext()); 1172 E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 1173 Operands.push_back(ARMOperand::CreateImm(ExprVal, S, E)); 1174 return false; 1175 } 1176 } 1177} 1178 1179// ParsePrefix - Parse ARM 16-bit relocations expression prefix, i.e. 1180// :lower16: and :upper16:. 1181bool ARMAsmParser::ParsePrefix(ARMMCExpr::VariantKind &RefKind) { 1182 RefKind = ARMMCExpr::VK_ARM_None; 1183 1184 // :lower16: and :upper16: modifiers 1185 assert(getLexer().is(AsmToken::Colon) && "expected a :"); 1186 Parser.Lex(); // Eat ':' 1187 1188 if (getLexer().isNot(AsmToken::Identifier)) { 1189 Error(Parser.getTok().getLoc(), "expected prefix identifier in operand"); 1190 return true; 1191 } 1192 1193 StringRef IDVal = Parser.getTok().getIdentifier(); 1194 if (IDVal == "lower16") { 1195 RefKind = ARMMCExpr::VK_ARM_LO16; 1196 } else if (IDVal == "upper16") { 1197 RefKind = ARMMCExpr::VK_ARM_HI16; 1198 } else { 1199 Error(Parser.getTok().getLoc(), "unexpected prefix in operand"); 1200 return true; 1201 } 1202 Parser.Lex(); 1203 1204 if (getLexer().isNot(AsmToken::Colon)) { 1205 Error(Parser.getTok().getLoc(), "unexpected token after prefix"); 1206 return true; 1207 } 1208 Parser.Lex(); // Eat the last ':' 1209 return false; 1210} 1211 1212const MCExpr * 1213ARMAsmParser::ApplyPrefixToExpr(const MCExpr *E, 1214 MCSymbolRefExpr::VariantKind Variant) { 1215 // Recurse over the given expression, rebuilding it to apply the given variant 1216 // to the leftmost symbol. 1217 if (Variant == MCSymbolRefExpr::VK_None) 1218 return E; 1219 1220 switch (E->getKind()) { 1221 case MCExpr::Target: 1222 llvm_unreachable("Can't handle target expr yet"); 1223 case MCExpr::Constant: 1224 llvm_unreachable("Can't handle lower16/upper16 of constant yet"); 1225 1226 case MCExpr::SymbolRef: { 1227 const MCSymbolRefExpr *SRE = cast<MCSymbolRefExpr>(E); 1228 1229 if (SRE->getKind() != MCSymbolRefExpr::VK_None) 1230 return 0; 1231 1232 return MCSymbolRefExpr::Create(&SRE->getSymbol(), Variant, getContext()); 1233 } 1234 1235 case MCExpr::Unary: 1236 llvm_unreachable("Can't handle unary expressions yet"); 1237 1238 case MCExpr::Binary: { 1239 const MCBinaryExpr *BE = cast<MCBinaryExpr>(E); 1240 const MCExpr *LHS = ApplyPrefixToExpr(BE->getLHS(), Variant); 1241 const MCExpr *RHS = BE->getRHS(); 1242 if (!LHS) 1243 return 0; 1244 1245 return MCBinaryExpr::Create(BE->getOpcode(), LHS, RHS, getContext()); 1246 } 1247 } 1248 1249 assert(0 && "Invalid expression kind!"); 1250 return 0; 1251} 1252 1253/// \brief Given a mnemonic, split out possible predication code and carry 1254/// setting letters to form a canonical mnemonic and flags. 1255// 1256// FIXME: Would be nice to autogen this. 1257static StringRef SplitMnemonicAndCC(StringRef Mnemonic, 1258 unsigned &PredicationCode, 1259 bool &CarrySetting) { 1260 PredicationCode = ARMCC::AL; 1261 CarrySetting = false; 1262 1263 // Ignore some mnemonics we know aren't predicated forms. 1264 // 1265 // FIXME: Would be nice to autogen this. 1266 if (Mnemonic == "teq" || Mnemonic == "vceq" || 1267 Mnemonic == "movs" || 1268 Mnemonic == "svc" || 1269 (Mnemonic == "mls" || Mnemonic == "smmls" || Mnemonic == "vcls" || 1270 Mnemonic == "vmls" || Mnemonic == "vnmls") || 1271 Mnemonic == "vacge" || Mnemonic == "vcge" || 1272 Mnemonic == "vclt" || 1273 Mnemonic == "vacgt" || Mnemonic == "vcgt" || 1274 Mnemonic == "vcle" || 1275 (Mnemonic == "smlal" || Mnemonic == "umaal" || Mnemonic == "umlal" || 1276 Mnemonic == "vabal" || Mnemonic == "vmlal" || Mnemonic == "vpadal" || 1277 Mnemonic == "vqdmlal")) 1278 return Mnemonic; 1279 1280 // First, split out any predication code. 1281 unsigned CC = StringSwitch<unsigned>(Mnemonic.substr(Mnemonic.size()-2)) 1282 .Case("eq", ARMCC::EQ) 1283 .Case("ne", ARMCC::NE) 1284 .Case("hs", ARMCC::HS) 1285 .Case("lo", ARMCC::LO) 1286 .Case("mi", ARMCC::MI) 1287 .Case("pl", ARMCC::PL) 1288 .Case("vs", ARMCC::VS) 1289 .Case("vc", ARMCC::VC) 1290 .Case("hi", ARMCC::HI) 1291 .Case("ls", ARMCC::LS) 1292 .Case("ge", ARMCC::GE) 1293 .Case("lt", ARMCC::LT) 1294 .Case("gt", ARMCC::GT) 1295 .Case("le", ARMCC::LE) 1296 .Case("al", ARMCC::AL) 1297 .Default(~0U); 1298 if (CC != ~0U) { 1299 Mnemonic = Mnemonic.slice(0, Mnemonic.size() - 2); 1300 PredicationCode = CC; 1301 } 1302 1303 // Next, determine if we have a carry setting bit. We explicitly ignore all 1304 // the instructions we know end in 's'. 1305 if (Mnemonic.endswith("s") && 1306 !(Mnemonic == "asrs" || Mnemonic == "cps" || Mnemonic == "mls" || 1307 Mnemonic == "movs" || Mnemonic == "mrs" || Mnemonic == "smmls" || 1308 Mnemonic == "vabs" || Mnemonic == "vcls" || Mnemonic == "vmls" || 1309 Mnemonic == "vmrs" || Mnemonic == "vnmls" || Mnemonic == "vqabs" || 1310 Mnemonic == "vrecps" || Mnemonic == "vrsqrts")) { 1311 Mnemonic = Mnemonic.slice(0, Mnemonic.size() - 1); 1312 CarrySetting = true; 1313 } 1314 1315 return Mnemonic; 1316} 1317 1318/// \brief Given a canonical mnemonic, determine if the instruction ever allows 1319/// inclusion of carry set or predication code operands. 1320// 1321// FIXME: It would be nice to autogen this. 1322void ARMAsmParser:: 1323GetMnemonicAcceptInfo(StringRef Mnemonic, bool &CanAcceptCarrySet, 1324 bool &CanAcceptPredicationCode) { 1325 bool isThumb = TM.getSubtarget<ARMSubtarget>().isThumb(); 1326 1327 if (Mnemonic == "and" || Mnemonic == "lsl" || Mnemonic == "lsr" || 1328 Mnemonic == "rrx" || Mnemonic == "ror" || Mnemonic == "sub" || 1329 Mnemonic == "smull" || Mnemonic == "add" || Mnemonic == "adc" || 1330 Mnemonic == "mul" || Mnemonic == "bic" || Mnemonic == "asr" || 1331 Mnemonic == "umlal" || Mnemonic == "orr" || Mnemonic == "mov" || 1332 Mnemonic == "rsb" || Mnemonic == "rsc" || Mnemonic == "orn" || 1333 Mnemonic == "sbc" || Mnemonic == "mla" || Mnemonic == "umull" || 1334 Mnemonic == "eor" || Mnemonic == "smlal" || Mnemonic == "mvn") { 1335 CanAcceptCarrySet = true; 1336 } else { 1337 CanAcceptCarrySet = false; 1338 } 1339 1340 if (Mnemonic == "cbnz" || Mnemonic == "setend" || Mnemonic == "dmb" || 1341 Mnemonic == "cps" || Mnemonic == "mcr2" || Mnemonic == "it" || 1342 Mnemonic == "mcrr2" || Mnemonic == "cbz" || Mnemonic == "cdp2" || 1343 Mnemonic == "trap" || Mnemonic == "mrc2" || Mnemonic == "mrrc2" || 1344 Mnemonic == "dsb" || Mnemonic == "movs" || Mnemonic == "isb" || 1345 Mnemonic == "clrex") { 1346 CanAcceptPredicationCode = false; 1347 } else { 1348 CanAcceptPredicationCode = true; 1349 } 1350 1351 if (isThumb) 1352 if (Mnemonic == "bkpt" || Mnemonic == "mcr" || Mnemonic == "mcrr" || 1353 Mnemonic == "mrc" || Mnemonic == "mrrc" || Mnemonic == "cdp") 1354 CanAcceptPredicationCode = false; 1355} 1356 1357/// Parse an arm instruction mnemonic followed by its operands. 1358bool ARMAsmParser::ParseInstruction(StringRef Name, SMLoc NameLoc, 1359 SmallVectorImpl<MCParsedAsmOperand*> &Operands) { 1360 // Create the leading tokens for the mnemonic, split by '.' characters. 1361 size_t Start = 0, Next = Name.find('.'); 1362 StringRef Head = Name.slice(Start, Next); 1363 1364 // Split out the predication code and carry setting flag from the mnemonic. 1365 unsigned PredicationCode; 1366 bool CarrySetting; 1367 Head = SplitMnemonicAndCC(Head, PredicationCode, CarrySetting); 1368 1369 Operands.push_back(ARMOperand::CreateToken(Head, NameLoc)); 1370 1371 // Next, add the CCOut and ConditionCode operands, if needed. 1372 // 1373 // For mnemonics which can ever incorporate a carry setting bit or predication 1374 // code, our matching model involves us always generating CCOut and 1375 // ConditionCode operands to match the mnemonic "as written" and then we let 1376 // the matcher deal with finding the right instruction or generating an 1377 // appropriate error. 1378 bool CanAcceptCarrySet, CanAcceptPredicationCode; 1379 GetMnemonicAcceptInfo(Head, CanAcceptCarrySet, CanAcceptPredicationCode); 1380 1381 // Add the carry setting operand, if necessary. 1382 // 1383 // FIXME: It would be awesome if we could somehow invent a location such that 1384 // match errors on this operand would print a nice diagnostic about how the 1385 // 's' character in the mnemonic resulted in a CCOut operand. 1386 if (CanAcceptCarrySet) { 1387 Operands.push_back(ARMOperand::CreateCCOut(CarrySetting ? ARM::CPSR : 0, 1388 NameLoc)); 1389 } else { 1390 // This mnemonic can't ever accept a carry set, but the user wrote one (or 1391 // misspelled another mnemonic). 1392 1393 // FIXME: Issue a nice error. 1394 } 1395 1396 // Add the predication code operand, if necessary. 1397 if (CanAcceptPredicationCode) { 1398 Operands.push_back(ARMOperand::CreateCondCode( 1399 ARMCC::CondCodes(PredicationCode), NameLoc)); 1400 } else { 1401 // This mnemonic can't ever accept a predication code, but the user wrote 1402 // one (or misspelled another mnemonic). 1403 1404 // FIXME: Issue a nice error. 1405 } 1406 1407 // Add the remaining tokens in the mnemonic. 1408 while (Next != StringRef::npos) { 1409 Start = Next; 1410 Next = Name.find('.', Start + 1); 1411 Head = Name.slice(Start, Next); 1412 1413 Operands.push_back(ARMOperand::CreateToken(Head, NameLoc)); 1414 } 1415 1416 // Read the remaining operands. 1417 if (getLexer().isNot(AsmToken::EndOfStatement)) { 1418 // Read the first operand. 1419 if (ParseOperand(Operands, Head)) { 1420 Parser.EatToEndOfStatement(); 1421 return true; 1422 } 1423 1424 while (getLexer().is(AsmToken::Comma)) { 1425 Parser.Lex(); // Eat the comma. 1426 1427 // Parse and remember the operand. 1428 if (ParseOperand(Operands, Head)) { 1429 Parser.EatToEndOfStatement(); 1430 return true; 1431 } 1432 } 1433 } 1434 1435 if (getLexer().isNot(AsmToken::EndOfStatement)) { 1436 Parser.EatToEndOfStatement(); 1437 return TokError("unexpected token in argument list"); 1438 } 1439 1440 Parser.Lex(); // Consume the EndOfStatement 1441 return false; 1442} 1443 1444bool ARMAsmParser:: 1445MatchAndEmitInstruction(SMLoc IDLoc, 1446 SmallVectorImpl<MCParsedAsmOperand*> &Operands, 1447 MCStreamer &Out) { 1448 MCInst Inst; 1449 unsigned ErrorInfo; 1450 MatchResultTy MatchResult, MatchResult2; 1451 MatchResult = MatchInstructionImpl(Operands, Inst, ErrorInfo); 1452 if (MatchResult != Match_Success) { 1453 // If we get a Match_InvalidOperand it might be some arithmetic instruction 1454 // that does not update the condition codes. So try adding a CCOut operand 1455 // with a value of reg0. 1456 if (MatchResult == Match_InvalidOperand) { 1457 Operands.insert(Operands.begin() + 1, 1458 ARMOperand::CreateCCOut(0, 1459 ((ARMOperand*)Operands[0])->getStartLoc())); 1460 MatchResult2 = MatchInstructionImpl(Operands, Inst, ErrorInfo); 1461 if (MatchResult2 == Match_Success) 1462 MatchResult = Match_Success; 1463 else { 1464 ARMOperand *CCOut = ((ARMOperand*)Operands[1]); 1465 Operands.erase(Operands.begin() + 1); 1466 delete CCOut; 1467 } 1468 } 1469 // If we get a Match_MnemonicFail it might be some arithmetic instruction 1470 // that updates the condition codes if it ends in 's'. So see if the 1471 // mnemonic ends in 's' and if so try removing the 's' and adding a CCOut 1472 // operand with a value of CPSR. 1473 else if(MatchResult == Match_MnemonicFail) { 1474 // Get the instruction mnemonic, which is the first token. 1475 StringRef Mnemonic = ((ARMOperand*)Operands[0])->getToken(); 1476 if (Mnemonic.substr(Mnemonic.size()-1) == "s") { 1477 // removed the 's' from the mnemonic for matching. 1478 StringRef MnemonicNoS = Mnemonic.slice(0, Mnemonic.size() - 1); 1479 SMLoc NameLoc = ((ARMOperand*)Operands[0])->getStartLoc(); 1480 ARMOperand *OldMnemonic = ((ARMOperand*)Operands[0]); 1481 Operands.erase(Operands.begin()); 1482 delete OldMnemonic; 1483 Operands.insert(Operands.begin(), 1484 ARMOperand::CreateToken(MnemonicNoS, NameLoc)); 1485 Operands.insert(Operands.begin() + 1, 1486 ARMOperand::CreateCCOut(ARM::CPSR, NameLoc)); 1487 MatchResult2 = MatchInstructionImpl(Operands, Inst, ErrorInfo); 1488 if (MatchResult2 == Match_Success) 1489 MatchResult = Match_Success; 1490 else { 1491 ARMOperand *OldMnemonic = ((ARMOperand*)Operands[0]); 1492 Operands.erase(Operands.begin()); 1493 delete OldMnemonic; 1494 Operands.insert(Operands.begin(), 1495 ARMOperand::CreateToken(Mnemonic, NameLoc)); 1496 ARMOperand *CCOut = ((ARMOperand*)Operands[1]); 1497 Operands.erase(Operands.begin() + 1); 1498 delete CCOut; 1499 } 1500 } 1501 } 1502 } 1503 switch (MatchResult) { 1504 case Match_Success: 1505 Out.EmitInstruction(Inst); 1506 return false; 1507 case Match_MissingFeature: 1508 Error(IDLoc, "instruction requires a CPU feature not currently enabled"); 1509 return true; 1510 case Match_InvalidOperand: { 1511 SMLoc ErrorLoc = IDLoc; 1512 if (ErrorInfo != ~0U) { 1513 if (ErrorInfo >= Operands.size()) 1514 return Error(IDLoc, "too few operands for instruction"); 1515 1516 ErrorLoc = ((ARMOperand*)Operands[ErrorInfo])->getStartLoc(); 1517 if (ErrorLoc == SMLoc()) ErrorLoc = IDLoc; 1518 } 1519 1520 return Error(ErrorLoc, "invalid operand for instruction"); 1521 } 1522 case Match_MnemonicFail: 1523 return Error(IDLoc, "unrecognized instruction mnemonic"); 1524 case Match_ConversionFail: 1525 return Error(IDLoc, "unable to convert operands to instruction"); 1526 } 1527 1528 llvm_unreachable("Implement any new match types added!"); 1529 return true; 1530} 1531 1532/// ParseDirective parses the arm specific directives 1533bool ARMAsmParser::ParseDirective(AsmToken DirectiveID) { 1534 StringRef IDVal = DirectiveID.getIdentifier(); 1535 if (IDVal == ".word") 1536 return ParseDirectiveWord(4, DirectiveID.getLoc()); 1537 else if (IDVal == ".thumb") 1538 return ParseDirectiveThumb(DirectiveID.getLoc()); 1539 else if (IDVal == ".thumb_func") 1540 return ParseDirectiveThumbFunc(DirectiveID.getLoc()); 1541 else if (IDVal == ".code") 1542 return ParseDirectiveCode(DirectiveID.getLoc()); 1543 else if (IDVal == ".syntax") 1544 return ParseDirectiveSyntax(DirectiveID.getLoc()); 1545 return true; 1546} 1547 1548/// ParseDirectiveWord 1549/// ::= .word [ expression (, expression)* ] 1550bool ARMAsmParser::ParseDirectiveWord(unsigned Size, SMLoc L) { 1551 if (getLexer().isNot(AsmToken::EndOfStatement)) { 1552 for (;;) { 1553 const MCExpr *Value; 1554 if (getParser().ParseExpression(Value)) 1555 return true; 1556 1557 getParser().getStreamer().EmitValue(Value, Size, 0/*addrspace*/); 1558 1559 if (getLexer().is(AsmToken::EndOfStatement)) 1560 break; 1561 1562 // FIXME: Improve diagnostic. 1563 if (getLexer().isNot(AsmToken::Comma)) 1564 return Error(L, "unexpected token in directive"); 1565 Parser.Lex(); 1566 } 1567 } 1568 1569 Parser.Lex(); 1570 return false; 1571} 1572 1573/// ParseDirectiveThumb 1574/// ::= .thumb 1575bool ARMAsmParser::ParseDirectiveThumb(SMLoc L) { 1576 if (getLexer().isNot(AsmToken::EndOfStatement)) 1577 return Error(L, "unexpected token in directive"); 1578 Parser.Lex(); 1579 1580 // TODO: set thumb mode 1581 // TODO: tell the MC streamer the mode 1582 // getParser().getStreamer().Emit???(); 1583 return false; 1584} 1585 1586/// ParseDirectiveThumbFunc 1587/// ::= .thumbfunc symbol_name 1588bool ARMAsmParser::ParseDirectiveThumbFunc(SMLoc L) { 1589 const AsmToken &Tok = Parser.getTok(); 1590 if (Tok.isNot(AsmToken::Identifier) && Tok.isNot(AsmToken::String)) 1591 return Error(L, "unexpected token in .thumb_func directive"); 1592 StringRef Name = Tok.getString(); 1593 Parser.Lex(); // Consume the identifier token. 1594 if (getLexer().isNot(AsmToken::EndOfStatement)) 1595 return Error(L, "unexpected token in directive"); 1596 Parser.Lex(); 1597 1598 // Mark symbol as a thumb symbol. 1599 MCSymbol *Func = getParser().getContext().GetOrCreateSymbol(Name); 1600 getParser().getStreamer().EmitThumbFunc(Func); 1601 return false; 1602} 1603 1604/// ParseDirectiveSyntax 1605/// ::= .syntax unified | divided 1606bool ARMAsmParser::ParseDirectiveSyntax(SMLoc L) { 1607 const AsmToken &Tok = Parser.getTok(); 1608 if (Tok.isNot(AsmToken::Identifier)) 1609 return Error(L, "unexpected token in .syntax directive"); 1610 StringRef Mode = Tok.getString(); 1611 if (Mode == "unified" || Mode == "UNIFIED") 1612 Parser.Lex(); 1613 else if (Mode == "divided" || Mode == "DIVIDED") 1614 return Error(L, "'.syntax divided' arm asssembly not supported"); 1615 else 1616 return Error(L, "unrecognized syntax mode in .syntax directive"); 1617 1618 if (getLexer().isNot(AsmToken::EndOfStatement)) 1619 return Error(Parser.getTok().getLoc(), "unexpected token in directive"); 1620 Parser.Lex(); 1621 1622 // TODO tell the MC streamer the mode 1623 // getParser().getStreamer().Emit???(); 1624 return false; 1625} 1626 1627/// ParseDirectiveCode 1628/// ::= .code 16 | 32 1629bool ARMAsmParser::ParseDirectiveCode(SMLoc L) { 1630 const AsmToken &Tok = Parser.getTok(); 1631 if (Tok.isNot(AsmToken::Integer)) 1632 return Error(L, "unexpected token in .code directive"); 1633 int64_t Val = Parser.getTok().getIntVal(); 1634 if (Val == 16) 1635 Parser.Lex(); 1636 else if (Val == 32) 1637 Parser.Lex(); 1638 else 1639 return Error(L, "invalid operand to .code directive"); 1640 1641 if (getLexer().isNot(AsmToken::EndOfStatement)) 1642 return Error(Parser.getTok().getLoc(), "unexpected token in directive"); 1643 Parser.Lex(); 1644 1645 // FIXME: We need to be able switch subtargets at this point so that 1646 // MatchInstructionImpl() will work when it gets the AvailableFeatures which 1647 // includes Feature_IsThumb or not to match the right instructions. This is 1648 // blocked on the FIXME in llvm-mc.cpp when creating the TargetMachine. 1649 if (Val == 16){ 1650 assert(TM.getSubtarget<ARMSubtarget>().isThumb() && 1651 "switching between arm/thumb not yet suppported via .code 16)"); 1652 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code16); 1653 } 1654 else{ 1655 assert(!TM.getSubtarget<ARMSubtarget>().isThumb() && 1656 "switching between thumb/arm not yet suppported via .code 32)"); 1657 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code32); 1658 } 1659 1660 return false; 1661} 1662 1663extern "C" void LLVMInitializeARMAsmLexer(); 1664 1665/// Force static initialization. 1666extern "C" void LLVMInitializeARMAsmParser() { 1667 RegisterAsmParser<ARMAsmParser> X(TheARMTarget); 1668 RegisterAsmParser<ARMAsmParser> Y(TheThumbTarget); 1669 LLVMInitializeARMAsmLexer(); 1670} 1671 1672#define GET_REGISTER_MATCHER 1673#define GET_MATCHER_IMPLEMENTATION 1674#include "ARMGenAsmMatcher.inc" 1675