• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //===-- SparcAsmParser.cpp - Parse Sparc 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/SparcMCExpr.h"
11 #include "MCTargetDesc/SparcMCTargetDesc.h"
12 #include "llvm/ADT/STLExtras.h"
13 #include "llvm/MC/MCContext.h"
14 #include "llvm/MC/MCInst.h"
15 #include "llvm/MC/MCObjectFileInfo.h"
16 #include "llvm/MC/MCParser/MCParsedAsmOperand.h"
17 #include "llvm/MC/MCParser/MCTargetAsmParser.h"
18 #include "llvm/MC/MCRegisterInfo.h"
19 #include "llvm/MC/MCStreamer.h"
20 #include "llvm/MC/MCSubtargetInfo.h"
21 #include "llvm/MC/MCSymbol.h"
22 #include "llvm/Support/TargetRegistry.h"
23 
24 using namespace llvm;
25 
26 // The generated AsmMatcher SparcGenAsmMatcher uses "Sparc" as the target
27 // namespace. But SPARC backend uses "SP" as its namespace.
28 namespace llvm {
29   namespace Sparc {
30     using namespace SP;
31   }
32 }
33 
34 namespace {
35 class SparcOperand;
36 class SparcAsmParser : public MCTargetAsmParser {
37 
38   MCAsmParser &Parser;
39 
40   /// @name Auto-generated Match Functions
41   /// {
42 
43 #define GET_ASSEMBLER_HEADER
44 #include "SparcGenAsmMatcher.inc"
45 
46   /// }
47 
48   // public interface of the MCTargetAsmParser.
49   bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
50                                OperandVector &Operands, MCStreamer &Out,
51                                uint64_t &ErrorInfo,
52                                bool MatchingInlineAsm) override;
53   bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc) override;
54   bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name,
55                         SMLoc NameLoc, OperandVector &Operands) override;
56   bool ParseDirective(AsmToken DirectiveID) override;
57 
58   unsigned validateTargetOperandClass(MCParsedAsmOperand &Op,
59                                       unsigned Kind) override;
60 
61   // Custom parse functions for Sparc specific operands.
62   OperandMatchResultTy parseMEMOperand(OperandVector &Operands);
63 
64   OperandMatchResultTy parseOperand(OperandVector &Operands, StringRef Name);
65 
66   OperandMatchResultTy
67   parseSparcAsmOperand(std::unique_ptr<SparcOperand> &Operand,
68                        bool isCall = false);
69 
70   OperandMatchResultTy parseBranchModifiers(OperandVector &Operands);
71 
72   // Helper function for dealing with %lo / %hi in PIC mode.
73   const SparcMCExpr *adjustPICRelocation(SparcMCExpr::VariantKind VK,
74                                          const MCExpr *subExpr);
75 
76   // returns true if Tok is matched to a register and returns register in RegNo.
77   bool matchRegisterName(const AsmToken &Tok, unsigned &RegNo,
78                          unsigned &RegKind);
79 
80   bool matchSparcAsmModifiers(const MCExpr *&EVal, SMLoc &EndLoc);
81   bool parseDirectiveWord(unsigned Size, SMLoc L);
82 
is64Bit() const83   bool is64Bit() const {
84     return getSTI().getTargetTriple().getArch() == Triple::sparcv9;
85   }
86 
87   void expandSET(MCInst &Inst, SMLoc IDLoc,
88                  SmallVectorImpl<MCInst> &Instructions);
89 
90 public:
SparcAsmParser(const MCSubtargetInfo & sti,MCAsmParser & parser,const MCInstrInfo & MII,const MCTargetOptions & Options)91   SparcAsmParser(const MCSubtargetInfo &sti, MCAsmParser &parser,
92                 const MCInstrInfo &MII,
93                 const MCTargetOptions &Options)
94       : MCTargetAsmParser(Options, sti), Parser(parser) {
95     // Initialize the set of available features.
96     setAvailableFeatures(ComputeAvailableFeatures(getSTI().getFeatureBits()));
97   }
98 
99 };
100 
101   static const MCPhysReg IntRegs[32] = {
102     Sparc::G0, Sparc::G1, Sparc::G2, Sparc::G3,
103     Sparc::G4, Sparc::G5, Sparc::G6, Sparc::G7,
104     Sparc::O0, Sparc::O1, Sparc::O2, Sparc::O3,
105     Sparc::O4, Sparc::O5, Sparc::O6, Sparc::O7,
106     Sparc::L0, Sparc::L1, Sparc::L2, Sparc::L3,
107     Sparc::L4, Sparc::L5, Sparc::L6, Sparc::L7,
108     Sparc::I0, Sparc::I1, Sparc::I2, Sparc::I3,
109     Sparc::I4, Sparc::I5, Sparc::I6, Sparc::I7 };
110 
111   static const MCPhysReg FloatRegs[32] = {
112     Sparc::F0,  Sparc::F1,  Sparc::F2,  Sparc::F3,
113     Sparc::F4,  Sparc::F5,  Sparc::F6,  Sparc::F7,
114     Sparc::F8,  Sparc::F9,  Sparc::F10, Sparc::F11,
115     Sparc::F12, Sparc::F13, Sparc::F14, Sparc::F15,
116     Sparc::F16, Sparc::F17, Sparc::F18, Sparc::F19,
117     Sparc::F20, Sparc::F21, Sparc::F22, Sparc::F23,
118     Sparc::F24, Sparc::F25, Sparc::F26, Sparc::F27,
119     Sparc::F28, Sparc::F29, Sparc::F30, Sparc::F31 };
120 
121   static const MCPhysReg DoubleRegs[32] = {
122     Sparc::D0,  Sparc::D1,  Sparc::D2,  Sparc::D3,
123     Sparc::D4,  Sparc::D5,  Sparc::D6,  Sparc::D7,
124     Sparc::D8,  Sparc::D7,  Sparc::D8,  Sparc::D9,
125     Sparc::D12, Sparc::D13, Sparc::D14, Sparc::D15,
126     Sparc::D16, Sparc::D17, Sparc::D18, Sparc::D19,
127     Sparc::D20, Sparc::D21, Sparc::D22, Sparc::D23,
128     Sparc::D24, Sparc::D25, Sparc::D26, Sparc::D27,
129     Sparc::D28, Sparc::D29, Sparc::D30, Sparc::D31 };
130 
131   static const MCPhysReg QuadFPRegs[32] = {
132     Sparc::Q0,  Sparc::Q1,  Sparc::Q2,  Sparc::Q3,
133     Sparc::Q4,  Sparc::Q5,  Sparc::Q6,  Sparc::Q7,
134     Sparc::Q8,  Sparc::Q9,  Sparc::Q10, Sparc::Q11,
135     Sparc::Q12, Sparc::Q13, Sparc::Q14, Sparc::Q15 };
136 
137   static const MCPhysReg ASRRegs[32] = {
138     SP::Y,     SP::ASR1,  SP::ASR2,  SP::ASR3,
139     SP::ASR4,  SP::ASR5,  SP::ASR6, SP::ASR7,
140     SP::ASR8,  SP::ASR9,  SP::ASR10, SP::ASR11,
141     SP::ASR12, SP::ASR13, SP::ASR14, SP::ASR15,
142     SP::ASR16, SP::ASR17, SP::ASR18, SP::ASR19,
143     SP::ASR20, SP::ASR21, SP::ASR22, SP::ASR23,
144     SP::ASR24, SP::ASR25, SP::ASR26, SP::ASR27,
145     SP::ASR28, SP::ASR29, SP::ASR30, SP::ASR31};
146 
147   static const MCPhysReg IntPairRegs[] = {
148     Sparc::G0_G1, Sparc::G2_G3, Sparc::G4_G5, Sparc::G6_G7,
149     Sparc::O0_O1, Sparc::O2_O3, Sparc::O4_O5, Sparc::O6_O7,
150     Sparc::L0_L1, Sparc::L2_L3, Sparc::L4_L5, Sparc::L6_L7,
151     Sparc::I0_I1, Sparc::I2_I3, Sparc::I4_I5, Sparc::I6_I7};
152 
153   static const MCPhysReg CoprocRegs[32] = {
154     Sparc::C0,  Sparc::C1,  Sparc::C2,  Sparc::C3,
155     Sparc::C4,  Sparc::C5,  Sparc::C6,  Sparc::C7,
156     Sparc::C8,  Sparc::C9,  Sparc::C10, Sparc::C11,
157     Sparc::C12, Sparc::C13, Sparc::C14, Sparc::C15,
158     Sparc::C16, Sparc::C17, Sparc::C18, Sparc::C19,
159     Sparc::C20, Sparc::C21, Sparc::C22, Sparc::C23,
160     Sparc::C24, Sparc::C25, Sparc::C26, Sparc::C27,
161     Sparc::C28, Sparc::C29, Sparc::C30, Sparc::C31 };
162 
163   static const MCPhysReg CoprocPairRegs[] = {
164     Sparc::C0_C1,   Sparc::C2_C3,   Sparc::C4_C5,   Sparc::C6_C7,
165     Sparc::C8_C9,   Sparc::C10_C11, Sparc::C12_C13, Sparc::C14_C15,
166     Sparc::C16_C17, Sparc::C18_C19, Sparc::C20_C21, Sparc::C22_C23,
167     Sparc::C24_C25, Sparc::C26_C27, Sparc::C28_C29, Sparc::C30_C31};
168 
169 /// SparcOperand - Instances of this class represent a parsed Sparc machine
170 /// instruction.
171 class SparcOperand : public MCParsedAsmOperand {
172 public:
173   enum RegisterKind {
174     rk_None,
175     rk_IntReg,
176     rk_IntPairReg,
177     rk_FloatReg,
178     rk_DoubleReg,
179     rk_QuadReg,
180     rk_CoprocReg,
181     rk_CoprocPairReg,
182     rk_Special,
183   };
184 
185 private:
186   enum KindTy {
187     k_Token,
188     k_Register,
189     k_Immediate,
190     k_MemoryReg,
191     k_MemoryImm
192   } Kind;
193 
194   SMLoc StartLoc, EndLoc;
195 
196   struct Token {
197     const char *Data;
198     unsigned Length;
199   };
200 
201   struct RegOp {
202     unsigned RegNum;
203     RegisterKind Kind;
204   };
205 
206   struct ImmOp {
207     const MCExpr *Val;
208   };
209 
210   struct MemOp {
211     unsigned Base;
212     unsigned OffsetReg;
213     const MCExpr *Off;
214   };
215 
216   union {
217     struct Token Tok;
218     struct RegOp Reg;
219     struct ImmOp Imm;
220     struct MemOp Mem;
221   };
222 public:
SparcOperand(KindTy K)223   SparcOperand(KindTy K) : MCParsedAsmOperand(), Kind(K) {}
224 
isToken() const225   bool isToken() const override { return Kind == k_Token; }
isReg() const226   bool isReg() const override { return Kind == k_Register; }
isImm() const227   bool isImm() const override { return Kind == k_Immediate; }
isMem() const228   bool isMem() const override { return isMEMrr() || isMEMri(); }
isMEMrr() const229   bool isMEMrr() const { return Kind == k_MemoryReg; }
isMEMri() const230   bool isMEMri() const { return Kind == k_MemoryImm; }
231 
isIntReg() const232   bool isIntReg() const {
233     return (Kind == k_Register && Reg.Kind == rk_IntReg);
234   }
235 
isFloatReg() const236   bool isFloatReg() const {
237     return (Kind == k_Register && Reg.Kind == rk_FloatReg);
238   }
239 
isFloatOrDoubleReg() const240   bool isFloatOrDoubleReg() const {
241     return (Kind == k_Register && (Reg.Kind == rk_FloatReg
242                                    || Reg.Kind == rk_DoubleReg));
243   }
244 
isCoprocReg() const245   bool isCoprocReg() const {
246     return (Kind == k_Register && Reg.Kind == rk_CoprocReg);
247   }
248 
getToken() const249   StringRef getToken() const {
250     assert(Kind == k_Token && "Invalid access!");
251     return StringRef(Tok.Data, Tok.Length);
252   }
253 
getReg() const254   unsigned getReg() const override {
255     assert((Kind == k_Register) && "Invalid access!");
256     return Reg.RegNum;
257   }
258 
getImm() const259   const MCExpr *getImm() const {
260     assert((Kind == k_Immediate) && "Invalid access!");
261     return Imm.Val;
262   }
263 
getMemBase() const264   unsigned getMemBase() const {
265     assert((Kind == k_MemoryReg || Kind == k_MemoryImm) && "Invalid access!");
266     return Mem.Base;
267   }
268 
getMemOffsetReg() const269   unsigned getMemOffsetReg() const {
270     assert((Kind == k_MemoryReg) && "Invalid access!");
271     return Mem.OffsetReg;
272   }
273 
getMemOff() const274   const MCExpr *getMemOff() const {
275     assert((Kind == k_MemoryImm) && "Invalid access!");
276     return Mem.Off;
277   }
278 
279   /// getStartLoc - Get the location of the first token of this operand.
getStartLoc() const280   SMLoc getStartLoc() const override {
281     return StartLoc;
282   }
283   /// getEndLoc - Get the location of the last token of this operand.
getEndLoc() const284   SMLoc getEndLoc() const override {
285     return EndLoc;
286   }
287 
print(raw_ostream & OS) const288   void print(raw_ostream &OS) const override {
289     switch (Kind) {
290     case k_Token:     OS << "Token: " << getToken() << "\n"; break;
291     case k_Register:  OS << "Reg: #" << getReg() << "\n"; break;
292     case k_Immediate: OS << "Imm: " << getImm() << "\n"; break;
293     case k_MemoryReg: OS << "Mem: " << getMemBase() << "+"
294                          << getMemOffsetReg() << "\n"; break;
295     case k_MemoryImm: assert(getMemOff() != nullptr);
296       OS << "Mem: " << getMemBase()
297          << "+" << *getMemOff()
298          << "\n"; break;
299     }
300   }
301 
addRegOperands(MCInst & Inst,unsigned N) const302   void addRegOperands(MCInst &Inst, unsigned N) const {
303     assert(N == 1 && "Invalid number of operands!");
304     Inst.addOperand(MCOperand::createReg(getReg()));
305   }
306 
addImmOperands(MCInst & Inst,unsigned N) const307   void addImmOperands(MCInst &Inst, unsigned N) const {
308     assert(N == 1 && "Invalid number of operands!");
309     const MCExpr *Expr = getImm();
310     addExpr(Inst, Expr);
311   }
312 
addExpr(MCInst & Inst,const MCExpr * Expr) const313   void addExpr(MCInst &Inst, const MCExpr *Expr) const{
314     // Add as immediate when possible.  Null MCExpr = 0.
315     if (!Expr)
316       Inst.addOperand(MCOperand::createImm(0));
317     else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr))
318       Inst.addOperand(MCOperand::createImm(CE->getValue()));
319     else
320       Inst.addOperand(MCOperand::createExpr(Expr));
321   }
322 
addMEMrrOperands(MCInst & Inst,unsigned N) const323   void addMEMrrOperands(MCInst &Inst, unsigned N) const {
324     assert(N == 2 && "Invalid number of operands!");
325 
326     Inst.addOperand(MCOperand::createReg(getMemBase()));
327 
328     assert(getMemOffsetReg() != 0 && "Invalid offset");
329     Inst.addOperand(MCOperand::createReg(getMemOffsetReg()));
330   }
331 
addMEMriOperands(MCInst & Inst,unsigned N) const332   void addMEMriOperands(MCInst &Inst, unsigned N) const {
333     assert(N == 2 && "Invalid number of operands!");
334 
335     Inst.addOperand(MCOperand::createReg(getMemBase()));
336 
337     const MCExpr *Expr = getMemOff();
338     addExpr(Inst, Expr);
339   }
340 
CreateToken(StringRef Str,SMLoc S)341   static std::unique_ptr<SparcOperand> CreateToken(StringRef Str, SMLoc S) {
342     auto Op = make_unique<SparcOperand>(k_Token);
343     Op->Tok.Data = Str.data();
344     Op->Tok.Length = Str.size();
345     Op->StartLoc = S;
346     Op->EndLoc = S;
347     return Op;
348   }
349 
CreateReg(unsigned RegNum,unsigned Kind,SMLoc S,SMLoc E)350   static std::unique_ptr<SparcOperand> CreateReg(unsigned RegNum, unsigned Kind,
351                                                  SMLoc S, SMLoc E) {
352     auto Op = make_unique<SparcOperand>(k_Register);
353     Op->Reg.RegNum = RegNum;
354     Op->Reg.Kind   = (SparcOperand::RegisterKind)Kind;
355     Op->StartLoc = S;
356     Op->EndLoc = E;
357     return Op;
358   }
359 
CreateImm(const MCExpr * Val,SMLoc S,SMLoc E)360   static std::unique_ptr<SparcOperand> CreateImm(const MCExpr *Val, SMLoc S,
361                                                  SMLoc E) {
362     auto Op = make_unique<SparcOperand>(k_Immediate);
363     Op->Imm.Val = Val;
364     Op->StartLoc = S;
365     Op->EndLoc = E;
366     return Op;
367   }
368 
MorphToIntPairReg(SparcOperand & Op)369   static bool MorphToIntPairReg(SparcOperand &Op) {
370     unsigned Reg = Op.getReg();
371     assert(Op.Reg.Kind == rk_IntReg);
372     unsigned regIdx = 32;
373     if (Reg >= Sparc::G0 && Reg <= Sparc::G7)
374       regIdx = Reg - Sparc::G0;
375     else if (Reg >= Sparc::O0 && Reg <= Sparc::O7)
376       regIdx = Reg - Sparc::O0 + 8;
377     else if (Reg >= Sparc::L0 && Reg <= Sparc::L7)
378       regIdx = Reg - Sparc::L0 + 16;
379     else if (Reg >= Sparc::I0 && Reg <= Sparc::I7)
380       regIdx = Reg - Sparc::I0 + 24;
381     if (regIdx % 2 || regIdx > 31)
382       return false;
383     Op.Reg.RegNum = IntPairRegs[regIdx / 2];
384     Op.Reg.Kind = rk_IntPairReg;
385     return true;
386   }
387 
MorphToDoubleReg(SparcOperand & Op)388   static bool MorphToDoubleReg(SparcOperand &Op) {
389     unsigned Reg = Op.getReg();
390     assert(Op.Reg.Kind == rk_FloatReg);
391     unsigned regIdx = Reg - Sparc::F0;
392     if (regIdx % 2 || regIdx > 31)
393       return false;
394     Op.Reg.RegNum = DoubleRegs[regIdx / 2];
395     Op.Reg.Kind = rk_DoubleReg;
396     return true;
397   }
398 
MorphToQuadReg(SparcOperand & Op)399   static bool MorphToQuadReg(SparcOperand &Op) {
400     unsigned Reg = Op.getReg();
401     unsigned regIdx = 0;
402     switch (Op.Reg.Kind) {
403     default: llvm_unreachable("Unexpected register kind!");
404     case rk_FloatReg:
405       regIdx = Reg - Sparc::F0;
406       if (regIdx % 4 || regIdx > 31)
407         return false;
408       Reg = QuadFPRegs[regIdx / 4];
409       break;
410     case rk_DoubleReg:
411       regIdx =  Reg - Sparc::D0;
412       if (regIdx % 2 || regIdx > 31)
413         return false;
414       Reg = QuadFPRegs[regIdx / 2];
415       break;
416     }
417     Op.Reg.RegNum = Reg;
418     Op.Reg.Kind = rk_QuadReg;
419     return true;
420   }
421 
MorphToCoprocPairReg(SparcOperand & Op)422   static bool MorphToCoprocPairReg(SparcOperand &Op) {
423     unsigned Reg = Op.getReg();
424     assert(Op.Reg.Kind == rk_CoprocReg);
425     unsigned regIdx = 32;
426     if (Reg >= Sparc::C0 && Reg <= Sparc::C31)
427       regIdx = Reg - Sparc::C0;
428     if (regIdx % 2 || regIdx > 31)
429       return false;
430     Op.Reg.RegNum = CoprocPairRegs[regIdx / 2];
431     Op.Reg.Kind = rk_CoprocPairReg;
432     return true;
433   }
434 
435   static std::unique_ptr<SparcOperand>
MorphToMEMrr(unsigned Base,std::unique_ptr<SparcOperand> Op)436   MorphToMEMrr(unsigned Base, std::unique_ptr<SparcOperand> Op) {
437     unsigned offsetReg = Op->getReg();
438     Op->Kind = k_MemoryReg;
439     Op->Mem.Base = Base;
440     Op->Mem.OffsetReg = offsetReg;
441     Op->Mem.Off = nullptr;
442     return Op;
443   }
444 
445   static std::unique_ptr<SparcOperand>
CreateMEMr(unsigned Base,SMLoc S,SMLoc E)446   CreateMEMr(unsigned Base, SMLoc S, SMLoc E) {
447     auto Op = make_unique<SparcOperand>(k_MemoryReg);
448     Op->Mem.Base = Base;
449     Op->Mem.OffsetReg = Sparc::G0;  // always 0
450     Op->Mem.Off = nullptr;
451     Op->StartLoc = S;
452     Op->EndLoc = E;
453     return Op;
454   }
455 
456   static std::unique_ptr<SparcOperand>
MorphToMEMri(unsigned Base,std::unique_ptr<SparcOperand> Op)457   MorphToMEMri(unsigned Base, std::unique_ptr<SparcOperand> Op) {
458     const MCExpr *Imm  = Op->getImm();
459     Op->Kind = k_MemoryImm;
460     Op->Mem.Base = Base;
461     Op->Mem.OffsetReg = 0;
462     Op->Mem.Off = Imm;
463     return Op;
464   }
465 };
466 
467 } // end namespace
468 
expandSET(MCInst & Inst,SMLoc IDLoc,SmallVectorImpl<MCInst> & Instructions)469 void SparcAsmParser::expandSET(MCInst &Inst, SMLoc IDLoc,
470                                SmallVectorImpl<MCInst> &Instructions) {
471   MCOperand MCRegOp = Inst.getOperand(0);
472   MCOperand MCValOp = Inst.getOperand(1);
473   assert(MCRegOp.isReg());
474   assert(MCValOp.isImm() || MCValOp.isExpr());
475 
476   // the imm operand can be either an expression or an immediate.
477   bool IsImm = Inst.getOperand(1).isImm();
478   int64_t RawImmValue = IsImm ? MCValOp.getImm() : 0;
479 
480   // Allow either a signed or unsigned 32-bit immediate.
481   if (RawImmValue < -2147483648LL || RawImmValue > 4294967295LL) {
482     Error(IDLoc, "set: argument must be between -2147483648 and 4294967295");
483     return;
484   }
485 
486   // If the value was expressed as a large unsigned number, that's ok.
487   // We want to see if it "looks like" a small signed number.
488   int32_t ImmValue = RawImmValue;
489   // For 'set' you can't use 'or' with a negative operand on V9 because
490   // that would splat the sign bit across the upper half of the destination
491   // register, whereas 'set' is defined to zero the high 32 bits.
492   bool IsEffectivelyImm13 =
493       IsImm && ((is64Bit() ? 0 : -4096) <= ImmValue && ImmValue < 4096);
494   const MCExpr *ValExpr;
495   if (IsImm)
496     ValExpr = MCConstantExpr::create(ImmValue, getContext());
497   else
498     ValExpr = MCValOp.getExpr();
499 
500   MCOperand PrevReg = MCOperand::createReg(Sparc::G0);
501 
502   // If not just a signed imm13 value, then either we use a 'sethi' with a
503   // following 'or', or a 'sethi' by itself if there are no more 1 bits.
504   // In either case, start with the 'sethi'.
505   if (!IsEffectivelyImm13) {
506     MCInst TmpInst;
507     const MCExpr *Expr = adjustPICRelocation(SparcMCExpr::VK_Sparc_HI, ValExpr);
508     TmpInst.setLoc(IDLoc);
509     TmpInst.setOpcode(SP::SETHIi);
510     TmpInst.addOperand(MCRegOp);
511     TmpInst.addOperand(MCOperand::createExpr(Expr));
512     Instructions.push_back(TmpInst);
513     PrevReg = MCRegOp;
514   }
515 
516   // The low bits require touching in 3 cases:
517   // * A non-immediate value will always require both instructions.
518   // * An effectively imm13 value needs only an 'or' instruction.
519   // * Otherwise, an immediate that is not effectively imm13 requires the
520   //   'or' only if bits remain after clearing the 22 bits that 'sethi' set.
521   // If the low bits are known zeros, there's nothing to do.
522   // In the second case, and only in that case, must we NOT clear
523   // bits of the immediate value via the %lo() assembler function.
524   // Note also, the 'or' instruction doesn't mind a large value in the case
525   // where the operand to 'set' was 0xFFFFFzzz - it does exactly what you mean.
526   if (!IsImm || IsEffectivelyImm13 || (ImmValue & 0x3ff)) {
527     MCInst TmpInst;
528     const MCExpr *Expr;
529     if (IsEffectivelyImm13)
530       Expr = ValExpr;
531     else
532       Expr = adjustPICRelocation(SparcMCExpr::VK_Sparc_LO, ValExpr);
533     TmpInst.setLoc(IDLoc);
534     TmpInst.setOpcode(SP::ORri);
535     TmpInst.addOperand(MCRegOp);
536     TmpInst.addOperand(PrevReg);
537     TmpInst.addOperand(MCOperand::createExpr(Expr));
538     Instructions.push_back(TmpInst);
539   }
540 }
541 
MatchAndEmitInstruction(SMLoc IDLoc,unsigned & Opcode,OperandVector & Operands,MCStreamer & Out,uint64_t & ErrorInfo,bool MatchingInlineAsm)542 bool SparcAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
543                                              OperandVector &Operands,
544                                              MCStreamer &Out,
545                                              uint64_t &ErrorInfo,
546                                              bool MatchingInlineAsm) {
547   MCInst Inst;
548   SmallVector<MCInst, 8> Instructions;
549   unsigned MatchResult = MatchInstructionImpl(Operands, Inst, ErrorInfo,
550                                               MatchingInlineAsm);
551   switch (MatchResult) {
552   case Match_Success: {
553     switch (Inst.getOpcode()) {
554     default:
555       Inst.setLoc(IDLoc);
556       Instructions.push_back(Inst);
557       break;
558     case SP::SET:
559       expandSET(Inst, IDLoc, Instructions);
560       break;
561     }
562 
563     for (const MCInst &I : Instructions) {
564       Out.EmitInstruction(I, getSTI());
565     }
566     return false;
567   }
568 
569   case Match_MissingFeature:
570     return Error(IDLoc,
571                  "instruction requires a CPU feature not currently enabled");
572 
573   case Match_InvalidOperand: {
574     SMLoc ErrorLoc = IDLoc;
575     if (ErrorInfo != ~0ULL) {
576       if (ErrorInfo >= Operands.size())
577         return Error(IDLoc, "too few operands for instruction");
578 
579       ErrorLoc = ((SparcOperand &)*Operands[ErrorInfo]).getStartLoc();
580       if (ErrorLoc == SMLoc())
581         ErrorLoc = IDLoc;
582     }
583 
584     return Error(ErrorLoc, "invalid operand for instruction");
585   }
586   case Match_MnemonicFail:
587     return Error(IDLoc, "invalid instruction mnemonic");
588   }
589   llvm_unreachable("Implement any new match types added!");
590 }
591 
592 bool SparcAsmParser::
ParseRegister(unsigned & RegNo,SMLoc & StartLoc,SMLoc & EndLoc)593 ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc)
594 {
595   const AsmToken &Tok = Parser.getTok();
596   StartLoc = Tok.getLoc();
597   EndLoc = Tok.getEndLoc();
598   RegNo = 0;
599   if (getLexer().getKind() != AsmToken::Percent)
600     return false;
601   Parser.Lex();
602   unsigned regKind = SparcOperand::rk_None;
603   if (matchRegisterName(Tok, RegNo, regKind)) {
604     Parser.Lex();
605     return false;
606   }
607 
608   return Error(StartLoc, "invalid register name");
609 }
610 
611 static void applyMnemonicAliases(StringRef &Mnemonic, uint64_t Features,
612                                  unsigned VariantID);
613 
ParseInstruction(ParseInstructionInfo & Info,StringRef Name,SMLoc NameLoc,OperandVector & Operands)614 bool SparcAsmParser::ParseInstruction(ParseInstructionInfo &Info,
615                                       StringRef Name, SMLoc NameLoc,
616                                       OperandVector &Operands) {
617 
618   // First operand in MCInst is instruction mnemonic.
619   Operands.push_back(SparcOperand::CreateToken(Name, NameLoc));
620 
621   // apply mnemonic aliases, if any, so that we can parse operands correctly.
622   applyMnemonicAliases(Name, getAvailableFeatures(), 0);
623 
624   if (getLexer().isNot(AsmToken::EndOfStatement)) {
625     // Read the first operand.
626     if (getLexer().is(AsmToken::Comma)) {
627       if (parseBranchModifiers(Operands) != MatchOperand_Success) {
628         SMLoc Loc = getLexer().getLoc();
629         Parser.eatToEndOfStatement();
630         return Error(Loc, "unexpected token");
631       }
632     }
633     if (parseOperand(Operands, Name) != MatchOperand_Success) {
634       SMLoc Loc = getLexer().getLoc();
635       Parser.eatToEndOfStatement();
636       return Error(Loc, "unexpected token");
637     }
638 
639     while (getLexer().is(AsmToken::Comma) || getLexer().is(AsmToken::Plus)) {
640       if (getLexer().is(AsmToken::Plus)) {
641       // Plus tokens are significant in software_traps (p83, sparcv8.pdf). We must capture them.
642         Operands.push_back(SparcOperand::CreateToken("+", Parser.getTok().getLoc()));
643       }
644       Parser.Lex(); // Eat the comma or plus.
645       // Parse and remember the operand.
646       if (parseOperand(Operands, Name) != MatchOperand_Success) {
647         SMLoc Loc = getLexer().getLoc();
648         Parser.eatToEndOfStatement();
649         return Error(Loc, "unexpected token");
650       }
651     }
652   }
653   if (getLexer().isNot(AsmToken::EndOfStatement)) {
654     SMLoc Loc = getLexer().getLoc();
655     Parser.eatToEndOfStatement();
656     return Error(Loc, "unexpected token");
657   }
658   Parser.Lex(); // Consume the EndOfStatement.
659   return false;
660 }
661 
662 bool SparcAsmParser::
ParseDirective(AsmToken DirectiveID)663 ParseDirective(AsmToken DirectiveID)
664 {
665   StringRef IDVal = DirectiveID.getString();
666 
667   if (IDVal == ".byte")
668     return parseDirectiveWord(1, DirectiveID.getLoc());
669 
670   if (IDVal == ".half")
671     return parseDirectiveWord(2, DirectiveID.getLoc());
672 
673   if (IDVal == ".word")
674     return parseDirectiveWord(4, DirectiveID.getLoc());
675 
676   if (IDVal == ".nword")
677     return parseDirectiveWord(is64Bit() ? 8 : 4, DirectiveID.getLoc());
678 
679   if (is64Bit() && IDVal == ".xword")
680     return parseDirectiveWord(8, DirectiveID.getLoc());
681 
682   if (IDVal == ".register") {
683     // For now, ignore .register directive.
684     Parser.eatToEndOfStatement();
685     return false;
686   }
687   if (IDVal == ".proc") {
688     // For compatibility, ignore this directive.
689     // (It's supposed to be an "optimization" in the Sun assembler)
690     Parser.eatToEndOfStatement();
691     return false;
692   }
693 
694   // Let the MC layer to handle other directives.
695   return true;
696 }
697 
parseDirectiveWord(unsigned Size,SMLoc L)698 bool SparcAsmParser:: parseDirectiveWord(unsigned Size, SMLoc L) {
699   if (getLexer().isNot(AsmToken::EndOfStatement)) {
700     for (;;) {
701       const MCExpr *Value;
702       if (getParser().parseExpression(Value))
703         return true;
704 
705       getParser().getStreamer().EmitValue(Value, Size);
706 
707       if (getLexer().is(AsmToken::EndOfStatement))
708         break;
709 
710       // FIXME: Improve diagnostic.
711       if (getLexer().isNot(AsmToken::Comma))
712         return Error(L, "unexpected token in directive");
713       Parser.Lex();
714     }
715   }
716   Parser.Lex();
717   return false;
718 }
719 
720 SparcAsmParser::OperandMatchResultTy
parseMEMOperand(OperandVector & Operands)721 SparcAsmParser::parseMEMOperand(OperandVector &Operands) {
722 
723   SMLoc S, E;
724   unsigned BaseReg = 0;
725 
726   if (ParseRegister(BaseReg, S, E)) {
727     return MatchOperand_NoMatch;
728   }
729 
730   switch (getLexer().getKind()) {
731   default: return MatchOperand_NoMatch;
732 
733   case AsmToken::Comma:
734   case AsmToken::RBrac:
735   case AsmToken::EndOfStatement:
736     Operands.push_back(SparcOperand::CreateMEMr(BaseReg, S, E));
737     return MatchOperand_Success;
738 
739   case AsmToken:: Plus:
740     Parser.Lex(); // Eat the '+'
741     break;
742   case AsmToken::Minus:
743     break;
744   }
745 
746   std::unique_ptr<SparcOperand> Offset;
747   OperandMatchResultTy ResTy = parseSparcAsmOperand(Offset);
748   if (ResTy != MatchOperand_Success || !Offset)
749     return MatchOperand_NoMatch;
750 
751   Operands.push_back(
752       Offset->isImm() ? SparcOperand::MorphToMEMri(BaseReg, std::move(Offset))
753                       : SparcOperand::MorphToMEMrr(BaseReg, std::move(Offset)));
754 
755   return MatchOperand_Success;
756 }
757 
758 SparcAsmParser::OperandMatchResultTy
parseOperand(OperandVector & Operands,StringRef Mnemonic)759 SparcAsmParser::parseOperand(OperandVector &Operands, StringRef Mnemonic) {
760 
761   OperandMatchResultTy ResTy = MatchOperandParserImpl(Operands, Mnemonic);
762 
763   // If there wasn't a custom match, try the generic matcher below. Otherwise,
764   // there was a match, but an error occurred, in which case, just return that
765   // the operand parsing failed.
766   if (ResTy == MatchOperand_Success || ResTy == MatchOperand_ParseFail)
767     return ResTy;
768 
769   if (getLexer().is(AsmToken::LBrac)) {
770     // Memory operand
771     Operands.push_back(SparcOperand::CreateToken("[",
772                                                  Parser.getTok().getLoc()));
773     Parser.Lex(); // Eat the [
774 
775     if (Mnemonic == "cas" || Mnemonic == "casx" || Mnemonic == "casa") {
776       SMLoc S = Parser.getTok().getLoc();
777       if (getLexer().getKind() != AsmToken::Percent)
778         return MatchOperand_NoMatch;
779       Parser.Lex(); // eat %
780 
781       unsigned RegNo, RegKind;
782       if (!matchRegisterName(Parser.getTok(), RegNo, RegKind))
783         return MatchOperand_NoMatch;
784 
785       Parser.Lex(); // Eat the identifier token.
786       SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer()-1);
787       Operands.push_back(SparcOperand::CreateReg(RegNo, RegKind, S, E));
788       ResTy = MatchOperand_Success;
789     } else {
790       ResTy = parseMEMOperand(Operands);
791     }
792 
793     if (ResTy != MatchOperand_Success)
794       return ResTy;
795 
796     if (!getLexer().is(AsmToken::RBrac))
797       return MatchOperand_ParseFail;
798 
799     Operands.push_back(SparcOperand::CreateToken("]",
800                                                  Parser.getTok().getLoc()));
801     Parser.Lex(); // Eat the ]
802 
803     // Parse an optional address-space identifier after the address.
804     if (getLexer().is(AsmToken::Integer)) {
805       std::unique_ptr<SparcOperand> Op;
806       ResTy = parseSparcAsmOperand(Op, false);
807       if (ResTy != MatchOperand_Success || !Op)
808         return MatchOperand_ParseFail;
809       Operands.push_back(std::move(Op));
810     }
811     return MatchOperand_Success;
812   }
813 
814   std::unique_ptr<SparcOperand> Op;
815 
816   ResTy = parseSparcAsmOperand(Op, (Mnemonic == "call"));
817   if (ResTy != MatchOperand_Success || !Op)
818     return MatchOperand_ParseFail;
819 
820   // Push the parsed operand into the list of operands
821   Operands.push_back(std::move(Op));
822 
823   return MatchOperand_Success;
824 }
825 
826 SparcAsmParser::OperandMatchResultTy
parseSparcAsmOperand(std::unique_ptr<SparcOperand> & Op,bool isCall)827 SparcAsmParser::parseSparcAsmOperand(std::unique_ptr<SparcOperand> &Op,
828                                      bool isCall) {
829 
830   SMLoc S = Parser.getTok().getLoc();
831   SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
832   const MCExpr *EVal;
833 
834   Op = nullptr;
835   switch (getLexer().getKind()) {
836   default:  break;
837 
838   case AsmToken::Percent:
839     Parser.Lex(); // Eat the '%'.
840     unsigned RegNo;
841     unsigned RegKind;
842     if (matchRegisterName(Parser.getTok(), RegNo, RegKind)) {
843       StringRef name = Parser.getTok().getString();
844       Parser.Lex(); // Eat the identifier token.
845       E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
846       switch (RegNo) {
847       default:
848         Op = SparcOperand::CreateReg(RegNo, RegKind, S, E);
849         break;
850       case Sparc::PSR:
851         Op = SparcOperand::CreateToken("%psr", S);
852         break;
853       case Sparc::FSR:
854         Op = SparcOperand::CreateToken("%fsr", S);
855         break;
856       case Sparc::FQ:
857         Op = SparcOperand::CreateToken("%fq", S);
858         break;
859       case Sparc::CPSR:
860         Op = SparcOperand::CreateToken("%csr", S);
861         break;
862       case Sparc::CPQ:
863         Op = SparcOperand::CreateToken("%cq", S);
864         break;
865       case Sparc::WIM:
866         Op = SparcOperand::CreateToken("%wim", S);
867         break;
868       case Sparc::TBR:
869         Op = SparcOperand::CreateToken("%tbr", S);
870         break;
871       case Sparc::ICC:
872         if (name == "xcc")
873           Op = SparcOperand::CreateToken("%xcc", S);
874         else
875           Op = SparcOperand::CreateToken("%icc", S);
876         break;
877       }
878       break;
879     }
880     if (matchSparcAsmModifiers(EVal, E)) {
881       E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
882       Op = SparcOperand::CreateImm(EVal, S, E);
883     }
884     break;
885 
886   case AsmToken::Minus:
887   case AsmToken::Integer:
888   case AsmToken::LParen:
889   case AsmToken::Dot:
890     if (!getParser().parseExpression(EVal, E))
891       Op = SparcOperand::CreateImm(EVal, S, E);
892     break;
893 
894   case AsmToken::Identifier: {
895     StringRef Identifier;
896     if (!getParser().parseIdentifier(Identifier)) {
897       E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
898       MCSymbol *Sym = getContext().getOrCreateSymbol(Identifier);
899 
900       const MCExpr *Res = MCSymbolRefExpr::create(Sym, MCSymbolRefExpr::VK_None,
901                                                   getContext());
902       if (isCall && getContext().getObjectFileInfo()->isPositionIndependent())
903         Res = SparcMCExpr::create(SparcMCExpr::VK_Sparc_WPLT30, Res,
904                                   getContext());
905       Op = SparcOperand::CreateImm(Res, S, E);
906     }
907     break;
908   }
909   }
910   return (Op) ? MatchOperand_Success : MatchOperand_ParseFail;
911 }
912 
913 SparcAsmParser::OperandMatchResultTy
parseBranchModifiers(OperandVector & Operands)914 SparcAsmParser::parseBranchModifiers(OperandVector &Operands) {
915 
916   // parse (,a|,pn|,pt)+
917 
918   while (getLexer().is(AsmToken::Comma)) {
919 
920     Parser.Lex(); // Eat the comma
921 
922     if (!getLexer().is(AsmToken::Identifier))
923       return MatchOperand_ParseFail;
924     StringRef modName = Parser.getTok().getString();
925     if (modName == "a" || modName == "pn" || modName == "pt") {
926       Operands.push_back(SparcOperand::CreateToken(modName,
927                                                    Parser.getTok().getLoc()));
928       Parser.Lex(); // eat the identifier.
929     }
930   }
931   return MatchOperand_Success;
932 }
933 
matchRegisterName(const AsmToken & Tok,unsigned & RegNo,unsigned & RegKind)934 bool SparcAsmParser::matchRegisterName(const AsmToken &Tok,
935                                        unsigned &RegNo,
936                                        unsigned &RegKind)
937 {
938   int64_t intVal = 0;
939   RegNo = 0;
940   RegKind = SparcOperand::rk_None;
941   if (Tok.is(AsmToken::Identifier)) {
942     StringRef name = Tok.getString();
943 
944     // %fp
945     if (name.equals("fp")) {
946       RegNo = Sparc::I6;
947       RegKind = SparcOperand::rk_IntReg;
948       return true;
949     }
950     // %sp
951     if (name.equals("sp")) {
952       RegNo = Sparc::O6;
953       RegKind = SparcOperand::rk_IntReg;
954       return true;
955     }
956 
957     if (name.equals("y")) {
958       RegNo = Sparc::Y;
959       RegKind = SparcOperand::rk_Special;
960       return true;
961     }
962 
963     if (name.substr(0, 3).equals_lower("asr")
964         && !name.substr(3).getAsInteger(10, intVal)
965         && intVal > 0 && intVal < 32) {
966       RegNo = ASRRegs[intVal];
967       RegKind = SparcOperand::rk_Special;
968       return true;
969     }
970 
971     // %fprs is an alias of %asr6.
972     if (name.equals("fprs")) {
973       RegNo = ASRRegs[6];
974       RegKind = SparcOperand::rk_Special;
975       return true;
976     }
977 
978     if (name.equals("icc")) {
979       RegNo = Sparc::ICC;
980       RegKind = SparcOperand::rk_Special;
981       return true;
982     }
983 
984     if (name.equals("psr")) {
985       RegNo = Sparc::PSR;
986       RegKind = SparcOperand::rk_Special;
987       return true;
988     }
989 
990     if (name.equals("fsr")) {
991       RegNo = Sparc::FSR;
992       RegKind = SparcOperand::rk_Special;
993       return true;
994     }
995 
996     if (name.equals("fq")) {
997       RegNo = Sparc::FQ;
998       RegKind = SparcOperand::rk_Special;
999       return true;
1000     }
1001 
1002     if (name.equals("csr")) {
1003       RegNo = Sparc::CPSR;
1004       RegKind = SparcOperand::rk_Special;
1005       return true;
1006     }
1007 
1008     if (name.equals("cq")) {
1009       RegNo = Sparc::CPQ;
1010       RegKind = SparcOperand::rk_Special;
1011       return true;
1012     }
1013 
1014     if (name.equals("wim")) {
1015       RegNo = Sparc::WIM;
1016       RegKind = SparcOperand::rk_Special;
1017       return true;
1018     }
1019 
1020     if (name.equals("tbr")) {
1021       RegNo = Sparc::TBR;
1022       RegKind = SparcOperand::rk_Special;
1023       return true;
1024     }
1025 
1026     if (name.equals("xcc")) {
1027       // FIXME:: check 64bit.
1028       RegNo = Sparc::ICC;
1029       RegKind = SparcOperand::rk_Special;
1030       return true;
1031     }
1032 
1033     // %fcc0 - %fcc3
1034     if (name.substr(0, 3).equals_lower("fcc")
1035         && !name.substr(3).getAsInteger(10, intVal)
1036         && intVal < 4) {
1037       // FIXME: check 64bit and  handle %fcc1 - %fcc3
1038       RegNo = Sparc::FCC0 + intVal;
1039       RegKind = SparcOperand::rk_Special;
1040       return true;
1041     }
1042 
1043     // %g0 - %g7
1044     if (name.substr(0, 1).equals_lower("g")
1045         && !name.substr(1).getAsInteger(10, intVal)
1046         && intVal < 8) {
1047       RegNo = IntRegs[intVal];
1048       RegKind = SparcOperand::rk_IntReg;
1049       return true;
1050     }
1051     // %o0 - %o7
1052     if (name.substr(0, 1).equals_lower("o")
1053         && !name.substr(1).getAsInteger(10, intVal)
1054         && intVal < 8) {
1055       RegNo = IntRegs[8 + intVal];
1056       RegKind = SparcOperand::rk_IntReg;
1057       return true;
1058     }
1059     if (name.substr(0, 1).equals_lower("l")
1060         && !name.substr(1).getAsInteger(10, intVal)
1061         && intVal < 8) {
1062       RegNo = IntRegs[16 + intVal];
1063       RegKind = SparcOperand::rk_IntReg;
1064       return true;
1065     }
1066     if (name.substr(0, 1).equals_lower("i")
1067         && !name.substr(1).getAsInteger(10, intVal)
1068         && intVal < 8) {
1069       RegNo = IntRegs[24 + intVal];
1070       RegKind = SparcOperand::rk_IntReg;
1071       return true;
1072     }
1073     // %f0 - %f31
1074     if (name.substr(0, 1).equals_lower("f")
1075         && !name.substr(1, 2).getAsInteger(10, intVal) && intVal < 32) {
1076       RegNo = FloatRegs[intVal];
1077       RegKind = SparcOperand::rk_FloatReg;
1078       return true;
1079     }
1080     // %f32 - %f62
1081     if (name.substr(0, 1).equals_lower("f")
1082         && !name.substr(1, 2).getAsInteger(10, intVal)
1083         && intVal >= 32 && intVal <= 62 && (intVal % 2 == 0)) {
1084       // FIXME: Check V9
1085       RegNo = DoubleRegs[intVal/2];
1086       RegKind = SparcOperand::rk_DoubleReg;
1087       return true;
1088     }
1089 
1090     // %r0 - %r31
1091     if (name.substr(0, 1).equals_lower("r")
1092         && !name.substr(1, 2).getAsInteger(10, intVal) && intVal < 31) {
1093       RegNo = IntRegs[intVal];
1094       RegKind = SparcOperand::rk_IntReg;
1095       return true;
1096     }
1097 
1098     // %c0 - %c31
1099     if (name.substr(0, 1).equals_lower("c")
1100         && !name.substr(1).getAsInteger(10, intVal)
1101         && intVal < 32) {
1102       RegNo = CoprocRegs[intVal];
1103       RegKind = SparcOperand::rk_CoprocReg;
1104       return true;
1105     }
1106 
1107     if (name.equals("tpc")) {
1108       RegNo = Sparc::TPC;
1109       RegKind = SparcOperand::rk_Special;
1110       return true;
1111     }
1112     if (name.equals("tnpc")) {
1113       RegNo = Sparc::TNPC;
1114       RegKind = SparcOperand::rk_Special;
1115       return true;
1116     }
1117     if (name.equals("tstate")) {
1118       RegNo = Sparc::TSTATE;
1119       RegKind = SparcOperand::rk_Special;
1120       return true;
1121     }
1122     if (name.equals("tt")) {
1123       RegNo = Sparc::TT;
1124       RegKind = SparcOperand::rk_Special;
1125       return true;
1126     }
1127     if (name.equals("tick")) {
1128       RegNo = Sparc::TICK;
1129       RegKind = SparcOperand::rk_Special;
1130       return true;
1131     }
1132     if (name.equals("tba")) {
1133       RegNo = Sparc::TBA;
1134       RegKind = SparcOperand::rk_Special;
1135       return true;
1136     }
1137     if (name.equals("pstate")) {
1138       RegNo = Sparc::PSTATE;
1139       RegKind = SparcOperand::rk_Special;
1140       return true;
1141     }
1142     if (name.equals("tl")) {
1143       RegNo = Sparc::TL;
1144       RegKind = SparcOperand::rk_Special;
1145       return true;
1146     }
1147     if (name.equals("pil")) {
1148       RegNo = Sparc::PIL;
1149       RegKind = SparcOperand::rk_Special;
1150       return true;
1151     }
1152     if (name.equals("cwp")) {
1153       RegNo = Sparc::CWP;
1154       RegKind = SparcOperand::rk_Special;
1155       return true;
1156     }
1157     if (name.equals("cansave")) {
1158       RegNo = Sparc::CANSAVE;
1159       RegKind = SparcOperand::rk_Special;
1160       return true;
1161     }
1162     if (name.equals("canrestore")) {
1163       RegNo = Sparc::CANRESTORE;
1164       RegKind = SparcOperand::rk_Special;
1165       return true;
1166     }
1167     if (name.equals("cleanwin")) {
1168       RegNo = Sparc::CLEANWIN;
1169       RegKind = SparcOperand::rk_Special;
1170       return true;
1171     }
1172     if (name.equals("otherwin")) {
1173       RegNo = Sparc::OTHERWIN;
1174       RegKind = SparcOperand::rk_Special;
1175       return true;
1176     }
1177     if (name.equals("wstate")) {
1178       RegNo = Sparc::WSTATE;
1179       RegKind = SparcOperand::rk_Special;
1180       return true;
1181     }
1182   }
1183   return false;
1184 }
1185 
1186 // Determine if an expression contains a reference to the symbol
1187 // "_GLOBAL_OFFSET_TABLE_".
hasGOTReference(const MCExpr * Expr)1188 static bool hasGOTReference(const MCExpr *Expr) {
1189   switch (Expr->getKind()) {
1190   case MCExpr::Target:
1191     if (const SparcMCExpr *SE = dyn_cast<SparcMCExpr>(Expr))
1192       return hasGOTReference(SE->getSubExpr());
1193     break;
1194 
1195   case MCExpr::Constant:
1196     break;
1197 
1198   case MCExpr::Binary: {
1199     const MCBinaryExpr *BE = cast<MCBinaryExpr>(Expr);
1200     return hasGOTReference(BE->getLHS()) || hasGOTReference(BE->getRHS());
1201   }
1202 
1203   case MCExpr::SymbolRef: {
1204     const MCSymbolRefExpr &SymRef = *cast<MCSymbolRefExpr>(Expr);
1205     return (SymRef.getSymbol().getName() == "_GLOBAL_OFFSET_TABLE_");
1206   }
1207 
1208   case MCExpr::Unary:
1209     return hasGOTReference(cast<MCUnaryExpr>(Expr)->getSubExpr());
1210   }
1211   return false;
1212 }
1213 
1214 const SparcMCExpr *
adjustPICRelocation(SparcMCExpr::VariantKind VK,const MCExpr * subExpr)1215 SparcAsmParser::adjustPICRelocation(SparcMCExpr::VariantKind VK,
1216                                     const MCExpr *subExpr)
1217 {
1218   // When in PIC mode, "%lo(...)" and "%hi(...)" behave differently.
1219   // If the expression refers contains _GLOBAL_OFFSETE_TABLE, it is
1220   // actually a %pc10 or %pc22 relocation. Otherwise, they are interpreted
1221   // as %got10 or %got22 relocation.
1222 
1223   if (getContext().getObjectFileInfo()->isPositionIndependent()) {
1224     switch(VK) {
1225     default: break;
1226     case SparcMCExpr::VK_Sparc_LO:
1227       VK = (hasGOTReference(subExpr) ? SparcMCExpr::VK_Sparc_PC10
1228                                      : SparcMCExpr::VK_Sparc_GOT10);
1229       break;
1230     case SparcMCExpr::VK_Sparc_HI:
1231       VK = (hasGOTReference(subExpr) ? SparcMCExpr::VK_Sparc_PC22
1232                                      : SparcMCExpr::VK_Sparc_GOT22);
1233       break;
1234     }
1235   }
1236 
1237   return SparcMCExpr::create(VK, subExpr, getContext());
1238 }
1239 
matchSparcAsmModifiers(const MCExpr * & EVal,SMLoc & EndLoc)1240 bool SparcAsmParser::matchSparcAsmModifiers(const MCExpr *&EVal,
1241                                             SMLoc &EndLoc)
1242 {
1243   AsmToken Tok = Parser.getTok();
1244   if (!Tok.is(AsmToken::Identifier))
1245     return false;
1246 
1247   StringRef name = Tok.getString();
1248 
1249   SparcMCExpr::VariantKind VK = SparcMCExpr::parseVariantKind(name);
1250 
1251   if (VK == SparcMCExpr::VK_Sparc_None)
1252     return false;
1253 
1254   Parser.Lex(); // Eat the identifier.
1255   if (Parser.getTok().getKind() != AsmToken::LParen)
1256     return false;
1257 
1258   Parser.Lex(); // Eat the LParen token.
1259   const MCExpr *subExpr;
1260   if (Parser.parseParenExpression(subExpr, EndLoc))
1261     return false;
1262 
1263   EVal = adjustPICRelocation(VK, subExpr);
1264   return true;
1265 }
1266 
LLVMInitializeSparcAsmParser()1267 extern "C" void LLVMInitializeSparcAsmParser() {
1268   RegisterMCAsmParser<SparcAsmParser> A(TheSparcTarget);
1269   RegisterMCAsmParser<SparcAsmParser> B(TheSparcV9Target);
1270   RegisterMCAsmParser<SparcAsmParser> C(TheSparcelTarget);
1271 }
1272 
1273 #define GET_REGISTER_MATCHER
1274 #define GET_MATCHER_IMPLEMENTATION
1275 #include "SparcGenAsmMatcher.inc"
1276 
validateTargetOperandClass(MCParsedAsmOperand & GOp,unsigned Kind)1277 unsigned SparcAsmParser::validateTargetOperandClass(MCParsedAsmOperand &GOp,
1278                                                     unsigned Kind) {
1279   SparcOperand &Op = (SparcOperand &)GOp;
1280   if (Op.isFloatOrDoubleReg()) {
1281     switch (Kind) {
1282     default: break;
1283     case MCK_DFPRegs:
1284       if (!Op.isFloatReg() || SparcOperand::MorphToDoubleReg(Op))
1285         return MCTargetAsmParser::Match_Success;
1286       break;
1287     case MCK_QFPRegs:
1288       if (SparcOperand::MorphToQuadReg(Op))
1289         return MCTargetAsmParser::Match_Success;
1290       break;
1291     }
1292   }
1293   if (Op.isIntReg() && Kind == MCK_IntPair) {
1294     if (SparcOperand::MorphToIntPairReg(Op))
1295       return MCTargetAsmParser::Match_Success;
1296   }
1297   if (Op.isCoprocReg() && Kind == MCK_CoprocPair) {
1298      if (SparcOperand::MorphToCoprocPairReg(Op))
1299        return MCTargetAsmParser::Match_Success;
1300    }
1301   return Match_InvalidOperand;
1302 }
1303