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