1 //===-- MipsAsmParser.cpp - Parse Mips 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/MipsABIInfo.h" 11 #include "MCTargetDesc/MipsMCExpr.h" 12 #include "MCTargetDesc/MipsMCTargetDesc.h" 13 #include "MipsRegisterInfo.h" 14 #include "MipsTargetStreamer.h" 15 #include "llvm/ADT/APInt.h" 16 #include "llvm/ADT/SmallVector.h" 17 #include "llvm/ADT/StringSwitch.h" 18 #include "llvm/MC/MCContext.h" 19 #include "llvm/MC/MCExpr.h" 20 #include "llvm/MC/MCInst.h" 21 #include "llvm/MC/MCInstBuilder.h" 22 #include "llvm/MC/MCParser/MCAsmLexer.h" 23 #include "llvm/MC/MCParser/MCParsedAsmOperand.h" 24 #include "llvm/MC/MCStreamer.h" 25 #include "llvm/MC/MCSubtargetInfo.h" 26 #include "llvm/MC/MCSymbol.h" 27 #include "llvm/MC/MCTargetAsmParser.h" 28 #include "llvm/Support/Debug.h" 29 #include "llvm/Support/MathExtras.h" 30 #include "llvm/Support/SourceMgr.h" 31 #include "llvm/Support/TargetRegistry.h" 32 #include <memory> 33 34 using namespace llvm; 35 36 #define DEBUG_TYPE "mips-asm-parser" 37 38 namespace llvm { 39 class MCInstrInfo; 40 } 41 42 namespace { 43 class MipsAssemblerOptions { 44 public: 45 MipsAssemblerOptions(uint64_t Features_) : 46 ATReg(1), Reorder(true), Macro(true), Features(Features_) {} 47 48 MipsAssemblerOptions(const MipsAssemblerOptions *Opts) { 49 ATReg = Opts->getATRegNum(); 50 Reorder = Opts->isReorder(); 51 Macro = Opts->isMacro(); 52 Features = Opts->getFeatures(); 53 } 54 55 unsigned getATRegNum() const { return ATReg; } 56 bool setATReg(unsigned Reg); 57 58 bool isReorder() const { return Reorder; } 59 void setReorder() { Reorder = true; } 60 void setNoReorder() { Reorder = false; } 61 62 bool isMacro() const { return Macro; } 63 void setMacro() { Macro = true; } 64 void setNoMacro() { Macro = false; } 65 66 uint64_t getFeatures() const { return Features; } 67 void setFeatures(uint64_t Features_) { Features = Features_; } 68 69 // Set of features that are either architecture features or referenced 70 // by them (e.g.: FeatureNaN2008 implied by FeatureMips32r6). 71 // The full table can be found in MipsGenSubtargetInfo.inc (MipsFeatureKV[]). 72 // The reason we need this mask is explained in the selectArch function. 73 // FIXME: Ideally we would like TableGen to generate this information. 74 static const uint64_t AllArchRelatedMask = 75 Mips::FeatureMips1 | Mips::FeatureMips2 | Mips::FeatureMips3 | 76 Mips::FeatureMips3_32 | Mips::FeatureMips3_32r2 | Mips::FeatureMips4 | 77 Mips::FeatureMips4_32 | Mips::FeatureMips4_32r2 | Mips::FeatureMips5 | 78 Mips::FeatureMips5_32r2 | Mips::FeatureMips32 | Mips::FeatureMips32r2 | 79 Mips::FeatureMips32r6 | Mips::FeatureMips64 | Mips::FeatureMips64r2 | 80 Mips::FeatureMips64r6 | Mips::FeatureCnMips | Mips::FeatureFP64Bit | 81 Mips::FeatureGP64Bit | Mips::FeatureNaN2008; 82 83 private: 84 unsigned ATReg; 85 bool Reorder; 86 bool Macro; 87 uint64_t Features; 88 }; 89 } 90 91 namespace { 92 class MipsAsmParser : public MCTargetAsmParser { 93 MipsTargetStreamer &getTargetStreamer() { 94 MCTargetStreamer &TS = *getParser().getStreamer().getTargetStreamer(); 95 return static_cast<MipsTargetStreamer &>(TS); 96 } 97 98 MCSubtargetInfo &STI; 99 MipsABIInfo ABI; 100 SmallVector<std::unique_ptr<MipsAssemblerOptions>, 2> AssemblerOptions; 101 MCSymbol *CurrentFn; // Pointer to the function being parsed. It may be a 102 // nullptr, which indicates that no function is currently 103 // selected. This usually happens after an '.end func' 104 // directive. 105 106 // Print a warning along with its fix-it message at the given range. 107 void printWarningWithFixIt(const Twine &Msg, const Twine &FixMsg, 108 SMRange Range, bool ShowColors = true); 109 110 #define GET_ASSEMBLER_HEADER 111 #include "MipsGenAsmMatcher.inc" 112 113 unsigned checkTargetMatchPredicate(MCInst &Inst) override; 114 115 bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, 116 OperandVector &Operands, MCStreamer &Out, 117 uint64_t &ErrorInfo, 118 bool MatchingInlineAsm) override; 119 120 /// Parse a register as used in CFI directives 121 bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc) override; 122 123 bool parseParenSuffix(StringRef Name, OperandVector &Operands); 124 125 bool parseBracketSuffix(StringRef Name, OperandVector &Operands); 126 127 bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name, 128 SMLoc NameLoc, OperandVector &Operands) override; 129 130 bool ParseDirective(AsmToken DirectiveID) override; 131 132 MipsAsmParser::OperandMatchResultTy parseMemOperand(OperandVector &Operands); 133 134 MipsAsmParser::OperandMatchResultTy 135 matchAnyRegisterNameWithoutDollar(OperandVector &Operands, 136 StringRef Identifier, SMLoc S); 137 138 MipsAsmParser::OperandMatchResultTy 139 matchAnyRegisterWithoutDollar(OperandVector &Operands, SMLoc S); 140 141 MipsAsmParser::OperandMatchResultTy parseAnyRegister(OperandVector &Operands); 142 143 MipsAsmParser::OperandMatchResultTy parseImm(OperandVector &Operands); 144 145 MipsAsmParser::OperandMatchResultTy parseJumpTarget(OperandVector &Operands); 146 147 MipsAsmParser::OperandMatchResultTy parseInvNum(OperandVector &Operands); 148 149 MipsAsmParser::OperandMatchResultTy parseLSAImm(OperandVector &Operands); 150 151 MipsAsmParser::OperandMatchResultTy 152 parseRegisterPair (OperandVector &Operands); 153 154 MipsAsmParser::OperandMatchResultTy 155 parseRegisterList (OperandVector &Operands); 156 157 bool searchSymbolAlias(OperandVector &Operands); 158 159 bool parseOperand(OperandVector &, StringRef Mnemonic); 160 161 bool needsExpansion(MCInst &Inst); 162 163 // Expands assembly pseudo instructions. 164 // Returns false on success, true otherwise. 165 bool expandInstruction(MCInst &Inst, SMLoc IDLoc, 166 SmallVectorImpl<MCInst> &Instructions); 167 168 bool expandJalWithRegs(MCInst &Inst, SMLoc IDLoc, 169 SmallVectorImpl<MCInst> &Instructions); 170 171 bool expandLoadImm(MCInst &Inst, SMLoc IDLoc, 172 SmallVectorImpl<MCInst> &Instructions); 173 174 bool expandLoadAddressImm(MCInst &Inst, SMLoc IDLoc, 175 SmallVectorImpl<MCInst> &Instructions); 176 177 bool expandLoadAddressReg(MCInst &Inst, SMLoc IDLoc, 178 SmallVectorImpl<MCInst> &Instructions); 179 bool expandUncondBranchMMPseudo(MCInst &Inst, SMLoc IDLoc, 180 SmallVectorImpl<MCInst> &Instructions); 181 182 void expandLoadAddressSym(MCInst &Inst, SMLoc IDLoc, 183 SmallVectorImpl<MCInst> &Instructions); 184 185 void expandMemInst(MCInst &Inst, SMLoc IDLoc, 186 SmallVectorImpl<MCInst> &Instructions, bool isLoad, 187 bool isImmOpnd); 188 189 bool expandLoadStoreMultiple(MCInst &Inst, SMLoc IDLoc, 190 SmallVectorImpl<MCInst> &Instructions); 191 192 bool reportParseError(Twine ErrorMsg); 193 bool reportParseError(SMLoc Loc, Twine ErrorMsg); 194 195 bool parseMemOffset(const MCExpr *&Res, bool isParenExpr); 196 bool parseRelocOperand(const MCExpr *&Res); 197 198 const MCExpr *evaluateRelocExpr(const MCExpr *Expr, StringRef RelocStr); 199 200 bool isEvaluated(const MCExpr *Expr); 201 bool parseSetMips0Directive(); 202 bool parseSetArchDirective(); 203 bool parseSetFeature(uint64_t Feature); 204 bool parseDirectiveCpLoad(SMLoc Loc); 205 bool parseDirectiveCPSetup(); 206 bool parseDirectiveNaN(); 207 bool parseDirectiveSet(); 208 bool parseDirectiveOption(); 209 210 bool parseSetAtDirective(); 211 bool parseSetNoAtDirective(); 212 bool parseSetMacroDirective(); 213 bool parseSetNoMacroDirective(); 214 bool parseSetMsaDirective(); 215 bool parseSetNoMsaDirective(); 216 bool parseSetNoDspDirective(); 217 bool parseSetReorderDirective(); 218 bool parseSetNoReorderDirective(); 219 bool parseSetMips16Directive(); 220 bool parseSetNoMips16Directive(); 221 bool parseSetFpDirective(); 222 bool parseSetPopDirective(); 223 bool parseSetPushDirective(); 224 225 bool parseSetAssignment(); 226 227 bool parseDataDirective(unsigned Size, SMLoc L); 228 bool parseDirectiveGpWord(); 229 bool parseDirectiveGpDWord(); 230 bool parseDirectiveModule(); 231 bool parseDirectiveModuleFP(); 232 bool parseFpABIValue(MipsABIFlagsSection::FpABIKind &FpABI, 233 StringRef Directive); 234 235 MCSymbolRefExpr::VariantKind getVariantKind(StringRef Symbol); 236 237 bool eatComma(StringRef ErrorStr); 238 239 int matchCPURegisterName(StringRef Symbol); 240 241 int matchHWRegsRegisterName(StringRef Symbol); 242 243 int matchRegisterByNumber(unsigned RegNum, unsigned RegClass); 244 245 int matchFPURegisterName(StringRef Name); 246 247 int matchFCCRegisterName(StringRef Name); 248 249 int matchACRegisterName(StringRef Name); 250 251 int matchMSA128RegisterName(StringRef Name); 252 253 int matchMSA128CtrlRegisterName(StringRef Name); 254 255 unsigned getReg(int RC, int RegNo); 256 257 unsigned getGPR(int RegNo); 258 259 int getATReg(SMLoc Loc); 260 261 bool processInstruction(MCInst &Inst, SMLoc IDLoc, 262 SmallVectorImpl<MCInst> &Instructions); 263 264 // Helper function that checks if the value of a vector index is within the 265 // boundaries of accepted values for each RegisterKind 266 // Example: INSERT.B $w0[n], $1 => 16 > n >= 0 267 bool validateMSAIndex(int Val, int RegKind); 268 269 // Selects a new architecture by updating the FeatureBits with the necessary 270 // info including implied dependencies. 271 // Internally, it clears all the feature bits related to *any* architecture 272 // and selects the new one using the ToggleFeature functionality of the 273 // MCSubtargetInfo object that handles implied dependencies. The reason we 274 // clear all the arch related bits manually is because ToggleFeature only 275 // clears the features that imply the feature being cleared and not the 276 // features implied by the feature being cleared. This is easier to see 277 // with an example: 278 // -------------------------------------------------- 279 // | Feature | Implies | 280 // | -------------------------------------------------| 281 // | FeatureMips1 | None | 282 // | FeatureMips2 | FeatureMips1 | 283 // | FeatureMips3 | FeatureMips2 | FeatureMipsGP64 | 284 // | FeatureMips4 | FeatureMips3 | 285 // | ... | | 286 // -------------------------------------------------- 287 // 288 // Setting Mips3 is equivalent to set: (FeatureMips3 | FeatureMips2 | 289 // FeatureMipsGP64 | FeatureMips1) 290 // Clearing Mips3 is equivalent to clear (FeatureMips3 | FeatureMips4). 291 void selectArch(StringRef ArchFeature) { 292 uint64_t FeatureBits = STI.getFeatureBits(); 293 FeatureBits &= ~MipsAssemblerOptions::AllArchRelatedMask; 294 STI.setFeatureBits(FeatureBits); 295 setAvailableFeatures( 296 ComputeAvailableFeatures(STI.ToggleFeature(ArchFeature))); 297 AssemblerOptions.back()->setFeatures(getAvailableFeatures()); 298 } 299 300 void setFeatureBits(uint64_t Feature, StringRef FeatureString) { 301 if (!(STI.getFeatureBits() & Feature)) { 302 setAvailableFeatures( 303 ComputeAvailableFeatures(STI.ToggleFeature(FeatureString))); 304 } 305 AssemblerOptions.back()->setFeatures(getAvailableFeatures()); 306 } 307 308 void clearFeatureBits(uint64_t Feature, StringRef FeatureString) { 309 if (STI.getFeatureBits() & Feature) { 310 setAvailableFeatures( 311 ComputeAvailableFeatures(STI.ToggleFeature(FeatureString))); 312 } 313 AssemblerOptions.back()->setFeatures(getAvailableFeatures()); 314 } 315 316 public: 317 enum MipsMatchResultTy { 318 Match_RequiresDifferentSrcAndDst = FIRST_TARGET_MATCH_RESULT_TY 319 #define GET_OPERAND_DIAGNOSTIC_TYPES 320 #include "MipsGenAsmMatcher.inc" 321 #undef GET_OPERAND_DIAGNOSTIC_TYPES 322 323 }; 324 325 MipsAsmParser(MCSubtargetInfo &sti, MCAsmParser &parser, 326 const MCInstrInfo &MII, const MCTargetOptions &Options) 327 : MCTargetAsmParser(), STI(sti), 328 ABI(MipsABIInfo::computeTargetABI(Triple(sti.getTargetTriple()), 329 sti.getCPU(), Options)) { 330 MCAsmParserExtension::Initialize(parser); 331 332 // Initialize the set of available features. 333 setAvailableFeatures(ComputeAvailableFeatures(STI.getFeatureBits())); 334 335 // Remember the initial assembler options. The user can not modify these. 336 AssemblerOptions.push_back( 337 make_unique<MipsAssemblerOptions>(getAvailableFeatures())); 338 339 // Create an assembler options environment for the user to modify. 340 AssemblerOptions.push_back( 341 make_unique<MipsAssemblerOptions>(getAvailableFeatures())); 342 343 getTargetStreamer().updateABIInfo(*this); 344 345 if (!isABI_O32() && !useOddSPReg() != 0) 346 report_fatal_error("-mno-odd-spreg requires the O32 ABI"); 347 348 CurrentFn = nullptr; 349 } 350 351 /// True if all of $fcc0 - $fcc7 exist for the current ISA. 352 bool hasEightFccRegisters() const { return hasMips4() || hasMips32(); } 353 354 bool isGP64bit() const { return STI.getFeatureBits() & Mips::FeatureGP64Bit; } 355 bool isFP64bit() const { return STI.getFeatureBits() & Mips::FeatureFP64Bit; } 356 const MipsABIInfo &getABI() const { return ABI; } 357 bool isABI_N32() const { return ABI.IsN32(); } 358 bool isABI_N64() const { return ABI.IsN64(); } 359 bool isABI_O32() const { return ABI.IsO32(); } 360 bool isABI_FPXX() const { return STI.getFeatureBits() & Mips::FeatureFPXX; } 361 362 bool useOddSPReg() const { 363 return !(STI.getFeatureBits() & Mips::FeatureNoOddSPReg); 364 } 365 366 bool inMicroMipsMode() const { 367 return STI.getFeatureBits() & Mips::FeatureMicroMips; 368 } 369 bool hasMips1() const { return STI.getFeatureBits() & Mips::FeatureMips1; } 370 bool hasMips2() const { return STI.getFeatureBits() & Mips::FeatureMips2; } 371 bool hasMips3() const { return STI.getFeatureBits() & Mips::FeatureMips3; } 372 bool hasMips4() const { return STI.getFeatureBits() & Mips::FeatureMips4; } 373 bool hasMips5() const { return STI.getFeatureBits() & Mips::FeatureMips5; } 374 bool hasMips32() const { 375 return (STI.getFeatureBits() & Mips::FeatureMips32); 376 } 377 bool hasMips64() const { 378 return (STI.getFeatureBits() & Mips::FeatureMips64); 379 } 380 bool hasMips32r2() const { 381 return (STI.getFeatureBits() & Mips::FeatureMips32r2); 382 } 383 bool hasMips64r2() const { 384 return (STI.getFeatureBits() & Mips::FeatureMips64r2); 385 } 386 bool hasMips32r6() const { 387 return (STI.getFeatureBits() & Mips::FeatureMips32r6); 388 } 389 bool hasMips64r6() const { 390 return (STI.getFeatureBits() & Mips::FeatureMips64r6); 391 } 392 bool hasCnMips() const { 393 return (STI.getFeatureBits() & Mips::FeatureCnMips); 394 } 395 bool hasDSP() const { return (STI.getFeatureBits() & Mips::FeatureDSP); } 396 bool hasDSPR2() const { return (STI.getFeatureBits() & Mips::FeatureDSPR2); } 397 bool hasMSA() const { return (STI.getFeatureBits() & Mips::FeatureMSA); } 398 399 bool inMips16Mode() const { 400 return STI.getFeatureBits() & Mips::FeatureMips16; 401 } 402 // TODO: see how can we get this info. 403 bool abiUsesSoftFloat() const { return false; } 404 405 /// Warn if RegNo is the current assembler temporary. 406 void warnIfAssemblerTemporary(int RegNo, SMLoc Loc); 407 }; 408 } 409 410 namespace { 411 412 /// MipsOperand - Instances of this class represent a parsed Mips machine 413 /// instruction. 414 class MipsOperand : public MCParsedAsmOperand { 415 public: 416 /// Broad categories of register classes 417 /// The exact class is finalized by the render method. 418 enum RegKind { 419 RegKind_GPR = 1, /// GPR32 and GPR64 (depending on isGP64bit()) 420 RegKind_FGR = 2, /// FGR32, FGR64, AFGR64 (depending on context and 421 /// isFP64bit()) 422 RegKind_FCC = 4, /// FCC 423 RegKind_MSA128 = 8, /// MSA128[BHWD] (makes no difference which) 424 RegKind_MSACtrl = 16, /// MSA control registers 425 RegKind_COP2 = 32, /// COP2 426 RegKind_ACC = 64, /// HI32DSP, LO32DSP, and ACC64DSP (depending on 427 /// context). 428 RegKind_CCR = 128, /// CCR 429 RegKind_HWRegs = 256, /// HWRegs 430 RegKind_COP3 = 512, /// COP3 431 432 /// Potentially any (e.g. $1) 433 RegKind_Numeric = RegKind_GPR | RegKind_FGR | RegKind_FCC | RegKind_MSA128 | 434 RegKind_MSACtrl | RegKind_COP2 | RegKind_ACC | 435 RegKind_CCR | RegKind_HWRegs | RegKind_COP3 436 }; 437 438 private: 439 enum KindTy { 440 k_Immediate, /// An immediate (possibly involving symbol references) 441 k_Memory, /// Base + Offset Memory Address 442 k_PhysRegister, /// A physical register from the Mips namespace 443 k_RegisterIndex, /// A register index in one or more RegKind. 444 k_Token, /// A simple token 445 k_RegList, /// A physical register list 446 k_RegPair /// A pair of physical register 447 } Kind; 448 449 public: 450 MipsOperand(KindTy K, MipsAsmParser &Parser) 451 : MCParsedAsmOperand(), Kind(K), AsmParser(Parser) {} 452 453 private: 454 /// For diagnostics, and checking the assembler temporary 455 MipsAsmParser &AsmParser; 456 457 struct Token { 458 const char *Data; 459 unsigned Length; 460 }; 461 462 struct PhysRegOp { 463 unsigned Num; /// Register Number 464 }; 465 466 struct RegIdxOp { 467 unsigned Index; /// Index into the register class 468 RegKind Kind; /// Bitfield of the kinds it could possibly be 469 const MCRegisterInfo *RegInfo; 470 }; 471 472 struct ImmOp { 473 const MCExpr *Val; 474 }; 475 476 struct MemOp { 477 MipsOperand *Base; 478 const MCExpr *Off; 479 }; 480 481 struct RegListOp { 482 SmallVector<unsigned, 10> *List; 483 }; 484 485 union { 486 struct Token Tok; 487 struct PhysRegOp PhysReg; 488 struct RegIdxOp RegIdx; 489 struct ImmOp Imm; 490 struct MemOp Mem; 491 struct RegListOp RegList; 492 }; 493 494 SMLoc StartLoc, EndLoc; 495 496 /// Internal constructor for register kinds 497 static std::unique_ptr<MipsOperand> CreateReg(unsigned Index, RegKind RegKind, 498 const MCRegisterInfo *RegInfo, 499 SMLoc S, SMLoc E, 500 MipsAsmParser &Parser) { 501 auto Op = make_unique<MipsOperand>(k_RegisterIndex, Parser); 502 Op->RegIdx.Index = Index; 503 Op->RegIdx.RegInfo = RegInfo; 504 Op->RegIdx.Kind = RegKind; 505 Op->StartLoc = S; 506 Op->EndLoc = E; 507 return Op; 508 } 509 510 public: 511 /// Coerce the register to GPR32 and return the real register for the current 512 /// target. 513 unsigned getGPR32Reg() const { 514 assert(isRegIdx() && (RegIdx.Kind & RegKind_GPR) && "Invalid access!"); 515 AsmParser.warnIfAssemblerTemporary(RegIdx.Index, StartLoc); 516 unsigned ClassID = Mips::GPR32RegClassID; 517 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 518 } 519 520 /// Coerce the register to GPR32 and return the real register for the current 521 /// target. 522 unsigned getGPRMM16Reg() const { 523 assert(isRegIdx() && (RegIdx.Kind & RegKind_GPR) && "Invalid access!"); 524 unsigned ClassID = Mips::GPR32RegClassID; 525 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 526 } 527 528 /// Coerce the register to GPR64 and return the real register for the current 529 /// target. 530 unsigned getGPR64Reg() const { 531 assert(isRegIdx() && (RegIdx.Kind & RegKind_GPR) && "Invalid access!"); 532 unsigned ClassID = Mips::GPR64RegClassID; 533 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 534 } 535 536 private: 537 /// Coerce the register to AFGR64 and return the real register for the current 538 /// target. 539 unsigned getAFGR64Reg() const { 540 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 541 if (RegIdx.Index % 2 != 0) 542 AsmParser.Warning(StartLoc, "Float register should be even."); 543 return RegIdx.RegInfo->getRegClass(Mips::AFGR64RegClassID) 544 .getRegister(RegIdx.Index / 2); 545 } 546 547 /// Coerce the register to FGR64 and return the real register for the current 548 /// target. 549 unsigned getFGR64Reg() const { 550 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 551 return RegIdx.RegInfo->getRegClass(Mips::FGR64RegClassID) 552 .getRegister(RegIdx.Index); 553 } 554 555 /// Coerce the register to FGR32 and return the real register for the current 556 /// target. 557 unsigned getFGR32Reg() const { 558 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 559 return RegIdx.RegInfo->getRegClass(Mips::FGR32RegClassID) 560 .getRegister(RegIdx.Index); 561 } 562 563 /// Coerce the register to FGRH32 and return the real register for the current 564 /// target. 565 unsigned getFGRH32Reg() const { 566 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 567 return RegIdx.RegInfo->getRegClass(Mips::FGRH32RegClassID) 568 .getRegister(RegIdx.Index); 569 } 570 571 /// Coerce the register to FCC and return the real register for the current 572 /// target. 573 unsigned getFCCReg() const { 574 assert(isRegIdx() && (RegIdx.Kind & RegKind_FCC) && "Invalid access!"); 575 return RegIdx.RegInfo->getRegClass(Mips::FCCRegClassID) 576 .getRegister(RegIdx.Index); 577 } 578 579 /// Coerce the register to MSA128 and return the real register for the current 580 /// target. 581 unsigned getMSA128Reg() const { 582 assert(isRegIdx() && (RegIdx.Kind & RegKind_MSA128) && "Invalid access!"); 583 // It doesn't matter which of the MSA128[BHWD] classes we use. They are all 584 // identical 585 unsigned ClassID = Mips::MSA128BRegClassID; 586 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 587 } 588 589 /// Coerce the register to MSACtrl and return the real register for the 590 /// current target. 591 unsigned getMSACtrlReg() const { 592 assert(isRegIdx() && (RegIdx.Kind & RegKind_MSACtrl) && "Invalid access!"); 593 unsigned ClassID = Mips::MSACtrlRegClassID; 594 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 595 } 596 597 /// Coerce the register to COP2 and return the real register for the 598 /// current target. 599 unsigned getCOP2Reg() const { 600 assert(isRegIdx() && (RegIdx.Kind & RegKind_COP2) && "Invalid access!"); 601 unsigned ClassID = Mips::COP2RegClassID; 602 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 603 } 604 605 /// Coerce the register to COP3 and return the real register for the 606 /// current target. 607 unsigned getCOP3Reg() const { 608 assert(isRegIdx() && (RegIdx.Kind & RegKind_COP3) && "Invalid access!"); 609 unsigned ClassID = Mips::COP3RegClassID; 610 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 611 } 612 613 /// Coerce the register to ACC64DSP and return the real register for the 614 /// current target. 615 unsigned getACC64DSPReg() const { 616 assert(isRegIdx() && (RegIdx.Kind & RegKind_ACC) && "Invalid access!"); 617 unsigned ClassID = Mips::ACC64DSPRegClassID; 618 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 619 } 620 621 /// Coerce the register to HI32DSP and return the real register for the 622 /// current target. 623 unsigned getHI32DSPReg() const { 624 assert(isRegIdx() && (RegIdx.Kind & RegKind_ACC) && "Invalid access!"); 625 unsigned ClassID = Mips::HI32DSPRegClassID; 626 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 627 } 628 629 /// Coerce the register to LO32DSP and return the real register for the 630 /// current target. 631 unsigned getLO32DSPReg() const { 632 assert(isRegIdx() && (RegIdx.Kind & RegKind_ACC) && "Invalid access!"); 633 unsigned ClassID = Mips::LO32DSPRegClassID; 634 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 635 } 636 637 /// Coerce the register to CCR and return the real register for the 638 /// current target. 639 unsigned getCCRReg() const { 640 assert(isRegIdx() && (RegIdx.Kind & RegKind_CCR) && "Invalid access!"); 641 unsigned ClassID = Mips::CCRRegClassID; 642 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 643 } 644 645 /// Coerce the register to HWRegs and return the real register for the 646 /// current target. 647 unsigned getHWRegsReg() const { 648 assert(isRegIdx() && (RegIdx.Kind & RegKind_HWRegs) && "Invalid access!"); 649 unsigned ClassID = Mips::HWRegsRegClassID; 650 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 651 } 652 653 public: 654 void addExpr(MCInst &Inst, const MCExpr *Expr) const { 655 // Add as immediate when possible. Null MCExpr = 0. 656 if (!Expr) 657 Inst.addOperand(MCOperand::CreateImm(0)); 658 else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr)) 659 Inst.addOperand(MCOperand::CreateImm(CE->getValue())); 660 else 661 Inst.addOperand(MCOperand::CreateExpr(Expr)); 662 } 663 664 void addRegOperands(MCInst &Inst, unsigned N) const { 665 llvm_unreachable("Use a custom parser instead"); 666 } 667 668 /// Render the operand to an MCInst as a GPR32 669 /// Asserts if the wrong number of operands are requested, or the operand 670 /// is not a k_RegisterIndex compatible with RegKind_GPR 671 void addGPR32AsmRegOperands(MCInst &Inst, unsigned N) const { 672 assert(N == 1 && "Invalid number of operands!"); 673 Inst.addOperand(MCOperand::CreateReg(getGPR32Reg())); 674 } 675 676 void addGPRMM16AsmRegOperands(MCInst &Inst, unsigned N) const { 677 assert(N == 1 && "Invalid number of operands!"); 678 Inst.addOperand(MCOperand::CreateReg(getGPRMM16Reg())); 679 } 680 681 void addGPRMM16AsmRegZeroOperands(MCInst &Inst, unsigned N) const { 682 assert(N == 1 && "Invalid number of operands!"); 683 Inst.addOperand(MCOperand::CreateReg(getGPRMM16Reg())); 684 } 685 686 /// Render the operand to an MCInst as a GPR64 687 /// Asserts if the wrong number of operands are requested, or the operand 688 /// is not a k_RegisterIndex compatible with RegKind_GPR 689 void addGPR64AsmRegOperands(MCInst &Inst, unsigned N) const { 690 assert(N == 1 && "Invalid number of operands!"); 691 Inst.addOperand(MCOperand::CreateReg(getGPR64Reg())); 692 } 693 694 void addAFGR64AsmRegOperands(MCInst &Inst, unsigned N) const { 695 assert(N == 1 && "Invalid number of operands!"); 696 Inst.addOperand(MCOperand::CreateReg(getAFGR64Reg())); 697 } 698 699 void addFGR64AsmRegOperands(MCInst &Inst, unsigned N) const { 700 assert(N == 1 && "Invalid number of operands!"); 701 Inst.addOperand(MCOperand::CreateReg(getFGR64Reg())); 702 } 703 704 void addFGR32AsmRegOperands(MCInst &Inst, unsigned N) const { 705 assert(N == 1 && "Invalid number of operands!"); 706 Inst.addOperand(MCOperand::CreateReg(getFGR32Reg())); 707 // FIXME: We ought to do this for -integrated-as without -via-file-asm too. 708 if (!AsmParser.useOddSPReg() && RegIdx.Index & 1) 709 AsmParser.Error(StartLoc, "-mno-odd-spreg prohibits the use of odd FPU " 710 "registers"); 711 } 712 713 void addFGRH32AsmRegOperands(MCInst &Inst, unsigned N) const { 714 assert(N == 1 && "Invalid number of operands!"); 715 Inst.addOperand(MCOperand::CreateReg(getFGRH32Reg())); 716 } 717 718 void addFCCAsmRegOperands(MCInst &Inst, unsigned N) const { 719 assert(N == 1 && "Invalid number of operands!"); 720 Inst.addOperand(MCOperand::CreateReg(getFCCReg())); 721 } 722 723 void addMSA128AsmRegOperands(MCInst &Inst, unsigned N) const { 724 assert(N == 1 && "Invalid number of operands!"); 725 Inst.addOperand(MCOperand::CreateReg(getMSA128Reg())); 726 } 727 728 void addMSACtrlAsmRegOperands(MCInst &Inst, unsigned N) const { 729 assert(N == 1 && "Invalid number of operands!"); 730 Inst.addOperand(MCOperand::CreateReg(getMSACtrlReg())); 731 } 732 733 void addCOP2AsmRegOperands(MCInst &Inst, unsigned N) const { 734 assert(N == 1 && "Invalid number of operands!"); 735 Inst.addOperand(MCOperand::CreateReg(getCOP2Reg())); 736 } 737 738 void addCOP3AsmRegOperands(MCInst &Inst, unsigned N) const { 739 assert(N == 1 && "Invalid number of operands!"); 740 Inst.addOperand(MCOperand::CreateReg(getCOP3Reg())); 741 } 742 743 void addACC64DSPAsmRegOperands(MCInst &Inst, unsigned N) const { 744 assert(N == 1 && "Invalid number of operands!"); 745 Inst.addOperand(MCOperand::CreateReg(getACC64DSPReg())); 746 } 747 748 void addHI32DSPAsmRegOperands(MCInst &Inst, unsigned N) const { 749 assert(N == 1 && "Invalid number of operands!"); 750 Inst.addOperand(MCOperand::CreateReg(getHI32DSPReg())); 751 } 752 753 void addLO32DSPAsmRegOperands(MCInst &Inst, unsigned N) const { 754 assert(N == 1 && "Invalid number of operands!"); 755 Inst.addOperand(MCOperand::CreateReg(getLO32DSPReg())); 756 } 757 758 void addCCRAsmRegOperands(MCInst &Inst, unsigned N) const { 759 assert(N == 1 && "Invalid number of operands!"); 760 Inst.addOperand(MCOperand::CreateReg(getCCRReg())); 761 } 762 763 void addHWRegsAsmRegOperands(MCInst &Inst, unsigned N) const { 764 assert(N == 1 && "Invalid number of operands!"); 765 Inst.addOperand(MCOperand::CreateReg(getHWRegsReg())); 766 } 767 768 void addImmOperands(MCInst &Inst, unsigned N) const { 769 assert(N == 1 && "Invalid number of operands!"); 770 const MCExpr *Expr = getImm(); 771 addExpr(Inst, Expr); 772 } 773 774 void addMemOperands(MCInst &Inst, unsigned N) const { 775 assert(N == 2 && "Invalid number of operands!"); 776 777 Inst.addOperand(MCOperand::CreateReg(getMemBase()->getGPR32Reg())); 778 779 const MCExpr *Expr = getMemOff(); 780 addExpr(Inst, Expr); 781 } 782 783 void addMicroMipsMemOperands(MCInst &Inst, unsigned N) const { 784 assert(N == 2 && "Invalid number of operands!"); 785 786 Inst.addOperand(MCOperand::CreateReg(getMemBase()->getGPRMM16Reg())); 787 788 const MCExpr *Expr = getMemOff(); 789 addExpr(Inst, Expr); 790 } 791 792 void addRegListOperands(MCInst &Inst, unsigned N) const { 793 assert(N == 1 && "Invalid number of operands!"); 794 795 for (auto RegNo : getRegList()) 796 Inst.addOperand(MCOperand::CreateReg(RegNo)); 797 } 798 799 void addRegPairOperands(MCInst &Inst, unsigned N) const { 800 assert(N == 2 && "Invalid number of operands!"); 801 unsigned RegNo = getRegPair(); 802 Inst.addOperand(MCOperand::CreateReg(RegNo++)); 803 Inst.addOperand(MCOperand::CreateReg(RegNo)); 804 } 805 806 bool isReg() const override { 807 // As a special case until we sort out the definition of div/divu, pretend 808 // that $0/$zero are k_PhysRegister so that MCK_ZERO works correctly. 809 if (isGPRAsmReg() && RegIdx.Index == 0) 810 return true; 811 812 return Kind == k_PhysRegister; 813 } 814 bool isRegIdx() const { return Kind == k_RegisterIndex; } 815 bool isImm() const override { return Kind == k_Immediate; } 816 bool isConstantImm() const { 817 return isImm() && dyn_cast<MCConstantExpr>(getImm()); 818 } 819 bool isToken() const override { 820 // Note: It's not possible to pretend that other operand kinds are tokens. 821 // The matcher emitter checks tokens first. 822 return Kind == k_Token; 823 } 824 bool isMem() const override { return Kind == k_Memory; } 825 bool isConstantMemOff() const { 826 return isMem() && dyn_cast<MCConstantExpr>(getMemOff()); 827 } 828 template <unsigned Bits> bool isMemWithSimmOffset() const { 829 return isMem() && isConstantMemOff() && isInt<Bits>(getConstantMemOff()); 830 } 831 bool isMemWithGRPMM16Base() const { 832 return isMem() && getMemBase()->isMM16AsmReg(); 833 } 834 template <unsigned Bits> bool isMemWithUimmOffsetSP() const { 835 return isMem() && isConstantMemOff() && isUInt<Bits>(getConstantMemOff()) 836 && getMemBase()->isRegIdx() && (getMemBase()->getGPR32Reg() == Mips::SP); 837 } 838 template <unsigned Bits> bool isMemWithUimmWordAlignedOffsetSP() const { 839 return isMem() && isConstantMemOff() && isUInt<Bits>(getConstantMemOff()) 840 && (getConstantMemOff() % 4 == 0) && getMemBase()->isRegIdx() 841 && (getMemBase()->getGPR32Reg() == Mips::SP); 842 } 843 bool isRegList16() const { 844 if (!isRegList()) 845 return false; 846 847 int Size = RegList.List->size(); 848 if (Size < 2 || Size > 5 || *RegList.List->begin() != Mips::S0 || 849 RegList.List->back() != Mips::RA) 850 return false; 851 852 int PrevReg = *RegList.List->begin(); 853 for (int i = 1; i < Size - 1; i++) { 854 int Reg = (*(RegList.List))[i]; 855 if ( Reg != PrevReg + 1) 856 return false; 857 PrevReg = Reg; 858 } 859 860 return true; 861 } 862 bool isInvNum() const { return Kind == k_Immediate; } 863 bool isLSAImm() const { 864 if (!isConstantImm()) 865 return false; 866 int64_t Val = getConstantImm(); 867 return 1 <= Val && Val <= 4; 868 } 869 bool isRegList() const { return Kind == k_RegList; } 870 871 StringRef getToken() const { 872 assert(Kind == k_Token && "Invalid access!"); 873 return StringRef(Tok.Data, Tok.Length); 874 } 875 bool isRegPair() const { return Kind == k_RegPair; } 876 877 unsigned getReg() const override { 878 // As a special case until we sort out the definition of div/divu, pretend 879 // that $0/$zero are k_PhysRegister so that MCK_ZERO works correctly. 880 if (Kind == k_RegisterIndex && RegIdx.Index == 0 && 881 RegIdx.Kind & RegKind_GPR) 882 return getGPR32Reg(); // FIXME: GPR64 too 883 884 assert(Kind == k_PhysRegister && "Invalid access!"); 885 return PhysReg.Num; 886 } 887 888 const MCExpr *getImm() const { 889 assert((Kind == k_Immediate) && "Invalid access!"); 890 return Imm.Val; 891 } 892 893 int64_t getConstantImm() const { 894 const MCExpr *Val = getImm(); 895 return static_cast<const MCConstantExpr *>(Val)->getValue(); 896 } 897 898 MipsOperand *getMemBase() const { 899 assert((Kind == k_Memory) && "Invalid access!"); 900 return Mem.Base; 901 } 902 903 const MCExpr *getMemOff() const { 904 assert((Kind == k_Memory) && "Invalid access!"); 905 return Mem.Off; 906 } 907 908 int64_t getConstantMemOff() const { 909 return static_cast<const MCConstantExpr *>(getMemOff())->getValue(); 910 } 911 912 const SmallVectorImpl<unsigned> &getRegList() const { 913 assert((Kind == k_RegList) && "Invalid access!"); 914 return *(RegList.List); 915 } 916 917 unsigned getRegPair() const { 918 assert((Kind == k_RegPair) && "Invalid access!"); 919 return RegIdx.Index; 920 } 921 922 static std::unique_ptr<MipsOperand> CreateToken(StringRef Str, SMLoc S, 923 MipsAsmParser &Parser) { 924 auto Op = make_unique<MipsOperand>(k_Token, Parser); 925 Op->Tok.Data = Str.data(); 926 Op->Tok.Length = Str.size(); 927 Op->StartLoc = S; 928 Op->EndLoc = S; 929 return Op; 930 } 931 932 /// Create a numeric register (e.g. $1). The exact register remains 933 /// unresolved until an instruction successfully matches 934 static std::unique_ptr<MipsOperand> 935 createNumericReg(unsigned Index, const MCRegisterInfo *RegInfo, SMLoc S, 936 SMLoc E, MipsAsmParser &Parser) { 937 DEBUG(dbgs() << "createNumericReg(" << Index << ", ...)\n"); 938 return CreateReg(Index, RegKind_Numeric, RegInfo, S, E, Parser); 939 } 940 941 /// Create a register that is definitely a GPR. 942 /// This is typically only used for named registers such as $gp. 943 static std::unique_ptr<MipsOperand> 944 createGPRReg(unsigned Index, const MCRegisterInfo *RegInfo, SMLoc S, SMLoc E, 945 MipsAsmParser &Parser) { 946 return CreateReg(Index, RegKind_GPR, RegInfo, S, E, Parser); 947 } 948 949 /// Create a register that is definitely a FGR. 950 /// This is typically only used for named registers such as $f0. 951 static std::unique_ptr<MipsOperand> 952 createFGRReg(unsigned Index, const MCRegisterInfo *RegInfo, SMLoc S, SMLoc E, 953 MipsAsmParser &Parser) { 954 return CreateReg(Index, RegKind_FGR, RegInfo, S, E, Parser); 955 } 956 957 /// Create a register that is definitely a HWReg. 958 /// This is typically only used for named registers such as $hwr_cpunum. 959 static std::unique_ptr<MipsOperand> 960 createHWRegsReg(unsigned Index, const MCRegisterInfo *RegInfo, 961 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 962 return CreateReg(Index, RegKind_HWRegs, RegInfo, S, E, Parser); 963 } 964 965 /// Create a register that is definitely an FCC. 966 /// This is typically only used for named registers such as $fcc0. 967 static std::unique_ptr<MipsOperand> 968 createFCCReg(unsigned Index, const MCRegisterInfo *RegInfo, SMLoc S, SMLoc E, 969 MipsAsmParser &Parser) { 970 return CreateReg(Index, RegKind_FCC, RegInfo, S, E, Parser); 971 } 972 973 /// Create a register that is definitely an ACC. 974 /// This is typically only used for named registers such as $ac0. 975 static std::unique_ptr<MipsOperand> 976 createACCReg(unsigned Index, const MCRegisterInfo *RegInfo, SMLoc S, SMLoc E, 977 MipsAsmParser &Parser) { 978 return CreateReg(Index, RegKind_ACC, RegInfo, S, E, Parser); 979 } 980 981 /// Create a register that is definitely an MSA128. 982 /// This is typically only used for named registers such as $w0. 983 static std::unique_ptr<MipsOperand> 984 createMSA128Reg(unsigned Index, const MCRegisterInfo *RegInfo, SMLoc S, 985 SMLoc E, MipsAsmParser &Parser) { 986 return CreateReg(Index, RegKind_MSA128, RegInfo, S, E, Parser); 987 } 988 989 /// Create a register that is definitely an MSACtrl. 990 /// This is typically only used for named registers such as $msaaccess. 991 static std::unique_ptr<MipsOperand> 992 createMSACtrlReg(unsigned Index, const MCRegisterInfo *RegInfo, SMLoc S, 993 SMLoc E, MipsAsmParser &Parser) { 994 return CreateReg(Index, RegKind_MSACtrl, RegInfo, S, E, Parser); 995 } 996 997 static std::unique_ptr<MipsOperand> 998 CreateImm(const MCExpr *Val, SMLoc S, SMLoc E, MipsAsmParser &Parser) { 999 auto Op = make_unique<MipsOperand>(k_Immediate, Parser); 1000 Op->Imm.Val = Val; 1001 Op->StartLoc = S; 1002 Op->EndLoc = E; 1003 return Op; 1004 } 1005 1006 static std::unique_ptr<MipsOperand> 1007 CreateMem(std::unique_ptr<MipsOperand> Base, const MCExpr *Off, SMLoc S, 1008 SMLoc E, MipsAsmParser &Parser) { 1009 auto Op = make_unique<MipsOperand>(k_Memory, Parser); 1010 Op->Mem.Base = Base.release(); 1011 Op->Mem.Off = Off; 1012 Op->StartLoc = S; 1013 Op->EndLoc = E; 1014 return Op; 1015 } 1016 1017 static std::unique_ptr<MipsOperand> 1018 CreateRegList(SmallVectorImpl<unsigned> &Regs, SMLoc StartLoc, SMLoc EndLoc, 1019 MipsAsmParser &Parser) { 1020 assert (Regs.size() > 0 && "Empty list not allowed"); 1021 1022 auto Op = make_unique<MipsOperand>(k_RegList, Parser); 1023 Op->RegList.List = new SmallVector<unsigned, 10>(); 1024 for (auto Reg : Regs) 1025 Op->RegList.List->push_back(Reg); 1026 Op->StartLoc = StartLoc; 1027 Op->EndLoc = EndLoc; 1028 return Op; 1029 } 1030 1031 static std::unique_ptr<MipsOperand> 1032 CreateRegPair(unsigned RegNo, SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1033 auto Op = make_unique<MipsOperand>(k_RegPair, Parser); 1034 Op->RegIdx.Index = RegNo; 1035 Op->StartLoc = S; 1036 Op->EndLoc = E; 1037 return Op; 1038 } 1039 1040 bool isGPRAsmReg() const { 1041 return isRegIdx() && RegIdx.Kind & RegKind_GPR && RegIdx.Index <= 31; 1042 } 1043 bool isMM16AsmReg() const { 1044 if (!(isRegIdx() && RegIdx.Kind)) 1045 return false; 1046 return ((RegIdx.Index >= 2 && RegIdx.Index <= 7) 1047 || RegIdx.Index == 16 || RegIdx.Index == 17); 1048 } 1049 bool isMM16AsmRegZero() const { 1050 if (!(isRegIdx() && RegIdx.Kind)) 1051 return false; 1052 return (RegIdx.Index == 0 || 1053 (RegIdx.Index >= 2 && RegIdx.Index <= 7) || 1054 RegIdx.Index == 17); 1055 } 1056 bool isFGRAsmReg() const { 1057 // AFGR64 is $0-$15 but we handle this in getAFGR64() 1058 return isRegIdx() && RegIdx.Kind & RegKind_FGR && RegIdx.Index <= 31; 1059 } 1060 bool isHWRegsAsmReg() const { 1061 return isRegIdx() && RegIdx.Kind & RegKind_HWRegs && RegIdx.Index <= 31; 1062 } 1063 bool isCCRAsmReg() const { 1064 return isRegIdx() && RegIdx.Kind & RegKind_CCR && RegIdx.Index <= 31; 1065 } 1066 bool isFCCAsmReg() const { 1067 if (!(isRegIdx() && RegIdx.Kind & RegKind_FCC)) 1068 return false; 1069 if (!AsmParser.hasEightFccRegisters()) 1070 return RegIdx.Index == 0; 1071 return RegIdx.Index <= 7; 1072 } 1073 bool isACCAsmReg() const { 1074 return isRegIdx() && RegIdx.Kind & RegKind_ACC && RegIdx.Index <= 3; 1075 } 1076 bool isCOP2AsmReg() const { 1077 return isRegIdx() && RegIdx.Kind & RegKind_COP2 && RegIdx.Index <= 31; 1078 } 1079 bool isCOP3AsmReg() const { 1080 return isRegIdx() && RegIdx.Kind & RegKind_COP3 && RegIdx.Index <= 31; 1081 } 1082 bool isMSA128AsmReg() const { 1083 return isRegIdx() && RegIdx.Kind & RegKind_MSA128 && RegIdx.Index <= 31; 1084 } 1085 bool isMSACtrlAsmReg() const { 1086 return isRegIdx() && RegIdx.Kind & RegKind_MSACtrl && RegIdx.Index <= 7; 1087 } 1088 1089 /// getStartLoc - Get the location of the first token of this operand. 1090 SMLoc getStartLoc() const override { return StartLoc; } 1091 /// getEndLoc - Get the location of the last token of this operand. 1092 SMLoc getEndLoc() const override { return EndLoc; } 1093 1094 virtual ~MipsOperand() { 1095 switch (Kind) { 1096 case k_Immediate: 1097 break; 1098 case k_Memory: 1099 delete Mem.Base; 1100 break; 1101 case k_RegList: 1102 delete RegList.List; 1103 case k_PhysRegister: 1104 case k_RegisterIndex: 1105 case k_Token: 1106 case k_RegPair: 1107 break; 1108 } 1109 } 1110 1111 void print(raw_ostream &OS) const override { 1112 switch (Kind) { 1113 case k_Immediate: 1114 OS << "Imm<"; 1115 Imm.Val->print(OS); 1116 OS << ">"; 1117 break; 1118 case k_Memory: 1119 OS << "Mem<"; 1120 Mem.Base->print(OS); 1121 OS << ", "; 1122 Mem.Off->print(OS); 1123 OS << ">"; 1124 break; 1125 case k_PhysRegister: 1126 OS << "PhysReg<" << PhysReg.Num << ">"; 1127 break; 1128 case k_RegisterIndex: 1129 OS << "RegIdx<" << RegIdx.Index << ":" << RegIdx.Kind << ">"; 1130 break; 1131 case k_Token: 1132 OS << Tok.Data; 1133 break; 1134 case k_RegList: 1135 OS << "RegList< "; 1136 for (auto Reg : (*RegList.List)) 1137 OS << Reg << " "; 1138 OS << ">"; 1139 break; 1140 case k_RegPair: 1141 OS << "RegPair<" << RegIdx.Index << "," << RegIdx.Index + 1 << ">"; 1142 break; 1143 } 1144 } 1145 }; // class MipsOperand 1146 } // namespace 1147 1148 namespace llvm { 1149 extern const MCInstrDesc MipsInsts[]; 1150 } 1151 static const MCInstrDesc &getInstDesc(unsigned Opcode) { 1152 return MipsInsts[Opcode]; 1153 } 1154 1155 static bool hasShortDelaySlot(unsigned Opcode) { 1156 switch (Opcode) { 1157 case Mips::JALS_MM: 1158 case Mips::JALRS_MM: 1159 case Mips::JALRS16_MM: 1160 case Mips::BGEZALS_MM: 1161 case Mips::BLTZALS_MM: 1162 return true; 1163 default: 1164 return false; 1165 } 1166 } 1167 1168 bool MipsAsmParser::processInstruction(MCInst &Inst, SMLoc IDLoc, 1169 SmallVectorImpl<MCInst> &Instructions) { 1170 const MCInstrDesc &MCID = getInstDesc(Inst.getOpcode()); 1171 1172 Inst.setLoc(IDLoc); 1173 1174 if (MCID.isBranch() || MCID.isCall()) { 1175 const unsigned Opcode = Inst.getOpcode(); 1176 MCOperand Offset; 1177 1178 switch (Opcode) { 1179 default: 1180 break; 1181 case Mips::BBIT0: 1182 case Mips::BBIT032: 1183 case Mips::BBIT1: 1184 case Mips::BBIT132: 1185 assert(hasCnMips() && "instruction only valid for octeon cpus"); 1186 // Fall through 1187 1188 case Mips::BEQ: 1189 case Mips::BNE: 1190 case Mips::BEQ_MM: 1191 case Mips::BNE_MM: 1192 assert(MCID.getNumOperands() == 3 && "unexpected number of operands"); 1193 Offset = Inst.getOperand(2); 1194 if (!Offset.isImm()) 1195 break; // We'll deal with this situation later on when applying fixups. 1196 if (!isIntN(inMicroMipsMode() ? 17 : 18, Offset.getImm())) 1197 return Error(IDLoc, "branch target out of range"); 1198 if (OffsetToAlignment(Offset.getImm(), 1199 1LL << (inMicroMipsMode() ? 1 : 2))) 1200 return Error(IDLoc, "branch to misaligned address"); 1201 break; 1202 case Mips::BGEZ: 1203 case Mips::BGTZ: 1204 case Mips::BLEZ: 1205 case Mips::BLTZ: 1206 case Mips::BGEZAL: 1207 case Mips::BLTZAL: 1208 case Mips::BC1F: 1209 case Mips::BC1T: 1210 case Mips::BGEZ_MM: 1211 case Mips::BGTZ_MM: 1212 case Mips::BLEZ_MM: 1213 case Mips::BLTZ_MM: 1214 case Mips::BGEZAL_MM: 1215 case Mips::BLTZAL_MM: 1216 case Mips::BC1F_MM: 1217 case Mips::BC1T_MM: 1218 assert(MCID.getNumOperands() == 2 && "unexpected number of operands"); 1219 Offset = Inst.getOperand(1); 1220 if (!Offset.isImm()) 1221 break; // We'll deal with this situation later on when applying fixups. 1222 if (!isIntN(inMicroMipsMode() ? 17 : 18, Offset.getImm())) 1223 return Error(IDLoc, "branch target out of range"); 1224 if (OffsetToAlignment(Offset.getImm(), 1225 1LL << (inMicroMipsMode() ? 1 : 2))) 1226 return Error(IDLoc, "branch to misaligned address"); 1227 break; 1228 case Mips::BEQZ16_MM: 1229 case Mips::BNEZ16_MM: 1230 assert(MCID.getNumOperands() == 2 && "unexpected number of operands"); 1231 Offset = Inst.getOperand(1); 1232 if (!Offset.isImm()) 1233 break; // We'll deal with this situation later on when applying fixups. 1234 if (!isIntN(8, Offset.getImm())) 1235 return Error(IDLoc, "branch target out of range"); 1236 if (OffsetToAlignment(Offset.getImm(), 2LL)) 1237 return Error(IDLoc, "branch to misaligned address"); 1238 break; 1239 } 1240 } 1241 1242 // SSNOP is deprecated on MIPS32r6/MIPS64r6 1243 // We still accept it but it is a normal nop. 1244 if (hasMips32r6() && Inst.getOpcode() == Mips::SSNOP) { 1245 std::string ISA = hasMips64r6() ? "MIPS64r6" : "MIPS32r6"; 1246 Warning(IDLoc, "ssnop is deprecated for " + ISA + " and is equivalent to a " 1247 "nop instruction"); 1248 } 1249 1250 if (hasCnMips()) { 1251 const unsigned Opcode = Inst.getOpcode(); 1252 MCOperand Opnd; 1253 int Imm; 1254 1255 switch (Opcode) { 1256 default: 1257 break; 1258 1259 case Mips::BBIT0: 1260 case Mips::BBIT032: 1261 case Mips::BBIT1: 1262 case Mips::BBIT132: 1263 assert(MCID.getNumOperands() == 3 && "unexpected number of operands"); 1264 // The offset is handled above 1265 Opnd = Inst.getOperand(1); 1266 if (!Opnd.isImm()) 1267 return Error(IDLoc, "expected immediate operand kind"); 1268 Imm = Opnd.getImm(); 1269 if (Imm < 0 || Imm > (Opcode == Mips::BBIT0 || 1270 Opcode == Mips::BBIT1 ? 63 : 31)) 1271 return Error(IDLoc, "immediate operand value out of range"); 1272 if (Imm > 31) { 1273 Inst.setOpcode(Opcode == Mips::BBIT0 ? Mips::BBIT032 1274 : Mips::BBIT132); 1275 Inst.getOperand(1).setImm(Imm - 32); 1276 } 1277 break; 1278 1279 case Mips::CINS: 1280 case Mips::CINS32: 1281 case Mips::EXTS: 1282 case Mips::EXTS32: 1283 assert(MCID.getNumOperands() == 4 && "unexpected number of operands"); 1284 // Check length 1285 Opnd = Inst.getOperand(3); 1286 if (!Opnd.isImm()) 1287 return Error(IDLoc, "expected immediate operand kind"); 1288 Imm = Opnd.getImm(); 1289 if (Imm < 0 || Imm > 31) 1290 return Error(IDLoc, "immediate operand value out of range"); 1291 // Check position 1292 Opnd = Inst.getOperand(2); 1293 if (!Opnd.isImm()) 1294 return Error(IDLoc, "expected immediate operand kind"); 1295 Imm = Opnd.getImm(); 1296 if (Imm < 0 || Imm > (Opcode == Mips::CINS || 1297 Opcode == Mips::EXTS ? 63 : 31)) 1298 return Error(IDLoc, "immediate operand value out of range"); 1299 if (Imm > 31) { 1300 Inst.setOpcode(Opcode == Mips::CINS ? Mips::CINS32 : Mips::EXTS32); 1301 Inst.getOperand(2).setImm(Imm - 32); 1302 } 1303 break; 1304 1305 case Mips::SEQi: 1306 case Mips::SNEi: 1307 assert(MCID.getNumOperands() == 3 && "unexpected number of operands"); 1308 Opnd = Inst.getOperand(2); 1309 if (!Opnd.isImm()) 1310 return Error(IDLoc, "expected immediate operand kind"); 1311 Imm = Opnd.getImm(); 1312 if (!isInt<10>(Imm)) 1313 return Error(IDLoc, "immediate operand value out of range"); 1314 break; 1315 } 1316 } 1317 1318 if (MCID.hasDelaySlot() && AssemblerOptions.back()->isReorder()) { 1319 // If this instruction has a delay slot and .set reorder is active, 1320 // emit a NOP after it. 1321 Instructions.push_back(Inst); 1322 MCInst NopInst; 1323 if (hasShortDelaySlot(Inst.getOpcode())) { 1324 NopInst.setOpcode(Mips::MOVE16_MM); 1325 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1326 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1327 } else { 1328 NopInst.setOpcode(Mips::SLL); 1329 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1330 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1331 NopInst.addOperand(MCOperand::CreateImm(0)); 1332 } 1333 Instructions.push_back(NopInst); 1334 return false; 1335 } 1336 1337 if (MCID.mayLoad() || MCID.mayStore()) { 1338 // Check the offset of memory operand, if it is a symbol 1339 // reference or immediate we may have to expand instructions. 1340 for (unsigned i = 0; i < MCID.getNumOperands(); i++) { 1341 const MCOperandInfo &OpInfo = MCID.OpInfo[i]; 1342 if ((OpInfo.OperandType == MCOI::OPERAND_MEMORY) || 1343 (OpInfo.OperandType == MCOI::OPERAND_UNKNOWN)) { 1344 MCOperand &Op = Inst.getOperand(i); 1345 if (Op.isImm()) { 1346 int MemOffset = Op.getImm(); 1347 if (MemOffset < -32768 || MemOffset > 32767) { 1348 // Offset can't exceed 16bit value. 1349 expandMemInst(Inst, IDLoc, Instructions, MCID.mayLoad(), true); 1350 return false; 1351 } 1352 } else if (Op.isExpr()) { 1353 const MCExpr *Expr = Op.getExpr(); 1354 if (Expr->getKind() == MCExpr::SymbolRef) { 1355 const MCSymbolRefExpr *SR = 1356 static_cast<const MCSymbolRefExpr *>(Expr); 1357 if (SR->getKind() == MCSymbolRefExpr::VK_None) { 1358 // Expand symbol. 1359 expandMemInst(Inst, IDLoc, Instructions, MCID.mayLoad(), false); 1360 return false; 1361 } 1362 } else if (!isEvaluated(Expr)) { 1363 expandMemInst(Inst, IDLoc, Instructions, MCID.mayLoad(), false); 1364 return false; 1365 } 1366 } 1367 } 1368 } // for 1369 } // if load/store 1370 1371 if (inMicroMipsMode()) { 1372 if (MCID.mayLoad()) { 1373 // Try to create 16-bit GP relative load instruction. 1374 for (unsigned i = 0; i < MCID.getNumOperands(); i++) { 1375 const MCOperandInfo &OpInfo = MCID.OpInfo[i]; 1376 if ((OpInfo.OperandType == MCOI::OPERAND_MEMORY) || 1377 (OpInfo.OperandType == MCOI::OPERAND_UNKNOWN)) { 1378 MCOperand &Op = Inst.getOperand(i); 1379 if (Op.isImm()) { 1380 int MemOffset = Op.getImm(); 1381 MCOperand &DstReg = Inst.getOperand(0); 1382 MCOperand &BaseReg = Inst.getOperand(1); 1383 if (isIntN(9, MemOffset) && (MemOffset % 4 == 0) && 1384 getContext().getRegisterInfo()->getRegClass( 1385 Mips::GPRMM16RegClassID).contains(DstReg.getReg()) && 1386 BaseReg.getReg() == Mips::GP) { 1387 MCInst TmpInst; 1388 TmpInst.setLoc(IDLoc); 1389 TmpInst.setOpcode(Mips::LWGP_MM); 1390 TmpInst.addOperand(MCOperand::CreateReg(DstReg.getReg())); 1391 TmpInst.addOperand(MCOperand::CreateReg(Mips::GP)); 1392 TmpInst.addOperand(MCOperand::CreateImm(MemOffset)); 1393 Instructions.push_back(TmpInst); 1394 return false; 1395 } 1396 } 1397 } 1398 } // for 1399 } // if load 1400 1401 // TODO: Handle this with the AsmOperandClass.PredicateMethod. 1402 1403 MCOperand Opnd; 1404 int Imm; 1405 1406 switch (Inst.getOpcode()) { 1407 default: 1408 break; 1409 case Mips::ADDIUS5_MM: 1410 Opnd = Inst.getOperand(2); 1411 if (!Opnd.isImm()) 1412 return Error(IDLoc, "expected immediate operand kind"); 1413 Imm = Opnd.getImm(); 1414 if (Imm < -8 || Imm > 7) 1415 return Error(IDLoc, "immediate operand value out of range"); 1416 break; 1417 case Mips::ADDIUSP_MM: 1418 Opnd = Inst.getOperand(0); 1419 if (!Opnd.isImm()) 1420 return Error(IDLoc, "expected immediate operand kind"); 1421 Imm = Opnd.getImm(); 1422 if (Imm < -1032 || Imm > 1028 || (Imm < 8 && Imm > -12) || 1423 Imm % 4 != 0) 1424 return Error(IDLoc, "immediate operand value out of range"); 1425 break; 1426 case Mips::SLL16_MM: 1427 case Mips::SRL16_MM: 1428 Opnd = Inst.getOperand(2); 1429 if (!Opnd.isImm()) 1430 return Error(IDLoc, "expected immediate operand kind"); 1431 Imm = Opnd.getImm(); 1432 if (Imm < 1 || Imm > 8) 1433 return Error(IDLoc, "immediate operand value out of range"); 1434 break; 1435 case Mips::LI16_MM: 1436 Opnd = Inst.getOperand(1); 1437 if (!Opnd.isImm()) 1438 return Error(IDLoc, "expected immediate operand kind"); 1439 Imm = Opnd.getImm(); 1440 if (Imm < -1 || Imm > 126) 1441 return Error(IDLoc, "immediate operand value out of range"); 1442 break; 1443 case Mips::ADDIUR2_MM: 1444 Opnd = Inst.getOperand(2); 1445 if (!Opnd.isImm()) 1446 return Error(IDLoc, "expected immediate operand kind"); 1447 Imm = Opnd.getImm(); 1448 if (!(Imm == 1 || Imm == -1 || 1449 ((Imm % 4 == 0) && Imm < 28 && Imm > 0))) 1450 return Error(IDLoc, "immediate operand value out of range"); 1451 break; 1452 case Mips::ADDIUR1SP_MM: 1453 Opnd = Inst.getOperand(1); 1454 if (!Opnd.isImm()) 1455 return Error(IDLoc, "expected immediate operand kind"); 1456 Imm = Opnd.getImm(); 1457 if (OffsetToAlignment(Imm, 4LL)) 1458 return Error(IDLoc, "misaligned immediate operand value"); 1459 if (Imm < 0 || Imm > 255) 1460 return Error(IDLoc, "immediate operand value out of range"); 1461 break; 1462 case Mips::ANDI16_MM: 1463 Opnd = Inst.getOperand(2); 1464 if (!Opnd.isImm()) 1465 return Error(IDLoc, "expected immediate operand kind"); 1466 Imm = Opnd.getImm(); 1467 if (!(Imm == 128 || (Imm >= 1 && Imm <= 4) || Imm == 7 || Imm == 8 || 1468 Imm == 15 || Imm == 16 || Imm == 31 || Imm == 32 || Imm == 63 || 1469 Imm == 64 || Imm == 255 || Imm == 32768 || Imm == 65535)) 1470 return Error(IDLoc, "immediate operand value out of range"); 1471 break; 1472 case Mips::LBU16_MM: 1473 Opnd = Inst.getOperand(2); 1474 if (!Opnd.isImm()) 1475 return Error(IDLoc, "expected immediate operand kind"); 1476 Imm = Opnd.getImm(); 1477 if (Imm < -1 || Imm > 14) 1478 return Error(IDLoc, "immediate operand value out of range"); 1479 break; 1480 case Mips::SB16_MM: 1481 Opnd = Inst.getOperand(2); 1482 if (!Opnd.isImm()) 1483 return Error(IDLoc, "expected immediate operand kind"); 1484 Imm = Opnd.getImm(); 1485 if (Imm < 0 || Imm > 15) 1486 return Error(IDLoc, "immediate operand value out of range"); 1487 break; 1488 case Mips::LHU16_MM: 1489 case Mips::SH16_MM: 1490 Opnd = Inst.getOperand(2); 1491 if (!Opnd.isImm()) 1492 return Error(IDLoc, "expected immediate operand kind"); 1493 Imm = Opnd.getImm(); 1494 if (Imm < 0 || Imm > 30 || (Imm % 2 != 0)) 1495 return Error(IDLoc, "immediate operand value out of range"); 1496 break; 1497 case Mips::LW16_MM: 1498 case Mips::SW16_MM: 1499 Opnd = Inst.getOperand(2); 1500 if (!Opnd.isImm()) 1501 return Error(IDLoc, "expected immediate operand kind"); 1502 Imm = Opnd.getImm(); 1503 if (Imm < 0 || Imm > 60 || (Imm % 4 != 0)) 1504 return Error(IDLoc, "immediate operand value out of range"); 1505 break; 1506 case Mips::CACHE: 1507 case Mips::PREF: 1508 Opnd = Inst.getOperand(2); 1509 if (!Opnd.isImm()) 1510 return Error(IDLoc, "expected immediate operand kind"); 1511 Imm = Opnd.getImm(); 1512 if (!isUInt<5>(Imm)) 1513 return Error(IDLoc, "immediate operand value out of range"); 1514 break; 1515 case Mips::ADDIUPC_MM: 1516 MCOperand Opnd = Inst.getOperand(1); 1517 if (!Opnd.isImm()) 1518 return Error(IDLoc, "expected immediate operand kind"); 1519 int Imm = Opnd.getImm(); 1520 if ((Imm % 4 != 0) || !isIntN(25, Imm)) 1521 return Error(IDLoc, "immediate operand value out of range"); 1522 break; 1523 } 1524 } 1525 1526 if (needsExpansion(Inst)) 1527 return expandInstruction(Inst, IDLoc, Instructions); 1528 else 1529 Instructions.push_back(Inst); 1530 1531 return false; 1532 } 1533 1534 bool MipsAsmParser::needsExpansion(MCInst &Inst) { 1535 1536 switch (Inst.getOpcode()) { 1537 case Mips::LoadImm32Reg: 1538 case Mips::LoadAddr32Imm: 1539 case Mips::LoadAddr32Reg: 1540 case Mips::LoadImm64Reg: 1541 case Mips::B_MM_Pseudo: 1542 case Mips::LWM_MM: 1543 case Mips::SWM_MM: 1544 case Mips::JalOneReg: 1545 case Mips::JalTwoReg: 1546 return true; 1547 default: 1548 return false; 1549 } 1550 } 1551 1552 bool MipsAsmParser::expandInstruction(MCInst &Inst, SMLoc IDLoc, 1553 SmallVectorImpl<MCInst> &Instructions) { 1554 switch (Inst.getOpcode()) { 1555 default: llvm_unreachable("unimplemented expansion"); 1556 case Mips::LoadImm32Reg: 1557 return expandLoadImm(Inst, IDLoc, Instructions); 1558 case Mips::LoadImm64Reg: 1559 if (!isGP64bit()) { 1560 Error(IDLoc, "instruction requires a 64-bit architecture"); 1561 return true; 1562 } 1563 return expandLoadImm(Inst, IDLoc, Instructions); 1564 case Mips::LoadAddr32Imm: 1565 return expandLoadAddressImm(Inst, IDLoc, Instructions); 1566 case Mips::LoadAddr32Reg: 1567 return expandLoadAddressReg(Inst, IDLoc, Instructions); 1568 case Mips::B_MM_Pseudo: 1569 return expandUncondBranchMMPseudo(Inst, IDLoc, Instructions); 1570 case Mips::SWM_MM: 1571 case Mips::LWM_MM: 1572 return expandLoadStoreMultiple(Inst, IDLoc, Instructions); 1573 case Mips::JalOneReg: 1574 case Mips::JalTwoReg: 1575 return expandJalWithRegs(Inst, IDLoc, Instructions); 1576 } 1577 } 1578 1579 namespace { 1580 template <bool PerformShift> 1581 void createShiftOr(MCOperand Operand, unsigned RegNo, SMLoc IDLoc, 1582 SmallVectorImpl<MCInst> &Instructions) { 1583 MCInst tmpInst; 1584 if (PerformShift) { 1585 tmpInst.setOpcode(Mips::DSLL); 1586 tmpInst.addOperand(MCOperand::CreateReg(RegNo)); 1587 tmpInst.addOperand(MCOperand::CreateReg(RegNo)); 1588 tmpInst.addOperand(MCOperand::CreateImm(16)); 1589 tmpInst.setLoc(IDLoc); 1590 Instructions.push_back(tmpInst); 1591 tmpInst.clear(); 1592 } 1593 tmpInst.setOpcode(Mips::ORi); 1594 tmpInst.addOperand(MCOperand::CreateReg(RegNo)); 1595 tmpInst.addOperand(MCOperand::CreateReg(RegNo)); 1596 tmpInst.addOperand(Operand); 1597 tmpInst.setLoc(IDLoc); 1598 Instructions.push_back(tmpInst); 1599 } 1600 1601 template <int Shift, bool PerformShift> 1602 void createShiftOr(int64_t Value, unsigned RegNo, SMLoc IDLoc, 1603 SmallVectorImpl<MCInst> &Instructions) { 1604 createShiftOr<PerformShift>( 1605 MCOperand::CreateImm(((Value & (0xffffLL << Shift)) >> Shift)), RegNo, 1606 IDLoc, Instructions); 1607 } 1608 } 1609 1610 bool MipsAsmParser::expandJalWithRegs(MCInst &Inst, SMLoc IDLoc, 1611 SmallVectorImpl<MCInst> &Instructions) { 1612 // Create a JALR instruction which is going to replace the pseudo-JAL. 1613 MCInst JalrInst; 1614 JalrInst.setLoc(IDLoc); 1615 const MCOperand FirstRegOp = Inst.getOperand(0); 1616 const unsigned Opcode = Inst.getOpcode(); 1617 1618 if (Opcode == Mips::JalOneReg) { 1619 // jal $rs => jalr $rs 1620 if (inMicroMipsMode()) { 1621 JalrInst.setOpcode(Mips::JALR16_MM); 1622 JalrInst.addOperand(FirstRegOp); 1623 } else { 1624 JalrInst.setOpcode(Mips::JALR); 1625 JalrInst.addOperand(MCOperand::CreateReg(Mips::RA)); 1626 JalrInst.addOperand(FirstRegOp); 1627 } 1628 } else if (Opcode == Mips::JalTwoReg) { 1629 // jal $rd, $rs => jalr $rd, $rs 1630 JalrInst.setOpcode(inMicroMipsMode() ? Mips::JALR_MM : Mips::JALR); 1631 JalrInst.addOperand(FirstRegOp); 1632 const MCOperand SecondRegOp = Inst.getOperand(1); 1633 JalrInst.addOperand(SecondRegOp); 1634 } 1635 Instructions.push_back(JalrInst); 1636 1637 // If .set reorder is active, emit a NOP after it. 1638 if (AssemblerOptions.back()->isReorder()) { 1639 // This is a 32-bit NOP because these 2 pseudo-instructions 1640 // do not have a short delay slot. 1641 MCInst NopInst; 1642 NopInst.setOpcode(Mips::SLL); 1643 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1644 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1645 NopInst.addOperand(MCOperand::CreateImm(0)); 1646 Instructions.push_back(NopInst); 1647 } 1648 1649 return false; 1650 } 1651 1652 bool MipsAsmParser::expandLoadImm(MCInst &Inst, SMLoc IDLoc, 1653 SmallVectorImpl<MCInst> &Instructions) { 1654 MCInst tmpInst; 1655 const MCOperand &ImmOp = Inst.getOperand(1); 1656 assert(ImmOp.isImm() && "expected immediate operand kind"); 1657 const MCOperand &RegOp = Inst.getOperand(0); 1658 assert(RegOp.isReg() && "expected register operand kind"); 1659 1660 int64_t ImmValue = ImmOp.getImm(); 1661 tmpInst.setLoc(IDLoc); 1662 // FIXME: gas has a special case for values that are 000...1111, which 1663 // becomes a li -1 and then a dsrl 1664 if (0 <= ImmValue && ImmValue <= 65535) { 1665 // For 0 <= j <= 65535. 1666 // li d,j => ori d,$zero,j 1667 tmpInst.setOpcode(Mips::ORi); 1668 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1669 tmpInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1670 tmpInst.addOperand(MCOperand::CreateImm(ImmValue)); 1671 Instructions.push_back(tmpInst); 1672 } else if (ImmValue < 0 && ImmValue >= -32768) { 1673 // For -32768 <= j < 0. 1674 // li d,j => addiu d,$zero,j 1675 tmpInst.setOpcode(Mips::ADDiu); 1676 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1677 tmpInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1678 tmpInst.addOperand(MCOperand::CreateImm(ImmValue)); 1679 Instructions.push_back(tmpInst); 1680 } else if ((ImmValue & 0xffffffff) == ImmValue) { 1681 // For any value of j that is representable as a 32-bit integer, create 1682 // a sequence of: 1683 // li d,j => lui d,hi16(j) 1684 // ori d,d,lo16(j) 1685 tmpInst.setOpcode(Mips::LUi); 1686 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1687 tmpInst.addOperand(MCOperand::CreateImm((ImmValue & 0xffff0000) >> 16)); 1688 Instructions.push_back(tmpInst); 1689 createShiftOr<0, false>(ImmValue, RegOp.getReg(), IDLoc, Instructions); 1690 } else if ((ImmValue & (0xffffLL << 48)) == 0) { 1691 if (!isGP64bit()) { 1692 Error(IDLoc, "instruction requires a 64-bit architecture"); 1693 return true; 1694 } 1695 1696 // <------- lo32 ------> 1697 // <------- hi32 ------> 1698 // <- hi16 -> <- lo16 -> 1699 // _________________________________ 1700 // | | | | 1701 // | 16-bytes | 16-bytes | 16-bytes | 1702 // |__________|__________|__________| 1703 // 1704 // For any value of j that is representable as a 48-bit integer, create 1705 // a sequence of: 1706 // li d,j => lui d,hi16(j) 1707 // ori d,d,hi16(lo32(j)) 1708 // dsll d,d,16 1709 // ori d,d,lo16(lo32(j)) 1710 tmpInst.setOpcode(Mips::LUi); 1711 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1712 tmpInst.addOperand( 1713 MCOperand::CreateImm((ImmValue & (0xffffLL << 32)) >> 32)); 1714 Instructions.push_back(tmpInst); 1715 createShiftOr<16, false>(ImmValue, RegOp.getReg(), IDLoc, Instructions); 1716 createShiftOr<0, true>(ImmValue, RegOp.getReg(), IDLoc, Instructions); 1717 } else { 1718 if (!isGP64bit()) { 1719 Error(IDLoc, "instruction requires a 64-bit architecture"); 1720 return true; 1721 } 1722 1723 // <------- hi32 ------> <------- lo32 ------> 1724 // <- hi16 -> <- lo16 -> 1725 // ___________________________________________ 1726 // | | | | | 1727 // | 16-bytes | 16-bytes | 16-bytes | 16-bytes | 1728 // |__________|__________|__________|__________| 1729 // 1730 // For any value of j that isn't representable as a 48-bit integer. 1731 // li d,j => lui d,hi16(j) 1732 // ori d,d,lo16(hi32(j)) 1733 // dsll d,d,16 1734 // ori d,d,hi16(lo32(j)) 1735 // dsll d,d,16 1736 // ori d,d,lo16(lo32(j)) 1737 tmpInst.setOpcode(Mips::LUi); 1738 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1739 tmpInst.addOperand( 1740 MCOperand::CreateImm((ImmValue & (0xffffLL << 48)) >> 48)); 1741 Instructions.push_back(tmpInst); 1742 createShiftOr<32, false>(ImmValue, RegOp.getReg(), IDLoc, Instructions); 1743 createShiftOr<16, true>(ImmValue, RegOp.getReg(), IDLoc, Instructions); 1744 createShiftOr<0, true>(ImmValue, RegOp.getReg(), IDLoc, Instructions); 1745 } 1746 return false; 1747 } 1748 1749 bool 1750 MipsAsmParser::expandLoadAddressReg(MCInst &Inst, SMLoc IDLoc, 1751 SmallVectorImpl<MCInst> &Instructions) { 1752 MCInst tmpInst; 1753 const MCOperand &ImmOp = Inst.getOperand(2); 1754 assert((ImmOp.isImm() || ImmOp.isExpr()) && 1755 "expected immediate operand kind"); 1756 if (!ImmOp.isImm()) { 1757 expandLoadAddressSym(Inst, IDLoc, Instructions); 1758 return false; 1759 } 1760 const MCOperand &SrcRegOp = Inst.getOperand(1); 1761 assert(SrcRegOp.isReg() && "expected register operand kind"); 1762 const MCOperand &DstRegOp = Inst.getOperand(0); 1763 assert(DstRegOp.isReg() && "expected register operand kind"); 1764 int ImmValue = ImmOp.getImm(); 1765 if (-32768 <= ImmValue && ImmValue <= 65535) { 1766 // For -32768 <= j <= 65535. 1767 // la d,j(s) => addiu d,s,j 1768 tmpInst.setOpcode(Mips::ADDiu); 1769 tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg())); 1770 tmpInst.addOperand(MCOperand::CreateReg(SrcRegOp.getReg())); 1771 tmpInst.addOperand(MCOperand::CreateImm(ImmValue)); 1772 Instructions.push_back(tmpInst); 1773 } else { 1774 // For any other value of j that is representable as a 32-bit integer. 1775 // la d,j(s) => lui d,hi16(j) 1776 // ori d,d,lo16(j) 1777 // addu d,d,s 1778 tmpInst.setOpcode(Mips::LUi); 1779 tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg())); 1780 tmpInst.addOperand(MCOperand::CreateImm((ImmValue & 0xffff0000) >> 16)); 1781 Instructions.push_back(tmpInst); 1782 tmpInst.clear(); 1783 tmpInst.setOpcode(Mips::ORi); 1784 tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg())); 1785 tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg())); 1786 tmpInst.addOperand(MCOperand::CreateImm(ImmValue & 0xffff)); 1787 Instructions.push_back(tmpInst); 1788 tmpInst.clear(); 1789 tmpInst.setOpcode(Mips::ADDu); 1790 tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg())); 1791 tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg())); 1792 tmpInst.addOperand(MCOperand::CreateReg(SrcRegOp.getReg())); 1793 Instructions.push_back(tmpInst); 1794 } 1795 return false; 1796 } 1797 1798 bool 1799 MipsAsmParser::expandLoadAddressImm(MCInst &Inst, SMLoc IDLoc, 1800 SmallVectorImpl<MCInst> &Instructions) { 1801 MCInst tmpInst; 1802 const MCOperand &ImmOp = Inst.getOperand(1); 1803 assert((ImmOp.isImm() || ImmOp.isExpr()) && 1804 "expected immediate operand kind"); 1805 if (!ImmOp.isImm()) { 1806 expandLoadAddressSym(Inst, IDLoc, Instructions); 1807 return false; 1808 } 1809 const MCOperand &RegOp = Inst.getOperand(0); 1810 assert(RegOp.isReg() && "expected register operand kind"); 1811 int ImmValue = ImmOp.getImm(); 1812 if (-32768 <= ImmValue && ImmValue <= 65535) { 1813 // For -32768 <= j <= 65535. 1814 // la d,j => addiu d,$zero,j 1815 tmpInst.setOpcode(Mips::ADDiu); 1816 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1817 tmpInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1818 tmpInst.addOperand(MCOperand::CreateImm(ImmValue)); 1819 Instructions.push_back(tmpInst); 1820 } else { 1821 // For any other value of j that is representable as a 32-bit integer. 1822 // la d,j => lui d,hi16(j) 1823 // ori d,d,lo16(j) 1824 tmpInst.setOpcode(Mips::LUi); 1825 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1826 tmpInst.addOperand(MCOperand::CreateImm((ImmValue & 0xffff0000) >> 16)); 1827 Instructions.push_back(tmpInst); 1828 tmpInst.clear(); 1829 tmpInst.setOpcode(Mips::ORi); 1830 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1831 tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg())); 1832 tmpInst.addOperand(MCOperand::CreateImm(ImmValue & 0xffff)); 1833 Instructions.push_back(tmpInst); 1834 } 1835 return false; 1836 } 1837 1838 void 1839 MipsAsmParser::expandLoadAddressSym(MCInst &Inst, SMLoc IDLoc, 1840 SmallVectorImpl<MCInst> &Instructions) { 1841 // FIXME: If we do have a valid at register to use, we should generate a 1842 // slightly shorter sequence here. 1843 MCInst tmpInst; 1844 int ExprOperandNo = 1; 1845 // Sometimes the assembly parser will get the immediate expression as 1846 // a $zero + an immediate. 1847 if (Inst.getNumOperands() == 3) { 1848 assert(Inst.getOperand(1).getReg() == 1849 (isGP64bit() ? Mips::ZERO_64 : Mips::ZERO)); 1850 ExprOperandNo = 2; 1851 } 1852 const MCOperand &SymOp = Inst.getOperand(ExprOperandNo); 1853 assert(SymOp.isExpr() && "expected symbol operand kind"); 1854 const MCOperand &RegOp = Inst.getOperand(0); 1855 unsigned RegNo = RegOp.getReg(); 1856 const MCSymbolRefExpr *Symbol = cast<MCSymbolRefExpr>(SymOp.getExpr()); 1857 const MCSymbolRefExpr *HiExpr = 1858 MCSymbolRefExpr::Create(Symbol->getSymbol().getName(), 1859 MCSymbolRefExpr::VK_Mips_ABS_HI, getContext()); 1860 const MCSymbolRefExpr *LoExpr = 1861 MCSymbolRefExpr::Create(Symbol->getSymbol().getName(), 1862 MCSymbolRefExpr::VK_Mips_ABS_LO, getContext()); 1863 if (isGP64bit()) { 1864 // If it's a 64-bit architecture, expand to: 1865 // la d,sym => lui d,highest(sym) 1866 // ori d,d,higher(sym) 1867 // dsll d,d,16 1868 // ori d,d,hi16(sym) 1869 // dsll d,d,16 1870 // ori d,d,lo16(sym) 1871 const MCSymbolRefExpr *HighestExpr = 1872 MCSymbolRefExpr::Create(Symbol->getSymbol().getName(), 1873 MCSymbolRefExpr::VK_Mips_HIGHEST, getContext()); 1874 const MCSymbolRefExpr *HigherExpr = 1875 MCSymbolRefExpr::Create(Symbol->getSymbol().getName(), 1876 MCSymbolRefExpr::VK_Mips_HIGHER, getContext()); 1877 1878 tmpInst.setOpcode(Mips::LUi); 1879 tmpInst.addOperand(MCOperand::CreateReg(RegNo)); 1880 tmpInst.addOperand(MCOperand::CreateExpr(HighestExpr)); 1881 Instructions.push_back(tmpInst); 1882 1883 createShiftOr<false>(MCOperand::CreateExpr(HigherExpr), RegNo, SMLoc(), 1884 Instructions); 1885 createShiftOr<true>(MCOperand::CreateExpr(HiExpr), RegNo, SMLoc(), 1886 Instructions); 1887 createShiftOr<true>(MCOperand::CreateExpr(LoExpr), RegNo, SMLoc(), 1888 Instructions); 1889 } else { 1890 // Otherwise, expand to: 1891 // la d,sym => lui d,hi16(sym) 1892 // ori d,d,lo16(sym) 1893 tmpInst.setOpcode(Mips::LUi); 1894 tmpInst.addOperand(MCOperand::CreateReg(RegNo)); 1895 tmpInst.addOperand(MCOperand::CreateExpr(HiExpr)); 1896 Instructions.push_back(tmpInst); 1897 1898 createShiftOr<false>(MCOperand::CreateExpr(LoExpr), RegNo, SMLoc(), 1899 Instructions); 1900 } 1901 } 1902 1903 bool MipsAsmParser::expandUncondBranchMMPseudo( 1904 MCInst &Inst, SMLoc IDLoc, SmallVectorImpl<MCInst> &Instructions) { 1905 assert(getInstDesc(Inst.getOpcode()).getNumOperands() == 1 && 1906 "unexpected number of operands"); 1907 1908 MCOperand Offset = Inst.getOperand(0); 1909 if (Offset.isExpr()) { 1910 Inst.clear(); 1911 Inst.setOpcode(Mips::BEQ_MM); 1912 Inst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1913 Inst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1914 Inst.addOperand(MCOperand::CreateExpr(Offset.getExpr())); 1915 } else { 1916 assert(Offset.isImm() && "expected immediate operand kind"); 1917 if (isIntN(11, Offset.getImm())) { 1918 // If offset fits into 11 bits then this instruction becomes microMIPS 1919 // 16-bit unconditional branch instruction. 1920 Inst.setOpcode(Mips::B16_MM); 1921 } else { 1922 if (!isIntN(17, Offset.getImm())) 1923 Error(IDLoc, "branch target out of range"); 1924 if (OffsetToAlignment(Offset.getImm(), 1LL << 1)) 1925 Error(IDLoc, "branch to misaligned address"); 1926 Inst.clear(); 1927 Inst.setOpcode(Mips::BEQ_MM); 1928 Inst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1929 Inst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1930 Inst.addOperand(MCOperand::CreateImm(Offset.getImm())); 1931 } 1932 } 1933 Instructions.push_back(Inst); 1934 1935 if (AssemblerOptions.back()->isReorder()) { 1936 // If .set reorder is active, emit a NOP after the branch instruction. 1937 MCInst NopInst; 1938 NopInst.setOpcode(Mips::MOVE16_MM); 1939 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1940 NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO)); 1941 Instructions.push_back(NopInst); 1942 } 1943 return false; 1944 } 1945 1946 void MipsAsmParser::expandMemInst(MCInst &Inst, SMLoc IDLoc, 1947 SmallVectorImpl<MCInst> &Instructions, 1948 bool isLoad, bool isImmOpnd) { 1949 const MCSymbolRefExpr *SR; 1950 MCInst TempInst; 1951 unsigned ImmOffset, HiOffset, LoOffset; 1952 const MCExpr *ExprOffset; 1953 unsigned TmpRegNum; 1954 // 1st operand is either the source or destination register. 1955 assert(Inst.getOperand(0).isReg() && "expected register operand kind"); 1956 unsigned RegOpNum = Inst.getOperand(0).getReg(); 1957 // 2nd operand is the base register. 1958 assert(Inst.getOperand(1).isReg() && "expected register operand kind"); 1959 unsigned BaseRegNum = Inst.getOperand(1).getReg(); 1960 // 3rd operand is either an immediate or expression. 1961 if (isImmOpnd) { 1962 assert(Inst.getOperand(2).isImm() && "expected immediate operand kind"); 1963 ImmOffset = Inst.getOperand(2).getImm(); 1964 LoOffset = ImmOffset & 0x0000ffff; 1965 HiOffset = (ImmOffset & 0xffff0000) >> 16; 1966 // If msb of LoOffset is 1(negative number) we must increment HiOffset. 1967 if (LoOffset & 0x8000) 1968 HiOffset++; 1969 } else 1970 ExprOffset = Inst.getOperand(2).getExpr(); 1971 // All instructions will have the same location. 1972 TempInst.setLoc(IDLoc); 1973 // These are some of the types of expansions we perform here: 1974 // 1) lw $8, sym => lui $8, %hi(sym) 1975 // lw $8, %lo(sym)($8) 1976 // 2) lw $8, offset($9) => lui $8, %hi(offset) 1977 // add $8, $8, $9 1978 // lw $8, %lo(offset)($9) 1979 // 3) lw $8, offset($8) => lui $at, %hi(offset) 1980 // add $at, $at, $8 1981 // lw $8, %lo(offset)($at) 1982 // 4) sw $8, sym => lui $at, %hi(sym) 1983 // sw $8, %lo(sym)($at) 1984 // 5) sw $8, offset($8) => lui $at, %hi(offset) 1985 // add $at, $at, $8 1986 // sw $8, %lo(offset)($at) 1987 // 6) ldc1 $f0, sym => lui $at, %hi(sym) 1988 // ldc1 $f0, %lo(sym)($at) 1989 // 1990 // For load instructions we can use the destination register as a temporary 1991 // if base and dst are different (examples 1 and 2) and if the base register 1992 // is general purpose otherwise we must use $at (example 6) and error if it's 1993 // not available. For stores we must use $at (examples 4 and 5) because we 1994 // must not clobber the source register setting up the offset. 1995 const MCInstrDesc &Desc = getInstDesc(Inst.getOpcode()); 1996 int16_t RegClassOp0 = Desc.OpInfo[0].RegClass; 1997 unsigned RegClassIDOp0 = 1998 getContext().getRegisterInfo()->getRegClass(RegClassOp0).getID(); 1999 bool IsGPR = (RegClassIDOp0 == Mips::GPR32RegClassID) || 2000 (RegClassIDOp0 == Mips::GPR64RegClassID); 2001 if (isLoad && IsGPR && (BaseRegNum != RegOpNum)) 2002 TmpRegNum = RegOpNum; 2003 else { 2004 int AT = getATReg(IDLoc); 2005 // At this point we need AT to perform the expansions and we exit if it is 2006 // not available. 2007 if (!AT) 2008 return; 2009 TmpRegNum = getReg( 2010 (isGP64bit()) ? Mips::GPR64RegClassID : Mips::GPR32RegClassID, AT); 2011 } 2012 2013 TempInst.setOpcode(Mips::LUi); 2014 TempInst.addOperand(MCOperand::CreateReg(TmpRegNum)); 2015 if (isImmOpnd) 2016 TempInst.addOperand(MCOperand::CreateImm(HiOffset)); 2017 else { 2018 if (ExprOffset->getKind() == MCExpr::SymbolRef) { 2019 SR = static_cast<const MCSymbolRefExpr *>(ExprOffset); 2020 const MCSymbolRefExpr *HiExpr = MCSymbolRefExpr::Create( 2021 SR->getSymbol().getName(), MCSymbolRefExpr::VK_Mips_ABS_HI, 2022 getContext()); 2023 TempInst.addOperand(MCOperand::CreateExpr(HiExpr)); 2024 } else { 2025 const MCExpr *HiExpr = evaluateRelocExpr(ExprOffset, "hi"); 2026 TempInst.addOperand(MCOperand::CreateExpr(HiExpr)); 2027 } 2028 } 2029 // Add the instruction to the list. 2030 Instructions.push_back(TempInst); 2031 // Prepare TempInst for next instruction. 2032 TempInst.clear(); 2033 // Add temp register to base. 2034 TempInst.setOpcode(Mips::ADDu); 2035 TempInst.addOperand(MCOperand::CreateReg(TmpRegNum)); 2036 TempInst.addOperand(MCOperand::CreateReg(TmpRegNum)); 2037 TempInst.addOperand(MCOperand::CreateReg(BaseRegNum)); 2038 Instructions.push_back(TempInst); 2039 TempInst.clear(); 2040 // And finally, create original instruction with low part 2041 // of offset and new base. 2042 TempInst.setOpcode(Inst.getOpcode()); 2043 TempInst.addOperand(MCOperand::CreateReg(RegOpNum)); 2044 TempInst.addOperand(MCOperand::CreateReg(TmpRegNum)); 2045 if (isImmOpnd) 2046 TempInst.addOperand(MCOperand::CreateImm(LoOffset)); 2047 else { 2048 if (ExprOffset->getKind() == MCExpr::SymbolRef) { 2049 const MCSymbolRefExpr *LoExpr = MCSymbolRefExpr::Create( 2050 SR->getSymbol().getName(), MCSymbolRefExpr::VK_Mips_ABS_LO, 2051 getContext()); 2052 TempInst.addOperand(MCOperand::CreateExpr(LoExpr)); 2053 } else { 2054 const MCExpr *LoExpr = evaluateRelocExpr(ExprOffset, "lo"); 2055 TempInst.addOperand(MCOperand::CreateExpr(LoExpr)); 2056 } 2057 } 2058 Instructions.push_back(TempInst); 2059 TempInst.clear(); 2060 } 2061 2062 bool 2063 MipsAsmParser::expandLoadStoreMultiple(MCInst &Inst, SMLoc IDLoc, 2064 SmallVectorImpl<MCInst> &Instructions) { 2065 unsigned OpNum = Inst.getNumOperands(); 2066 unsigned Opcode = Inst.getOpcode(); 2067 unsigned NewOpcode = Opcode == Mips::SWM_MM ? Mips::SWM32_MM : Mips::LWM32_MM; 2068 2069 assert (Inst.getOperand(OpNum - 1).isImm() && 2070 Inst.getOperand(OpNum - 2).isReg() && 2071 Inst.getOperand(OpNum - 3).isReg() && "Invalid instruction operand."); 2072 2073 if (OpNum < 8 && Inst.getOperand(OpNum - 1).getImm() <= 60 && 2074 Inst.getOperand(OpNum - 1).getImm() >= 0 && 2075 Inst.getOperand(OpNum - 2).getReg() == Mips::SP && 2076 Inst.getOperand(OpNum - 3).getReg() == Mips::RA) 2077 // It can be implemented as SWM16 or LWM16 instruction. 2078 NewOpcode = Opcode == Mips::SWM_MM ? Mips::SWM16_MM : Mips::LWM16_MM; 2079 2080 Inst.setOpcode(NewOpcode); 2081 Instructions.push_back(Inst); 2082 return false; 2083 } 2084 2085 unsigned MipsAsmParser::checkTargetMatchPredicate(MCInst &Inst) { 2086 // As described by the Mips32r2 spec, the registers Rd and Rs for 2087 // jalr.hb must be different. 2088 unsigned Opcode = Inst.getOpcode(); 2089 2090 if (Opcode == Mips::JALR_HB && 2091 (Inst.getOperand(0).getReg() == Inst.getOperand(1).getReg())) 2092 return Match_RequiresDifferentSrcAndDst; 2093 2094 return Match_Success; 2095 } 2096 2097 bool MipsAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, 2098 OperandVector &Operands, 2099 MCStreamer &Out, 2100 uint64_t &ErrorInfo, 2101 bool MatchingInlineAsm) { 2102 2103 MCInst Inst; 2104 SmallVector<MCInst, 8> Instructions; 2105 unsigned MatchResult = 2106 MatchInstructionImpl(Operands, Inst, ErrorInfo, MatchingInlineAsm); 2107 2108 switch (MatchResult) { 2109 case Match_Success: { 2110 if (processInstruction(Inst, IDLoc, Instructions)) 2111 return true; 2112 for (unsigned i = 0; i < Instructions.size(); i++) 2113 Out.EmitInstruction(Instructions[i], STI); 2114 return false; 2115 } 2116 case Match_MissingFeature: 2117 Error(IDLoc, "instruction requires a CPU feature not currently enabled"); 2118 return true; 2119 case Match_InvalidOperand: { 2120 SMLoc ErrorLoc = IDLoc; 2121 if (ErrorInfo != ~0ULL) { 2122 if (ErrorInfo >= Operands.size()) 2123 return Error(IDLoc, "too few operands for instruction"); 2124 2125 ErrorLoc = ((MipsOperand &)*Operands[ErrorInfo]).getStartLoc(); 2126 if (ErrorLoc == SMLoc()) 2127 ErrorLoc = IDLoc; 2128 } 2129 2130 return Error(ErrorLoc, "invalid operand for instruction"); 2131 } 2132 case Match_MnemonicFail: 2133 return Error(IDLoc, "invalid instruction"); 2134 case Match_RequiresDifferentSrcAndDst: 2135 return Error(IDLoc, "source and destination must be different"); 2136 } 2137 2138 llvm_unreachable("Implement any new match types added!"); 2139 } 2140 2141 void MipsAsmParser::warnIfAssemblerTemporary(int RegIndex, SMLoc Loc) { 2142 if ((RegIndex != 0) && 2143 ((int)AssemblerOptions.back()->getATRegNum() == RegIndex)) { 2144 if (RegIndex == 1) 2145 Warning(Loc, "used $at without \".set noat\""); 2146 else 2147 Warning(Loc, Twine("used $") + Twine(RegIndex) + " with \".set at=$" + 2148 Twine(RegIndex) + "\""); 2149 } 2150 } 2151 2152 void 2153 MipsAsmParser::printWarningWithFixIt(const Twine &Msg, const Twine &FixMsg, 2154 SMRange Range, bool ShowColors) { 2155 getSourceManager().PrintMessage(Range.Start, SourceMgr::DK_Warning, Msg, 2156 Range, SMFixIt(Range, FixMsg), 2157 ShowColors); 2158 } 2159 2160 int MipsAsmParser::matchCPURegisterName(StringRef Name) { 2161 int CC; 2162 2163 CC = StringSwitch<unsigned>(Name) 2164 .Case("zero", 0) 2165 .Case("at", 1) 2166 .Case("a0", 4) 2167 .Case("a1", 5) 2168 .Case("a2", 6) 2169 .Case("a3", 7) 2170 .Case("v0", 2) 2171 .Case("v1", 3) 2172 .Case("s0", 16) 2173 .Case("s1", 17) 2174 .Case("s2", 18) 2175 .Case("s3", 19) 2176 .Case("s4", 20) 2177 .Case("s5", 21) 2178 .Case("s6", 22) 2179 .Case("s7", 23) 2180 .Case("k0", 26) 2181 .Case("k1", 27) 2182 .Case("gp", 28) 2183 .Case("sp", 29) 2184 .Case("fp", 30) 2185 .Case("s8", 30) 2186 .Case("ra", 31) 2187 .Case("t0", 8) 2188 .Case("t1", 9) 2189 .Case("t2", 10) 2190 .Case("t3", 11) 2191 .Case("t4", 12) 2192 .Case("t5", 13) 2193 .Case("t6", 14) 2194 .Case("t7", 15) 2195 .Case("t8", 24) 2196 .Case("t9", 25) 2197 .Default(-1); 2198 2199 if (!(isABI_N32() || isABI_N64())) 2200 return CC; 2201 2202 if (12 <= CC && CC <= 15) { 2203 // Name is one of t4-t7 2204 AsmToken RegTok = getLexer().peekTok(); 2205 SMRange RegRange = RegTok.getLocRange(); 2206 2207 StringRef FixedName = StringSwitch<StringRef>(Name) 2208 .Case("t4", "t0") 2209 .Case("t5", "t1") 2210 .Case("t6", "t2") 2211 .Case("t7", "t3") 2212 .Default(""); 2213 assert(FixedName != "" && "Register name is not one of t4-t7."); 2214 2215 printWarningWithFixIt("register names $t4-$t7 are only available in O32.", 2216 "Did you mean $" + FixedName + "?", RegRange); 2217 } 2218 2219 // Although SGI documentation just cuts out t0-t3 for n32/n64, 2220 // GNU pushes the values of t0-t3 to override the o32/o64 values for t4-t7 2221 // We are supporting both cases, so for t0-t3 we'll just push them to t4-t7. 2222 if (8 <= CC && CC <= 11) 2223 CC += 4; 2224 2225 if (CC == -1) 2226 CC = StringSwitch<unsigned>(Name) 2227 .Case("a4", 8) 2228 .Case("a5", 9) 2229 .Case("a6", 10) 2230 .Case("a7", 11) 2231 .Case("kt0", 26) 2232 .Case("kt1", 27) 2233 .Default(-1); 2234 2235 return CC; 2236 } 2237 2238 int MipsAsmParser::matchHWRegsRegisterName(StringRef Name) { 2239 int CC; 2240 2241 CC = StringSwitch<unsigned>(Name) 2242 .Case("hwr_cpunum", 0) 2243 .Case("hwr_synci_step", 1) 2244 .Case("hwr_cc", 2) 2245 .Case("hwr_ccres", 3) 2246 .Case("hwr_ulr", 29) 2247 .Default(-1); 2248 2249 return CC; 2250 } 2251 2252 int MipsAsmParser::matchFPURegisterName(StringRef Name) { 2253 2254 if (Name[0] == 'f') { 2255 StringRef NumString = Name.substr(1); 2256 unsigned IntVal; 2257 if (NumString.getAsInteger(10, IntVal)) 2258 return -1; // This is not an integer. 2259 if (IntVal > 31) // Maximum index for fpu register. 2260 return -1; 2261 return IntVal; 2262 } 2263 return -1; 2264 } 2265 2266 int MipsAsmParser::matchFCCRegisterName(StringRef Name) { 2267 2268 if (Name.startswith("fcc")) { 2269 StringRef NumString = Name.substr(3); 2270 unsigned IntVal; 2271 if (NumString.getAsInteger(10, IntVal)) 2272 return -1; // This is not an integer. 2273 if (IntVal > 7) // There are only 8 fcc registers. 2274 return -1; 2275 return IntVal; 2276 } 2277 return -1; 2278 } 2279 2280 int MipsAsmParser::matchACRegisterName(StringRef Name) { 2281 2282 if (Name.startswith("ac")) { 2283 StringRef NumString = Name.substr(2); 2284 unsigned IntVal; 2285 if (NumString.getAsInteger(10, IntVal)) 2286 return -1; // This is not an integer. 2287 if (IntVal > 3) // There are only 3 acc registers. 2288 return -1; 2289 return IntVal; 2290 } 2291 return -1; 2292 } 2293 2294 int MipsAsmParser::matchMSA128RegisterName(StringRef Name) { 2295 unsigned IntVal; 2296 2297 if (Name.front() != 'w' || Name.drop_front(1).getAsInteger(10, IntVal)) 2298 return -1; 2299 2300 if (IntVal > 31) 2301 return -1; 2302 2303 return IntVal; 2304 } 2305 2306 int MipsAsmParser::matchMSA128CtrlRegisterName(StringRef Name) { 2307 int CC; 2308 2309 CC = StringSwitch<unsigned>(Name) 2310 .Case("msair", 0) 2311 .Case("msacsr", 1) 2312 .Case("msaaccess", 2) 2313 .Case("msasave", 3) 2314 .Case("msamodify", 4) 2315 .Case("msarequest", 5) 2316 .Case("msamap", 6) 2317 .Case("msaunmap", 7) 2318 .Default(-1); 2319 2320 return CC; 2321 } 2322 2323 bool MipsAssemblerOptions::setATReg(unsigned Reg) { 2324 if (Reg > 31) 2325 return false; 2326 2327 ATReg = Reg; 2328 return true; 2329 } 2330 2331 int MipsAsmParser::getATReg(SMLoc Loc) { 2332 int AT = AssemblerOptions.back()->getATRegNum(); 2333 if (AT == 0) 2334 reportParseError(Loc, 2335 "pseudo-instruction requires $at, which is not available"); 2336 return AT; 2337 } 2338 2339 unsigned MipsAsmParser::getReg(int RC, int RegNo) { 2340 return *(getContext().getRegisterInfo()->getRegClass(RC).begin() + RegNo); 2341 } 2342 2343 unsigned MipsAsmParser::getGPR(int RegNo) { 2344 return getReg(isGP64bit() ? Mips::GPR64RegClassID : Mips::GPR32RegClassID, 2345 RegNo); 2346 } 2347 2348 int MipsAsmParser::matchRegisterByNumber(unsigned RegNum, unsigned RegClass) { 2349 if (RegNum > 2350 getContext().getRegisterInfo()->getRegClass(RegClass).getNumRegs() - 1) 2351 return -1; 2352 2353 return getReg(RegClass, RegNum); 2354 } 2355 2356 bool MipsAsmParser::parseOperand(OperandVector &Operands, StringRef Mnemonic) { 2357 MCAsmParser &Parser = getParser(); 2358 DEBUG(dbgs() << "parseOperand\n"); 2359 2360 // Check if the current operand has a custom associated parser, if so, try to 2361 // custom parse the operand, or fallback to the general approach. 2362 OperandMatchResultTy ResTy = MatchOperandParserImpl(Operands, Mnemonic); 2363 if (ResTy == MatchOperand_Success) 2364 return false; 2365 // If there wasn't a custom match, try the generic matcher below. Otherwise, 2366 // there was a match, but an error occurred, in which case, just return that 2367 // the operand parsing failed. 2368 if (ResTy == MatchOperand_ParseFail) 2369 return true; 2370 2371 DEBUG(dbgs() << ".. Generic Parser\n"); 2372 2373 switch (getLexer().getKind()) { 2374 default: 2375 Error(Parser.getTok().getLoc(), "unexpected token in operand"); 2376 return true; 2377 case AsmToken::Dollar: { 2378 // Parse the register. 2379 SMLoc S = Parser.getTok().getLoc(); 2380 2381 // Almost all registers have been parsed by custom parsers. There is only 2382 // one exception to this. $zero (and it's alias $0) will reach this point 2383 // for div, divu, and similar instructions because it is not an operand 2384 // to the instruction definition but an explicit register. Special case 2385 // this situation for now. 2386 if (parseAnyRegister(Operands) != MatchOperand_NoMatch) 2387 return false; 2388 2389 // Maybe it is a symbol reference. 2390 StringRef Identifier; 2391 if (Parser.parseIdentifier(Identifier)) 2392 return true; 2393 2394 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2395 MCSymbol *Sym = getContext().GetOrCreateSymbol("$" + Identifier); 2396 // Otherwise create a symbol reference. 2397 const MCExpr *Res = 2398 MCSymbolRefExpr::Create(Sym, MCSymbolRefExpr::VK_None, getContext()); 2399 2400 Operands.push_back(MipsOperand::CreateImm(Res, S, E, *this)); 2401 return false; 2402 } 2403 // Else drop to expression parsing. 2404 case AsmToken::LParen: 2405 case AsmToken::Minus: 2406 case AsmToken::Plus: 2407 case AsmToken::Integer: 2408 case AsmToken::Tilde: 2409 case AsmToken::String: { 2410 DEBUG(dbgs() << ".. generic integer\n"); 2411 OperandMatchResultTy ResTy = parseImm(Operands); 2412 return ResTy != MatchOperand_Success; 2413 } 2414 case AsmToken::Percent: { 2415 // It is a symbol reference or constant expression. 2416 const MCExpr *IdVal; 2417 SMLoc S = Parser.getTok().getLoc(); // Start location of the operand. 2418 if (parseRelocOperand(IdVal)) 2419 return true; 2420 2421 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2422 2423 Operands.push_back(MipsOperand::CreateImm(IdVal, S, E, *this)); 2424 return false; 2425 } // case AsmToken::Percent 2426 } // switch(getLexer().getKind()) 2427 return true; 2428 } 2429 2430 const MCExpr *MipsAsmParser::evaluateRelocExpr(const MCExpr *Expr, 2431 StringRef RelocStr) { 2432 const MCExpr *Res; 2433 // Check the type of the expression. 2434 if (const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(Expr)) { 2435 // It's a constant, evaluate reloc value. 2436 int16_t Val; 2437 switch (getVariantKind(RelocStr)) { 2438 case MCSymbolRefExpr::VK_Mips_ABS_LO: 2439 // Get the 1st 16-bits. 2440 Val = MCE->getValue() & 0xffff; 2441 break; 2442 case MCSymbolRefExpr::VK_Mips_ABS_HI: 2443 // Get the 2nd 16-bits. Also add 1 if bit 15 is 1, to compensate for low 2444 // 16 bits being negative. 2445 Val = ((MCE->getValue() + 0x8000) >> 16) & 0xffff; 2446 break; 2447 case MCSymbolRefExpr::VK_Mips_HIGHER: 2448 // Get the 3rd 16-bits. 2449 Val = ((MCE->getValue() + 0x80008000LL) >> 32) & 0xffff; 2450 break; 2451 case MCSymbolRefExpr::VK_Mips_HIGHEST: 2452 // Get the 4th 16-bits. 2453 Val = ((MCE->getValue() + 0x800080008000LL) >> 48) & 0xffff; 2454 break; 2455 default: 2456 report_fatal_error("unsupported reloc value"); 2457 } 2458 return MCConstantExpr::Create(Val, getContext()); 2459 } 2460 2461 if (const MCSymbolRefExpr *MSRE = dyn_cast<MCSymbolRefExpr>(Expr)) { 2462 // It's a symbol, create a symbolic expression from the symbol. 2463 StringRef Symbol = MSRE->getSymbol().getName(); 2464 MCSymbolRefExpr::VariantKind VK = getVariantKind(RelocStr); 2465 Res = MCSymbolRefExpr::Create(Symbol, VK, getContext()); 2466 return Res; 2467 } 2468 2469 if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(Expr)) { 2470 MCSymbolRefExpr::VariantKind VK = getVariantKind(RelocStr); 2471 2472 // Try to create target expression. 2473 if (MipsMCExpr::isSupportedBinaryExpr(VK, BE)) 2474 return MipsMCExpr::Create(VK, Expr, getContext()); 2475 2476 const MCExpr *LExp = evaluateRelocExpr(BE->getLHS(), RelocStr); 2477 const MCExpr *RExp = evaluateRelocExpr(BE->getRHS(), RelocStr); 2478 Res = MCBinaryExpr::Create(BE->getOpcode(), LExp, RExp, getContext()); 2479 return Res; 2480 } 2481 2482 if (const MCUnaryExpr *UN = dyn_cast<MCUnaryExpr>(Expr)) { 2483 const MCExpr *UnExp = evaluateRelocExpr(UN->getSubExpr(), RelocStr); 2484 Res = MCUnaryExpr::Create(UN->getOpcode(), UnExp, getContext()); 2485 return Res; 2486 } 2487 // Just return the original expression. 2488 return Expr; 2489 } 2490 2491 bool MipsAsmParser::isEvaluated(const MCExpr *Expr) { 2492 2493 switch (Expr->getKind()) { 2494 case MCExpr::Constant: 2495 return true; 2496 case MCExpr::SymbolRef: 2497 return (cast<MCSymbolRefExpr>(Expr)->getKind() != MCSymbolRefExpr::VK_None); 2498 case MCExpr::Binary: 2499 if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(Expr)) { 2500 if (!isEvaluated(BE->getLHS())) 2501 return false; 2502 return isEvaluated(BE->getRHS()); 2503 } 2504 case MCExpr::Unary: 2505 return isEvaluated(cast<MCUnaryExpr>(Expr)->getSubExpr()); 2506 case MCExpr::Target: 2507 return true; 2508 } 2509 return false; 2510 } 2511 2512 bool MipsAsmParser::parseRelocOperand(const MCExpr *&Res) { 2513 MCAsmParser &Parser = getParser(); 2514 Parser.Lex(); // Eat the % token. 2515 const AsmToken &Tok = Parser.getTok(); // Get next token, operation. 2516 if (Tok.isNot(AsmToken::Identifier)) 2517 return true; 2518 2519 std::string Str = Tok.getIdentifier().str(); 2520 2521 Parser.Lex(); // Eat the identifier. 2522 // Now make an expression from the rest of the operand. 2523 const MCExpr *IdVal; 2524 SMLoc EndLoc; 2525 2526 if (getLexer().getKind() == AsmToken::LParen) { 2527 while (1) { 2528 Parser.Lex(); // Eat the '(' token. 2529 if (getLexer().getKind() == AsmToken::Percent) { 2530 Parser.Lex(); // Eat the % token. 2531 const AsmToken &nextTok = Parser.getTok(); 2532 if (nextTok.isNot(AsmToken::Identifier)) 2533 return true; 2534 Str += "(%"; 2535 Str += nextTok.getIdentifier(); 2536 Parser.Lex(); // Eat the identifier. 2537 if (getLexer().getKind() != AsmToken::LParen) 2538 return true; 2539 } else 2540 break; 2541 } 2542 if (getParser().parseParenExpression(IdVal, EndLoc)) 2543 return true; 2544 2545 while (getLexer().getKind() == AsmToken::RParen) 2546 Parser.Lex(); // Eat the ')' token. 2547 2548 } else 2549 return true; // Parenthesis must follow the relocation operand. 2550 2551 Res = evaluateRelocExpr(IdVal, Str); 2552 return false; 2553 } 2554 2555 bool MipsAsmParser::ParseRegister(unsigned &RegNo, SMLoc &StartLoc, 2556 SMLoc &EndLoc) { 2557 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> Operands; 2558 OperandMatchResultTy ResTy = parseAnyRegister(Operands); 2559 if (ResTy == MatchOperand_Success) { 2560 assert(Operands.size() == 1); 2561 MipsOperand &Operand = static_cast<MipsOperand &>(*Operands.front()); 2562 StartLoc = Operand.getStartLoc(); 2563 EndLoc = Operand.getEndLoc(); 2564 2565 // AFAIK, we only support numeric registers and named GPR's in CFI 2566 // directives. 2567 // Don't worry about eating tokens before failing. Using an unrecognised 2568 // register is a parse error. 2569 if (Operand.isGPRAsmReg()) { 2570 // Resolve to GPR32 or GPR64 appropriately. 2571 RegNo = isGP64bit() ? Operand.getGPR64Reg() : Operand.getGPR32Reg(); 2572 } 2573 2574 return (RegNo == (unsigned)-1); 2575 } 2576 2577 assert(Operands.size() == 0); 2578 return (RegNo == (unsigned)-1); 2579 } 2580 2581 bool MipsAsmParser::parseMemOffset(const MCExpr *&Res, bool isParenExpr) { 2582 MCAsmParser &Parser = getParser(); 2583 SMLoc S; 2584 bool Result = true; 2585 2586 while (getLexer().getKind() == AsmToken::LParen) 2587 Parser.Lex(); 2588 2589 switch (getLexer().getKind()) { 2590 default: 2591 return true; 2592 case AsmToken::Identifier: 2593 case AsmToken::LParen: 2594 case AsmToken::Integer: 2595 case AsmToken::Minus: 2596 case AsmToken::Plus: 2597 if (isParenExpr) 2598 Result = getParser().parseParenExpression(Res, S); 2599 else 2600 Result = (getParser().parseExpression(Res)); 2601 while (getLexer().getKind() == AsmToken::RParen) 2602 Parser.Lex(); 2603 break; 2604 case AsmToken::Percent: 2605 Result = parseRelocOperand(Res); 2606 } 2607 return Result; 2608 } 2609 2610 MipsAsmParser::OperandMatchResultTy 2611 MipsAsmParser::parseMemOperand(OperandVector &Operands) { 2612 MCAsmParser &Parser = getParser(); 2613 DEBUG(dbgs() << "parseMemOperand\n"); 2614 const MCExpr *IdVal = nullptr; 2615 SMLoc S; 2616 bool isParenExpr = false; 2617 MipsAsmParser::OperandMatchResultTy Res = MatchOperand_NoMatch; 2618 // First operand is the offset. 2619 S = Parser.getTok().getLoc(); 2620 2621 if (getLexer().getKind() == AsmToken::LParen) { 2622 Parser.Lex(); 2623 isParenExpr = true; 2624 } 2625 2626 if (getLexer().getKind() != AsmToken::Dollar) { 2627 if (parseMemOffset(IdVal, isParenExpr)) 2628 return MatchOperand_ParseFail; 2629 2630 const AsmToken &Tok = Parser.getTok(); // Get the next token. 2631 if (Tok.isNot(AsmToken::LParen)) { 2632 MipsOperand &Mnemonic = static_cast<MipsOperand &>(*Operands[0]); 2633 if (Mnemonic.getToken() == "la") { 2634 SMLoc E = 2635 SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2636 Operands.push_back(MipsOperand::CreateImm(IdVal, S, E, *this)); 2637 return MatchOperand_Success; 2638 } 2639 if (Tok.is(AsmToken::EndOfStatement)) { 2640 SMLoc E = 2641 SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2642 2643 // Zero register assumed, add a memory operand with ZERO as its base. 2644 // "Base" will be managed by k_Memory. 2645 auto Base = MipsOperand::createGPRReg(0, getContext().getRegisterInfo(), 2646 S, E, *this); 2647 Operands.push_back( 2648 MipsOperand::CreateMem(std::move(Base), IdVal, S, E, *this)); 2649 return MatchOperand_Success; 2650 } 2651 Error(Parser.getTok().getLoc(), "'(' expected"); 2652 return MatchOperand_ParseFail; 2653 } 2654 2655 Parser.Lex(); // Eat the '(' token. 2656 } 2657 2658 Res = parseAnyRegister(Operands); 2659 if (Res != MatchOperand_Success) 2660 return Res; 2661 2662 if (Parser.getTok().isNot(AsmToken::RParen)) { 2663 Error(Parser.getTok().getLoc(), "')' expected"); 2664 return MatchOperand_ParseFail; 2665 } 2666 2667 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2668 2669 Parser.Lex(); // Eat the ')' token. 2670 2671 if (!IdVal) 2672 IdVal = MCConstantExpr::Create(0, getContext()); 2673 2674 // Replace the register operand with the memory operand. 2675 std::unique_ptr<MipsOperand> op( 2676 static_cast<MipsOperand *>(Operands.back().release())); 2677 // Remove the register from the operands. 2678 // "op" will be managed by k_Memory. 2679 Operands.pop_back(); 2680 // Add the memory operand. 2681 if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(IdVal)) { 2682 int64_t Imm; 2683 if (IdVal->EvaluateAsAbsolute(Imm)) 2684 IdVal = MCConstantExpr::Create(Imm, getContext()); 2685 else if (BE->getLHS()->getKind() != MCExpr::SymbolRef) 2686 IdVal = MCBinaryExpr::Create(BE->getOpcode(), BE->getRHS(), BE->getLHS(), 2687 getContext()); 2688 } 2689 2690 Operands.push_back(MipsOperand::CreateMem(std::move(op), IdVal, S, E, *this)); 2691 return MatchOperand_Success; 2692 } 2693 2694 bool MipsAsmParser::searchSymbolAlias(OperandVector &Operands) { 2695 MCAsmParser &Parser = getParser(); 2696 MCSymbol *Sym = getContext().LookupSymbol(Parser.getTok().getIdentifier()); 2697 if (Sym) { 2698 SMLoc S = Parser.getTok().getLoc(); 2699 const MCExpr *Expr; 2700 if (Sym->isVariable()) 2701 Expr = Sym->getVariableValue(); 2702 else 2703 return false; 2704 if (Expr->getKind() == MCExpr::SymbolRef) { 2705 const MCSymbolRefExpr *Ref = static_cast<const MCSymbolRefExpr *>(Expr); 2706 StringRef DefSymbol = Ref->getSymbol().getName(); 2707 if (DefSymbol.startswith("$")) { 2708 OperandMatchResultTy ResTy = 2709 matchAnyRegisterNameWithoutDollar(Operands, DefSymbol.substr(1), S); 2710 if (ResTy == MatchOperand_Success) { 2711 Parser.Lex(); 2712 return true; 2713 } else if (ResTy == MatchOperand_ParseFail) 2714 llvm_unreachable("Should never ParseFail"); 2715 return false; 2716 } 2717 } else if (Expr->getKind() == MCExpr::Constant) { 2718 Parser.Lex(); 2719 const MCConstantExpr *Const = static_cast<const MCConstantExpr *>(Expr); 2720 Operands.push_back( 2721 MipsOperand::CreateImm(Const, S, Parser.getTok().getLoc(), *this)); 2722 return true; 2723 } 2724 } 2725 return false; 2726 } 2727 2728 MipsAsmParser::OperandMatchResultTy 2729 MipsAsmParser::matchAnyRegisterNameWithoutDollar(OperandVector &Operands, 2730 StringRef Identifier, 2731 SMLoc S) { 2732 int Index = matchCPURegisterName(Identifier); 2733 if (Index != -1) { 2734 Operands.push_back(MipsOperand::createGPRReg( 2735 Index, getContext().getRegisterInfo(), S, getLexer().getLoc(), *this)); 2736 return MatchOperand_Success; 2737 } 2738 2739 Index = matchHWRegsRegisterName(Identifier); 2740 if (Index != -1) { 2741 Operands.push_back(MipsOperand::createHWRegsReg( 2742 Index, getContext().getRegisterInfo(), S, getLexer().getLoc(), *this)); 2743 return MatchOperand_Success; 2744 } 2745 2746 Index = matchFPURegisterName(Identifier); 2747 if (Index != -1) { 2748 Operands.push_back(MipsOperand::createFGRReg( 2749 Index, getContext().getRegisterInfo(), S, getLexer().getLoc(), *this)); 2750 return MatchOperand_Success; 2751 } 2752 2753 Index = matchFCCRegisterName(Identifier); 2754 if (Index != -1) { 2755 Operands.push_back(MipsOperand::createFCCReg( 2756 Index, getContext().getRegisterInfo(), S, getLexer().getLoc(), *this)); 2757 return MatchOperand_Success; 2758 } 2759 2760 Index = matchACRegisterName(Identifier); 2761 if (Index != -1) { 2762 Operands.push_back(MipsOperand::createACCReg( 2763 Index, getContext().getRegisterInfo(), S, getLexer().getLoc(), *this)); 2764 return MatchOperand_Success; 2765 } 2766 2767 Index = matchMSA128RegisterName(Identifier); 2768 if (Index != -1) { 2769 Operands.push_back(MipsOperand::createMSA128Reg( 2770 Index, getContext().getRegisterInfo(), S, getLexer().getLoc(), *this)); 2771 return MatchOperand_Success; 2772 } 2773 2774 Index = matchMSA128CtrlRegisterName(Identifier); 2775 if (Index != -1) { 2776 Operands.push_back(MipsOperand::createMSACtrlReg( 2777 Index, getContext().getRegisterInfo(), S, getLexer().getLoc(), *this)); 2778 return MatchOperand_Success; 2779 } 2780 2781 return MatchOperand_NoMatch; 2782 } 2783 2784 MipsAsmParser::OperandMatchResultTy 2785 MipsAsmParser::matchAnyRegisterWithoutDollar(OperandVector &Operands, SMLoc S) { 2786 MCAsmParser &Parser = getParser(); 2787 auto Token = Parser.getLexer().peekTok(false); 2788 2789 if (Token.is(AsmToken::Identifier)) { 2790 DEBUG(dbgs() << ".. identifier\n"); 2791 StringRef Identifier = Token.getIdentifier(); 2792 OperandMatchResultTy ResTy = 2793 matchAnyRegisterNameWithoutDollar(Operands, Identifier, S); 2794 return ResTy; 2795 } else if (Token.is(AsmToken::Integer)) { 2796 DEBUG(dbgs() << ".. integer\n"); 2797 Operands.push_back(MipsOperand::createNumericReg( 2798 Token.getIntVal(), getContext().getRegisterInfo(), S, Token.getLoc(), 2799 *this)); 2800 return MatchOperand_Success; 2801 } 2802 2803 DEBUG(dbgs() << Parser.getTok().getKind() << "\n"); 2804 2805 return MatchOperand_NoMatch; 2806 } 2807 2808 MipsAsmParser::OperandMatchResultTy 2809 MipsAsmParser::parseAnyRegister(OperandVector &Operands) { 2810 MCAsmParser &Parser = getParser(); 2811 DEBUG(dbgs() << "parseAnyRegister\n"); 2812 2813 auto Token = Parser.getTok(); 2814 2815 SMLoc S = Token.getLoc(); 2816 2817 if (Token.isNot(AsmToken::Dollar)) { 2818 DEBUG(dbgs() << ".. !$ -> try sym aliasing\n"); 2819 if (Token.is(AsmToken::Identifier)) { 2820 if (searchSymbolAlias(Operands)) 2821 return MatchOperand_Success; 2822 } 2823 DEBUG(dbgs() << ".. !symalias -> NoMatch\n"); 2824 return MatchOperand_NoMatch; 2825 } 2826 DEBUG(dbgs() << ".. $\n"); 2827 2828 OperandMatchResultTy ResTy = matchAnyRegisterWithoutDollar(Operands, S); 2829 if (ResTy == MatchOperand_Success) { 2830 Parser.Lex(); // $ 2831 Parser.Lex(); // identifier 2832 } 2833 return ResTy; 2834 } 2835 2836 MipsAsmParser::OperandMatchResultTy 2837 MipsAsmParser::parseImm(OperandVector &Operands) { 2838 MCAsmParser &Parser = getParser(); 2839 switch (getLexer().getKind()) { 2840 default: 2841 return MatchOperand_NoMatch; 2842 case AsmToken::LParen: 2843 case AsmToken::Minus: 2844 case AsmToken::Plus: 2845 case AsmToken::Integer: 2846 case AsmToken::Tilde: 2847 case AsmToken::String: 2848 break; 2849 } 2850 2851 const MCExpr *IdVal; 2852 SMLoc S = Parser.getTok().getLoc(); 2853 if (getParser().parseExpression(IdVal)) 2854 return MatchOperand_ParseFail; 2855 2856 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2857 Operands.push_back(MipsOperand::CreateImm(IdVal, S, E, *this)); 2858 return MatchOperand_Success; 2859 } 2860 2861 MipsAsmParser::OperandMatchResultTy 2862 MipsAsmParser::parseJumpTarget(OperandVector &Operands) { 2863 MCAsmParser &Parser = getParser(); 2864 DEBUG(dbgs() << "parseJumpTarget\n"); 2865 2866 SMLoc S = getLexer().getLoc(); 2867 2868 // Integers and expressions are acceptable 2869 OperandMatchResultTy ResTy = parseImm(Operands); 2870 if (ResTy != MatchOperand_NoMatch) 2871 return ResTy; 2872 2873 // Registers are a valid target and have priority over symbols. 2874 ResTy = parseAnyRegister(Operands); 2875 if (ResTy != MatchOperand_NoMatch) 2876 return ResTy; 2877 2878 const MCExpr *Expr = nullptr; 2879 if (Parser.parseExpression(Expr)) { 2880 // We have no way of knowing if a symbol was consumed so we must ParseFail 2881 return MatchOperand_ParseFail; 2882 } 2883 Operands.push_back( 2884 MipsOperand::CreateImm(Expr, S, getLexer().getLoc(), *this)); 2885 return MatchOperand_Success; 2886 } 2887 2888 MipsAsmParser::OperandMatchResultTy 2889 MipsAsmParser::parseInvNum(OperandVector &Operands) { 2890 MCAsmParser &Parser = getParser(); 2891 const MCExpr *IdVal; 2892 // If the first token is '$' we may have register operand. 2893 if (Parser.getTok().is(AsmToken::Dollar)) 2894 return MatchOperand_NoMatch; 2895 SMLoc S = Parser.getTok().getLoc(); 2896 if (getParser().parseExpression(IdVal)) 2897 return MatchOperand_ParseFail; 2898 const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(IdVal); 2899 assert(MCE && "Unexpected MCExpr type."); 2900 int64_t Val = MCE->getValue(); 2901 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 2902 Operands.push_back(MipsOperand::CreateImm( 2903 MCConstantExpr::Create(0 - Val, getContext()), S, E, *this)); 2904 return MatchOperand_Success; 2905 } 2906 2907 MipsAsmParser::OperandMatchResultTy 2908 MipsAsmParser::parseLSAImm(OperandVector &Operands) { 2909 MCAsmParser &Parser = getParser(); 2910 switch (getLexer().getKind()) { 2911 default: 2912 return MatchOperand_NoMatch; 2913 case AsmToken::LParen: 2914 case AsmToken::Plus: 2915 case AsmToken::Minus: 2916 case AsmToken::Integer: 2917 break; 2918 } 2919 2920 const MCExpr *Expr; 2921 SMLoc S = Parser.getTok().getLoc(); 2922 2923 if (getParser().parseExpression(Expr)) 2924 return MatchOperand_ParseFail; 2925 2926 int64_t Val; 2927 if (!Expr->EvaluateAsAbsolute(Val)) { 2928 Error(S, "expected immediate value"); 2929 return MatchOperand_ParseFail; 2930 } 2931 2932 // The LSA instruction allows a 2-bit unsigned immediate. For this reason 2933 // and because the CPU always adds one to the immediate field, the allowed 2934 // range becomes 1..4. We'll only check the range here and will deal 2935 // with the addition/subtraction when actually decoding/encoding 2936 // the instruction. 2937 if (Val < 1 || Val > 4) { 2938 Error(S, "immediate not in range (1..4)"); 2939 return MatchOperand_ParseFail; 2940 } 2941 2942 Operands.push_back( 2943 MipsOperand::CreateImm(Expr, S, Parser.getTok().getLoc(), *this)); 2944 return MatchOperand_Success; 2945 } 2946 2947 MipsAsmParser::OperandMatchResultTy 2948 MipsAsmParser::parseRegisterList(OperandVector &Operands) { 2949 MCAsmParser &Parser = getParser(); 2950 SmallVector<unsigned, 10> Regs; 2951 unsigned RegNo; 2952 unsigned PrevReg = Mips::NoRegister; 2953 bool RegRange = false; 2954 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 8> TmpOperands; 2955 2956 if (Parser.getTok().isNot(AsmToken::Dollar)) 2957 return MatchOperand_ParseFail; 2958 2959 SMLoc S = Parser.getTok().getLoc(); 2960 while (parseAnyRegister(TmpOperands) == MatchOperand_Success) { 2961 SMLoc E = getLexer().getLoc(); 2962 MipsOperand &Reg = static_cast<MipsOperand &>(*TmpOperands.back()); 2963 RegNo = isGP64bit() ? Reg.getGPR64Reg() : Reg.getGPR32Reg(); 2964 if (RegRange) { 2965 // Remove last register operand because registers from register range 2966 // should be inserted first. 2967 if (RegNo == Mips::RA) { 2968 Regs.push_back(RegNo); 2969 } else { 2970 unsigned TmpReg = PrevReg + 1; 2971 while (TmpReg <= RegNo) { 2972 if ((TmpReg < Mips::S0) || (TmpReg > Mips::S7)) { 2973 Error(E, "invalid register operand"); 2974 return MatchOperand_ParseFail; 2975 } 2976 2977 PrevReg = TmpReg; 2978 Regs.push_back(TmpReg++); 2979 } 2980 } 2981 2982 RegRange = false; 2983 } else { 2984 if ((PrevReg == Mips::NoRegister) && (RegNo != Mips::S0) && 2985 (RegNo != Mips::RA)) { 2986 Error(E, "$16 or $31 expected"); 2987 return MatchOperand_ParseFail; 2988 } else if (((RegNo < Mips::S0) || (RegNo > Mips::S7)) && 2989 (RegNo != Mips::FP) && (RegNo != Mips::RA)) { 2990 Error(E, "invalid register operand"); 2991 return MatchOperand_ParseFail; 2992 } else if ((PrevReg != Mips::NoRegister) && (RegNo != PrevReg + 1) && 2993 (RegNo != Mips::FP) && (RegNo != Mips::RA)) { 2994 Error(E, "consecutive register numbers expected"); 2995 return MatchOperand_ParseFail; 2996 } 2997 2998 Regs.push_back(RegNo); 2999 } 3000 3001 if (Parser.getTok().is(AsmToken::Minus)) 3002 RegRange = true; 3003 3004 if (!Parser.getTok().isNot(AsmToken::Minus) && 3005 !Parser.getTok().isNot(AsmToken::Comma)) { 3006 Error(E, "',' or '-' expected"); 3007 return MatchOperand_ParseFail; 3008 } 3009 3010 Lex(); // Consume comma or minus 3011 if (Parser.getTok().isNot(AsmToken::Dollar)) 3012 break; 3013 3014 PrevReg = RegNo; 3015 } 3016 3017 SMLoc E = Parser.getTok().getLoc(); 3018 Operands.push_back(MipsOperand::CreateRegList(Regs, S, E, *this)); 3019 parseMemOperand(Operands); 3020 return MatchOperand_Success; 3021 } 3022 3023 MipsAsmParser::OperandMatchResultTy 3024 MipsAsmParser::parseRegisterPair(OperandVector &Operands) { 3025 MCAsmParser &Parser = getParser(); 3026 3027 SMLoc S = Parser.getTok().getLoc(); 3028 if (parseAnyRegister(Operands) != MatchOperand_Success) 3029 return MatchOperand_ParseFail; 3030 3031 SMLoc E = Parser.getTok().getLoc(); 3032 MipsOperand &Op = static_cast<MipsOperand &>(*Operands.back()); 3033 unsigned Reg = Op.getGPR32Reg(); 3034 Operands.pop_back(); 3035 Operands.push_back(MipsOperand::CreateRegPair(Reg, S, E, *this)); 3036 return MatchOperand_Success; 3037 } 3038 3039 MCSymbolRefExpr::VariantKind MipsAsmParser::getVariantKind(StringRef Symbol) { 3040 3041 MCSymbolRefExpr::VariantKind VK = 3042 StringSwitch<MCSymbolRefExpr::VariantKind>(Symbol) 3043 .Case("hi", MCSymbolRefExpr::VK_Mips_ABS_HI) 3044 .Case("lo", MCSymbolRefExpr::VK_Mips_ABS_LO) 3045 .Case("gp_rel", MCSymbolRefExpr::VK_Mips_GPREL) 3046 .Case("call16", MCSymbolRefExpr::VK_Mips_GOT_CALL) 3047 .Case("got", MCSymbolRefExpr::VK_Mips_GOT) 3048 .Case("tlsgd", MCSymbolRefExpr::VK_Mips_TLSGD) 3049 .Case("tlsldm", MCSymbolRefExpr::VK_Mips_TLSLDM) 3050 .Case("dtprel_hi", MCSymbolRefExpr::VK_Mips_DTPREL_HI) 3051 .Case("dtprel_lo", MCSymbolRefExpr::VK_Mips_DTPREL_LO) 3052 .Case("gottprel", MCSymbolRefExpr::VK_Mips_GOTTPREL) 3053 .Case("tprel_hi", MCSymbolRefExpr::VK_Mips_TPREL_HI) 3054 .Case("tprel_lo", MCSymbolRefExpr::VK_Mips_TPREL_LO) 3055 .Case("got_disp", MCSymbolRefExpr::VK_Mips_GOT_DISP) 3056 .Case("got_page", MCSymbolRefExpr::VK_Mips_GOT_PAGE) 3057 .Case("got_ofst", MCSymbolRefExpr::VK_Mips_GOT_OFST) 3058 .Case("hi(%neg(%gp_rel", MCSymbolRefExpr::VK_Mips_GPOFF_HI) 3059 .Case("lo(%neg(%gp_rel", MCSymbolRefExpr::VK_Mips_GPOFF_LO) 3060 .Case("got_hi", MCSymbolRefExpr::VK_Mips_GOT_HI16) 3061 .Case("got_lo", MCSymbolRefExpr::VK_Mips_GOT_LO16) 3062 .Case("call_hi", MCSymbolRefExpr::VK_Mips_CALL_HI16) 3063 .Case("call_lo", MCSymbolRefExpr::VK_Mips_CALL_LO16) 3064 .Case("higher", MCSymbolRefExpr::VK_Mips_HIGHER) 3065 .Case("highest", MCSymbolRefExpr::VK_Mips_HIGHEST) 3066 .Case("pcrel_hi", MCSymbolRefExpr::VK_Mips_PCREL_HI16) 3067 .Case("pcrel_lo", MCSymbolRefExpr::VK_Mips_PCREL_LO16) 3068 .Default(MCSymbolRefExpr::VK_None); 3069 3070 assert(VK != MCSymbolRefExpr::VK_None); 3071 3072 return VK; 3073 } 3074 3075 /// Sometimes (i.e. load/stores) the operand may be followed immediately by 3076 /// either this. 3077 /// ::= '(', register, ')' 3078 /// handle it before we iterate so we don't get tripped up by the lack of 3079 /// a comma. 3080 bool MipsAsmParser::parseParenSuffix(StringRef Name, OperandVector &Operands) { 3081 MCAsmParser &Parser = getParser(); 3082 if (getLexer().is(AsmToken::LParen)) { 3083 Operands.push_back( 3084 MipsOperand::CreateToken("(", getLexer().getLoc(), *this)); 3085 Parser.Lex(); 3086 if (parseOperand(Operands, Name)) { 3087 SMLoc Loc = getLexer().getLoc(); 3088 Parser.eatToEndOfStatement(); 3089 return Error(Loc, "unexpected token in argument list"); 3090 } 3091 if (Parser.getTok().isNot(AsmToken::RParen)) { 3092 SMLoc Loc = getLexer().getLoc(); 3093 Parser.eatToEndOfStatement(); 3094 return Error(Loc, "unexpected token, expected ')'"); 3095 } 3096 Operands.push_back( 3097 MipsOperand::CreateToken(")", getLexer().getLoc(), *this)); 3098 Parser.Lex(); 3099 } 3100 return false; 3101 } 3102 3103 /// Sometimes (i.e. in MSA) the operand may be followed immediately by 3104 /// either one of these. 3105 /// ::= '[', register, ']' 3106 /// ::= '[', integer, ']' 3107 /// handle it before we iterate so we don't get tripped up by the lack of 3108 /// a comma. 3109 bool MipsAsmParser::parseBracketSuffix(StringRef Name, 3110 OperandVector &Operands) { 3111 MCAsmParser &Parser = getParser(); 3112 if (getLexer().is(AsmToken::LBrac)) { 3113 Operands.push_back( 3114 MipsOperand::CreateToken("[", getLexer().getLoc(), *this)); 3115 Parser.Lex(); 3116 if (parseOperand(Operands, Name)) { 3117 SMLoc Loc = getLexer().getLoc(); 3118 Parser.eatToEndOfStatement(); 3119 return Error(Loc, "unexpected token in argument list"); 3120 } 3121 if (Parser.getTok().isNot(AsmToken::RBrac)) { 3122 SMLoc Loc = getLexer().getLoc(); 3123 Parser.eatToEndOfStatement(); 3124 return Error(Loc, "unexpected token, expected ']'"); 3125 } 3126 Operands.push_back( 3127 MipsOperand::CreateToken("]", getLexer().getLoc(), *this)); 3128 Parser.Lex(); 3129 } 3130 return false; 3131 } 3132 3133 bool MipsAsmParser::ParseInstruction(ParseInstructionInfo &Info, StringRef Name, 3134 SMLoc NameLoc, OperandVector &Operands) { 3135 MCAsmParser &Parser = getParser(); 3136 DEBUG(dbgs() << "ParseInstruction\n"); 3137 3138 // We have reached first instruction, module directive are now forbidden. 3139 getTargetStreamer().forbidModuleDirective(); 3140 3141 // Check if we have valid mnemonic 3142 if (!mnemonicIsValid(Name, 0)) { 3143 Parser.eatToEndOfStatement(); 3144 return Error(NameLoc, "unknown instruction"); 3145 } 3146 // First operand in MCInst is instruction mnemonic. 3147 Operands.push_back(MipsOperand::CreateToken(Name, NameLoc, *this)); 3148 3149 // Read the remaining operands. 3150 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3151 // Read the first operand. 3152 if (parseOperand(Operands, Name)) { 3153 SMLoc Loc = getLexer().getLoc(); 3154 Parser.eatToEndOfStatement(); 3155 return Error(Loc, "unexpected token in argument list"); 3156 } 3157 if (getLexer().is(AsmToken::LBrac) && parseBracketSuffix(Name, Operands)) 3158 return true; 3159 // AFAIK, parenthesis suffixes are never on the first operand 3160 3161 while (getLexer().is(AsmToken::Comma)) { 3162 Parser.Lex(); // Eat the comma. 3163 // Parse and remember the operand. 3164 if (parseOperand(Operands, Name)) { 3165 SMLoc Loc = getLexer().getLoc(); 3166 Parser.eatToEndOfStatement(); 3167 return Error(Loc, "unexpected token in argument list"); 3168 } 3169 // Parse bracket and parenthesis suffixes before we iterate 3170 if (getLexer().is(AsmToken::LBrac)) { 3171 if (parseBracketSuffix(Name, Operands)) 3172 return true; 3173 } else if (getLexer().is(AsmToken::LParen) && 3174 parseParenSuffix(Name, Operands)) 3175 return true; 3176 } 3177 } 3178 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3179 SMLoc Loc = getLexer().getLoc(); 3180 Parser.eatToEndOfStatement(); 3181 return Error(Loc, "unexpected token in argument list"); 3182 } 3183 Parser.Lex(); // Consume the EndOfStatement. 3184 return false; 3185 } 3186 3187 bool MipsAsmParser::reportParseError(Twine ErrorMsg) { 3188 MCAsmParser &Parser = getParser(); 3189 SMLoc Loc = getLexer().getLoc(); 3190 Parser.eatToEndOfStatement(); 3191 return Error(Loc, ErrorMsg); 3192 } 3193 3194 bool MipsAsmParser::reportParseError(SMLoc Loc, Twine ErrorMsg) { 3195 return Error(Loc, ErrorMsg); 3196 } 3197 3198 bool MipsAsmParser::parseSetNoAtDirective() { 3199 MCAsmParser &Parser = getParser(); 3200 // Line should look like: ".set noat". 3201 // set at reg to 0. 3202 AssemblerOptions.back()->setATReg(0); 3203 // eat noat 3204 Parser.Lex(); 3205 // If this is not the end of the statement, report an error. 3206 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3207 reportParseError("unexpected token, expected end of statement"); 3208 return false; 3209 } 3210 Parser.Lex(); // Consume the EndOfStatement. 3211 return false; 3212 } 3213 3214 bool MipsAsmParser::parseSetAtDirective() { 3215 MCAsmParser &Parser = getParser(); 3216 // Line can be .set at - defaults to $1 3217 // or .set at=$reg 3218 int AtRegNo; 3219 getParser().Lex(); 3220 if (getLexer().is(AsmToken::EndOfStatement)) { 3221 AssemblerOptions.back()->setATReg(1); 3222 Parser.Lex(); // Consume the EndOfStatement. 3223 return false; 3224 } else if (getLexer().is(AsmToken::Equal)) { 3225 getParser().Lex(); // Eat the '='. 3226 if (getLexer().isNot(AsmToken::Dollar)) { 3227 reportParseError("unexpected token, expected dollar sign '$'"); 3228 return false; 3229 } 3230 Parser.Lex(); // Eat the '$'. 3231 const AsmToken &Reg = Parser.getTok(); 3232 if (Reg.is(AsmToken::Identifier)) { 3233 AtRegNo = matchCPURegisterName(Reg.getIdentifier()); 3234 } else if (Reg.is(AsmToken::Integer)) { 3235 AtRegNo = Reg.getIntVal(); 3236 } else { 3237 reportParseError("unexpected token, expected identifier or integer"); 3238 return false; 3239 } 3240 3241 if (AtRegNo < 0 || AtRegNo > 31) { 3242 reportParseError("unexpected token in statement"); 3243 return false; 3244 } 3245 3246 if (!AssemblerOptions.back()->setATReg(AtRegNo)) { 3247 reportParseError("invalid register"); 3248 return false; 3249 } 3250 getParser().Lex(); // Eat the register. 3251 3252 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3253 reportParseError("unexpected token, expected end of statement"); 3254 return false; 3255 } 3256 Parser.Lex(); // Consume the EndOfStatement. 3257 return false; 3258 } else { 3259 reportParseError("unexpected token in statement"); 3260 return false; 3261 } 3262 } 3263 3264 bool MipsAsmParser::parseSetReorderDirective() { 3265 MCAsmParser &Parser = getParser(); 3266 Parser.Lex(); 3267 // If this is not the end of the statement, report an error. 3268 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3269 reportParseError("unexpected token, expected end of statement"); 3270 return false; 3271 } 3272 AssemblerOptions.back()->setReorder(); 3273 getTargetStreamer().emitDirectiveSetReorder(); 3274 Parser.Lex(); // Consume the EndOfStatement. 3275 return false; 3276 } 3277 3278 bool MipsAsmParser::parseSetNoReorderDirective() { 3279 MCAsmParser &Parser = getParser(); 3280 Parser.Lex(); 3281 // If this is not the end of the statement, report an error. 3282 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3283 reportParseError("unexpected token, expected end of statement"); 3284 return false; 3285 } 3286 AssemblerOptions.back()->setNoReorder(); 3287 getTargetStreamer().emitDirectiveSetNoReorder(); 3288 Parser.Lex(); // Consume the EndOfStatement. 3289 return false; 3290 } 3291 3292 bool MipsAsmParser::parseSetMacroDirective() { 3293 MCAsmParser &Parser = getParser(); 3294 Parser.Lex(); 3295 // If this is not the end of the statement, report an error. 3296 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3297 reportParseError("unexpected token, expected end of statement"); 3298 return false; 3299 } 3300 AssemblerOptions.back()->setMacro(); 3301 Parser.Lex(); // Consume the EndOfStatement. 3302 return false; 3303 } 3304 3305 bool MipsAsmParser::parseSetNoMacroDirective() { 3306 MCAsmParser &Parser = getParser(); 3307 Parser.Lex(); 3308 // If this is not the end of the statement, report an error. 3309 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3310 reportParseError("unexpected token, expected end of statement"); 3311 return false; 3312 } 3313 if (AssemblerOptions.back()->isReorder()) { 3314 reportParseError("`noreorder' must be set before `nomacro'"); 3315 return false; 3316 } 3317 AssemblerOptions.back()->setNoMacro(); 3318 Parser.Lex(); // Consume the EndOfStatement. 3319 return false; 3320 } 3321 3322 bool MipsAsmParser::parseSetMsaDirective() { 3323 MCAsmParser &Parser = getParser(); 3324 Parser.Lex(); 3325 3326 // If this is not the end of the statement, report an error. 3327 if (getLexer().isNot(AsmToken::EndOfStatement)) 3328 return reportParseError("unexpected token, expected end of statement"); 3329 3330 setFeatureBits(Mips::FeatureMSA, "msa"); 3331 getTargetStreamer().emitDirectiveSetMsa(); 3332 return false; 3333 } 3334 3335 bool MipsAsmParser::parseSetNoMsaDirective() { 3336 MCAsmParser &Parser = getParser(); 3337 Parser.Lex(); 3338 3339 // If this is not the end of the statement, report an error. 3340 if (getLexer().isNot(AsmToken::EndOfStatement)) 3341 return reportParseError("unexpected token, expected end of statement"); 3342 3343 clearFeatureBits(Mips::FeatureMSA, "msa"); 3344 getTargetStreamer().emitDirectiveSetNoMsa(); 3345 return false; 3346 } 3347 3348 bool MipsAsmParser::parseSetNoDspDirective() { 3349 MCAsmParser &Parser = getParser(); 3350 Parser.Lex(); // Eat "nodsp". 3351 3352 // If this is not the end of the statement, report an error. 3353 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3354 reportParseError("unexpected token, expected end of statement"); 3355 return false; 3356 } 3357 3358 clearFeatureBits(Mips::FeatureDSP, "dsp"); 3359 getTargetStreamer().emitDirectiveSetNoDsp(); 3360 return false; 3361 } 3362 3363 bool MipsAsmParser::parseSetMips16Directive() { 3364 MCAsmParser &Parser = getParser(); 3365 Parser.Lex(); // Eat "mips16". 3366 3367 // If this is not the end of the statement, report an error. 3368 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3369 reportParseError("unexpected token, expected end of statement"); 3370 return false; 3371 } 3372 3373 setFeatureBits(Mips::FeatureMips16, "mips16"); 3374 getTargetStreamer().emitDirectiveSetMips16(); 3375 Parser.Lex(); // Consume the EndOfStatement. 3376 return false; 3377 } 3378 3379 bool MipsAsmParser::parseSetNoMips16Directive() { 3380 MCAsmParser &Parser = getParser(); 3381 Parser.Lex(); // Eat "nomips16". 3382 3383 // If this is not the end of the statement, report an error. 3384 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3385 reportParseError("unexpected token, expected end of statement"); 3386 return false; 3387 } 3388 3389 clearFeatureBits(Mips::FeatureMips16, "mips16"); 3390 getTargetStreamer().emitDirectiveSetNoMips16(); 3391 Parser.Lex(); // Consume the EndOfStatement. 3392 return false; 3393 } 3394 3395 bool MipsAsmParser::parseSetFpDirective() { 3396 MCAsmParser &Parser = getParser(); 3397 MipsABIFlagsSection::FpABIKind FpAbiVal; 3398 // Line can be: .set fp=32 3399 // .set fp=xx 3400 // .set fp=64 3401 Parser.Lex(); // Eat fp token 3402 AsmToken Tok = Parser.getTok(); 3403 if (Tok.isNot(AsmToken::Equal)) { 3404 reportParseError("unexpected token, expected equals sign '='"); 3405 return false; 3406 } 3407 Parser.Lex(); // Eat '=' token. 3408 Tok = Parser.getTok(); 3409 3410 if (!parseFpABIValue(FpAbiVal, ".set")) 3411 return false; 3412 3413 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3414 reportParseError("unexpected token, expected end of statement"); 3415 return false; 3416 } 3417 getTargetStreamer().emitDirectiveSetFp(FpAbiVal); 3418 Parser.Lex(); // Consume the EndOfStatement. 3419 return false; 3420 } 3421 3422 bool MipsAsmParser::parseSetPopDirective() { 3423 MCAsmParser &Parser = getParser(); 3424 SMLoc Loc = getLexer().getLoc(); 3425 3426 Parser.Lex(); 3427 if (getLexer().isNot(AsmToken::EndOfStatement)) 3428 return reportParseError("unexpected token, expected end of statement"); 3429 3430 // Always keep an element on the options "stack" to prevent the user 3431 // from changing the initial options. This is how we remember them. 3432 if (AssemblerOptions.size() == 2) 3433 return reportParseError(Loc, ".set pop with no .set push"); 3434 3435 AssemblerOptions.pop_back(); 3436 setAvailableFeatures(AssemblerOptions.back()->getFeatures()); 3437 3438 getTargetStreamer().emitDirectiveSetPop(); 3439 return false; 3440 } 3441 3442 bool MipsAsmParser::parseSetPushDirective() { 3443 MCAsmParser &Parser = getParser(); 3444 Parser.Lex(); 3445 if (getLexer().isNot(AsmToken::EndOfStatement)) 3446 return reportParseError("unexpected token, expected end of statement"); 3447 3448 // Create a copy of the current assembler options environment and push it. 3449 AssemblerOptions.push_back( 3450 make_unique<MipsAssemblerOptions>(AssemblerOptions.back().get())); 3451 3452 getTargetStreamer().emitDirectiveSetPush(); 3453 return false; 3454 } 3455 3456 bool MipsAsmParser::parseSetAssignment() { 3457 StringRef Name; 3458 const MCExpr *Value; 3459 MCAsmParser &Parser = getParser(); 3460 3461 if (Parser.parseIdentifier(Name)) 3462 reportParseError("expected identifier after .set"); 3463 3464 if (getLexer().isNot(AsmToken::Comma)) 3465 return reportParseError("unexpected token, expected comma"); 3466 Lex(); // Eat comma 3467 3468 if (Parser.parseExpression(Value)) 3469 return reportParseError("expected valid expression after comma"); 3470 3471 // Check if the Name already exists as a symbol. 3472 MCSymbol *Sym = getContext().LookupSymbol(Name); 3473 if (Sym) 3474 return reportParseError("symbol already defined"); 3475 Sym = getContext().GetOrCreateSymbol(Name); 3476 Sym->setVariableValue(Value); 3477 3478 return false; 3479 } 3480 3481 bool MipsAsmParser::parseSetMips0Directive() { 3482 MCAsmParser &Parser = getParser(); 3483 Parser.Lex(); 3484 if (getLexer().isNot(AsmToken::EndOfStatement)) 3485 return reportParseError("unexpected token, expected end of statement"); 3486 3487 // Reset assembler options to their initial values. 3488 setAvailableFeatures(AssemblerOptions.front()->getFeatures()); 3489 AssemblerOptions.back()->setFeatures(AssemblerOptions.front()->getFeatures()); 3490 3491 getTargetStreamer().emitDirectiveSetMips0(); 3492 return false; 3493 } 3494 3495 bool MipsAsmParser::parseSetArchDirective() { 3496 MCAsmParser &Parser = getParser(); 3497 Parser.Lex(); 3498 if (getLexer().isNot(AsmToken::Equal)) 3499 return reportParseError("unexpected token, expected equals sign"); 3500 3501 Parser.Lex(); 3502 StringRef Arch; 3503 if (Parser.parseIdentifier(Arch)) 3504 return reportParseError("expected arch identifier"); 3505 3506 StringRef ArchFeatureName = 3507 StringSwitch<StringRef>(Arch) 3508 .Case("mips1", "mips1") 3509 .Case("mips2", "mips2") 3510 .Case("mips3", "mips3") 3511 .Case("mips4", "mips4") 3512 .Case("mips5", "mips5") 3513 .Case("mips32", "mips32") 3514 .Case("mips32r2", "mips32r2") 3515 .Case("mips32r6", "mips32r6") 3516 .Case("mips64", "mips64") 3517 .Case("mips64r2", "mips64r2") 3518 .Case("mips64r6", "mips64r6") 3519 .Case("cnmips", "cnmips") 3520 .Case("r4000", "mips3") // This is an implementation of Mips3. 3521 .Default(""); 3522 3523 if (ArchFeatureName.empty()) 3524 return reportParseError("unsupported architecture"); 3525 3526 selectArch(ArchFeatureName); 3527 getTargetStreamer().emitDirectiveSetArch(Arch); 3528 return false; 3529 } 3530 3531 bool MipsAsmParser::parseSetFeature(uint64_t Feature) { 3532 MCAsmParser &Parser = getParser(); 3533 Parser.Lex(); 3534 if (getLexer().isNot(AsmToken::EndOfStatement)) 3535 return reportParseError("unexpected token, expected end of statement"); 3536 3537 switch (Feature) { 3538 default: 3539 llvm_unreachable("Unimplemented feature"); 3540 case Mips::FeatureDSP: 3541 setFeatureBits(Mips::FeatureDSP, "dsp"); 3542 getTargetStreamer().emitDirectiveSetDsp(); 3543 break; 3544 case Mips::FeatureMicroMips: 3545 getTargetStreamer().emitDirectiveSetMicroMips(); 3546 break; 3547 case Mips::FeatureMips1: 3548 selectArch("mips1"); 3549 getTargetStreamer().emitDirectiveSetMips1(); 3550 break; 3551 case Mips::FeatureMips2: 3552 selectArch("mips2"); 3553 getTargetStreamer().emitDirectiveSetMips2(); 3554 break; 3555 case Mips::FeatureMips3: 3556 selectArch("mips3"); 3557 getTargetStreamer().emitDirectiveSetMips3(); 3558 break; 3559 case Mips::FeatureMips4: 3560 selectArch("mips4"); 3561 getTargetStreamer().emitDirectiveSetMips4(); 3562 break; 3563 case Mips::FeatureMips5: 3564 selectArch("mips5"); 3565 getTargetStreamer().emitDirectiveSetMips5(); 3566 break; 3567 case Mips::FeatureMips32: 3568 selectArch("mips32"); 3569 getTargetStreamer().emitDirectiveSetMips32(); 3570 break; 3571 case Mips::FeatureMips32r2: 3572 selectArch("mips32r2"); 3573 getTargetStreamer().emitDirectiveSetMips32R2(); 3574 break; 3575 case Mips::FeatureMips32r6: 3576 selectArch("mips32r6"); 3577 getTargetStreamer().emitDirectiveSetMips32R6(); 3578 break; 3579 case Mips::FeatureMips64: 3580 selectArch("mips64"); 3581 getTargetStreamer().emitDirectiveSetMips64(); 3582 break; 3583 case Mips::FeatureMips64r2: 3584 selectArch("mips64r2"); 3585 getTargetStreamer().emitDirectiveSetMips64R2(); 3586 break; 3587 case Mips::FeatureMips64r6: 3588 selectArch("mips64r6"); 3589 getTargetStreamer().emitDirectiveSetMips64R6(); 3590 break; 3591 } 3592 return false; 3593 } 3594 3595 bool MipsAsmParser::eatComma(StringRef ErrorStr) { 3596 MCAsmParser &Parser = getParser(); 3597 if (getLexer().isNot(AsmToken::Comma)) { 3598 SMLoc Loc = getLexer().getLoc(); 3599 Parser.eatToEndOfStatement(); 3600 return Error(Loc, ErrorStr); 3601 } 3602 3603 Parser.Lex(); // Eat the comma. 3604 return true; 3605 } 3606 3607 bool MipsAsmParser::parseDirectiveCpLoad(SMLoc Loc) { 3608 if (AssemblerOptions.back()->isReorder()) 3609 Warning(Loc, ".cpload should be inside a noreorder section"); 3610 3611 if (inMips16Mode()) { 3612 reportParseError(".cpload is not supported in Mips16 mode"); 3613 return false; 3614 } 3615 3616 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> Reg; 3617 OperandMatchResultTy ResTy = parseAnyRegister(Reg); 3618 if (ResTy == MatchOperand_NoMatch || ResTy == MatchOperand_ParseFail) { 3619 reportParseError("expected register containing function address"); 3620 return false; 3621 } 3622 3623 MipsOperand &RegOpnd = static_cast<MipsOperand &>(*Reg[0]); 3624 if (!RegOpnd.isGPRAsmReg()) { 3625 reportParseError(RegOpnd.getStartLoc(), "invalid register"); 3626 return false; 3627 } 3628 3629 // If this is not the end of the statement, report an error. 3630 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3631 reportParseError("unexpected token, expected end of statement"); 3632 return false; 3633 } 3634 3635 getTargetStreamer().emitDirectiveCpLoad(RegOpnd.getGPR32Reg()); 3636 return false; 3637 } 3638 3639 bool MipsAsmParser::parseDirectiveCPSetup() { 3640 MCAsmParser &Parser = getParser(); 3641 unsigned FuncReg; 3642 unsigned Save; 3643 bool SaveIsReg = true; 3644 3645 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> TmpReg; 3646 OperandMatchResultTy ResTy = parseAnyRegister(TmpReg); 3647 if (ResTy == MatchOperand_NoMatch) { 3648 reportParseError("expected register containing function address"); 3649 Parser.eatToEndOfStatement(); 3650 return false; 3651 } 3652 3653 MipsOperand &FuncRegOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 3654 if (!FuncRegOpnd.isGPRAsmReg()) { 3655 reportParseError(FuncRegOpnd.getStartLoc(), "invalid register"); 3656 Parser.eatToEndOfStatement(); 3657 return false; 3658 } 3659 3660 FuncReg = FuncRegOpnd.getGPR32Reg(); 3661 TmpReg.clear(); 3662 3663 if (!eatComma("unexpected token, expected comma")) 3664 return true; 3665 3666 ResTy = parseAnyRegister(TmpReg); 3667 if (ResTy == MatchOperand_NoMatch) { 3668 const AsmToken &Tok = Parser.getTok(); 3669 if (Tok.is(AsmToken::Integer)) { 3670 Save = Tok.getIntVal(); 3671 SaveIsReg = false; 3672 Parser.Lex(); 3673 } else { 3674 reportParseError("expected save register or stack offset"); 3675 Parser.eatToEndOfStatement(); 3676 return false; 3677 } 3678 } else { 3679 MipsOperand &SaveOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 3680 if (!SaveOpnd.isGPRAsmReg()) { 3681 reportParseError(SaveOpnd.getStartLoc(), "invalid register"); 3682 Parser.eatToEndOfStatement(); 3683 return false; 3684 } 3685 Save = SaveOpnd.getGPR32Reg(); 3686 } 3687 3688 if (!eatComma("unexpected token, expected comma")) 3689 return true; 3690 3691 StringRef Name; 3692 if (Parser.parseIdentifier(Name)) 3693 reportParseError("expected identifier"); 3694 MCSymbol *Sym = getContext().GetOrCreateSymbol(Name); 3695 3696 getTargetStreamer().emitDirectiveCpsetup(FuncReg, Save, *Sym, SaveIsReg); 3697 return false; 3698 } 3699 3700 bool MipsAsmParser::parseDirectiveNaN() { 3701 MCAsmParser &Parser = getParser(); 3702 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3703 const AsmToken &Tok = Parser.getTok(); 3704 3705 if (Tok.getString() == "2008") { 3706 Parser.Lex(); 3707 getTargetStreamer().emitDirectiveNaN2008(); 3708 return false; 3709 } else if (Tok.getString() == "legacy") { 3710 Parser.Lex(); 3711 getTargetStreamer().emitDirectiveNaNLegacy(); 3712 return false; 3713 } 3714 } 3715 // If we don't recognize the option passed to the .nan 3716 // directive (e.g. no option or unknown option), emit an error. 3717 reportParseError("invalid option in .nan directive"); 3718 return false; 3719 } 3720 3721 bool MipsAsmParser::parseDirectiveSet() { 3722 MCAsmParser &Parser = getParser(); 3723 // Get the next token. 3724 const AsmToken &Tok = Parser.getTok(); 3725 3726 if (Tok.getString() == "noat") { 3727 return parseSetNoAtDirective(); 3728 } else if (Tok.getString() == "at") { 3729 return parseSetAtDirective(); 3730 } else if (Tok.getString() == "arch") { 3731 return parseSetArchDirective(); 3732 } else if (Tok.getString() == "fp") { 3733 return parseSetFpDirective(); 3734 } else if (Tok.getString() == "pop") { 3735 return parseSetPopDirective(); 3736 } else if (Tok.getString() == "push") { 3737 return parseSetPushDirective(); 3738 } else if (Tok.getString() == "reorder") { 3739 return parseSetReorderDirective(); 3740 } else if (Tok.getString() == "noreorder") { 3741 return parseSetNoReorderDirective(); 3742 } else if (Tok.getString() == "macro") { 3743 return parseSetMacroDirective(); 3744 } else if (Tok.getString() == "nomacro") { 3745 return parseSetNoMacroDirective(); 3746 } else if (Tok.getString() == "mips16") { 3747 return parseSetMips16Directive(); 3748 } else if (Tok.getString() == "nomips16") { 3749 return parseSetNoMips16Directive(); 3750 } else if (Tok.getString() == "nomicromips") { 3751 getTargetStreamer().emitDirectiveSetNoMicroMips(); 3752 Parser.eatToEndOfStatement(); 3753 return false; 3754 } else if (Tok.getString() == "micromips") { 3755 return parseSetFeature(Mips::FeatureMicroMips); 3756 } else if (Tok.getString() == "mips0") { 3757 return parseSetMips0Directive(); 3758 } else if (Tok.getString() == "mips1") { 3759 return parseSetFeature(Mips::FeatureMips1); 3760 } else if (Tok.getString() == "mips2") { 3761 return parseSetFeature(Mips::FeatureMips2); 3762 } else if (Tok.getString() == "mips3") { 3763 return parseSetFeature(Mips::FeatureMips3); 3764 } else if (Tok.getString() == "mips4") { 3765 return parseSetFeature(Mips::FeatureMips4); 3766 } else if (Tok.getString() == "mips5") { 3767 return parseSetFeature(Mips::FeatureMips5); 3768 } else if (Tok.getString() == "mips32") { 3769 return parseSetFeature(Mips::FeatureMips32); 3770 } else if (Tok.getString() == "mips32r2") { 3771 return parseSetFeature(Mips::FeatureMips32r2); 3772 } else if (Tok.getString() == "mips32r6") { 3773 return parseSetFeature(Mips::FeatureMips32r6); 3774 } else if (Tok.getString() == "mips64") { 3775 return parseSetFeature(Mips::FeatureMips64); 3776 } else if (Tok.getString() == "mips64r2") { 3777 return parseSetFeature(Mips::FeatureMips64r2); 3778 } else if (Tok.getString() == "mips64r6") { 3779 return parseSetFeature(Mips::FeatureMips64r6); 3780 } else if (Tok.getString() == "dsp") { 3781 return parseSetFeature(Mips::FeatureDSP); 3782 } else if (Tok.getString() == "nodsp") { 3783 return parseSetNoDspDirective(); 3784 } else if (Tok.getString() == "msa") { 3785 return parseSetMsaDirective(); 3786 } else if (Tok.getString() == "nomsa") { 3787 return parseSetNoMsaDirective(); 3788 } else { 3789 // It is just an identifier, look for an assignment. 3790 parseSetAssignment(); 3791 return false; 3792 } 3793 3794 return true; 3795 } 3796 3797 /// parseDataDirective 3798 /// ::= .word [ expression (, expression)* ] 3799 bool MipsAsmParser::parseDataDirective(unsigned Size, SMLoc L) { 3800 MCAsmParser &Parser = getParser(); 3801 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3802 for (;;) { 3803 const MCExpr *Value; 3804 if (getParser().parseExpression(Value)) 3805 return true; 3806 3807 getParser().getStreamer().EmitValue(Value, Size); 3808 3809 if (getLexer().is(AsmToken::EndOfStatement)) 3810 break; 3811 3812 if (getLexer().isNot(AsmToken::Comma)) 3813 return Error(L, "unexpected token, expected comma"); 3814 Parser.Lex(); 3815 } 3816 } 3817 3818 Parser.Lex(); 3819 return false; 3820 } 3821 3822 /// parseDirectiveGpWord 3823 /// ::= .gpword local_sym 3824 bool MipsAsmParser::parseDirectiveGpWord() { 3825 MCAsmParser &Parser = getParser(); 3826 const MCExpr *Value; 3827 // EmitGPRel32Value requires an expression, so we are using base class 3828 // method to evaluate the expression. 3829 if (getParser().parseExpression(Value)) 3830 return true; 3831 getParser().getStreamer().EmitGPRel32Value(Value); 3832 3833 if (getLexer().isNot(AsmToken::EndOfStatement)) 3834 return Error(getLexer().getLoc(), 3835 "unexpected token, expected end of statement"); 3836 Parser.Lex(); // Eat EndOfStatement token. 3837 return false; 3838 } 3839 3840 /// parseDirectiveGpDWord 3841 /// ::= .gpdword local_sym 3842 bool MipsAsmParser::parseDirectiveGpDWord() { 3843 MCAsmParser &Parser = getParser(); 3844 const MCExpr *Value; 3845 // EmitGPRel64Value requires an expression, so we are using base class 3846 // method to evaluate the expression. 3847 if (getParser().parseExpression(Value)) 3848 return true; 3849 getParser().getStreamer().EmitGPRel64Value(Value); 3850 3851 if (getLexer().isNot(AsmToken::EndOfStatement)) 3852 return Error(getLexer().getLoc(), 3853 "unexpected token, expected end of statement"); 3854 Parser.Lex(); // Eat EndOfStatement token. 3855 return false; 3856 } 3857 3858 bool MipsAsmParser::parseDirectiveOption() { 3859 MCAsmParser &Parser = getParser(); 3860 // Get the option token. 3861 AsmToken Tok = Parser.getTok(); 3862 // At the moment only identifiers are supported. 3863 if (Tok.isNot(AsmToken::Identifier)) { 3864 Error(Parser.getTok().getLoc(), "unexpected token, expected identifier"); 3865 Parser.eatToEndOfStatement(); 3866 return false; 3867 } 3868 3869 StringRef Option = Tok.getIdentifier(); 3870 3871 if (Option == "pic0") { 3872 getTargetStreamer().emitDirectiveOptionPic0(); 3873 Parser.Lex(); 3874 if (Parser.getTok().isNot(AsmToken::EndOfStatement)) { 3875 Error(Parser.getTok().getLoc(), 3876 "unexpected token, expected end of statement"); 3877 Parser.eatToEndOfStatement(); 3878 } 3879 return false; 3880 } 3881 3882 if (Option == "pic2") { 3883 getTargetStreamer().emitDirectiveOptionPic2(); 3884 Parser.Lex(); 3885 if (Parser.getTok().isNot(AsmToken::EndOfStatement)) { 3886 Error(Parser.getTok().getLoc(), 3887 "unexpected token, expected end of statement"); 3888 Parser.eatToEndOfStatement(); 3889 } 3890 return false; 3891 } 3892 3893 // Unknown option. 3894 Warning(Parser.getTok().getLoc(), 3895 "unknown option, expected 'pic0' or 'pic2'"); 3896 Parser.eatToEndOfStatement(); 3897 return false; 3898 } 3899 3900 /// parseDirectiveModule 3901 /// ::= .module oddspreg 3902 /// ::= .module nooddspreg 3903 /// ::= .module fp=value 3904 bool MipsAsmParser::parseDirectiveModule() { 3905 MCAsmParser &Parser = getParser(); 3906 MCAsmLexer &Lexer = getLexer(); 3907 SMLoc L = Lexer.getLoc(); 3908 3909 if (!getTargetStreamer().isModuleDirectiveAllowed()) { 3910 // TODO : get a better message. 3911 reportParseError(".module directive must appear before any code"); 3912 return false; 3913 } 3914 3915 StringRef Option; 3916 if (Parser.parseIdentifier(Option)) { 3917 reportParseError("expected .module option identifier"); 3918 return false; 3919 } 3920 3921 if (Option == "oddspreg") { 3922 getTargetStreamer().emitDirectiveModuleOddSPReg(true, isABI_O32()); 3923 clearFeatureBits(Mips::FeatureNoOddSPReg, "nooddspreg"); 3924 3925 // If this is not the end of the statement, report an error. 3926 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3927 reportParseError("unexpected token, expected end of statement"); 3928 return false; 3929 } 3930 3931 return false; // parseDirectiveModule has finished successfully. 3932 } else if (Option == "nooddspreg") { 3933 if (!isABI_O32()) { 3934 Error(L, "'.module nooddspreg' requires the O32 ABI"); 3935 return false; 3936 } 3937 3938 getTargetStreamer().emitDirectiveModuleOddSPReg(false, isABI_O32()); 3939 setFeatureBits(Mips::FeatureNoOddSPReg, "nooddspreg"); 3940 3941 // If this is not the end of the statement, report an error. 3942 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3943 reportParseError("unexpected token, expected end of statement"); 3944 return false; 3945 } 3946 3947 return false; // parseDirectiveModule has finished successfully. 3948 } else if (Option == "fp") { 3949 return parseDirectiveModuleFP(); 3950 } else { 3951 return Error(L, "'" + Twine(Option) + "' is not a valid .module option."); 3952 } 3953 } 3954 3955 /// parseDirectiveModuleFP 3956 /// ::= =32 3957 /// ::= =xx 3958 /// ::= =64 3959 bool MipsAsmParser::parseDirectiveModuleFP() { 3960 MCAsmParser &Parser = getParser(); 3961 MCAsmLexer &Lexer = getLexer(); 3962 3963 if (Lexer.isNot(AsmToken::Equal)) { 3964 reportParseError("unexpected token, expected equals sign '='"); 3965 return false; 3966 } 3967 Parser.Lex(); // Eat '=' token. 3968 3969 MipsABIFlagsSection::FpABIKind FpABI; 3970 if (!parseFpABIValue(FpABI, ".module")) 3971 return false; 3972 3973 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3974 reportParseError("unexpected token, expected end of statement"); 3975 return false; 3976 } 3977 3978 // Emit appropriate flags. 3979 getTargetStreamer().emitDirectiveModuleFP(FpABI, isABI_O32()); 3980 Parser.Lex(); // Consume the EndOfStatement. 3981 return false; 3982 } 3983 3984 bool MipsAsmParser::parseFpABIValue(MipsABIFlagsSection::FpABIKind &FpABI, 3985 StringRef Directive) { 3986 MCAsmParser &Parser = getParser(); 3987 MCAsmLexer &Lexer = getLexer(); 3988 3989 if (Lexer.is(AsmToken::Identifier)) { 3990 StringRef Value = Parser.getTok().getString(); 3991 Parser.Lex(); 3992 3993 if (Value != "xx") { 3994 reportParseError("unsupported value, expected 'xx', '32' or '64'"); 3995 return false; 3996 } 3997 3998 if (!isABI_O32()) { 3999 reportParseError("'" + Directive + " fp=xx' requires the O32 ABI"); 4000 return false; 4001 } 4002 4003 FpABI = MipsABIFlagsSection::FpABIKind::XX; 4004 return true; 4005 } 4006 4007 if (Lexer.is(AsmToken::Integer)) { 4008 unsigned Value = Parser.getTok().getIntVal(); 4009 Parser.Lex(); 4010 4011 if (Value != 32 && Value != 64) { 4012 reportParseError("unsupported value, expected 'xx', '32' or '64'"); 4013 return false; 4014 } 4015 4016 if (Value == 32) { 4017 if (!isABI_O32()) { 4018 reportParseError("'" + Directive + " fp=32' requires the O32 ABI"); 4019 return false; 4020 } 4021 4022 FpABI = MipsABIFlagsSection::FpABIKind::S32; 4023 } else 4024 FpABI = MipsABIFlagsSection::FpABIKind::S64; 4025 4026 return true; 4027 } 4028 4029 return false; 4030 } 4031 4032 bool MipsAsmParser::ParseDirective(AsmToken DirectiveID) { 4033 MCAsmParser &Parser = getParser(); 4034 StringRef IDVal = DirectiveID.getString(); 4035 4036 if (IDVal == ".cpload") 4037 return parseDirectiveCpLoad(DirectiveID.getLoc()); 4038 if (IDVal == ".dword") { 4039 parseDataDirective(8, DirectiveID.getLoc()); 4040 return false; 4041 } 4042 if (IDVal == ".ent") { 4043 StringRef SymbolName; 4044 4045 if (Parser.parseIdentifier(SymbolName)) { 4046 reportParseError("expected identifier after .ent"); 4047 return false; 4048 } 4049 4050 // There's an undocumented extension that allows an integer to 4051 // follow the name of the procedure which AFAICS is ignored by GAS. 4052 // Example: .ent foo,2 4053 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4054 if (getLexer().isNot(AsmToken::Comma)) { 4055 // Even though we accept this undocumented extension for compatibility 4056 // reasons, the additional integer argument does not actually change 4057 // the behaviour of the '.ent' directive, so we would like to discourage 4058 // its use. We do this by not referring to the extended version in 4059 // error messages which are not directly related to its use. 4060 reportParseError("unexpected token, expected end of statement"); 4061 return false; 4062 } 4063 Parser.Lex(); // Eat the comma. 4064 const MCExpr *DummyNumber; 4065 int64_t DummyNumberVal; 4066 // If the user was explicitly trying to use the extended version, 4067 // we still give helpful extension-related error messages. 4068 if (Parser.parseExpression(DummyNumber)) { 4069 reportParseError("expected number after comma"); 4070 return false; 4071 } 4072 if (!DummyNumber->EvaluateAsAbsolute(DummyNumberVal)) { 4073 reportParseError("expected an absolute expression after comma"); 4074 return false; 4075 } 4076 } 4077 4078 // If this is not the end of the statement, report an error. 4079 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4080 reportParseError("unexpected token, expected end of statement"); 4081 return false; 4082 } 4083 4084 MCSymbol *Sym = getContext().GetOrCreateSymbol(SymbolName); 4085 4086 getTargetStreamer().emitDirectiveEnt(*Sym); 4087 CurrentFn = Sym; 4088 return false; 4089 } 4090 4091 if (IDVal == ".end") { 4092 StringRef SymbolName; 4093 4094 if (Parser.parseIdentifier(SymbolName)) { 4095 reportParseError("expected identifier after .end"); 4096 return false; 4097 } 4098 4099 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4100 reportParseError("unexpected token, expected end of statement"); 4101 return false; 4102 } 4103 4104 if (CurrentFn == nullptr) { 4105 reportParseError(".end used without .ent"); 4106 return false; 4107 } 4108 4109 if ((SymbolName != CurrentFn->getName())) { 4110 reportParseError(".end symbol does not match .ent symbol"); 4111 return false; 4112 } 4113 4114 getTargetStreamer().emitDirectiveEnd(SymbolName); 4115 CurrentFn = nullptr; 4116 return false; 4117 } 4118 4119 if (IDVal == ".frame") { 4120 // .frame $stack_reg, frame_size_in_bytes, $return_reg 4121 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> TmpReg; 4122 OperandMatchResultTy ResTy = parseAnyRegister(TmpReg); 4123 if (ResTy == MatchOperand_NoMatch || ResTy == MatchOperand_ParseFail) { 4124 reportParseError("expected stack register"); 4125 return false; 4126 } 4127 4128 MipsOperand &StackRegOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 4129 if (!StackRegOpnd.isGPRAsmReg()) { 4130 reportParseError(StackRegOpnd.getStartLoc(), 4131 "expected general purpose register"); 4132 return false; 4133 } 4134 unsigned StackReg = StackRegOpnd.getGPR32Reg(); 4135 4136 if (Parser.getTok().is(AsmToken::Comma)) 4137 Parser.Lex(); 4138 else { 4139 reportParseError("unexpected token, expected comma"); 4140 return false; 4141 } 4142 4143 // Parse the frame size. 4144 const MCExpr *FrameSize; 4145 int64_t FrameSizeVal; 4146 4147 if (Parser.parseExpression(FrameSize)) { 4148 reportParseError("expected frame size value"); 4149 return false; 4150 } 4151 4152 if (!FrameSize->EvaluateAsAbsolute(FrameSizeVal)) { 4153 reportParseError("frame size not an absolute expression"); 4154 return false; 4155 } 4156 4157 if (Parser.getTok().is(AsmToken::Comma)) 4158 Parser.Lex(); 4159 else { 4160 reportParseError("unexpected token, expected comma"); 4161 return false; 4162 } 4163 4164 // Parse the return register. 4165 TmpReg.clear(); 4166 ResTy = parseAnyRegister(TmpReg); 4167 if (ResTy == MatchOperand_NoMatch || ResTy == MatchOperand_ParseFail) { 4168 reportParseError("expected return register"); 4169 return false; 4170 } 4171 4172 MipsOperand &ReturnRegOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 4173 if (!ReturnRegOpnd.isGPRAsmReg()) { 4174 reportParseError(ReturnRegOpnd.getStartLoc(), 4175 "expected general purpose register"); 4176 return false; 4177 } 4178 4179 // If this is not the end of the statement, report an error. 4180 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4181 reportParseError("unexpected token, expected end of statement"); 4182 return false; 4183 } 4184 4185 getTargetStreamer().emitFrame(StackReg, FrameSizeVal, 4186 ReturnRegOpnd.getGPR32Reg()); 4187 return false; 4188 } 4189 4190 if (IDVal == ".set") { 4191 return parseDirectiveSet(); 4192 } 4193 4194 if (IDVal == ".mask" || IDVal == ".fmask") { 4195 // .mask bitmask, frame_offset 4196 // bitmask: One bit for each register used. 4197 // frame_offset: Offset from Canonical Frame Address ($sp on entry) where 4198 // first register is expected to be saved. 4199 // Examples: 4200 // .mask 0x80000000, -4 4201 // .fmask 0x80000000, -4 4202 // 4203 4204 // Parse the bitmask 4205 const MCExpr *BitMask; 4206 int64_t BitMaskVal; 4207 4208 if (Parser.parseExpression(BitMask)) { 4209 reportParseError("expected bitmask value"); 4210 return false; 4211 } 4212 4213 if (!BitMask->EvaluateAsAbsolute(BitMaskVal)) { 4214 reportParseError("bitmask not an absolute expression"); 4215 return false; 4216 } 4217 4218 if (Parser.getTok().is(AsmToken::Comma)) 4219 Parser.Lex(); 4220 else { 4221 reportParseError("unexpected token, expected comma"); 4222 return false; 4223 } 4224 4225 // Parse the frame_offset 4226 const MCExpr *FrameOffset; 4227 int64_t FrameOffsetVal; 4228 4229 if (Parser.parseExpression(FrameOffset)) { 4230 reportParseError("expected frame offset value"); 4231 return false; 4232 } 4233 4234 if (!FrameOffset->EvaluateAsAbsolute(FrameOffsetVal)) { 4235 reportParseError("frame offset not an absolute expression"); 4236 return false; 4237 } 4238 4239 // If this is not the end of the statement, report an error. 4240 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4241 reportParseError("unexpected token, expected end of statement"); 4242 return false; 4243 } 4244 4245 if (IDVal == ".mask") 4246 getTargetStreamer().emitMask(BitMaskVal, FrameOffsetVal); 4247 else 4248 getTargetStreamer().emitFMask(BitMaskVal, FrameOffsetVal); 4249 return false; 4250 } 4251 4252 if (IDVal == ".nan") 4253 return parseDirectiveNaN(); 4254 4255 if (IDVal == ".gpword") { 4256 parseDirectiveGpWord(); 4257 return false; 4258 } 4259 4260 if (IDVal == ".gpdword") { 4261 parseDirectiveGpDWord(); 4262 return false; 4263 } 4264 4265 if (IDVal == ".word") { 4266 parseDataDirective(4, DirectiveID.getLoc()); 4267 return false; 4268 } 4269 4270 if (IDVal == ".option") 4271 return parseDirectiveOption(); 4272 4273 if (IDVal == ".abicalls") { 4274 getTargetStreamer().emitDirectiveAbiCalls(); 4275 if (Parser.getTok().isNot(AsmToken::EndOfStatement)) { 4276 Error(Parser.getTok().getLoc(), 4277 "unexpected token, expected end of statement"); 4278 // Clear line 4279 Parser.eatToEndOfStatement(); 4280 } 4281 return false; 4282 } 4283 4284 if (IDVal == ".cpsetup") 4285 return parseDirectiveCPSetup(); 4286 4287 if (IDVal == ".module") 4288 return parseDirectiveModule(); 4289 4290 return true; 4291 } 4292 4293 extern "C" void LLVMInitializeMipsAsmParser() { 4294 RegisterMCAsmParser<MipsAsmParser> X(TheMipsTarget); 4295 RegisterMCAsmParser<MipsAsmParser> Y(TheMipselTarget); 4296 RegisterMCAsmParser<MipsAsmParser> A(TheMips64Target); 4297 RegisterMCAsmParser<MipsAsmParser> B(TheMips64elTarget); 4298 } 4299 4300 #define GET_REGISTER_MATCHER 4301 #define GET_MATCHER_IMPLEMENTATION 4302 #include "MipsGenAsmMatcher.inc" 4303