[mips] Use ptr_rc to simplify definitions of base+index load/store instructions.
[oota-llvm.git] / lib / Target / Mips / Disassembler / MipsDisassembler.cpp
1 //===- MipsDisassembler.cpp - Disassembler for Mips -------------*- C++ -*-===//
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 // This file is part of the Mips Disassembler.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #include "Mips.h"
15 #include "MipsRegisterInfo.h"
16 #include "MipsSubtarget.h"
17 #include "llvm/MC/MCDisassembler.h"
18 #include "llvm/MC/MCFixedLenDisassembler.h"
19 #include "llvm/MC/MCInst.h"
20 #include "llvm/MC/MCSubtargetInfo.h"
21 #include "llvm/Support/MathExtras.h"
22 #include "llvm/Support/MemoryObject.h"
23 #include "llvm/Support/TargetRegistry.h"
24
25 using namespace llvm;
26
27 typedef MCDisassembler::DecodeStatus DecodeStatus;
28
29 namespace {
30
31 /// MipsDisassemblerBase - a disasembler class for Mips.
32 class MipsDisassemblerBase : public MCDisassembler {
33 public:
34   /// Constructor     - Initializes the disassembler.
35   ///
36   MipsDisassemblerBase(const MCSubtargetInfo &STI, const MCRegisterInfo *Info,
37                        bool bigEndian) :
38     MCDisassembler(STI), RegInfo(Info),
39     IsN64(STI.getFeatureBits() & Mips::FeatureN64), isBigEndian(bigEndian) {}
40
41   virtual ~MipsDisassemblerBase() {}
42
43   const MCRegisterInfo *getRegInfo() const { return RegInfo.get(); }
44
45   bool isN64() const { return IsN64; }
46
47 private:
48   OwningPtr<const MCRegisterInfo> RegInfo;
49   bool IsN64;
50 protected:
51   bool isBigEndian;
52 };
53
54 /// MipsDisassembler - a disasembler class for Mips32.
55 class MipsDisassembler : public MipsDisassemblerBase {
56 public:
57   /// Constructor     - Initializes the disassembler.
58   ///
59   MipsDisassembler(const MCSubtargetInfo &STI, const MCRegisterInfo *Info,
60                    bool bigEndian) :
61     MipsDisassemblerBase(STI, Info, bigEndian) {}
62
63   /// getInstruction - See MCDisassembler.
64   virtual DecodeStatus getInstruction(MCInst &instr,
65                                       uint64_t &size,
66                                       const MemoryObject &region,
67                                       uint64_t address,
68                                       raw_ostream &vStream,
69                                       raw_ostream &cStream) const;
70 };
71
72
73 /// Mips64Disassembler - a disasembler class for Mips64.
74 class Mips64Disassembler : public MipsDisassemblerBase {
75 public:
76   /// Constructor     - Initializes the disassembler.
77   ///
78   Mips64Disassembler(const MCSubtargetInfo &STI, const MCRegisterInfo *Info,
79                      bool bigEndian) :
80     MipsDisassemblerBase(STI, Info, bigEndian) {}
81
82   /// getInstruction - See MCDisassembler.
83   virtual DecodeStatus getInstruction(MCInst &instr,
84                                       uint64_t &size,
85                                       const MemoryObject &region,
86                                       uint64_t address,
87                                       raw_ostream &vStream,
88                                       raw_ostream &cStream) const;
89 };
90
91 } // end anonymous namespace
92
93 // Forward declare these because the autogenerated code will reference them.
94 // Definitions are further down.
95 static DecodeStatus DecodeGPR64RegisterClass(MCInst &Inst,
96                                              unsigned RegNo,
97                                              uint64_t Address,
98                                              const void *Decoder);
99
100 static DecodeStatus DecodeCPU16RegsRegisterClass(MCInst &Inst,
101                                                  unsigned RegNo,
102                                                  uint64_t Address,
103                                                  const void *Decoder);
104
105 static DecodeStatus DecodeGPR32RegisterClass(MCInst &Inst,
106                                              unsigned RegNo,
107                                              uint64_t Address,
108                                              const void *Decoder);
109
110 static DecodeStatus DecodePtrRegisterClass(MCInst &Inst,
111                                            unsigned Insn,
112                                            uint64_t Address,
113                                            const void *Decoder);
114
115 static DecodeStatus DecodeDSPRRegisterClass(MCInst &Inst,
116                                             unsigned RegNo,
117                                             uint64_t Address,
118                                             const void *Decoder);
119
120 static DecodeStatus DecodeFGR64RegisterClass(MCInst &Inst,
121                                              unsigned RegNo,
122                                              uint64_t Address,
123                                              const void *Decoder);
124
125 static DecodeStatus DecodeFGR32RegisterClass(MCInst &Inst,
126                                              unsigned RegNo,
127                                              uint64_t Address,
128                                              const void *Decoder);
129
130 static DecodeStatus DecodeFGRH32RegisterClass(MCInst &Inst,
131                                               unsigned RegNo,
132                                               uint64_t Address,
133                                               const void *Decoder);
134
135 static DecodeStatus DecodeCCRRegisterClass(MCInst &Inst,
136                                            unsigned RegNo,
137                                            uint64_t Address,
138                                            const void *Decoder);
139
140 static DecodeStatus DecodeFCCRegisterClass(MCInst &Inst,
141                                            unsigned RegNo,
142                                            uint64_t Address,
143                                            const void *Decoder);
144
145 static DecodeStatus DecodeHWRegsRegisterClass(MCInst &Inst,
146                                               unsigned Insn,
147                                               uint64_t Address,
148                                               const void *Decoder);
149
150 static DecodeStatus DecodeAFGR64RegisterClass(MCInst &Inst,
151                                               unsigned RegNo,
152                                               uint64_t Address,
153                                               const void *Decoder);
154
155 static DecodeStatus DecodeACC64DSPRegisterClass(MCInst &Inst,
156                                                 unsigned RegNo,
157                                                 uint64_t Address,
158                                                 const void *Decoder);
159
160 static DecodeStatus DecodeHI32DSPRegisterClass(MCInst &Inst,
161                                                unsigned RegNo,
162                                                uint64_t Address,
163                                                const void *Decoder);
164
165 static DecodeStatus DecodeLO32DSPRegisterClass(MCInst &Inst,
166                                                unsigned RegNo,
167                                                uint64_t Address,
168                                                const void *Decoder);
169
170 static DecodeStatus DecodeBranchTarget(MCInst &Inst,
171                                        unsigned Offset,
172                                        uint64_t Address,
173                                        const void *Decoder);
174
175 static DecodeStatus DecodeJumpTarget(MCInst &Inst,
176                                      unsigned Insn,
177                                      uint64_t Address,
178                                      const void *Decoder);
179
180 static DecodeStatus DecodeMem(MCInst &Inst,
181                               unsigned Insn,
182                               uint64_t Address,
183                               const void *Decoder);
184
185 static DecodeStatus DecodeFMem(MCInst &Inst, unsigned Insn,
186                                uint64_t Address,
187                                const void *Decoder);
188
189 static DecodeStatus DecodeSimm16(MCInst &Inst,
190                                  unsigned Insn,
191                                  uint64_t Address,
192                                  const void *Decoder);
193
194 static DecodeStatus DecodeInsSize(MCInst &Inst,
195                                   unsigned Insn,
196                                   uint64_t Address,
197                                   const void *Decoder);
198
199 static DecodeStatus DecodeExtSize(MCInst &Inst,
200                                   unsigned Insn,
201                                   uint64_t Address,
202                                   const void *Decoder);
203
204 namespace llvm {
205 extern Target TheMipselTarget, TheMipsTarget, TheMips64Target,
206               TheMips64elTarget;
207 }
208
209 static MCDisassembler *createMipsDisassembler(
210                        const Target &T,
211                        const MCSubtargetInfo &STI) {
212   return new MipsDisassembler(STI, T.createMCRegInfo(""), true);
213 }
214
215 static MCDisassembler *createMipselDisassembler(
216                        const Target &T,
217                        const MCSubtargetInfo &STI) {
218   return new MipsDisassembler(STI, T.createMCRegInfo(""), false);
219 }
220
221 static MCDisassembler *createMips64Disassembler(
222                        const Target &T,
223                        const MCSubtargetInfo &STI) {
224   return new Mips64Disassembler(STI, T.createMCRegInfo(""), true);
225 }
226
227 static MCDisassembler *createMips64elDisassembler(
228                        const Target &T,
229                        const MCSubtargetInfo &STI) {
230   return new Mips64Disassembler(STI, T.createMCRegInfo(""), false);
231 }
232
233 extern "C" void LLVMInitializeMipsDisassembler() {
234   // Register the disassembler.
235   TargetRegistry::RegisterMCDisassembler(TheMipsTarget,
236                                          createMipsDisassembler);
237   TargetRegistry::RegisterMCDisassembler(TheMipselTarget,
238                                          createMipselDisassembler);
239   TargetRegistry::RegisterMCDisassembler(TheMips64Target,
240                                          createMips64Disassembler);
241   TargetRegistry::RegisterMCDisassembler(TheMips64elTarget,
242                                          createMips64elDisassembler);
243 }
244
245
246 #include "MipsGenDisassemblerTables.inc"
247
248   /// readInstruction - read four bytes from the MemoryObject
249   /// and return 32 bit word sorted according to the given endianess
250 static DecodeStatus readInstruction32(const MemoryObject &region,
251                                       uint64_t address,
252                                       uint64_t &size,
253                                       uint32_t &insn,
254                                       bool isBigEndian) {
255   uint8_t Bytes[4];
256
257   // We want to read exactly 4 Bytes of data.
258   if (region.readBytes(address, 4, Bytes) == -1) {
259     size = 0;
260     return MCDisassembler::Fail;
261   }
262
263   if (isBigEndian) {
264     // Encoded as a big-endian 32-bit word in the stream.
265     insn = (Bytes[3] <<  0) |
266            (Bytes[2] <<  8) |
267            (Bytes[1] << 16) |
268            (Bytes[0] << 24);
269   }
270   else {
271     // Encoded as a small-endian 32-bit word in the stream.
272     insn = (Bytes[0] <<  0) |
273            (Bytes[1] <<  8) |
274            (Bytes[2] << 16) |
275            (Bytes[3] << 24);
276   }
277
278   return MCDisassembler::Success;
279 }
280
281 DecodeStatus
282 MipsDisassembler::getInstruction(MCInst &instr,
283                                  uint64_t &Size,
284                                  const MemoryObject &Region,
285                                  uint64_t Address,
286                                  raw_ostream &vStream,
287                                  raw_ostream &cStream) const {
288   uint32_t Insn;
289
290   DecodeStatus Result = readInstruction32(Region, Address, Size,
291                                           Insn, isBigEndian);
292   if (Result == MCDisassembler::Fail)
293     return MCDisassembler::Fail;
294
295   // Calling the auto-generated decoder function.
296   Result = decodeInstruction(DecoderTableMips32, instr, Insn, Address,
297                              this, STI);
298   if (Result != MCDisassembler::Fail) {
299     Size = 4;
300     return Result;
301   }
302
303   return MCDisassembler::Fail;
304 }
305
306 DecodeStatus
307 Mips64Disassembler::getInstruction(MCInst &instr,
308                                    uint64_t &Size,
309                                    const MemoryObject &Region,
310                                    uint64_t Address,
311                                    raw_ostream &vStream,
312                                    raw_ostream &cStream) const {
313   uint32_t Insn;
314
315   DecodeStatus Result = readInstruction32(Region, Address, Size,
316                                           Insn, isBigEndian);
317   if (Result == MCDisassembler::Fail)
318     return MCDisassembler::Fail;
319
320   // Calling the auto-generated decoder function.
321   Result = decodeInstruction(DecoderTableMips6432, instr, Insn, Address,
322                              this, STI);
323   if (Result != MCDisassembler::Fail) {
324     Size = 4;
325     return Result;
326   }
327   // If we fail to decode in Mips64 decoder space we can try in Mips32
328   Result = decodeInstruction(DecoderTableMips32, instr, Insn, Address,
329                              this, STI);
330   if (Result != MCDisassembler::Fail) {
331     Size = 4;
332     return Result;
333   }
334
335   return MCDisassembler::Fail;
336 }
337
338 static unsigned getReg(const void *D, unsigned RC, unsigned RegNo) {
339   const MipsDisassemblerBase *Dis = static_cast<const MipsDisassemblerBase*>(D);
340   return *(Dis->getRegInfo()->getRegClass(RC).begin() + RegNo);
341 }
342
343 static DecodeStatus DecodeCPU16RegsRegisterClass(MCInst &Inst,
344                                                  unsigned RegNo,
345                                                  uint64_t Address,
346                                                  const void *Decoder) {
347
348   return MCDisassembler::Fail;
349
350 }
351
352 static DecodeStatus DecodeGPR64RegisterClass(MCInst &Inst,
353                                              unsigned RegNo,
354                                              uint64_t Address,
355                                              const void *Decoder) {
356
357   if (RegNo > 31)
358     return MCDisassembler::Fail;
359
360   unsigned Reg = getReg(Decoder, Mips::GPR64RegClassID, RegNo);
361   Inst.addOperand(MCOperand::CreateReg(Reg));
362   return MCDisassembler::Success;
363 }
364
365 static DecodeStatus DecodeGPR32RegisterClass(MCInst &Inst,
366                                              unsigned RegNo,
367                                              uint64_t Address,
368                                              const void *Decoder) {
369   if (RegNo > 31)
370     return MCDisassembler::Fail;
371   unsigned Reg = getReg(Decoder, Mips::GPR32RegClassID, RegNo);
372   Inst.addOperand(MCOperand::CreateReg(Reg));
373   return MCDisassembler::Success;
374 }
375
376 static DecodeStatus DecodePtrRegisterClass(MCInst &Inst,
377                                            unsigned RegNo,
378                                            uint64_t Address,
379                                            const void *Decoder) {
380   if (static_cast<const MipsDisassembler *>(Decoder)->isN64())
381     return DecodeGPR64RegisterClass(Inst, RegNo, Address, Decoder);
382
383   return DecodeGPR32RegisterClass(Inst, RegNo, Address, Decoder);
384 }
385
386 static DecodeStatus DecodeDSPRRegisterClass(MCInst &Inst,
387                                             unsigned RegNo,
388                                             uint64_t Address,
389                                             const void *Decoder) {
390   return DecodeGPR32RegisterClass(Inst, RegNo, Address, Decoder);
391 }
392
393 static DecodeStatus DecodeFGR64RegisterClass(MCInst &Inst,
394                                              unsigned RegNo,
395                                              uint64_t Address,
396                                              const void *Decoder) {
397   if (RegNo > 31)
398     return MCDisassembler::Fail;
399
400   unsigned Reg = getReg(Decoder, Mips::FGR64RegClassID, RegNo);
401   Inst.addOperand(MCOperand::CreateReg(Reg));
402   return MCDisassembler::Success;
403 }
404
405 static DecodeStatus DecodeFGR32RegisterClass(MCInst &Inst,
406                                              unsigned RegNo,
407                                              uint64_t Address,
408                                              const void *Decoder) {
409   if (RegNo > 31)
410     return MCDisassembler::Fail;
411
412   unsigned Reg = getReg(Decoder, Mips::FGR32RegClassID, RegNo);
413   Inst.addOperand(MCOperand::CreateReg(Reg));
414   return MCDisassembler::Success;
415 }
416
417 static DecodeStatus DecodeFGRH32RegisterClass(MCInst &Inst,
418                                               unsigned RegNo,
419                                               uint64_t Address,
420                                               const void *Decoder) {
421   if (RegNo > 31)
422     return MCDisassembler::Fail;
423
424   unsigned Reg = getReg(Decoder, Mips::FGRH32RegClassID, RegNo);
425   Inst.addOperand(MCOperand::CreateReg(Reg));
426   return MCDisassembler::Success;
427 }
428
429 static DecodeStatus DecodeCCRRegisterClass(MCInst &Inst,
430                                            unsigned RegNo,
431                                            uint64_t Address,
432                                            const void *Decoder) {
433   if (RegNo > 31)
434     return MCDisassembler::Fail;
435   unsigned Reg = getReg(Decoder, Mips::CCRRegClassID, RegNo);
436   Inst.addOperand(MCOperand::CreateReg(Reg));
437   return MCDisassembler::Success;
438 }
439
440 static DecodeStatus DecodeFCCRegisterClass(MCInst &Inst,
441                                            unsigned RegNo,
442                                            uint64_t Address,
443                                            const void *Decoder) {
444   if (RegNo > 7)
445     return MCDisassembler::Fail;
446   unsigned Reg = getReg(Decoder, Mips::FCCRegClassID, RegNo);
447   Inst.addOperand(MCOperand::CreateReg(Reg));
448   return MCDisassembler::Success;
449 }
450
451 static DecodeStatus DecodeMem(MCInst &Inst,
452                               unsigned Insn,
453                               uint64_t Address,
454                               const void *Decoder) {
455   int Offset = SignExtend32<16>(Insn & 0xffff);
456   unsigned Reg = fieldFromInstruction(Insn, 16, 5);
457   unsigned Base = fieldFromInstruction(Insn, 21, 5);
458
459   Reg = getReg(Decoder, Mips::GPR32RegClassID, Reg);
460   Base = getReg(Decoder, Mips::GPR32RegClassID, Base);
461
462   if(Inst.getOpcode() == Mips::SC){
463     Inst.addOperand(MCOperand::CreateReg(Reg));
464   }
465
466   Inst.addOperand(MCOperand::CreateReg(Reg));
467   Inst.addOperand(MCOperand::CreateReg(Base));
468   Inst.addOperand(MCOperand::CreateImm(Offset));
469
470   return MCDisassembler::Success;
471 }
472
473 static DecodeStatus DecodeFMem(MCInst &Inst,
474                                unsigned Insn,
475                                uint64_t Address,
476                                const void *Decoder) {
477   int Offset = SignExtend32<16>(Insn & 0xffff);
478   unsigned Reg = fieldFromInstruction(Insn, 16, 5);
479   unsigned Base = fieldFromInstruction(Insn, 21, 5);
480
481   Reg = getReg(Decoder, Mips::FGR64RegClassID, Reg);
482   Base = getReg(Decoder, Mips::GPR32RegClassID, Base);
483
484   Inst.addOperand(MCOperand::CreateReg(Reg));
485   Inst.addOperand(MCOperand::CreateReg(Base));
486   Inst.addOperand(MCOperand::CreateImm(Offset));
487
488   return MCDisassembler::Success;
489 }
490
491
492 static DecodeStatus DecodeHWRegsRegisterClass(MCInst &Inst,
493                                               unsigned RegNo,
494                                               uint64_t Address,
495                                               const void *Decoder) {
496   // Currently only hardware register 29 is supported.
497   if (RegNo != 29)
498     return  MCDisassembler::Fail;
499   Inst.addOperand(MCOperand::CreateReg(Mips::HWR29));
500   return MCDisassembler::Success;
501 }
502
503 static DecodeStatus DecodeAFGR64RegisterClass(MCInst &Inst,
504                                               unsigned RegNo,
505                                               uint64_t Address,
506                                               const void *Decoder) {
507   if (RegNo > 30 || RegNo %2)
508     return MCDisassembler::Fail;
509
510   ;
511   unsigned Reg = getReg(Decoder, Mips::AFGR64RegClassID, RegNo /2);
512   Inst.addOperand(MCOperand::CreateReg(Reg));
513   return MCDisassembler::Success;
514 }
515
516 static DecodeStatus DecodeACC64DSPRegisterClass(MCInst &Inst,
517                                                 unsigned RegNo,
518                                                 uint64_t Address,
519                                                 const void *Decoder) {
520   if (RegNo >= 4)
521     return MCDisassembler::Fail;
522
523   unsigned Reg = getReg(Decoder, Mips::ACC64DSPRegClassID, RegNo);
524   Inst.addOperand(MCOperand::CreateReg(Reg));
525   return MCDisassembler::Success;
526 }
527
528 static DecodeStatus DecodeHI32DSPRegisterClass(MCInst &Inst,
529                                                unsigned RegNo,
530                                                uint64_t Address,
531                                                const void *Decoder) {
532   if (RegNo >= 4)
533     return MCDisassembler::Fail;
534
535   unsigned Reg = getReg(Decoder, Mips::HI32DSPRegClassID, RegNo);
536   Inst.addOperand(MCOperand::CreateReg(Reg));
537   return MCDisassembler::Success;
538 }
539
540 static DecodeStatus DecodeLO32DSPRegisterClass(MCInst &Inst,
541                                                unsigned RegNo,
542                                                uint64_t Address,
543                                                const void *Decoder) {
544   if (RegNo >= 4)
545     return MCDisassembler::Fail;
546
547   unsigned Reg = getReg(Decoder, Mips::LO32DSPRegClassID, RegNo);
548   Inst.addOperand(MCOperand::CreateReg(Reg));
549   return MCDisassembler::Success;
550 }
551
552 static DecodeStatus DecodeBranchTarget(MCInst &Inst,
553                                        unsigned Offset,
554                                        uint64_t Address,
555                                        const void *Decoder) {
556   unsigned BranchOffset = Offset & 0xffff;
557   BranchOffset = SignExtend32<18>(BranchOffset << 2) + 4;
558   Inst.addOperand(MCOperand::CreateImm(BranchOffset));
559   return MCDisassembler::Success;
560 }
561
562 static DecodeStatus DecodeJumpTarget(MCInst &Inst,
563                                      unsigned Insn,
564                                      uint64_t Address,
565                                      const void *Decoder) {
566
567   unsigned JumpOffset = fieldFromInstruction(Insn, 0, 26) << 2;
568   Inst.addOperand(MCOperand::CreateImm(JumpOffset));
569   return MCDisassembler::Success;
570 }
571
572
573 static DecodeStatus DecodeSimm16(MCInst &Inst,
574                                  unsigned Insn,
575                                  uint64_t Address,
576                                  const void *Decoder) {
577   Inst.addOperand(MCOperand::CreateImm(SignExtend32<16>(Insn)));
578   return MCDisassembler::Success;
579 }
580
581 static DecodeStatus DecodeInsSize(MCInst &Inst,
582                                   unsigned Insn,
583                                   uint64_t Address,
584                                   const void *Decoder) {
585   // First we need to grab the pos(lsb) from MCInst.
586   int Pos = Inst.getOperand(2).getImm();
587   int Size = (int) Insn - Pos + 1;
588   Inst.addOperand(MCOperand::CreateImm(SignExtend32<16>(Size)));
589   return MCDisassembler::Success;
590 }
591
592 static DecodeStatus DecodeExtSize(MCInst &Inst,
593                                   unsigned Insn,
594                                   uint64_t Address,
595                                   const void *Decoder) {
596   int Size = (int) Insn  + 1;
597   Inst.addOperand(MCOperand::CreateImm(SignExtend32<16>(Size)));
598   return MCDisassembler::Success;
599 }