LLVM API Documentation

SparcAsmParser.cpp
Go to the documentation of this file.
00001 //===-- SparcAsmParser.cpp - Parse Sparc assembly to MCInst instructions --===//
00002 //
00003 //                     The LLVM Compiler Infrastructure
00004 //
00005 // This file is distributed under the University of Illinois Open Source
00006 // License. See LICENSE.TXT for details.
00007 //
00008 //===----------------------------------------------------------------------===//
00009 
00010 #include "MCTargetDesc/SparcMCTargetDesc.h"
00011 #include "MCTargetDesc/SparcMCExpr.h"
00012 #include "llvm/ADT/STLExtras.h"
00013 #include "llvm/MC/MCContext.h"
00014 #include "llvm/MC/MCInst.h"
00015 #include "llvm/MC/MCObjectFileInfo.h"
00016 #include "llvm/MC/MCParser/MCParsedAsmOperand.h"
00017 #include "llvm/MC/MCStreamer.h"
00018 #include "llvm/MC/MCSubtargetInfo.h"
00019 #include "llvm/MC/MCSymbol.h"
00020 #include "llvm/MC/MCTargetAsmParser.h"
00021 #include "llvm/Support/TargetRegistry.h"
00022 
00023 using namespace llvm;
00024 
00025 // The generated AsmMatcher SparcGenAsmMatcher uses "Sparc" as the target
00026 // namespace. But SPARC backend uses "SP" as its namespace.
00027 namespace llvm {
00028   namespace Sparc {
00029     using namespace SP;
00030   }
00031 }
00032 
00033 namespace {
00034 class SparcOperand;
00035 class SparcAsmParser : public MCTargetAsmParser {
00036 
00037   MCSubtargetInfo &STI;
00038   MCAsmParser &Parser;
00039 
00040   /// @name Auto-generated Match Functions
00041   /// {
00042 
00043 #define GET_ASSEMBLER_HEADER
00044 #include "SparcGenAsmMatcher.inc"
00045 
00046   /// }
00047 
00048   // public interface of the MCTargetAsmParser.
00049   bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
00050                                OperandVector &Operands, MCStreamer &Out,
00051                                uint64_t &ErrorInfo,
00052                                bool MatchingInlineAsm) override;
00053   bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc) override;
00054   bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name,
00055                         SMLoc NameLoc, OperandVector &Operands) override;
00056   bool ParseDirective(AsmToken DirectiveID) override;
00057 
00058   unsigned validateTargetOperandClass(MCParsedAsmOperand &Op,
00059                                       unsigned Kind) override;
00060 
00061   // Custom parse functions for Sparc specific operands.
00062   OperandMatchResultTy parseMEMOperand(OperandVector &Operands);
00063 
00064   OperandMatchResultTy parseOperand(OperandVector &Operands, StringRef Name);
00065 
00066   OperandMatchResultTy
00067   parseSparcAsmOperand(std::unique_ptr<SparcOperand> &Operand,
00068                        bool isCall = false);
00069 
00070   OperandMatchResultTy parseBranchModifiers(OperandVector &Operands);
00071 
00072   // returns true if Tok is matched to a register and returns register in RegNo.
00073   bool matchRegisterName(const AsmToken &Tok, unsigned &RegNo,
00074                          unsigned &RegKind);
00075 
00076   bool matchSparcAsmModifiers(const MCExpr *&EVal, SMLoc &EndLoc);
00077   bool parseDirectiveWord(unsigned Size, SMLoc L);
00078 
00079   bool is64Bit() const { return STI.getTargetTriple().startswith("sparcv9"); }
00080 public:
00081   SparcAsmParser(MCSubtargetInfo &sti, MCAsmParser &parser,
00082                 const MCInstrInfo &MII,
00083                 const MCTargetOptions &Options)
00084       : MCTargetAsmParser(), STI(sti), Parser(parser) {
00085     // Initialize the set of available features.
00086     setAvailableFeatures(ComputeAvailableFeatures(STI.getFeatureBits()));
00087   }
00088 
00089 };
00090 
00091   static unsigned IntRegs[32] = {
00092     Sparc::G0, Sparc::G1, Sparc::G2, Sparc::G3,
00093     Sparc::G4, Sparc::G5, Sparc::G6, Sparc::G7,
00094     Sparc::O0, Sparc::O1, Sparc::O2, Sparc::O3,
00095     Sparc::O4, Sparc::O5, Sparc::O6, Sparc::O7,
00096     Sparc::L0, Sparc::L1, Sparc::L2, Sparc::L3,
00097     Sparc::L4, Sparc::L5, Sparc::L6, Sparc::L7,
00098     Sparc::I0, Sparc::I1, Sparc::I2, Sparc::I3,
00099     Sparc::I4, Sparc::I5, Sparc::I6, Sparc::I7 };
00100 
00101   static unsigned FloatRegs[32] = {
00102     Sparc::F0,  Sparc::F1,  Sparc::F2,  Sparc::F3,
00103     Sparc::F4,  Sparc::F5,  Sparc::F6,  Sparc::F7,
00104     Sparc::F8,  Sparc::F9,  Sparc::F10, Sparc::F11,
00105     Sparc::F12, Sparc::F13, Sparc::F14, Sparc::F15,
00106     Sparc::F16, Sparc::F17, Sparc::F18, Sparc::F19,
00107     Sparc::F20, Sparc::F21, Sparc::F22, Sparc::F23,
00108     Sparc::F24, Sparc::F25, Sparc::F26, Sparc::F27,
00109     Sparc::F28, Sparc::F29, Sparc::F30, Sparc::F31 };
00110 
00111   static unsigned DoubleRegs[32] = {
00112     Sparc::D0,  Sparc::D1,  Sparc::D2,  Sparc::D3,
00113     Sparc::D4,  Sparc::D5,  Sparc::D6,  Sparc::D7,
00114     Sparc::D8,  Sparc::D7,  Sparc::D8,  Sparc::D9,
00115     Sparc::D12, Sparc::D13, Sparc::D14, Sparc::D15,
00116     Sparc::D16, Sparc::D17, Sparc::D18, Sparc::D19,
00117     Sparc::D20, Sparc::D21, Sparc::D22, Sparc::D23,
00118     Sparc::D24, Sparc::D25, Sparc::D26, Sparc::D27,
00119     Sparc::D28, Sparc::D29, Sparc::D30, Sparc::D31 };
00120 
00121   static unsigned QuadFPRegs[32] = {
00122     Sparc::Q0,  Sparc::Q1,  Sparc::Q2,  Sparc::Q3,
00123     Sparc::Q4,  Sparc::Q5,  Sparc::Q6,  Sparc::Q7,
00124     Sparc::Q8,  Sparc::Q9,  Sparc::Q10, Sparc::Q11,
00125     Sparc::Q12, Sparc::Q13, Sparc::Q14, Sparc::Q15 };
00126 
00127 
00128 /// SparcOperand - Instances of this class represent a parsed Sparc machine
00129 /// instruction.
00130 class SparcOperand : public MCParsedAsmOperand {
00131 public:
00132   enum RegisterKind {
00133     rk_None,
00134     rk_IntReg,
00135     rk_FloatReg,
00136     rk_DoubleReg,
00137     rk_QuadReg,
00138     rk_CCReg,
00139     rk_Y
00140   };
00141 private:
00142   enum KindTy {
00143     k_Token,
00144     k_Register,
00145     k_Immediate,
00146     k_MemoryReg,
00147     k_MemoryImm
00148   } Kind;
00149 
00150   SMLoc StartLoc, EndLoc;
00151 
00152   struct Token {
00153     const char *Data;
00154     unsigned Length;
00155   };
00156 
00157   struct RegOp {
00158     unsigned RegNum;
00159     RegisterKind Kind;
00160   };
00161 
00162   struct ImmOp {
00163     const MCExpr *Val;
00164   };
00165 
00166   struct MemOp {
00167     unsigned Base;
00168     unsigned OffsetReg;
00169     const MCExpr *Off;
00170   };
00171 
00172   union {
00173     struct Token Tok;
00174     struct RegOp Reg;
00175     struct ImmOp Imm;
00176     struct MemOp Mem;
00177   };
00178 public:
00179   SparcOperand(KindTy K) : MCParsedAsmOperand(), Kind(K) {}
00180 
00181   bool isToken() const override { return Kind == k_Token; }
00182   bool isReg() const override { return Kind == k_Register; }
00183   bool isImm() const override { return Kind == k_Immediate; }
00184   bool isMem() const override { return isMEMrr() || isMEMri(); }
00185   bool isMEMrr() const { return Kind == k_MemoryReg; }
00186   bool isMEMri() const { return Kind == k_MemoryImm; }
00187 
00188   bool isFloatReg() const {
00189     return (Kind == k_Register && Reg.Kind == rk_FloatReg);
00190   }
00191 
00192   bool isFloatOrDoubleReg() const {
00193     return (Kind == k_Register && (Reg.Kind == rk_FloatReg
00194                                    || Reg.Kind == rk_DoubleReg));
00195   }
00196 
00197 
00198   StringRef getToken() const {
00199     assert(Kind == k_Token && "Invalid access!");
00200     return StringRef(Tok.Data, Tok.Length);
00201   }
00202 
00203   unsigned getReg() const override {
00204     assert((Kind == k_Register) && "Invalid access!");
00205     return Reg.RegNum;
00206   }
00207 
00208   const MCExpr *getImm() const {
00209     assert((Kind == k_Immediate) && "Invalid access!");
00210     return Imm.Val;
00211   }
00212 
00213   unsigned getMemBase() const {
00214     assert((Kind == k_MemoryReg || Kind == k_MemoryImm) && "Invalid access!");
00215     return Mem.Base;
00216   }
00217 
00218   unsigned getMemOffsetReg() const {
00219     assert((Kind == k_MemoryReg) && "Invalid access!");
00220     return Mem.OffsetReg;
00221   }
00222 
00223   const MCExpr *getMemOff() const {
00224     assert((Kind == k_MemoryImm) && "Invalid access!");
00225     return Mem.Off;
00226   }
00227 
00228   /// getStartLoc - Get the location of the first token of this operand.
00229   SMLoc getStartLoc() const override {
00230     return StartLoc;
00231   }
00232   /// getEndLoc - Get the location of the last token of this operand.
00233   SMLoc getEndLoc() const override {
00234     return EndLoc;
00235   }
00236 
00237   void print(raw_ostream &OS) const override {
00238     switch (Kind) {
00239     case k_Token:     OS << "Token: " << getToken() << "\n"; break;
00240     case k_Register:  OS << "Reg: #" << getReg() << "\n"; break;
00241     case k_Immediate: OS << "Imm: " << getImm() << "\n"; break;
00242     case k_MemoryReg: OS << "Mem: " << getMemBase() << "+"
00243                          << getMemOffsetReg() << "\n"; break;
00244     case k_MemoryImm: assert(getMemOff() != nullptr);
00245       OS << "Mem: " << getMemBase()
00246          << "+" << *getMemOff()
00247          << "\n"; break;
00248     }
00249   }
00250 
00251   void addRegOperands(MCInst &Inst, unsigned N) const {
00252     assert(N == 1 && "Invalid number of operands!");
00253     Inst.addOperand(MCOperand::CreateReg(getReg()));
00254   }
00255 
00256   void addImmOperands(MCInst &Inst, unsigned N) const {
00257     assert(N == 1 && "Invalid number of operands!");
00258     const MCExpr *Expr = getImm();
00259     addExpr(Inst, Expr);
00260   }
00261 
00262   void addExpr(MCInst &Inst, const MCExpr *Expr) const{
00263     // Add as immediate when possible.  Null MCExpr = 0.
00264     if (!Expr)
00265       Inst.addOperand(MCOperand::CreateImm(0));
00266     else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr))
00267       Inst.addOperand(MCOperand::CreateImm(CE->getValue()));
00268     else
00269       Inst.addOperand(MCOperand::CreateExpr(Expr));
00270   }
00271 
00272   void addMEMrrOperands(MCInst &Inst, unsigned N) const {
00273     assert(N == 2 && "Invalid number of operands!");
00274 
00275     Inst.addOperand(MCOperand::CreateReg(getMemBase()));
00276 
00277     assert(getMemOffsetReg() != 0 && "Invalid offset");
00278     Inst.addOperand(MCOperand::CreateReg(getMemOffsetReg()));
00279   }
00280 
00281   void addMEMriOperands(MCInst &Inst, unsigned N) const {
00282     assert(N == 2 && "Invalid number of operands!");
00283 
00284     Inst.addOperand(MCOperand::CreateReg(getMemBase()));
00285 
00286     const MCExpr *Expr = getMemOff();
00287     addExpr(Inst, Expr);
00288   }
00289 
00290   static std::unique_ptr<SparcOperand> CreateToken(StringRef Str, SMLoc S) {
00291     auto Op = make_unique<SparcOperand>(k_Token);
00292     Op->Tok.Data = Str.data();
00293     Op->Tok.Length = Str.size();
00294     Op->StartLoc = S;
00295     Op->EndLoc = S;
00296     return Op;
00297   }
00298 
00299   static std::unique_ptr<SparcOperand> CreateReg(unsigned RegNum, unsigned Kind,
00300                                                  SMLoc S, SMLoc E) {
00301     auto Op = make_unique<SparcOperand>(k_Register);
00302     Op->Reg.RegNum = RegNum;
00303     Op->Reg.Kind   = (SparcOperand::RegisterKind)Kind;
00304     Op->StartLoc = S;
00305     Op->EndLoc = E;
00306     return Op;
00307   }
00308 
00309   static std::unique_ptr<SparcOperand> CreateImm(const MCExpr *Val, SMLoc S,
00310                                                  SMLoc E) {
00311     auto Op = make_unique<SparcOperand>(k_Immediate);
00312     Op->Imm.Val = Val;
00313     Op->StartLoc = S;
00314     Op->EndLoc = E;
00315     return Op;
00316   }
00317 
00318   static bool MorphToDoubleReg(SparcOperand &Op) {
00319     unsigned Reg = Op.getReg();
00320     assert(Op.Reg.Kind == rk_FloatReg);
00321     unsigned regIdx = Reg - Sparc::F0;
00322     if (regIdx % 2 || regIdx > 31)
00323       return false;
00324     Op.Reg.RegNum = DoubleRegs[regIdx / 2];
00325     Op.Reg.Kind = rk_DoubleReg;
00326     return true;
00327   }
00328 
00329   static bool MorphToQuadReg(SparcOperand &Op) {
00330     unsigned Reg = Op.getReg();
00331     unsigned regIdx = 0;
00332     switch (Op.Reg.Kind) {
00333     default: llvm_unreachable("Unexpected register kind!");
00334     case rk_FloatReg:
00335       regIdx = Reg - Sparc::F0;
00336       if (regIdx % 4 || regIdx > 31)
00337         return false;
00338       Reg = QuadFPRegs[regIdx / 4];
00339       break;
00340     case rk_DoubleReg:
00341       regIdx =  Reg - Sparc::D0;
00342       if (regIdx % 2 || regIdx > 31)
00343         return false;
00344       Reg = QuadFPRegs[regIdx / 2];
00345       break;
00346     }
00347     Op.Reg.RegNum = Reg;
00348     Op.Reg.Kind = rk_QuadReg;
00349     return true;
00350   }
00351 
00352   static std::unique_ptr<SparcOperand>
00353   MorphToMEMrr(unsigned Base, std::unique_ptr<SparcOperand> Op) {
00354     unsigned offsetReg = Op->getReg();
00355     Op->Kind = k_MemoryReg;
00356     Op->Mem.Base = Base;
00357     Op->Mem.OffsetReg = offsetReg;
00358     Op->Mem.Off = nullptr;
00359     return Op;
00360   }
00361 
00362   static std::unique_ptr<SparcOperand>
00363   CreateMEMri(unsigned Base, const MCExpr *Off, SMLoc S, SMLoc E) {
00364     auto Op = make_unique<SparcOperand>(k_MemoryImm);
00365     Op->Mem.Base = Base;
00366     Op->Mem.OffsetReg = 0;
00367     Op->Mem.Off = Off;
00368     Op->StartLoc = S;
00369     Op->EndLoc = E;
00370     return Op;
00371   }
00372 
00373   static std::unique_ptr<SparcOperand>
00374   MorphToMEMri(unsigned Base, std::unique_ptr<SparcOperand> Op) {
00375     const MCExpr *Imm  = Op->getImm();
00376     Op->Kind = k_MemoryImm;
00377     Op->Mem.Base = Base;
00378     Op->Mem.OffsetReg = 0;
00379     Op->Mem.Off = Imm;
00380     return Op;
00381   }
00382 };
00383 
00384 } // end namespace
00385 
00386 bool SparcAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
00387                                              OperandVector &Operands,
00388                                              MCStreamer &Out,
00389                                              uint64_t &ErrorInfo,
00390                                              bool MatchingInlineAsm) {
00391   MCInst Inst;
00392   SmallVector<MCInst, 8> Instructions;
00393   unsigned MatchResult = MatchInstructionImpl(Operands, Inst, ErrorInfo,
00394                                               MatchingInlineAsm);
00395   switch (MatchResult) {
00396   default:
00397     break;
00398 
00399   case Match_Success: {
00400     Inst.setLoc(IDLoc);
00401     Out.EmitInstruction(Inst, STI);
00402     return false;
00403   }
00404 
00405   case Match_MissingFeature:
00406     return Error(IDLoc,
00407                  "instruction requires a CPU feature not currently enabled");
00408 
00409   case Match_InvalidOperand: {
00410     SMLoc ErrorLoc = IDLoc;
00411     if (ErrorInfo != ~0ULL) {
00412       if (ErrorInfo >= Operands.size())
00413         return Error(IDLoc, "too few operands for instruction");
00414 
00415       ErrorLoc = ((SparcOperand &)*Operands[ErrorInfo]).getStartLoc();
00416       if (ErrorLoc == SMLoc())
00417         ErrorLoc = IDLoc;
00418     }
00419 
00420     return Error(ErrorLoc, "invalid operand for instruction");
00421   }
00422   case Match_MnemonicFail:
00423     return Error(IDLoc, "invalid instruction mnemonic");
00424   }
00425   return true;
00426 }
00427 
00428 bool SparcAsmParser::
00429 ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc)
00430 {
00431   const AsmToken &Tok = Parser.getTok();
00432   StartLoc = Tok.getLoc();
00433   EndLoc = Tok.getEndLoc();
00434   RegNo = 0;
00435   if (getLexer().getKind() != AsmToken::Percent)
00436     return false;
00437   Parser.Lex();
00438   unsigned regKind = SparcOperand::rk_None;
00439   if (matchRegisterName(Tok, RegNo, regKind)) {
00440     Parser.Lex();
00441     return false;
00442   }
00443 
00444   return Error(StartLoc, "invalid register name");
00445 }
00446 
00447 static void applyMnemonicAliases(StringRef &Mnemonic, uint64_t Features,
00448                                  unsigned VariantID);
00449 
00450 bool SparcAsmParser::ParseInstruction(ParseInstructionInfo &Info,
00451                                       StringRef Name, SMLoc NameLoc,
00452                                       OperandVector &Operands) {
00453 
00454   // First operand in MCInst is instruction mnemonic.
00455   Operands.push_back(SparcOperand::CreateToken(Name, NameLoc));
00456 
00457   // apply mnemonic aliases, if any, so that we can parse operands correctly.
00458   applyMnemonicAliases(Name, getAvailableFeatures(), 0);
00459 
00460   if (getLexer().isNot(AsmToken::EndOfStatement)) {
00461     // Read the first operand.
00462     if (getLexer().is(AsmToken::Comma)) {
00463       if (parseBranchModifiers(Operands) != MatchOperand_Success) {
00464         SMLoc Loc = getLexer().getLoc();
00465         Parser.eatToEndOfStatement();
00466         return Error(Loc, "unexpected token");
00467       }
00468     }
00469     if (parseOperand(Operands, Name) != MatchOperand_Success) {
00470       SMLoc Loc = getLexer().getLoc();
00471       Parser.eatToEndOfStatement();
00472       return Error(Loc, "unexpected token");
00473     }
00474 
00475     while (getLexer().is(AsmToken::Comma)) {
00476       Parser.Lex(); // Eat the comma.
00477       // Parse and remember the operand.
00478       if (parseOperand(Operands, Name) != MatchOperand_Success) {
00479         SMLoc Loc = getLexer().getLoc();
00480         Parser.eatToEndOfStatement();
00481         return Error(Loc, "unexpected token");
00482       }
00483     }
00484   }
00485   if (getLexer().isNot(AsmToken::EndOfStatement)) {
00486     SMLoc Loc = getLexer().getLoc();
00487     Parser.eatToEndOfStatement();
00488     return Error(Loc, "unexpected token");
00489   }
00490   Parser.Lex(); // Consume the EndOfStatement.
00491   return false;
00492 }
00493 
00494 bool SparcAsmParser::
00495 ParseDirective(AsmToken DirectiveID)
00496 {
00497   StringRef IDVal = DirectiveID.getString();
00498 
00499   if (IDVal == ".byte")
00500     return parseDirectiveWord(1, DirectiveID.getLoc());
00501 
00502   if (IDVal == ".half")
00503     return parseDirectiveWord(2, DirectiveID.getLoc());
00504 
00505   if (IDVal == ".word")
00506     return parseDirectiveWord(4, DirectiveID.getLoc());
00507 
00508   if (IDVal == ".nword")
00509     return parseDirectiveWord(is64Bit() ? 8 : 4, DirectiveID.getLoc());
00510 
00511   if (is64Bit() && IDVal == ".xword")
00512     return parseDirectiveWord(8, DirectiveID.getLoc());
00513 
00514   if (IDVal == ".register") {
00515     // For now, ignore .register directive.
00516     Parser.eatToEndOfStatement();
00517     return false;
00518   }
00519 
00520   // Let the MC layer to handle other directives.
00521   return true;
00522 }
00523 
00524 bool SparcAsmParser:: parseDirectiveWord(unsigned Size, SMLoc L) {
00525   if (getLexer().isNot(AsmToken::EndOfStatement)) {
00526     for (;;) {
00527       const MCExpr *Value;
00528       if (getParser().parseExpression(Value))
00529         return true;
00530 
00531       getParser().getStreamer().EmitValue(Value, Size);
00532 
00533       if (getLexer().is(AsmToken::EndOfStatement))
00534         break;
00535 
00536       // FIXME: Improve diagnostic.
00537       if (getLexer().isNot(AsmToken::Comma))
00538         return Error(L, "unexpected token in directive");
00539       Parser.Lex();
00540     }
00541   }
00542   Parser.Lex();
00543   return false;
00544 }
00545 
00546 SparcAsmParser::OperandMatchResultTy
00547 SparcAsmParser::parseMEMOperand(OperandVector &Operands) {
00548 
00549   SMLoc S, E;
00550   unsigned BaseReg = 0;
00551 
00552   if (ParseRegister(BaseReg, S, E)) {
00553     return MatchOperand_NoMatch;
00554   }
00555 
00556   switch (getLexer().getKind()) {
00557   default: return MatchOperand_NoMatch;
00558 
00559   case AsmToken::Comma:
00560   case AsmToken::RBrac:
00561   case AsmToken::EndOfStatement:
00562     Operands.push_back(SparcOperand::CreateMEMri(BaseReg, nullptr, S, E));
00563     return MatchOperand_Success;
00564 
00565   case AsmToken:: Plus:
00566     Parser.Lex(); // Eat the '+'
00567     break;
00568   case AsmToken::Minus:
00569     break;
00570   }
00571 
00572   std::unique_ptr<SparcOperand> Offset;
00573   OperandMatchResultTy ResTy = parseSparcAsmOperand(Offset);
00574   if (ResTy != MatchOperand_Success || !Offset)
00575     return MatchOperand_NoMatch;
00576 
00577   Operands.push_back(
00578       Offset->isImm() ? SparcOperand::MorphToMEMri(BaseReg, std::move(Offset))
00579                       : SparcOperand::MorphToMEMrr(BaseReg, std::move(Offset)));
00580 
00581   return MatchOperand_Success;
00582 }
00583 
00584 SparcAsmParser::OperandMatchResultTy
00585 SparcAsmParser::parseOperand(OperandVector &Operands, StringRef Mnemonic) {
00586 
00587   OperandMatchResultTy ResTy = MatchOperandParserImpl(Operands, Mnemonic);
00588 
00589   // If there wasn't a custom match, try the generic matcher below. Otherwise,
00590   // there was a match, but an error occurred, in which case, just return that
00591   // the operand parsing failed.
00592   if (ResTy == MatchOperand_Success || ResTy == MatchOperand_ParseFail)
00593     return ResTy;
00594 
00595   if (getLexer().is(AsmToken::LBrac)) {
00596     // Memory operand
00597     Operands.push_back(SparcOperand::CreateToken("[",
00598                                                  Parser.getTok().getLoc()));
00599     Parser.Lex(); // Eat the [
00600 
00601     if (Mnemonic == "cas" || Mnemonic == "casx") {
00602       SMLoc S = Parser.getTok().getLoc();
00603       if (getLexer().getKind() != AsmToken::Percent)
00604         return MatchOperand_NoMatch;
00605       Parser.Lex(); // eat %
00606 
00607       unsigned RegNo, RegKind;
00608       if (!matchRegisterName(Parser.getTok(), RegNo, RegKind))
00609         return MatchOperand_NoMatch;
00610 
00611       Parser.Lex(); // Eat the identifier token.
00612       SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer()-1);
00613       Operands.push_back(SparcOperand::CreateReg(RegNo, RegKind, S, E));
00614       ResTy = MatchOperand_Success;
00615     } else {
00616       ResTy = parseMEMOperand(Operands);
00617     }
00618 
00619     if (ResTy != MatchOperand_Success)
00620       return ResTy;
00621 
00622     if (!getLexer().is(AsmToken::RBrac))
00623       return MatchOperand_ParseFail;
00624 
00625     Operands.push_back(SparcOperand::CreateToken("]",
00626                                                  Parser.getTok().getLoc()));
00627     Parser.Lex(); // Eat the ]
00628     return MatchOperand_Success;
00629   }
00630 
00631   std::unique_ptr<SparcOperand> Op;
00632 
00633   ResTy = parseSparcAsmOperand(Op, (Mnemonic == "call"));
00634   if (ResTy != MatchOperand_Success || !Op)
00635     return MatchOperand_ParseFail;
00636 
00637   // Push the parsed operand into the list of operands
00638   Operands.push_back(std::move(Op));
00639 
00640   return MatchOperand_Success;
00641 }
00642 
00643 SparcAsmParser::OperandMatchResultTy
00644 SparcAsmParser::parseSparcAsmOperand(std::unique_ptr<SparcOperand> &Op,
00645                                      bool isCall) {
00646 
00647   SMLoc S = Parser.getTok().getLoc();
00648   SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
00649   const MCExpr *EVal;
00650 
00651   Op = nullptr;
00652   switch (getLexer().getKind()) {
00653   default:  break;
00654 
00655   case AsmToken::Percent:
00656     Parser.Lex(); // Eat the '%'.
00657     unsigned RegNo;
00658     unsigned RegKind;
00659     if (matchRegisterName(Parser.getTok(), RegNo, RegKind)) {
00660       StringRef name = Parser.getTok().getString();
00661       Parser.Lex(); // Eat the identifier token.
00662       E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
00663       switch (RegNo) {
00664       default:
00665         Op = SparcOperand::CreateReg(RegNo, RegKind, S, E);
00666         break;
00667       case Sparc::Y:
00668         Op = SparcOperand::CreateToken("%y", S);
00669         break;
00670 
00671       case Sparc::ICC:
00672         if (name == "xcc")
00673           Op = SparcOperand::CreateToken("%xcc", S);
00674         else
00675           Op = SparcOperand::CreateToken("%icc", S);
00676         break;
00677       }
00678       break;
00679     }
00680     if (matchSparcAsmModifiers(EVal, E)) {
00681       E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
00682       Op = SparcOperand::CreateImm(EVal, S, E);
00683     }
00684     break;
00685 
00686   case AsmToken::Minus:
00687   case AsmToken::Integer:
00688     if (!getParser().parseExpression(EVal, E))
00689       Op = SparcOperand::CreateImm(EVal, S, E);
00690     break;
00691 
00692   case AsmToken::Identifier: {
00693     StringRef Identifier;
00694     if (!getParser().parseIdentifier(Identifier)) {
00695       E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
00696       MCSymbol *Sym = getContext().GetOrCreateSymbol(Identifier);
00697 
00698       const MCExpr *Res = MCSymbolRefExpr::Create(Sym, MCSymbolRefExpr::VK_None,
00699                                                   getContext());
00700       if (isCall &&
00701           getContext().getObjectFileInfo()->getRelocM() == Reloc::PIC_)
00702         Res = SparcMCExpr::Create(SparcMCExpr::VK_Sparc_WPLT30, Res,
00703                                   getContext());
00704       Op = SparcOperand::CreateImm(Res, S, E);
00705     }
00706     break;
00707   }
00708   }
00709   return (Op) ? MatchOperand_Success : MatchOperand_ParseFail;
00710 }
00711 
00712 SparcAsmParser::OperandMatchResultTy
00713 SparcAsmParser::parseBranchModifiers(OperandVector &Operands) {
00714 
00715   // parse (,a|,pn|,pt)+
00716 
00717   while (getLexer().is(AsmToken::Comma)) {
00718 
00719     Parser.Lex(); // Eat the comma
00720 
00721     if (!getLexer().is(AsmToken::Identifier))
00722       return MatchOperand_ParseFail;
00723     StringRef modName = Parser.getTok().getString();
00724     if (modName == "a" || modName == "pn" || modName == "pt") {
00725       Operands.push_back(SparcOperand::CreateToken(modName,
00726                                                    Parser.getTok().getLoc()));
00727       Parser.Lex(); // eat the identifier.
00728     }
00729   }
00730   return MatchOperand_Success;
00731 }
00732 
00733 bool SparcAsmParser::matchRegisterName(const AsmToken &Tok,
00734                                        unsigned &RegNo,
00735                                        unsigned &RegKind)
00736 {
00737   int64_t intVal = 0;
00738   RegNo = 0;
00739   RegKind = SparcOperand::rk_None;
00740   if (Tok.is(AsmToken::Identifier)) {
00741     StringRef name = Tok.getString();
00742 
00743     // %fp
00744     if (name.equals("fp")) {
00745       RegNo = Sparc::I6;
00746       RegKind = SparcOperand::rk_IntReg;
00747       return true;
00748     }
00749     // %sp
00750     if (name.equals("sp")) {
00751       RegNo = Sparc::O6;
00752       RegKind = SparcOperand::rk_IntReg;
00753       return true;
00754     }
00755 
00756     if (name.equals("y")) {
00757       RegNo = Sparc::Y;
00758       RegKind = SparcOperand::rk_Y;
00759       return true;
00760     }
00761 
00762     if (name.equals("icc")) {
00763       RegNo = Sparc::ICC;
00764       RegKind = SparcOperand::rk_CCReg;
00765       return true;
00766     }
00767 
00768     if (name.equals("xcc")) {
00769       // FIXME:: check 64bit.
00770       RegNo = Sparc::ICC;
00771       RegKind = SparcOperand::rk_CCReg;
00772       return true;
00773     }
00774 
00775     // %fcc0 - %fcc3
00776     if (name.substr(0, 3).equals_lower("fcc")
00777         && !name.substr(3).getAsInteger(10, intVal)
00778         && intVal < 4) {
00779       // FIXME: check 64bit and  handle %fcc1 - %fcc3
00780       RegNo = Sparc::FCC0 + intVal;
00781       RegKind = SparcOperand::rk_CCReg;
00782       return true;
00783     }
00784 
00785     // %g0 - %g7
00786     if (name.substr(0, 1).equals_lower("g")
00787         && !name.substr(1).getAsInteger(10, intVal)
00788         && intVal < 8) {
00789       RegNo = IntRegs[intVal];
00790       RegKind = SparcOperand::rk_IntReg;
00791       return true;
00792     }
00793     // %o0 - %o7
00794     if (name.substr(0, 1).equals_lower("o")
00795         && !name.substr(1).getAsInteger(10, intVal)
00796         && intVal < 8) {
00797       RegNo = IntRegs[8 + intVal];
00798       RegKind = SparcOperand::rk_IntReg;
00799       return true;
00800     }
00801     if (name.substr(0, 1).equals_lower("l")
00802         && !name.substr(1).getAsInteger(10, intVal)
00803         && intVal < 8) {
00804       RegNo = IntRegs[16 + intVal];
00805       RegKind = SparcOperand::rk_IntReg;
00806       return true;
00807     }
00808     if (name.substr(0, 1).equals_lower("i")
00809         && !name.substr(1).getAsInteger(10, intVal)
00810         && intVal < 8) {
00811       RegNo = IntRegs[24 + intVal];
00812       RegKind = SparcOperand::rk_IntReg;
00813       return true;
00814     }
00815     // %f0 - %f31
00816     if (name.substr(0, 1).equals_lower("f")
00817         && !name.substr(1, 2).getAsInteger(10, intVal) && intVal < 32) {
00818       RegNo = FloatRegs[intVal];
00819       RegKind = SparcOperand::rk_FloatReg;
00820       return true;
00821     }
00822     // %f32 - %f62
00823     if (name.substr(0, 1).equals_lower("f")
00824         && !name.substr(1, 2).getAsInteger(10, intVal)
00825         && intVal >= 32 && intVal <= 62 && (intVal % 2 == 0)) {
00826       // FIXME: Check V9
00827       RegNo = DoubleRegs[intVal/2];
00828       RegKind = SparcOperand::rk_DoubleReg;
00829       return true;
00830     }
00831 
00832     // %r0 - %r31
00833     if (name.substr(0, 1).equals_lower("r")
00834         && !name.substr(1, 2).getAsInteger(10, intVal) && intVal < 31) {
00835       RegNo = IntRegs[intVal];
00836       RegKind = SparcOperand::rk_IntReg;
00837       return true;
00838     }
00839   }
00840   return false;
00841 }
00842 
00843 static bool hasGOTReference(const MCExpr *Expr) {
00844   switch (Expr->getKind()) {
00845   case MCExpr::Target:
00846     if (const SparcMCExpr *SE = dyn_cast<SparcMCExpr>(Expr))
00847       return hasGOTReference(SE->getSubExpr());
00848     break;
00849 
00850   case MCExpr::Constant:
00851     break;
00852 
00853   case MCExpr::Binary: {
00854     const MCBinaryExpr *BE = cast<MCBinaryExpr>(Expr);
00855     return hasGOTReference(BE->getLHS()) || hasGOTReference(BE->getRHS());
00856   }
00857 
00858   case MCExpr::SymbolRef: {
00859     const MCSymbolRefExpr &SymRef = *cast<MCSymbolRefExpr>(Expr);
00860     return (SymRef.getSymbol().getName() == "_GLOBAL_OFFSET_TABLE_");
00861   }
00862 
00863   case MCExpr::Unary:
00864     return hasGOTReference(cast<MCUnaryExpr>(Expr)->getSubExpr());
00865   }
00866   return false;
00867 }
00868 
00869 bool SparcAsmParser::matchSparcAsmModifiers(const MCExpr *&EVal,
00870                                             SMLoc &EndLoc)
00871 {
00872   AsmToken Tok = Parser.getTok();
00873   if (!Tok.is(AsmToken::Identifier))
00874     return false;
00875 
00876   StringRef name = Tok.getString();
00877 
00878   SparcMCExpr::VariantKind VK = SparcMCExpr::parseVariantKind(name);
00879 
00880   if (VK == SparcMCExpr::VK_Sparc_None)
00881     return false;
00882 
00883   Parser.Lex(); // Eat the identifier.
00884   if (Parser.getTok().getKind() != AsmToken::LParen)
00885     return false;
00886 
00887   Parser.Lex(); // Eat the LParen token.
00888   const MCExpr *subExpr;
00889   if (Parser.parseParenExpression(subExpr, EndLoc))
00890     return false;
00891 
00892   bool isPIC = getContext().getObjectFileInfo()->getRelocM() == Reloc::PIC_;
00893 
00894   switch(VK) {
00895   default: break;
00896   case SparcMCExpr::VK_Sparc_LO:
00897     VK =  (hasGOTReference(subExpr)
00898            ? SparcMCExpr::VK_Sparc_PC10
00899            : (isPIC ? SparcMCExpr::VK_Sparc_GOT10 : VK));
00900     break;
00901   case SparcMCExpr::VK_Sparc_HI:
00902     VK =  (hasGOTReference(subExpr)
00903            ? SparcMCExpr::VK_Sparc_PC22
00904            : (isPIC ? SparcMCExpr::VK_Sparc_GOT22 : VK));
00905     break;
00906   }
00907 
00908   EVal = SparcMCExpr::Create(VK, subExpr, getContext());
00909   return true;
00910 }
00911 
00912 
00913 extern "C" void LLVMInitializeSparcAsmParser() {
00914   RegisterMCAsmParser<SparcAsmParser> A(TheSparcTarget);
00915   RegisterMCAsmParser<SparcAsmParser> B(TheSparcV9Target);
00916 }
00917 
00918 #define GET_REGISTER_MATCHER
00919 #define GET_MATCHER_IMPLEMENTATION
00920 #include "SparcGenAsmMatcher.inc"
00921 
00922 unsigned SparcAsmParser::validateTargetOperandClass(MCParsedAsmOperand &GOp,
00923                                                     unsigned Kind) {
00924   SparcOperand &Op = (SparcOperand &)GOp;
00925   if (Op.isFloatOrDoubleReg()) {
00926     switch (Kind) {
00927     default: break;
00928     case MCK_DFPRegs:
00929       if (!Op.isFloatReg() || SparcOperand::MorphToDoubleReg(Op))
00930         return MCTargetAsmParser::Match_Success;
00931       break;
00932     case MCK_QFPRegs:
00933       if (SparcOperand::MorphToQuadReg(Op))
00934         return MCTargetAsmParser::Match_Success;
00935       break;
00936     }
00937   }
00938   return Match_InvalidOperand;
00939 }