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