[mips] Add error message when trying to use $at in '.set noat' mode.
[oota-llvm.git] / lib / Target / Mips / AsmParser / MipsAsmParser.cpp
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/MC/MCContext.h"
17 #include "llvm/MC/MCExpr.h"
18 #include "llvm/MC/MCInst.h"
19 #include "llvm/MC/MCInstBuilder.h"
20 #include "llvm/MC/MCParser/MCAsmLexer.h"
21 #include "llvm/MC/MCParser/MCParsedAsmOperand.h"
22 #include "llvm/MC/MCStreamer.h"
23 #include "llvm/MC/MCSubtargetInfo.h"
24 #include "llvm/MC/MCSymbol.h"
25 #include "llvm/MC/MCTargetAsmParser.h"
26 #include "llvm/Support/MathExtras.h"
27 #include "llvm/Support/TargetRegistry.h"
28
29 using namespace llvm;
30
31 namespace llvm {
32 class MCInstrInfo;
33 }
34
35 namespace {
36 class MipsAssemblerOptions {
37 public:
38   MipsAssemblerOptions() : aTReg(1), reorder(true), macro(true) {}
39
40   unsigned getATRegNum() { return aTReg; }
41   bool setATReg(unsigned Reg);
42
43   bool isReorder() { return reorder; }
44   void setReorder() { reorder = true; }
45   void setNoreorder() { reorder = false; }
46
47   bool isMacro() { return macro; }
48   void setMacro() { macro = true; }
49   void setNomacro() { macro = false; }
50
51 private:
52   unsigned aTReg;
53   bool reorder;
54   bool macro;
55 };
56 }
57
58 namespace {
59 class MipsAsmParser : public MCTargetAsmParser {
60
61   MipsTargetStreamer &getTargetStreamer() {
62     MCTargetStreamer &TS = *Parser.getStreamer().getTargetStreamer();
63     return static_cast<MipsTargetStreamer &>(TS);
64   }
65
66   MCSubtargetInfo &STI;
67   MCAsmParser &Parser;
68   MipsAssemblerOptions Options;
69   bool hasConsumedDollar;
70
71 #define GET_ASSEMBLER_HEADER
72 #include "MipsGenAsmMatcher.inc"
73
74   bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
75                                SmallVectorImpl<MCParsedAsmOperand *> &Operands,
76                                MCStreamer &Out, unsigned &ErrorInfo,
77                                bool MatchingInlineAsm);
78
79   bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc);
80
81   bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name,
82                         SMLoc NameLoc,
83                         SmallVectorImpl<MCParsedAsmOperand *> &Operands);
84
85   bool ParseDirective(AsmToken DirectiveID);
86
87   MipsAsmParser::OperandMatchResultTy
88   parseRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands, int RegKind);
89
90   MipsAsmParser::OperandMatchResultTy
91   parseMSARegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands, int RegKind);
92
93   MipsAsmParser::OperandMatchResultTy
94   parseMSACtrlRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
95                    int RegKind);
96
97   MipsAsmParser::OperandMatchResultTy
98   parseMemOperand(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
99
100   bool parsePtrReg(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
101                    int RegKind);
102
103   MipsAsmParser::OperandMatchResultTy
104   parsePtrReg(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
105
106   MipsAsmParser::OperandMatchResultTy
107   parseGPR32(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
108
109   MipsAsmParser::OperandMatchResultTy
110   parseGPR64(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
111
112   MipsAsmParser::OperandMatchResultTy
113   parseHWRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
114
115   MipsAsmParser::OperandMatchResultTy
116   parseCCRRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
117
118   MipsAsmParser::OperandMatchResultTy
119   parseAFGR64Regs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
120
121   MipsAsmParser::OperandMatchResultTy
122   parseFGR64Regs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
123
124   MipsAsmParser::OperandMatchResultTy
125   parseFGR32Regs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
126
127   MipsAsmParser::OperandMatchResultTy
128   parseFGRH32Regs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
129
130   MipsAsmParser::OperandMatchResultTy
131   parseFCCRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
132
133   MipsAsmParser::OperandMatchResultTy
134   parseACC64DSP(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
135
136   MipsAsmParser::OperandMatchResultTy
137   parseLO32DSP(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
138
139   MipsAsmParser::OperandMatchResultTy
140   parseHI32DSP(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
141
142   MipsAsmParser::OperandMatchResultTy
143   parseCOP2(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
144
145   MipsAsmParser::OperandMatchResultTy
146   parseMSA128BRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
147
148   MipsAsmParser::OperandMatchResultTy
149   parseMSA128HRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
150
151   MipsAsmParser::OperandMatchResultTy
152   parseMSA128WRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
153
154   MipsAsmParser::OperandMatchResultTy
155   parseMSA128DRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
156
157   MipsAsmParser::OperandMatchResultTy
158   parseMSA128CtrlRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
159
160   MipsAsmParser::OperandMatchResultTy
161   parseInvNum(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
162
163   MipsAsmParser::OperandMatchResultTy
164   parseLSAImm(SmallVectorImpl<MCParsedAsmOperand *> &Operands);
165
166   bool searchSymbolAlias(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
167                          unsigned RegKind);
168
169   bool ParseOperand(SmallVectorImpl<MCParsedAsmOperand *> &,
170                     StringRef Mnemonic);
171
172   int tryParseRegister(bool is64BitReg);
173
174   bool tryParseRegisterOperand(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
175                                bool is64BitReg);
176
177   bool needsExpansion(MCInst &Inst);
178
179   void expandInstruction(MCInst &Inst, SMLoc IDLoc,
180                          SmallVectorImpl<MCInst> &Instructions);
181   void expandLoadImm(MCInst &Inst, SMLoc IDLoc,
182                      SmallVectorImpl<MCInst> &Instructions);
183   void expandLoadAddressImm(MCInst &Inst, SMLoc IDLoc,
184                             SmallVectorImpl<MCInst> &Instructions);
185   void expandLoadAddressReg(MCInst &Inst, SMLoc IDLoc,
186                             SmallVectorImpl<MCInst> &Instructions);
187   void expandMemInst(MCInst &Inst, SMLoc IDLoc,
188                      SmallVectorImpl<MCInst> &Instructions, bool isLoad,
189                      bool isImmOpnd);
190   bool reportParseError(StringRef ErrorMsg);
191
192   bool parseMemOffset(const MCExpr *&Res, bool isParenExpr);
193   bool parseRelocOperand(const MCExpr *&Res);
194
195   const MCExpr *evaluateRelocExpr(const MCExpr *Expr, StringRef RelocStr);
196
197   bool isEvaluated(const MCExpr *Expr);
198   bool parseDirectiveSet();
199   bool parseDirectiveOption();
200
201   bool parseSetAtDirective();
202   bool parseSetNoAtDirective();
203   bool parseSetMacroDirective();
204   bool parseSetNoMacroDirective();
205   bool parseSetReorderDirective();
206   bool parseSetNoReorderDirective();
207   bool parseSetMips16Directive();
208   bool parseSetNoMips16Directive();
209
210   bool parseSetAssignment();
211
212   bool parseDirectiveWord(unsigned Size, SMLoc L);
213   bool parseDirectiveGpWord();
214
215   MCSymbolRefExpr::VariantKind getVariantKind(StringRef Symbol);
216
217   bool isMips64() const {
218     return (STI.getFeatureBits() & Mips::FeatureMips64) != 0;
219   }
220
221   bool isFP64() const {
222     return (STI.getFeatureBits() & Mips::FeatureFP64Bit) != 0;
223   }
224
225   bool isN64() const { return STI.getFeatureBits() & Mips::FeatureN64; }
226
227   bool isMicroMips() const {
228     return STI.getFeatureBits() & Mips::FeatureMicroMips;
229   }
230
231   int matchRegisterName(StringRef Symbol, bool is64BitReg);
232
233   int matchCPURegisterName(StringRef Symbol);
234
235   int matchRegisterByNumber(unsigned RegNum, unsigned RegClass);
236
237   int matchFPURegisterName(StringRef Name);
238
239   int matchFCCRegisterName(StringRef Name);
240
241   int matchACRegisterName(StringRef Name);
242
243   int matchMSA128RegisterName(StringRef Name);
244
245   int matchMSA128CtrlRegisterName(StringRef Name);
246
247   int regKindToRegClass(int RegKind);
248
249   unsigned getReg(int RC, int RegNo);
250
251   int getATReg();
252
253   bool processInstruction(MCInst &Inst, SMLoc IDLoc,
254                           SmallVectorImpl<MCInst> &Instructions);
255
256   // Helper function that checks if the value of a vector index is within the
257   // boundaries of accepted values for each RegisterKind
258   // Example: INSERT.B $w0[n], $1 => 16 > n >= 0
259   bool validateMSAIndex(int Val, int RegKind);
260
261   void setFeatureBits(unsigned Feature, StringRef FeatureString) {
262     if (!(STI.getFeatureBits() & Feature)) {
263       setAvailableFeatures(ComputeAvailableFeatures(
264                            STI.ToggleFeature(FeatureString)));
265     }
266   }
267
268   void clearFeatureBits(unsigned Feature, StringRef FeatureString) {
269     if (STI.getFeatureBits() & Feature) {
270      setAvailableFeatures(ComputeAvailableFeatures(
271                            STI.ToggleFeature(FeatureString)));
272     }
273   }
274
275 public:
276   MipsAsmParser(MCSubtargetInfo &sti, MCAsmParser &parser,
277                 const MCInstrInfo &MII)
278       : MCTargetAsmParser(), STI(sti), Parser(parser),
279         hasConsumedDollar(false) {
280     // Initialize the set of available features.
281     setAvailableFeatures(ComputeAvailableFeatures(STI.getFeatureBits()));
282
283     // Assert exactly one ABI was chosen.
284     assert((((STI.getFeatureBits() & Mips::FeatureO32) != 0) +
285             ((STI.getFeatureBits() & Mips::FeatureEABI) != 0) +
286             ((STI.getFeatureBits() & Mips::FeatureN32) != 0) +
287             ((STI.getFeatureBits() & Mips::FeatureN64) != 0)) == 1);
288   }
289
290   MCAsmParser &getParser() const { return Parser; }
291   MCAsmLexer &getLexer() const { return Parser.getLexer(); }
292 };
293 }
294
295 namespace {
296
297 /// MipsOperand - Instances of this class represent a parsed Mips machine
298 /// instruction.
299 class MipsOperand : public MCParsedAsmOperand {
300
301 public:
302   enum RegisterKind {
303     Kind_None,
304     Kind_GPR32,
305     Kind_GPR64,
306     Kind_HWRegs,
307     Kind_FGR32Regs,
308     Kind_FGRH32Regs,
309     Kind_FGR64Regs,
310     Kind_AFGR64Regs,
311     Kind_CCRRegs,
312     Kind_FCCRegs,
313     Kind_ACC64DSP,
314     Kind_LO32DSP,
315     Kind_HI32DSP,
316     Kind_COP2,
317     Kind_MSA128BRegs,
318     Kind_MSA128HRegs,
319     Kind_MSA128WRegs,
320     Kind_MSA128DRegs,
321     Kind_MSA128CtrlRegs
322   };
323
324 private:
325   enum KindTy {
326     k_CondCode,
327     k_CoprocNum,
328     k_Immediate,
329     k_Memory,
330     k_PostIndexRegister,
331     k_Register,
332     k_PtrReg,
333     k_Token,
334     k_LSAImm
335   } Kind;
336
337   MipsOperand(KindTy K) : MCParsedAsmOperand(), Kind(K) {}
338
339   struct Token {
340     const char *Data;
341     unsigned Length;
342   };
343
344   struct RegOp {
345     unsigned RegNum;
346     RegisterKind Kind;
347   };
348
349   struct ImmOp {
350     const MCExpr *Val;
351   };
352
353   struct MemOp {
354     unsigned Base;
355     const MCExpr *Off;
356   };
357
358   union {
359     struct Token Tok;
360     struct RegOp Reg;
361     struct ImmOp Imm;
362     struct MemOp Mem;
363   };
364
365   SMLoc StartLoc, EndLoc;
366
367 public:
368   void addRegOperands(MCInst &Inst, unsigned N) const {
369     assert(N == 1 && "Invalid number of operands!");
370     Inst.addOperand(MCOperand::CreateReg(getReg()));
371   }
372
373   void addPtrRegOperands(MCInst &Inst, unsigned N) const {
374     assert(N == 1 && "Invalid number of operands!");
375     Inst.addOperand(MCOperand::CreateReg(getPtrReg()));
376   }
377
378   void addExpr(MCInst &Inst, const MCExpr *Expr) const {
379     // Add as immediate when possible.  Null MCExpr = 0.
380     if (Expr == 0)
381       Inst.addOperand(MCOperand::CreateImm(0));
382     else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr))
383       Inst.addOperand(MCOperand::CreateImm(CE->getValue()));
384     else
385       Inst.addOperand(MCOperand::CreateExpr(Expr));
386   }
387
388   void addImmOperands(MCInst &Inst, unsigned N) const {
389     assert(N == 1 && "Invalid number of operands!");
390     const MCExpr *Expr = getImm();
391     addExpr(Inst, Expr);
392   }
393
394   void addMemOperands(MCInst &Inst, unsigned N) const {
395     assert(N == 2 && "Invalid number of operands!");
396
397     Inst.addOperand(MCOperand::CreateReg(getMemBase()));
398
399     const MCExpr *Expr = getMemOff();
400     addExpr(Inst, Expr);
401   }
402
403   bool isReg() const { return Kind == k_Register; }
404   bool isImm() const { return Kind == k_Immediate; }
405   bool isToken() const { return Kind == k_Token; }
406   bool isMem() const { return Kind == k_Memory; }
407   bool isPtrReg() const { return Kind == k_PtrReg; }
408   bool isInvNum() const { return Kind == k_Immediate; }
409   bool isLSAImm() const { return Kind == k_LSAImm; }
410
411   StringRef getToken() const {
412     assert(Kind == k_Token && "Invalid access!");
413     return StringRef(Tok.Data, Tok.Length);
414   }
415
416   unsigned getReg() const {
417     assert((Kind == k_Register) && "Invalid access!");
418     return Reg.RegNum;
419   }
420
421   unsigned getPtrReg() const {
422     assert((Kind == k_PtrReg) && "Invalid access!");
423     return Reg.RegNum;
424   }
425
426   void setRegKind(RegisterKind RegKind) {
427     assert((Kind == k_Register || Kind == k_PtrReg) && "Invalid access!");
428     Reg.Kind = RegKind;
429   }
430
431   const MCExpr *getImm() const {
432     assert((Kind == k_Immediate || Kind == k_LSAImm) && "Invalid access!");
433     return Imm.Val;
434   }
435
436   unsigned getMemBase() const {
437     assert((Kind == k_Memory) && "Invalid access!");
438     return Mem.Base;
439   }
440
441   const MCExpr *getMemOff() const {
442     assert((Kind == k_Memory) && "Invalid access!");
443     return Mem.Off;
444   }
445
446   static MipsOperand *CreateToken(StringRef Str, SMLoc S) {
447     MipsOperand *Op = new MipsOperand(k_Token);
448     Op->Tok.Data = Str.data();
449     Op->Tok.Length = Str.size();
450     Op->StartLoc = S;
451     Op->EndLoc = S;
452     return Op;
453   }
454
455   static MipsOperand *CreateReg(unsigned RegNum, SMLoc S, SMLoc E) {
456     MipsOperand *Op = new MipsOperand(k_Register);
457     Op->Reg.RegNum = RegNum;
458     Op->StartLoc = S;
459     Op->EndLoc = E;
460     return Op;
461   }
462
463   static MipsOperand *CreatePtrReg(unsigned RegNum, SMLoc S, SMLoc E) {
464     MipsOperand *Op = new MipsOperand(k_PtrReg);
465     Op->Reg.RegNum = RegNum;
466     Op->StartLoc = S;
467     Op->EndLoc = E;
468     return Op;
469   }
470
471   static MipsOperand *CreateImm(const MCExpr *Val, SMLoc S, SMLoc E) {
472     MipsOperand *Op = new MipsOperand(k_Immediate);
473     Op->Imm.Val = Val;
474     Op->StartLoc = S;
475     Op->EndLoc = E;
476     return Op;
477   }
478
479   static MipsOperand *CreateLSAImm(const MCExpr *Val, SMLoc S, SMLoc E) {
480     MipsOperand *Op = new MipsOperand(k_LSAImm);
481     Op->Imm.Val = Val;
482     Op->StartLoc = S;
483     Op->EndLoc = E;
484     return Op;
485   }
486
487   static MipsOperand *CreateMem(unsigned Base, const MCExpr *Off, SMLoc S,
488                                 SMLoc E) {
489     MipsOperand *Op = new MipsOperand(k_Memory);
490     Op->Mem.Base = Base;
491     Op->Mem.Off = Off;
492     Op->StartLoc = S;
493     Op->EndLoc = E;
494     return Op;
495   }
496
497   bool isGPR32Asm() const {
498     return Kind == k_Register && Reg.Kind == Kind_GPR32;
499   }
500   void addRegAsmOperands(MCInst &Inst, unsigned N) const {
501     Inst.addOperand(MCOperand::CreateReg(Reg.RegNum));
502   }
503
504   bool isGPR64Asm() const {
505     return Kind == k_Register && Reg.Kind == Kind_GPR64;
506   }
507
508   bool isHWRegsAsm() const {
509     assert((Kind == k_Register) && "Invalid access!");
510     return Reg.Kind == Kind_HWRegs;
511   }
512
513   bool isCCRAsm() const {
514     assert((Kind == k_Register) && "Invalid access!");
515     return Reg.Kind == Kind_CCRRegs;
516   }
517
518   bool isAFGR64Asm() const {
519     return Kind == k_Register && Reg.Kind == Kind_AFGR64Regs;
520   }
521
522   bool isFGR64Asm() const {
523     return Kind == k_Register && Reg.Kind == Kind_FGR64Regs;
524   }
525
526   bool isFGR32Asm() const {
527     return (Kind == k_Register) && Reg.Kind == Kind_FGR32Regs;
528   }
529
530   bool isFGRH32Asm() const {
531     return (Kind == k_Register) && Reg.Kind == Kind_FGRH32Regs;
532   }
533
534   bool isFCCRegsAsm() const {
535     return (Kind == k_Register) && Reg.Kind == Kind_FCCRegs;
536   }
537
538   bool isACC64DSPAsm() const {
539     return Kind == k_Register && Reg.Kind == Kind_ACC64DSP;
540   }
541
542   bool isLO32DSPAsm() const {
543     return Kind == k_Register && Reg.Kind == Kind_LO32DSP;
544   }
545
546   bool isHI32DSPAsm() const {
547     return Kind == k_Register && Reg.Kind == Kind_HI32DSP;
548   }
549
550   bool isCOP2Asm() const { return Kind == k_Register && Reg.Kind == Kind_COP2; }
551
552   bool isMSA128BAsm() const {
553     return Kind == k_Register && Reg.Kind == Kind_MSA128BRegs;
554   }
555
556   bool isMSA128HAsm() const {
557     return Kind == k_Register && Reg.Kind == Kind_MSA128HRegs;
558   }
559
560   bool isMSA128WAsm() const {
561     return Kind == k_Register && Reg.Kind == Kind_MSA128WRegs;
562   }
563
564   bool isMSA128DAsm() const {
565     return Kind == k_Register && Reg.Kind == Kind_MSA128DRegs;
566   }
567
568   bool isMSA128CRAsm() const {
569     return Kind == k_Register && Reg.Kind == Kind_MSA128CtrlRegs;
570   }
571
572   /// getStartLoc - Get the location of the first token of this operand.
573   SMLoc getStartLoc() const { return StartLoc; }
574   /// getEndLoc - Get the location of the last token of this operand.
575   SMLoc getEndLoc() const { return EndLoc; }
576
577   virtual void print(raw_ostream &OS) const {
578     llvm_unreachable("unimplemented!");
579   }
580 }; // class MipsOperand
581 } // namespace
582
583 namespace llvm {
584 extern const MCInstrDesc MipsInsts[];
585 }
586 static const MCInstrDesc &getInstDesc(unsigned Opcode) {
587   return MipsInsts[Opcode];
588 }
589
590 bool MipsAsmParser::processInstruction(MCInst &Inst, SMLoc IDLoc,
591                                        SmallVectorImpl<MCInst> &Instructions) {
592   const MCInstrDesc &MCID = getInstDesc(Inst.getOpcode());
593
594   Inst.setLoc(IDLoc);
595
596   if (MCID.isBranch() || MCID.isCall()) {
597     const unsigned Opcode = Inst.getOpcode();
598     MCOperand Offset;
599
600     switch (Opcode) {
601     default:
602       break;
603     case Mips::BEQ:
604     case Mips::BNE:
605       assert(MCID.getNumOperands() == 3 && "unexpected number of operands");
606       Offset = Inst.getOperand(2);
607       if (!Offset.isImm())
608         break; // We'll deal with this situation later on when applying fixups.
609       if (!isIntN(isMicroMips() ? 17 : 18, Offset.getImm()))
610         return Error(IDLoc, "branch target out of range");
611       if (OffsetToAlignment(Offset.getImm(), 1LL << (isMicroMips() ? 1 : 2)))
612         return Error(IDLoc, "branch to misaligned address");
613       break;
614     case Mips::BGEZ:
615     case Mips::BGTZ:
616     case Mips::BLEZ:
617     case Mips::BLTZ:
618     case Mips::BGEZAL:
619     case Mips::BLTZAL:
620     case Mips::BC1F:
621     case Mips::BC1T:
622       assert(MCID.getNumOperands() == 2 && "unexpected number of operands");
623       Offset = Inst.getOperand(1);
624       if (!Offset.isImm())
625         break; // We'll deal with this situation later on when applying fixups.
626       if (!isIntN(isMicroMips() ? 17 : 18, Offset.getImm()))
627         return Error(IDLoc, "branch target out of range");
628       if (OffsetToAlignment(Offset.getImm(), 1LL << (isMicroMips() ? 1 : 2)))
629         return Error(IDLoc, "branch to misaligned address");
630       break;
631     }
632   }
633
634   if (MCID.hasDelaySlot() && Options.isReorder()) {
635     // If this instruction has a delay slot and .set reorder is active,
636     // emit a NOP after it.
637     Instructions.push_back(Inst);
638     MCInst NopInst;
639     NopInst.setOpcode(Mips::SLL);
640     NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO));
641     NopInst.addOperand(MCOperand::CreateReg(Mips::ZERO));
642     NopInst.addOperand(MCOperand::CreateImm(0));
643     Instructions.push_back(NopInst);
644     return false;
645   }
646
647   if (MCID.mayLoad() || MCID.mayStore()) {
648     // Check the offset of memory operand, if it is a symbol
649     // reference or immediate we may have to expand instructions.
650     for (unsigned i = 0; i < MCID.getNumOperands(); i++) {
651       const MCOperandInfo &OpInfo = MCID.OpInfo[i];
652       if ((OpInfo.OperandType == MCOI::OPERAND_MEMORY) ||
653           (OpInfo.OperandType == MCOI::OPERAND_UNKNOWN)) {
654         MCOperand &Op = Inst.getOperand(i);
655         if (Op.isImm()) {
656           int MemOffset = Op.getImm();
657           if (MemOffset < -32768 || MemOffset > 32767) {
658             // Offset can't exceed 16bit value.
659             expandMemInst(Inst, IDLoc, Instructions, MCID.mayLoad(), true);
660             return false;
661           }
662         } else if (Op.isExpr()) {
663           const MCExpr *Expr = Op.getExpr();
664           if (Expr->getKind() == MCExpr::SymbolRef) {
665             const MCSymbolRefExpr *SR =
666                 static_cast<const MCSymbolRefExpr *>(Expr);
667             if (SR->getKind() == MCSymbolRefExpr::VK_None) {
668               // Expand symbol.
669               expandMemInst(Inst, IDLoc, Instructions, MCID.mayLoad(), false);
670               return false;
671             }
672           } else if (!isEvaluated(Expr)) {
673             expandMemInst(Inst, IDLoc, Instructions, MCID.mayLoad(), false);
674             return false;
675           }
676         }
677       }
678     } // for
679   }   // if load/store
680
681   if (needsExpansion(Inst))
682     expandInstruction(Inst, IDLoc, Instructions);
683   else
684     Instructions.push_back(Inst);
685
686   return false;
687 }
688
689 bool MipsAsmParser::needsExpansion(MCInst &Inst) {
690
691   switch (Inst.getOpcode()) {
692   case Mips::LoadImm32Reg:
693   case Mips::LoadAddr32Imm:
694   case Mips::LoadAddr32Reg:
695   case Mips::SUBi:
696   case Mips::SUBiu:
697   case Mips::DSUBi:
698   case Mips::DSUBiu:
699     return true;
700   default:
701     return false;
702   }
703 }
704
705 void MipsAsmParser::expandInstruction(MCInst &Inst, SMLoc IDLoc,
706                                       SmallVectorImpl<MCInst> &Instructions) {
707   switch (Inst.getOpcode()) {
708   case Mips::LoadImm32Reg:
709     return expandLoadImm(Inst, IDLoc, Instructions);
710   case Mips::LoadAddr32Imm:
711     return expandLoadAddressImm(Inst, IDLoc, Instructions);
712   case Mips::LoadAddr32Reg:
713     return expandLoadAddressReg(Inst, IDLoc, Instructions);
714   case Mips::SUBi:
715     Instructions.push_back(MCInstBuilder(Mips::ADDi)
716                                .addReg(Inst.getOperand(0).getReg())
717                                .addReg(Inst.getOperand(1).getReg())
718                                .addImm(-Inst.getOperand(2).getImm()));
719     return;
720   case Mips::SUBiu:
721     Instructions.push_back(MCInstBuilder(Mips::ADDiu)
722                                .addReg(Inst.getOperand(0).getReg())
723                                .addReg(Inst.getOperand(1).getReg())
724                                .addImm(-Inst.getOperand(2).getImm()));
725     return;
726   case Mips::DSUBi:
727     Instructions.push_back(MCInstBuilder(Mips::DADDi)
728                                .addReg(Inst.getOperand(0).getReg())
729                                .addReg(Inst.getOperand(1).getReg())
730                                .addImm(-Inst.getOperand(2).getImm()));
731     return;
732   case Mips::DSUBiu:
733     Instructions.push_back(MCInstBuilder(Mips::DADDiu)
734                                .addReg(Inst.getOperand(0).getReg())
735                                .addReg(Inst.getOperand(1).getReg())
736                                .addImm(-Inst.getOperand(2).getImm()));
737     return;
738   }
739 }
740
741 void MipsAsmParser::expandLoadImm(MCInst &Inst, SMLoc IDLoc,
742                                   SmallVectorImpl<MCInst> &Instructions) {
743   MCInst tmpInst;
744   const MCOperand &ImmOp = Inst.getOperand(1);
745   assert(ImmOp.isImm() && "expected immediate operand kind");
746   const MCOperand &RegOp = Inst.getOperand(0);
747   assert(RegOp.isReg() && "expected register operand kind");
748
749   int ImmValue = ImmOp.getImm();
750   tmpInst.setLoc(IDLoc);
751   if (0 <= ImmValue && ImmValue <= 65535) {
752     // For 0 <= j <= 65535.
753     // li d,j => ori d,$zero,j
754     tmpInst.setOpcode(Mips::ORi);
755     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
756     tmpInst.addOperand(MCOperand::CreateReg(Mips::ZERO));
757     tmpInst.addOperand(MCOperand::CreateImm(ImmValue));
758     Instructions.push_back(tmpInst);
759   } else if (ImmValue < 0 && ImmValue >= -32768) {
760     // For -32768 <= j < 0.
761     // li d,j => addiu d,$zero,j
762     tmpInst.setOpcode(Mips::ADDiu);
763     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
764     tmpInst.addOperand(MCOperand::CreateReg(Mips::ZERO));
765     tmpInst.addOperand(MCOperand::CreateImm(ImmValue));
766     Instructions.push_back(tmpInst);
767   } else {
768     // For any other value of j that is representable as a 32-bit integer.
769     // li d,j => lui d,hi16(j)
770     //           ori d,d,lo16(j)
771     tmpInst.setOpcode(Mips::LUi);
772     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
773     tmpInst.addOperand(MCOperand::CreateImm((ImmValue & 0xffff0000) >> 16));
774     Instructions.push_back(tmpInst);
775     tmpInst.clear();
776     tmpInst.setOpcode(Mips::ORi);
777     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
778     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
779     tmpInst.addOperand(MCOperand::CreateImm(ImmValue & 0xffff));
780     tmpInst.setLoc(IDLoc);
781     Instructions.push_back(tmpInst);
782   }
783 }
784
785 void
786 MipsAsmParser::expandLoadAddressReg(MCInst &Inst, SMLoc IDLoc,
787                                     SmallVectorImpl<MCInst> &Instructions) {
788   MCInst tmpInst;
789   const MCOperand &ImmOp = Inst.getOperand(2);
790   assert(ImmOp.isImm() && "expected immediate operand kind");
791   const MCOperand &SrcRegOp = Inst.getOperand(1);
792   assert(SrcRegOp.isReg() && "expected register operand kind");
793   const MCOperand &DstRegOp = Inst.getOperand(0);
794   assert(DstRegOp.isReg() && "expected register operand kind");
795   int ImmValue = ImmOp.getImm();
796   if (-32768 <= ImmValue && ImmValue <= 65535) {
797     // For -32768 <= j <= 65535.
798     // la d,j(s) => addiu d,s,j
799     tmpInst.setOpcode(Mips::ADDiu);
800     tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg()));
801     tmpInst.addOperand(MCOperand::CreateReg(SrcRegOp.getReg()));
802     tmpInst.addOperand(MCOperand::CreateImm(ImmValue));
803     Instructions.push_back(tmpInst);
804   } else {
805     // For any other value of j that is representable as a 32-bit integer.
806     // la d,j(s) => lui d,hi16(j)
807     //              ori d,d,lo16(j)
808     //              addu d,d,s
809     tmpInst.setOpcode(Mips::LUi);
810     tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg()));
811     tmpInst.addOperand(MCOperand::CreateImm((ImmValue & 0xffff0000) >> 16));
812     Instructions.push_back(tmpInst);
813     tmpInst.clear();
814     tmpInst.setOpcode(Mips::ORi);
815     tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg()));
816     tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg()));
817     tmpInst.addOperand(MCOperand::CreateImm(ImmValue & 0xffff));
818     Instructions.push_back(tmpInst);
819     tmpInst.clear();
820     tmpInst.setOpcode(Mips::ADDu);
821     tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg()));
822     tmpInst.addOperand(MCOperand::CreateReg(DstRegOp.getReg()));
823     tmpInst.addOperand(MCOperand::CreateReg(SrcRegOp.getReg()));
824     Instructions.push_back(tmpInst);
825   }
826 }
827
828 void
829 MipsAsmParser::expandLoadAddressImm(MCInst &Inst, SMLoc IDLoc,
830                                     SmallVectorImpl<MCInst> &Instructions) {
831   MCInst tmpInst;
832   const MCOperand &ImmOp = Inst.getOperand(1);
833   assert(ImmOp.isImm() && "expected immediate operand kind");
834   const MCOperand &RegOp = Inst.getOperand(0);
835   assert(RegOp.isReg() && "expected register operand kind");
836   int ImmValue = ImmOp.getImm();
837   if (-32768 <= ImmValue && ImmValue <= 65535) {
838     // For -32768 <= j <= 65535.
839     // la d,j => addiu d,$zero,j
840     tmpInst.setOpcode(Mips::ADDiu);
841     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
842     tmpInst.addOperand(MCOperand::CreateReg(Mips::ZERO));
843     tmpInst.addOperand(MCOperand::CreateImm(ImmValue));
844     Instructions.push_back(tmpInst);
845   } else {
846     // For any other value of j that is representable as a 32-bit integer.
847     // la d,j => lui d,hi16(j)
848     //           ori d,d,lo16(j)
849     tmpInst.setOpcode(Mips::LUi);
850     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
851     tmpInst.addOperand(MCOperand::CreateImm((ImmValue & 0xffff0000) >> 16));
852     Instructions.push_back(tmpInst);
853     tmpInst.clear();
854     tmpInst.setOpcode(Mips::ORi);
855     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
856     tmpInst.addOperand(MCOperand::CreateReg(RegOp.getReg()));
857     tmpInst.addOperand(MCOperand::CreateImm(ImmValue & 0xffff));
858     Instructions.push_back(tmpInst);
859   }
860 }
861
862 void MipsAsmParser::expandMemInst(MCInst &Inst, SMLoc IDLoc,
863                                   SmallVectorImpl<MCInst> &Instructions,
864                                   bool isLoad, bool isImmOpnd) {
865   const MCSymbolRefExpr *SR;
866   MCInst TempInst;
867   unsigned ImmOffset, HiOffset, LoOffset;
868   const MCExpr *ExprOffset;
869   unsigned TmpRegNum;
870   unsigned AtRegNum = getReg(
871       (isMips64()) ? Mips::GPR64RegClassID : Mips::GPR32RegClassID, getATReg());
872   // 1st operand is either the source or destination register.
873   assert(Inst.getOperand(0).isReg() && "expected register operand kind");
874   unsigned RegOpNum = Inst.getOperand(0).getReg();
875   // 2nd operand is the base register.
876   assert(Inst.getOperand(1).isReg() && "expected register operand kind");
877   unsigned BaseRegNum = Inst.getOperand(1).getReg();
878   // 3rd operand is either an immediate or expression.
879   if (isImmOpnd) {
880     assert(Inst.getOperand(2).isImm() && "expected immediate operand kind");
881     ImmOffset = Inst.getOperand(2).getImm();
882     LoOffset = ImmOffset & 0x0000ffff;
883     HiOffset = (ImmOffset & 0xffff0000) >> 16;
884     // If msb of LoOffset is 1(negative number) we must increment HiOffset.
885     if (LoOffset & 0x8000)
886       HiOffset++;
887   } else
888     ExprOffset = Inst.getOperand(2).getExpr();
889   // All instructions will have the same location.
890   TempInst.setLoc(IDLoc);
891   // 1st instruction in expansion is LUi. For load instruction we can use
892   // the dst register as a temporary if base and dst are different,
893   // but for stores we must use $at.
894   TmpRegNum = (isLoad && (BaseRegNum != RegOpNum)) ? RegOpNum : AtRegNum;
895   TempInst.setOpcode(Mips::LUi);
896   TempInst.addOperand(MCOperand::CreateReg(TmpRegNum));
897   if (isImmOpnd)
898     TempInst.addOperand(MCOperand::CreateImm(HiOffset));
899   else {
900     if (ExprOffset->getKind() == MCExpr::SymbolRef) {
901       SR = static_cast<const MCSymbolRefExpr *>(ExprOffset);
902       const MCSymbolRefExpr *HiExpr = MCSymbolRefExpr::Create(
903           SR->getSymbol().getName(), MCSymbolRefExpr::VK_Mips_ABS_HI,
904           getContext());
905       TempInst.addOperand(MCOperand::CreateExpr(HiExpr));
906     } else {
907       const MCExpr *HiExpr = evaluateRelocExpr(ExprOffset, "hi");
908       TempInst.addOperand(MCOperand::CreateExpr(HiExpr));
909     }
910   }
911   // Add the instruction to the list.
912   Instructions.push_back(TempInst);
913   // Prepare TempInst for next instruction.
914   TempInst.clear();
915   // Add temp register to base.
916   TempInst.setOpcode(Mips::ADDu);
917   TempInst.addOperand(MCOperand::CreateReg(TmpRegNum));
918   TempInst.addOperand(MCOperand::CreateReg(TmpRegNum));
919   TempInst.addOperand(MCOperand::CreateReg(BaseRegNum));
920   Instructions.push_back(TempInst);
921   TempInst.clear();
922   // And finally, create original instruction with low part
923   // of offset and new base.
924   TempInst.setOpcode(Inst.getOpcode());
925   TempInst.addOperand(MCOperand::CreateReg(RegOpNum));
926   TempInst.addOperand(MCOperand::CreateReg(TmpRegNum));
927   if (isImmOpnd)
928     TempInst.addOperand(MCOperand::CreateImm(LoOffset));
929   else {
930     if (ExprOffset->getKind() == MCExpr::SymbolRef) {
931       const MCSymbolRefExpr *LoExpr = MCSymbolRefExpr::Create(
932           SR->getSymbol().getName(), MCSymbolRefExpr::VK_Mips_ABS_LO,
933           getContext());
934       TempInst.addOperand(MCOperand::CreateExpr(LoExpr));
935     } else {
936       const MCExpr *LoExpr = evaluateRelocExpr(ExprOffset, "lo");
937       TempInst.addOperand(MCOperand::CreateExpr(LoExpr));
938     }
939   }
940   Instructions.push_back(TempInst);
941   TempInst.clear();
942 }
943
944 bool MipsAsmParser::MatchAndEmitInstruction(
945     SMLoc IDLoc, unsigned &Opcode,
946     SmallVectorImpl<MCParsedAsmOperand *> &Operands, MCStreamer &Out,
947     unsigned &ErrorInfo, bool MatchingInlineAsm) {
948   MCInst Inst;
949   SmallVector<MCInst, 8> Instructions;
950   unsigned MatchResult =
951       MatchInstructionImpl(Operands, Inst, ErrorInfo, MatchingInlineAsm);
952
953   switch (MatchResult) {
954   default:
955     break;
956   case Match_Success: {
957     if (processInstruction(Inst, IDLoc, Instructions))
958       return true;
959     for (unsigned i = 0; i < Instructions.size(); i++)
960       Out.EmitInstruction(Instructions[i], STI);
961     return false;
962   }
963   case Match_MissingFeature:
964     Error(IDLoc, "instruction requires a CPU feature not currently enabled");
965     return true;
966   case Match_InvalidOperand: {
967     SMLoc ErrorLoc = IDLoc;
968     if (ErrorInfo != ~0U) {
969       if (ErrorInfo >= Operands.size())
970         return Error(IDLoc, "too few operands for instruction");
971
972       ErrorLoc = ((MipsOperand *)Operands[ErrorInfo])->getStartLoc();
973       if (ErrorLoc == SMLoc())
974         ErrorLoc = IDLoc;
975     }
976
977     return Error(ErrorLoc, "invalid operand for instruction");
978   }
979   case Match_MnemonicFail:
980     return Error(IDLoc, "invalid instruction");
981   }
982   return true;
983 }
984
985 int MipsAsmParser::matchCPURegisterName(StringRef Name) {
986   int CC;
987
988   if (Name == "at")
989     return getATReg();
990
991   CC = StringSwitch<unsigned>(Name)
992            .Case("zero", 0)
993            .Case("a0", 4)
994            .Case("a1", 5)
995            .Case("a2", 6)
996            .Case("a3", 7)
997            .Case("v0", 2)
998            .Case("v1", 3)
999            .Case("s0", 16)
1000            .Case("s1", 17)
1001            .Case("s2", 18)
1002            .Case("s3", 19)
1003            .Case("s4", 20)
1004            .Case("s5", 21)
1005            .Case("s6", 22)
1006            .Case("s7", 23)
1007            .Case("k0", 26)
1008            .Case("k1", 27)
1009            .Case("sp", 29)
1010            .Case("fp", 30)
1011            .Case("gp", 28)
1012            .Case("ra", 31)
1013            .Case("t0", 8)
1014            .Case("t1", 9)
1015            .Case("t2", 10)
1016            .Case("t3", 11)
1017            .Case("t4", 12)
1018            .Case("t5", 13)
1019            .Case("t6", 14)
1020            .Case("t7", 15)
1021            .Case("t8", 24)
1022            .Case("t9", 25)
1023            .Default(-1);
1024
1025   // Although SGI documentation just cuts out t0-t3 for n32/n64,
1026   // GNU pushes the values of t0-t3 to override the o32/o64 values for t4-t7
1027   // We are supporting both cases, so for t0-t3 we'll just push them to t4-t7.
1028   if (isMips64() && 8 <= CC && CC <= 11)
1029     CC += 4;
1030
1031   if (CC == -1 && isMips64())
1032     CC = StringSwitch<unsigned>(Name)
1033              .Case("a4", 8)
1034              .Case("a5", 9)
1035              .Case("a6", 10)
1036              .Case("a7", 11)
1037              .Case("kt0", 26)
1038              .Case("kt1", 27)
1039              .Case("s8", 30)
1040              .Default(-1);
1041
1042   return CC;
1043 }
1044
1045 int MipsAsmParser::matchFPURegisterName(StringRef Name) {
1046
1047   if (Name[0] == 'f') {
1048     StringRef NumString = Name.substr(1);
1049     unsigned IntVal;
1050     if (NumString.getAsInteger(10, IntVal))
1051       return -1;     // This is not an integer.
1052     if (IntVal > 31) // Maximum index for fpu register.
1053       return -1;
1054     return IntVal;
1055   }
1056   return -1;
1057 }
1058
1059 int MipsAsmParser::matchFCCRegisterName(StringRef Name) {
1060
1061   if (Name.startswith("fcc")) {
1062     StringRef NumString = Name.substr(3);
1063     unsigned IntVal;
1064     if (NumString.getAsInteger(10, IntVal))
1065       return -1;    // This is not an integer.
1066     if (IntVal > 7) // There are only 8 fcc registers.
1067       return -1;
1068     return IntVal;
1069   }
1070   return -1;
1071 }
1072
1073 int MipsAsmParser::matchACRegisterName(StringRef Name) {
1074
1075   if (Name.startswith("ac")) {
1076     StringRef NumString = Name.substr(2);
1077     unsigned IntVal;
1078     if (NumString.getAsInteger(10, IntVal))
1079       return -1;    // This is not an integer.
1080     if (IntVal > 3) // There are only 3 acc registers.
1081       return -1;
1082     return IntVal;
1083   }
1084   return -1;
1085 }
1086
1087 int MipsAsmParser::matchMSA128RegisterName(StringRef Name) {
1088   unsigned IntVal;
1089
1090   if (Name.front() != 'w' || Name.drop_front(1).getAsInteger(10, IntVal))
1091     return -1;
1092
1093   if (IntVal > 31)
1094     return -1;
1095
1096   return IntVal;
1097 }
1098
1099 int MipsAsmParser::matchMSA128CtrlRegisterName(StringRef Name) {
1100   int CC;
1101
1102   CC = StringSwitch<unsigned>(Name)
1103            .Case("msair", 0)
1104            .Case("msacsr", 1)
1105            .Case("msaaccess", 2)
1106            .Case("msasave", 3)
1107            .Case("msamodify", 4)
1108            .Case("msarequest", 5)
1109            .Case("msamap", 6)
1110            .Case("msaunmap", 7)
1111            .Default(-1);
1112
1113   return CC;
1114 }
1115
1116 int MipsAsmParser::matchRegisterName(StringRef Name, bool is64BitReg) {
1117
1118   int CC;
1119   CC = matchCPURegisterName(Name);
1120   if (CC != -1)
1121     return matchRegisterByNumber(CC, is64BitReg ? Mips::GPR64RegClassID
1122                                                 : Mips::GPR32RegClassID);
1123   CC = matchFPURegisterName(Name);
1124   // TODO: decide about fpu register class
1125   if (CC != -1)
1126     return matchRegisterByNumber(CC, isFP64() ? Mips::FGR64RegClassID
1127                                               : Mips::FGR32RegClassID);
1128   return matchMSA128RegisterName(Name);
1129 }
1130
1131 int MipsAsmParser::regKindToRegClass(int RegKind) {
1132
1133   switch (RegKind) {
1134   case MipsOperand::Kind_GPR32:
1135     return Mips::GPR32RegClassID;
1136   case MipsOperand::Kind_GPR64:
1137     return Mips::GPR64RegClassID;
1138   case MipsOperand::Kind_HWRegs:
1139     return Mips::HWRegsRegClassID;
1140   case MipsOperand::Kind_FGR32Regs:
1141     return Mips::FGR32RegClassID;
1142   case MipsOperand::Kind_FGRH32Regs:
1143     return Mips::FGRH32RegClassID;
1144   case MipsOperand::Kind_FGR64Regs:
1145     return Mips::FGR64RegClassID;
1146   case MipsOperand::Kind_AFGR64Regs:
1147     return Mips::AFGR64RegClassID;
1148   case MipsOperand::Kind_CCRRegs:
1149     return Mips::CCRRegClassID;
1150   case MipsOperand::Kind_ACC64DSP:
1151     return Mips::ACC64DSPRegClassID;
1152   case MipsOperand::Kind_FCCRegs:
1153     return Mips::FCCRegClassID;
1154   case MipsOperand::Kind_MSA128BRegs:
1155     return Mips::MSA128BRegClassID;
1156   case MipsOperand::Kind_MSA128HRegs:
1157     return Mips::MSA128HRegClassID;
1158   case MipsOperand::Kind_MSA128WRegs:
1159     return Mips::MSA128WRegClassID;
1160   case MipsOperand::Kind_MSA128DRegs:
1161     return Mips::MSA128DRegClassID;
1162   case MipsOperand::Kind_MSA128CtrlRegs:
1163     return Mips::MSACtrlRegClassID;
1164   default:
1165     return -1;
1166   }
1167 }
1168
1169 bool MipsAssemblerOptions::setATReg(unsigned Reg) {
1170   if (Reg > 31)
1171     return false;
1172
1173   aTReg = Reg;
1174   return true;
1175 }
1176
1177 int MipsAsmParser::getATReg() {
1178   int AT = Options.getATRegNum();
1179   if (AT == 0)
1180     TokError("Pseudo instruction requires $at, which is not available");
1181   return AT;
1182 }
1183
1184 unsigned MipsAsmParser::getReg(int RC, int RegNo) {
1185   return *(getContext().getRegisterInfo()->getRegClass(RC).begin() + RegNo);
1186 }
1187
1188 int MipsAsmParser::matchRegisterByNumber(unsigned RegNum, unsigned RegClass) {
1189   if (RegNum >
1190       getContext().getRegisterInfo()->getRegClass(RegClass).getNumRegs())
1191     return -1;
1192
1193   return getReg(RegClass, RegNum);
1194 }
1195
1196 int MipsAsmParser::tryParseRegister(bool is64BitReg) {
1197   const AsmToken &Tok = Parser.getTok();
1198   int RegNum = -1;
1199
1200   if (Tok.is(AsmToken::Identifier)) {
1201     std::string lowerCase = Tok.getString().lower();
1202     RegNum = matchRegisterName(lowerCase, is64BitReg);
1203   } else if (Tok.is(AsmToken::Integer))
1204     RegNum = matchRegisterByNumber(static_cast<unsigned>(Tok.getIntVal()),
1205                                    is64BitReg ? Mips::GPR64RegClassID
1206                                               : Mips::GPR32RegClassID);
1207   return RegNum;
1208 }
1209
1210 bool MipsAsmParser::tryParseRegisterOperand(
1211     SmallVectorImpl<MCParsedAsmOperand *> &Operands, bool is64BitReg) {
1212
1213   SMLoc S = Parser.getTok().getLoc();
1214   int RegNo = -1;
1215
1216   RegNo = tryParseRegister(is64BitReg);
1217   if (RegNo == -1)
1218     return true;
1219
1220   Operands.push_back(
1221       MipsOperand::CreateReg(RegNo, S, Parser.getTok().getLoc()));
1222   Parser.Lex(); // Eat register token.
1223   return false;
1224 }
1225
1226 bool
1227 MipsAsmParser::ParseOperand(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
1228                             StringRef Mnemonic) {
1229   // Check if the current operand has a custom associated parser, if so, try to
1230   // custom parse the operand, or fallback to the general approach.
1231   OperandMatchResultTy ResTy = MatchOperandParserImpl(Operands, Mnemonic);
1232   if (ResTy == MatchOperand_Success)
1233     return false;
1234   // If there wasn't a custom match, try the generic matcher below. Otherwise,
1235   // there was a match, but an error occurred, in which case, just return that
1236   // the operand parsing failed.
1237   if (ResTy == MatchOperand_ParseFail)
1238     return true;
1239
1240   switch (getLexer().getKind()) {
1241   default:
1242     Error(Parser.getTok().getLoc(), "unexpected token in operand");
1243     return true;
1244   case AsmToken::Dollar: {
1245     // Parse the register.
1246     SMLoc S = Parser.getTok().getLoc();
1247     Parser.Lex(); // Eat dollar token.
1248     // Parse the register operand.
1249     if (!tryParseRegisterOperand(Operands, isMips64())) {
1250       if (getLexer().is(AsmToken::LParen)) {
1251         // Check if it is indexed addressing operand.
1252         Operands.push_back(MipsOperand::CreateToken("(", S));
1253         Parser.Lex(); // Eat the parenthesis.
1254         if (getLexer().isNot(AsmToken::Dollar))
1255           return true;
1256
1257         Parser.Lex(); // Eat the dollar
1258         if (tryParseRegisterOperand(Operands, isMips64()))
1259           return true;
1260
1261         if (!getLexer().is(AsmToken::RParen))
1262           return true;
1263
1264         S = Parser.getTok().getLoc();
1265         Operands.push_back(MipsOperand::CreateToken(")", S));
1266         Parser.Lex();
1267       }
1268       return false;
1269     }
1270     // Maybe it is a symbol reference.
1271     StringRef Identifier;
1272     if (Parser.parseIdentifier(Identifier))
1273       return true;
1274
1275     SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
1276     MCSymbol *Sym = getContext().GetOrCreateSymbol("$" + Identifier);
1277     // Otherwise create a symbol reference.
1278     const MCExpr *Res =
1279         MCSymbolRefExpr::Create(Sym, MCSymbolRefExpr::VK_None, getContext());
1280
1281     Operands.push_back(MipsOperand::CreateImm(Res, S, E));
1282     return false;
1283   }
1284   case AsmToken::Identifier:
1285     // For instruction aliases like "bc1f $Label" dedicated parser will
1286     // eat the '$' sign before failing. So in order to look for appropriate
1287     // label we must check first if we have already consumed '$'.
1288     if (hasConsumedDollar) {
1289       hasConsumedDollar = false;
1290       SMLoc S = Parser.getTok().getLoc();
1291       StringRef Identifier;
1292       if (Parser.parseIdentifier(Identifier))
1293         return true;
1294       SMLoc E =
1295           SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
1296       MCSymbol *Sym = getContext().GetOrCreateSymbol("$" + Identifier);
1297       // Create a symbol reference.
1298       const MCExpr *Res =
1299           MCSymbolRefExpr::Create(Sym, MCSymbolRefExpr::VK_None, getContext());
1300
1301       Operands.push_back(MipsOperand::CreateImm(Res, S, E));
1302       return false;
1303     }
1304     // Look for the existing symbol, we should check if
1305     // we need to assign the proper RegisterKind.
1306     if (searchSymbolAlias(Operands, MipsOperand::Kind_None))
1307       return false;
1308   // Else drop to expression parsing.
1309   case AsmToken::LParen:
1310   case AsmToken::Minus:
1311   case AsmToken::Plus:
1312   case AsmToken::Integer:
1313   case AsmToken::String: {
1314     // Quoted label names.
1315     const MCExpr *IdVal;
1316     SMLoc S = Parser.getTok().getLoc();
1317     if (getParser().parseExpression(IdVal))
1318       return true;
1319     SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
1320     Operands.push_back(MipsOperand::CreateImm(IdVal, S, E));
1321     return false;
1322   }
1323   case AsmToken::Percent: {
1324     // It is a symbol reference or constant expression.
1325     const MCExpr *IdVal;
1326     SMLoc S = Parser.getTok().getLoc(); // Start location of the operand.
1327     if (parseRelocOperand(IdVal))
1328       return true;
1329
1330     SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
1331
1332     Operands.push_back(MipsOperand::CreateImm(IdVal, S, E));
1333     return false;
1334   } // case AsmToken::Percent
1335   } // switch(getLexer().getKind())
1336   return true;
1337 }
1338
1339 const MCExpr *MipsAsmParser::evaluateRelocExpr(const MCExpr *Expr,
1340                                                StringRef RelocStr) {
1341   const MCExpr *Res;
1342   // Check the type of the expression.
1343   if (const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(Expr)) {
1344     // It's a constant, evaluate lo or hi value.
1345     if (RelocStr == "lo") {
1346       short Val = MCE->getValue();
1347       Res = MCConstantExpr::Create(Val, getContext());
1348     } else if (RelocStr == "hi") {
1349       int Val = MCE->getValue();
1350       int LoSign = Val & 0x8000;
1351       Val = (Val & 0xffff0000) >> 16;
1352       // Lower part is treated as a signed int, so if it is negative
1353       // we must add 1 to the hi part to compensate.
1354       if (LoSign)
1355         Val++;
1356       Res = MCConstantExpr::Create(Val, getContext());
1357     } else {
1358       llvm_unreachable("Invalid RelocStr value");
1359     }
1360     return Res;
1361   }
1362
1363   if (const MCSymbolRefExpr *MSRE = dyn_cast<MCSymbolRefExpr>(Expr)) {
1364     // It's a symbol, create a symbolic expression from the symbol.
1365     StringRef Symbol = MSRE->getSymbol().getName();
1366     MCSymbolRefExpr::VariantKind VK = getVariantKind(RelocStr);
1367     Res = MCSymbolRefExpr::Create(Symbol, VK, getContext());
1368     return Res;
1369   }
1370
1371   if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(Expr)) {
1372     MCSymbolRefExpr::VariantKind VK = getVariantKind(RelocStr);
1373
1374     // Check for %hi(sym1-sym2) and %lo(sym1-sym2) expressions.
1375     if (isa<MCSymbolRefExpr>(BE->getLHS()) && isa<MCSymbolRefExpr>(BE->getRHS())
1376         && (VK == MCSymbolRefExpr::VK_Mips_ABS_HI
1377             || VK == MCSymbolRefExpr::VK_Mips_ABS_LO)) {
1378       // Create target expression for %hi(sym1-sym2) and %lo(sym1-sym2).
1379       if (VK == MCSymbolRefExpr::VK_Mips_ABS_HI)
1380         return MipsMCExpr::CreateHi(Expr, getContext());
1381       return MipsMCExpr::CreateLo(Expr, getContext());
1382     }
1383
1384     const MCExpr *LExp = evaluateRelocExpr(BE->getLHS(), RelocStr);
1385     const MCExpr *RExp = evaluateRelocExpr(BE->getRHS(), RelocStr);
1386     Res = MCBinaryExpr::Create(BE->getOpcode(), LExp, RExp, getContext());
1387     return Res;
1388   }
1389
1390   if (const MCUnaryExpr *UN = dyn_cast<MCUnaryExpr>(Expr)) {
1391     const MCExpr *UnExp = evaluateRelocExpr(UN->getSubExpr(), RelocStr);
1392     Res = MCUnaryExpr::Create(UN->getOpcode(), UnExp, getContext());
1393     return Res;
1394   }
1395   // Just return the original expression.
1396   return Expr;
1397 }
1398
1399 bool MipsAsmParser::isEvaluated(const MCExpr *Expr) {
1400
1401   switch (Expr->getKind()) {
1402   case MCExpr::Constant:
1403     return true;
1404   case MCExpr::SymbolRef:
1405     return (cast<MCSymbolRefExpr>(Expr)->getKind() != MCSymbolRefExpr::VK_None);
1406   case MCExpr::Binary:
1407     if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(Expr)) {
1408       if (!isEvaluated(BE->getLHS()))
1409         return false;
1410       return isEvaluated(BE->getRHS());
1411     }
1412   case MCExpr::Unary:
1413     return isEvaluated(cast<MCUnaryExpr>(Expr)->getSubExpr());
1414   case MCExpr::Target:
1415     return true;
1416   }
1417   return false;
1418 }
1419
1420 bool MipsAsmParser::parseRelocOperand(const MCExpr *&Res) {
1421   Parser.Lex();                          // Eat the % token.
1422   const AsmToken &Tok = Parser.getTok(); // Get next token, operation.
1423   if (Tok.isNot(AsmToken::Identifier))
1424     return true;
1425
1426   std::string Str = Tok.getIdentifier().str();
1427
1428   Parser.Lex(); // Eat the identifier.
1429   // Now make an expression from the rest of the operand.
1430   const MCExpr *IdVal;
1431   SMLoc EndLoc;
1432
1433   if (getLexer().getKind() == AsmToken::LParen) {
1434     while (1) {
1435       Parser.Lex(); // Eat the '(' token.
1436       if (getLexer().getKind() == AsmToken::Percent) {
1437         Parser.Lex(); // Eat the % token.
1438         const AsmToken &nextTok = Parser.getTok();
1439         if (nextTok.isNot(AsmToken::Identifier))
1440           return true;
1441         Str += "(%";
1442         Str += nextTok.getIdentifier();
1443         Parser.Lex(); // Eat the identifier.
1444         if (getLexer().getKind() != AsmToken::LParen)
1445           return true;
1446       } else
1447         break;
1448     }
1449     if (getParser().parseParenExpression(IdVal, EndLoc))
1450       return true;
1451
1452     while (getLexer().getKind() == AsmToken::RParen)
1453       Parser.Lex(); // Eat the ')' token.
1454
1455   } else
1456     return true; // Parenthesis must follow the relocation operand.
1457
1458   Res = evaluateRelocExpr(IdVal, Str);
1459   return false;
1460 }
1461
1462 bool MipsAsmParser::ParseRegister(unsigned &RegNo, SMLoc &StartLoc,
1463                                   SMLoc &EndLoc) {
1464   StartLoc = Parser.getTok().getLoc();
1465   RegNo = tryParseRegister(isMips64());
1466   EndLoc = Parser.getTok().getLoc();
1467   return (RegNo == (unsigned)-1);
1468 }
1469
1470 bool MipsAsmParser::parseMemOffset(const MCExpr *&Res, bool isParenExpr) {
1471   SMLoc S;
1472   bool Result = true;
1473
1474   while (getLexer().getKind() == AsmToken::LParen)
1475     Parser.Lex();
1476
1477   switch (getLexer().getKind()) {
1478   default:
1479     return true;
1480   case AsmToken::Identifier:
1481   case AsmToken::LParen:
1482   case AsmToken::Integer:
1483   case AsmToken::Minus:
1484   case AsmToken::Plus:
1485     if (isParenExpr)
1486       Result = getParser().parseParenExpression(Res, S);
1487     else
1488       Result = (getParser().parseExpression(Res));
1489     while (getLexer().getKind() == AsmToken::RParen)
1490       Parser.Lex();
1491     break;
1492   case AsmToken::Percent:
1493     Result = parseRelocOperand(Res);
1494   }
1495   return Result;
1496 }
1497
1498 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseMemOperand(
1499     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1500
1501   const MCExpr *IdVal = 0;
1502   SMLoc S;
1503   bool isParenExpr = false;
1504   MipsAsmParser::OperandMatchResultTy Res = MatchOperand_NoMatch;
1505   // First operand is the offset.
1506   S = Parser.getTok().getLoc();
1507
1508   if (getLexer().getKind() == AsmToken::LParen) {
1509     Parser.Lex();
1510     isParenExpr = true;
1511   }
1512
1513   if (getLexer().getKind() != AsmToken::Dollar) {
1514     if (parseMemOffset(IdVal, isParenExpr))
1515       return MatchOperand_ParseFail;
1516
1517     const AsmToken &Tok = Parser.getTok(); // Get the next token.
1518     if (Tok.isNot(AsmToken::LParen)) {
1519       MipsOperand *Mnemonic = static_cast<MipsOperand *>(Operands[0]);
1520       if (Mnemonic->getToken() == "la") {
1521         SMLoc E =
1522             SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
1523         Operands.push_back(MipsOperand::CreateImm(IdVal, S, E));
1524         return MatchOperand_Success;
1525       }
1526       if (Tok.is(AsmToken::EndOfStatement)) {
1527         SMLoc E =
1528             SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
1529
1530         // Zero register assumed, add a memory operand with ZERO as its base.
1531         Operands.push_back(MipsOperand::CreateMem(
1532             isMips64() ? Mips::ZERO_64 : Mips::ZERO, IdVal, S, E));
1533         return MatchOperand_Success;
1534       }
1535       Error(Parser.getTok().getLoc(), "'(' expected");
1536       return MatchOperand_ParseFail;
1537     }
1538
1539     Parser.Lex(); // Eat the '(' token.
1540   }
1541
1542   Res = parseRegs(Operands, isMips64() ? (int)MipsOperand::Kind_GPR64
1543                                        : (int)MipsOperand::Kind_GPR32);
1544   if (Res != MatchOperand_Success)
1545     return Res;
1546
1547   if (Parser.getTok().isNot(AsmToken::RParen)) {
1548     Error(Parser.getTok().getLoc(), "')' expected");
1549     return MatchOperand_ParseFail;
1550   }
1551
1552   SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
1553
1554   Parser.Lex(); // Eat the ')' token.
1555
1556   if (IdVal == 0)
1557     IdVal = MCConstantExpr::Create(0, getContext());
1558
1559   // Replace the register operand with the memory operand.
1560   MipsOperand *op = static_cast<MipsOperand *>(Operands.back());
1561   int RegNo = op->getReg();
1562   // Remove the register from the operands.
1563   Operands.pop_back();
1564   // Add the memory operand.
1565   if (const MCBinaryExpr *BE = dyn_cast<MCBinaryExpr>(IdVal)) {
1566     int64_t Imm;
1567     if (IdVal->EvaluateAsAbsolute(Imm))
1568       IdVal = MCConstantExpr::Create(Imm, getContext());
1569     else if (BE->getLHS()->getKind() != MCExpr::SymbolRef)
1570       IdVal = MCBinaryExpr::Create(BE->getOpcode(), BE->getRHS(), BE->getLHS(),
1571                                    getContext());
1572   }
1573
1574   Operands.push_back(MipsOperand::CreateMem(RegNo, IdVal, S, E));
1575   delete op;
1576   return MatchOperand_Success;
1577 }
1578
1579 bool MipsAsmParser::parsePtrReg(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
1580                                 int RegKind) {
1581   // If the first token is not '$' we have an error.
1582   if (Parser.getTok().isNot(AsmToken::Dollar))
1583     return false;
1584
1585   SMLoc S = Parser.getTok().getLoc();
1586   Parser.Lex();
1587   AsmToken::TokenKind TkKind = getLexer().getKind();
1588   int Reg;
1589
1590   if (TkKind == AsmToken::Integer) {
1591     Reg = matchRegisterByNumber(Parser.getTok().getIntVal(),
1592                                 regKindToRegClass(RegKind));
1593     if (Reg == -1)
1594       return false;
1595   } else if (TkKind == AsmToken::Identifier) {
1596     if ((Reg = matchCPURegisterName(Parser.getTok().getString().lower())) == -1)
1597       return false;
1598     Reg = getReg(regKindToRegClass(RegKind), Reg);
1599   } else {
1600     return false;
1601   }
1602
1603   MipsOperand *Op = MipsOperand::CreatePtrReg(Reg, S, Parser.getTok().getLoc());
1604   Op->setRegKind((MipsOperand::RegisterKind)RegKind);
1605   Operands.push_back(Op);
1606   Parser.Lex();
1607   return true;
1608 }
1609
1610 MipsAsmParser::OperandMatchResultTy
1611 MipsAsmParser::parsePtrReg(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1612   MipsOperand::RegisterKind RegKind =
1613       isN64() ? MipsOperand::Kind_GPR64 : MipsOperand::Kind_GPR32;
1614
1615   // Parse index register.
1616   if (!parsePtrReg(Operands, RegKind))
1617     return MatchOperand_NoMatch;
1618
1619   // Parse '('.
1620   if (Parser.getTok().isNot(AsmToken::LParen))
1621     return MatchOperand_NoMatch;
1622
1623   Operands.push_back(MipsOperand::CreateToken("(", getLexer().getLoc()));
1624   Parser.Lex();
1625
1626   // Parse base register.
1627   if (!parsePtrReg(Operands, RegKind))
1628     return MatchOperand_NoMatch;
1629
1630   // Parse ')'.
1631   if (Parser.getTok().isNot(AsmToken::RParen))
1632     return MatchOperand_NoMatch;
1633
1634   Operands.push_back(MipsOperand::CreateToken(")", getLexer().getLoc()));
1635   Parser.Lex();
1636
1637   return MatchOperand_Success;
1638 }
1639
1640 MipsAsmParser::OperandMatchResultTy
1641 MipsAsmParser::parseRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
1642                          int RegKind) {
1643   MipsOperand::RegisterKind Kind = (MipsOperand::RegisterKind)RegKind;
1644   if (getLexer().getKind() == AsmToken::Identifier && !hasConsumedDollar) {
1645     if (searchSymbolAlias(Operands, Kind))
1646       return MatchOperand_Success;
1647     return MatchOperand_NoMatch;
1648   }
1649   SMLoc S = Parser.getTok().getLoc();
1650   // If the first token is not '$', we have an error.
1651   if (Parser.getTok().isNot(AsmToken::Dollar) && !hasConsumedDollar)
1652     return MatchOperand_NoMatch;
1653   if (!hasConsumedDollar) {
1654     Parser.Lex(); // Eat the '$'
1655     hasConsumedDollar = true;
1656   }
1657   if (getLexer().getKind() == AsmToken::Identifier) {
1658     int RegNum = -1;
1659     std::string RegName = Parser.getTok().getString().lower();
1660     // Match register by name
1661     switch (RegKind) {
1662     case MipsOperand::Kind_GPR32:
1663     case MipsOperand::Kind_GPR64:
1664       RegNum = matchCPURegisterName(RegName);
1665       break;
1666     case MipsOperand::Kind_AFGR64Regs:
1667     case MipsOperand::Kind_FGR64Regs:
1668     case MipsOperand::Kind_FGR32Regs:
1669     case MipsOperand::Kind_FGRH32Regs:
1670       RegNum = matchFPURegisterName(RegName);
1671       if (RegKind == MipsOperand::Kind_AFGR64Regs)
1672         RegNum /= 2;
1673       else if (RegKind == MipsOperand::Kind_FGRH32Regs && !isFP64())
1674         if (RegNum != -1 && RegNum % 2 != 0)
1675           Warning(S, "Float register should be even.");
1676       break;
1677     case MipsOperand::Kind_FCCRegs:
1678       RegNum = matchFCCRegisterName(RegName);
1679       break;
1680     case MipsOperand::Kind_ACC64DSP:
1681       RegNum = matchACRegisterName(RegName);
1682       break;
1683     default:
1684       break; // No match, value is set to -1.
1685     }
1686     // No match found, return _NoMatch to give a chance to other round.
1687     if (RegNum < 0)
1688       return MatchOperand_NoMatch;
1689
1690     int RegVal = getReg(regKindToRegClass(Kind), RegNum);
1691     if (RegVal == -1)
1692       return MatchOperand_NoMatch;
1693
1694     MipsOperand *Op =
1695         MipsOperand::CreateReg(RegVal, S, Parser.getTok().getLoc());
1696     Op->setRegKind(Kind);
1697     Operands.push_back(Op);
1698     hasConsumedDollar = false;
1699     Parser.Lex(); // Eat the register name.
1700     return MatchOperand_Success;
1701   } else if (getLexer().getKind() == AsmToken::Integer) {
1702     unsigned RegNum = Parser.getTok().getIntVal();
1703     if (Kind == MipsOperand::Kind_HWRegs) {
1704       if (RegNum != 29)
1705         return MatchOperand_NoMatch;
1706       // Only hwreg 29 is supported, found at index 0.
1707       RegNum = 0;
1708     }
1709     int Reg = matchRegisterByNumber(RegNum, regKindToRegClass(Kind));
1710     if (Reg == -1)
1711       return MatchOperand_NoMatch;
1712     MipsOperand *Op = MipsOperand::CreateReg(Reg, S, Parser.getTok().getLoc());
1713     Op->setRegKind(Kind);
1714     Operands.push_back(Op);
1715     hasConsumedDollar = false;
1716     Parser.Lex(); // Eat the register number.
1717     if ((RegKind == MipsOperand::Kind_GPR32) &&
1718         (getLexer().is(AsmToken::LParen))) {
1719       // Check if it is indexed addressing operand.
1720       Operands.push_back(MipsOperand::CreateToken("(", getLexer().getLoc()));
1721       Parser.Lex(); // Eat the parenthesis.
1722       if (parseRegs(Operands, RegKind) != MatchOperand_Success)
1723         return MatchOperand_NoMatch;
1724       if (getLexer().isNot(AsmToken::RParen))
1725         return MatchOperand_NoMatch;
1726       Operands.push_back(MipsOperand::CreateToken(")", getLexer().getLoc()));
1727       Parser.Lex();
1728     }
1729     return MatchOperand_Success;
1730   }
1731   return MatchOperand_NoMatch;
1732 }
1733
1734 bool MipsAsmParser::validateMSAIndex(int Val, int RegKind) {
1735   MipsOperand::RegisterKind Kind = (MipsOperand::RegisterKind)RegKind;
1736
1737   if (Val < 0)
1738     return false;
1739
1740   switch (Kind) {
1741   default:
1742     return false;
1743   case MipsOperand::Kind_MSA128BRegs:
1744     return Val < 16;
1745   case MipsOperand::Kind_MSA128HRegs:
1746     return Val < 8;
1747   case MipsOperand::Kind_MSA128WRegs:
1748     return Val < 4;
1749   case MipsOperand::Kind_MSA128DRegs:
1750     return Val < 2;
1751   }
1752 }
1753
1754 MipsAsmParser::OperandMatchResultTy
1755 MipsAsmParser::parseMSARegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
1756                             int RegKind) {
1757   MipsOperand::RegisterKind Kind = (MipsOperand::RegisterKind)RegKind;
1758   SMLoc S = Parser.getTok().getLoc();
1759   std::string RegName;
1760
1761   if (Parser.getTok().isNot(AsmToken::Dollar))
1762     return MatchOperand_NoMatch;
1763
1764   switch (RegKind) {
1765   default:
1766     return MatchOperand_ParseFail;
1767   case MipsOperand::Kind_MSA128BRegs:
1768   case MipsOperand::Kind_MSA128HRegs:
1769   case MipsOperand::Kind_MSA128WRegs:
1770   case MipsOperand::Kind_MSA128DRegs:
1771     break;
1772   }
1773
1774   Parser.Lex(); // Eat the '$'.
1775   if (getLexer().getKind() == AsmToken::Identifier)
1776     RegName = Parser.getTok().getString().lower();
1777   else
1778     return MatchOperand_ParseFail;
1779
1780   int RegNum = matchMSA128RegisterName(RegName);
1781
1782   if (RegNum < 0 || RegNum > 31)
1783     return MatchOperand_ParseFail;
1784
1785   int RegVal = getReg(regKindToRegClass(Kind), RegNum);
1786   if (RegVal == -1)
1787     return MatchOperand_ParseFail;
1788
1789   MipsOperand *Op = MipsOperand::CreateReg(RegVal, S, Parser.getTok().getLoc());
1790   Op->setRegKind(Kind);
1791   Operands.push_back(Op);
1792
1793   Parser.Lex(); // Eat the register identifier.
1794
1795   // MSA registers may be suffixed with an index in the form of:
1796   // 1) Immediate expression.
1797   // 2) General Purpose Register.
1798   // Examples:
1799   //   1) copy_s.b $29,$w0[0]
1800   //   2) sld.b $w0,$w1[$1]
1801
1802   if (Parser.getTok().isNot(AsmToken::LBrac))
1803     return MatchOperand_Success;
1804
1805   MipsOperand *Mnemonic = static_cast<MipsOperand *>(Operands[0]);
1806
1807   Operands.push_back(MipsOperand::CreateToken("[", Parser.getTok().getLoc()));
1808   Parser.Lex(); // Parse the '[' token.
1809
1810   if (Parser.getTok().is(AsmToken::Dollar)) {
1811     // This must be a GPR.
1812     MipsOperand *RegOp;
1813     SMLoc VIdx = Parser.getTok().getLoc();
1814     Parser.Lex(); // Parse the '$' token.
1815
1816     // GPR have aliases and we must account for that. Example: $30 == $fp
1817     if (getLexer().getKind() == AsmToken::Integer) {
1818       unsigned RegNum = Parser.getTok().getIntVal();
1819       int Reg = matchRegisterByNumber(
1820           RegNum, regKindToRegClass(MipsOperand::Kind_GPR32));
1821       if (Reg == -1) {
1822         Error(VIdx, "invalid general purpose register");
1823         return MatchOperand_ParseFail;
1824       }
1825
1826       RegOp = MipsOperand::CreateReg(Reg, VIdx, Parser.getTok().getLoc());
1827     } else if (getLexer().getKind() == AsmToken::Identifier) {
1828       int RegNum = -1;
1829       std::string RegName = Parser.getTok().getString().lower();
1830
1831       RegNum = matchCPURegisterName(RegName);
1832       if (RegNum == -1) {
1833         Error(VIdx, "general purpose register expected");
1834         return MatchOperand_ParseFail;
1835       }
1836       RegNum = getReg(regKindToRegClass(MipsOperand::Kind_GPR32), RegNum);
1837       RegOp = MipsOperand::CreateReg(RegNum, VIdx, Parser.getTok().getLoc());
1838     } else
1839       return MatchOperand_ParseFail;
1840
1841     RegOp->setRegKind(MipsOperand::Kind_GPR32);
1842     Operands.push_back(RegOp);
1843     Parser.Lex(); // Eat the register identifier.
1844
1845     if (Parser.getTok().isNot(AsmToken::RBrac))
1846       return MatchOperand_ParseFail;
1847
1848     Operands.push_back(MipsOperand::CreateToken("]", Parser.getTok().getLoc()));
1849     Parser.Lex(); // Parse the ']' token.
1850
1851     return MatchOperand_Success;
1852   }
1853
1854   // The index must be a constant expression then.
1855   SMLoc VIdx = Parser.getTok().getLoc();
1856   const MCExpr *ImmVal;
1857
1858   if (getParser().parseExpression(ImmVal))
1859     return MatchOperand_ParseFail;
1860
1861   const MCConstantExpr *expr = dyn_cast<MCConstantExpr>(ImmVal);
1862   if (!expr || !validateMSAIndex((int)expr->getValue(), Kind)) {
1863     Error(VIdx, "invalid immediate value");
1864     return MatchOperand_ParseFail;
1865   }
1866
1867   SMLoc E = Parser.getTok().getEndLoc();
1868
1869   if (Parser.getTok().isNot(AsmToken::RBrac))
1870     return MatchOperand_ParseFail;
1871
1872   bool insve =
1873       Mnemonic->getToken() == "insve.b" || Mnemonic->getToken() == "insve.h" ||
1874       Mnemonic->getToken() == "insve.w" || Mnemonic->getToken() == "insve.d";
1875
1876   // The second vector index of insve instructions is always 0.
1877   if (insve && Operands.size() > 6) {
1878     if (expr->getValue() != 0) {
1879       Error(VIdx, "immediate value must be 0");
1880       return MatchOperand_ParseFail;
1881     }
1882     Operands.push_back(MipsOperand::CreateToken("0", VIdx));
1883   } else
1884     Operands.push_back(MipsOperand::CreateImm(expr, VIdx, E));
1885
1886   Operands.push_back(MipsOperand::CreateToken("]", Parser.getTok().getLoc()));
1887
1888   Parser.Lex(); // Parse the ']' token.
1889
1890   return MatchOperand_Success;
1891 }
1892
1893 MipsAsmParser::OperandMatchResultTy
1894 MipsAsmParser::parseMSACtrlRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands,
1895                                 int RegKind) {
1896   MipsOperand::RegisterKind Kind = (MipsOperand::RegisterKind)RegKind;
1897
1898   if (Kind != MipsOperand::Kind_MSA128CtrlRegs)
1899     return MatchOperand_NoMatch;
1900
1901   if (Parser.getTok().isNot(AsmToken::Dollar))
1902     return MatchOperand_ParseFail;
1903
1904   SMLoc S = Parser.getTok().getLoc();
1905
1906   Parser.Lex(); // Eat the '$' symbol.
1907
1908   int RegNum = -1;
1909   if (getLexer().getKind() == AsmToken::Identifier)
1910     RegNum = matchMSA128CtrlRegisterName(Parser.getTok().getString().lower());
1911   else if (getLexer().getKind() == AsmToken::Integer)
1912     RegNum = Parser.getTok().getIntVal();
1913   else
1914     return MatchOperand_ParseFail;
1915
1916   if (RegNum < 0 || RegNum > 7)
1917     return MatchOperand_ParseFail;
1918
1919   int RegVal = getReg(regKindToRegClass(Kind), RegNum);
1920   if (RegVal == -1)
1921     return MatchOperand_ParseFail;
1922
1923   MipsOperand *RegOp =
1924       MipsOperand::CreateReg(RegVal, S, Parser.getTok().getLoc());
1925   RegOp->setRegKind(MipsOperand::Kind_MSA128CtrlRegs);
1926   Operands.push_back(RegOp);
1927   Parser.Lex(); // Eat the register identifier.
1928
1929   return MatchOperand_Success;
1930 }
1931
1932 MipsAsmParser::OperandMatchResultTy
1933 MipsAsmParser::parseGPR64(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1934
1935   if (!isMips64())
1936     return MatchOperand_NoMatch;
1937   return parseRegs(Operands, (int)MipsOperand::Kind_GPR64);
1938 }
1939
1940 MipsAsmParser::OperandMatchResultTy
1941 MipsAsmParser::parseGPR32(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1942   return parseRegs(Operands, (int)MipsOperand::Kind_GPR32);
1943 }
1944
1945 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseAFGR64Regs(
1946     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1947
1948   if (isFP64())
1949     return MatchOperand_NoMatch;
1950   return parseRegs(Operands, (int)MipsOperand::Kind_AFGR64Regs);
1951 }
1952
1953 MipsAsmParser::OperandMatchResultTy
1954 MipsAsmParser::parseFGR64Regs(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1955   if (!isFP64())
1956     return MatchOperand_NoMatch;
1957   return parseRegs(Operands, (int)MipsOperand::Kind_FGR64Regs);
1958 }
1959
1960 MipsAsmParser::OperandMatchResultTy
1961 MipsAsmParser::parseFGR32Regs(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1962   return parseRegs(Operands, (int)MipsOperand::Kind_FGR32Regs);
1963 }
1964
1965 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseFGRH32Regs(
1966     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1967   return parseRegs(Operands, (int)MipsOperand::Kind_FGRH32Regs);
1968 }
1969
1970 MipsAsmParser::OperandMatchResultTy
1971 MipsAsmParser::parseFCCRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1972   return parseRegs(Operands, (int)MipsOperand::Kind_FCCRegs);
1973 }
1974
1975 MipsAsmParser::OperandMatchResultTy
1976 MipsAsmParser::parseACC64DSP(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1977   return parseRegs(Operands, (int)MipsOperand::Kind_ACC64DSP);
1978 }
1979
1980 MipsAsmParser::OperandMatchResultTy
1981 MipsAsmParser::parseLO32DSP(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
1982   // If the first token is not '$' we have an error.
1983   if (Parser.getTok().isNot(AsmToken::Dollar))
1984     return MatchOperand_NoMatch;
1985
1986   SMLoc S = Parser.getTok().getLoc();
1987   Parser.Lex(); // Eat the '$'
1988
1989   const AsmToken &Tok = Parser.getTok(); // Get next token.
1990
1991   if (Tok.isNot(AsmToken::Identifier))
1992     return MatchOperand_NoMatch;
1993
1994   if (!Tok.getIdentifier().startswith("ac"))
1995     return MatchOperand_NoMatch;
1996
1997   StringRef NumString = Tok.getIdentifier().substr(2);
1998
1999   unsigned IntVal;
2000   if (NumString.getAsInteger(10, IntVal))
2001     return MatchOperand_NoMatch;
2002
2003   unsigned Reg = matchRegisterByNumber(IntVal, Mips::LO32DSPRegClassID);
2004
2005   MipsOperand *Op = MipsOperand::CreateReg(Reg, S, Parser.getTok().getLoc());
2006   Op->setRegKind(MipsOperand::Kind_LO32DSP);
2007   Operands.push_back(Op);
2008
2009   Parser.Lex(); // Eat the register number.
2010   return MatchOperand_Success;
2011 }
2012
2013 MipsAsmParser::OperandMatchResultTy
2014 MipsAsmParser::parseHI32DSP(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2015   // If the first token is not '$' we have an error.
2016   if (Parser.getTok().isNot(AsmToken::Dollar))
2017     return MatchOperand_NoMatch;
2018
2019   SMLoc S = Parser.getTok().getLoc();
2020   Parser.Lex(); // Eat the '$'
2021
2022   const AsmToken &Tok = Parser.getTok(); // Get next token.
2023
2024   if (Tok.isNot(AsmToken::Identifier))
2025     return MatchOperand_NoMatch;
2026
2027   if (!Tok.getIdentifier().startswith("ac"))
2028     return MatchOperand_NoMatch;
2029
2030   StringRef NumString = Tok.getIdentifier().substr(2);
2031
2032   unsigned IntVal;
2033   if (NumString.getAsInteger(10, IntVal))
2034     return MatchOperand_NoMatch;
2035
2036   unsigned Reg = matchRegisterByNumber(IntVal, Mips::HI32DSPRegClassID);
2037
2038   MipsOperand *Op = MipsOperand::CreateReg(Reg, S, Parser.getTok().getLoc());
2039   Op->setRegKind(MipsOperand::Kind_HI32DSP);
2040   Operands.push_back(Op);
2041
2042   Parser.Lex(); // Eat the register number.
2043   return MatchOperand_Success;
2044 }
2045
2046 MipsAsmParser::OperandMatchResultTy
2047 MipsAsmParser::parseCOP2(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2048   // If the first token is not '$' we have an error.
2049   if (Parser.getTok().isNot(AsmToken::Dollar))
2050     return MatchOperand_NoMatch;
2051
2052   SMLoc S = Parser.getTok().getLoc();
2053   Parser.Lex(); // Eat the '$'
2054
2055   const AsmToken &Tok = Parser.getTok(); // Get next token.
2056
2057   if (Tok.isNot(AsmToken::Integer))
2058     return MatchOperand_NoMatch;
2059
2060   unsigned IntVal = Tok.getIntVal();
2061
2062   unsigned Reg = matchRegisterByNumber(IntVal, Mips::COP2RegClassID);
2063
2064   MipsOperand *Op = MipsOperand::CreateReg(Reg, S, Parser.getTok().getLoc());
2065   Op->setRegKind(MipsOperand::Kind_COP2);
2066   Operands.push_back(Op);
2067
2068   Parser.Lex(); // Eat the register number.
2069   return MatchOperand_Success;
2070 }
2071
2072 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseMSA128BRegs(
2073     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2074   return parseMSARegs(Operands, (int)MipsOperand::Kind_MSA128BRegs);
2075 }
2076
2077 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseMSA128HRegs(
2078     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2079   return parseMSARegs(Operands, (int)MipsOperand::Kind_MSA128HRegs);
2080 }
2081
2082 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseMSA128WRegs(
2083     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2084   return parseMSARegs(Operands, (int)MipsOperand::Kind_MSA128WRegs);
2085 }
2086
2087 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseMSA128DRegs(
2088     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2089   return parseMSARegs(Operands, (int)MipsOperand::Kind_MSA128DRegs);
2090 }
2091
2092 MipsAsmParser::OperandMatchResultTy MipsAsmParser::parseMSA128CtrlRegs(
2093     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2094   return parseMSACtrlRegs(Operands, (int)MipsOperand::Kind_MSA128CtrlRegs);
2095 }
2096
2097 bool MipsAsmParser::searchSymbolAlias(
2098     SmallVectorImpl<MCParsedAsmOperand *> &Operands, unsigned RegKind) {
2099
2100   MCSymbol *Sym = getContext().LookupSymbol(Parser.getTok().getIdentifier());
2101   if (Sym) {
2102     SMLoc S = Parser.getTok().getLoc();
2103     const MCExpr *Expr;
2104     if (Sym->isVariable())
2105       Expr = Sym->getVariableValue();
2106     else
2107       return false;
2108     if (Expr->getKind() == MCExpr::SymbolRef) {
2109       MipsOperand::RegisterKind Kind = (MipsOperand::RegisterKind)RegKind;
2110       const MCSymbolRefExpr *Ref = static_cast<const MCSymbolRefExpr *>(Expr);
2111       const StringRef DefSymbol = Ref->getSymbol().getName();
2112       if (DefSymbol.startswith("$")) {
2113         int RegNum = -1;
2114         APInt IntVal(32, -1);
2115         if (!DefSymbol.substr(1).getAsInteger(10, IntVal))
2116           RegNum = matchRegisterByNumber(IntVal.getZExtValue(),
2117                                          isMips64() ? Mips::GPR64RegClassID
2118                                                     : Mips::GPR32RegClassID);
2119         else {
2120           // Lookup for the register with the corresponding name.
2121           switch (Kind) {
2122           case MipsOperand::Kind_AFGR64Regs:
2123           case MipsOperand::Kind_FGR64Regs:
2124             RegNum = matchFPURegisterName(DefSymbol.substr(1));
2125             break;
2126           case MipsOperand::Kind_FGR32Regs:
2127             RegNum = matchFPURegisterName(DefSymbol.substr(1));
2128             break;
2129           case MipsOperand::Kind_GPR64:
2130           case MipsOperand::Kind_GPR32:
2131           default:
2132             RegNum = matchCPURegisterName(DefSymbol.substr(1));
2133             break;
2134           }
2135           if (RegNum > -1)
2136             RegNum = getReg(regKindToRegClass(Kind), RegNum);
2137         }
2138         if (RegNum > -1) {
2139           Parser.Lex();
2140           MipsOperand *op =
2141               MipsOperand::CreateReg(RegNum, S, Parser.getTok().getLoc());
2142           op->setRegKind(Kind);
2143           Operands.push_back(op);
2144           return true;
2145         }
2146       }
2147     } else if (Expr->getKind() == MCExpr::Constant) {
2148       Parser.Lex();
2149       const MCConstantExpr *Const = static_cast<const MCConstantExpr *>(Expr);
2150       MipsOperand *op =
2151           MipsOperand::CreateImm(Const, S, Parser.getTok().getLoc());
2152       Operands.push_back(op);
2153       return true;
2154     }
2155   }
2156   return false;
2157 }
2158
2159 MipsAsmParser::OperandMatchResultTy
2160 MipsAsmParser::parseHWRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2161   return parseRegs(Operands, (int)MipsOperand::Kind_HWRegs);
2162 }
2163
2164 MipsAsmParser::OperandMatchResultTy
2165 MipsAsmParser::parseCCRRegs(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2166   return parseRegs(Operands, (int)MipsOperand::Kind_CCRRegs);
2167 }
2168
2169 MipsAsmParser::OperandMatchResultTy
2170 MipsAsmParser::parseInvNum(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2171   const MCExpr *IdVal;
2172   // If the first token is '$' we may have register operand.
2173   if (Parser.getTok().is(AsmToken::Dollar))
2174     return MatchOperand_NoMatch;
2175   SMLoc S = Parser.getTok().getLoc();
2176   if (getParser().parseExpression(IdVal))
2177     return MatchOperand_ParseFail;
2178   const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(IdVal);
2179   assert(MCE && "Unexpected MCExpr type.");
2180   int64_t Val = MCE->getValue();
2181   SMLoc E = SMLoc::getFromPointer(Parser.getTok().getLoc().getPointer() - 1);
2182   Operands.push_back(MipsOperand::CreateImm(
2183       MCConstantExpr::Create(0 - Val, getContext()), S, E));
2184   return MatchOperand_Success;
2185 }
2186
2187 MipsAsmParser::OperandMatchResultTy
2188 MipsAsmParser::parseLSAImm(SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2189   switch (getLexer().getKind()) {
2190   default:
2191     return MatchOperand_NoMatch;
2192   case AsmToken::LParen:
2193   case AsmToken::Plus:
2194   case AsmToken::Minus:
2195   case AsmToken::Integer:
2196     break;
2197   }
2198
2199   const MCExpr *Expr;
2200   SMLoc S = Parser.getTok().getLoc();
2201
2202   if (getParser().parseExpression(Expr))
2203     return MatchOperand_ParseFail;
2204
2205   int64_t Val;
2206   if (!Expr->EvaluateAsAbsolute(Val)) {
2207     Error(S, "expected immediate value");
2208     return MatchOperand_ParseFail;
2209   }
2210
2211   // The LSA instruction allows a 2-bit unsigned immediate. For this reason
2212   // and because the CPU always adds one to the immediate field, the allowed
2213   // range becomes 1..4. We'll only check the range here and will deal
2214   // with the addition/subtraction when actually decoding/encoding
2215   // the instruction.
2216   if (Val < 1 || Val > 4) {
2217     Error(S, "immediate not in range (1..4)");
2218     return MatchOperand_ParseFail;
2219   }
2220
2221   Operands.push_back(
2222       MipsOperand::CreateLSAImm(Expr, S, Parser.getTok().getLoc()));
2223   return MatchOperand_Success;
2224 }
2225
2226 MCSymbolRefExpr::VariantKind MipsAsmParser::getVariantKind(StringRef Symbol) {
2227
2228   MCSymbolRefExpr::VariantKind VK =
2229       StringSwitch<MCSymbolRefExpr::VariantKind>(Symbol)
2230           .Case("hi", MCSymbolRefExpr::VK_Mips_ABS_HI)
2231           .Case("lo", MCSymbolRefExpr::VK_Mips_ABS_LO)
2232           .Case("gp_rel", MCSymbolRefExpr::VK_Mips_GPREL)
2233           .Case("call16", MCSymbolRefExpr::VK_Mips_GOT_CALL)
2234           .Case("got", MCSymbolRefExpr::VK_Mips_GOT)
2235           .Case("tlsgd", MCSymbolRefExpr::VK_Mips_TLSGD)
2236           .Case("tlsldm", MCSymbolRefExpr::VK_Mips_TLSLDM)
2237           .Case("dtprel_hi", MCSymbolRefExpr::VK_Mips_DTPREL_HI)
2238           .Case("dtprel_lo", MCSymbolRefExpr::VK_Mips_DTPREL_LO)
2239           .Case("gottprel", MCSymbolRefExpr::VK_Mips_GOTTPREL)
2240           .Case("tprel_hi", MCSymbolRefExpr::VK_Mips_TPREL_HI)
2241           .Case("tprel_lo", MCSymbolRefExpr::VK_Mips_TPREL_LO)
2242           .Case("got_disp", MCSymbolRefExpr::VK_Mips_GOT_DISP)
2243           .Case("got_page", MCSymbolRefExpr::VK_Mips_GOT_PAGE)
2244           .Case("got_ofst", MCSymbolRefExpr::VK_Mips_GOT_OFST)
2245           .Case("hi(%neg(%gp_rel", MCSymbolRefExpr::VK_Mips_GPOFF_HI)
2246           .Case("lo(%neg(%gp_rel", MCSymbolRefExpr::VK_Mips_GPOFF_LO)
2247           .Default(MCSymbolRefExpr::VK_None);
2248
2249   return VK;
2250 }
2251
2252 bool MipsAsmParser::ParseInstruction(
2253     ParseInstructionInfo &Info, StringRef Name, SMLoc NameLoc,
2254     SmallVectorImpl<MCParsedAsmOperand *> &Operands) {
2255   // Check if we have valid mnemonic
2256   if (!mnemonicIsValid(Name, 0)) {
2257     Parser.eatToEndOfStatement();
2258     return Error(NameLoc, "Unknown instruction");
2259   }
2260   // First operand in MCInst is instruction mnemonic.
2261   Operands.push_back(MipsOperand::CreateToken(Name, NameLoc));
2262
2263   // Read the remaining operands.
2264   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2265     // Read the first operand.
2266     if (ParseOperand(Operands, Name)) {
2267       SMLoc Loc = getLexer().getLoc();
2268       Parser.eatToEndOfStatement();
2269       return Error(Loc, "unexpected token in argument list");
2270     }
2271
2272     while (getLexer().is(AsmToken::Comma)) {
2273       Parser.Lex(); // Eat the comma.
2274       // Parse and remember the operand.
2275       if (ParseOperand(Operands, Name)) {
2276         SMLoc Loc = getLexer().getLoc();
2277         Parser.eatToEndOfStatement();
2278         return Error(Loc, "unexpected token in argument list");
2279       }
2280     }
2281   }
2282   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2283     SMLoc Loc = getLexer().getLoc();
2284     Parser.eatToEndOfStatement();
2285     return Error(Loc, "unexpected token in argument list");
2286   }
2287   Parser.Lex(); // Consume the EndOfStatement.
2288   return false;
2289 }
2290
2291 bool MipsAsmParser::reportParseError(StringRef ErrorMsg) {
2292   SMLoc Loc = getLexer().getLoc();
2293   Parser.eatToEndOfStatement();
2294   return Error(Loc, ErrorMsg);
2295 }
2296
2297 bool MipsAsmParser::parseSetNoAtDirective() {
2298   // Line should look like: ".set noat".
2299   // set at reg to 0.
2300   Options.setATReg(0);
2301   // eat noat
2302   Parser.Lex();
2303   // If this is not the end of the statement, report an error.
2304   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2305     reportParseError("unexpected token in statement");
2306     return false;
2307   }
2308   Parser.Lex(); // Consume the EndOfStatement.
2309   return false;
2310 }
2311
2312 bool MipsAsmParser::parseSetAtDirective() {
2313   // Line can be .set at - defaults to $1
2314   // or .set at=$reg
2315   int AtRegNo;
2316   getParser().Lex();
2317   if (getLexer().is(AsmToken::EndOfStatement)) {
2318     Options.setATReg(1);
2319     Parser.Lex(); // Consume the EndOfStatement.
2320     return false;
2321   } else if (getLexer().is(AsmToken::Equal)) {
2322     getParser().Lex(); // Eat the '='.
2323     if (getLexer().isNot(AsmToken::Dollar)) {
2324       reportParseError("unexpected token in statement");
2325       return false;
2326     }
2327     Parser.Lex(); // Eat the '$'.
2328     const AsmToken &Reg = Parser.getTok();
2329     if (Reg.is(AsmToken::Identifier)) {
2330       AtRegNo = matchCPURegisterName(Reg.getIdentifier());
2331     } else if (Reg.is(AsmToken::Integer)) {
2332       AtRegNo = Reg.getIntVal();
2333     } else {
2334       reportParseError("unexpected token in statement");
2335       return false;
2336     }
2337
2338     if (AtRegNo < 1 || AtRegNo > 31) {
2339       reportParseError("unexpected token in statement");
2340       return false;
2341     }
2342
2343     if (!Options.setATReg(AtRegNo)) {
2344       reportParseError("unexpected token in statement");
2345       return false;
2346     }
2347     getParser().Lex(); // Eat the register.
2348
2349     if (getLexer().isNot(AsmToken::EndOfStatement)) {
2350       reportParseError("unexpected token in statement");
2351       return false;
2352     }
2353     Parser.Lex(); // Consume the EndOfStatement.
2354     return false;
2355   } else {
2356     reportParseError("unexpected token in statement");
2357     return false;
2358   }
2359 }
2360
2361 bool MipsAsmParser::parseSetReorderDirective() {
2362   Parser.Lex();
2363   // If this is not the end of the statement, report an error.
2364   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2365     reportParseError("unexpected token in statement");
2366     return false;
2367   }
2368   Options.setReorder();
2369   getTargetStreamer().emitDirectiveSetReorder();
2370   Parser.Lex(); // Consume the EndOfStatement.
2371   return false;
2372 }
2373
2374 bool MipsAsmParser::parseSetNoReorderDirective() {
2375   Parser.Lex();
2376   // If this is not the end of the statement, report an error.
2377   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2378     reportParseError("unexpected token in statement");
2379     return false;
2380   }
2381   Options.setNoreorder();
2382   getTargetStreamer().emitDirectiveSetNoReorder();
2383   Parser.Lex(); // Consume the EndOfStatement.
2384   return false;
2385 }
2386
2387 bool MipsAsmParser::parseSetMacroDirective() {
2388   Parser.Lex();
2389   // If this is not the end of the statement, report an error.
2390   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2391     reportParseError("unexpected token in statement");
2392     return false;
2393   }
2394   Options.setMacro();
2395   Parser.Lex(); // Consume the EndOfStatement.
2396   return false;
2397 }
2398
2399 bool MipsAsmParser::parseSetNoMacroDirective() {
2400   Parser.Lex();
2401   // If this is not the end of the statement, report an error.
2402   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2403     reportParseError("`noreorder' must be set before `nomacro'");
2404     return false;
2405   }
2406   if (Options.isReorder()) {
2407     reportParseError("`noreorder' must be set before `nomacro'");
2408     return false;
2409   }
2410   Options.setNomacro();
2411   Parser.Lex(); // Consume the EndOfStatement.
2412   return false;
2413 }
2414
2415 bool MipsAsmParser::parseSetMips16Directive() {
2416   Parser.Lex();
2417   // If this is not the end of the statement, report an error.
2418   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2419     reportParseError("unexpected token in statement");
2420     return false;
2421   }
2422   getTargetStreamer().emitDirectiveSetMips16();
2423   Parser.Lex(); // Consume the EndOfStatement.
2424   return false;
2425 }
2426
2427 bool MipsAsmParser::parseSetNoMips16Directive() {
2428   Parser.Lex();
2429   // If this is not the end of the statement, report an error.
2430   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2431     reportParseError("unexpected token in statement");
2432     return false;
2433   }
2434   // For now do nothing.
2435   Parser.Lex(); // Consume the EndOfStatement.
2436   return false;
2437 }
2438
2439 bool MipsAsmParser::parseSetAssignment() {
2440   StringRef Name;
2441   const MCExpr *Value;
2442
2443   if (Parser.parseIdentifier(Name))
2444     reportParseError("expected identifier after .set");
2445
2446   if (getLexer().isNot(AsmToken::Comma))
2447     return reportParseError("unexpected token in .set directive");
2448   Lex(); // Eat comma
2449
2450   if (Parser.parseExpression(Value))
2451     return reportParseError("expected valid expression after comma");
2452
2453   // Check if the Name already exists as a symbol.
2454   MCSymbol *Sym = getContext().LookupSymbol(Name);
2455   if (Sym)
2456     return reportParseError("symbol already defined");
2457   Sym = getContext().GetOrCreateSymbol(Name);
2458   Sym->setVariableValue(Value);
2459
2460   return false;
2461 }
2462
2463 bool MipsAsmParser::parseDirectiveSet() {
2464
2465   // Get the next token.
2466   const AsmToken &Tok = Parser.getTok();
2467
2468   if (Tok.getString() == "noat") {
2469     return parseSetNoAtDirective();
2470   } else if (Tok.getString() == "at") {
2471     return parseSetAtDirective();
2472   } else if (Tok.getString() == "reorder") {
2473     return parseSetReorderDirective();
2474   } else if (Tok.getString() == "noreorder") {
2475     return parseSetNoReorderDirective();
2476   } else if (Tok.getString() == "macro") {
2477     return parseSetMacroDirective();
2478   } else if (Tok.getString() == "nomacro") {
2479     return parseSetNoMacroDirective();
2480   } else if (Tok.getString() == "mips16") {
2481     return parseSetMips16Directive();
2482   } else if (Tok.getString() == "nomips16") {
2483     return parseSetNoMips16Directive();
2484   } else if (Tok.getString() == "nomicromips") {
2485     getTargetStreamer().emitDirectiveSetNoMicroMips();
2486     Parser.eatToEndOfStatement();
2487     return false;
2488   } else if (Tok.getString() == "micromips") {
2489     getTargetStreamer().emitDirectiveSetMicroMips();
2490     Parser.eatToEndOfStatement();
2491     return false;
2492   } else if (Tok.getString() == "mips32r2") {
2493     Parser.Lex(); // Eat token.
2494     if (getLexer().isNot(AsmToken::EndOfStatement))
2495       return reportParseError("unexpected token in .set directive");
2496     setFeatureBits(Mips::FeatureMips32r2,"mips32r2");
2497     getTargetStreamer().emitDirectiveSetMips32R2();
2498     return false;
2499   } else if (Tok.getString() == "dsp") {
2500     Parser.Lex(); // Eat token.
2501     if (getLexer().isNot(AsmToken::EndOfStatement))
2502       return reportParseError("unexpected token in .set directive");
2503     setFeatureBits(Mips::FeatureDSP, "dsp");
2504     getTargetStreamer().emitDirectiveSetDsp();
2505     return false;
2506   } else {
2507     // It is just an identifier, look for an assignment.
2508     parseSetAssignment();
2509     return false;
2510   }
2511
2512   return true;
2513 }
2514
2515 /// parseDirectiveWord
2516 ///  ::= .word [ expression (, expression)* ]
2517 bool MipsAsmParser::parseDirectiveWord(unsigned Size, SMLoc L) {
2518   if (getLexer().isNot(AsmToken::EndOfStatement)) {
2519     for (;;) {
2520       const MCExpr *Value;
2521       if (getParser().parseExpression(Value))
2522         return true;
2523
2524       getParser().getStreamer().EmitValue(Value, Size);
2525
2526       if (getLexer().is(AsmToken::EndOfStatement))
2527         break;
2528
2529       // FIXME: Improve diagnostic.
2530       if (getLexer().isNot(AsmToken::Comma))
2531         return Error(L, "unexpected token in directive");
2532       Parser.Lex();
2533     }
2534   }
2535
2536   Parser.Lex();
2537   return false;
2538 }
2539
2540 /// parseDirectiveGpWord
2541 ///  ::= .gpword local_sym
2542 bool MipsAsmParser::parseDirectiveGpWord() {
2543   const MCExpr *Value;
2544   // EmitGPRel32Value requires an expression, so we are using base class
2545   // method to evaluate the expression.
2546   if (getParser().parseExpression(Value))
2547     return true;
2548   getParser().getStreamer().EmitGPRel32Value(Value);
2549
2550   if (getLexer().isNot(AsmToken::EndOfStatement))
2551     return Error(getLexer().getLoc(), "unexpected token in directive");
2552   Parser.Lex(); // Eat EndOfStatement token.
2553   return false;
2554 }
2555
2556 bool MipsAsmParser::parseDirectiveOption() {
2557   // Get the option token.
2558   AsmToken Tok = Parser.getTok();
2559   // At the moment only identifiers are supported.
2560   if (Tok.isNot(AsmToken::Identifier)) {
2561     Error(Parser.getTok().getLoc(), "unexpected token in .option directive");
2562     Parser.eatToEndOfStatement();
2563     return false;
2564   }
2565
2566   StringRef Option = Tok.getIdentifier();
2567
2568   if (Option == "pic0") {
2569     getTargetStreamer().emitDirectiveOptionPic0();
2570     Parser.Lex();
2571     if (Parser.getTok().isNot(AsmToken::EndOfStatement)) {
2572       Error(Parser.getTok().getLoc(),
2573             "unexpected token in .option pic0 directive");
2574       Parser.eatToEndOfStatement();
2575     }
2576     return false;
2577   }
2578
2579   // Unknown option.
2580   Warning(Parser.getTok().getLoc(), "unknown option in .option directive");
2581   Parser.eatToEndOfStatement();
2582   return false;
2583 }
2584
2585 bool MipsAsmParser::ParseDirective(AsmToken DirectiveID) {
2586   StringRef IDVal = DirectiveID.getString();
2587
2588   if (IDVal == ".ent") {
2589     // Ignore this directive for now.
2590     Parser.Lex();
2591     return false;
2592   }
2593
2594   if (IDVal == ".end") {
2595     // Ignore this directive for now.
2596     Parser.Lex();
2597     return false;
2598   }
2599
2600   if (IDVal == ".frame") {
2601     // Ignore this directive for now.
2602     Parser.eatToEndOfStatement();
2603     return false;
2604   }
2605
2606   if (IDVal == ".set") {
2607     return parseDirectiveSet();
2608   }
2609
2610   if (IDVal == ".fmask") {
2611     // Ignore this directive for now.
2612     Parser.eatToEndOfStatement();
2613     return false;
2614   }
2615
2616   if (IDVal == ".mask") {
2617     // Ignore this directive for now.
2618     Parser.eatToEndOfStatement();
2619     return false;
2620   }
2621
2622   if (IDVal == ".gpword") {
2623     // Ignore this directive for now.
2624     parseDirectiveGpWord();
2625     return false;
2626   }
2627
2628   if (IDVal == ".word") {
2629     parseDirectiveWord(4, DirectiveID.getLoc());
2630     return false;
2631   }
2632
2633   if (IDVal == ".option")
2634     return parseDirectiveOption();
2635
2636   if (IDVal == ".abicalls") {
2637     getTargetStreamer().emitDirectiveAbiCalls();
2638     if (Parser.getTok().isNot(AsmToken::EndOfStatement)) {
2639       Error(Parser.getTok().getLoc(), "unexpected token in directive");
2640       // Clear line
2641       Parser.eatToEndOfStatement();
2642     }
2643     return false;
2644   }
2645
2646   return true;
2647 }
2648
2649 extern "C" void LLVMInitializeMipsAsmParser() {
2650   RegisterMCAsmParser<MipsAsmParser> X(TheMipsTarget);
2651   RegisterMCAsmParser<MipsAsmParser> Y(TheMipselTarget);
2652   RegisterMCAsmParser<MipsAsmParser> A(TheMips64Target);
2653   RegisterMCAsmParser<MipsAsmParser> B(TheMips64elTarget);
2654 }
2655
2656 #define GET_REGISTER_MATCHER
2657 #define GET_MATCHER_IMPLEMENTATION
2658 #include "MipsGenAsmMatcher.inc"