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 "MipsTargetObjectFile.h" 15 #include "MipsTargetStreamer.h" 16 #include "MCTargetDesc/MipsBaseInfo.h" 17 #include "llvm/ADT/SmallVector.h" 18 #include "llvm/ADT/StringSwitch.h" 19 #include "llvm/MC/MCContext.h" 20 #include "llvm/MC/MCExpr.h" 21 #include "llvm/MC/MCInst.h" 22 #include "llvm/MC/MCInstBuilder.h" 23 #include "llvm/MC/MCParser/MCAsmLexer.h" 24 #include "llvm/MC/MCParser/MCParsedAsmOperand.h" 25 #include "llvm/MC/MCParser/MCTargetAsmParser.h" 26 #include "llvm/MC/MCSectionELF.h" 27 #include "llvm/MC/MCStreamer.h" 28 #include "llvm/MC/MCSubtargetInfo.h" 29 #include "llvm/MC/MCSymbol.h" 30 #include "llvm/Support/Debug.h" 31 #include "llvm/Support/ELF.h" 32 #include "llvm/Support/MathExtras.h" 33 #include "llvm/Support/SourceMgr.h" 34 #include "llvm/Support/TargetRegistry.h" 35 #include "llvm/Support/raw_ostream.h" 36 #include <memory> 37 38 using namespace llvm; 39 40 #define DEBUG_TYPE "mips-asm-parser" 41 42 namespace llvm { 43 class MCInstrInfo; 44 } 45 46 namespace { 47 class MipsAssemblerOptions { 48 public: 49 MipsAssemblerOptions(const FeatureBitset &Features_) : 50 ATReg(1), Reorder(true), Macro(true), Features(Features_) {} 51 52 MipsAssemblerOptions(const MipsAssemblerOptions *Opts) { 53 ATReg = Opts->getATRegIndex(); 54 Reorder = Opts->isReorder(); 55 Macro = Opts->isMacro(); 56 Features = Opts->getFeatures(); 57 } 58 59 unsigned getATRegIndex() const { return ATReg; } 60 bool setATRegIndex(unsigned Reg) { 61 if (Reg > 31) 62 return false; 63 64 ATReg = Reg; 65 return true; 66 } 67 68 bool isReorder() const { return Reorder; } 69 void setReorder() { Reorder = true; } 70 void setNoReorder() { Reorder = false; } 71 72 bool isMacro() const { return Macro; } 73 void setMacro() { Macro = true; } 74 void setNoMacro() { Macro = false; } 75 76 const FeatureBitset &getFeatures() const { return Features; } 77 void setFeatures(const FeatureBitset &Features_) { Features = Features_; } 78 79 // Set of features that are either architecture features or referenced 80 // by them (e.g.: FeatureNaN2008 implied by FeatureMips32r6). 81 // The full table can be found in MipsGenSubtargetInfo.inc (MipsFeatureKV[]). 82 // The reason we need this mask is explained in the selectArch function. 83 // FIXME: Ideally we would like TableGen to generate this information. 84 static const FeatureBitset AllArchRelatedMask; 85 86 private: 87 unsigned ATReg; 88 bool Reorder; 89 bool Macro; 90 FeatureBitset Features; 91 }; 92 } 93 94 const FeatureBitset MipsAssemblerOptions::AllArchRelatedMask = { 95 Mips::FeatureMips1, Mips::FeatureMips2, Mips::FeatureMips3, 96 Mips::FeatureMips3_32, Mips::FeatureMips3_32r2, Mips::FeatureMips4, 97 Mips::FeatureMips4_32, Mips::FeatureMips4_32r2, Mips::FeatureMips5, 98 Mips::FeatureMips5_32r2, Mips::FeatureMips32, Mips::FeatureMips32r2, 99 Mips::FeatureMips32r3, Mips::FeatureMips32r5, Mips::FeatureMips32r6, 100 Mips::FeatureMips64, Mips::FeatureMips64r2, Mips::FeatureMips64r3, 101 Mips::FeatureMips64r5, Mips::FeatureMips64r6, Mips::FeatureCnMips, 102 Mips::FeatureFP64Bit, Mips::FeatureGP64Bit, Mips::FeatureNaN2008 103 }; 104 105 namespace { 106 class MipsAsmParser : public MCTargetAsmParser { 107 MipsTargetStreamer &getTargetStreamer() { 108 MCTargetStreamer &TS = *getParser().getStreamer().getTargetStreamer(); 109 return static_cast<MipsTargetStreamer &>(TS); 110 } 111 112 MipsABIInfo ABI; 113 SmallVector<std::unique_ptr<MipsAssemblerOptions>, 2> AssemblerOptions; 114 MCSymbol *CurrentFn; // Pointer to the function being parsed. It may be a 115 // nullptr, which indicates that no function is currently 116 // selected. This usually happens after an '.end func' 117 // directive. 118 bool IsLittleEndian; 119 bool IsPicEnabled; 120 bool IsCpRestoreSet; 121 int CpRestoreOffset; 122 unsigned CpSaveLocation; 123 /// If true, then CpSaveLocation is a register, otherwise it's an offset. 124 bool CpSaveLocationIsRegister; 125 126 // Print a warning along with its fix-it message at the given range. 127 void printWarningWithFixIt(const Twine &Msg, const Twine &FixMsg, 128 SMRange Range, bool ShowColors = true); 129 130 #define GET_ASSEMBLER_HEADER 131 #include "MipsGenAsmMatcher.inc" 132 133 unsigned 134 checkEarlyTargetMatchPredicate(MCInst &Inst, 135 const OperandVector &Operands) override; 136 unsigned checkTargetMatchPredicate(MCInst &Inst) override; 137 138 bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, 139 OperandVector &Operands, MCStreamer &Out, 140 uint64_t &ErrorInfo, 141 bool MatchingInlineAsm) override; 142 143 /// Parse a register as used in CFI directives 144 bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc) override; 145 146 bool parseParenSuffix(StringRef Name, OperandVector &Operands); 147 148 bool parseBracketSuffix(StringRef Name, OperandVector &Operands); 149 150 bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name, 151 SMLoc NameLoc, OperandVector &Operands) override; 152 153 bool ParseDirective(AsmToken DirectiveID) override; 154 155 OperandMatchResultTy parseMemOperand(OperandVector &Operands); 156 OperandMatchResultTy 157 matchAnyRegisterNameWithoutDollar(OperandVector &Operands, 158 StringRef Identifier, SMLoc S); 159 OperandMatchResultTy matchAnyRegisterWithoutDollar(OperandVector &Operands, 160 SMLoc S); 161 OperandMatchResultTy parseAnyRegister(OperandVector &Operands); 162 OperandMatchResultTy parseImm(OperandVector &Operands); 163 OperandMatchResultTy parseJumpTarget(OperandVector &Operands); 164 OperandMatchResultTy parseInvNum(OperandVector &Operands); 165 OperandMatchResultTy parseRegisterPair(OperandVector &Operands); 166 OperandMatchResultTy parseMovePRegPair(OperandVector &Operands); 167 OperandMatchResultTy parseRegisterList(OperandVector &Operands); 168 169 bool searchSymbolAlias(OperandVector &Operands); 170 171 bool parseOperand(OperandVector &, StringRef Mnemonic); 172 173 enum MacroExpanderResultTy { 174 MER_NotAMacro, 175 MER_Success, 176 MER_Fail, 177 }; 178 179 // Expands assembly pseudo instructions. 180 MacroExpanderResultTy tryExpandInstruction(MCInst &Inst, SMLoc IDLoc, 181 MCStreamer &Out, 182 const MCSubtargetInfo *STI); 183 184 bool expandJalWithRegs(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 185 const MCSubtargetInfo *STI); 186 187 bool loadImmediate(int64_t ImmValue, unsigned DstReg, unsigned SrcReg, 188 bool Is32BitImm, bool IsAddress, SMLoc IDLoc, 189 MCStreamer &Out, const MCSubtargetInfo *STI); 190 191 bool loadAndAddSymbolAddress(const MCExpr *SymExpr, unsigned DstReg, 192 unsigned SrcReg, bool Is32BitSym, SMLoc IDLoc, 193 MCStreamer &Out, const MCSubtargetInfo *STI); 194 195 bool expandLoadImm(MCInst &Inst, bool Is32BitImm, SMLoc IDLoc, 196 MCStreamer &Out, const MCSubtargetInfo *STI); 197 198 bool expandLoadAddress(unsigned DstReg, unsigned BaseReg, 199 const MCOperand &Offset, bool Is32BitAddress, 200 SMLoc IDLoc, MCStreamer &Out, 201 const MCSubtargetInfo *STI); 202 203 bool expandUncondBranchMMPseudo(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 204 const MCSubtargetInfo *STI); 205 206 void expandMemInst(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 207 const MCSubtargetInfo *STI, bool IsLoad, bool IsImmOpnd); 208 209 void expandLoadInst(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 210 const MCSubtargetInfo *STI, bool IsImmOpnd); 211 212 void expandStoreInst(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 213 const MCSubtargetInfo *STI, bool IsImmOpnd); 214 215 bool expandLoadStoreMultiple(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 216 const MCSubtargetInfo *STI); 217 218 bool expandAliasImmediate(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 219 const MCSubtargetInfo *STI); 220 221 bool expandBranchImm(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 222 const MCSubtargetInfo *STI); 223 224 bool expandCondBranches(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 225 const MCSubtargetInfo *STI); 226 227 bool expandDiv(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 228 const MCSubtargetInfo *STI, const bool IsMips64, 229 const bool Signed); 230 231 bool expandTrunc(MCInst &Inst, bool IsDouble, bool Is64FPU, SMLoc IDLoc, 232 MCStreamer &Out, const MCSubtargetInfo *STI); 233 234 bool expandUlh(MCInst &Inst, bool Signed, SMLoc IDLoc, MCStreamer &Out, 235 const MCSubtargetInfo *STI); 236 237 bool expandUlw(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 238 const MCSubtargetInfo *STI); 239 240 bool expandRotation(MCInst &Inst, SMLoc IDLoc, 241 MCStreamer &Out, const MCSubtargetInfo *STI); 242 bool expandRotationImm(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 243 const MCSubtargetInfo *STI); 244 bool expandDRotation(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 245 const MCSubtargetInfo *STI); 246 bool expandDRotationImm(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 247 const MCSubtargetInfo *STI); 248 249 bool expandAbs(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 250 const MCSubtargetInfo *STI); 251 252 bool reportParseError(Twine ErrorMsg); 253 bool reportParseError(SMLoc Loc, Twine ErrorMsg); 254 255 bool parseMemOffset(const MCExpr *&Res, bool isParenExpr); 256 257 bool isEvaluated(const MCExpr *Expr); 258 bool parseSetMips0Directive(); 259 bool parseSetArchDirective(); 260 bool parseSetFeature(uint64_t Feature); 261 bool isPicAndNotNxxAbi(); // Used by .cpload, .cprestore, and .cpsetup. 262 bool parseDirectiveCpLoad(SMLoc Loc); 263 bool parseDirectiveCpRestore(SMLoc Loc); 264 bool parseDirectiveCPSetup(); 265 bool parseDirectiveCPReturn(); 266 bool parseDirectiveNaN(); 267 bool parseDirectiveSet(); 268 bool parseDirectiveOption(); 269 bool parseInsnDirective(); 270 bool parseSSectionDirective(StringRef Section, unsigned Type); 271 272 bool parseSetAtDirective(); 273 bool parseSetNoAtDirective(); 274 bool parseSetMacroDirective(); 275 bool parseSetNoMacroDirective(); 276 bool parseSetMsaDirective(); 277 bool parseSetNoMsaDirective(); 278 bool parseSetNoDspDirective(); 279 bool parseSetReorderDirective(); 280 bool parseSetNoReorderDirective(); 281 bool parseSetMips16Directive(); 282 bool parseSetNoMips16Directive(); 283 bool parseSetFpDirective(); 284 bool parseSetOddSPRegDirective(); 285 bool parseSetNoOddSPRegDirective(); 286 bool parseSetPopDirective(); 287 bool parseSetPushDirective(); 288 bool parseSetSoftFloatDirective(); 289 bool parseSetHardFloatDirective(); 290 291 bool parseSetAssignment(); 292 293 bool parseDataDirective(unsigned Size, SMLoc L); 294 bool parseDirectiveGpWord(); 295 bool parseDirectiveGpDWord(); 296 bool parseDirectiveDtpRelWord(); 297 bool parseDirectiveDtpRelDWord(); 298 bool parseDirectiveTpRelWord(); 299 bool parseDirectiveTpRelDWord(); 300 bool parseDirectiveModule(); 301 bool parseDirectiveModuleFP(); 302 bool parseFpABIValue(MipsABIFlagsSection::FpABIKind &FpABI, 303 StringRef Directive); 304 305 bool parseInternalDirectiveReallowModule(); 306 307 bool eatComma(StringRef ErrorStr); 308 309 int matchCPURegisterName(StringRef Symbol); 310 311 int matchHWRegsRegisterName(StringRef Symbol); 312 313 int matchFPURegisterName(StringRef Name); 314 315 int matchFCCRegisterName(StringRef Name); 316 317 int matchACRegisterName(StringRef Name); 318 319 int matchMSA128RegisterName(StringRef Name); 320 321 int matchMSA128CtrlRegisterName(StringRef Name); 322 323 unsigned getReg(int RC, int RegNo); 324 325 /// Returns the internal register number for the current AT. Also checks if 326 /// the current AT is unavailable (set to $0) and gives an error if it is. 327 /// This should be used in pseudo-instruction expansions which need AT. 328 unsigned getATReg(SMLoc Loc); 329 330 bool processInstruction(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 331 const MCSubtargetInfo *STI); 332 333 // Helper function that checks if the value of a vector index is within the 334 // boundaries of accepted values for each RegisterKind 335 // Example: INSERT.B $w0[n], $1 => 16 > n >= 0 336 bool validateMSAIndex(int Val, int RegKind); 337 338 // Selects a new architecture by updating the FeatureBits with the necessary 339 // info including implied dependencies. 340 // Internally, it clears all the feature bits related to *any* architecture 341 // and selects the new one using the ToggleFeature functionality of the 342 // MCSubtargetInfo object that handles implied dependencies. The reason we 343 // clear all the arch related bits manually is because ToggleFeature only 344 // clears the features that imply the feature being cleared and not the 345 // features implied by the feature being cleared. This is easier to see 346 // with an example: 347 // -------------------------------------------------- 348 // | Feature | Implies | 349 // | -------------------------------------------------| 350 // | FeatureMips1 | None | 351 // | FeatureMips2 | FeatureMips1 | 352 // | FeatureMips3 | FeatureMips2 | FeatureMipsGP64 | 353 // | FeatureMips4 | FeatureMips3 | 354 // | ... | | 355 // -------------------------------------------------- 356 // 357 // Setting Mips3 is equivalent to set: (FeatureMips3 | FeatureMips2 | 358 // FeatureMipsGP64 | FeatureMips1) 359 // Clearing Mips3 is equivalent to clear (FeatureMips3 | FeatureMips4). 360 void selectArch(StringRef ArchFeature) { 361 MCSubtargetInfo &STI = copySTI(); 362 FeatureBitset FeatureBits = STI.getFeatureBits(); 363 FeatureBits &= ~MipsAssemblerOptions::AllArchRelatedMask; 364 STI.setFeatureBits(FeatureBits); 365 setAvailableFeatures( 366 ComputeAvailableFeatures(STI.ToggleFeature(ArchFeature))); 367 AssemblerOptions.back()->setFeatures(STI.getFeatureBits()); 368 } 369 370 void setFeatureBits(uint64_t Feature, StringRef FeatureString) { 371 if (!(getSTI().getFeatureBits()[Feature])) { 372 MCSubtargetInfo &STI = copySTI(); 373 setAvailableFeatures( 374 ComputeAvailableFeatures(STI.ToggleFeature(FeatureString))); 375 AssemblerOptions.back()->setFeatures(STI.getFeatureBits()); 376 } 377 } 378 379 void clearFeatureBits(uint64_t Feature, StringRef FeatureString) { 380 if (getSTI().getFeatureBits()[Feature]) { 381 MCSubtargetInfo &STI = copySTI(); 382 setAvailableFeatures( 383 ComputeAvailableFeatures(STI.ToggleFeature(FeatureString))); 384 AssemblerOptions.back()->setFeatures(STI.getFeatureBits()); 385 } 386 } 387 388 void setModuleFeatureBits(uint64_t Feature, StringRef FeatureString) { 389 setFeatureBits(Feature, FeatureString); 390 AssemblerOptions.front()->setFeatures(getSTI().getFeatureBits()); 391 } 392 393 void clearModuleFeatureBits(uint64_t Feature, StringRef FeatureString) { 394 clearFeatureBits(Feature, FeatureString); 395 AssemblerOptions.front()->setFeatures(getSTI().getFeatureBits()); 396 } 397 398 public: 399 enum MipsMatchResultTy { 400 Match_RequiresDifferentSrcAndDst = FIRST_TARGET_MATCH_RESULT_TY, 401 Match_RequiresDifferentOperands, 402 Match_RequiresNoZeroRegister, 403 Match_RequiresSameSrcAndDst, 404 #define GET_OPERAND_DIAGNOSTIC_TYPES 405 #include "MipsGenAsmMatcher.inc" 406 #undef GET_OPERAND_DIAGNOSTIC_TYPES 407 }; 408 409 MipsAsmParser(const MCSubtargetInfo &sti, MCAsmParser &parser, 410 const MCInstrInfo &MII, const MCTargetOptions &Options) 411 : MCTargetAsmParser(Options, sti), 412 ABI(MipsABIInfo::computeTargetABI(Triple(sti.getTargetTriple()), 413 sti.getCPU(), Options)) { 414 MCAsmParserExtension::Initialize(parser); 415 416 parser.addAliasForDirective(".asciiz", ".asciz"); 417 418 // Initialize the set of available features. 419 setAvailableFeatures(ComputeAvailableFeatures(getSTI().getFeatureBits())); 420 421 // Remember the initial assembler options. The user can not modify these. 422 AssemblerOptions.push_back( 423 llvm::make_unique<MipsAssemblerOptions>(getSTI().getFeatureBits())); 424 425 // Create an assembler options environment for the user to modify. 426 AssemblerOptions.push_back( 427 llvm::make_unique<MipsAssemblerOptions>(getSTI().getFeatureBits())); 428 429 getTargetStreamer().updateABIInfo(*this); 430 431 if (!isABI_O32() && !useOddSPReg() != 0) 432 report_fatal_error("-mno-odd-spreg requires the O32 ABI"); 433 434 CurrentFn = nullptr; 435 436 IsPicEnabled = getContext().getObjectFileInfo()->isPositionIndependent(); 437 438 IsCpRestoreSet = false; 439 CpRestoreOffset = -1; 440 441 const Triple &TheTriple = sti.getTargetTriple(); 442 if ((TheTriple.getArch() == Triple::mips) || 443 (TheTriple.getArch() == Triple::mips64)) 444 IsLittleEndian = false; 445 else 446 IsLittleEndian = true; 447 } 448 449 /// True if all of $fcc0 - $fcc7 exist for the current ISA. 450 bool hasEightFccRegisters() const { return hasMips4() || hasMips32(); } 451 452 bool isGP64bit() const { 453 return getSTI().getFeatureBits()[Mips::FeatureGP64Bit]; 454 } 455 bool isFP64bit() const { 456 return getSTI().getFeatureBits()[Mips::FeatureFP64Bit]; 457 } 458 const MipsABIInfo &getABI() const { return ABI; } 459 bool isABI_N32() const { return ABI.IsN32(); } 460 bool isABI_N64() const { return ABI.IsN64(); } 461 bool isABI_O32() const { return ABI.IsO32(); } 462 bool isABI_FPXX() const { 463 return getSTI().getFeatureBits()[Mips::FeatureFPXX]; 464 } 465 466 bool useOddSPReg() const { 467 return !(getSTI().getFeatureBits()[Mips::FeatureNoOddSPReg]); 468 } 469 470 bool inMicroMipsMode() const { 471 return getSTI().getFeatureBits()[Mips::FeatureMicroMips]; 472 } 473 bool hasMips1() const { 474 return getSTI().getFeatureBits()[Mips::FeatureMips1]; 475 } 476 bool hasMips2() const { 477 return getSTI().getFeatureBits()[Mips::FeatureMips2]; 478 } 479 bool hasMips3() const { 480 return getSTI().getFeatureBits()[Mips::FeatureMips3]; 481 } 482 bool hasMips4() const { 483 return getSTI().getFeatureBits()[Mips::FeatureMips4]; 484 } 485 bool hasMips5() const { 486 return getSTI().getFeatureBits()[Mips::FeatureMips5]; 487 } 488 bool hasMips32() const { 489 return getSTI().getFeatureBits()[Mips::FeatureMips32]; 490 } 491 bool hasMips64() const { 492 return getSTI().getFeatureBits()[Mips::FeatureMips64]; 493 } 494 bool hasMips32r2() const { 495 return getSTI().getFeatureBits()[Mips::FeatureMips32r2]; 496 } 497 bool hasMips64r2() const { 498 return getSTI().getFeatureBits()[Mips::FeatureMips64r2]; 499 } 500 bool hasMips32r3() const { 501 return (getSTI().getFeatureBits()[Mips::FeatureMips32r3]); 502 } 503 bool hasMips64r3() const { 504 return (getSTI().getFeatureBits()[Mips::FeatureMips64r3]); 505 } 506 bool hasMips32r5() const { 507 return (getSTI().getFeatureBits()[Mips::FeatureMips32r5]); 508 } 509 bool hasMips64r5() const { 510 return (getSTI().getFeatureBits()[Mips::FeatureMips64r5]); 511 } 512 bool hasMips32r6() const { 513 return getSTI().getFeatureBits()[Mips::FeatureMips32r6]; 514 } 515 bool hasMips64r6() const { 516 return getSTI().getFeatureBits()[Mips::FeatureMips64r6]; 517 } 518 519 bool hasDSP() const { 520 return getSTI().getFeatureBits()[Mips::FeatureDSP]; 521 } 522 bool hasDSPR2() const { 523 return getSTI().getFeatureBits()[Mips::FeatureDSPR2]; 524 } 525 bool hasDSPR3() const { 526 return getSTI().getFeatureBits()[Mips::FeatureDSPR3]; 527 } 528 bool hasMSA() const { 529 return getSTI().getFeatureBits()[Mips::FeatureMSA]; 530 } 531 bool hasCnMips() const { 532 return (getSTI().getFeatureBits()[Mips::FeatureCnMips]); 533 } 534 535 bool inPicMode() { 536 return IsPicEnabled; 537 } 538 539 bool inMips16Mode() const { 540 return getSTI().getFeatureBits()[Mips::FeatureMips16]; 541 } 542 543 bool useTraps() const { 544 return getSTI().getFeatureBits()[Mips::FeatureUseTCCInDIV]; 545 } 546 547 bool useSoftFloat() const { 548 return getSTI().getFeatureBits()[Mips::FeatureSoftFloat]; 549 } 550 551 /// Warn if RegIndex is the same as the current AT. 552 void warnIfRegIndexIsAT(unsigned RegIndex, SMLoc Loc); 553 554 void warnIfNoMacro(SMLoc Loc); 555 556 bool isLittle() const { return IsLittleEndian; } 557 558 const MCExpr *createTargetUnaryExpr(const MCExpr *E, 559 AsmToken::TokenKind OperatorToken, 560 MCContext &Ctx) override { 561 switch(OperatorToken) { 562 default: 563 llvm_unreachable("Unknown token"); 564 return nullptr; 565 case AsmToken::PercentCall16: 566 return MipsMCExpr::create(MipsMCExpr::MEK_GOT_CALL, E, Ctx); 567 case AsmToken::PercentCall_Hi: 568 return MipsMCExpr::create(MipsMCExpr::MEK_CALL_HI16, E, Ctx); 569 case AsmToken::PercentCall_Lo: 570 return MipsMCExpr::create(MipsMCExpr::MEK_CALL_LO16, E, Ctx); 571 case AsmToken::PercentDtprel_Hi: 572 return MipsMCExpr::create(MipsMCExpr::MEK_DTPREL_HI, E, Ctx); 573 case AsmToken::PercentDtprel_Lo: 574 return MipsMCExpr::create(MipsMCExpr::MEK_DTPREL_LO, E, Ctx); 575 case AsmToken::PercentGot: 576 return MipsMCExpr::create(MipsMCExpr::MEK_GOT, E, Ctx); 577 case AsmToken::PercentGot_Disp: 578 return MipsMCExpr::create(MipsMCExpr::MEK_GOT_DISP, E, Ctx); 579 case AsmToken::PercentGot_Hi: 580 return MipsMCExpr::create(MipsMCExpr::MEK_GOT_HI16, E, Ctx); 581 case AsmToken::PercentGot_Lo: 582 return MipsMCExpr::create(MipsMCExpr::MEK_GOT_LO16, E, Ctx); 583 case AsmToken::PercentGot_Ofst: 584 return MipsMCExpr::create(MipsMCExpr::MEK_GOT_OFST, E, Ctx); 585 case AsmToken::PercentGot_Page: 586 return MipsMCExpr::create(MipsMCExpr::MEK_GOT_PAGE, E, Ctx); 587 case AsmToken::PercentGottprel: 588 return MipsMCExpr::create(MipsMCExpr::MEK_GOTTPREL, E, Ctx); 589 case AsmToken::PercentGp_Rel: 590 return MipsMCExpr::create(MipsMCExpr::MEK_GPREL, E, Ctx); 591 case AsmToken::PercentHi: 592 return MipsMCExpr::create(MipsMCExpr::MEK_HI, E, Ctx); 593 case AsmToken::PercentHigher: 594 return MipsMCExpr::create(MipsMCExpr::MEK_HIGHER, E, Ctx); 595 case AsmToken::PercentHighest: 596 return MipsMCExpr::create(MipsMCExpr::MEK_HIGHEST, E, Ctx); 597 case AsmToken::PercentLo: 598 return MipsMCExpr::create(MipsMCExpr::MEK_LO, E, Ctx); 599 case AsmToken::PercentNeg: 600 return MipsMCExpr::create(MipsMCExpr::MEK_NEG, E, Ctx); 601 case AsmToken::PercentPcrel_Hi: 602 return MipsMCExpr::create(MipsMCExpr::MEK_PCREL_HI16, E, Ctx); 603 case AsmToken::PercentPcrel_Lo: 604 return MipsMCExpr::create(MipsMCExpr::MEK_PCREL_LO16, E, Ctx); 605 case AsmToken::PercentTlsgd: 606 return MipsMCExpr::create(MipsMCExpr::MEK_TLSGD, E, Ctx); 607 case AsmToken::PercentTlsldm: 608 return MipsMCExpr::create(MipsMCExpr::MEK_TLSLDM, E, Ctx); 609 case AsmToken::PercentTprel_Hi: 610 return MipsMCExpr::create(MipsMCExpr::MEK_TPREL_HI, E, Ctx); 611 case AsmToken::PercentTprel_Lo: 612 return MipsMCExpr::create(MipsMCExpr::MEK_TPREL_LO, E, Ctx); 613 } 614 } 615 }; 616 } 617 618 namespace { 619 620 /// MipsOperand - Instances of this class represent a parsed Mips machine 621 /// instruction. 622 class MipsOperand : public MCParsedAsmOperand { 623 public: 624 /// Broad categories of register classes 625 /// The exact class is finalized by the render method. 626 enum RegKind { 627 RegKind_GPR = 1, /// GPR32 and GPR64 (depending on isGP64bit()) 628 RegKind_FGR = 2, /// FGR32, FGR64, AFGR64 (depending on context and 629 /// isFP64bit()) 630 RegKind_FCC = 4, /// FCC 631 RegKind_MSA128 = 8, /// MSA128[BHWD] (makes no difference which) 632 RegKind_MSACtrl = 16, /// MSA control registers 633 RegKind_COP2 = 32, /// COP2 634 RegKind_ACC = 64, /// HI32DSP, LO32DSP, and ACC64DSP (depending on 635 /// context). 636 RegKind_CCR = 128, /// CCR 637 RegKind_HWRegs = 256, /// HWRegs 638 RegKind_COP3 = 512, /// COP3 639 RegKind_COP0 = 1024, /// COP0 640 /// Potentially any (e.g. $1) 641 RegKind_Numeric = RegKind_GPR | RegKind_FGR | RegKind_FCC | RegKind_MSA128 | 642 RegKind_MSACtrl | RegKind_COP2 | RegKind_ACC | 643 RegKind_CCR | RegKind_HWRegs | RegKind_COP3 | RegKind_COP0 644 }; 645 646 private: 647 enum KindTy { 648 k_Immediate, /// An immediate (possibly involving symbol references) 649 k_Memory, /// Base + Offset Memory Address 650 k_RegisterIndex, /// A register index in one or more RegKind. 651 k_Token, /// A simple token 652 k_RegList, /// A physical register list 653 k_RegPair /// A pair of physical register 654 } Kind; 655 656 public: 657 MipsOperand(KindTy K, MipsAsmParser &Parser) 658 : MCParsedAsmOperand(), Kind(K), AsmParser(Parser) {} 659 660 private: 661 /// For diagnostics, and checking the assembler temporary 662 MipsAsmParser &AsmParser; 663 664 struct Token { 665 const char *Data; 666 unsigned Length; 667 }; 668 669 struct RegIdxOp { 670 unsigned Index; /// Index into the register class 671 RegKind Kind; /// Bitfield of the kinds it could possibly be 672 struct Token Tok; /// The input token this operand originated from. 673 const MCRegisterInfo *RegInfo; 674 }; 675 676 struct ImmOp { 677 const MCExpr *Val; 678 }; 679 680 struct MemOp { 681 MipsOperand *Base; 682 const MCExpr *Off; 683 }; 684 685 struct RegListOp { 686 SmallVector<unsigned, 10> *List; 687 }; 688 689 union { 690 struct Token Tok; 691 struct RegIdxOp RegIdx; 692 struct ImmOp Imm; 693 struct MemOp Mem; 694 struct RegListOp RegList; 695 }; 696 697 SMLoc StartLoc, EndLoc; 698 699 /// Internal constructor for register kinds 700 static std::unique_ptr<MipsOperand> CreateReg(unsigned Index, StringRef Str, 701 RegKind RegKind, 702 const MCRegisterInfo *RegInfo, 703 SMLoc S, SMLoc E, 704 MipsAsmParser &Parser) { 705 auto Op = make_unique<MipsOperand>(k_RegisterIndex, Parser); 706 Op->RegIdx.Index = Index; 707 Op->RegIdx.RegInfo = RegInfo; 708 Op->RegIdx.Kind = RegKind; 709 Op->RegIdx.Tok.Data = Str.data(); 710 Op->RegIdx.Tok.Length = Str.size(); 711 Op->StartLoc = S; 712 Op->EndLoc = E; 713 return Op; 714 } 715 716 public: 717 /// Coerce the register to GPR32 and return the real register for the current 718 /// target. 719 unsigned getGPR32Reg() const { 720 assert(isRegIdx() && (RegIdx.Kind & RegKind_GPR) && "Invalid access!"); 721 AsmParser.warnIfRegIndexIsAT(RegIdx.Index, StartLoc); 722 unsigned ClassID = Mips::GPR32RegClassID; 723 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 724 } 725 726 /// Coerce the register to GPR32 and return the real register for the current 727 /// target. 728 unsigned getGPRMM16Reg() const { 729 assert(isRegIdx() && (RegIdx.Kind & RegKind_GPR) && "Invalid access!"); 730 unsigned ClassID = Mips::GPR32RegClassID; 731 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 732 } 733 734 /// Coerce the register to GPR64 and return the real register for the current 735 /// target. 736 unsigned getGPR64Reg() const { 737 assert(isRegIdx() && (RegIdx.Kind & RegKind_GPR) && "Invalid access!"); 738 unsigned ClassID = Mips::GPR64RegClassID; 739 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 740 } 741 742 private: 743 /// Coerce the register to AFGR64 and return the real register for the current 744 /// target. 745 unsigned getAFGR64Reg() const { 746 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 747 if (RegIdx.Index % 2 != 0) 748 AsmParser.Warning(StartLoc, "Float register should be even."); 749 return RegIdx.RegInfo->getRegClass(Mips::AFGR64RegClassID) 750 .getRegister(RegIdx.Index / 2); 751 } 752 753 /// Coerce the register to FGR64 and return the real register for the current 754 /// target. 755 unsigned getFGR64Reg() const { 756 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 757 return RegIdx.RegInfo->getRegClass(Mips::FGR64RegClassID) 758 .getRegister(RegIdx.Index); 759 } 760 761 /// Coerce the register to FGR32 and return the real register for the current 762 /// target. 763 unsigned getFGR32Reg() const { 764 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 765 return RegIdx.RegInfo->getRegClass(Mips::FGR32RegClassID) 766 .getRegister(RegIdx.Index); 767 } 768 769 /// Coerce the register to FGRH32 and return the real register for the current 770 /// target. 771 unsigned getFGRH32Reg() const { 772 assert(isRegIdx() && (RegIdx.Kind & RegKind_FGR) && "Invalid access!"); 773 return RegIdx.RegInfo->getRegClass(Mips::FGRH32RegClassID) 774 .getRegister(RegIdx.Index); 775 } 776 777 /// Coerce the register to FCC and return the real register for the current 778 /// target. 779 unsigned getFCCReg() const { 780 assert(isRegIdx() && (RegIdx.Kind & RegKind_FCC) && "Invalid access!"); 781 return RegIdx.RegInfo->getRegClass(Mips::FCCRegClassID) 782 .getRegister(RegIdx.Index); 783 } 784 785 /// Coerce the register to MSA128 and return the real register for the current 786 /// target. 787 unsigned getMSA128Reg() const { 788 assert(isRegIdx() && (RegIdx.Kind & RegKind_MSA128) && "Invalid access!"); 789 // It doesn't matter which of the MSA128[BHWD] classes we use. They are all 790 // identical 791 unsigned ClassID = Mips::MSA128BRegClassID; 792 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 793 } 794 795 /// Coerce the register to MSACtrl and return the real register for the 796 /// current target. 797 unsigned getMSACtrlReg() const { 798 assert(isRegIdx() && (RegIdx.Kind & RegKind_MSACtrl) && "Invalid access!"); 799 unsigned ClassID = Mips::MSACtrlRegClassID; 800 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 801 } 802 803 /// Coerce the register to COP0 and return the real register for the 804 /// current target. 805 unsigned getCOP0Reg() const { 806 assert(isRegIdx() && (RegIdx.Kind & RegKind_COP0) && "Invalid access!"); 807 unsigned ClassID = Mips::COP0RegClassID; 808 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 809 } 810 811 /// Coerce the register to COP2 and return the real register for the 812 /// current target. 813 unsigned getCOP2Reg() const { 814 assert(isRegIdx() && (RegIdx.Kind & RegKind_COP2) && "Invalid access!"); 815 unsigned ClassID = Mips::COP2RegClassID; 816 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 817 } 818 819 /// Coerce the register to COP3 and return the real register for the 820 /// current target. 821 unsigned getCOP3Reg() const { 822 assert(isRegIdx() && (RegIdx.Kind & RegKind_COP3) && "Invalid access!"); 823 unsigned ClassID = Mips::COP3RegClassID; 824 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 825 } 826 827 /// Coerce the register to ACC64DSP and return the real register for the 828 /// current target. 829 unsigned getACC64DSPReg() const { 830 assert(isRegIdx() && (RegIdx.Kind & RegKind_ACC) && "Invalid access!"); 831 unsigned ClassID = Mips::ACC64DSPRegClassID; 832 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 833 } 834 835 /// Coerce the register to HI32DSP and return the real register for the 836 /// current target. 837 unsigned getHI32DSPReg() const { 838 assert(isRegIdx() && (RegIdx.Kind & RegKind_ACC) && "Invalid access!"); 839 unsigned ClassID = Mips::HI32DSPRegClassID; 840 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 841 } 842 843 /// Coerce the register to LO32DSP and return the real register for the 844 /// current target. 845 unsigned getLO32DSPReg() const { 846 assert(isRegIdx() && (RegIdx.Kind & RegKind_ACC) && "Invalid access!"); 847 unsigned ClassID = Mips::LO32DSPRegClassID; 848 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 849 } 850 851 /// Coerce the register to CCR and return the real register for the 852 /// current target. 853 unsigned getCCRReg() const { 854 assert(isRegIdx() && (RegIdx.Kind & RegKind_CCR) && "Invalid access!"); 855 unsigned ClassID = Mips::CCRRegClassID; 856 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 857 } 858 859 /// Coerce the register to HWRegs and return the real register for the 860 /// current target. 861 unsigned getHWRegsReg() const { 862 assert(isRegIdx() && (RegIdx.Kind & RegKind_HWRegs) && "Invalid access!"); 863 unsigned ClassID = Mips::HWRegsRegClassID; 864 return RegIdx.RegInfo->getRegClass(ClassID).getRegister(RegIdx.Index); 865 } 866 867 public: 868 void addExpr(MCInst &Inst, const MCExpr *Expr) const { 869 // Add as immediate when possible. Null MCExpr = 0. 870 if (!Expr) 871 Inst.addOperand(MCOperand::createImm(0)); 872 else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr)) 873 Inst.addOperand(MCOperand::createImm(CE->getValue())); 874 else 875 Inst.addOperand(MCOperand::createExpr(Expr)); 876 } 877 878 void addRegOperands(MCInst &Inst, unsigned N) const { 879 llvm_unreachable("Use a custom parser instead"); 880 } 881 882 /// Render the operand to an MCInst as a GPR32 883 /// Asserts if the wrong number of operands are requested, or the operand 884 /// is not a k_RegisterIndex compatible with RegKind_GPR 885 void addGPR32AsmRegOperands(MCInst &Inst, unsigned N) const { 886 assert(N == 1 && "Invalid number of operands!"); 887 Inst.addOperand(MCOperand::createReg(getGPR32Reg())); 888 } 889 890 void addGPRMM16AsmRegOperands(MCInst &Inst, unsigned N) const { 891 assert(N == 1 && "Invalid number of operands!"); 892 Inst.addOperand(MCOperand::createReg(getGPRMM16Reg())); 893 } 894 895 void addGPRMM16AsmRegZeroOperands(MCInst &Inst, unsigned N) const { 896 assert(N == 1 && "Invalid number of operands!"); 897 Inst.addOperand(MCOperand::createReg(getGPRMM16Reg())); 898 } 899 900 void addGPRMM16AsmRegMovePOperands(MCInst &Inst, unsigned N) const { 901 assert(N == 1 && "Invalid number of operands!"); 902 Inst.addOperand(MCOperand::createReg(getGPRMM16Reg())); 903 } 904 905 /// Render the operand to an MCInst as a GPR64 906 /// Asserts if the wrong number of operands are requested, or the operand 907 /// is not a k_RegisterIndex compatible with RegKind_GPR 908 void addGPR64AsmRegOperands(MCInst &Inst, unsigned N) const { 909 assert(N == 1 && "Invalid number of operands!"); 910 Inst.addOperand(MCOperand::createReg(getGPR64Reg())); 911 } 912 913 void addAFGR64AsmRegOperands(MCInst &Inst, unsigned N) const { 914 assert(N == 1 && "Invalid number of operands!"); 915 Inst.addOperand(MCOperand::createReg(getAFGR64Reg())); 916 } 917 918 void addFGR64AsmRegOperands(MCInst &Inst, unsigned N) const { 919 assert(N == 1 && "Invalid number of operands!"); 920 Inst.addOperand(MCOperand::createReg(getFGR64Reg())); 921 } 922 923 void addFGR32AsmRegOperands(MCInst &Inst, unsigned N) const { 924 assert(N == 1 && "Invalid number of operands!"); 925 Inst.addOperand(MCOperand::createReg(getFGR32Reg())); 926 // FIXME: We ought to do this for -integrated-as without -via-file-asm too. 927 // FIXME: This should propagate failure up to parseStatement. 928 if (!AsmParser.useOddSPReg() && RegIdx.Index & 1) 929 AsmParser.getParser().printError( 930 StartLoc, "-mno-odd-spreg prohibits the use of odd FPU " 931 "registers"); 932 } 933 934 void addFGRH32AsmRegOperands(MCInst &Inst, unsigned N) const { 935 assert(N == 1 && "Invalid number of operands!"); 936 Inst.addOperand(MCOperand::createReg(getFGRH32Reg())); 937 } 938 939 void addFCCAsmRegOperands(MCInst &Inst, unsigned N) const { 940 assert(N == 1 && "Invalid number of operands!"); 941 Inst.addOperand(MCOperand::createReg(getFCCReg())); 942 } 943 944 void addMSA128AsmRegOperands(MCInst &Inst, unsigned N) const { 945 assert(N == 1 && "Invalid number of operands!"); 946 Inst.addOperand(MCOperand::createReg(getMSA128Reg())); 947 } 948 949 void addMSACtrlAsmRegOperands(MCInst &Inst, unsigned N) const { 950 assert(N == 1 && "Invalid number of operands!"); 951 Inst.addOperand(MCOperand::createReg(getMSACtrlReg())); 952 } 953 954 void addCOP0AsmRegOperands(MCInst &Inst, unsigned N) const { 955 assert(N == 1 && "Invalid number of operands!"); 956 Inst.addOperand(MCOperand::createReg(getCOP0Reg())); 957 } 958 959 void addCOP2AsmRegOperands(MCInst &Inst, unsigned N) const { 960 assert(N == 1 && "Invalid number of operands!"); 961 Inst.addOperand(MCOperand::createReg(getCOP2Reg())); 962 } 963 964 void addCOP3AsmRegOperands(MCInst &Inst, unsigned N) const { 965 assert(N == 1 && "Invalid number of operands!"); 966 Inst.addOperand(MCOperand::createReg(getCOP3Reg())); 967 } 968 969 void addACC64DSPAsmRegOperands(MCInst &Inst, unsigned N) const { 970 assert(N == 1 && "Invalid number of operands!"); 971 Inst.addOperand(MCOperand::createReg(getACC64DSPReg())); 972 } 973 974 void addHI32DSPAsmRegOperands(MCInst &Inst, unsigned N) const { 975 assert(N == 1 && "Invalid number of operands!"); 976 Inst.addOperand(MCOperand::createReg(getHI32DSPReg())); 977 } 978 979 void addLO32DSPAsmRegOperands(MCInst &Inst, unsigned N) const { 980 assert(N == 1 && "Invalid number of operands!"); 981 Inst.addOperand(MCOperand::createReg(getLO32DSPReg())); 982 } 983 984 void addCCRAsmRegOperands(MCInst &Inst, unsigned N) const { 985 assert(N == 1 && "Invalid number of operands!"); 986 Inst.addOperand(MCOperand::createReg(getCCRReg())); 987 } 988 989 void addHWRegsAsmRegOperands(MCInst &Inst, unsigned N) const { 990 assert(N == 1 && "Invalid number of operands!"); 991 Inst.addOperand(MCOperand::createReg(getHWRegsReg())); 992 } 993 994 template <unsigned Bits, int Offset = 0, int AdjustOffset = 0> 995 void addConstantUImmOperands(MCInst &Inst, unsigned N) const { 996 assert(N == 1 && "Invalid number of operands!"); 997 uint64_t Imm = getConstantImm() - Offset; 998 Imm &= (1ULL << Bits) - 1; 999 Imm += Offset; 1000 Imm += AdjustOffset; 1001 Inst.addOperand(MCOperand::createImm(Imm)); 1002 } 1003 1004 template <unsigned Bits> 1005 void addSImmOperands(MCInst &Inst, unsigned N) const { 1006 if (isImm() && !isConstantImm()) { 1007 addExpr(Inst, getImm()); 1008 return; 1009 } 1010 addConstantSImmOperands<Bits, 0, 0>(Inst, N); 1011 } 1012 1013 template <unsigned Bits> 1014 void addUImmOperands(MCInst &Inst, unsigned N) const { 1015 if (isImm() && !isConstantImm()) { 1016 addExpr(Inst, getImm()); 1017 return; 1018 } 1019 addConstantUImmOperands<Bits, 0, 0>(Inst, N); 1020 } 1021 1022 template <unsigned Bits, int Offset = 0, int AdjustOffset = 0> 1023 void addConstantSImmOperands(MCInst &Inst, unsigned N) const { 1024 assert(N == 1 && "Invalid number of operands!"); 1025 int64_t Imm = getConstantImm() - Offset; 1026 Imm = SignExtend64<Bits>(Imm); 1027 Imm += Offset; 1028 Imm += AdjustOffset; 1029 Inst.addOperand(MCOperand::createImm(Imm)); 1030 } 1031 1032 void addImmOperands(MCInst &Inst, unsigned N) const { 1033 assert(N == 1 && "Invalid number of operands!"); 1034 const MCExpr *Expr = getImm(); 1035 addExpr(Inst, Expr); 1036 } 1037 1038 void addMemOperands(MCInst &Inst, unsigned N) const { 1039 assert(N == 2 && "Invalid number of operands!"); 1040 1041 Inst.addOperand(MCOperand::createReg(AsmParser.getABI().ArePtrs64bit() 1042 ? getMemBase()->getGPR64Reg() 1043 : getMemBase()->getGPR32Reg())); 1044 1045 const MCExpr *Expr = getMemOff(); 1046 addExpr(Inst, Expr); 1047 } 1048 1049 void addMicroMipsMemOperands(MCInst &Inst, unsigned N) const { 1050 assert(N == 2 && "Invalid number of operands!"); 1051 1052 Inst.addOperand(MCOperand::createReg(getMemBase()->getGPRMM16Reg())); 1053 1054 const MCExpr *Expr = getMemOff(); 1055 addExpr(Inst, Expr); 1056 } 1057 1058 void addRegListOperands(MCInst &Inst, unsigned N) const { 1059 assert(N == 1 && "Invalid number of operands!"); 1060 1061 for (auto RegNo : getRegList()) 1062 Inst.addOperand(MCOperand::createReg(RegNo)); 1063 } 1064 1065 void addRegPairOperands(MCInst &Inst, unsigned N) const { 1066 assert(N == 2 && "Invalid number of operands!"); 1067 assert((RegIdx.Kind & RegKind_GPR) && "Invalid access!"); 1068 unsigned RegNo = getRegPair(); 1069 AsmParser.warnIfRegIndexIsAT(RegNo, StartLoc); 1070 Inst.addOperand(MCOperand::createReg( 1071 RegIdx.RegInfo->getRegClass( 1072 AsmParser.getABI().AreGprs64bit() 1073 ? Mips::GPR64RegClassID 1074 : Mips::GPR32RegClassID).getRegister(RegNo++))); 1075 Inst.addOperand(MCOperand::createReg( 1076 RegIdx.RegInfo->getRegClass( 1077 AsmParser.getABI().AreGprs64bit() 1078 ? Mips::GPR64RegClassID 1079 : Mips::GPR32RegClassID).getRegister(RegNo))); 1080 } 1081 1082 void addMovePRegPairOperands(MCInst &Inst, unsigned N) const { 1083 assert(N == 2 && "Invalid number of operands!"); 1084 for (auto RegNo : getRegList()) 1085 Inst.addOperand(MCOperand::createReg(RegNo)); 1086 } 1087 1088 bool isReg() const override { 1089 // As a special case until we sort out the definition of div/divu, accept 1090 // $0/$zero here so that MCK_ZERO works correctly. 1091 return isGPRAsmReg() && RegIdx.Index == 0; 1092 } 1093 bool isRegIdx() const { return Kind == k_RegisterIndex; } 1094 bool isImm() const override { return Kind == k_Immediate; } 1095 bool isConstantImm() const { 1096 int64_t Res; 1097 return isImm() && getImm()->evaluateAsAbsolute(Res); 1098 } 1099 bool isConstantImmz() const { 1100 return isConstantImm() && getConstantImm() == 0; 1101 } 1102 template <unsigned Bits, int Offset = 0> bool isConstantUImm() const { 1103 return isConstantImm() && isUInt<Bits>(getConstantImm() - Offset); 1104 } 1105 template <unsigned Bits> bool isSImm() const { 1106 return isConstantImm() ? isInt<Bits>(getConstantImm()) : isImm(); 1107 } 1108 template <unsigned Bits> bool isUImm() const { 1109 return isConstantImm() ? isUInt<Bits>(getConstantImm()) : isImm(); 1110 } 1111 template <unsigned Bits> bool isAnyImm() const { 1112 return isConstantImm() ? (isInt<Bits>(getConstantImm()) || 1113 isUInt<Bits>(getConstantImm())) 1114 : isImm(); 1115 } 1116 template <unsigned Bits, int Offset = 0> bool isConstantSImm() const { 1117 return isConstantImm() && isInt<Bits>(getConstantImm() - Offset); 1118 } 1119 template <unsigned Bottom, unsigned Top> bool isConstantUImmRange() const { 1120 return isConstantImm() && getConstantImm() >= Bottom && 1121 getConstantImm() <= Top; 1122 } 1123 bool isToken() const override { 1124 // Note: It's not possible to pretend that other operand kinds are tokens. 1125 // The matcher emitter checks tokens first. 1126 return Kind == k_Token; 1127 } 1128 bool isMem() const override { return Kind == k_Memory; } 1129 bool isConstantMemOff() const { 1130 return isMem() && isa<MCConstantExpr>(getMemOff()); 1131 } 1132 // Allow relocation operators. 1133 // FIXME: This predicate and others need to look through binary expressions 1134 // and determine whether a Value is a constant or not. 1135 template <unsigned Bits, unsigned ShiftAmount = 0> 1136 bool isMemWithSimmOffset() const { 1137 if (!isMem()) 1138 return false; 1139 if (!getMemBase()->isGPRAsmReg()) 1140 return false; 1141 if (isa<MCTargetExpr>(getMemOff()) || 1142 (isConstantMemOff() && 1143 isShiftedInt<Bits, ShiftAmount>(getConstantMemOff()))) 1144 return true; 1145 MCValue Res; 1146 bool IsReloc = getMemOff()->evaluateAsRelocatable(Res, nullptr, nullptr); 1147 return IsReloc && isShiftedInt<Bits, ShiftAmount>(Res.getConstant()); 1148 } 1149 bool isMemWithGRPMM16Base() const { 1150 return isMem() && getMemBase()->isMM16AsmReg(); 1151 } 1152 template <unsigned Bits> bool isMemWithUimmOffsetSP() const { 1153 return isMem() && isConstantMemOff() && isUInt<Bits>(getConstantMemOff()) 1154 && getMemBase()->isRegIdx() && (getMemBase()->getGPR32Reg() == Mips::SP); 1155 } 1156 template <unsigned Bits> bool isMemWithUimmWordAlignedOffsetSP() const { 1157 return isMem() && isConstantMemOff() && isUInt<Bits>(getConstantMemOff()) 1158 && (getConstantMemOff() % 4 == 0) && getMemBase()->isRegIdx() 1159 && (getMemBase()->getGPR32Reg() == Mips::SP); 1160 } 1161 template <unsigned Bits> bool isMemWithSimmWordAlignedOffsetGP() const { 1162 return isMem() && isConstantMemOff() && isInt<Bits>(getConstantMemOff()) 1163 && (getConstantMemOff() % 4 == 0) && getMemBase()->isRegIdx() 1164 && (getMemBase()->getGPR32Reg() == Mips::GP); 1165 } 1166 template <unsigned Bits, unsigned ShiftLeftAmount> 1167 bool isScaledUImm() const { 1168 return isConstantImm() && 1169 isShiftedUInt<Bits, ShiftLeftAmount>(getConstantImm()); 1170 } 1171 template <unsigned Bits, unsigned ShiftLeftAmount> 1172 bool isScaledSImm() const { 1173 if (isConstantImm() && isShiftedInt<Bits, ShiftLeftAmount>(getConstantImm())) 1174 return true; 1175 // Operand can also be a symbol or symbol plus offset in case of relocations. 1176 if (Kind != k_Immediate) 1177 return false; 1178 MCValue Res; 1179 bool Success = getImm()->evaluateAsRelocatable(Res, nullptr, nullptr); 1180 return Success && isShiftedInt<Bits, ShiftLeftAmount>(Res.getConstant()); 1181 } 1182 bool isRegList16() const { 1183 if (!isRegList()) 1184 return false; 1185 1186 int Size = RegList.List->size(); 1187 if (Size < 2 || Size > 5) 1188 return false; 1189 1190 unsigned R0 = RegList.List->front(); 1191 unsigned R1 = RegList.List->back(); 1192 if (!((R0 == Mips::S0 && R1 == Mips::RA) || 1193 (R0 == Mips::S0_64 && R1 == Mips::RA_64))) 1194 return false; 1195 1196 int PrevReg = *RegList.List->begin(); 1197 for (int i = 1; i < Size - 1; i++) { 1198 int Reg = (*(RegList.List))[i]; 1199 if ( Reg != PrevReg + 1) 1200 return false; 1201 PrevReg = Reg; 1202 } 1203 1204 return true; 1205 } 1206 bool isInvNum() const { return Kind == k_Immediate; } 1207 bool isLSAImm() const { 1208 if (!isConstantImm()) 1209 return false; 1210 int64_t Val = getConstantImm(); 1211 return 1 <= Val && Val <= 4; 1212 } 1213 bool isRegList() const { return Kind == k_RegList; } 1214 bool isMovePRegPair() const { 1215 if (Kind != k_RegList || RegList.List->size() != 2) 1216 return false; 1217 1218 unsigned R0 = RegList.List->front(); 1219 unsigned R1 = RegList.List->back(); 1220 1221 if ((R0 == Mips::A1 && R1 == Mips::A2) || 1222 (R0 == Mips::A1 && R1 == Mips::A3) || 1223 (R0 == Mips::A2 && R1 == Mips::A3) || 1224 (R0 == Mips::A0 && R1 == Mips::S5) || 1225 (R0 == Mips::A0 && R1 == Mips::S6) || 1226 (R0 == Mips::A0 && R1 == Mips::A1) || 1227 (R0 == Mips::A0 && R1 == Mips::A2) || 1228 (R0 == Mips::A0 && R1 == Mips::A3) || 1229 (R0 == Mips::A1_64 && R1 == Mips::A2_64) || 1230 (R0 == Mips::A1_64 && R1 == Mips::A3_64) || 1231 (R0 == Mips::A2_64 && R1 == Mips::A3_64) || 1232 (R0 == Mips::A0_64 && R1 == Mips::S5_64) || 1233 (R0 == Mips::A0_64 && R1 == Mips::S6_64) || 1234 (R0 == Mips::A0_64 && R1 == Mips::A1_64) || 1235 (R0 == Mips::A0_64 && R1 == Mips::A2_64) || 1236 (R0 == Mips::A0_64 && R1 == Mips::A3_64)) 1237 return true; 1238 1239 return false; 1240 } 1241 1242 StringRef getToken() const { 1243 assert(Kind == k_Token && "Invalid access!"); 1244 return StringRef(Tok.Data, Tok.Length); 1245 } 1246 bool isRegPair() const { 1247 return Kind == k_RegPair && RegIdx.Index <= 30; 1248 } 1249 1250 unsigned getReg() const override { 1251 // As a special case until we sort out the definition of div/divu, accept 1252 // $0/$zero here so that MCK_ZERO works correctly. 1253 if (Kind == k_RegisterIndex && RegIdx.Index == 0 && 1254 RegIdx.Kind & RegKind_GPR) 1255 return getGPR32Reg(); // FIXME: GPR64 too 1256 1257 llvm_unreachable("Invalid access!"); 1258 return 0; 1259 } 1260 1261 const MCExpr *getImm() const { 1262 assert((Kind == k_Immediate) && "Invalid access!"); 1263 return Imm.Val; 1264 } 1265 1266 int64_t getConstantImm() const { 1267 const MCExpr *Val = getImm(); 1268 int64_t Value = 0; 1269 (void)Val->evaluateAsAbsolute(Value); 1270 return Value; 1271 } 1272 1273 MipsOperand *getMemBase() const { 1274 assert((Kind == k_Memory) && "Invalid access!"); 1275 return Mem.Base; 1276 } 1277 1278 const MCExpr *getMemOff() const { 1279 assert((Kind == k_Memory) && "Invalid access!"); 1280 return Mem.Off; 1281 } 1282 1283 int64_t getConstantMemOff() const { 1284 return static_cast<const MCConstantExpr *>(getMemOff())->getValue(); 1285 } 1286 1287 const SmallVectorImpl<unsigned> &getRegList() const { 1288 assert((Kind == k_RegList) && "Invalid access!"); 1289 return *(RegList.List); 1290 } 1291 1292 unsigned getRegPair() const { 1293 assert((Kind == k_RegPair) && "Invalid access!"); 1294 return RegIdx.Index; 1295 } 1296 1297 static std::unique_ptr<MipsOperand> CreateToken(StringRef Str, SMLoc S, 1298 MipsAsmParser &Parser) { 1299 auto Op = make_unique<MipsOperand>(k_Token, Parser); 1300 Op->Tok.Data = Str.data(); 1301 Op->Tok.Length = Str.size(); 1302 Op->StartLoc = S; 1303 Op->EndLoc = S; 1304 return Op; 1305 } 1306 1307 /// Create a numeric register (e.g. $1). The exact register remains 1308 /// unresolved until an instruction successfully matches 1309 static std::unique_ptr<MipsOperand> 1310 createNumericReg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1311 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1312 DEBUG(dbgs() << "createNumericReg(" << Index << ", ...)\n"); 1313 return CreateReg(Index, Str, RegKind_Numeric, RegInfo, S, E, Parser); 1314 } 1315 1316 /// Create a register that is definitely a GPR. 1317 /// This is typically only used for named registers such as $gp. 1318 static std::unique_ptr<MipsOperand> 1319 createGPRReg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1320 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1321 return CreateReg(Index, Str, RegKind_GPR, RegInfo, S, E, Parser); 1322 } 1323 1324 /// Create a register that is definitely a FGR. 1325 /// This is typically only used for named registers such as $f0. 1326 static std::unique_ptr<MipsOperand> 1327 createFGRReg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1328 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1329 return CreateReg(Index, Str, RegKind_FGR, RegInfo, S, E, Parser); 1330 } 1331 1332 /// Create a register that is definitely a HWReg. 1333 /// This is typically only used for named registers such as $hwr_cpunum. 1334 static std::unique_ptr<MipsOperand> 1335 createHWRegsReg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1336 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1337 return CreateReg(Index, Str, RegKind_HWRegs, RegInfo, S, E, Parser); 1338 } 1339 1340 /// Create a register that is definitely an FCC. 1341 /// This is typically only used for named registers such as $fcc0. 1342 static std::unique_ptr<MipsOperand> 1343 createFCCReg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1344 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1345 return CreateReg(Index, Str, RegKind_FCC, RegInfo, S, E, Parser); 1346 } 1347 1348 /// Create a register that is definitely an ACC. 1349 /// This is typically only used for named registers such as $ac0. 1350 static std::unique_ptr<MipsOperand> 1351 createACCReg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1352 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1353 return CreateReg(Index, Str, RegKind_ACC, RegInfo, S, E, Parser); 1354 } 1355 1356 /// Create a register that is definitely an MSA128. 1357 /// This is typically only used for named registers such as $w0. 1358 static std::unique_ptr<MipsOperand> 1359 createMSA128Reg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1360 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1361 return CreateReg(Index, Str, RegKind_MSA128, RegInfo, S, E, Parser); 1362 } 1363 1364 /// Create a register that is definitely an MSACtrl. 1365 /// This is typically only used for named registers such as $msaaccess. 1366 static std::unique_ptr<MipsOperand> 1367 createMSACtrlReg(unsigned Index, StringRef Str, const MCRegisterInfo *RegInfo, 1368 SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1369 return CreateReg(Index, Str, RegKind_MSACtrl, RegInfo, S, E, Parser); 1370 } 1371 1372 static std::unique_ptr<MipsOperand> 1373 CreateImm(const MCExpr *Val, SMLoc S, SMLoc E, MipsAsmParser &Parser) { 1374 auto Op = make_unique<MipsOperand>(k_Immediate, Parser); 1375 Op->Imm.Val = Val; 1376 Op->StartLoc = S; 1377 Op->EndLoc = E; 1378 return Op; 1379 } 1380 1381 static std::unique_ptr<MipsOperand> 1382 CreateMem(std::unique_ptr<MipsOperand> Base, const MCExpr *Off, SMLoc S, 1383 SMLoc E, MipsAsmParser &Parser) { 1384 auto Op = make_unique<MipsOperand>(k_Memory, Parser); 1385 Op->Mem.Base = Base.release(); 1386 Op->Mem.Off = Off; 1387 Op->StartLoc = S; 1388 Op->EndLoc = E; 1389 return Op; 1390 } 1391 1392 static std::unique_ptr<MipsOperand> 1393 CreateRegList(SmallVectorImpl<unsigned> &Regs, SMLoc StartLoc, SMLoc EndLoc, 1394 MipsAsmParser &Parser) { 1395 assert (Regs.size() > 0 && "Empty list not allowed"); 1396 1397 auto Op = make_unique<MipsOperand>(k_RegList, Parser); 1398 Op->RegList.List = new SmallVector<unsigned, 10>(Regs.begin(), Regs.end()); 1399 Op->StartLoc = StartLoc; 1400 Op->EndLoc = EndLoc; 1401 return Op; 1402 } 1403 1404 static std::unique_ptr<MipsOperand> CreateRegPair(const MipsOperand &MOP, 1405 SMLoc S, SMLoc E, 1406 MipsAsmParser &Parser) { 1407 auto Op = make_unique<MipsOperand>(k_RegPair, Parser); 1408 Op->RegIdx.Index = MOP.RegIdx.Index; 1409 Op->RegIdx.RegInfo = MOP.RegIdx.RegInfo; 1410 Op->RegIdx.Kind = MOP.RegIdx.Kind; 1411 Op->StartLoc = S; 1412 Op->EndLoc = E; 1413 return Op; 1414 } 1415 1416 bool isGPRAsmReg() const { 1417 return isRegIdx() && RegIdx.Kind & RegKind_GPR && RegIdx.Index <= 31; 1418 } 1419 bool isMM16AsmReg() const { 1420 if (!(isRegIdx() && RegIdx.Kind)) 1421 return false; 1422 return ((RegIdx.Index >= 2 && RegIdx.Index <= 7) 1423 || RegIdx.Index == 16 || RegIdx.Index == 17); 1424 } 1425 bool isMM16AsmRegZero() const { 1426 if (!(isRegIdx() && RegIdx.Kind)) 1427 return false; 1428 return (RegIdx.Index == 0 || 1429 (RegIdx.Index >= 2 && RegIdx.Index <= 7) || 1430 RegIdx.Index == 17); 1431 } 1432 bool isMM16AsmRegMoveP() const { 1433 if (!(isRegIdx() && RegIdx.Kind)) 1434 return false; 1435 return (RegIdx.Index == 0 || (RegIdx.Index >= 2 && RegIdx.Index <= 3) || 1436 (RegIdx.Index >= 16 && RegIdx.Index <= 20)); 1437 } 1438 bool isFGRAsmReg() const { 1439 // AFGR64 is $0-$15 but we handle this in getAFGR64() 1440 return isRegIdx() && RegIdx.Kind & RegKind_FGR && RegIdx.Index <= 31; 1441 } 1442 bool isHWRegsAsmReg() const { 1443 return isRegIdx() && RegIdx.Kind & RegKind_HWRegs && RegIdx.Index <= 31; 1444 } 1445 bool isCCRAsmReg() const { 1446 return isRegIdx() && RegIdx.Kind & RegKind_CCR && RegIdx.Index <= 31; 1447 } 1448 bool isFCCAsmReg() const { 1449 if (!(isRegIdx() && RegIdx.Kind & RegKind_FCC)) 1450 return false; 1451 if (!AsmParser.hasEightFccRegisters()) 1452 return RegIdx.Index == 0; 1453 return RegIdx.Index <= 7; 1454 } 1455 bool isACCAsmReg() const { 1456 return isRegIdx() && RegIdx.Kind & RegKind_ACC && RegIdx.Index <= 3; 1457 } 1458 bool isCOP0AsmReg() const { 1459 return isRegIdx() && RegIdx.Kind & RegKind_COP0 && RegIdx.Index <= 31; 1460 } 1461 bool isCOP2AsmReg() const { 1462 return isRegIdx() && RegIdx.Kind & RegKind_COP2 && RegIdx.Index <= 31; 1463 } 1464 bool isCOP3AsmReg() const { 1465 return isRegIdx() && RegIdx.Kind & RegKind_COP3 && RegIdx.Index <= 31; 1466 } 1467 bool isMSA128AsmReg() const { 1468 return isRegIdx() && RegIdx.Kind & RegKind_MSA128 && RegIdx.Index <= 31; 1469 } 1470 bool isMSACtrlAsmReg() const { 1471 return isRegIdx() && RegIdx.Kind & RegKind_MSACtrl && RegIdx.Index <= 7; 1472 } 1473 1474 /// getStartLoc - Get the location of the first token of this operand. 1475 SMLoc getStartLoc() const override { return StartLoc; } 1476 /// getEndLoc - Get the location of the last token of this operand. 1477 SMLoc getEndLoc() const override { return EndLoc; } 1478 1479 virtual ~MipsOperand() { 1480 switch (Kind) { 1481 case k_Immediate: 1482 break; 1483 case k_Memory: 1484 delete Mem.Base; 1485 break; 1486 case k_RegList: 1487 delete RegList.List; 1488 case k_RegisterIndex: 1489 case k_Token: 1490 case k_RegPair: 1491 break; 1492 } 1493 } 1494 1495 void print(raw_ostream &OS) const override { 1496 switch (Kind) { 1497 case k_Immediate: 1498 OS << "Imm<"; 1499 OS << *Imm.Val; 1500 OS << ">"; 1501 break; 1502 case k_Memory: 1503 OS << "Mem<"; 1504 Mem.Base->print(OS); 1505 OS << ", "; 1506 OS << *Mem.Off; 1507 OS << ">"; 1508 break; 1509 case k_RegisterIndex: 1510 OS << "RegIdx<" << RegIdx.Index << ":" << RegIdx.Kind << ", " 1511 << StringRef(RegIdx.Tok.Data, RegIdx.Tok.Length) << ">"; 1512 break; 1513 case k_Token: 1514 OS << getToken(); 1515 break; 1516 case k_RegList: 1517 OS << "RegList< "; 1518 for (auto Reg : (*RegList.List)) 1519 OS << Reg << " "; 1520 OS << ">"; 1521 break; 1522 case k_RegPair: 1523 OS << "RegPair<" << RegIdx.Index << "," << RegIdx.Index + 1 << ">"; 1524 break; 1525 } 1526 } 1527 1528 bool isValidForTie(const MipsOperand &Other) const { 1529 if (Kind != Other.Kind) 1530 return false; 1531 1532 switch (Kind) { 1533 default: 1534 llvm_unreachable("Unexpected kind"); 1535 return false; 1536 case k_RegisterIndex: { 1537 StringRef Token(RegIdx.Tok.Data, RegIdx.Tok.Length); 1538 StringRef OtherToken(Other.RegIdx.Tok.Data, Other.RegIdx.Tok.Length); 1539 return Token == OtherToken; 1540 } 1541 } 1542 } 1543 }; // class MipsOperand 1544 } // namespace 1545 1546 namespace llvm { 1547 extern const MCInstrDesc MipsInsts[]; 1548 } 1549 static const MCInstrDesc &getInstDesc(unsigned Opcode) { 1550 return MipsInsts[Opcode]; 1551 } 1552 1553 static bool hasShortDelaySlot(unsigned Opcode) { 1554 switch (Opcode) { 1555 case Mips::JALS_MM: 1556 case Mips::JALRS_MM: 1557 case Mips::JALRS16_MM: 1558 case Mips::BGEZALS_MM: 1559 case Mips::BLTZALS_MM: 1560 return true; 1561 default: 1562 return false; 1563 } 1564 } 1565 1566 static const MCSymbol *getSingleMCSymbol(const MCExpr *Expr) { 1567 if (const MCSymbolRefExpr *SRExpr = dyn_cast<MCSymbolRefExpr>(Expr)) { 1568 return &SRExpr->getSymbol(); 1569 } 1570 1571 if (const MCBinaryExpr *BExpr = dyn_cast<MCBinaryExpr>(Expr)) { 1572 const MCSymbol *LHSSym = getSingleMCSymbol(BExpr->getLHS()); 1573 const MCSymbol *RHSSym = getSingleMCSymbol(BExpr->getRHS()); 1574 1575 if (LHSSym) 1576 return LHSSym; 1577 1578 if (RHSSym) 1579 return RHSSym; 1580 1581 return nullptr; 1582 } 1583 1584 if (const MCUnaryExpr *UExpr = dyn_cast<MCUnaryExpr>(Expr)) 1585 return getSingleMCSymbol(UExpr->getSubExpr()); 1586 1587 return nullptr; 1588 } 1589 1590 static unsigned countMCSymbolRefExpr(const MCExpr *Expr) { 1591 if (isa<MCSymbolRefExpr>(Expr)) 1592 return 1; 1593 1594 if (const MCBinaryExpr *BExpr = dyn_cast<MCBinaryExpr>(Expr)) 1595 return countMCSymbolRefExpr(BExpr->getLHS()) + 1596 countMCSymbolRefExpr(BExpr->getRHS()); 1597 1598 if (const MCUnaryExpr *UExpr = dyn_cast<MCUnaryExpr>(Expr)) 1599 return countMCSymbolRefExpr(UExpr->getSubExpr()); 1600 1601 return 0; 1602 } 1603 1604 bool MipsAsmParser::processInstruction(MCInst &Inst, SMLoc IDLoc, 1605 MCStreamer &Out, 1606 const MCSubtargetInfo *STI) { 1607 MipsTargetStreamer &TOut = getTargetStreamer(); 1608 const MCInstrDesc &MCID = getInstDesc(Inst.getOpcode()); 1609 bool ExpandedJalSym = false; 1610 1611 Inst.setLoc(IDLoc); 1612 1613 if (MCID.isBranch() || MCID.isCall()) { 1614 const unsigned Opcode = Inst.getOpcode(); 1615 MCOperand Offset; 1616 1617 switch (Opcode) { 1618 default: 1619 break; 1620 case Mips::BBIT0: 1621 case Mips::BBIT032: 1622 case Mips::BBIT1: 1623 case Mips::BBIT132: 1624 assert(hasCnMips() && "instruction only valid for octeon cpus"); 1625 LLVM_FALLTHROUGH; 1626 1627 case Mips::BEQ: 1628 case Mips::BNE: 1629 case Mips::BEQ_MM: 1630 case Mips::BNE_MM: 1631 assert(MCID.getNumOperands() == 3 && "unexpected number of operands"); 1632 Offset = Inst.getOperand(2); 1633 if (!Offset.isImm()) 1634 break; // We'll deal with this situation later on when applying fixups. 1635 if (!isIntN(inMicroMipsMode() ? 17 : 18, Offset.getImm())) 1636 return Error(IDLoc, "branch target out of range"); 1637 if (OffsetToAlignment(Offset.getImm(), 1638 1LL << (inMicroMipsMode() ? 1 : 2))) 1639 return Error(IDLoc, "branch to misaligned address"); 1640 break; 1641 case Mips::BGEZ: 1642 case Mips::BGTZ: 1643 case Mips::BLEZ: 1644 case Mips::BLTZ: 1645 case Mips::BGEZAL: 1646 case Mips::BLTZAL: 1647 case Mips::BC1F: 1648 case Mips::BC1T: 1649 case Mips::BGEZ_MM: 1650 case Mips::BGTZ_MM: 1651 case Mips::BLEZ_MM: 1652 case Mips::BLTZ_MM: 1653 case Mips::BGEZAL_MM: 1654 case Mips::BLTZAL_MM: 1655 case Mips::BC1F_MM: 1656 case Mips::BC1T_MM: 1657 case Mips::BC1EQZC_MMR6: 1658 case Mips::BC1NEZC_MMR6: 1659 case Mips::BC2EQZC_MMR6: 1660 case Mips::BC2NEZC_MMR6: 1661 assert(MCID.getNumOperands() == 2 && "unexpected number of operands"); 1662 Offset = Inst.getOperand(1); 1663 if (!Offset.isImm()) 1664 break; // We'll deal with this situation later on when applying fixups. 1665 if (!isIntN(inMicroMipsMode() ? 17 : 18, Offset.getImm())) 1666 return Error(IDLoc, "branch target out of range"); 1667 if (OffsetToAlignment(Offset.getImm(), 1668 1LL << (inMicroMipsMode() ? 1 : 2))) 1669 return Error(IDLoc, "branch to misaligned address"); 1670 break; 1671 case Mips::BGEC: case Mips::BGEC_MMR6: 1672 case Mips::BLTC: case Mips::BLTC_MMR6: 1673 case Mips::BGEUC: case Mips::BGEUC_MMR6: 1674 case Mips::BLTUC: case Mips::BLTUC_MMR6: 1675 case Mips::BEQC: case Mips::BEQC_MMR6: 1676 case Mips::BNEC: case Mips::BNEC_MMR6: 1677 assert(MCID.getNumOperands() == 3 && "unexpected number of operands"); 1678 Offset = Inst.getOperand(2); 1679 if (!Offset.isImm()) 1680 break; // We'll deal with this situation later on when applying fixups. 1681 if (!isIntN(18, Offset.getImm())) 1682 return Error(IDLoc, "branch target out of range"); 1683 if (OffsetToAlignment(Offset.getImm(), 1LL << 2)) 1684 return Error(IDLoc, "branch to misaligned address"); 1685 break; 1686 case Mips::BLEZC: case Mips::BLEZC_MMR6: 1687 case Mips::BGEZC: case Mips::BGEZC_MMR6: 1688 case Mips::BGTZC: case Mips::BGTZC_MMR6: 1689 case Mips::BLTZC: case Mips::BLTZC_MMR6: 1690 assert(MCID.getNumOperands() == 2 && "unexpected number of operands"); 1691 Offset = Inst.getOperand(1); 1692 if (!Offset.isImm()) 1693 break; // We'll deal with this situation later on when applying fixups. 1694 if (!isIntN(18, Offset.getImm())) 1695 return Error(IDLoc, "branch target out of range"); 1696 if (OffsetToAlignment(Offset.getImm(), 1LL << 2)) 1697 return Error(IDLoc, "branch to misaligned address"); 1698 break; 1699 case Mips::BEQZC: case Mips::BEQZC_MMR6: 1700 case Mips::BNEZC: case Mips::BNEZC_MMR6: 1701 assert(MCID.getNumOperands() == 2 && "unexpected number of operands"); 1702 Offset = Inst.getOperand(1); 1703 if (!Offset.isImm()) 1704 break; // We'll deal with this situation later on when applying fixups. 1705 if (!isIntN(23, Offset.getImm())) 1706 return Error(IDLoc, "branch target out of range"); 1707 if (OffsetToAlignment(Offset.getImm(), 1LL << 2)) 1708 return Error(IDLoc, "branch to misaligned address"); 1709 break; 1710 case Mips::BEQZ16_MM: 1711 case Mips::BEQZC16_MMR6: 1712 case Mips::BNEZ16_MM: 1713 case Mips::BNEZC16_MMR6: 1714 assert(MCID.getNumOperands() == 2 && "unexpected number of operands"); 1715 Offset = Inst.getOperand(1); 1716 if (!Offset.isImm()) 1717 break; // We'll deal with this situation later on when applying fixups. 1718 if (!isInt<8>(Offset.getImm())) 1719 return Error(IDLoc, "branch target out of range"); 1720 if (OffsetToAlignment(Offset.getImm(), 2LL)) 1721 return Error(IDLoc, "branch to misaligned address"); 1722 break; 1723 } 1724 } 1725 1726 // SSNOP is deprecated on MIPS32r6/MIPS64r6 1727 // We still accept it but it is a normal nop. 1728 if (hasMips32r6() && Inst.getOpcode() == Mips::SSNOP) { 1729 std::string ISA = hasMips64r6() ? "MIPS64r6" : "MIPS32r6"; 1730 Warning(IDLoc, "ssnop is deprecated for " + ISA + " and is equivalent to a " 1731 "nop instruction"); 1732 } 1733 1734 if (hasCnMips()) { 1735 const unsigned Opcode = Inst.getOpcode(); 1736 MCOperand Opnd; 1737 int Imm; 1738 1739 switch (Opcode) { 1740 default: 1741 break; 1742 1743 case Mips::BBIT0: 1744 case Mips::BBIT032: 1745 case Mips::BBIT1: 1746 case Mips::BBIT132: 1747 assert(MCID.getNumOperands() == 3 && "unexpected number of operands"); 1748 // The offset is handled above 1749 Opnd = Inst.getOperand(1); 1750 if (!Opnd.isImm()) 1751 return Error(IDLoc, "expected immediate operand kind"); 1752 Imm = Opnd.getImm(); 1753 if (Imm < 0 || Imm > (Opcode == Mips::BBIT0 || 1754 Opcode == Mips::BBIT1 ? 63 : 31)) 1755 return Error(IDLoc, "immediate operand value out of range"); 1756 if (Imm > 31) { 1757 Inst.setOpcode(Opcode == Mips::BBIT0 ? Mips::BBIT032 1758 : Mips::BBIT132); 1759 Inst.getOperand(1).setImm(Imm - 32); 1760 } 1761 break; 1762 1763 case Mips::SEQi: 1764 case Mips::SNEi: 1765 assert(MCID.getNumOperands() == 3 && "unexpected number of operands"); 1766 Opnd = Inst.getOperand(2); 1767 if (!Opnd.isImm()) 1768 return Error(IDLoc, "expected immediate operand kind"); 1769 Imm = Opnd.getImm(); 1770 if (!isInt<10>(Imm)) 1771 return Error(IDLoc, "immediate operand value out of range"); 1772 break; 1773 } 1774 } 1775 1776 // This expansion is not in a function called by tryExpandInstruction() 1777 // because the pseudo-instruction doesn't have a distinct opcode. 1778 if ((Inst.getOpcode() == Mips::JAL || Inst.getOpcode() == Mips::JAL_MM) && 1779 inPicMode()) { 1780 warnIfNoMacro(IDLoc); 1781 1782 const MCExpr *JalExpr = Inst.getOperand(0).getExpr(); 1783 1784 // We can do this expansion if there's only 1 symbol in the argument 1785 // expression. 1786 if (countMCSymbolRefExpr(JalExpr) > 1) 1787 return Error(IDLoc, "jal doesn't support multiple symbols in PIC mode"); 1788 1789 // FIXME: This is checking the expression can be handled by the later stages 1790 // of the assembler. We ought to leave it to those later stages. 1791 const MCSymbol *JalSym = getSingleMCSymbol(JalExpr); 1792 1793 // FIXME: Add support for label+offset operands (currently causes an error). 1794 // FIXME: Add support for forward-declared local symbols. 1795 // FIXME: Add expansion for when the LargeGOT option is enabled. 1796 if (JalSym->isInSection() || JalSym->isTemporary()) { 1797 if (isABI_O32()) { 1798 // If it's a local symbol and the O32 ABI is being used, we expand to: 1799 // lw $25, 0($gp) 1800 // R_(MICRO)MIPS_GOT16 label 1801 // addiu $25, $25, 0 1802 // R_(MICRO)MIPS_LO16 label 1803 // jalr $25 1804 const MCExpr *Got16RelocExpr = 1805 MipsMCExpr::create(MipsMCExpr::MEK_GOT, JalExpr, getContext()); 1806 const MCExpr *Lo16RelocExpr = 1807 MipsMCExpr::create(MipsMCExpr::MEK_LO, JalExpr, getContext()); 1808 1809 TOut.emitRRX(Mips::LW, Mips::T9, Mips::GP, 1810 MCOperand::createExpr(Got16RelocExpr), IDLoc, STI); 1811 TOut.emitRRX(Mips::ADDiu, Mips::T9, Mips::T9, 1812 MCOperand::createExpr(Lo16RelocExpr), IDLoc, STI); 1813 } else if (isABI_N32() || isABI_N64()) { 1814 // If it's a local symbol and the N32/N64 ABIs are being used, 1815 // we expand to: 1816 // lw/ld $25, 0($gp) 1817 // R_(MICRO)MIPS_GOT_DISP label 1818 // jalr $25 1819 const MCExpr *GotDispRelocExpr = 1820 MipsMCExpr::create(MipsMCExpr::MEK_GOT_DISP, JalExpr, getContext()); 1821 1822 TOut.emitRRX(ABI.ArePtrs64bit() ? Mips::LD : Mips::LW, Mips::T9, 1823 Mips::GP, MCOperand::createExpr(GotDispRelocExpr), IDLoc, 1824 STI); 1825 } 1826 } else { 1827 // If it's an external/weak symbol, we expand to: 1828 // lw/ld $25, 0($gp) 1829 // R_(MICRO)MIPS_CALL16 label 1830 // jalr $25 1831 const MCExpr *Call16RelocExpr = 1832 MipsMCExpr::create(MipsMCExpr::MEK_GOT_CALL, JalExpr, getContext()); 1833 1834 TOut.emitRRX(ABI.ArePtrs64bit() ? Mips::LD : Mips::LW, Mips::T9, Mips::GP, 1835 MCOperand::createExpr(Call16RelocExpr), IDLoc, STI); 1836 } 1837 1838 MCInst JalrInst; 1839 if (IsCpRestoreSet && inMicroMipsMode()) 1840 JalrInst.setOpcode(Mips::JALRS_MM); 1841 else 1842 JalrInst.setOpcode(inMicroMipsMode() ? Mips::JALR_MM : Mips::JALR); 1843 JalrInst.addOperand(MCOperand::createReg(Mips::RA)); 1844 JalrInst.addOperand(MCOperand::createReg(Mips::T9)); 1845 1846 // FIXME: Add an R_(MICRO)MIPS_JALR relocation after the JALR. 1847 // This relocation is supposed to be an optimization hint for the linker 1848 // and is not necessary for correctness. 1849 1850 Inst = JalrInst; 1851 ExpandedJalSym = true; 1852 } 1853 1854 bool IsPCRelativeLoad = (MCID.TSFlags & MipsII::IsPCRelativeLoad) != 0; 1855 if ((MCID.mayLoad() || MCID.mayStore()) && !IsPCRelativeLoad) { 1856 // Check the offset of memory operand, if it is a symbol 1857 // reference or immediate we may have to expand instructions. 1858 for (unsigned i = 0; i < MCID.getNumOperands(); i++) { 1859 const MCOperandInfo &OpInfo = MCID.OpInfo[i]; 1860 if ((OpInfo.OperandType == MCOI::OPERAND_MEMORY) || 1861 (OpInfo.OperandType == MCOI::OPERAND_UNKNOWN)) { 1862 MCOperand &Op = Inst.getOperand(i); 1863 if (Op.isImm()) { 1864 int MemOffset = Op.getImm(); 1865 if (MemOffset < -32768 || MemOffset > 32767) { 1866 // Offset can't exceed 16bit value. 1867 expandMemInst(Inst, IDLoc, Out, STI, MCID.mayLoad(), true); 1868 return getParser().hasPendingError(); 1869 } 1870 } else if (Op.isExpr()) { 1871 const MCExpr *Expr = Op.getExpr(); 1872 if (Expr->getKind() == MCExpr::SymbolRef) { 1873 const MCSymbolRefExpr *SR = 1874 static_cast<const MCSymbolRefExpr *>(Expr); 1875 if (SR->getKind() == MCSymbolRefExpr::VK_None) { 1876 // Expand symbol. 1877 expandMemInst(Inst, IDLoc, Out, STI, MCID.mayLoad(), false); 1878 return getParser().hasPendingError(); 1879 } 1880 } else if (!isEvaluated(Expr)) { 1881 expandMemInst(Inst, IDLoc, Out, STI, MCID.mayLoad(), false); 1882 return getParser().hasPendingError(); 1883 } 1884 } 1885 } 1886 } // for 1887 } // if load/store 1888 1889 if (inMicroMipsMode()) { 1890 if (MCID.mayLoad()) { 1891 // Try to create 16-bit GP relative load instruction. 1892 for (unsigned i = 0; i < MCID.getNumOperands(); i++) { 1893 const MCOperandInfo &OpInfo = MCID.OpInfo[i]; 1894 if ((OpInfo.OperandType == MCOI::OPERAND_MEMORY) || 1895 (OpInfo.OperandType == MCOI::OPERAND_UNKNOWN)) { 1896 MCOperand &Op = Inst.getOperand(i); 1897 if (Op.isImm()) { 1898 int MemOffset = Op.getImm(); 1899 MCOperand &DstReg = Inst.getOperand(0); 1900 MCOperand &BaseReg = Inst.getOperand(1); 1901 if (isInt<9>(MemOffset) && (MemOffset % 4 == 0) && 1902 getContext().getRegisterInfo()->getRegClass( 1903 Mips::GPRMM16RegClassID).contains(DstReg.getReg()) && 1904 (BaseReg.getReg() == Mips::GP || 1905 BaseReg.getReg() == Mips::GP_64)) { 1906 1907 TOut.emitRRI(Mips::LWGP_MM, DstReg.getReg(), Mips::GP, MemOffset, 1908 IDLoc, STI); 1909 return false; 1910 } 1911 } 1912 } 1913 } // for 1914 } // if load 1915 1916 // TODO: Handle this with the AsmOperandClass.PredicateMethod. 1917 1918 MCOperand Opnd; 1919 int Imm; 1920 1921 switch (Inst.getOpcode()) { 1922 default: 1923 break; 1924 case Mips::ADDIUSP_MM: 1925 Opnd = Inst.getOperand(0); 1926 if (!Opnd.isImm()) 1927 return Error(IDLoc, "expected immediate operand kind"); 1928 Imm = Opnd.getImm(); 1929 if (Imm < -1032 || Imm > 1028 || (Imm < 8 && Imm > -12) || 1930 Imm % 4 != 0) 1931 return Error(IDLoc, "immediate operand value out of range"); 1932 break; 1933 case Mips::SLL16_MM: 1934 case Mips::SRL16_MM: 1935 Opnd = Inst.getOperand(2); 1936 if (!Opnd.isImm()) 1937 return Error(IDLoc, "expected immediate operand kind"); 1938 Imm = Opnd.getImm(); 1939 if (Imm < 1 || Imm > 8) 1940 return Error(IDLoc, "immediate operand value out of range"); 1941 break; 1942 case Mips::LI16_MM: 1943 Opnd = Inst.getOperand(1); 1944 if (!Opnd.isImm()) 1945 return Error(IDLoc, "expected immediate operand kind"); 1946 Imm = Opnd.getImm(); 1947 if (Imm < -1 || Imm > 126) 1948 return Error(IDLoc, "immediate operand value out of range"); 1949 break; 1950 case Mips::ADDIUR2_MM: 1951 Opnd = Inst.getOperand(2); 1952 if (!Opnd.isImm()) 1953 return Error(IDLoc, "expected immediate operand kind"); 1954 Imm = Opnd.getImm(); 1955 if (!(Imm == 1 || Imm == -1 || 1956 ((Imm % 4 == 0) && Imm < 28 && Imm > 0))) 1957 return Error(IDLoc, "immediate operand value out of range"); 1958 break; 1959 case Mips::ANDI16_MM: 1960 Opnd = Inst.getOperand(2); 1961 if (!Opnd.isImm()) 1962 return Error(IDLoc, "expected immediate operand kind"); 1963 Imm = Opnd.getImm(); 1964 if (!(Imm == 128 || (Imm >= 1 && Imm <= 4) || Imm == 7 || Imm == 8 || 1965 Imm == 15 || Imm == 16 || Imm == 31 || Imm == 32 || Imm == 63 || 1966 Imm == 64 || Imm == 255 || Imm == 32768 || Imm == 65535)) 1967 return Error(IDLoc, "immediate operand value out of range"); 1968 break; 1969 case Mips::LBU16_MM: 1970 Opnd = Inst.getOperand(2); 1971 if (!Opnd.isImm()) 1972 return Error(IDLoc, "expected immediate operand kind"); 1973 Imm = Opnd.getImm(); 1974 if (Imm < -1 || Imm > 14) 1975 return Error(IDLoc, "immediate operand value out of range"); 1976 break; 1977 case Mips::SB16_MM: 1978 case Mips::SB16_MMR6: 1979 Opnd = Inst.getOperand(2); 1980 if (!Opnd.isImm()) 1981 return Error(IDLoc, "expected immediate operand kind"); 1982 Imm = Opnd.getImm(); 1983 if (Imm < 0 || Imm > 15) 1984 return Error(IDLoc, "immediate operand value out of range"); 1985 break; 1986 case Mips::LHU16_MM: 1987 case Mips::SH16_MM: 1988 case Mips::SH16_MMR6: 1989 Opnd = Inst.getOperand(2); 1990 if (!Opnd.isImm()) 1991 return Error(IDLoc, "expected immediate operand kind"); 1992 Imm = Opnd.getImm(); 1993 if (Imm < 0 || Imm > 30 || (Imm % 2 != 0)) 1994 return Error(IDLoc, "immediate operand value out of range"); 1995 break; 1996 case Mips::LW16_MM: 1997 case Mips::SW16_MM: 1998 case Mips::SW16_MMR6: 1999 Opnd = Inst.getOperand(2); 2000 if (!Opnd.isImm()) 2001 return Error(IDLoc, "expected immediate operand kind"); 2002 Imm = Opnd.getImm(); 2003 if (Imm < 0 || Imm > 60 || (Imm % 4 != 0)) 2004 return Error(IDLoc, "immediate operand value out of range"); 2005 break; 2006 case Mips::ADDIUPC_MM: 2007 MCOperand Opnd = Inst.getOperand(1); 2008 if (!Opnd.isImm()) 2009 return Error(IDLoc, "expected immediate operand kind"); 2010 int Imm = Opnd.getImm(); 2011 if ((Imm % 4 != 0) || !isInt<25>(Imm)) 2012 return Error(IDLoc, "immediate operand value out of range"); 2013 break; 2014 } 2015 } 2016 2017 bool FillDelaySlot = 2018 MCID.hasDelaySlot() && AssemblerOptions.back()->isReorder(); 2019 if (FillDelaySlot) 2020 TOut.emitDirectiveSetNoReorder(); 2021 2022 MacroExpanderResultTy ExpandResult = 2023 tryExpandInstruction(Inst, IDLoc, Out, STI); 2024 switch (ExpandResult) { 2025 case MER_NotAMacro: 2026 Out.EmitInstruction(Inst, *STI); 2027 break; 2028 case MER_Success: 2029 break; 2030 case MER_Fail: 2031 return true; 2032 } 2033 2034 // We know we emitted an instruction on the MER_NotAMacro or MER_Success path. 2035 // If we're in microMIPS mode then we must also set EF_MIPS_MICROMIPS. 2036 if (inMicroMipsMode()) 2037 TOut.setUsesMicroMips(); 2038 2039 // If this instruction has a delay slot and .set reorder is active, 2040 // emit a NOP after it. 2041 if (FillDelaySlot) { 2042 TOut.emitEmptyDelaySlot(hasShortDelaySlot(Inst.getOpcode()), IDLoc, STI); 2043 TOut.emitDirectiveSetReorder(); 2044 } 2045 2046 if ((Inst.getOpcode() == Mips::JalOneReg || 2047 Inst.getOpcode() == Mips::JalTwoReg || ExpandedJalSym) && 2048 isPicAndNotNxxAbi()) { 2049 if (IsCpRestoreSet) { 2050 // We need a NOP between the JALR and the LW: 2051 // If .set reorder has been used, we've already emitted a NOP. 2052 // If .set noreorder has been used, we need to emit a NOP at this point. 2053 if (!AssemblerOptions.back()->isReorder()) 2054 TOut.emitEmptyDelaySlot(hasShortDelaySlot(Inst.getOpcode()), IDLoc, 2055 STI); 2056 2057 // Load the $gp from the stack. 2058 TOut.emitGPRestore(CpRestoreOffset, IDLoc, STI); 2059 } else 2060 Warning(IDLoc, "no .cprestore used in PIC mode"); 2061 } 2062 2063 return false; 2064 } 2065 2066 MipsAsmParser::MacroExpanderResultTy 2067 MipsAsmParser::tryExpandInstruction(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 2068 const MCSubtargetInfo *STI) { 2069 switch (Inst.getOpcode()) { 2070 default: 2071 return MER_NotAMacro; 2072 case Mips::LoadImm32: 2073 return expandLoadImm(Inst, true, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2074 case Mips::LoadImm64: 2075 return expandLoadImm(Inst, false, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2076 case Mips::LoadAddrImm32: 2077 case Mips::LoadAddrImm64: 2078 assert(Inst.getOperand(0).isReg() && "expected register operand kind"); 2079 assert((Inst.getOperand(1).isImm() || Inst.getOperand(1).isExpr()) && 2080 "expected immediate operand kind"); 2081 2082 return expandLoadAddress(Inst.getOperand(0).getReg(), Mips::NoRegister, 2083 Inst.getOperand(1), 2084 Inst.getOpcode() == Mips::LoadAddrImm32, IDLoc, 2085 Out, STI) 2086 ? MER_Fail 2087 : MER_Success; 2088 case Mips::LoadAddrReg32: 2089 case Mips::LoadAddrReg64: 2090 assert(Inst.getOperand(0).isReg() && "expected register operand kind"); 2091 assert(Inst.getOperand(1).isReg() && "expected register operand kind"); 2092 assert((Inst.getOperand(2).isImm() || Inst.getOperand(2).isExpr()) && 2093 "expected immediate operand kind"); 2094 2095 return expandLoadAddress(Inst.getOperand(0).getReg(), 2096 Inst.getOperand(1).getReg(), Inst.getOperand(2), 2097 Inst.getOpcode() == Mips::LoadAddrReg32, IDLoc, 2098 Out, STI) 2099 ? MER_Fail 2100 : MER_Success; 2101 case Mips::B_MM_Pseudo: 2102 case Mips::B_MMR6_Pseudo: 2103 return expandUncondBranchMMPseudo(Inst, IDLoc, Out, STI) ? MER_Fail 2104 : MER_Success; 2105 case Mips::SWM_MM: 2106 case Mips::LWM_MM: 2107 return expandLoadStoreMultiple(Inst, IDLoc, Out, STI) ? MER_Fail 2108 : MER_Success; 2109 case Mips::JalOneReg: 2110 case Mips::JalTwoReg: 2111 return expandJalWithRegs(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2112 case Mips::BneImm: 2113 case Mips::BeqImm: 2114 return expandBranchImm(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2115 case Mips::BLT: 2116 case Mips::BLE: 2117 case Mips::BGE: 2118 case Mips::BGT: 2119 case Mips::BLTU: 2120 case Mips::BLEU: 2121 case Mips::BGEU: 2122 case Mips::BGTU: 2123 case Mips::BLTL: 2124 case Mips::BLEL: 2125 case Mips::BGEL: 2126 case Mips::BGTL: 2127 case Mips::BLTUL: 2128 case Mips::BLEUL: 2129 case Mips::BGEUL: 2130 case Mips::BGTUL: 2131 case Mips::BLTImmMacro: 2132 case Mips::BLEImmMacro: 2133 case Mips::BGEImmMacro: 2134 case Mips::BGTImmMacro: 2135 case Mips::BLTUImmMacro: 2136 case Mips::BLEUImmMacro: 2137 case Mips::BGEUImmMacro: 2138 case Mips::BGTUImmMacro: 2139 case Mips::BLTLImmMacro: 2140 case Mips::BLELImmMacro: 2141 case Mips::BGELImmMacro: 2142 case Mips::BGTLImmMacro: 2143 case Mips::BLTULImmMacro: 2144 case Mips::BLEULImmMacro: 2145 case Mips::BGEULImmMacro: 2146 case Mips::BGTULImmMacro: 2147 return expandCondBranches(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2148 case Mips::SDivMacro: 2149 return expandDiv(Inst, IDLoc, Out, STI, false, true) ? MER_Fail 2150 : MER_Success; 2151 case Mips::DSDivMacro: 2152 return expandDiv(Inst, IDLoc, Out, STI, true, true) ? MER_Fail 2153 : MER_Success; 2154 case Mips::UDivMacro: 2155 return expandDiv(Inst, IDLoc, Out, STI, false, false) ? MER_Fail 2156 : MER_Success; 2157 case Mips::DUDivMacro: 2158 return expandDiv(Inst, IDLoc, Out, STI, true, false) ? MER_Fail 2159 : MER_Success; 2160 case Mips::PseudoTRUNC_W_S: 2161 return expandTrunc(Inst, false, false, IDLoc, Out, STI) ? MER_Fail 2162 : MER_Success; 2163 case Mips::PseudoTRUNC_W_D32: 2164 return expandTrunc(Inst, true, false, IDLoc, Out, STI) ? MER_Fail 2165 : MER_Success; 2166 case Mips::PseudoTRUNC_W_D: 2167 return expandTrunc(Inst, true, true, IDLoc, Out, STI) ? MER_Fail 2168 : MER_Success; 2169 case Mips::Ulh: 2170 return expandUlh(Inst, true, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2171 case Mips::Ulhu: 2172 return expandUlh(Inst, false, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2173 case Mips::Ulw: 2174 return expandUlw(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2175 case Mips::NORImm: 2176 return expandAliasImmediate(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2177 case Mips::ADDi: 2178 case Mips::ADDiu: 2179 case Mips::SLTi: 2180 case Mips::SLTiu: 2181 if ((Inst.getNumOperands() == 3) && Inst.getOperand(0).isReg() && 2182 Inst.getOperand(1).isReg() && Inst.getOperand(2).isImm()) { 2183 int64_t ImmValue = Inst.getOperand(2).getImm(); 2184 if (isInt<16>(ImmValue)) 2185 return MER_NotAMacro; 2186 return expandAliasImmediate(Inst, IDLoc, Out, STI) ? MER_Fail 2187 : MER_Success; 2188 } 2189 return MER_NotAMacro; 2190 case Mips::ANDi: 2191 case Mips::ORi: 2192 case Mips::XORi: 2193 if ((Inst.getNumOperands() == 3) && Inst.getOperand(0).isReg() && 2194 Inst.getOperand(1).isReg() && Inst.getOperand(2).isImm()) { 2195 int64_t ImmValue = Inst.getOperand(2).getImm(); 2196 if (isUInt<16>(ImmValue)) 2197 return MER_NotAMacro; 2198 return expandAliasImmediate(Inst, IDLoc, Out, STI) ? MER_Fail 2199 : MER_Success; 2200 } 2201 return MER_NotAMacro; 2202 case Mips::ROL: 2203 case Mips::ROR: 2204 return expandRotation(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2205 case Mips::ROLImm: 2206 case Mips::RORImm: 2207 return expandRotationImm(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2208 case Mips::DROL: 2209 case Mips::DROR: 2210 return expandDRotation(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2211 case Mips::DROLImm: 2212 case Mips::DRORImm: 2213 return expandDRotationImm(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2214 case Mips::ABSMacro: 2215 return expandAbs(Inst, IDLoc, Out, STI) ? MER_Fail : MER_Success; 2216 } 2217 } 2218 2219 bool MipsAsmParser::expandJalWithRegs(MCInst &Inst, SMLoc IDLoc, 2220 MCStreamer &Out, 2221 const MCSubtargetInfo *STI) { 2222 MipsTargetStreamer &TOut = getTargetStreamer(); 2223 2224 // Create a JALR instruction which is going to replace the pseudo-JAL. 2225 MCInst JalrInst; 2226 JalrInst.setLoc(IDLoc); 2227 const MCOperand FirstRegOp = Inst.getOperand(0); 2228 const unsigned Opcode = Inst.getOpcode(); 2229 2230 if (Opcode == Mips::JalOneReg) { 2231 // jal $rs => jalr $rs 2232 if (IsCpRestoreSet && inMicroMipsMode()) { 2233 JalrInst.setOpcode(Mips::JALRS16_MM); 2234 JalrInst.addOperand(FirstRegOp); 2235 } else if (inMicroMipsMode()) { 2236 JalrInst.setOpcode(hasMips32r6() ? Mips::JALRC16_MMR6 : Mips::JALR16_MM); 2237 JalrInst.addOperand(FirstRegOp); 2238 } else { 2239 JalrInst.setOpcode(Mips::JALR); 2240 JalrInst.addOperand(MCOperand::createReg(Mips::RA)); 2241 JalrInst.addOperand(FirstRegOp); 2242 } 2243 } else if (Opcode == Mips::JalTwoReg) { 2244 // jal $rd, $rs => jalr $rd, $rs 2245 if (IsCpRestoreSet && inMicroMipsMode()) 2246 JalrInst.setOpcode(Mips::JALRS_MM); 2247 else 2248 JalrInst.setOpcode(inMicroMipsMode() ? Mips::JALR_MM : Mips::JALR); 2249 JalrInst.addOperand(FirstRegOp); 2250 const MCOperand SecondRegOp = Inst.getOperand(1); 2251 JalrInst.addOperand(SecondRegOp); 2252 } 2253 Out.EmitInstruction(JalrInst, *STI); 2254 2255 // If .set reorder is active and branch instruction has a delay slot, 2256 // emit a NOP after it. 2257 const MCInstrDesc &MCID = getInstDesc(JalrInst.getOpcode()); 2258 if (MCID.hasDelaySlot() && AssemblerOptions.back()->isReorder()) 2259 TOut.emitEmptyDelaySlot(hasShortDelaySlot(JalrInst.getOpcode()), IDLoc, 2260 STI); 2261 2262 return false; 2263 } 2264 2265 /// Can the value be represented by a unsigned N-bit value and a shift left? 2266 template <unsigned N> static bool isShiftedUIntAtAnyPosition(uint64_t x) { 2267 unsigned BitNum = findFirstSet(x); 2268 2269 return (x == x >> BitNum << BitNum) && isUInt<N>(x >> BitNum); 2270 } 2271 2272 /// Load (or add) an immediate into a register. 2273 /// 2274 /// @param ImmValue The immediate to load. 2275 /// @param DstReg The register that will hold the immediate. 2276 /// @param SrcReg A register to add to the immediate or Mips::NoRegister 2277 /// for a simple initialization. 2278 /// @param Is32BitImm Is ImmValue 32-bit or 64-bit? 2279 /// @param IsAddress True if the immediate represents an address. False if it 2280 /// is an integer. 2281 /// @param IDLoc Location of the immediate in the source file. 2282 bool MipsAsmParser::loadImmediate(int64_t ImmValue, unsigned DstReg, 2283 unsigned SrcReg, bool Is32BitImm, 2284 bool IsAddress, SMLoc IDLoc, MCStreamer &Out, 2285 const MCSubtargetInfo *STI) { 2286 MipsTargetStreamer &TOut = getTargetStreamer(); 2287 2288 if (!Is32BitImm && !isGP64bit()) { 2289 Error(IDLoc, "instruction requires a 64-bit architecture"); 2290 return true; 2291 } 2292 2293 if (Is32BitImm) { 2294 if (isInt<32>(ImmValue) || isUInt<32>(ImmValue)) { 2295 // Sign extend up to 64-bit so that the predicates match the hardware 2296 // behaviour. In particular, isInt<16>(0xffff8000) and similar should be 2297 // true. 2298 ImmValue = SignExtend64<32>(ImmValue); 2299 } else { 2300 Error(IDLoc, "instruction requires a 32-bit immediate"); 2301 return true; 2302 } 2303 } 2304 2305 unsigned ZeroReg = IsAddress ? ABI.GetNullPtr() : ABI.GetZeroReg(); 2306 unsigned AdduOp = !Is32BitImm ? Mips::DADDu : Mips::ADDu; 2307 2308 bool UseSrcReg = false; 2309 if (SrcReg != Mips::NoRegister) 2310 UseSrcReg = true; 2311 2312 unsigned TmpReg = DstReg; 2313 if (UseSrcReg && 2314 getContext().getRegisterInfo()->isSuperOrSubRegisterEq(DstReg, SrcReg)) { 2315 // At this point we need AT to perform the expansions and we exit if it is 2316 // not available. 2317 unsigned ATReg = getATReg(IDLoc); 2318 if (!ATReg) 2319 return true; 2320 TmpReg = ATReg; 2321 } 2322 2323 if (isInt<16>(ImmValue)) { 2324 if (!UseSrcReg) 2325 SrcReg = ZeroReg; 2326 2327 // This doesn't quite follow the usual ABI expectations for N32 but matches 2328 // traditional assembler behaviour. N32 would normally use addiu for both 2329 // integers and addresses. 2330 if (IsAddress && !Is32BitImm) { 2331 TOut.emitRRI(Mips::DADDiu, DstReg, SrcReg, ImmValue, IDLoc, STI); 2332 return false; 2333 } 2334 2335 TOut.emitRRI(Mips::ADDiu, DstReg, SrcReg, ImmValue, IDLoc, STI); 2336 return false; 2337 } 2338 2339 if (isUInt<16>(ImmValue)) { 2340 unsigned TmpReg = DstReg; 2341 if (SrcReg == DstReg) { 2342 TmpReg = getATReg(IDLoc); 2343 if (!TmpReg) 2344 return true; 2345 } 2346 2347 TOut.emitRRI(Mips::ORi, TmpReg, ZeroReg, ImmValue, IDLoc, STI); 2348 if (UseSrcReg) 2349 TOut.emitRRR(ABI.GetPtrAdduOp(), DstReg, TmpReg, SrcReg, IDLoc, STI); 2350 return false; 2351 } 2352 2353 if (isInt<32>(ImmValue) || isUInt<32>(ImmValue)) { 2354 warnIfNoMacro(IDLoc); 2355 2356 uint16_t Bits31To16 = (ImmValue >> 16) & 0xffff; 2357 uint16_t Bits15To0 = ImmValue & 0xffff; 2358 2359 if (!Is32BitImm && !isInt<32>(ImmValue)) { 2360 // Traditional behaviour seems to special case this particular value. It's 2361 // not clear why other masks are handled differently. 2362 if (ImmValue == 0xffffffff) { 2363 TOut.emitRI(Mips::LUi, TmpReg, 0xffff, IDLoc, STI); 2364 TOut.emitRRI(Mips::DSRL32, TmpReg, TmpReg, 0, IDLoc, STI); 2365 if (UseSrcReg) 2366 TOut.emitRRR(AdduOp, DstReg, TmpReg, SrcReg, IDLoc, STI); 2367 return false; 2368 } 2369 2370 // Expand to an ORi instead of a LUi to avoid sign-extending into the 2371 // upper 32 bits. 2372 TOut.emitRRI(Mips::ORi, TmpReg, ZeroReg, Bits31To16, IDLoc, STI); 2373 TOut.emitRRI(Mips::DSLL, TmpReg, TmpReg, 16, IDLoc, STI); 2374 if (Bits15To0) 2375 TOut.emitRRI(Mips::ORi, TmpReg, TmpReg, Bits15To0, IDLoc, STI); 2376 if (UseSrcReg) 2377 TOut.emitRRR(AdduOp, DstReg, TmpReg, SrcReg, IDLoc, STI); 2378 return false; 2379 } 2380 2381 TOut.emitRI(Mips::LUi, TmpReg, Bits31To16, IDLoc, STI); 2382 if (Bits15To0) 2383 TOut.emitRRI(Mips::ORi, TmpReg, TmpReg, Bits15To0, IDLoc, STI); 2384 if (UseSrcReg) 2385 TOut.emitRRR(AdduOp, DstReg, TmpReg, SrcReg, IDLoc, STI); 2386 return false; 2387 } 2388 2389 if (isShiftedUIntAtAnyPosition<16>(ImmValue)) { 2390 if (Is32BitImm) { 2391 Error(IDLoc, "instruction requires a 32-bit immediate"); 2392 return true; 2393 } 2394 2395 // Traditionally, these immediates are shifted as little as possible and as 2396 // such we align the most significant bit to bit 15 of our temporary. 2397 unsigned FirstSet = findFirstSet((uint64_t)ImmValue); 2398 unsigned LastSet = findLastSet((uint64_t)ImmValue); 2399 unsigned ShiftAmount = FirstSet - (15 - (LastSet - FirstSet)); 2400 uint16_t Bits = (ImmValue >> ShiftAmount) & 0xffff; 2401 TOut.emitRRI(Mips::ORi, TmpReg, ZeroReg, Bits, IDLoc, STI); 2402 TOut.emitRRI(Mips::DSLL, TmpReg, TmpReg, ShiftAmount, IDLoc, STI); 2403 2404 if (UseSrcReg) 2405 TOut.emitRRR(AdduOp, DstReg, TmpReg, SrcReg, IDLoc, STI); 2406 2407 return false; 2408 } 2409 2410 warnIfNoMacro(IDLoc); 2411 2412 // The remaining case is packed with a sequence of dsll and ori with zeros 2413 // being omitted and any neighbouring dsll's being coalesced. 2414 // The highest 32-bit's are equivalent to a 32-bit immediate load. 2415 2416 // Load bits 32-63 of ImmValue into bits 0-31 of the temporary register. 2417 if (loadImmediate(ImmValue >> 32, TmpReg, Mips::NoRegister, true, false, 2418 IDLoc, Out, STI)) 2419 return false; 2420 2421 // Shift and accumulate into the register. If a 16-bit chunk is zero, then 2422 // skip it and defer the shift to the next chunk. 2423 unsigned ShiftCarriedForwards = 16; 2424 for (int BitNum = 16; BitNum >= 0; BitNum -= 16) { 2425 uint16_t ImmChunk = (ImmValue >> BitNum) & 0xffff; 2426 2427 if (ImmChunk != 0) { 2428 TOut.emitDSLL(TmpReg, TmpReg, ShiftCarriedForwards, IDLoc, STI); 2429 TOut.emitRRI(Mips::ORi, TmpReg, TmpReg, ImmChunk, IDLoc, STI); 2430 ShiftCarriedForwards = 0; 2431 } 2432 2433 ShiftCarriedForwards += 16; 2434 } 2435 ShiftCarriedForwards -= 16; 2436 2437 // Finish any remaining shifts left by trailing zeros. 2438 if (ShiftCarriedForwards) 2439 TOut.emitDSLL(TmpReg, TmpReg, ShiftCarriedForwards, IDLoc, STI); 2440 2441 if (UseSrcReg) 2442 TOut.emitRRR(AdduOp, DstReg, TmpReg, SrcReg, IDLoc, STI); 2443 2444 return false; 2445 } 2446 2447 bool MipsAsmParser::expandLoadImm(MCInst &Inst, bool Is32BitImm, SMLoc IDLoc, 2448 MCStreamer &Out, const MCSubtargetInfo *STI) { 2449 const MCOperand &ImmOp = Inst.getOperand(1); 2450 assert(ImmOp.isImm() && "expected immediate operand kind"); 2451 const MCOperand &DstRegOp = Inst.getOperand(0); 2452 assert(DstRegOp.isReg() && "expected register operand kind"); 2453 2454 if (loadImmediate(ImmOp.getImm(), DstRegOp.getReg(), Mips::NoRegister, 2455 Is32BitImm, false, IDLoc, Out, STI)) 2456 return true; 2457 2458 return false; 2459 } 2460 2461 bool MipsAsmParser::expandLoadAddress(unsigned DstReg, unsigned BaseReg, 2462 const MCOperand &Offset, 2463 bool Is32BitAddress, SMLoc IDLoc, 2464 MCStreamer &Out, 2465 const MCSubtargetInfo *STI) { 2466 // la can't produce a usable address when addresses are 64-bit. 2467 if (Is32BitAddress && ABI.ArePtrs64bit()) { 2468 // FIXME: Demote this to a warning and continue as if we had 'dla' instead. 2469 // We currently can't do this because we depend on the equality 2470 // operator and N64 can end up with a GPR32/GPR64 mismatch. 2471 Error(IDLoc, "la used to load 64-bit address"); 2472 // Continue as if we had 'dla' instead. 2473 Is32BitAddress = false; 2474 return true; 2475 } 2476 2477 // dla requires 64-bit addresses. 2478 if (!Is32BitAddress && !hasMips3()) { 2479 Error(IDLoc, "instruction requires a 64-bit architecture"); 2480 return true; 2481 } 2482 2483 if (!Offset.isImm()) 2484 return loadAndAddSymbolAddress(Offset.getExpr(), DstReg, BaseReg, 2485 Is32BitAddress, IDLoc, Out, STI); 2486 2487 if (!ABI.ArePtrs64bit()) { 2488 // Continue as if we had 'la' whether we had 'la' or 'dla'. 2489 Is32BitAddress = true; 2490 } 2491 2492 return loadImmediate(Offset.getImm(), DstReg, BaseReg, Is32BitAddress, true, 2493 IDLoc, Out, STI); 2494 } 2495 2496 bool MipsAsmParser::loadAndAddSymbolAddress(const MCExpr *SymExpr, 2497 unsigned DstReg, unsigned SrcReg, 2498 bool Is32BitSym, SMLoc IDLoc, 2499 MCStreamer &Out, 2500 const MCSubtargetInfo *STI) { 2501 MipsTargetStreamer &TOut = getTargetStreamer(); 2502 bool UseSrcReg = SrcReg != Mips::NoRegister; 2503 warnIfNoMacro(IDLoc); 2504 2505 if (inPicMode() && ABI.IsO32()) { 2506 MCValue Res; 2507 if (!SymExpr->evaluateAsRelocatable(Res, nullptr, nullptr)) { 2508 Error(IDLoc, "expected relocatable expression"); 2509 return true; 2510 } 2511 if (Res.getSymB() != nullptr) { 2512 Error(IDLoc, "expected relocatable expression with only one symbol"); 2513 return true; 2514 } 2515 2516 // The case where the result register is $25 is somewhat special. If the 2517 // symbol in the final relocation is external and not modified with a 2518 // constant then we must use R_MIPS_CALL16 instead of R_MIPS_GOT16. 2519 if ((DstReg == Mips::T9 || DstReg == Mips::T9_64) && !UseSrcReg && 2520 Res.getConstant() == 0 && !Res.getSymA()->getSymbol().isInSection() && 2521 !Res.getSymA()->getSymbol().isTemporary()) { 2522 const MCExpr *CallExpr = 2523 MipsMCExpr::create(MipsMCExpr::MEK_GOT_CALL, SymExpr, getContext()); 2524 TOut.emitRRX(Mips::LW, DstReg, ABI.GetGlobalPtr(), 2525 MCOperand::createExpr(CallExpr), IDLoc, STI); 2526 return false; 2527 } 2528 2529 // The remaining cases are: 2530 // External GOT: lw $tmp, %got(symbol+offset)($gp) 2531 // >addiu $tmp, $tmp, %lo(offset) 2532 // >addiu $rd, $tmp, $rs 2533 // Local GOT: lw $tmp, %got(symbol+offset)($gp) 2534 // addiu $tmp, $tmp, %lo(symbol+offset)($gp) 2535 // >addiu $rd, $tmp, $rs 2536 // The addiu's marked with a '>' may be omitted if they are redundant. If 2537 // this happens then the last instruction must use $rd as the result 2538 // register. 2539 const MipsMCExpr *GotExpr = 2540 MipsMCExpr::create(MipsMCExpr::MEK_GOT, SymExpr, getContext()); 2541 const MCExpr *LoExpr = nullptr; 2542 if (Res.getSymA()->getSymbol().isInSection() || 2543 Res.getSymA()->getSymbol().isTemporary()) 2544 LoExpr = MipsMCExpr::create(MipsMCExpr::MEK_LO, SymExpr, getContext()); 2545 else if (Res.getConstant() != 0) { 2546 // External symbols fully resolve the symbol with just the %got(symbol) 2547 // but we must still account for any offset to the symbol for expressions 2548 // like symbol+8. 2549 LoExpr = MCConstantExpr::create(Res.getConstant(), getContext()); 2550 } 2551 2552 unsigned TmpReg = DstReg; 2553 if (UseSrcReg && 2554 getContext().getRegisterInfo()->isSuperOrSubRegisterEq(DstReg, 2555 SrcReg)) { 2556 // If $rs is the same as $rd, we need to use AT. 2557 // If it is not available we exit. 2558 unsigned ATReg = getATReg(IDLoc); 2559 if (!ATReg) 2560 return true; 2561 TmpReg = ATReg; 2562 } 2563 2564 TOut.emitRRX(Mips::LW, TmpReg, ABI.GetGlobalPtr(), 2565 MCOperand::createExpr(GotExpr), IDLoc, STI); 2566 2567 if (LoExpr) 2568 TOut.emitRRX(Mips::ADDiu, TmpReg, TmpReg, MCOperand::createExpr(LoExpr), 2569 IDLoc, STI); 2570 2571 if (UseSrcReg) 2572 TOut.emitRRR(Mips::ADDu, DstReg, TmpReg, SrcReg, IDLoc, STI); 2573 2574 return false; 2575 } 2576 2577 const MipsMCExpr *HiExpr = 2578 MipsMCExpr::create(MipsMCExpr::MEK_HI, SymExpr, getContext()); 2579 const MipsMCExpr *LoExpr = 2580 MipsMCExpr::create(MipsMCExpr::MEK_LO, SymExpr, getContext()); 2581 2582 // This is the 64-bit symbol address expansion. 2583 if (ABI.ArePtrs64bit() && isGP64bit()) { 2584 // We always need AT for the 64-bit expansion. 2585 // If it is not available we exit. 2586 unsigned ATReg = getATReg(IDLoc); 2587 if (!ATReg) 2588 return true; 2589 2590 const MipsMCExpr *HighestExpr = 2591 MipsMCExpr::create(MipsMCExpr::MEK_HIGHEST, SymExpr, getContext()); 2592 const MipsMCExpr *HigherExpr = 2593 MipsMCExpr::create(MipsMCExpr::MEK_HIGHER, SymExpr, getContext()); 2594 2595 if (UseSrcReg && 2596 getContext().getRegisterInfo()->isSuperOrSubRegisterEq(DstReg, 2597 SrcReg)) { 2598 // If $rs is the same as $rd: 2599 // (d)la $rd, sym($rd) => lui $at, %highest(sym) 2600 // daddiu $at, $at, %higher(sym) 2601 // dsll $at, $at, 16 2602 // daddiu $at, $at, %hi(sym) 2603 // dsll $at, $at, 16 2604 // daddiu $at, $at, %lo(sym) 2605 // daddu $rd, $at, $rd 2606 TOut.emitRX(Mips::LUi, ATReg, MCOperand::createExpr(HighestExpr), IDLoc, 2607 STI); 2608 TOut.emitRRX(Mips::DADDiu, ATReg, ATReg, 2609 MCOperand::createExpr(HigherExpr), IDLoc, STI); 2610 TOut.emitRRI(Mips::DSLL, ATReg, ATReg, 16, IDLoc, STI); 2611 TOut.emitRRX(Mips::DADDiu, ATReg, ATReg, MCOperand::createExpr(HiExpr), 2612 IDLoc, STI); 2613 TOut.emitRRI(Mips::DSLL, ATReg, ATReg, 16, IDLoc, STI); 2614 TOut.emitRRX(Mips::DADDiu, ATReg, ATReg, MCOperand::createExpr(LoExpr), 2615 IDLoc, STI); 2616 TOut.emitRRR(Mips::DADDu, DstReg, ATReg, SrcReg, IDLoc, STI); 2617 2618 return false; 2619 } 2620 2621 // Otherwise, if the $rs is different from $rd or if $rs isn't specified: 2622 // (d)la $rd, sym/sym($rs) => lui $rd, %highest(sym) 2623 // lui $at, %hi(sym) 2624 // daddiu $rd, $rd, %higher(sym) 2625 // daddiu $at, $at, %lo(sym) 2626 // dsll32 $rd, $rd, 0 2627 // daddu $rd, $rd, $at 2628 // (daddu $rd, $rd, $rs) 2629 TOut.emitRX(Mips::LUi, DstReg, MCOperand::createExpr(HighestExpr), IDLoc, 2630 STI); 2631 TOut.emitRX(Mips::LUi, ATReg, MCOperand::createExpr(HiExpr), IDLoc, STI); 2632 TOut.emitRRX(Mips::DADDiu, DstReg, DstReg, 2633 MCOperand::createExpr(HigherExpr), IDLoc, STI); 2634 TOut.emitRRX(Mips::DADDiu, ATReg, ATReg, MCOperand::createExpr(LoExpr), 2635 IDLoc, STI); 2636 TOut.emitRRI(Mips::DSLL32, DstReg, DstReg, 0, IDLoc, STI); 2637 TOut.emitRRR(Mips::DADDu, DstReg, DstReg, ATReg, IDLoc, STI); 2638 if (UseSrcReg) 2639 TOut.emitRRR(Mips::DADDu, DstReg, DstReg, SrcReg, IDLoc, STI); 2640 2641 return false; 2642 } 2643 2644 // And now, the 32-bit symbol address expansion: 2645 // If $rs is the same as $rd: 2646 // (d)la $rd, sym($rd) => lui $at, %hi(sym) 2647 // ori $at, $at, %lo(sym) 2648 // addu $rd, $at, $rd 2649 // Otherwise, if the $rs is different from $rd or if $rs isn't specified: 2650 // (d)la $rd, sym/sym($rs) => lui $rd, %hi(sym) 2651 // ori $rd, $rd, %lo(sym) 2652 // (addu $rd, $rd, $rs) 2653 unsigned TmpReg = DstReg; 2654 if (UseSrcReg && 2655 getContext().getRegisterInfo()->isSuperOrSubRegisterEq(DstReg, SrcReg)) { 2656 // If $rs is the same as $rd, we need to use AT. 2657 // If it is not available we exit. 2658 unsigned ATReg = getATReg(IDLoc); 2659 if (!ATReg) 2660 return true; 2661 TmpReg = ATReg; 2662 } 2663 2664 TOut.emitRX(Mips::LUi, TmpReg, MCOperand::createExpr(HiExpr), IDLoc, STI); 2665 TOut.emitRRX(Mips::ADDiu, TmpReg, TmpReg, MCOperand::createExpr(LoExpr), 2666 IDLoc, STI); 2667 2668 if (UseSrcReg) 2669 TOut.emitRRR(Mips::ADDu, DstReg, TmpReg, SrcReg, IDLoc, STI); 2670 else 2671 assert( 2672 getContext().getRegisterInfo()->isSuperOrSubRegisterEq(DstReg, TmpReg)); 2673 2674 return false; 2675 } 2676 2677 bool MipsAsmParser::expandUncondBranchMMPseudo(MCInst &Inst, SMLoc IDLoc, 2678 MCStreamer &Out, 2679 const MCSubtargetInfo *STI) { 2680 MipsTargetStreamer &TOut = getTargetStreamer(); 2681 2682 assert(getInstDesc(Inst.getOpcode()).getNumOperands() == 1 && 2683 "unexpected number of operands"); 2684 2685 MCOperand Offset = Inst.getOperand(0); 2686 if (Offset.isExpr()) { 2687 Inst.clear(); 2688 Inst.setOpcode(Mips::BEQ_MM); 2689 Inst.addOperand(MCOperand::createReg(Mips::ZERO)); 2690 Inst.addOperand(MCOperand::createReg(Mips::ZERO)); 2691 Inst.addOperand(MCOperand::createExpr(Offset.getExpr())); 2692 } else { 2693 assert(Offset.isImm() && "expected immediate operand kind"); 2694 if (isInt<11>(Offset.getImm())) { 2695 // If offset fits into 11 bits then this instruction becomes microMIPS 2696 // 16-bit unconditional branch instruction. 2697 if (inMicroMipsMode()) 2698 Inst.setOpcode(hasMips32r6() ? Mips::BC16_MMR6 : Mips::B16_MM); 2699 } else { 2700 if (!isInt<17>(Offset.getImm())) 2701 return Error(IDLoc, "branch target out of range"); 2702 if (OffsetToAlignment(Offset.getImm(), 1LL << 1)) 2703 return Error(IDLoc, "branch to misaligned address"); 2704 Inst.clear(); 2705 Inst.setOpcode(Mips::BEQ_MM); 2706 Inst.addOperand(MCOperand::createReg(Mips::ZERO)); 2707 Inst.addOperand(MCOperand::createReg(Mips::ZERO)); 2708 Inst.addOperand(MCOperand::createImm(Offset.getImm())); 2709 } 2710 } 2711 Out.EmitInstruction(Inst, *STI); 2712 2713 // If .set reorder is active and branch instruction has a delay slot, 2714 // emit a NOP after it. 2715 const MCInstrDesc &MCID = getInstDesc(Inst.getOpcode()); 2716 if (MCID.hasDelaySlot() && AssemblerOptions.back()->isReorder()) 2717 TOut.emitEmptyDelaySlot(true, IDLoc, STI); 2718 2719 return false; 2720 } 2721 2722 bool MipsAsmParser::expandBranchImm(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 2723 const MCSubtargetInfo *STI) { 2724 MipsTargetStreamer &TOut = getTargetStreamer(); 2725 const MCOperand &DstRegOp = Inst.getOperand(0); 2726 assert(DstRegOp.isReg() && "expected register operand kind"); 2727 2728 const MCOperand &ImmOp = Inst.getOperand(1); 2729 assert(ImmOp.isImm() && "expected immediate operand kind"); 2730 2731 const MCOperand &MemOffsetOp = Inst.getOperand(2); 2732 assert((MemOffsetOp.isImm() || MemOffsetOp.isExpr()) && 2733 "expected immediate or expression operand"); 2734 2735 unsigned OpCode = 0; 2736 switch(Inst.getOpcode()) { 2737 case Mips::BneImm: 2738 OpCode = Mips::BNE; 2739 break; 2740 case Mips::BeqImm: 2741 OpCode = Mips::BEQ; 2742 break; 2743 default: 2744 llvm_unreachable("Unknown immediate branch pseudo-instruction."); 2745 break; 2746 } 2747 2748 int64_t ImmValue = ImmOp.getImm(); 2749 if (ImmValue == 0) 2750 TOut.emitRRX(OpCode, DstRegOp.getReg(), Mips::ZERO, MemOffsetOp, IDLoc, 2751 STI); 2752 else { 2753 warnIfNoMacro(IDLoc); 2754 2755 unsigned ATReg = getATReg(IDLoc); 2756 if (!ATReg) 2757 return true; 2758 2759 if (loadImmediate(ImmValue, ATReg, Mips::NoRegister, !isGP64bit(), true, 2760 IDLoc, Out, STI)) 2761 return true; 2762 2763 TOut.emitRRX(OpCode, DstRegOp.getReg(), ATReg, MemOffsetOp, IDLoc, STI); 2764 } 2765 return false; 2766 } 2767 2768 void MipsAsmParser::expandMemInst(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 2769 const MCSubtargetInfo *STI, bool IsLoad, 2770 bool IsImmOpnd) { 2771 if (IsLoad) { 2772 expandLoadInst(Inst, IDLoc, Out, STI, IsImmOpnd); 2773 return; 2774 } 2775 expandStoreInst(Inst, IDLoc, Out, STI, IsImmOpnd); 2776 } 2777 2778 void MipsAsmParser::expandLoadInst(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 2779 const MCSubtargetInfo *STI, bool IsImmOpnd) { 2780 MipsTargetStreamer &TOut = getTargetStreamer(); 2781 2782 unsigned DstReg = Inst.getOperand(0).getReg(); 2783 unsigned BaseReg = Inst.getOperand(1).getReg(); 2784 2785 const MCInstrDesc &Desc = getInstDesc(Inst.getOpcode()); 2786 int16_t DstRegClass = Desc.OpInfo[0].RegClass; 2787 unsigned DstRegClassID = 2788 getContext().getRegisterInfo()->getRegClass(DstRegClass).getID(); 2789 bool IsGPR = (DstRegClassID == Mips::GPR32RegClassID) || 2790 (DstRegClassID == Mips::GPR64RegClassID); 2791 2792 if (IsImmOpnd) { 2793 // Try to use DstReg as the temporary. 2794 if (IsGPR && (BaseReg != DstReg)) { 2795 TOut.emitLoadWithImmOffset(Inst.getOpcode(), DstReg, BaseReg, 2796 Inst.getOperand(2).getImm(), DstReg, IDLoc, 2797 STI); 2798 return; 2799 } 2800 2801 // At this point we need AT to perform the expansions and we exit if it is 2802 // not available. 2803 unsigned ATReg = getATReg(IDLoc); 2804 if (!ATReg) 2805 return; 2806 2807 TOut.emitLoadWithImmOffset(Inst.getOpcode(), DstReg, BaseReg, 2808 Inst.getOperand(2).getImm(), ATReg, IDLoc, STI); 2809 return; 2810 } 2811 2812 const MCExpr *ExprOffset = Inst.getOperand(2).getExpr(); 2813 MCOperand LoOperand = MCOperand::createExpr( 2814 MipsMCExpr::create(MipsMCExpr::MEK_LO, ExprOffset, getContext())); 2815 MCOperand HiOperand = MCOperand::createExpr( 2816 MipsMCExpr::create(MipsMCExpr::MEK_HI, ExprOffset, getContext())); 2817 2818 // Try to use DstReg as the temporary. 2819 if (IsGPR && (BaseReg != DstReg)) { 2820 TOut.emitLoadWithSymOffset(Inst.getOpcode(), DstReg, BaseReg, HiOperand, 2821 LoOperand, DstReg, IDLoc, STI); 2822 return; 2823 } 2824 2825 // At this point we need AT to perform the expansions and we exit if it is 2826 // not available. 2827 unsigned ATReg = getATReg(IDLoc); 2828 if (!ATReg) 2829 return; 2830 2831 TOut.emitLoadWithSymOffset(Inst.getOpcode(), DstReg, BaseReg, HiOperand, 2832 LoOperand, ATReg, IDLoc, STI); 2833 } 2834 2835 void MipsAsmParser::expandStoreInst(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 2836 const MCSubtargetInfo *STI, 2837 bool IsImmOpnd) { 2838 MipsTargetStreamer &TOut = getTargetStreamer(); 2839 2840 unsigned SrcReg = Inst.getOperand(0).getReg(); 2841 unsigned BaseReg = Inst.getOperand(1).getReg(); 2842 2843 if (IsImmOpnd) { 2844 TOut.emitStoreWithImmOffset(Inst.getOpcode(), SrcReg, BaseReg, 2845 Inst.getOperand(2).getImm(), 2846 [&]() { return getATReg(IDLoc); }, IDLoc, STI); 2847 return; 2848 } 2849 2850 unsigned ATReg = getATReg(IDLoc); 2851 if (!ATReg) 2852 return; 2853 2854 const MCExpr *ExprOffset = Inst.getOperand(2).getExpr(); 2855 MCOperand LoOperand = MCOperand::createExpr( 2856 MipsMCExpr::create(MipsMCExpr::MEK_LO, ExprOffset, getContext())); 2857 MCOperand HiOperand = MCOperand::createExpr( 2858 MipsMCExpr::create(MipsMCExpr::MEK_HI, ExprOffset, getContext())); 2859 TOut.emitStoreWithSymOffset(Inst.getOpcode(), SrcReg, BaseReg, HiOperand, 2860 LoOperand, ATReg, IDLoc, STI); 2861 } 2862 2863 bool MipsAsmParser::expandLoadStoreMultiple(MCInst &Inst, SMLoc IDLoc, 2864 MCStreamer &Out, 2865 const MCSubtargetInfo *STI) { 2866 unsigned OpNum = Inst.getNumOperands(); 2867 unsigned Opcode = Inst.getOpcode(); 2868 unsigned NewOpcode = Opcode == Mips::SWM_MM ? Mips::SWM32_MM : Mips::LWM32_MM; 2869 2870 assert (Inst.getOperand(OpNum - 1).isImm() && 2871 Inst.getOperand(OpNum - 2).isReg() && 2872 Inst.getOperand(OpNum - 3).isReg() && "Invalid instruction operand."); 2873 2874 if (OpNum < 8 && Inst.getOperand(OpNum - 1).getImm() <= 60 && 2875 Inst.getOperand(OpNum - 1).getImm() >= 0 && 2876 (Inst.getOperand(OpNum - 2).getReg() == Mips::SP || 2877 Inst.getOperand(OpNum - 2).getReg() == Mips::SP_64) && 2878 (Inst.getOperand(OpNum - 3).getReg() == Mips::RA || 2879 Inst.getOperand(OpNum - 3).getReg() == Mips::RA_64)) { 2880 // It can be implemented as SWM16 or LWM16 instruction. 2881 if (inMicroMipsMode() && hasMips32r6()) 2882 NewOpcode = Opcode == Mips::SWM_MM ? Mips::SWM16_MMR6 : Mips::LWM16_MMR6; 2883 else 2884 NewOpcode = Opcode == Mips::SWM_MM ? Mips::SWM16_MM : Mips::LWM16_MM; 2885 } 2886 2887 Inst.setOpcode(NewOpcode); 2888 Out.EmitInstruction(Inst, *STI); 2889 return false; 2890 } 2891 2892 bool MipsAsmParser::expandCondBranches(MCInst &Inst, SMLoc IDLoc, 2893 MCStreamer &Out, 2894 const MCSubtargetInfo *STI) { 2895 MipsTargetStreamer &TOut = getTargetStreamer(); 2896 bool EmittedNoMacroWarning = false; 2897 unsigned PseudoOpcode = Inst.getOpcode(); 2898 unsigned SrcReg = Inst.getOperand(0).getReg(); 2899 const MCOperand &TrgOp = Inst.getOperand(1); 2900 const MCExpr *OffsetExpr = Inst.getOperand(2).getExpr(); 2901 2902 unsigned ZeroSrcOpcode, ZeroTrgOpcode; 2903 bool ReverseOrderSLT, IsUnsigned, IsLikely, AcceptsEquality; 2904 2905 unsigned TrgReg; 2906 if (TrgOp.isReg()) 2907 TrgReg = TrgOp.getReg(); 2908 else if (TrgOp.isImm()) { 2909 warnIfNoMacro(IDLoc); 2910 EmittedNoMacroWarning = true; 2911 2912 TrgReg = getATReg(IDLoc); 2913 if (!TrgReg) 2914 return true; 2915 2916 switch(PseudoOpcode) { 2917 default: 2918 llvm_unreachable("unknown opcode for branch pseudo-instruction"); 2919 case Mips::BLTImmMacro: 2920 PseudoOpcode = Mips::BLT; 2921 break; 2922 case Mips::BLEImmMacro: 2923 PseudoOpcode = Mips::BLE; 2924 break; 2925 case Mips::BGEImmMacro: 2926 PseudoOpcode = Mips::BGE; 2927 break; 2928 case Mips::BGTImmMacro: 2929 PseudoOpcode = Mips::BGT; 2930 break; 2931 case Mips::BLTUImmMacro: 2932 PseudoOpcode = Mips::BLTU; 2933 break; 2934 case Mips::BLEUImmMacro: 2935 PseudoOpcode = Mips::BLEU; 2936 break; 2937 case Mips::BGEUImmMacro: 2938 PseudoOpcode = Mips::BGEU; 2939 break; 2940 case Mips::BGTUImmMacro: 2941 PseudoOpcode = Mips::BGTU; 2942 break; 2943 case Mips::BLTLImmMacro: 2944 PseudoOpcode = Mips::BLTL; 2945 break; 2946 case Mips::BLELImmMacro: 2947 PseudoOpcode = Mips::BLEL; 2948 break; 2949 case Mips::BGELImmMacro: 2950 PseudoOpcode = Mips::BGEL; 2951 break; 2952 case Mips::BGTLImmMacro: 2953 PseudoOpcode = Mips::BGTL; 2954 break; 2955 case Mips::BLTULImmMacro: 2956 PseudoOpcode = Mips::BLTUL; 2957 break; 2958 case Mips::BLEULImmMacro: 2959 PseudoOpcode = Mips::BLEUL; 2960 break; 2961 case Mips::BGEULImmMacro: 2962 PseudoOpcode = Mips::BGEUL; 2963 break; 2964 case Mips::BGTULImmMacro: 2965 PseudoOpcode = Mips::BGTUL; 2966 break; 2967 } 2968 2969 if (loadImmediate(TrgOp.getImm(), TrgReg, Mips::NoRegister, !isGP64bit(), 2970 false, IDLoc, Out, STI)) 2971 return true; 2972 } 2973 2974 switch (PseudoOpcode) { 2975 case Mips::BLT: 2976 case Mips::BLTU: 2977 case Mips::BLTL: 2978 case Mips::BLTUL: 2979 AcceptsEquality = false; 2980 ReverseOrderSLT = false; 2981 IsUnsigned = ((PseudoOpcode == Mips::BLTU) || (PseudoOpcode == Mips::BLTUL)); 2982 IsLikely = ((PseudoOpcode == Mips::BLTL) || (PseudoOpcode == Mips::BLTUL)); 2983 ZeroSrcOpcode = Mips::BGTZ; 2984 ZeroTrgOpcode = Mips::BLTZ; 2985 break; 2986 case Mips::BLE: 2987 case Mips::BLEU: 2988 case Mips::BLEL: 2989 case Mips::BLEUL: 2990 AcceptsEquality = true; 2991 ReverseOrderSLT = true; 2992 IsUnsigned = ((PseudoOpcode == Mips::BLEU) || (PseudoOpcode == Mips::BLEUL)); 2993 IsLikely = ((PseudoOpcode == Mips::BLEL) || (PseudoOpcode == Mips::BLEUL)); 2994 ZeroSrcOpcode = Mips::BGEZ; 2995 ZeroTrgOpcode = Mips::BLEZ; 2996 break; 2997 case Mips::BGE: 2998 case Mips::BGEU: 2999 case Mips::BGEL: 3000 case Mips::BGEUL: 3001 AcceptsEquality = true; 3002 ReverseOrderSLT = false; 3003 IsUnsigned = ((PseudoOpcode == Mips::BGEU) || (PseudoOpcode == Mips::BGEUL)); 3004 IsLikely = ((PseudoOpcode == Mips::BGEL) || (PseudoOpcode == Mips::BGEUL)); 3005 ZeroSrcOpcode = Mips::BLEZ; 3006 ZeroTrgOpcode = Mips::BGEZ; 3007 break; 3008 case Mips::BGT: 3009 case Mips::BGTU: 3010 case Mips::BGTL: 3011 case Mips::BGTUL: 3012 AcceptsEquality = false; 3013 ReverseOrderSLT = true; 3014 IsUnsigned = ((PseudoOpcode == Mips::BGTU) || (PseudoOpcode == Mips::BGTUL)); 3015 IsLikely = ((PseudoOpcode == Mips::BGTL) || (PseudoOpcode == Mips::BGTUL)); 3016 ZeroSrcOpcode = Mips::BLTZ; 3017 ZeroTrgOpcode = Mips::BGTZ; 3018 break; 3019 default: 3020 llvm_unreachable("unknown opcode for branch pseudo-instruction"); 3021 } 3022 3023 bool IsTrgRegZero = (TrgReg == Mips::ZERO); 3024 bool IsSrcRegZero = (SrcReg == Mips::ZERO); 3025 if (IsSrcRegZero && IsTrgRegZero) { 3026 // FIXME: All of these Opcode-specific if's are needed for compatibility 3027 // with GAS' behaviour. However, they may not generate the most efficient 3028 // code in some circumstances. 3029 if (PseudoOpcode == Mips::BLT) { 3030 TOut.emitRX(Mips::BLTZ, Mips::ZERO, MCOperand::createExpr(OffsetExpr), 3031 IDLoc, STI); 3032 return false; 3033 } 3034 if (PseudoOpcode == Mips::BLE) { 3035 TOut.emitRX(Mips::BLEZ, Mips::ZERO, MCOperand::createExpr(OffsetExpr), 3036 IDLoc, STI); 3037 Warning(IDLoc, "branch is always taken"); 3038 return false; 3039 } 3040 if (PseudoOpcode == Mips::BGE) { 3041 TOut.emitRX(Mips::BGEZ, Mips::ZERO, MCOperand::createExpr(OffsetExpr), 3042 IDLoc, STI); 3043 Warning(IDLoc, "branch is always taken"); 3044 return false; 3045 } 3046 if (PseudoOpcode == Mips::BGT) { 3047 TOut.emitRX(Mips::BGTZ, Mips::ZERO, MCOperand::createExpr(OffsetExpr), 3048 IDLoc, STI); 3049 return false; 3050 } 3051 if (PseudoOpcode == Mips::BGTU) { 3052 TOut.emitRRX(Mips::BNE, Mips::ZERO, Mips::ZERO, 3053 MCOperand::createExpr(OffsetExpr), IDLoc, STI); 3054 return false; 3055 } 3056 if (AcceptsEquality) { 3057 // If both registers are $0 and the pseudo-branch accepts equality, it 3058 // will always be taken, so we emit an unconditional branch. 3059 TOut.emitRRX(Mips::BEQ, Mips::ZERO, Mips::ZERO, 3060 MCOperand::createExpr(OffsetExpr), IDLoc, STI); 3061 Warning(IDLoc, "branch is always taken"); 3062 return false; 3063 } 3064 // If both registers are $0 and the pseudo-branch does not accept 3065 // equality, it will never be taken, so we don't have to emit anything. 3066 return false; 3067 } 3068 if (IsSrcRegZero || IsTrgRegZero) { 3069 if ((IsSrcRegZero && PseudoOpcode == Mips::BGTU) || 3070 (IsTrgRegZero && PseudoOpcode == Mips::BLTU)) { 3071 // If the $rs is $0 and the pseudo-branch is BGTU (0 > x) or 3072 // if the $rt is $0 and the pseudo-branch is BLTU (x < 0), 3073 // the pseudo-branch will never be taken, so we don't emit anything. 3074 // This only applies to unsigned pseudo-branches. 3075 return false; 3076 } 3077 if ((IsSrcRegZero && PseudoOpcode == Mips::BLEU) || 3078 (IsTrgRegZero && PseudoOpcode == Mips::BGEU)) { 3079 // If the $rs is $0 and the pseudo-branch is BLEU (0 <= x) or 3080 // if the $rt is $0 and the pseudo-branch is BGEU (x >= 0), 3081 // the pseudo-branch will always be taken, so we emit an unconditional 3082 // branch. 3083 // This only applies to unsigned pseudo-branches. 3084 TOut.emitRRX(Mips::BEQ, Mips::ZERO, Mips::ZERO, 3085 MCOperand::createExpr(OffsetExpr), IDLoc, STI); 3086 Warning(IDLoc, "branch is always taken"); 3087 return false; 3088 } 3089 if (IsUnsigned) { 3090 // If the $rs is $0 and the pseudo-branch is BLTU (0 < x) or 3091 // if the $rt is $0 and the pseudo-branch is BGTU (x > 0), 3092 // the pseudo-branch will be taken only when the non-zero register is 3093 // different from 0, so we emit a BNEZ. 3094 // 3095 // If the $rs is $0 and the pseudo-branch is BGEU (0 >= x) or 3096 // if the $rt is $0 and the pseudo-branch is BLEU (x <= 0), 3097 // the pseudo-branch will be taken only when the non-zero register is 3098 // equal to 0, so we emit a BEQZ. 3099 // 3100 // Because only BLEU and BGEU branch on equality, we can use the 3101 // AcceptsEquality variable to decide when to emit the BEQZ. 3102 TOut.emitRRX(AcceptsEquality ? Mips::BEQ : Mips::BNE, 3103 IsSrcRegZero ? TrgReg : SrcReg, Mips::ZERO, 3104 MCOperand::createExpr(OffsetExpr), IDLoc, STI); 3105 return false; 3106 } 3107 // If we have a signed pseudo-branch and one of the registers is $0, 3108 // we can use an appropriate compare-to-zero branch. We select which one 3109 // to use in the switch statement above. 3110 TOut.emitRX(IsSrcRegZero ? ZeroSrcOpcode : ZeroTrgOpcode, 3111 IsSrcRegZero ? TrgReg : SrcReg, 3112 MCOperand::createExpr(OffsetExpr), IDLoc, STI); 3113 return false; 3114 } 3115 3116 // If neither the SrcReg nor the TrgReg are $0, we need AT to perform the 3117 // expansions. If it is not available, we return. 3118 unsigned ATRegNum = getATReg(IDLoc); 3119 if (!ATRegNum) 3120 return true; 3121 3122 if (!EmittedNoMacroWarning) 3123 warnIfNoMacro(IDLoc); 3124 3125 // SLT fits well with 2 of our 4 pseudo-branches: 3126 // BLT, where $rs < $rt, translates into "slt $at, $rs, $rt" and 3127 // BGT, where $rs > $rt, translates into "slt $at, $rt, $rs". 3128 // If the result of the SLT is 1, we branch, and if it's 0, we don't. 3129 // This is accomplished by using a BNEZ with the result of the SLT. 3130 // 3131 // The other 2 pseudo-branches are opposites of the above 2 (BGE with BLT 3132 // and BLE with BGT), so we change the BNEZ into a a BEQZ. 3133 // Because only BGE and BLE branch on equality, we can use the 3134 // AcceptsEquality variable to decide when to emit the BEQZ. 3135 // Note that the order of the SLT arguments doesn't change between 3136 // opposites. 3137 // 3138 // The same applies to the unsigned variants, except that SLTu is used 3139 // instead of SLT. 3140 TOut.emitRRR(IsUnsigned ? Mips::SLTu : Mips::SLT, ATRegNum, 3141 ReverseOrderSLT ? TrgReg : SrcReg, 3142 ReverseOrderSLT ? SrcReg : TrgReg, IDLoc, STI); 3143 3144 TOut.emitRRX(IsLikely ? (AcceptsEquality ? Mips::BEQL : Mips::BNEL) 3145 : (AcceptsEquality ? Mips::BEQ : Mips::BNE), 3146 ATRegNum, Mips::ZERO, MCOperand::createExpr(OffsetExpr), IDLoc, 3147 STI); 3148 return false; 3149 } 3150 3151 bool MipsAsmParser::expandDiv(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 3152 const MCSubtargetInfo *STI, const bool IsMips64, 3153 const bool Signed) { 3154 MipsTargetStreamer &TOut = getTargetStreamer(); 3155 3156 warnIfNoMacro(IDLoc); 3157 3158 const MCOperand &RdRegOp = Inst.getOperand(0); 3159 assert(RdRegOp.isReg() && "expected register operand kind"); 3160 unsigned RdReg = RdRegOp.getReg(); 3161 3162 const MCOperand &RsRegOp = Inst.getOperand(1); 3163 assert(RsRegOp.isReg() && "expected register operand kind"); 3164 unsigned RsReg = RsRegOp.getReg(); 3165 3166 const MCOperand &RtRegOp = Inst.getOperand(2); 3167 assert(RtRegOp.isReg() && "expected register operand kind"); 3168 unsigned RtReg = RtRegOp.getReg(); 3169 unsigned DivOp; 3170 unsigned ZeroReg; 3171 3172 if (IsMips64) { 3173 DivOp = Signed ? Mips::DSDIV : Mips::DUDIV; 3174 ZeroReg = Mips::ZERO_64; 3175 } else { 3176 DivOp = Signed ? Mips::SDIV : Mips::UDIV; 3177 ZeroReg = Mips::ZERO; 3178 } 3179 3180 bool UseTraps = useTraps(); 3181 3182 if (RsReg == Mips::ZERO || RsReg == Mips::ZERO_64) { 3183 if (RtReg == Mips::ZERO || RtReg == Mips::ZERO_64) 3184 Warning(IDLoc, "dividing zero by zero"); 3185 if (IsMips64) { 3186 if (Signed && (RtReg == Mips::ZERO || RtReg == Mips::ZERO_64)) { 3187 if (UseTraps) { 3188 TOut.emitRRI(Mips::TEQ, RtReg, ZeroReg, 0x7, IDLoc, STI); 3189 return false; 3190 } 3191 3192 TOut.emitII(Mips::BREAK, 0x7, 0, IDLoc, STI); 3193 return false; 3194 } 3195 } else { 3196 TOut.emitRR(DivOp, RsReg, RtReg, IDLoc, STI); 3197 return false; 3198 } 3199 } 3200 3201 if (RtReg == Mips::ZERO || RtReg == Mips::ZERO_64) { 3202 Warning(IDLoc, "division by zero"); 3203 if (Signed) { 3204 if (UseTraps) { 3205 TOut.emitRRI(Mips::TEQ, RtReg, ZeroReg, 0x7, IDLoc, STI); 3206 return false; 3207 } 3208 3209 TOut.emitII(Mips::BREAK, 0x7, 0, IDLoc, STI); 3210 return false; 3211 } 3212 } 3213 3214 // FIXME: The values for these two BranchTarget variables may be different in 3215 // micromips. These magic numbers need to be removed. 3216 unsigned BranchTargetNoTraps; 3217 unsigned BranchTarget; 3218 3219 if (UseTraps) { 3220 BranchTarget = IsMips64 ? 12 : 8; 3221 TOut.emitRRI(Mips::TEQ, RtReg, ZeroReg, 0x7, IDLoc, STI); 3222 } else { 3223 BranchTarget = IsMips64 ? 20 : 16; 3224 BranchTargetNoTraps = 8; 3225 // Branch to the li instruction. 3226 TOut.emitRRI(Mips::BNE, RtReg, ZeroReg, BranchTargetNoTraps, IDLoc, STI); 3227 } 3228 3229 TOut.emitRR(DivOp, RsReg, RtReg, IDLoc, STI); 3230 3231 if (!UseTraps) 3232 TOut.emitII(Mips::BREAK, 0x7, 0, IDLoc, STI); 3233 3234 if (!Signed) { 3235 TOut.emitR(Mips::MFLO, RdReg, IDLoc, STI); 3236 return false; 3237 } 3238 3239 unsigned ATReg = getATReg(IDLoc); 3240 if (!ATReg) 3241 return true; 3242 3243 TOut.emitRRI(Mips::ADDiu, ATReg, ZeroReg, -1, IDLoc, STI); 3244 if (IsMips64) { 3245 // Branch to the mflo instruction. 3246 TOut.emitRRI(Mips::BNE, RtReg, ATReg, BranchTarget, IDLoc, STI); 3247 TOut.emitRRI(Mips::ADDiu, ATReg, ZeroReg, 1, IDLoc, STI); 3248 TOut.emitRRI(Mips::DSLL32, ATReg, ATReg, 0x1f, IDLoc, STI); 3249 } else { 3250 // Branch to the mflo instruction. 3251 TOut.emitRRI(Mips::BNE, RtReg, ATReg, BranchTarget, IDLoc, STI); 3252 TOut.emitRI(Mips::LUi, ATReg, (uint16_t)0x8000, IDLoc, STI); 3253 } 3254 3255 if (UseTraps) 3256 TOut.emitRRI(Mips::TEQ, RsReg, ATReg, 0x6, IDLoc, STI); 3257 else { 3258 // Branch to the mflo instruction. 3259 TOut.emitRRI(Mips::BNE, RsReg, ATReg, BranchTargetNoTraps, IDLoc, STI); 3260 TOut.emitRRI(Mips::SLL, ZeroReg, ZeroReg, 0, IDLoc, STI); 3261 TOut.emitII(Mips::BREAK, 0x6, 0, IDLoc, STI); 3262 } 3263 TOut.emitR(Mips::MFLO, RdReg, IDLoc, STI); 3264 return false; 3265 } 3266 3267 bool MipsAsmParser::expandTrunc(MCInst &Inst, bool IsDouble, bool Is64FPU, 3268 SMLoc IDLoc, MCStreamer &Out, 3269 const MCSubtargetInfo *STI) { 3270 MipsTargetStreamer &TOut = getTargetStreamer(); 3271 3272 assert(Inst.getNumOperands() == 3 && "Invalid operand count"); 3273 assert(Inst.getOperand(0).isReg() && Inst.getOperand(1).isReg() && 3274 Inst.getOperand(2).isReg() && "Invalid instruction operand."); 3275 3276 unsigned FirstReg = Inst.getOperand(0).getReg(); 3277 unsigned SecondReg = Inst.getOperand(1).getReg(); 3278 unsigned ThirdReg = Inst.getOperand(2).getReg(); 3279 3280 if (hasMips1() && !hasMips2()) { 3281 unsigned ATReg = getATReg(IDLoc); 3282 if (!ATReg) 3283 return true; 3284 TOut.emitRR(Mips::CFC1, ThirdReg, Mips::RA, IDLoc, STI); 3285 TOut.emitRR(Mips::CFC1, ThirdReg, Mips::RA, IDLoc, STI); 3286 TOut.emitNop(IDLoc, STI); 3287 TOut.emitRRI(Mips::ORi, ATReg, ThirdReg, 0x3, IDLoc, STI); 3288 TOut.emitRRI(Mips::XORi, ATReg, ATReg, 0x2, IDLoc, STI); 3289 TOut.emitRR(Mips::CTC1, Mips::RA, ATReg, IDLoc, STI); 3290 TOut.emitNop(IDLoc, STI); 3291 TOut.emitRR(IsDouble ? (Is64FPU ? Mips::CVT_W_D64 : Mips::CVT_W_D32) 3292 : Mips::CVT_W_S, 3293 FirstReg, SecondReg, IDLoc, STI); 3294 TOut.emitRR(Mips::CTC1, Mips::RA, ThirdReg, IDLoc, STI); 3295 TOut.emitNop(IDLoc, STI); 3296 return false; 3297 } 3298 3299 TOut.emitRR(IsDouble ? (Is64FPU ? Mips::TRUNC_W_D64 : Mips::TRUNC_W_D32) 3300 : Mips::TRUNC_W_S, 3301 FirstReg, SecondReg, IDLoc, STI); 3302 3303 return false; 3304 } 3305 3306 bool MipsAsmParser::expandUlh(MCInst &Inst, bool Signed, SMLoc IDLoc, 3307 MCStreamer &Out, const MCSubtargetInfo *STI) { 3308 MipsTargetStreamer &TOut = getTargetStreamer(); 3309 3310 if (hasMips32r6() || hasMips64r6()) { 3311 return Error(IDLoc, "instruction not supported on mips32r6 or mips64r6"); 3312 } 3313 3314 warnIfNoMacro(IDLoc); 3315 3316 const MCOperand &DstRegOp = Inst.getOperand(0); 3317 assert(DstRegOp.isReg() && "expected register operand kind"); 3318 3319 const MCOperand &SrcRegOp = Inst.getOperand(1); 3320 assert(SrcRegOp.isReg() && "expected register operand kind"); 3321 3322 const MCOperand &OffsetImmOp = Inst.getOperand(2); 3323 assert(OffsetImmOp.isImm() && "expected immediate operand kind"); 3324 3325 unsigned DstReg = DstRegOp.getReg(); 3326 unsigned SrcReg = SrcRegOp.getReg(); 3327 int64_t OffsetValue = OffsetImmOp.getImm(); 3328 3329 // NOTE: We always need AT for ULHU, as it is always used as the source 3330 // register for one of the LBu's. 3331 unsigned ATReg = getATReg(IDLoc); 3332 if (!ATReg) 3333 return true; 3334 3335 // When the value of offset+1 does not fit in 16 bits, we have to load the 3336 // offset in AT, (D)ADDu the original source register (if there was one), and 3337 // then use AT as the source register for the 2 generated LBu's. 3338 bool LoadedOffsetInAT = false; 3339 if (!isInt<16>(OffsetValue + 1) || !isInt<16>(OffsetValue)) { 3340 LoadedOffsetInAT = true; 3341 3342 if (loadImmediate(OffsetValue, ATReg, Mips::NoRegister, !ABI.ArePtrs64bit(), 3343 true, IDLoc, Out, STI)) 3344 return true; 3345 3346 // NOTE: We do this (D)ADDu here instead of doing it in loadImmediate() 3347 // because it will make our output more similar to GAS'. For example, 3348 // generating an "ori $1, $zero, 32768" followed by an "addu $1, $1, $9", 3349 // instead of just an "ori $1, $9, 32768". 3350 // NOTE: If there is no source register specified in the ULHU, the parser 3351 // will interpret it as $0. 3352 if (SrcReg != Mips::ZERO && SrcReg != Mips::ZERO_64) 3353 TOut.emitAddu(ATReg, ATReg, SrcReg, ABI.ArePtrs64bit(), STI); 3354 } 3355 3356 unsigned FirstLbuDstReg = LoadedOffsetInAT ? DstReg : ATReg; 3357 unsigned SecondLbuDstReg = LoadedOffsetInAT ? ATReg : DstReg; 3358 unsigned LbuSrcReg = LoadedOffsetInAT ? ATReg : SrcReg; 3359 3360 int64_t FirstLbuOffset = 0, SecondLbuOffset = 0; 3361 if (isLittle()) { 3362 FirstLbuOffset = LoadedOffsetInAT ? 1 : (OffsetValue + 1); 3363 SecondLbuOffset = LoadedOffsetInAT ? 0 : OffsetValue; 3364 } else { 3365 FirstLbuOffset = LoadedOffsetInAT ? 0 : OffsetValue; 3366 SecondLbuOffset = LoadedOffsetInAT ? 1 : (OffsetValue + 1); 3367 } 3368 3369 unsigned SllReg = LoadedOffsetInAT ? DstReg : ATReg; 3370 3371 TOut.emitRRI(Signed ? Mips::LB : Mips::LBu, FirstLbuDstReg, LbuSrcReg, 3372 FirstLbuOffset, IDLoc, STI); 3373 3374 TOut.emitRRI(Mips::LBu, SecondLbuDstReg, LbuSrcReg, SecondLbuOffset, IDLoc, 3375 STI); 3376 3377 TOut.emitRRI(Mips::SLL, SllReg, SllReg, 8, IDLoc, STI); 3378 3379 TOut.emitRRR(Mips::OR, DstReg, DstReg, ATReg, IDLoc, STI); 3380 3381 return false; 3382 } 3383 3384 bool MipsAsmParser::expandUlw(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 3385 const MCSubtargetInfo *STI) { 3386 MipsTargetStreamer &TOut = getTargetStreamer(); 3387 3388 if (hasMips32r6() || hasMips64r6()) 3389 return Error(IDLoc, "instruction not supported on mips32r6 or mips64r6"); 3390 3391 const MCOperand &DstRegOp = Inst.getOperand(0); 3392 assert(DstRegOp.isReg() && "expected register operand kind"); 3393 3394 const MCOperand &SrcRegOp = Inst.getOperand(1); 3395 assert(SrcRegOp.isReg() && "expected register operand kind"); 3396 3397 const MCOperand &OffsetImmOp = Inst.getOperand(2); 3398 assert(OffsetImmOp.isImm() && "expected immediate operand kind"); 3399 3400 unsigned SrcReg = SrcRegOp.getReg(); 3401 int64_t OffsetValue = OffsetImmOp.getImm(); 3402 unsigned ATReg = 0; 3403 3404 // When the value of offset+3 does not fit in 16 bits, we have to load the 3405 // offset in AT, (D)ADDu the original source register (if there was one), and 3406 // then use AT as the source register for the generated LWL and LWR. 3407 bool LoadedOffsetInAT = false; 3408 if (!isInt<16>(OffsetValue + 3) || !isInt<16>(OffsetValue)) { 3409 ATReg = getATReg(IDLoc); 3410 if (!ATReg) 3411 return true; 3412 LoadedOffsetInAT = true; 3413 3414 warnIfNoMacro(IDLoc); 3415 3416 if (loadImmediate(OffsetValue, ATReg, Mips::NoRegister, !ABI.ArePtrs64bit(), 3417 true, IDLoc, Out, STI)) 3418 return true; 3419 3420 // NOTE: We do this (D)ADDu here instead of doing it in loadImmediate() 3421 // because it will make our output more similar to GAS'. For example, 3422 // generating an "ori $1, $zero, 32768" followed by an "addu $1, $1, $9", 3423 // instead of just an "ori $1, $9, 32768". 3424 // NOTE: If there is no source register specified in the ULW, the parser 3425 // will interpret it as $0. 3426 if (SrcReg != Mips::ZERO && SrcReg != Mips::ZERO_64) 3427 TOut.emitAddu(ATReg, ATReg, SrcReg, ABI.ArePtrs64bit(), STI); 3428 } 3429 3430 unsigned FinalSrcReg = LoadedOffsetInAT ? ATReg : SrcReg; 3431 int64_t LeftLoadOffset = 0, RightLoadOffset = 0; 3432 if (isLittle()) { 3433 LeftLoadOffset = LoadedOffsetInAT ? 3 : (OffsetValue + 3); 3434 RightLoadOffset = LoadedOffsetInAT ? 0 : OffsetValue; 3435 } else { 3436 LeftLoadOffset = LoadedOffsetInAT ? 0 : OffsetValue; 3437 RightLoadOffset = LoadedOffsetInAT ? 3 : (OffsetValue + 3); 3438 } 3439 3440 TOut.emitRRI(Mips::LWL, DstRegOp.getReg(), FinalSrcReg, LeftLoadOffset, IDLoc, 3441 STI); 3442 3443 TOut.emitRRI(Mips::LWR, DstRegOp.getReg(), FinalSrcReg, RightLoadOffset, 3444 IDLoc, STI); 3445 3446 return false; 3447 } 3448 3449 bool MipsAsmParser::expandAliasImmediate(MCInst &Inst, SMLoc IDLoc, 3450 MCStreamer &Out, 3451 const MCSubtargetInfo *STI) { 3452 MipsTargetStreamer &TOut = getTargetStreamer(); 3453 3454 assert (Inst.getNumOperands() == 3 && "Invalid operand count"); 3455 assert (Inst.getOperand(0).isReg() && 3456 Inst.getOperand(1).isReg() && 3457 Inst.getOperand(2).isImm() && "Invalid instruction operand."); 3458 3459 unsigned ATReg = Mips::NoRegister; 3460 unsigned FinalDstReg = Mips::NoRegister; 3461 unsigned DstReg = Inst.getOperand(0).getReg(); 3462 unsigned SrcReg = Inst.getOperand(1).getReg(); 3463 int64_t ImmValue = Inst.getOperand(2).getImm(); 3464 3465 bool Is32Bit = isInt<32>(ImmValue) || isUInt<32>(ImmValue); 3466 3467 unsigned FinalOpcode = Inst.getOpcode(); 3468 3469 if (DstReg == SrcReg) { 3470 ATReg = getATReg(Inst.getLoc()); 3471 if (!ATReg) 3472 return true; 3473 FinalDstReg = DstReg; 3474 DstReg = ATReg; 3475 } 3476 3477 if (!loadImmediate(ImmValue, DstReg, Mips::NoRegister, Is32Bit, false, Inst.getLoc(), Out, STI)) { 3478 switch (FinalOpcode) { 3479 default: 3480 llvm_unreachable("unimplemented expansion"); 3481 case (Mips::ADDi): 3482 FinalOpcode = Mips::ADD; 3483 break; 3484 case (Mips::ADDiu): 3485 FinalOpcode = Mips::ADDu; 3486 break; 3487 case (Mips::ANDi): 3488 FinalOpcode = Mips::AND; 3489 break; 3490 case (Mips::NORImm): 3491 FinalOpcode = Mips::NOR; 3492 break; 3493 case (Mips::ORi): 3494 FinalOpcode = Mips::OR; 3495 break; 3496 case (Mips::SLTi): 3497 FinalOpcode = Mips::SLT; 3498 break; 3499 case (Mips::SLTiu): 3500 FinalOpcode = Mips::SLTu; 3501 break; 3502 case (Mips::XORi): 3503 FinalOpcode = Mips::XOR; 3504 break; 3505 } 3506 3507 if (FinalDstReg == Mips::NoRegister) 3508 TOut.emitRRR(FinalOpcode, DstReg, DstReg, SrcReg, IDLoc, STI); 3509 else 3510 TOut.emitRRR(FinalOpcode, FinalDstReg, FinalDstReg, DstReg, IDLoc, STI); 3511 return false; 3512 } 3513 return true; 3514 } 3515 3516 bool MipsAsmParser::expandRotation(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 3517 const MCSubtargetInfo *STI) { 3518 MipsTargetStreamer &TOut = getTargetStreamer(); 3519 unsigned ATReg = Mips::NoRegister; 3520 unsigned DReg = Inst.getOperand(0).getReg(); 3521 unsigned SReg = Inst.getOperand(1).getReg(); 3522 unsigned TReg = Inst.getOperand(2).getReg(); 3523 unsigned TmpReg = DReg; 3524 3525 unsigned FirstShift = Mips::NOP; 3526 unsigned SecondShift = Mips::NOP; 3527 3528 if (hasMips32r2()) { 3529 3530 if (DReg == SReg) { 3531 TmpReg = getATReg(Inst.getLoc()); 3532 if (!TmpReg) 3533 return true; 3534 } 3535 3536 if (Inst.getOpcode() == Mips::ROL) { 3537 TOut.emitRRR(Mips::SUBu, TmpReg, Mips::ZERO, TReg, Inst.getLoc(), STI); 3538 TOut.emitRRR(Mips::ROTRV, DReg, SReg, TmpReg, Inst.getLoc(), STI); 3539 return false; 3540 } 3541 3542 if (Inst.getOpcode() == Mips::ROR) { 3543 TOut.emitRRR(Mips::ROTRV, DReg, SReg, TReg, Inst.getLoc(), STI); 3544 return false; 3545 } 3546 3547 return true; 3548 } 3549 3550 if (hasMips32()) { 3551 3552 switch (Inst.getOpcode()) { 3553 default: 3554 llvm_unreachable("unexpected instruction opcode"); 3555 case Mips::ROL: 3556 FirstShift = Mips::SRLV; 3557 SecondShift = Mips::SLLV; 3558 break; 3559 case Mips::ROR: 3560 FirstShift = Mips::SLLV; 3561 SecondShift = Mips::SRLV; 3562 break; 3563 } 3564 3565 ATReg = getATReg(Inst.getLoc()); 3566 if (!ATReg) 3567 return true; 3568 3569 TOut.emitRRR(Mips::SUBu, ATReg, Mips::ZERO, TReg, Inst.getLoc(), STI); 3570 TOut.emitRRR(FirstShift, ATReg, SReg, ATReg, Inst.getLoc(), STI); 3571 TOut.emitRRR(SecondShift, DReg, SReg, TReg, Inst.getLoc(), STI); 3572 TOut.emitRRR(Mips::OR, DReg, DReg, ATReg, Inst.getLoc(), STI); 3573 3574 return false; 3575 } 3576 3577 return true; 3578 } 3579 3580 bool MipsAsmParser::expandRotationImm(MCInst &Inst, SMLoc IDLoc, 3581 MCStreamer &Out, 3582 const MCSubtargetInfo *STI) { 3583 MipsTargetStreamer &TOut = getTargetStreamer(); 3584 unsigned ATReg = Mips::NoRegister; 3585 unsigned DReg = Inst.getOperand(0).getReg(); 3586 unsigned SReg = Inst.getOperand(1).getReg(); 3587 int64_t ImmValue = Inst.getOperand(2).getImm(); 3588 3589 unsigned FirstShift = Mips::NOP; 3590 unsigned SecondShift = Mips::NOP; 3591 3592 if (hasMips32r2()) { 3593 3594 if (Inst.getOpcode() == Mips::ROLImm) { 3595 uint64_t MaxShift = 32; 3596 uint64_t ShiftValue = ImmValue; 3597 if (ImmValue != 0) 3598 ShiftValue = MaxShift - ImmValue; 3599 TOut.emitRRI(Mips::ROTR, DReg, SReg, ShiftValue, Inst.getLoc(), STI); 3600 return false; 3601 } 3602 3603 if (Inst.getOpcode() == Mips::RORImm) { 3604 TOut.emitRRI(Mips::ROTR, DReg, SReg, ImmValue, Inst.getLoc(), STI); 3605 return false; 3606 } 3607 3608 return true; 3609 } 3610 3611 if (hasMips32()) { 3612 3613 if (ImmValue == 0) { 3614 TOut.emitRRI(Mips::SRL, DReg, SReg, 0, Inst.getLoc(), STI); 3615 return false; 3616 } 3617 3618 switch (Inst.getOpcode()) { 3619 default: 3620 llvm_unreachable("unexpected instruction opcode"); 3621 case Mips::ROLImm: 3622 FirstShift = Mips::SLL; 3623 SecondShift = Mips::SRL; 3624 break; 3625 case Mips::RORImm: 3626 FirstShift = Mips::SRL; 3627 SecondShift = Mips::SLL; 3628 break; 3629 } 3630 3631 ATReg = getATReg(Inst.getLoc()); 3632 if (!ATReg) 3633 return true; 3634 3635 TOut.emitRRI(FirstShift, ATReg, SReg, ImmValue, Inst.getLoc(), STI); 3636 TOut.emitRRI(SecondShift, DReg, SReg, 32 - ImmValue, Inst.getLoc(), STI); 3637 TOut.emitRRR(Mips::OR, DReg, DReg, ATReg, Inst.getLoc(), STI); 3638 3639 return false; 3640 } 3641 3642 return true; 3643 } 3644 3645 bool MipsAsmParser::expandDRotation(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 3646 const MCSubtargetInfo *STI) { 3647 MipsTargetStreamer &TOut = getTargetStreamer(); 3648 unsigned ATReg = Mips::NoRegister; 3649 unsigned DReg = Inst.getOperand(0).getReg(); 3650 unsigned SReg = Inst.getOperand(1).getReg(); 3651 unsigned TReg = Inst.getOperand(2).getReg(); 3652 unsigned TmpReg = DReg; 3653 3654 unsigned FirstShift = Mips::NOP; 3655 unsigned SecondShift = Mips::NOP; 3656 3657 if (hasMips64r2()) { 3658 3659 if (TmpReg == SReg) { 3660 TmpReg = getATReg(Inst.getLoc()); 3661 if (!TmpReg) 3662 return true; 3663 } 3664 3665 if (Inst.getOpcode() == Mips::DROL) { 3666 TOut.emitRRR(Mips::DSUBu, TmpReg, Mips::ZERO, TReg, Inst.getLoc(), STI); 3667 TOut.emitRRR(Mips::DROTRV, DReg, SReg, TmpReg, Inst.getLoc(), STI); 3668 return false; 3669 } 3670 3671 if (Inst.getOpcode() == Mips::DROR) { 3672 TOut.emitRRR(Mips::DROTRV, DReg, SReg, TReg, Inst.getLoc(), STI); 3673 return false; 3674 } 3675 3676 return true; 3677 } 3678 3679 if (hasMips64()) { 3680 3681 switch (Inst.getOpcode()) { 3682 default: 3683 llvm_unreachable("unexpected instruction opcode"); 3684 case Mips::DROL: 3685 FirstShift = Mips::DSRLV; 3686 SecondShift = Mips::DSLLV; 3687 break; 3688 case Mips::DROR: 3689 FirstShift = Mips::DSLLV; 3690 SecondShift = Mips::DSRLV; 3691 break; 3692 } 3693 3694 ATReg = getATReg(Inst.getLoc()); 3695 if (!ATReg) 3696 return true; 3697 3698 TOut.emitRRR(Mips::DSUBu, ATReg, Mips::ZERO, TReg, Inst.getLoc(), STI); 3699 TOut.emitRRR(FirstShift, ATReg, SReg, ATReg, Inst.getLoc(), STI); 3700 TOut.emitRRR(SecondShift, DReg, SReg, TReg, Inst.getLoc(), STI); 3701 TOut.emitRRR(Mips::OR, DReg, DReg, ATReg, Inst.getLoc(), STI); 3702 3703 return false; 3704 } 3705 3706 return true; 3707 } 3708 3709 bool MipsAsmParser::expandDRotationImm(MCInst &Inst, SMLoc IDLoc, 3710 MCStreamer &Out, 3711 const MCSubtargetInfo *STI) { 3712 MipsTargetStreamer &TOut = getTargetStreamer(); 3713 unsigned ATReg = Mips::NoRegister; 3714 unsigned DReg = Inst.getOperand(0).getReg(); 3715 unsigned SReg = Inst.getOperand(1).getReg(); 3716 int64_t ImmValue = Inst.getOperand(2).getImm() % 64; 3717 3718 unsigned FirstShift = Mips::NOP; 3719 unsigned SecondShift = Mips::NOP; 3720 3721 MCInst TmpInst; 3722 3723 if (hasMips64r2()) { 3724 3725 unsigned FinalOpcode = Mips::NOP; 3726 if (ImmValue == 0) 3727 FinalOpcode = Mips::DROTR; 3728 else if (ImmValue % 32 == 0) 3729 FinalOpcode = Mips::DROTR32; 3730 else if ((ImmValue >= 1) && (ImmValue <= 32)) { 3731 if (Inst.getOpcode() == Mips::DROLImm) 3732 FinalOpcode = Mips::DROTR32; 3733 else 3734 FinalOpcode = Mips::DROTR; 3735 } else if (ImmValue >= 33) { 3736 if (Inst.getOpcode() == Mips::DROLImm) 3737 FinalOpcode = Mips::DROTR; 3738 else 3739 FinalOpcode = Mips::DROTR32; 3740 } 3741 3742 uint64_t ShiftValue = ImmValue % 32; 3743 if (Inst.getOpcode() == Mips::DROLImm) 3744 ShiftValue = (32 - ImmValue % 32) % 32; 3745 3746 TOut.emitRRI(FinalOpcode, DReg, SReg, ShiftValue, Inst.getLoc(), STI); 3747 3748 return false; 3749 } 3750 3751 if (hasMips64()) { 3752 3753 if (ImmValue == 0) { 3754 TOut.emitRRI(Mips::DSRL, DReg, SReg, 0, Inst.getLoc(), STI); 3755 return false; 3756 } 3757 3758 switch (Inst.getOpcode()) { 3759 default: 3760 llvm_unreachable("unexpected instruction opcode"); 3761 case Mips::DROLImm: 3762 if ((ImmValue >= 1) && (ImmValue <= 31)) { 3763 FirstShift = Mips::DSLL; 3764 SecondShift = Mips::DSRL32; 3765 } 3766 if (ImmValue == 32) { 3767 FirstShift = Mips::DSLL32; 3768 SecondShift = Mips::DSRL32; 3769 } 3770 if ((ImmValue >= 33) && (ImmValue <= 63)) { 3771 FirstShift = Mips::DSLL32; 3772 SecondShift = Mips::DSRL; 3773 } 3774 break; 3775 case Mips::DRORImm: 3776 if ((ImmValue >= 1) && (ImmValue <= 31)) { 3777 FirstShift = Mips::DSRL; 3778 SecondShift = Mips::DSLL32; 3779 } 3780 if (ImmValue == 32) { 3781 FirstShift = Mips::DSRL32; 3782 SecondShift = Mips::DSLL32; 3783 } 3784 if ((ImmValue >= 33) && (ImmValue <= 63)) { 3785 FirstShift = Mips::DSRL32; 3786 SecondShift = Mips::DSLL; 3787 } 3788 break; 3789 } 3790 3791 ATReg = getATReg(Inst.getLoc()); 3792 if (!ATReg) 3793 return true; 3794 3795 TOut.emitRRI(FirstShift, ATReg, SReg, ImmValue % 32, Inst.getLoc(), STI); 3796 TOut.emitRRI(SecondShift, DReg, SReg, (32 - ImmValue % 32) % 32, 3797 Inst.getLoc(), STI); 3798 TOut.emitRRR(Mips::OR, DReg, DReg, ATReg, Inst.getLoc(), STI); 3799 3800 return false; 3801 } 3802 3803 return true; 3804 } 3805 3806 bool MipsAsmParser::expandAbs(MCInst &Inst, SMLoc IDLoc, MCStreamer &Out, 3807 const MCSubtargetInfo *STI) { 3808 MipsTargetStreamer &TOut = getTargetStreamer(); 3809 unsigned FirstRegOp = Inst.getOperand(0).getReg(); 3810 unsigned SecondRegOp = Inst.getOperand(1).getReg(); 3811 3812 TOut.emitRI(Mips::BGEZ, SecondRegOp, 8, IDLoc, STI); 3813 if (FirstRegOp != SecondRegOp) 3814 TOut.emitRRR(Mips::ADDu, FirstRegOp, SecondRegOp, Mips::ZERO, IDLoc, STI); 3815 else 3816 TOut.emitEmptyDelaySlot(false, IDLoc, STI); 3817 TOut.emitRRR(Mips::SUB, FirstRegOp, Mips::ZERO, SecondRegOp, IDLoc, STI); 3818 3819 return false; 3820 } 3821 3822 unsigned 3823 MipsAsmParser::checkEarlyTargetMatchPredicate(MCInst &Inst, 3824 const OperandVector &Operands) { 3825 switch (Inst.getOpcode()) { 3826 default: 3827 return Match_Success; 3828 case Mips::DATI: 3829 case Mips::DAHI: 3830 if (static_cast<MipsOperand &>(*Operands[1]) 3831 .isValidForTie(static_cast<MipsOperand &>(*Operands[2]))) 3832 return Match_Success; 3833 return Match_RequiresSameSrcAndDst; 3834 } 3835 } 3836 unsigned MipsAsmParser::checkTargetMatchPredicate(MCInst &Inst) { 3837 switch (Inst.getOpcode()) { 3838 // As described by the Mips32r2 spec, the registers Rd and Rs for 3839 // jalr.hb must be different. 3840 // It also applies for registers Rt and Rs of microMIPSr6 jalrc.hb instruction 3841 // and registers Rd and Base for microMIPS lwp instruction 3842 case Mips::JALR_HB: 3843 case Mips::JALRC_HB_MMR6: 3844 case Mips::JALRC_MMR6: 3845 if (Inst.getOperand(0).getReg() == Inst.getOperand(1).getReg()) 3846 return Match_RequiresDifferentSrcAndDst; 3847 return Match_Success; 3848 case Mips::LWP_MM: 3849 case Mips::LWP_MMR6: 3850 if (Inst.getOperand(0).getReg() == Inst.getOperand(2).getReg()) 3851 return Match_RequiresDifferentSrcAndDst; 3852 return Match_Success; 3853 // As described the MIPSR6 spec, the compact branches that compare registers 3854 // must: 3855 // a) Not use the zero register. 3856 // b) Not use the same register twice. 3857 // c) rs < rt for bnec, beqc. 3858 // NB: For this case, the encoding will swap the operands as their 3859 // ordering doesn't matter. GAS performs this transformation too. 3860 // Hence, that constraint does not have to be enforced. 3861 // 3862 // The compact branches that branch iff the signed addition of two registers 3863 // would overflow must have rs >= rt. That can be handled like beqc/bnec with 3864 // operand swapping. They do not have restriction of using the zero register. 3865 case Mips::BLEZC: case Mips::BLEZC_MMR6: 3866 case Mips::BGEZC: case Mips::BGEZC_MMR6: 3867 case Mips::BGTZC: case Mips::BGTZC_MMR6: 3868 case Mips::BLTZC: case Mips::BLTZC_MMR6: 3869 case Mips::BEQZC: case Mips::BEQZC_MMR6: 3870 case Mips::BNEZC: case Mips::BNEZC_MMR6: 3871 case Mips::BLEZC64: 3872 case Mips::BGEZC64: 3873 case Mips::BGTZC64: 3874 case Mips::BLTZC64: 3875 case Mips::BEQZC64: 3876 case Mips::BNEZC64: 3877 if (Inst.getOperand(0).getReg() == Mips::ZERO || 3878 Inst.getOperand(0).getReg() == Mips::ZERO_64) 3879 return Match_RequiresNoZeroRegister; 3880 return Match_Success; 3881 case Mips::BGEC: case Mips::BGEC_MMR6: 3882 case Mips::BLTC: case Mips::BLTC_MMR6: 3883 case Mips::BGEUC: case Mips::BGEUC_MMR6: 3884 case Mips::BLTUC: case Mips::BLTUC_MMR6: 3885 case Mips::BEQC: case Mips::BEQC_MMR6: 3886 case Mips::BNEC: case Mips::BNEC_MMR6: 3887 case Mips::BGEC64: 3888 case Mips::BLTC64: 3889 case Mips::BGEUC64: 3890 case Mips::BLTUC64: 3891 case Mips::BEQC64: 3892 case Mips::BNEC64: 3893 if (Inst.getOperand(0).getReg() == Mips::ZERO || 3894 Inst.getOperand(0).getReg() == Mips::ZERO_64) 3895 return Match_RequiresNoZeroRegister; 3896 if (Inst.getOperand(1).getReg() == Mips::ZERO || 3897 Inst.getOperand(1).getReg() == Mips::ZERO_64) 3898 return Match_RequiresNoZeroRegister; 3899 if (Inst.getOperand(0).getReg() == Inst.getOperand(1).getReg()) 3900 return Match_RequiresDifferentOperands; 3901 return Match_Success; 3902 default: 3903 return Match_Success; 3904 } 3905 } 3906 3907 static SMLoc RefineErrorLoc(const SMLoc Loc, const OperandVector &Operands, 3908 uint64_t ErrorInfo) { 3909 if (ErrorInfo != ~0ULL && ErrorInfo < Operands.size()) { 3910 SMLoc ErrorLoc = Operands[ErrorInfo]->getStartLoc(); 3911 if (ErrorLoc == SMLoc()) 3912 return Loc; 3913 return ErrorLoc; 3914 } 3915 return Loc; 3916 } 3917 3918 bool MipsAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, 3919 OperandVector &Operands, 3920 MCStreamer &Out, 3921 uint64_t &ErrorInfo, 3922 bool MatchingInlineAsm) { 3923 3924 MCInst Inst; 3925 unsigned MatchResult = 3926 MatchInstructionImpl(Operands, Inst, ErrorInfo, MatchingInlineAsm); 3927 3928 switch (MatchResult) { 3929 case Match_Success: { 3930 if (processInstruction(Inst, IDLoc, Out, STI)) 3931 return true; 3932 return false; 3933 } 3934 case Match_MissingFeature: 3935 Error(IDLoc, "instruction requires a CPU feature not currently enabled"); 3936 return true; 3937 case Match_InvalidOperand: { 3938 SMLoc ErrorLoc = IDLoc; 3939 if (ErrorInfo != ~0ULL) { 3940 if (ErrorInfo >= Operands.size()) 3941 return Error(IDLoc, "too few operands for instruction"); 3942 3943 ErrorLoc = Operands[ErrorInfo]->getStartLoc(); 3944 if (ErrorLoc == SMLoc()) 3945 ErrorLoc = IDLoc; 3946 } 3947 3948 return Error(ErrorLoc, "invalid operand for instruction"); 3949 } 3950 case Match_MnemonicFail: 3951 return Error(IDLoc, "invalid instruction"); 3952 case Match_RequiresDifferentSrcAndDst: 3953 return Error(IDLoc, "source and destination must be different"); 3954 case Match_RequiresDifferentOperands: 3955 return Error(IDLoc, "registers must be different"); 3956 case Match_RequiresNoZeroRegister: 3957 return Error(IDLoc, "invalid operand ($zero) for instruction"); 3958 case Match_RequiresSameSrcAndDst: 3959 return Error(IDLoc, "source and destination must match"); 3960 case Match_Immz: 3961 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), "expected '0'"); 3962 case Match_UImm1_0: 3963 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3964 "expected 1-bit unsigned immediate"); 3965 case Match_UImm2_0: 3966 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3967 "expected 2-bit unsigned immediate"); 3968 case Match_UImm2_1: 3969 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3970 "expected immediate in range 1 .. 4"); 3971 case Match_UImm3_0: 3972 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3973 "expected 3-bit unsigned immediate"); 3974 case Match_UImm4_0: 3975 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3976 "expected 4-bit unsigned immediate"); 3977 case Match_SImm4_0: 3978 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3979 "expected 4-bit signed immediate"); 3980 case Match_UImm5_0: 3981 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3982 "expected 5-bit unsigned immediate"); 3983 case Match_SImm5_0: 3984 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3985 "expected 5-bit signed immediate"); 3986 case Match_UImm5_1: 3987 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3988 "expected immediate in range 1 .. 32"); 3989 case Match_UImm5_32: 3990 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3991 "expected immediate in range 32 .. 63"); 3992 case Match_UImm5_33: 3993 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3994 "expected immediate in range 33 .. 64"); 3995 case Match_UImm5_0_Report_UImm6: 3996 // This is used on UImm5 operands that have a corresponding UImm5_32 3997 // operand to avoid confusing the user. 3998 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 3999 "expected 6-bit unsigned immediate"); 4000 case Match_UImm5_Lsl2: 4001 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4002 "expected both 7-bit unsigned immediate and multiple of 4"); 4003 case Match_UImmRange2_64: 4004 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4005 "expected immediate in range 2 .. 64"); 4006 case Match_UImm6_0: 4007 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4008 "expected 6-bit unsigned immediate"); 4009 case Match_UImm6_Lsl2: 4010 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4011 "expected both 8-bit unsigned immediate and multiple of 4"); 4012 case Match_SImm6_0: 4013 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4014 "expected 6-bit signed immediate"); 4015 case Match_UImm7_0: 4016 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4017 "expected 7-bit unsigned immediate"); 4018 case Match_UImm7_N1: 4019 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4020 "expected immediate in range -1 .. 126"); 4021 case Match_SImm7_Lsl2: 4022 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4023 "expected both 9-bit signed immediate and multiple of 4"); 4024 case Match_UImm8_0: 4025 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4026 "expected 8-bit unsigned immediate"); 4027 case Match_UImm10_0: 4028 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4029 "expected 10-bit unsigned immediate"); 4030 case Match_SImm10_0: 4031 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4032 "expected 10-bit signed immediate"); 4033 case Match_SImm11_0: 4034 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4035 "expected 11-bit signed immediate"); 4036 case Match_UImm16: 4037 case Match_UImm16_Relaxed: 4038 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4039 "expected 16-bit unsigned immediate"); 4040 case Match_SImm16: 4041 case Match_SImm16_Relaxed: 4042 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4043 "expected 16-bit signed immediate"); 4044 case Match_SImm19_Lsl2: 4045 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4046 "expected both 19-bit signed immediate and multiple of 4"); 4047 case Match_UImm20_0: 4048 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4049 "expected 20-bit unsigned immediate"); 4050 case Match_UImm26_0: 4051 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4052 "expected 26-bit unsigned immediate"); 4053 case Match_SImm32: 4054 case Match_SImm32_Relaxed: 4055 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4056 "expected 32-bit signed immediate"); 4057 case Match_UImm32_Coerced: 4058 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4059 "expected 32-bit immediate"); 4060 case Match_MemSImm9: 4061 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4062 "expected memory with 9-bit signed offset"); 4063 case Match_MemSImm10: 4064 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4065 "expected memory with 10-bit signed offset"); 4066 case Match_MemSImm10Lsl1: 4067 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4068 "expected memory with 11-bit signed offset and multiple of 2"); 4069 case Match_MemSImm10Lsl2: 4070 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4071 "expected memory with 12-bit signed offset and multiple of 4"); 4072 case Match_MemSImm10Lsl3: 4073 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4074 "expected memory with 13-bit signed offset and multiple of 8"); 4075 case Match_MemSImm11: 4076 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4077 "expected memory with 11-bit signed offset"); 4078 case Match_MemSImm12: 4079 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4080 "expected memory with 12-bit signed offset"); 4081 case Match_MemSImm16: 4082 return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo), 4083 "expected memory with 16-bit signed offset"); 4084 } 4085 4086 llvm_unreachable("Implement any new match types added!"); 4087 } 4088 4089 void MipsAsmParser::warnIfRegIndexIsAT(unsigned RegIndex, SMLoc Loc) { 4090 if (RegIndex != 0 && AssemblerOptions.back()->getATRegIndex() == RegIndex) 4091 Warning(Loc, "used $at (currently $" + Twine(RegIndex) + 4092 ") without \".set noat\""); 4093 } 4094 4095 void MipsAsmParser::warnIfNoMacro(SMLoc Loc) { 4096 if (!AssemblerOptions.back()->isMacro()) 4097 Warning(Loc, "macro instruction expanded into multiple instructions"); 4098 } 4099 4100 void 4101 MipsAsmParser::printWarningWithFixIt(const Twine &Msg, const Twine &FixMsg, 4102 SMRange Range, bool ShowColors) { 4103 getSourceManager().PrintMessage(Range.Start, SourceMgr::DK_Warning, Msg, 4104 Range, SMFixIt(Range, FixMsg), 4105 ShowColors); 4106 } 4107 4108 int MipsAsmParser::matchCPURegisterName(StringRef Name) { 4109 int CC; 4110 4111 CC = StringSwitch<unsigned>(Name) 4112 .Case("zero", 0) 4113 .Case("at", 1) 4114 .Case("a0", 4) 4115 .Case("a1", 5) 4116 .Case("a2", 6) 4117 .Case("a3", 7) 4118 .Case("v0", 2) 4119 .Case("v1", 3) 4120 .Case("s0", 16) 4121 .Case("s1", 17) 4122 .Case("s2", 18) 4123 .Case("s3", 19) 4124 .Case("s4", 20) 4125 .Case("s5", 21) 4126 .Case("s6", 22) 4127 .Case("s7", 23) 4128 .Case("k0", 26) 4129 .Case("k1", 27) 4130 .Case("gp", 28) 4131 .Case("sp", 29) 4132 .Case("fp", 30) 4133 .Case("s8", 30) 4134 .Case("ra", 31) 4135 .Case("t0", 8) 4136 .Case("t1", 9) 4137 .Case("t2", 10) 4138 .Case("t3", 11) 4139 .Case("t4", 12) 4140 .Case("t5", 13) 4141 .Case("t6", 14) 4142 .Case("t7", 15) 4143 .Case("t8", 24) 4144 .Case("t9", 25) 4145 .Default(-1); 4146 4147 if (!(isABI_N32() || isABI_N64())) 4148 return CC; 4149 4150 if (12 <= CC && CC <= 15) { 4151 // Name is one of t4-t7 4152 AsmToken RegTok = getLexer().peekTok(); 4153 SMRange RegRange = RegTok.getLocRange(); 4154 4155 StringRef FixedName = StringSwitch<StringRef>(Name) 4156 .Case("t4", "t0") 4157 .Case("t5", "t1") 4158 .Case("t6", "t2") 4159 .Case("t7", "t3") 4160 .Default(""); 4161 assert(FixedName != "" && "Register name is not one of t4-t7."); 4162 4163 printWarningWithFixIt("register names $t4-$t7 are only available in O32.", 4164 "Did you mean $" + FixedName + "?", RegRange); 4165 } 4166 4167 // Although SGI documentation just cuts out t0-t3 for n32/n64, 4168 // GNU pushes the values of t0-t3 to override the o32/o64 values for t4-t7 4169 // We are supporting both cases, so for t0-t3 we'll just push them to t4-t7. 4170 if (8 <= CC && CC <= 11) 4171 CC += 4; 4172 4173 if (CC == -1) 4174 CC = StringSwitch<unsigned>(Name) 4175 .Case("a4", 8) 4176 .Case("a5", 9) 4177 .Case("a6", 10) 4178 .Case("a7", 11) 4179 .Case("kt0", 26) 4180 .Case("kt1", 27) 4181 .Default(-1); 4182 4183 return CC; 4184 } 4185 4186 int MipsAsmParser::matchHWRegsRegisterName(StringRef Name) { 4187 int CC; 4188 4189 CC = StringSwitch<unsigned>(Name) 4190 .Case("hwr_cpunum", 0) 4191 .Case("hwr_synci_step", 1) 4192 .Case("hwr_cc", 2) 4193 .Case("hwr_ccres", 3) 4194 .Case("hwr_ulr", 29) 4195 .Default(-1); 4196 4197 return CC; 4198 } 4199 4200 int MipsAsmParser::matchFPURegisterName(StringRef Name) { 4201 4202 if (Name[0] == 'f') { 4203 StringRef NumString = Name.substr(1); 4204 unsigned IntVal; 4205 if (NumString.getAsInteger(10, IntVal)) 4206 return -1; // This is not an integer. 4207 if (IntVal > 31) // Maximum index for fpu register. 4208 return -1; 4209 return IntVal; 4210 } 4211 return -1; 4212 } 4213 4214 int MipsAsmParser::matchFCCRegisterName(StringRef Name) { 4215 4216 if (Name.startswith("fcc")) { 4217 StringRef NumString = Name.substr(3); 4218 unsigned IntVal; 4219 if (NumString.getAsInteger(10, IntVal)) 4220 return -1; // This is not an integer. 4221 if (IntVal > 7) // There are only 8 fcc registers. 4222 return -1; 4223 return IntVal; 4224 } 4225 return -1; 4226 } 4227 4228 int MipsAsmParser::matchACRegisterName(StringRef Name) { 4229 4230 if (Name.startswith("ac")) { 4231 StringRef NumString = Name.substr(2); 4232 unsigned IntVal; 4233 if (NumString.getAsInteger(10, IntVal)) 4234 return -1; // This is not an integer. 4235 if (IntVal > 3) // There are only 3 acc registers. 4236 return -1; 4237 return IntVal; 4238 } 4239 return -1; 4240 } 4241 4242 int MipsAsmParser::matchMSA128RegisterName(StringRef Name) { 4243 unsigned IntVal; 4244 4245 if (Name.front() != 'w' || Name.drop_front(1).getAsInteger(10, IntVal)) 4246 return -1; 4247 4248 if (IntVal > 31) 4249 return -1; 4250 4251 return IntVal; 4252 } 4253 4254 int MipsAsmParser::matchMSA128CtrlRegisterName(StringRef Name) { 4255 int CC; 4256 4257 CC = StringSwitch<unsigned>(Name) 4258 .Case("msair", 0) 4259 .Case("msacsr", 1) 4260 .Case("msaaccess", 2) 4261 .Case("msasave", 3) 4262 .Case("msamodify", 4) 4263 .Case("msarequest", 5) 4264 .Case("msamap", 6) 4265 .Case("msaunmap", 7) 4266 .Default(-1); 4267 4268 return CC; 4269 } 4270 4271 unsigned MipsAsmParser::getATReg(SMLoc Loc) { 4272 unsigned ATIndex = AssemblerOptions.back()->getATRegIndex(); 4273 if (ATIndex == 0) { 4274 reportParseError(Loc, 4275 "pseudo-instruction requires $at, which is not available"); 4276 return 0; 4277 } 4278 unsigned AT = getReg( 4279 (isGP64bit()) ? Mips::GPR64RegClassID : Mips::GPR32RegClassID, ATIndex); 4280 return AT; 4281 } 4282 4283 unsigned MipsAsmParser::getReg(int RC, int RegNo) { 4284 return *(getContext().getRegisterInfo()->getRegClass(RC).begin() + RegNo); 4285 } 4286 4287 bool MipsAsmParser::parseOperand(OperandVector &Operands, StringRef Mnemonic) { 4288 MCAsmParser &Parser = getParser(); 4289 DEBUG(dbgs() << "parseOperand\n"); 4290 4291 // Check if the current operand has a custom associated parser, if so, try to 4292 // custom parse the operand, or fallback to the general approach. 4293 OperandMatchResultTy ResTy = MatchOperandParserImpl(Operands, Mnemonic); 4294 if (ResTy == MatchOperand_Success) 4295 return false; 4296 // If there wasn't a custom match, try the generic matcher below. Otherwise, 4297 // there was a match, but an error occurred, in which case, just return that 4298 // the operand parsing failed. 4299 if (ResTy == MatchOperand_ParseFail) 4300 return true; 4301 4302 DEBUG(dbgs() << ".. Generic Parser\n"); 4303 4304 switch (getLexer().getKind()) { 4305 case AsmToken::Dollar: { 4306 // Parse the register. 4307 SMLoc S = Parser.getTok().getLoc(); 4308 4309 // Almost all registers have been parsed by custom parsers. There is only 4310 // one exception to this. $zero (and it's alias $0) will reach this point 4311 // for div, divu, and similar instructions because it is not an operand 4312 // to the instruction definition but an explicit register. Special case 4313 // this situation for now. 4314 if (parseAnyRegister(Operands) != MatchOperand_NoMatch) 4315 return false; 4316 4317 // Maybe it is a symbol reference. 4318 StringRef Identifier; 4319 if (Parser.parseIdentifier(Identifier)) 4320 return true; 4321 4322 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 4323 MCSymbol *Sym = getContext().getOrCreateSymbol("$" + Identifier); 4324 // Otherwise create a symbol reference. 4325 const MCExpr *Res = 4326 MCSymbolRefExpr::create(Sym, MCSymbolRefExpr::VK_None, getContext()); 4327 4328 Operands.push_back(MipsOperand::CreateImm(Res, S, E, *this)); 4329 return false; 4330 } 4331 default: { 4332 DEBUG(dbgs() << ".. generic integer expression\n"); 4333 4334 const MCExpr *Expr; 4335 SMLoc S = Parser.getTok().getLoc(); // Start location of the operand. 4336 if (getParser().parseExpression(Expr)) 4337 return true; 4338 4339 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 4340 4341 Operands.push_back(MipsOperand::CreateImm(Expr, S, E, *this)); 4342 return false; 4343 } 4344 } // switch(getLexer().getKind()) 4345 return true; 4346 } 4347 4348 bool MipsAsmParser::isEvaluated(const MCExpr *Expr) { 4349 4350 switch (Expr->getKind()) { 4351 case MCExpr::Constant: 4352 return true; 4353 case MCExpr::SymbolRef: 4354 return (cast<MCSymbolRefExpr>(Expr)->getKind() != MCSymbolRefExpr::VK_None); 4355 case MCExpr::Binary: 4356 if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(Expr)) { 4357 if (!isEvaluated(BE->getLHS())) 4358 return false; 4359 return isEvaluated(BE->getRHS()); 4360 } 4361 case MCExpr::Unary: 4362 return isEvaluated(cast<MCUnaryExpr>(Expr)->getSubExpr()); 4363 case MCExpr::Target: 4364 return true; 4365 } 4366 return false; 4367 } 4368 4369 bool MipsAsmParser::ParseRegister(unsigned &RegNo, SMLoc &StartLoc, 4370 SMLoc &EndLoc) { 4371 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> Operands; 4372 OperandMatchResultTy ResTy = parseAnyRegister(Operands); 4373 if (ResTy == MatchOperand_Success) { 4374 assert(Operands.size() == 1); 4375 MipsOperand &Operand = static_cast<MipsOperand &>(*Operands.front()); 4376 StartLoc = Operand.getStartLoc(); 4377 EndLoc = Operand.getEndLoc(); 4378 4379 // AFAIK, we only support numeric registers and named GPR's in CFI 4380 // directives. 4381 // Don't worry about eating tokens before failing. Using an unrecognised 4382 // register is a parse error. 4383 if (Operand.isGPRAsmReg()) { 4384 // Resolve to GPR32 or GPR64 appropriately. 4385 RegNo = isGP64bit() ? Operand.getGPR64Reg() : Operand.getGPR32Reg(); 4386 } 4387 4388 return (RegNo == (unsigned)-1); 4389 } 4390 4391 assert(Operands.size() == 0); 4392 return (RegNo == (unsigned)-1); 4393 } 4394 4395 bool MipsAsmParser::parseMemOffset(const MCExpr *&Res, bool isParenExpr) { 4396 SMLoc S; 4397 4398 if (isParenExpr) 4399 return getParser().parseParenExprOfDepth(0, Res, S); 4400 return getParser().parseExpression(Res); 4401 } 4402 4403 MipsAsmParser::OperandMatchResultTy 4404 MipsAsmParser::parseMemOperand(OperandVector &Operands) { 4405 MCAsmParser &Parser = getParser(); 4406 DEBUG(dbgs() << "parseMemOperand\n"); 4407 const MCExpr *IdVal = nullptr; 4408 SMLoc S; 4409 bool isParenExpr = false; 4410 MipsAsmParser::OperandMatchResultTy Res = MatchOperand_NoMatch; 4411 // First operand is the offset. 4412 S = Parser.getTok().getLoc(); 4413 4414 if (getLexer().getKind() == AsmToken::LParen) { 4415 Parser.Lex(); 4416 isParenExpr = true; 4417 } 4418 4419 if (getLexer().getKind() != AsmToken::Dollar) { 4420 if (parseMemOffset(IdVal, isParenExpr)) 4421 return MatchOperand_ParseFail; 4422 4423 const AsmToken &Tok = Parser.getTok(); // Get the next token. 4424 if (Tok.isNot(AsmToken::LParen)) { 4425 MipsOperand &Mnemonic = static_cast<MipsOperand &>(*Operands[0]); 4426 if (Mnemonic.getToken() == "la" || Mnemonic.getToken() == "dla") { 4427 SMLoc E = 4428 SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 4429 Operands.push_back(MipsOperand::CreateImm(IdVal, S, E, *this)); 4430 return MatchOperand_Success; 4431 } 4432 if (Tok.is(AsmToken::EndOfStatement)) { 4433 SMLoc E = 4434 SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 4435 4436 // Zero register assumed, add a memory operand with ZERO as its base. 4437 // "Base" will be managed by k_Memory. 4438 auto Base = MipsOperand::createGPRReg( 4439 0, "0", getContext().getRegisterInfo(), S, E, *this); 4440 Operands.push_back( 4441 MipsOperand::CreateMem(std::move(Base), IdVal, S, E, *this)); 4442 return MatchOperand_Success; 4443 } 4444 Error(Parser.getTok().getLoc(), "'(' expected"); 4445 return MatchOperand_ParseFail; 4446 } 4447 4448 Parser.Lex(); // Eat the '(' token. 4449 } 4450 4451 Res = parseAnyRegister(Operands); 4452 if (Res != MatchOperand_Success) 4453 return Res; 4454 4455 if (Parser.getTok().isNot(AsmToken::RParen)) { 4456 Error(Parser.getTok().getLoc(), "')' expected"); 4457 return MatchOperand_ParseFail; 4458 } 4459 4460 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 4461 4462 Parser.Lex(); // Eat the ')' token. 4463 4464 if (!IdVal) 4465 IdVal = MCConstantExpr::create(0, getContext()); 4466 4467 // Replace the register operand with the memory operand. 4468 std::unique_ptr<MipsOperand> op( 4469 static_cast<MipsOperand *>(Operands.back().release())); 4470 // Remove the register from the operands. 4471 // "op" will be managed by k_Memory. 4472 Operands.pop_back(); 4473 // Add the memory operand. 4474 if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(IdVal)) { 4475 int64_t Imm; 4476 if (IdVal->evaluateAsAbsolute(Imm)) 4477 IdVal = MCConstantExpr::create(Imm, getContext()); 4478 else if (BE->getLHS()->getKind() != MCExpr::SymbolRef) 4479 IdVal = MCBinaryExpr::create(BE->getOpcode(), BE->getRHS(), BE->getLHS(), 4480 getContext()); 4481 } 4482 4483 Operands.push_back(MipsOperand::CreateMem(std::move(op), IdVal, S, E, *this)); 4484 return MatchOperand_Success; 4485 } 4486 4487 bool MipsAsmParser::searchSymbolAlias(OperandVector &Operands) { 4488 MCAsmParser &Parser = getParser(); 4489 MCSymbol *Sym = getContext().lookupSymbol(Parser.getTok().getIdentifier()); 4490 if (Sym) { 4491 SMLoc S = Parser.getTok().getLoc(); 4492 const MCExpr *Expr; 4493 if (Sym->isVariable()) 4494 Expr = Sym->getVariableValue(); 4495 else 4496 return false; 4497 if (Expr->getKind() == MCExpr::SymbolRef) { 4498 const MCSymbolRefExpr *Ref = static_cast<const MCSymbolRefExpr *>(Expr); 4499 StringRef DefSymbol = Ref->getSymbol().getName(); 4500 if (DefSymbol.startswith("$")) { 4501 OperandMatchResultTy ResTy = 4502 matchAnyRegisterNameWithoutDollar(Operands, DefSymbol.substr(1), S); 4503 if (ResTy == MatchOperand_Success) { 4504 Parser.Lex(); 4505 return true; 4506 } else if (ResTy == MatchOperand_ParseFail) 4507 llvm_unreachable("Should never ParseFail"); 4508 return false; 4509 } 4510 } 4511 } 4512 return false; 4513 } 4514 4515 MipsAsmParser::OperandMatchResultTy 4516 MipsAsmParser::matchAnyRegisterNameWithoutDollar(OperandVector &Operands, 4517 StringRef Identifier, 4518 SMLoc S) { 4519 int Index = matchCPURegisterName(Identifier); 4520 if (Index != -1) { 4521 Operands.push_back(MipsOperand::createGPRReg( 4522 Index, Identifier, getContext().getRegisterInfo(), S, 4523 getLexer().getLoc(), *this)); 4524 return MatchOperand_Success; 4525 } 4526 4527 Index = matchHWRegsRegisterName(Identifier); 4528 if (Index != -1) { 4529 Operands.push_back(MipsOperand::createHWRegsReg( 4530 Index, Identifier, getContext().getRegisterInfo(), S, 4531 getLexer().getLoc(), *this)); 4532 return MatchOperand_Success; 4533 } 4534 4535 Index = matchFPURegisterName(Identifier); 4536 if (Index != -1) { 4537 Operands.push_back(MipsOperand::createFGRReg( 4538 Index, Identifier, getContext().getRegisterInfo(), S, 4539 getLexer().getLoc(), *this)); 4540 return MatchOperand_Success; 4541 } 4542 4543 Index = matchFCCRegisterName(Identifier); 4544 if (Index != -1) { 4545 Operands.push_back(MipsOperand::createFCCReg( 4546 Index, Identifier, getContext().getRegisterInfo(), S, 4547 getLexer().getLoc(), *this)); 4548 return MatchOperand_Success; 4549 } 4550 4551 Index = matchACRegisterName(Identifier); 4552 if (Index != -1) { 4553 Operands.push_back(MipsOperand::createACCReg( 4554 Index, Identifier, getContext().getRegisterInfo(), S, 4555 getLexer().getLoc(), *this)); 4556 return MatchOperand_Success; 4557 } 4558 4559 Index = matchMSA128RegisterName(Identifier); 4560 if (Index != -1) { 4561 Operands.push_back(MipsOperand::createMSA128Reg( 4562 Index, Identifier, getContext().getRegisterInfo(), S, 4563 getLexer().getLoc(), *this)); 4564 return MatchOperand_Success; 4565 } 4566 4567 Index = matchMSA128CtrlRegisterName(Identifier); 4568 if (Index != -1) { 4569 Operands.push_back(MipsOperand::createMSACtrlReg( 4570 Index, Identifier, getContext().getRegisterInfo(), S, 4571 getLexer().getLoc(), *this)); 4572 return MatchOperand_Success; 4573 } 4574 4575 return MatchOperand_NoMatch; 4576 } 4577 4578 MipsAsmParser::OperandMatchResultTy 4579 MipsAsmParser::matchAnyRegisterWithoutDollar(OperandVector &Operands, SMLoc S) { 4580 MCAsmParser &Parser = getParser(); 4581 auto Token = Parser.getLexer().peekTok(false); 4582 4583 if (Token.is(AsmToken::Identifier)) { 4584 DEBUG(dbgs() << ".. identifier\n"); 4585 StringRef Identifier = Token.getIdentifier(); 4586 OperandMatchResultTy ResTy = 4587 matchAnyRegisterNameWithoutDollar(Operands, Identifier, S); 4588 return ResTy; 4589 } else if (Token.is(AsmToken::Integer)) { 4590 DEBUG(dbgs() << ".. integer\n"); 4591 Operands.push_back(MipsOperand::createNumericReg( 4592 Token.getIntVal(), Token.getString(), getContext().getRegisterInfo(), S, 4593 Token.getLoc(), *this)); 4594 return MatchOperand_Success; 4595 } 4596 4597 DEBUG(dbgs() << Parser.getTok().getKind() << "\n"); 4598 4599 return MatchOperand_NoMatch; 4600 } 4601 4602 MipsAsmParser::OperandMatchResultTy 4603 MipsAsmParser::parseAnyRegister(OperandVector &Operands) { 4604 MCAsmParser &Parser = getParser(); 4605 DEBUG(dbgs() << "parseAnyRegister\n"); 4606 4607 auto Token = Parser.getTok(); 4608 4609 SMLoc S = Token.getLoc(); 4610 4611 if (Token.isNot(AsmToken::Dollar)) { 4612 DEBUG(dbgs() << ".. !$ -> try sym aliasing\n"); 4613 if (Token.is(AsmToken::Identifier)) { 4614 if (searchSymbolAlias(Operands)) 4615 return MatchOperand_Success; 4616 } 4617 DEBUG(dbgs() << ".. !symalias -> NoMatch\n"); 4618 return MatchOperand_NoMatch; 4619 } 4620 DEBUG(dbgs() << ".. $\n"); 4621 4622 OperandMatchResultTy ResTy = matchAnyRegisterWithoutDollar(Operands, S); 4623 if (ResTy == MatchOperand_Success) { 4624 Parser.Lex(); // $ 4625 Parser.Lex(); // identifier 4626 } 4627 return ResTy; 4628 } 4629 4630 MipsAsmParser::OperandMatchResultTy 4631 MipsAsmParser::parseJumpTarget(OperandVector &Operands) { 4632 MCAsmParser &Parser = getParser(); 4633 DEBUG(dbgs() << "parseJumpTarget\n"); 4634 4635 SMLoc S = getLexer().getLoc(); 4636 4637 // Registers are a valid target and have priority over symbols. 4638 OperandMatchResultTy ResTy = parseAnyRegister(Operands); 4639 if (ResTy != MatchOperand_NoMatch) 4640 return ResTy; 4641 4642 // Integers and expressions are acceptable 4643 const MCExpr *Expr = nullptr; 4644 if (Parser.parseExpression(Expr)) { 4645 // We have no way of knowing if a symbol was consumed so we must ParseFail 4646 return MatchOperand_ParseFail; 4647 } 4648 Operands.push_back( 4649 MipsOperand::CreateImm(Expr, S, getLexer().getLoc(), *this)); 4650 return MatchOperand_Success; 4651 } 4652 4653 MipsAsmParser::OperandMatchResultTy 4654 MipsAsmParser::parseInvNum(OperandVector &Operands) { 4655 MCAsmParser &Parser = getParser(); 4656 const MCExpr *IdVal; 4657 // If the first token is '$' we may have register operand. 4658 if (Parser.getTok().is(AsmToken::Dollar)) 4659 return MatchOperand_NoMatch; 4660 SMLoc S = Parser.getTok().getLoc(); 4661 if (getParser().parseExpression(IdVal)) 4662 return MatchOperand_ParseFail; 4663 const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(IdVal); 4664 assert(MCE && "Unexpected MCExpr type."); 4665 int64_t Val = MCE->getValue(); 4666 SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1); 4667 Operands.push_back(MipsOperand::CreateImm( 4668 MCConstantExpr::create(0 - Val, getContext()), S, E, *this)); 4669 return MatchOperand_Success; 4670 } 4671 4672 MipsAsmParser::OperandMatchResultTy 4673 MipsAsmParser::parseRegisterList(OperandVector &Operands) { 4674 MCAsmParser &Parser = getParser(); 4675 SmallVector<unsigned, 10> Regs; 4676 unsigned RegNo; 4677 unsigned PrevReg = Mips::NoRegister; 4678 bool RegRange = false; 4679 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 8> TmpOperands; 4680 4681 if (Parser.getTok().isNot(AsmToken::Dollar)) 4682 return MatchOperand_ParseFail; 4683 4684 SMLoc S = Parser.getTok().getLoc(); 4685 while (parseAnyRegister(TmpOperands) == MatchOperand_Success) { 4686 SMLoc E = getLexer().getLoc(); 4687 MipsOperand &Reg = static_cast<MipsOperand &>(*TmpOperands.back()); 4688 RegNo = isGP64bit() ? Reg.getGPR64Reg() : Reg.getGPR32Reg(); 4689 if (RegRange) { 4690 // Remove last register operand because registers from register range 4691 // should be inserted first. 4692 if ((isGP64bit() && RegNo == Mips::RA_64) || 4693 (!isGP64bit() && RegNo == Mips::RA)) { 4694 Regs.push_back(RegNo); 4695 } else { 4696 unsigned TmpReg = PrevReg + 1; 4697 while (TmpReg <= RegNo) { 4698 if ((((TmpReg < Mips::S0) || (TmpReg > Mips::S7)) && !isGP64bit()) || 4699 (((TmpReg < Mips::S0_64) || (TmpReg > Mips::S7_64)) && 4700 isGP64bit())) { 4701 Error(E, "invalid register operand"); 4702 return MatchOperand_ParseFail; 4703 } 4704 4705 PrevReg = TmpReg; 4706 Regs.push_back(TmpReg++); 4707 } 4708 } 4709 4710 RegRange = false; 4711 } else { 4712 if ((PrevReg == Mips::NoRegister) && 4713 ((isGP64bit() && (RegNo != Mips::S0_64) && (RegNo != Mips::RA_64)) || 4714 (!isGP64bit() && (RegNo != Mips::S0) && (RegNo != Mips::RA)))) { 4715 Error(E, "$16 or $31 expected"); 4716 return MatchOperand_ParseFail; 4717 } else if (!(((RegNo == Mips::FP || RegNo == Mips::RA || 4718 (RegNo >= Mips::S0 && RegNo <= Mips::S7)) && 4719 !isGP64bit()) || 4720 ((RegNo == Mips::FP_64 || RegNo == Mips::RA_64 || 4721 (RegNo >= Mips::S0_64 && RegNo <= Mips::S7_64)) && 4722 isGP64bit()))) { 4723 Error(E, "invalid register operand"); 4724 return MatchOperand_ParseFail; 4725 } else if ((PrevReg != Mips::NoRegister) && (RegNo != PrevReg + 1) && 4726 ((RegNo != Mips::FP && RegNo != Mips::RA && !isGP64bit()) || 4727 (RegNo != Mips::FP_64 && RegNo != Mips::RA_64 && 4728 isGP64bit()))) { 4729 Error(E, "consecutive register numbers expected"); 4730 return MatchOperand_ParseFail; 4731 } 4732 4733 Regs.push_back(RegNo); 4734 } 4735 4736 if (Parser.getTok().is(AsmToken::Minus)) 4737 RegRange = true; 4738 4739 if (!Parser.getTok().isNot(AsmToken::Minus) && 4740 !Parser.getTok().isNot(AsmToken::Comma)) { 4741 Error(E, "',' or '-' expected"); 4742 return MatchOperand_ParseFail; 4743 } 4744 4745 Lex(); // Consume comma or minus 4746 if (Parser.getTok().isNot(AsmToken::Dollar)) 4747 break; 4748 4749 PrevReg = RegNo; 4750 } 4751 4752 SMLoc E = Parser.getTok().getLoc(); 4753 Operands.push_back(MipsOperand::CreateRegList(Regs, S, E, *this)); 4754 parseMemOperand(Operands); 4755 return MatchOperand_Success; 4756 } 4757 4758 MipsAsmParser::OperandMatchResultTy 4759 MipsAsmParser::parseRegisterPair(OperandVector &Operands) { 4760 MCAsmParser &Parser = getParser(); 4761 4762 SMLoc S = Parser.getTok().getLoc(); 4763 if (parseAnyRegister(Operands) != MatchOperand_Success) 4764 return MatchOperand_ParseFail; 4765 4766 SMLoc E = Parser.getTok().getLoc(); 4767 MipsOperand Op = static_cast<MipsOperand &>(*Operands.back()); 4768 4769 Operands.pop_back(); 4770 Operands.push_back(MipsOperand::CreateRegPair(Op, S, E, *this)); 4771 return MatchOperand_Success; 4772 } 4773 4774 MipsAsmParser::OperandMatchResultTy 4775 MipsAsmParser::parseMovePRegPair(OperandVector &Operands) { 4776 MCAsmParser &Parser = getParser(); 4777 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 8> TmpOperands; 4778 SmallVector<unsigned, 10> Regs; 4779 4780 if (Parser.getTok().isNot(AsmToken::Dollar)) 4781 return MatchOperand_ParseFail; 4782 4783 SMLoc S = Parser.getTok().getLoc(); 4784 4785 if (parseAnyRegister(TmpOperands) != MatchOperand_Success) 4786 return MatchOperand_ParseFail; 4787 4788 MipsOperand *Reg = &static_cast<MipsOperand &>(*TmpOperands.back()); 4789 unsigned RegNo = isGP64bit() ? Reg->getGPR64Reg() : Reg->getGPR32Reg(); 4790 Regs.push_back(RegNo); 4791 4792 SMLoc E = Parser.getTok().getLoc(); 4793 if (Parser.getTok().isNot(AsmToken::Comma)) { 4794 Error(E, "',' expected"); 4795 return MatchOperand_ParseFail; 4796 } 4797 4798 // Remove comma. 4799 Parser.Lex(); 4800 4801 if (parseAnyRegister(TmpOperands) != MatchOperand_Success) 4802 return MatchOperand_ParseFail; 4803 4804 Reg = &static_cast<MipsOperand &>(*TmpOperands.back()); 4805 RegNo = isGP64bit() ? Reg->getGPR64Reg() : Reg->getGPR32Reg(); 4806 Regs.push_back(RegNo); 4807 4808 Operands.push_back(MipsOperand::CreateRegList(Regs, S, E, *this)); 4809 4810 return MatchOperand_Success; 4811 } 4812 4813 /// Sometimes (i.e. load/stores) the operand may be followed immediately by 4814 /// either this. 4815 /// ::= '(', register, ')' 4816 /// handle it before we iterate so we don't get tripped up by the lack of 4817 /// a comma. 4818 bool MipsAsmParser::parseParenSuffix(StringRef Name, OperandVector &Operands) { 4819 MCAsmParser &Parser = getParser(); 4820 if (getLexer().is(AsmToken::LParen)) { 4821 Operands.push_back( 4822 MipsOperand::CreateToken("(", getLexer().getLoc(), *this)); 4823 Parser.Lex(); 4824 if (parseOperand(Operands, Name)) { 4825 SMLoc Loc = getLexer().getLoc(); 4826 return Error(Loc, "unexpected token in argument list"); 4827 } 4828 if (Parser.getTok().isNot(AsmToken::RParen)) { 4829 SMLoc Loc = getLexer().getLoc(); 4830 return Error(Loc, "unexpected token, expected ')'"); 4831 } 4832 Operands.push_back( 4833 MipsOperand::CreateToken(")", getLexer().getLoc(), *this)); 4834 Parser.Lex(); 4835 } 4836 return false; 4837 } 4838 4839 /// Sometimes (i.e. in MSA) the operand may be followed immediately by 4840 /// either one of these. 4841 /// ::= '[', register, ']' 4842 /// ::= '[', integer, ']' 4843 /// handle it before we iterate so we don't get tripped up by the lack of 4844 /// a comma. 4845 bool MipsAsmParser::parseBracketSuffix(StringRef Name, 4846 OperandVector &Operands) { 4847 MCAsmParser &Parser = getParser(); 4848 if (getLexer().is(AsmToken::LBrac)) { 4849 Operands.push_back( 4850 MipsOperand::CreateToken("[", getLexer().getLoc(), *this)); 4851 Parser.Lex(); 4852 if (parseOperand(Operands, Name)) { 4853 SMLoc Loc = getLexer().getLoc(); 4854 return Error(Loc, "unexpected token in argument list"); 4855 } 4856 if (Parser.getTok().isNot(AsmToken::RBrac)) { 4857 SMLoc Loc = getLexer().getLoc(); 4858 return Error(Loc, "unexpected token, expected ']'"); 4859 } 4860 Operands.push_back( 4861 MipsOperand::CreateToken("]", getLexer().getLoc(), *this)); 4862 Parser.Lex(); 4863 } 4864 return false; 4865 } 4866 4867 bool MipsAsmParser::ParseInstruction(ParseInstructionInfo &Info, StringRef Name, 4868 SMLoc NameLoc, OperandVector &Operands) { 4869 MCAsmParser &Parser = getParser(); 4870 DEBUG(dbgs() << "ParseInstruction\n"); 4871 4872 // We have reached first instruction, module directive are now forbidden. 4873 getTargetStreamer().forbidModuleDirective(); 4874 4875 // Check if we have valid mnemonic 4876 if (!mnemonicIsValid(Name, 0)) { 4877 return Error(NameLoc, "unknown instruction"); 4878 } 4879 // First operand in MCInst is instruction mnemonic. 4880 Operands.push_back(MipsOperand::CreateToken(Name, NameLoc, *this)); 4881 4882 // Read the remaining operands. 4883 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4884 // Read the first operand. 4885 if (parseOperand(Operands, Name)) { 4886 SMLoc Loc = getLexer().getLoc(); 4887 return Error(Loc, "unexpected token in argument list"); 4888 } 4889 if (getLexer().is(AsmToken::LBrac) && parseBracketSuffix(Name, Operands)) 4890 return true; 4891 // AFAIK, parenthesis suffixes are never on the first operand 4892 4893 while (getLexer().is(AsmToken::Comma)) { 4894 Parser.Lex(); // Eat the comma. 4895 // Parse and remember the operand. 4896 if (parseOperand(Operands, Name)) { 4897 SMLoc Loc = getLexer().getLoc(); 4898 return Error(Loc, "unexpected token in argument list"); 4899 } 4900 // Parse bracket and parenthesis suffixes before we iterate 4901 if (getLexer().is(AsmToken::LBrac)) { 4902 if (parseBracketSuffix(Name, Operands)) 4903 return true; 4904 } else if (getLexer().is(AsmToken::LParen) && 4905 parseParenSuffix(Name, Operands)) 4906 return true; 4907 } 4908 } 4909 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4910 SMLoc Loc = getLexer().getLoc(); 4911 return Error(Loc, "unexpected token in argument list"); 4912 } 4913 Parser.Lex(); // Consume the EndOfStatement. 4914 return false; 4915 } 4916 4917 // FIXME: Given that these have the same name, these should both be 4918 // consistent on affecting the Parser. 4919 bool MipsAsmParser::reportParseError(Twine ErrorMsg) { 4920 SMLoc Loc = getLexer().getLoc(); 4921 return Error(Loc, ErrorMsg); 4922 } 4923 4924 bool MipsAsmParser::reportParseError(SMLoc Loc, Twine ErrorMsg) { 4925 return Error(Loc, ErrorMsg); 4926 } 4927 4928 bool MipsAsmParser::parseSetNoAtDirective() { 4929 MCAsmParser &Parser = getParser(); 4930 // Line should look like: ".set noat". 4931 4932 // Set the $at register to $0. 4933 AssemblerOptions.back()->setATRegIndex(0); 4934 4935 Parser.Lex(); // Eat "noat". 4936 4937 // If this is not the end of the statement, report an error. 4938 if (getLexer().isNot(AsmToken::EndOfStatement)) { 4939 reportParseError("unexpected token, expected end of statement"); 4940 return false; 4941 } 4942 4943 getTargetStreamer().emitDirectiveSetNoAt(); 4944 Parser.Lex(); // Consume the EndOfStatement. 4945 return false; 4946 } 4947 4948 bool MipsAsmParser::parseSetAtDirective() { 4949 // Line can be: ".set at", which sets $at to $1 4950 // or ".set at=$reg", which sets $at to $reg. 4951 MCAsmParser &Parser = getParser(); 4952 Parser.Lex(); // Eat "at". 4953 4954 if (getLexer().is(AsmToken::EndOfStatement)) { 4955 // No register was specified, so we set $at to $1. 4956 AssemblerOptions.back()->setATRegIndex(1); 4957 4958 getTargetStreamer().emitDirectiveSetAt(); 4959 Parser.Lex(); // Consume the EndOfStatement. 4960 return false; 4961 } 4962 4963 if (getLexer().isNot(AsmToken::Equal)) { 4964 reportParseError("unexpected token, expected equals sign"); 4965 return false; 4966 } 4967 Parser.Lex(); // Eat "=". 4968 4969 if (getLexer().isNot(AsmToken::Dollar)) { 4970 if (getLexer().is(AsmToken::EndOfStatement)) { 4971 reportParseError("no register specified"); 4972 return false; 4973 } else { 4974 reportParseError("unexpected token, expected dollar sign '$'"); 4975 return false; 4976 } 4977 } 4978 Parser.Lex(); // Eat "$". 4979 4980 // Find out what "reg" is. 4981 unsigned AtRegNo; 4982 const AsmToken &Reg = Parser.getTok(); 4983 if (Reg.is(AsmToken::Identifier)) { 4984 AtRegNo = matchCPURegisterName(Reg.getIdentifier()); 4985 } else if (Reg.is(AsmToken::Integer)) { 4986 AtRegNo = Reg.getIntVal(); 4987 } else { 4988 reportParseError("unexpected token, expected identifier or integer"); 4989 return false; 4990 } 4991 4992 // Check if $reg is a valid register. If it is, set $at to $reg. 4993 if (!AssemblerOptions.back()->setATRegIndex(AtRegNo)) { 4994 reportParseError("invalid register"); 4995 return false; 4996 } 4997 Parser.Lex(); // Eat "reg". 4998 4999 // If this is not the end of the statement, report an error. 5000 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5001 reportParseError("unexpected token, expected end of statement"); 5002 return false; 5003 } 5004 5005 getTargetStreamer().emitDirectiveSetAtWithArg(AtRegNo); 5006 5007 Parser.Lex(); // Consume the EndOfStatement. 5008 return false; 5009 } 5010 5011 bool MipsAsmParser::parseSetReorderDirective() { 5012 MCAsmParser &Parser = getParser(); 5013 Parser.Lex(); 5014 // If this is not the end of the statement, report an error. 5015 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5016 reportParseError("unexpected token, expected end of statement"); 5017 return false; 5018 } 5019 AssemblerOptions.back()->setReorder(); 5020 getTargetStreamer().emitDirectiveSetReorder(); 5021 Parser.Lex(); // Consume the EndOfStatement. 5022 return false; 5023 } 5024 5025 bool MipsAsmParser::parseSetNoReorderDirective() { 5026 MCAsmParser &Parser = getParser(); 5027 Parser.Lex(); 5028 // If this is not the end of the statement, report an error. 5029 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5030 reportParseError("unexpected token, expected end of statement"); 5031 return false; 5032 } 5033 AssemblerOptions.back()->setNoReorder(); 5034 getTargetStreamer().emitDirectiveSetNoReorder(); 5035 Parser.Lex(); // Consume the EndOfStatement. 5036 return false; 5037 } 5038 5039 bool MipsAsmParser::parseSetMacroDirective() { 5040 MCAsmParser &Parser = getParser(); 5041 Parser.Lex(); 5042 // If this is not the end of the statement, report an error. 5043 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5044 reportParseError("unexpected token, expected end of statement"); 5045 return false; 5046 } 5047 AssemblerOptions.back()->setMacro(); 5048 getTargetStreamer().emitDirectiveSetMacro(); 5049 Parser.Lex(); // Consume the EndOfStatement. 5050 return false; 5051 } 5052 5053 bool MipsAsmParser::parseSetNoMacroDirective() { 5054 MCAsmParser &Parser = getParser(); 5055 Parser.Lex(); 5056 // If this is not the end of the statement, report an error. 5057 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5058 reportParseError("unexpected token, expected end of statement"); 5059 return false; 5060 } 5061 if (AssemblerOptions.back()->isReorder()) { 5062 reportParseError("`noreorder' must be set before `nomacro'"); 5063 return false; 5064 } 5065 AssemblerOptions.back()->setNoMacro(); 5066 getTargetStreamer().emitDirectiveSetNoMacro(); 5067 Parser.Lex(); // Consume the EndOfStatement. 5068 return false; 5069 } 5070 5071 bool MipsAsmParser::parseSetMsaDirective() { 5072 MCAsmParser &Parser = getParser(); 5073 Parser.Lex(); 5074 5075 // If this is not the end of the statement, report an error. 5076 if (getLexer().isNot(AsmToken::EndOfStatement)) 5077 return reportParseError("unexpected token, expected end of statement"); 5078 5079 setFeatureBits(Mips::FeatureMSA, "msa"); 5080 getTargetStreamer().emitDirectiveSetMsa(); 5081 return false; 5082 } 5083 5084 bool MipsAsmParser::parseSetNoMsaDirective() { 5085 MCAsmParser &Parser = getParser(); 5086 Parser.Lex(); 5087 5088 // If this is not the end of the statement, report an error. 5089 if (getLexer().isNot(AsmToken::EndOfStatement)) 5090 return reportParseError("unexpected token, expected end of statement"); 5091 5092 clearFeatureBits(Mips::FeatureMSA, "msa"); 5093 getTargetStreamer().emitDirectiveSetNoMsa(); 5094 return false; 5095 } 5096 5097 bool MipsAsmParser::parseSetNoDspDirective() { 5098 MCAsmParser &Parser = getParser(); 5099 Parser.Lex(); // Eat "nodsp". 5100 5101 // If this is not the end of the statement, report an error. 5102 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5103 reportParseError("unexpected token, expected end of statement"); 5104 return false; 5105 } 5106 5107 clearFeatureBits(Mips::FeatureDSP, "dsp"); 5108 getTargetStreamer().emitDirectiveSetNoDsp(); 5109 return false; 5110 } 5111 5112 bool MipsAsmParser::parseSetMips16Directive() { 5113 MCAsmParser &Parser = getParser(); 5114 Parser.Lex(); // Eat "mips16". 5115 5116 // If this is not the end of the statement, report an error. 5117 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5118 reportParseError("unexpected token, expected end of statement"); 5119 return false; 5120 } 5121 5122 setFeatureBits(Mips::FeatureMips16, "mips16"); 5123 getTargetStreamer().emitDirectiveSetMips16(); 5124 Parser.Lex(); // Consume the EndOfStatement. 5125 return false; 5126 } 5127 5128 bool MipsAsmParser::parseSetNoMips16Directive() { 5129 MCAsmParser &Parser = getParser(); 5130 Parser.Lex(); // Eat "nomips16". 5131 5132 // If this is not the end of the statement, report an error. 5133 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5134 reportParseError("unexpected token, expected end of statement"); 5135 return false; 5136 } 5137 5138 clearFeatureBits(Mips::FeatureMips16, "mips16"); 5139 getTargetStreamer().emitDirectiveSetNoMips16(); 5140 Parser.Lex(); // Consume the EndOfStatement. 5141 return false; 5142 } 5143 5144 bool MipsAsmParser::parseSetFpDirective() { 5145 MCAsmParser &Parser = getParser(); 5146 MipsABIFlagsSection::FpABIKind FpAbiVal; 5147 // Line can be: .set fp=32 5148 // .set fp=xx 5149 // .set fp=64 5150 Parser.Lex(); // Eat fp token 5151 AsmToken Tok = Parser.getTok(); 5152 if (Tok.isNot(AsmToken::Equal)) { 5153 reportParseError("unexpected token, expected equals sign '='"); 5154 return false; 5155 } 5156 Parser.Lex(); // Eat '=' token. 5157 Tok = Parser.getTok(); 5158 5159 if (!parseFpABIValue(FpAbiVal, ".set")) 5160 return false; 5161 5162 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5163 reportParseError("unexpected token, expected end of statement"); 5164 return false; 5165 } 5166 getTargetStreamer().emitDirectiveSetFp(FpAbiVal); 5167 Parser.Lex(); // Consume the EndOfStatement. 5168 return false; 5169 } 5170 5171 bool MipsAsmParser::parseSetOddSPRegDirective() { 5172 MCAsmParser &Parser = getParser(); 5173 5174 Parser.Lex(); // Eat "oddspreg". 5175 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5176 reportParseError("unexpected token, expected end of statement"); 5177 return false; 5178 } 5179 5180 clearFeatureBits(Mips::FeatureNoOddSPReg, "nooddspreg"); 5181 getTargetStreamer().emitDirectiveSetOddSPReg(); 5182 return false; 5183 } 5184 5185 bool MipsAsmParser::parseSetNoOddSPRegDirective() { 5186 MCAsmParser &Parser = getParser(); 5187 5188 Parser.Lex(); // Eat "nooddspreg". 5189 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5190 reportParseError("unexpected token, expected end of statement"); 5191 return false; 5192 } 5193 5194 setFeatureBits(Mips::FeatureNoOddSPReg, "nooddspreg"); 5195 getTargetStreamer().emitDirectiveSetNoOddSPReg(); 5196 return false; 5197 } 5198 5199 bool MipsAsmParser::parseSetPopDirective() { 5200 MCAsmParser &Parser = getParser(); 5201 SMLoc Loc = getLexer().getLoc(); 5202 5203 Parser.Lex(); 5204 if (getLexer().isNot(AsmToken::EndOfStatement)) 5205 return reportParseError("unexpected token, expected end of statement"); 5206 5207 // Always keep an element on the options "stack" to prevent the user 5208 // from changing the initial options. This is how we remember them. 5209 if (AssemblerOptions.size() == 2) 5210 return reportParseError(Loc, ".set pop with no .set push"); 5211 5212 MCSubtargetInfo &STI = copySTI(); 5213 AssemblerOptions.pop_back(); 5214 setAvailableFeatures( 5215 ComputeAvailableFeatures(AssemblerOptions.back()->getFeatures())); 5216 STI.setFeatureBits(AssemblerOptions.back()->getFeatures()); 5217 5218 getTargetStreamer().emitDirectiveSetPop(); 5219 return false; 5220 } 5221 5222 bool MipsAsmParser::parseSetPushDirective() { 5223 MCAsmParser &Parser = getParser(); 5224 Parser.Lex(); 5225 if (getLexer().isNot(AsmToken::EndOfStatement)) 5226 return reportParseError("unexpected token, expected end of statement"); 5227 5228 // Create a copy of the current assembler options environment and push it. 5229 AssemblerOptions.push_back( 5230 make_unique<MipsAssemblerOptions>(AssemblerOptions.back().get())); 5231 5232 getTargetStreamer().emitDirectiveSetPush(); 5233 return false; 5234 } 5235 5236 bool MipsAsmParser::parseSetSoftFloatDirective() { 5237 MCAsmParser &Parser = getParser(); 5238 Parser.Lex(); 5239 if (getLexer().isNot(AsmToken::EndOfStatement)) 5240 return reportParseError("unexpected token, expected end of statement"); 5241 5242 setFeatureBits(Mips::FeatureSoftFloat, "soft-float"); 5243 getTargetStreamer().emitDirectiveSetSoftFloat(); 5244 return false; 5245 } 5246 5247 bool MipsAsmParser::parseSetHardFloatDirective() { 5248 MCAsmParser &Parser = getParser(); 5249 Parser.Lex(); 5250 if (getLexer().isNot(AsmToken::EndOfStatement)) 5251 return reportParseError("unexpected token, expected end of statement"); 5252 5253 clearFeatureBits(Mips::FeatureSoftFloat, "soft-float"); 5254 getTargetStreamer().emitDirectiveSetHardFloat(); 5255 return false; 5256 } 5257 5258 bool MipsAsmParser::parseSetAssignment() { 5259 StringRef Name; 5260 const MCExpr *Value; 5261 MCAsmParser &Parser = getParser(); 5262 5263 if (Parser.parseIdentifier(Name)) 5264 reportParseError("expected identifier after .set"); 5265 5266 if (getLexer().isNot(AsmToken::Comma)) 5267 return reportParseError("unexpected token, expected comma"); 5268 Lex(); // Eat comma 5269 5270 if (Parser.parseExpression(Value)) 5271 return reportParseError("expected valid expression after comma"); 5272 5273 MCSymbol *Sym = getContext().getOrCreateSymbol(Name); 5274 Sym->setVariableValue(Value); 5275 5276 return false; 5277 } 5278 5279 bool MipsAsmParser::parseSetMips0Directive() { 5280 MCAsmParser &Parser = getParser(); 5281 Parser.Lex(); 5282 if (getLexer().isNot(AsmToken::EndOfStatement)) 5283 return reportParseError("unexpected token, expected end of statement"); 5284 5285 // Reset assembler options to their initial values. 5286 MCSubtargetInfo &STI = copySTI(); 5287 setAvailableFeatures( 5288 ComputeAvailableFeatures(AssemblerOptions.front()->getFeatures())); 5289 STI.setFeatureBits(AssemblerOptions.front()->getFeatures()); 5290 AssemblerOptions.back()->setFeatures(AssemblerOptions.front()->getFeatures()); 5291 5292 getTargetStreamer().emitDirectiveSetMips0(); 5293 return false; 5294 } 5295 5296 bool MipsAsmParser::parseSetArchDirective() { 5297 MCAsmParser &Parser = getParser(); 5298 Parser.Lex(); 5299 if (getLexer().isNot(AsmToken::Equal)) 5300 return reportParseError("unexpected token, expected equals sign"); 5301 5302 Parser.Lex(); 5303 StringRef Arch; 5304 if (Parser.parseIdentifier(Arch)) 5305 return reportParseError("expected arch identifier"); 5306 5307 StringRef ArchFeatureName = 5308 StringSwitch<StringRef>(Arch) 5309 .Case("mips1", "mips1") 5310 .Case("mips2", "mips2") 5311 .Case("mips3", "mips3") 5312 .Case("mips4", "mips4") 5313 .Case("mips5", "mips5") 5314 .Case("mips32", "mips32") 5315 .Case("mips32r2", "mips32r2") 5316 .Case("mips32r3", "mips32r3") 5317 .Case("mips32r5", "mips32r5") 5318 .Case("mips32r6", "mips32r6") 5319 .Case("mips64", "mips64") 5320 .Case("mips64r2", "mips64r2") 5321 .Case("mips64r3", "mips64r3") 5322 .Case("mips64r5", "mips64r5") 5323 .Case("mips64r6", "mips64r6") 5324 .Case("octeon", "cnmips") 5325 .Case("r4000", "mips3") // This is an implementation of Mips3. 5326 .Default(""); 5327 5328 if (ArchFeatureName.empty()) 5329 return reportParseError("unsupported architecture"); 5330 5331 selectArch(ArchFeatureName); 5332 getTargetStreamer().emitDirectiveSetArch(Arch); 5333 return false; 5334 } 5335 5336 bool MipsAsmParser::parseSetFeature(uint64_t Feature) { 5337 MCAsmParser &Parser = getParser(); 5338 Parser.Lex(); 5339 if (getLexer().isNot(AsmToken::EndOfStatement)) 5340 return reportParseError("unexpected token, expected end of statement"); 5341 5342 switch (Feature) { 5343 default: 5344 llvm_unreachable("Unimplemented feature"); 5345 case Mips::FeatureDSP: 5346 setFeatureBits(Mips::FeatureDSP, "dsp"); 5347 getTargetStreamer().emitDirectiveSetDsp(); 5348 break; 5349 case Mips::FeatureMicroMips: 5350 setFeatureBits(Mips::FeatureMicroMips, "micromips"); 5351 getTargetStreamer().emitDirectiveSetMicroMips(); 5352 break; 5353 case Mips::FeatureMips1: 5354 selectArch("mips1"); 5355 getTargetStreamer().emitDirectiveSetMips1(); 5356 break; 5357 case Mips::FeatureMips2: 5358 selectArch("mips2"); 5359 getTargetStreamer().emitDirectiveSetMips2(); 5360 break; 5361 case Mips::FeatureMips3: 5362 selectArch("mips3"); 5363 getTargetStreamer().emitDirectiveSetMips3(); 5364 break; 5365 case Mips::FeatureMips4: 5366 selectArch("mips4"); 5367 getTargetStreamer().emitDirectiveSetMips4(); 5368 break; 5369 case Mips::FeatureMips5: 5370 selectArch("mips5"); 5371 getTargetStreamer().emitDirectiveSetMips5(); 5372 break; 5373 case Mips::FeatureMips32: 5374 selectArch("mips32"); 5375 getTargetStreamer().emitDirectiveSetMips32(); 5376 break; 5377 case Mips::FeatureMips32r2: 5378 selectArch("mips32r2"); 5379 getTargetStreamer().emitDirectiveSetMips32R2(); 5380 break; 5381 case Mips::FeatureMips32r3: 5382 selectArch("mips32r3"); 5383 getTargetStreamer().emitDirectiveSetMips32R3(); 5384 break; 5385 case Mips::FeatureMips32r5: 5386 selectArch("mips32r5"); 5387 getTargetStreamer().emitDirectiveSetMips32R5(); 5388 break; 5389 case Mips::FeatureMips32r6: 5390 selectArch("mips32r6"); 5391 getTargetStreamer().emitDirectiveSetMips32R6(); 5392 break; 5393 case Mips::FeatureMips64: 5394 selectArch("mips64"); 5395 getTargetStreamer().emitDirectiveSetMips64(); 5396 break; 5397 case Mips::FeatureMips64r2: 5398 selectArch("mips64r2"); 5399 getTargetStreamer().emitDirectiveSetMips64R2(); 5400 break; 5401 case Mips::FeatureMips64r3: 5402 selectArch("mips64r3"); 5403 getTargetStreamer().emitDirectiveSetMips64R3(); 5404 break; 5405 case Mips::FeatureMips64r5: 5406 selectArch("mips64r5"); 5407 getTargetStreamer().emitDirectiveSetMips64R5(); 5408 break; 5409 case Mips::FeatureMips64r6: 5410 selectArch("mips64r6"); 5411 getTargetStreamer().emitDirectiveSetMips64R6(); 5412 break; 5413 } 5414 return false; 5415 } 5416 5417 bool MipsAsmParser::eatComma(StringRef ErrorStr) { 5418 MCAsmParser &Parser = getParser(); 5419 if (getLexer().isNot(AsmToken::Comma)) { 5420 SMLoc Loc = getLexer().getLoc(); 5421 return Error(Loc, ErrorStr); 5422 } 5423 5424 Parser.Lex(); // Eat the comma. 5425 return true; 5426 } 5427 5428 // Used to determine if .cpload, .cprestore, and .cpsetup have any effect. 5429 // In this class, it is only used for .cprestore. 5430 // FIXME: Only keep track of IsPicEnabled in one place, instead of in both 5431 // MipsTargetELFStreamer and MipsAsmParser. 5432 bool MipsAsmParser::isPicAndNotNxxAbi() { 5433 return inPicMode() && !(isABI_N32() || isABI_N64()); 5434 } 5435 5436 bool MipsAsmParser::parseDirectiveCpLoad(SMLoc Loc) { 5437 if (AssemblerOptions.back()->isReorder()) 5438 Warning(Loc, ".cpload should be inside a noreorder section"); 5439 5440 if (inMips16Mode()) { 5441 reportParseError(".cpload is not supported in Mips16 mode"); 5442 return false; 5443 } 5444 5445 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> Reg; 5446 OperandMatchResultTy ResTy = parseAnyRegister(Reg); 5447 if (ResTy == MatchOperand_NoMatch || ResTy == MatchOperand_ParseFail) { 5448 reportParseError("expected register containing function address"); 5449 return false; 5450 } 5451 5452 MipsOperand &RegOpnd = static_cast<MipsOperand &>(*Reg[0]); 5453 if (!RegOpnd.isGPRAsmReg()) { 5454 reportParseError(RegOpnd.getStartLoc(), "invalid register"); 5455 return false; 5456 } 5457 5458 // If this is not the end of the statement, report an error. 5459 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5460 reportParseError("unexpected token, expected end of statement"); 5461 return false; 5462 } 5463 5464 getTargetStreamer().emitDirectiveCpLoad(RegOpnd.getGPR32Reg()); 5465 return false; 5466 } 5467 5468 bool MipsAsmParser::parseDirectiveCpRestore(SMLoc Loc) { 5469 MCAsmParser &Parser = getParser(); 5470 5471 // Note that .cprestore is ignored if used with the N32 and N64 ABIs or if it 5472 // is used in non-PIC mode. 5473 5474 if (inMips16Mode()) { 5475 reportParseError(".cprestore is not supported in Mips16 mode"); 5476 return false; 5477 } 5478 5479 // Get the stack offset value. 5480 const MCExpr *StackOffset; 5481 int64_t StackOffsetVal; 5482 if (Parser.parseExpression(StackOffset)) { 5483 reportParseError("expected stack offset value"); 5484 return false; 5485 } 5486 5487 if (!StackOffset->evaluateAsAbsolute(StackOffsetVal)) { 5488 reportParseError("stack offset is not an absolute expression"); 5489 return false; 5490 } 5491 5492 if (StackOffsetVal < 0) { 5493 Warning(Loc, ".cprestore with negative stack offset has no effect"); 5494 IsCpRestoreSet = false; 5495 } else { 5496 IsCpRestoreSet = true; 5497 CpRestoreOffset = StackOffsetVal; 5498 } 5499 5500 // If this is not the end of the statement, report an error. 5501 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5502 reportParseError("unexpected token, expected end of statement"); 5503 return false; 5504 } 5505 5506 if (!getTargetStreamer().emitDirectiveCpRestore( 5507 CpRestoreOffset, [&]() { return getATReg(Loc); }, Loc, STI)) 5508 return true; 5509 Parser.Lex(); // Consume the EndOfStatement. 5510 return false; 5511 } 5512 5513 bool MipsAsmParser::parseDirectiveCPSetup() { 5514 MCAsmParser &Parser = getParser(); 5515 unsigned FuncReg; 5516 unsigned Save; 5517 bool SaveIsReg = true; 5518 5519 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> TmpReg; 5520 OperandMatchResultTy ResTy = parseAnyRegister(TmpReg); 5521 if (ResTy == MatchOperand_NoMatch) { 5522 reportParseError("expected register containing function address"); 5523 return false; 5524 } 5525 5526 MipsOperand &FuncRegOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 5527 if (!FuncRegOpnd.isGPRAsmReg()) { 5528 reportParseError(FuncRegOpnd.getStartLoc(), "invalid register"); 5529 return false; 5530 } 5531 5532 FuncReg = FuncRegOpnd.getGPR32Reg(); 5533 TmpReg.clear(); 5534 5535 if (!eatComma("unexpected token, expected comma")) 5536 return true; 5537 5538 ResTy = parseAnyRegister(TmpReg); 5539 if (ResTy == MatchOperand_NoMatch) { 5540 const MCExpr *OffsetExpr; 5541 int64_t OffsetVal; 5542 SMLoc ExprLoc = getLexer().getLoc(); 5543 5544 if (Parser.parseExpression(OffsetExpr) || 5545 !OffsetExpr->evaluateAsAbsolute(OffsetVal)) { 5546 reportParseError(ExprLoc, "expected save register or stack offset"); 5547 return false; 5548 } 5549 5550 Save = OffsetVal; 5551 SaveIsReg = false; 5552 } else { 5553 MipsOperand &SaveOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 5554 if (!SaveOpnd.isGPRAsmReg()) { 5555 reportParseError(SaveOpnd.getStartLoc(), "invalid register"); 5556 return false; 5557 } 5558 Save = SaveOpnd.getGPR32Reg(); 5559 } 5560 5561 if (!eatComma("unexpected token, expected comma")) 5562 return true; 5563 5564 const MCExpr *Expr; 5565 if (Parser.parseExpression(Expr)) { 5566 reportParseError("expected expression"); 5567 return false; 5568 } 5569 5570 if (Expr->getKind() != MCExpr::SymbolRef) { 5571 reportParseError("expected symbol"); 5572 return false; 5573 } 5574 const MCSymbolRefExpr *Ref = static_cast<const MCSymbolRefExpr *>(Expr); 5575 5576 CpSaveLocation = Save; 5577 CpSaveLocationIsRegister = SaveIsReg; 5578 5579 getTargetStreamer().emitDirectiveCpsetup(FuncReg, Save, Ref->getSymbol(), 5580 SaveIsReg); 5581 return false; 5582 } 5583 5584 bool MipsAsmParser::parseDirectiveCPReturn() { 5585 getTargetStreamer().emitDirectiveCpreturn(CpSaveLocation, 5586 CpSaveLocationIsRegister); 5587 return false; 5588 } 5589 5590 bool MipsAsmParser::parseDirectiveNaN() { 5591 MCAsmParser &Parser = getParser(); 5592 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5593 const AsmToken &Tok = Parser.getTok(); 5594 5595 if (Tok.getString() == "2008") { 5596 Parser.Lex(); 5597 getTargetStreamer().emitDirectiveNaN2008(); 5598 return false; 5599 } else if (Tok.getString() == "legacy") { 5600 Parser.Lex(); 5601 getTargetStreamer().emitDirectiveNaNLegacy(); 5602 return false; 5603 } 5604 } 5605 // If we don't recognize the option passed to the .nan 5606 // directive (e.g. no option or unknown option), emit an error. 5607 reportParseError("invalid option in .nan directive"); 5608 return false; 5609 } 5610 5611 bool MipsAsmParser::parseDirectiveSet() { 5612 MCAsmParser &Parser = getParser(); 5613 // Get the next token. 5614 const AsmToken &Tok = Parser.getTok(); 5615 5616 if (Tok.getString() == "noat") { 5617 return parseSetNoAtDirective(); 5618 } else if (Tok.getString() == "at") { 5619 return parseSetAtDirective(); 5620 } else if (Tok.getString() == "arch") { 5621 return parseSetArchDirective(); 5622 } else if (Tok.getString() == "fp") { 5623 return parseSetFpDirective(); 5624 } else if (Tok.getString() == "oddspreg") { 5625 return parseSetOddSPRegDirective(); 5626 } else if (Tok.getString() == "nooddspreg") { 5627 return parseSetNoOddSPRegDirective(); 5628 } else if (Tok.getString() == "pop") { 5629 return parseSetPopDirective(); 5630 } else if (Tok.getString() == "push") { 5631 return parseSetPushDirective(); 5632 } else if (Tok.getString() == "reorder") { 5633 return parseSetReorderDirective(); 5634 } else if (Tok.getString() == "noreorder") { 5635 return parseSetNoReorderDirective(); 5636 } else if (Tok.getString() == "macro") { 5637 return parseSetMacroDirective(); 5638 } else if (Tok.getString() == "nomacro") { 5639 return parseSetNoMacroDirective(); 5640 } else if (Tok.getString() == "mips16") { 5641 return parseSetMips16Directive(); 5642 } else if (Tok.getString() == "nomips16") { 5643 return parseSetNoMips16Directive(); 5644 } else if (Tok.getString() == "nomicromips") { 5645 clearFeatureBits(Mips::FeatureMicroMips, "micromips"); 5646 getTargetStreamer().emitDirectiveSetNoMicroMips(); 5647 Parser.eatToEndOfStatement(); 5648 return false; 5649 } else if (Tok.getString() == "micromips") { 5650 return parseSetFeature(Mips::FeatureMicroMips); 5651 } else if (Tok.getString() == "mips0") { 5652 return parseSetMips0Directive(); 5653 } else if (Tok.getString() == "mips1") { 5654 return parseSetFeature(Mips::FeatureMips1); 5655 } else if (Tok.getString() == "mips2") { 5656 return parseSetFeature(Mips::FeatureMips2); 5657 } else if (Tok.getString() == "mips3") { 5658 return parseSetFeature(Mips::FeatureMips3); 5659 } else if (Tok.getString() == "mips4") { 5660 return parseSetFeature(Mips::FeatureMips4); 5661 } else if (Tok.getString() == "mips5") { 5662 return parseSetFeature(Mips::FeatureMips5); 5663 } else if (Tok.getString() == "mips32") { 5664 return parseSetFeature(Mips::FeatureMips32); 5665 } else if (Tok.getString() == "mips32r2") { 5666 return parseSetFeature(Mips::FeatureMips32r2); 5667 } else if (Tok.getString() == "mips32r3") { 5668 return parseSetFeature(Mips::FeatureMips32r3); 5669 } else if (Tok.getString() == "mips32r5") { 5670 return parseSetFeature(Mips::FeatureMips32r5); 5671 } else if (Tok.getString() == "mips32r6") { 5672 return parseSetFeature(Mips::FeatureMips32r6); 5673 } else if (Tok.getString() == "mips64") { 5674 return parseSetFeature(Mips::FeatureMips64); 5675 } else if (Tok.getString() == "mips64r2") { 5676 return parseSetFeature(Mips::FeatureMips64r2); 5677 } else if (Tok.getString() == "mips64r3") { 5678 return parseSetFeature(Mips::FeatureMips64r3); 5679 } else if (Tok.getString() == "mips64r5") { 5680 return parseSetFeature(Mips::FeatureMips64r5); 5681 } else if (Tok.getString() == "mips64r6") { 5682 return parseSetFeature(Mips::FeatureMips64r6); 5683 } else if (Tok.getString() == "dsp") { 5684 return parseSetFeature(Mips::FeatureDSP); 5685 } else if (Tok.getString() == "nodsp") { 5686 return parseSetNoDspDirective(); 5687 } else if (Tok.getString() == "msa") { 5688 return parseSetMsaDirective(); 5689 } else if (Tok.getString() == "nomsa") { 5690 return parseSetNoMsaDirective(); 5691 } else if (Tok.getString() == "softfloat") { 5692 return parseSetSoftFloatDirective(); 5693 } else if (Tok.getString() == "hardfloat") { 5694 return parseSetHardFloatDirective(); 5695 } else { 5696 // It is just an identifier, look for an assignment. 5697 parseSetAssignment(); 5698 return false; 5699 } 5700 5701 return true; 5702 } 5703 5704 /// parseDataDirective 5705 /// ::= .word [ expression (, expression)* ] 5706 bool MipsAsmParser::parseDataDirective(unsigned Size, SMLoc L) { 5707 MCAsmParser &Parser = getParser(); 5708 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5709 for (;;) { 5710 const MCExpr *Value; 5711 if (getParser().parseExpression(Value)) 5712 return true; 5713 5714 getParser().getStreamer().EmitValue(Value, Size); 5715 5716 if (getLexer().is(AsmToken::EndOfStatement)) 5717 break; 5718 5719 if (getLexer().isNot(AsmToken::Comma)) 5720 return Error(L, "unexpected token, expected comma"); 5721 Parser.Lex(); 5722 } 5723 } 5724 5725 Parser.Lex(); 5726 return false; 5727 } 5728 5729 /// parseDirectiveGpWord 5730 /// ::= .gpword local_sym 5731 bool MipsAsmParser::parseDirectiveGpWord() { 5732 MCAsmParser &Parser = getParser(); 5733 const MCExpr *Value; 5734 // EmitGPRel32Value requires an expression, so we are using base class 5735 // method to evaluate the expression. 5736 if (getParser().parseExpression(Value)) 5737 return true; 5738 getParser().getStreamer().EmitGPRel32Value(Value); 5739 5740 if (getLexer().isNot(AsmToken::EndOfStatement)) 5741 return Error(getLexer().getLoc(), 5742 "unexpected token, expected end of statement"); 5743 Parser.Lex(); // Eat EndOfStatement token. 5744 return false; 5745 } 5746 5747 /// parseDirectiveGpDWord 5748 /// ::= .gpdword local_sym 5749 bool MipsAsmParser::parseDirectiveGpDWord() { 5750 MCAsmParser &Parser = getParser(); 5751 const MCExpr *Value; 5752 // EmitGPRel64Value requires an expression, so we are using base class 5753 // method to evaluate the expression. 5754 if (getParser().parseExpression(Value)) 5755 return true; 5756 getParser().getStreamer().EmitGPRel64Value(Value); 5757 5758 if (getLexer().isNot(AsmToken::EndOfStatement)) 5759 return Error(getLexer().getLoc(), 5760 "unexpected token, expected end of statement"); 5761 Parser.Lex(); // Eat EndOfStatement token. 5762 return false; 5763 } 5764 5765 /// parseDirectiveDtpRelWord 5766 /// ::= .dtprelword tls_sym 5767 bool MipsAsmParser::parseDirectiveDtpRelWord() { 5768 MCAsmParser &Parser = getParser(); 5769 const MCExpr *Value; 5770 // EmitDTPRel32Value requires an expression, so we are using base class 5771 // method to evaluate the expression. 5772 if (getParser().parseExpression(Value)) 5773 return true; 5774 getParser().getStreamer().EmitDTPRel32Value(Value); 5775 5776 if (getLexer().isNot(AsmToken::EndOfStatement)) 5777 return Error(getLexer().getLoc(), 5778 "unexpected token, expected end of statement"); 5779 Parser.Lex(); // Eat EndOfStatement token. 5780 return false; 5781 } 5782 5783 /// parseDirectiveDtpRelDWord 5784 /// ::= .dtpreldword tls_sym 5785 bool MipsAsmParser::parseDirectiveDtpRelDWord() { 5786 MCAsmParser &Parser = getParser(); 5787 const MCExpr *Value; 5788 // EmitDTPRel64Value requires an expression, so we are using base class 5789 // method to evaluate the expression. 5790 if (getParser().parseExpression(Value)) 5791 return true; 5792 getParser().getStreamer().EmitDTPRel64Value(Value); 5793 5794 if (getLexer().isNot(AsmToken::EndOfStatement)) 5795 return Error(getLexer().getLoc(), 5796 "unexpected token, expected end of statement"); 5797 Parser.Lex(); // Eat EndOfStatement token. 5798 return false; 5799 } 5800 5801 /// parseDirectiveTpRelWord 5802 /// ::= .tprelword tls_sym 5803 bool MipsAsmParser::parseDirectiveTpRelWord() { 5804 MCAsmParser &Parser = getParser(); 5805 const MCExpr *Value; 5806 // EmitTPRel32Value requires an expression, so we are using base class 5807 // method to evaluate the expression. 5808 if (getParser().parseExpression(Value)) 5809 return true; 5810 getParser().getStreamer().EmitTPRel32Value(Value); 5811 5812 if (getLexer().isNot(AsmToken::EndOfStatement)) 5813 return Error(getLexer().getLoc(), 5814 "unexpected token, expected end of statement"); 5815 Parser.Lex(); // Eat EndOfStatement token. 5816 return false; 5817 } 5818 5819 /// parseDirectiveTpRelDWord 5820 /// ::= .tpreldword tls_sym 5821 bool MipsAsmParser::parseDirectiveTpRelDWord() { 5822 MCAsmParser &Parser = getParser(); 5823 const MCExpr *Value; 5824 // EmitTPRel64Value requires an expression, so we are using base class 5825 // method to evaluate the expression. 5826 if (getParser().parseExpression(Value)) 5827 return true; 5828 getParser().getStreamer().EmitTPRel64Value(Value); 5829 5830 if (getLexer().isNot(AsmToken::EndOfStatement)) 5831 return Error(getLexer().getLoc(), 5832 "unexpected token, expected end of statement"); 5833 Parser.Lex(); // Eat EndOfStatement token. 5834 return false; 5835 } 5836 5837 bool MipsAsmParser::parseDirectiveOption() { 5838 MCAsmParser &Parser = getParser(); 5839 // Get the option token. 5840 AsmToken Tok = Parser.getTok(); 5841 // At the moment only identifiers are supported. 5842 if (Tok.isNot(AsmToken::Identifier)) { 5843 return Error(Parser.getTok().getLoc(), 5844 "unexpected token, expected identifier"); 5845 } 5846 5847 StringRef Option = Tok.getIdentifier(); 5848 5849 if (Option == "pic0") { 5850 // MipsAsmParser needs to know if the current PIC mode changes. 5851 IsPicEnabled = false; 5852 5853 getTargetStreamer().emitDirectiveOptionPic0(); 5854 Parser.Lex(); 5855 if (Parser.getTok().isNot(AsmToken::EndOfStatement)) { 5856 return Error(Parser.getTok().getLoc(), 5857 "unexpected token, expected end of statement"); 5858 } 5859 return false; 5860 } 5861 5862 if (Option == "pic2") { 5863 // MipsAsmParser needs to know if the current PIC mode changes. 5864 IsPicEnabled = true; 5865 5866 getTargetStreamer().emitDirectiveOptionPic2(); 5867 Parser.Lex(); 5868 if (Parser.getTok().isNot(AsmToken::EndOfStatement)) { 5869 return Error(Parser.getTok().getLoc(), 5870 "unexpected token, expected end of statement"); 5871 } 5872 return false; 5873 } 5874 5875 // Unknown option. 5876 Warning(Parser.getTok().getLoc(), 5877 "unknown option, expected 'pic0' or 'pic2'"); 5878 Parser.eatToEndOfStatement(); 5879 return false; 5880 } 5881 5882 /// parseInsnDirective 5883 /// ::= .insn 5884 bool MipsAsmParser::parseInsnDirective() { 5885 // If this is not the end of the statement, report an error. 5886 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5887 reportParseError("unexpected token, expected end of statement"); 5888 return false; 5889 } 5890 5891 // The actual label marking happens in 5892 // MipsELFStreamer::createPendingLabelRelocs(). 5893 getTargetStreamer().emitDirectiveInsn(); 5894 5895 getParser().Lex(); // Eat EndOfStatement token. 5896 return false; 5897 } 5898 5899 /// parseSSectionDirective 5900 /// ::= .sbss 5901 /// ::= .sdata 5902 bool MipsAsmParser::parseSSectionDirective(StringRef Section, unsigned Type) { 5903 // If this is not the end of the statement, report an error. 5904 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5905 reportParseError("unexpected token, expected end of statement"); 5906 return false; 5907 } 5908 5909 MCSection *ELFSection = getContext().getELFSection( 5910 Section, Type, ELF::SHF_WRITE | ELF::SHF_ALLOC | ELF::SHF_MIPS_GPREL); 5911 getParser().getStreamer().SwitchSection(ELFSection); 5912 5913 getParser().Lex(); // Eat EndOfStatement token. 5914 return false; 5915 } 5916 5917 /// parseDirectiveModule 5918 /// ::= .module oddspreg 5919 /// ::= .module nooddspreg 5920 /// ::= .module fp=value 5921 /// ::= .module softfloat 5922 /// ::= .module hardfloat 5923 bool MipsAsmParser::parseDirectiveModule() { 5924 MCAsmParser &Parser = getParser(); 5925 MCAsmLexer &Lexer = getLexer(); 5926 SMLoc L = Lexer.getLoc(); 5927 5928 if (!getTargetStreamer().isModuleDirectiveAllowed()) { 5929 // TODO : get a better message. 5930 reportParseError(".module directive must appear before any code"); 5931 return false; 5932 } 5933 5934 StringRef Option; 5935 if (Parser.parseIdentifier(Option)) { 5936 reportParseError("expected .module option identifier"); 5937 return false; 5938 } 5939 5940 if (Option == "oddspreg") { 5941 clearModuleFeatureBits(Mips::FeatureNoOddSPReg, "nooddspreg"); 5942 5943 // Synchronize the abiflags information with the FeatureBits information we 5944 // changed above. 5945 getTargetStreamer().updateABIInfo(*this); 5946 5947 // If printing assembly, use the recently updated abiflags information. 5948 // If generating ELF, don't do anything (the .MIPS.abiflags section gets 5949 // emitted at the end). 5950 getTargetStreamer().emitDirectiveModuleOddSPReg(); 5951 5952 // If this is not the end of the statement, report an error. 5953 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5954 reportParseError("unexpected token, expected end of statement"); 5955 return false; 5956 } 5957 5958 return false; // parseDirectiveModule has finished successfully. 5959 } else if (Option == "nooddspreg") { 5960 if (!isABI_O32()) { 5961 return Error(L, "'.module nooddspreg' requires the O32 ABI"); 5962 } 5963 5964 setModuleFeatureBits(Mips::FeatureNoOddSPReg, "nooddspreg"); 5965 5966 // Synchronize the abiflags information with the FeatureBits information we 5967 // changed above. 5968 getTargetStreamer().updateABIInfo(*this); 5969 5970 // If printing assembly, use the recently updated abiflags information. 5971 // If generating ELF, don't do anything (the .MIPS.abiflags section gets 5972 // emitted at the end). 5973 getTargetStreamer().emitDirectiveModuleOddSPReg(); 5974 5975 // If this is not the end of the statement, report an error. 5976 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5977 reportParseError("unexpected token, expected end of statement"); 5978 return false; 5979 } 5980 5981 return false; // parseDirectiveModule has finished successfully. 5982 } else if (Option == "fp") { 5983 return parseDirectiveModuleFP(); 5984 } else if (Option == "softfloat") { 5985 setModuleFeatureBits(Mips::FeatureSoftFloat, "soft-float"); 5986 5987 // Synchronize the ABI Flags information with the FeatureBits information we 5988 // updated above. 5989 getTargetStreamer().updateABIInfo(*this); 5990 5991 // If printing assembly, use the recently updated ABI Flags information. 5992 // If generating ELF, don't do anything (the .MIPS.abiflags section gets 5993 // emitted later). 5994 getTargetStreamer().emitDirectiveModuleSoftFloat(); 5995 5996 // If this is not the end of the statement, report an error. 5997 if (getLexer().isNot(AsmToken::EndOfStatement)) { 5998 reportParseError("unexpected token, expected end of statement"); 5999 return false; 6000 } 6001 6002 return false; // parseDirectiveModule has finished successfully. 6003 } else if (Option == "hardfloat") { 6004 clearModuleFeatureBits(Mips::FeatureSoftFloat, "soft-float"); 6005 6006 // Synchronize the ABI Flags information with the FeatureBits information we 6007 // updated above. 6008 getTargetStreamer().updateABIInfo(*this); 6009 6010 // If printing assembly, use the recently updated ABI Flags information. 6011 // If generating ELF, don't do anything (the .MIPS.abiflags section gets 6012 // emitted later). 6013 getTargetStreamer().emitDirectiveModuleHardFloat(); 6014 6015 // If this is not the end of the statement, report an error. 6016 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6017 reportParseError("unexpected token, expected end of statement"); 6018 return false; 6019 } 6020 6021 return false; // parseDirectiveModule has finished successfully. 6022 } else { 6023 return Error(L, "'" + Twine(Option) + "' is not a valid .module option."); 6024 } 6025 } 6026 6027 /// parseDirectiveModuleFP 6028 /// ::= =32 6029 /// ::= =xx 6030 /// ::= =64 6031 bool MipsAsmParser::parseDirectiveModuleFP() { 6032 MCAsmParser &Parser = getParser(); 6033 MCAsmLexer &Lexer = getLexer(); 6034 6035 if (Lexer.isNot(AsmToken::Equal)) { 6036 reportParseError("unexpected token, expected equals sign '='"); 6037 return false; 6038 } 6039 Parser.Lex(); // Eat '=' token. 6040 6041 MipsABIFlagsSection::FpABIKind FpABI; 6042 if (!parseFpABIValue(FpABI, ".module")) 6043 return false; 6044 6045 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6046 reportParseError("unexpected token, expected end of statement"); 6047 return false; 6048 } 6049 6050 // Synchronize the abiflags information with the FeatureBits information we 6051 // changed above. 6052 getTargetStreamer().updateABIInfo(*this); 6053 6054 // If printing assembly, use the recently updated abiflags information. 6055 // If generating ELF, don't do anything (the .MIPS.abiflags section gets 6056 // emitted at the end). 6057 getTargetStreamer().emitDirectiveModuleFP(); 6058 6059 Parser.Lex(); // Consume the EndOfStatement. 6060 return false; 6061 } 6062 6063 bool MipsAsmParser::parseFpABIValue(MipsABIFlagsSection::FpABIKind &FpABI, 6064 StringRef Directive) { 6065 MCAsmParser &Parser = getParser(); 6066 MCAsmLexer &Lexer = getLexer(); 6067 bool ModuleLevelOptions = Directive == ".module"; 6068 6069 if (Lexer.is(AsmToken::Identifier)) { 6070 StringRef Value = Parser.getTok().getString(); 6071 Parser.Lex(); 6072 6073 if (Value != "xx") { 6074 reportParseError("unsupported value, expected 'xx', '32' or '64'"); 6075 return false; 6076 } 6077 6078 if (!isABI_O32()) { 6079 reportParseError("'" + Directive + " fp=xx' requires the O32 ABI"); 6080 return false; 6081 } 6082 6083 FpABI = MipsABIFlagsSection::FpABIKind::XX; 6084 if (ModuleLevelOptions) { 6085 setModuleFeatureBits(Mips::FeatureFPXX, "fpxx"); 6086 clearModuleFeatureBits(Mips::FeatureFP64Bit, "fp64"); 6087 } else { 6088 setFeatureBits(Mips::FeatureFPXX, "fpxx"); 6089 clearFeatureBits(Mips::FeatureFP64Bit, "fp64"); 6090 } 6091 return true; 6092 } 6093 6094 if (Lexer.is(AsmToken::Integer)) { 6095 unsigned Value = Parser.getTok().getIntVal(); 6096 Parser.Lex(); 6097 6098 if (Value != 32 && Value != 64) { 6099 reportParseError("unsupported value, expected 'xx', '32' or '64'"); 6100 return false; 6101 } 6102 6103 if (Value == 32) { 6104 if (!isABI_O32()) { 6105 reportParseError("'" + Directive + " fp=32' requires the O32 ABI"); 6106 return false; 6107 } 6108 6109 FpABI = MipsABIFlagsSection::FpABIKind::S32; 6110 if (ModuleLevelOptions) { 6111 clearModuleFeatureBits(Mips::FeatureFPXX, "fpxx"); 6112 clearModuleFeatureBits(Mips::FeatureFP64Bit, "fp64"); 6113 } else { 6114 clearFeatureBits(Mips::FeatureFPXX, "fpxx"); 6115 clearFeatureBits(Mips::FeatureFP64Bit, "fp64"); 6116 } 6117 } else { 6118 FpABI = MipsABIFlagsSection::FpABIKind::S64; 6119 if (ModuleLevelOptions) { 6120 clearModuleFeatureBits(Mips::FeatureFPXX, "fpxx"); 6121 setModuleFeatureBits(Mips::FeatureFP64Bit, "fp64"); 6122 } else { 6123 clearFeatureBits(Mips::FeatureFPXX, "fpxx"); 6124 setFeatureBits(Mips::FeatureFP64Bit, "fp64"); 6125 } 6126 } 6127 6128 return true; 6129 } 6130 6131 return false; 6132 } 6133 6134 bool MipsAsmParser::ParseDirective(AsmToken DirectiveID) { 6135 // This returns false if this function recognizes the directive 6136 // regardless of whether it is successfully handles or reports an 6137 // error. Otherwise it returns true to give the generic parser a 6138 // chance at recognizing it. 6139 6140 MCAsmParser &Parser = getParser(); 6141 StringRef IDVal = DirectiveID.getString(); 6142 6143 if (IDVal == ".cpload") { 6144 parseDirectiveCpLoad(DirectiveID.getLoc()); 6145 return false; 6146 } 6147 if (IDVal == ".cprestore") { 6148 parseDirectiveCpRestore(DirectiveID.getLoc()); 6149 return false; 6150 } 6151 if (IDVal == ".dword") { 6152 parseDataDirective(8, DirectiveID.getLoc()); 6153 return false; 6154 } 6155 if (IDVal == ".ent") { 6156 StringRef SymbolName; 6157 6158 if (Parser.parseIdentifier(SymbolName)) { 6159 reportParseError("expected identifier after .ent"); 6160 return false; 6161 } 6162 6163 // There's an undocumented extension that allows an integer to 6164 // follow the name of the procedure which AFAICS is ignored by GAS. 6165 // Example: .ent foo,2 6166 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6167 if (getLexer().isNot(AsmToken::Comma)) { 6168 // Even though we accept this undocumented extension for compatibility 6169 // reasons, the additional integer argument does not actually change 6170 // the behaviour of the '.ent' directive, so we would like to discourage 6171 // its use. We do this by not referring to the extended version in 6172 // error messages which are not directly related to its use. 6173 reportParseError("unexpected token, expected end of statement"); 6174 return false; 6175 } 6176 Parser.Lex(); // Eat the comma. 6177 const MCExpr *DummyNumber; 6178 int64_t DummyNumberVal; 6179 // If the user was explicitly trying to use the extended version, 6180 // we still give helpful extension-related error messages. 6181 if (Parser.parseExpression(DummyNumber)) { 6182 reportParseError("expected number after comma"); 6183 return false; 6184 } 6185 if (!DummyNumber->evaluateAsAbsolute(DummyNumberVal)) { 6186 reportParseError("expected an absolute expression after comma"); 6187 return false; 6188 } 6189 } 6190 6191 // If this is not the end of the statement, report an error. 6192 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6193 reportParseError("unexpected token, expected end of statement"); 6194 return false; 6195 } 6196 6197 MCSymbol *Sym = getContext().getOrCreateSymbol(SymbolName); 6198 6199 getTargetStreamer().emitDirectiveEnt(*Sym); 6200 CurrentFn = Sym; 6201 IsCpRestoreSet = false; 6202 return false; 6203 } 6204 6205 if (IDVal == ".end") { 6206 StringRef SymbolName; 6207 6208 if (Parser.parseIdentifier(SymbolName)) { 6209 reportParseError("expected identifier after .end"); 6210 return false; 6211 } 6212 6213 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6214 reportParseError("unexpected token, expected end of statement"); 6215 return false; 6216 } 6217 6218 if (CurrentFn == nullptr) { 6219 reportParseError(".end used without .ent"); 6220 return false; 6221 } 6222 6223 if ((SymbolName != CurrentFn->getName())) { 6224 reportParseError(".end symbol does not match .ent symbol"); 6225 return false; 6226 } 6227 6228 getTargetStreamer().emitDirectiveEnd(SymbolName); 6229 CurrentFn = nullptr; 6230 IsCpRestoreSet = false; 6231 return false; 6232 } 6233 6234 if (IDVal == ".frame") { 6235 // .frame $stack_reg, frame_size_in_bytes, $return_reg 6236 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> TmpReg; 6237 OperandMatchResultTy ResTy = parseAnyRegister(TmpReg); 6238 if (ResTy == MatchOperand_NoMatch || ResTy == MatchOperand_ParseFail) { 6239 reportParseError("expected stack register"); 6240 return false; 6241 } 6242 6243 MipsOperand &StackRegOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 6244 if (!StackRegOpnd.isGPRAsmReg()) { 6245 reportParseError(StackRegOpnd.getStartLoc(), 6246 "expected general purpose register"); 6247 return false; 6248 } 6249 unsigned StackReg = StackRegOpnd.getGPR32Reg(); 6250 6251 if (Parser.getTok().is(AsmToken::Comma)) 6252 Parser.Lex(); 6253 else { 6254 reportParseError("unexpected token, expected comma"); 6255 return false; 6256 } 6257 6258 // Parse the frame size. 6259 const MCExpr *FrameSize; 6260 int64_t FrameSizeVal; 6261 6262 if (Parser.parseExpression(FrameSize)) { 6263 reportParseError("expected frame size value"); 6264 return false; 6265 } 6266 6267 if (!FrameSize->evaluateAsAbsolute(FrameSizeVal)) { 6268 reportParseError("frame size not an absolute expression"); 6269 return false; 6270 } 6271 6272 if (Parser.getTok().is(AsmToken::Comma)) 6273 Parser.Lex(); 6274 else { 6275 reportParseError("unexpected token, expected comma"); 6276 return false; 6277 } 6278 6279 // Parse the return register. 6280 TmpReg.clear(); 6281 ResTy = parseAnyRegister(TmpReg); 6282 if (ResTy == MatchOperand_NoMatch || ResTy == MatchOperand_ParseFail) { 6283 reportParseError("expected return register"); 6284 return false; 6285 } 6286 6287 MipsOperand &ReturnRegOpnd = static_cast<MipsOperand &>(*TmpReg[0]); 6288 if (!ReturnRegOpnd.isGPRAsmReg()) { 6289 reportParseError(ReturnRegOpnd.getStartLoc(), 6290 "expected general purpose register"); 6291 return false; 6292 } 6293 6294 // If this is not the end of the statement, report an error. 6295 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6296 reportParseError("unexpected token, expected end of statement"); 6297 return false; 6298 } 6299 6300 getTargetStreamer().emitFrame(StackReg, FrameSizeVal, 6301 ReturnRegOpnd.getGPR32Reg()); 6302 IsCpRestoreSet = false; 6303 return false; 6304 } 6305 6306 if (IDVal == ".set") { 6307 parseDirectiveSet(); 6308 return false; 6309 } 6310 6311 if (IDVal == ".mask" || IDVal == ".fmask") { 6312 // .mask bitmask, frame_offset 6313 // bitmask: One bit for each register used. 6314 // frame_offset: Offset from Canonical Frame Address ($sp on entry) where 6315 // first register is expected to be saved. 6316 // Examples: 6317 // .mask 0x80000000, -4 6318 // .fmask 0x80000000, -4 6319 // 6320 6321 // Parse the bitmask 6322 const MCExpr *BitMask; 6323 int64_t BitMaskVal; 6324 6325 if (Parser.parseExpression(BitMask)) { 6326 reportParseError("expected bitmask value"); 6327 return false; 6328 } 6329 6330 if (!BitMask->evaluateAsAbsolute(BitMaskVal)) { 6331 reportParseError("bitmask not an absolute expression"); 6332 return false; 6333 } 6334 6335 if (Parser.getTok().is(AsmToken::Comma)) 6336 Parser.Lex(); 6337 else { 6338 reportParseError("unexpected token, expected comma"); 6339 return false; 6340 } 6341 6342 // Parse the frame_offset 6343 const MCExpr *FrameOffset; 6344 int64_t FrameOffsetVal; 6345 6346 if (Parser.parseExpression(FrameOffset)) { 6347 reportParseError("expected frame offset value"); 6348 return false; 6349 } 6350 6351 if (!FrameOffset->evaluateAsAbsolute(FrameOffsetVal)) { 6352 reportParseError("frame offset not an absolute expression"); 6353 return false; 6354 } 6355 6356 // If this is not the end of the statement, report an error. 6357 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6358 reportParseError("unexpected token, expected end of statement"); 6359 return false; 6360 } 6361 6362 if (IDVal == ".mask") 6363 getTargetStreamer().emitMask(BitMaskVal, FrameOffsetVal); 6364 else 6365 getTargetStreamer().emitFMask(BitMaskVal, FrameOffsetVal); 6366 return false; 6367 } 6368 6369 if (IDVal == ".nan") 6370 return parseDirectiveNaN(); 6371 6372 if (IDVal == ".gpword") { 6373 parseDirectiveGpWord(); 6374 return false; 6375 } 6376 6377 if (IDVal == ".gpdword") { 6378 parseDirectiveGpDWord(); 6379 return false; 6380 } 6381 6382 if (IDVal == ".dtprelword") { 6383 parseDirectiveDtpRelWord(); 6384 return false; 6385 } 6386 6387 if (IDVal == ".dtpreldword") { 6388 parseDirectiveDtpRelDWord(); 6389 return false; 6390 } 6391 6392 if (IDVal == ".tprelword") { 6393 parseDirectiveTpRelWord(); 6394 return false; 6395 } 6396 6397 if (IDVal == ".tpreldword") { 6398 parseDirectiveTpRelDWord(); 6399 return false; 6400 } 6401 6402 if (IDVal == ".word") { 6403 parseDataDirective(4, DirectiveID.getLoc()); 6404 return false; 6405 } 6406 6407 if (IDVal == ".hword") { 6408 parseDataDirective(2, DirectiveID.getLoc()); 6409 return false; 6410 } 6411 6412 if (IDVal == ".option") { 6413 parseDirectiveOption(); 6414 return false; 6415 } 6416 6417 if (IDVal == ".abicalls") { 6418 getTargetStreamer().emitDirectiveAbiCalls(); 6419 if (Parser.getTok().isNot(AsmToken::EndOfStatement)) { 6420 Error(Parser.getTok().getLoc(), 6421 "unexpected token, expected end of statement"); 6422 } 6423 return false; 6424 } 6425 6426 if (IDVal == ".cpsetup") { 6427 parseDirectiveCPSetup(); 6428 return false; 6429 } 6430 if (IDVal == ".cpreturn") { 6431 parseDirectiveCPReturn(); 6432 return false; 6433 } 6434 if (IDVal == ".module") { 6435 parseDirectiveModule(); 6436 return false; 6437 } 6438 if (IDVal == ".llvm_internal_mips_reallow_module_directive") { 6439 parseInternalDirectiveReallowModule(); 6440 return false; 6441 } 6442 if (IDVal == ".insn") { 6443 parseInsnDirective(); 6444 return false; 6445 } 6446 if (IDVal == ".sbss") { 6447 parseSSectionDirective(IDVal, ELF::SHT_NOBITS); 6448 return false; 6449 } 6450 if (IDVal == ".sdata") { 6451 parseSSectionDirective(IDVal, ELF::SHT_PROGBITS); 6452 return false; 6453 } 6454 6455 return true; 6456 } 6457 6458 bool MipsAsmParser::parseInternalDirectiveReallowModule() { 6459 // If this is not the end of the statement, report an error. 6460 if (getLexer().isNot(AsmToken::EndOfStatement)) { 6461 reportParseError("unexpected token, expected end of statement"); 6462 return false; 6463 } 6464 6465 getTargetStreamer().reallowModuleDirective(); 6466 6467 getParser().Lex(); // Eat EndOfStatement token. 6468 return false; 6469 } 6470 6471 extern "C" void LLVMInitializeMipsAsmParser() { 6472 RegisterMCAsmParser<MipsAsmParser> X(getTheMipsTarget()); 6473 RegisterMCAsmParser<MipsAsmParser> Y(getTheMipselTarget()); 6474 RegisterMCAsmParser<MipsAsmParser> A(getTheMips64Target()); 6475 RegisterMCAsmParser<MipsAsmParser> B(getTheMips64elTarget()); 6476 } 6477 6478 #define GET_REGISTER_MATCHER 6479 #define GET_MATCHER_IMPLEMENTATION 6480 #include "MipsGenAsmMatcher.inc" 6481