blob: b6b265cd1ed12a24d83519e22bfff907e638efe5 [file] [log] [blame]
Akira Hatanaka71928e62012-04-17 18:03:21 +00001//===- 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"
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000015#include "MipsRegisterInfo.h"
Chandler Carruthed0881b2012-12-03 16:50:05 +000016#include "MipsSubtarget.h"
Akira Hatanaka71928e62012-04-17 18:03:21 +000017#include "llvm/MC/MCDisassembler.h"
Jim Grosbachecaef492012-08-14 19:06:05 +000018#include "llvm/MC/MCFixedLenDisassembler.h"
Chandler Carruthed0881b2012-12-03 16:50:05 +000019#include "llvm/MC/MCInst.h"
20#include "llvm/MC/MCSubtargetInfo.h"
21#include "llvm/Support/MathExtras.h"
Akira Hatanaka71928e62012-04-17 18:03:21 +000022#include "llvm/Support/MemoryObject.h"
23#include "llvm/Support/TargetRegistry.h"
Akira Hatanaka71928e62012-04-17 18:03:21 +000024
Akira Hatanaka71928e62012-04-17 18:03:21 +000025using namespace llvm;
26
27typedef MCDisassembler::DecodeStatus DecodeStatus;
28
Benjamin Kramercb3e98c2012-05-01 14:34:24 +000029namespace {
30
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000031/// MipsDisassemblerBase - a disasembler class for Mips.
32class MipsDisassemblerBase : public MCDisassembler {
Akira Hatanaka71928e62012-04-17 18:03:21 +000033public:
34 /// Constructor - Initializes the disassembler.
35 ///
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000036 MipsDisassemblerBase(const MCSubtargetInfo &STI, const MCRegisterInfo *Info,
37 bool bigEndian) :
38 MCDisassembler(STI), RegInfo(Info), isBigEndian(bigEndian) {}
Akira Hatanaka71928e62012-04-17 18:03:21 +000039
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000040 virtual ~MipsDisassemblerBase() {}
Akira Hatanaka71928e62012-04-17 18:03:21 +000041
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000042 const MCRegisterInfo *getRegInfo() const { return RegInfo; }
43
Akira Hatanaka71928e62012-04-17 18:03:21 +000044private:
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000045 const MCRegisterInfo *RegInfo;
46protected:
Akira Hatanaka71928e62012-04-17 18:03:21 +000047 bool isBigEndian;
48};
49
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000050/// MipsDisassembler - a disasembler class for Mips32.
51class MipsDisassembler : public MipsDisassemblerBase {
52public:
53 /// Constructor - Initializes the disassembler.
54 ///
55 MipsDisassembler(const MCSubtargetInfo &STI, const MCRegisterInfo *Info,
56 bool bigEndian) :
57 MipsDisassemblerBase(STI, Info, bigEndian) {}
58
59 /// getInstruction - See MCDisassembler.
60 virtual DecodeStatus getInstruction(MCInst &instr,
61 uint64_t &size,
62 const MemoryObject &region,
63 uint64_t address,
64 raw_ostream &vStream,
65 raw_ostream &cStream) const;
66};
67
Akira Hatanaka71928e62012-04-17 18:03:21 +000068
69/// Mips64Disassembler - a disasembler class for Mips64.
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000070class Mips64Disassembler : public MipsDisassemblerBase {
Akira Hatanaka71928e62012-04-17 18:03:21 +000071public:
72 /// Constructor - Initializes the disassembler.
73 ///
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000074 Mips64Disassembler(const MCSubtargetInfo &STI, const MCRegisterInfo *Info,
75 bool bigEndian) :
76 MipsDisassemblerBase(STI, Info, bigEndian) {}
Akira Hatanaka71928e62012-04-17 18:03:21 +000077
78 /// getInstruction - See MCDisassembler.
Akira Hatanaka9bf2b562012-07-09 18:46:47 +000079 virtual DecodeStatus getInstruction(MCInst &instr,
80 uint64_t &size,
81 const MemoryObject &region,
82 uint64_t address,
83 raw_ostream &vStream,
84 raw_ostream &cStream) const;
Akira Hatanaka71928e62012-04-17 18:03:21 +000085};
86
Benjamin Kramercb3e98c2012-05-01 14:34:24 +000087} // end anonymous namespace
88
Akira Hatanaka71928e62012-04-17 18:03:21 +000089// Forward declare these because the autogenerated code will reference them.
90// Definitions are further down.
91static DecodeStatus DecodeCPU64RegsRegisterClass(MCInst &Inst,
92 unsigned RegNo,
93 uint64_t Address,
94 const void *Decoder);
95
Reed Kotlerec8a5492013-02-14 03:05:25 +000096static DecodeStatus DecodeCPU16RegsRegisterClass(MCInst &Inst,
97 unsigned RegNo,
98 uint64_t Address,
99 const void *Decoder);
100
Akira Hatanaka71928e62012-04-17 18:03:21 +0000101static DecodeStatus DecodeCPURegsRegisterClass(MCInst &Inst,
102 unsigned RegNo,
103 uint64_t Address,
104 const void *Decoder);
105
Akira Hatanakaecabd1a2012-09-27 02:01:10 +0000106static DecodeStatus DecodeDSPRegsRegisterClass(MCInst &Inst,
107 unsigned RegNo,
108 uint64_t Address,
109 const void *Decoder);
110
Akira Hatanaka71928e62012-04-17 18:03:21 +0000111static DecodeStatus DecodeFGR64RegisterClass(MCInst &Inst,
112 unsigned RegNo,
113 uint64_t Address,
114 const void *Decoder);
115
116static DecodeStatus DecodeFGR32RegisterClass(MCInst &Inst,
117 unsigned RegNo,
118 uint64_t Address,
119 const void *Decoder);
120
121static DecodeStatus DecodeCCRRegisterClass(MCInst &Inst,
122 unsigned RegNo,
123 uint64_t Address,
124 const void *Decoder);
125
126static DecodeStatus DecodeHWRegsRegisterClass(MCInst &Inst,
127 unsigned Insn,
128 uint64_t Address,
129 const void *Decoder);
130
131static DecodeStatus DecodeAFGR64RegisterClass(MCInst &Inst,
132 unsigned RegNo,
133 uint64_t Address,
134 const void *Decoder);
135
Jack Carter2a74a87b2013-01-17 00:28:20 +0000136static DecodeStatus DecodeHWRegs64RegisterClass(MCInst &Inst,
137 unsigned Insn,
138 uint64_t Address,
139 const void *Decoder);
140
Akira Hatanakafb221c12013-03-30 01:58:00 +0000141static DecodeStatus DecodeACRegsDSPRegisterClass(MCInst &Inst,
142 unsigned RegNo,
143 uint64_t Address,
144 const void *Decoder);
Akira Hatanakaecabd1a2012-09-27 02:01:10 +0000145
Akira Hatanaka59bfaf72013-04-18 00:52:44 +0000146static DecodeStatus DecodeHIRegsDSPRegisterClass(MCInst &Inst,
147 unsigned RegNo,
148 uint64_t Address,
149 const void *Decoder);
150
151static DecodeStatus DecodeLORegsDSPRegisterClass(MCInst &Inst,
152 unsigned RegNo,
153 uint64_t Address,
154 const void *Decoder);
155
Akira Hatanaka71928e62012-04-17 18:03:21 +0000156static DecodeStatus DecodeBranchTarget(MCInst &Inst,
157 unsigned Offset,
158 uint64_t Address,
159 const void *Decoder);
160
161static DecodeStatus DecodeBC1(MCInst &Inst,
162 unsigned Insn,
163 uint64_t Address,
164 const void *Decoder);
165
166
167static DecodeStatus DecodeJumpTarget(MCInst &Inst,
168 unsigned Insn,
169 uint64_t Address,
170 const void *Decoder);
171
172static DecodeStatus DecodeMem(MCInst &Inst,
173 unsigned Insn,
174 uint64_t Address,
175 const void *Decoder);
176
177static DecodeStatus DecodeFMem(MCInst &Inst, unsigned Insn,
178 uint64_t Address,
179 const void *Decoder);
180
181static DecodeStatus DecodeSimm16(MCInst &Inst,
182 unsigned Insn,
183 uint64_t Address,
184 const void *Decoder);
185
186static DecodeStatus DecodeCondCode(MCInst &Inst,
187 unsigned Insn,
188 uint64_t Address,
189 const void *Decoder);
190
191static DecodeStatus DecodeInsSize(MCInst &Inst,
192 unsigned Insn,
193 uint64_t Address,
194 const void *Decoder);
195
196static DecodeStatus DecodeExtSize(MCInst &Inst,
197 unsigned Insn,
198 uint64_t Address,
199 const void *Decoder);
200
201namespace llvm {
202extern Target TheMipselTarget, TheMipsTarget, TheMips64Target,
203 TheMips64elTarget;
204}
205
206static MCDisassembler *createMipsDisassembler(
207 const Target &T,
208 const MCSubtargetInfo &STI) {
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000209 return new MipsDisassembler(STI, T.createMCRegInfo(""), true);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000210}
211
212static MCDisassembler *createMipselDisassembler(
213 const Target &T,
214 const MCSubtargetInfo &STI) {
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000215 return new MipsDisassembler(STI, T.createMCRegInfo(""), false);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000216}
217
218static MCDisassembler *createMips64Disassembler(
219 const Target &T,
220 const MCSubtargetInfo &STI) {
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000221 return new Mips64Disassembler(STI, T.createMCRegInfo(""), true);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000222}
223
224static MCDisassembler *createMips64elDisassembler(
225 const Target &T,
226 const MCSubtargetInfo &STI) {
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000227 return new Mips64Disassembler(STI, T.createMCRegInfo(""), false);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000228}
229
230extern "C" void LLVMInitializeMipsDisassembler() {
231 // Register the disassembler.
232 TargetRegistry::RegisterMCDisassembler(TheMipsTarget,
233 createMipsDisassembler);
234 TargetRegistry::RegisterMCDisassembler(TheMipselTarget,
235 createMipselDisassembler);
236 TargetRegistry::RegisterMCDisassembler(TheMips64Target,
237 createMips64Disassembler);
238 TargetRegistry::RegisterMCDisassembler(TheMips64elTarget,
239 createMips64elDisassembler);
240}
241
242
243#include "MipsGenDisassemblerTables.inc"
244
245 /// readInstruction - read four bytes from the MemoryObject
246 /// and return 32 bit word sorted according to the given endianess
247static DecodeStatus readInstruction32(const MemoryObject &region,
248 uint64_t address,
249 uint64_t &size,
250 uint32_t &insn,
251 bool isBigEndian) {
252 uint8_t Bytes[4];
253
254 // We want to read exactly 4 Bytes of data.
Benjamin Kramer534d3a42013-05-24 10:54:58 +0000255 if (region.readBytes(address, 4, Bytes) == -1) {
Akira Hatanaka71928e62012-04-17 18:03:21 +0000256 size = 0;
257 return MCDisassembler::Fail;
258 }
259
260 if (isBigEndian) {
261 // Encoded as a big-endian 32-bit word in the stream.
262 insn = (Bytes[3] << 0) |
263 (Bytes[2] << 8) |
264 (Bytes[1] << 16) |
265 (Bytes[0] << 24);
266 }
267 else {
268 // Encoded as a small-endian 32-bit word in the stream.
269 insn = (Bytes[0] << 0) |
270 (Bytes[1] << 8) |
271 (Bytes[2] << 16) |
272 (Bytes[3] << 24);
273 }
274
275 return MCDisassembler::Success;
276}
277
278DecodeStatus
279MipsDisassembler::getInstruction(MCInst &instr,
280 uint64_t &Size,
281 const MemoryObject &Region,
282 uint64_t Address,
283 raw_ostream &vStream,
284 raw_ostream &cStream) const {
285 uint32_t Insn;
286
287 DecodeStatus Result = readInstruction32(Region, Address, Size,
288 Insn, isBigEndian);
289 if (Result == MCDisassembler::Fail)
290 return MCDisassembler::Fail;
291
292 // Calling the auto-generated decoder function.
Jim Grosbachecaef492012-08-14 19:06:05 +0000293 Result = decodeInstruction(DecoderTableMips32, instr, Insn, Address,
294 this, STI);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000295 if (Result != MCDisassembler::Fail) {
296 Size = 4;
297 return Result;
298 }
299
300 return MCDisassembler::Fail;
301}
302
303DecodeStatus
304Mips64Disassembler::getInstruction(MCInst &instr,
305 uint64_t &Size,
306 const MemoryObject &Region,
307 uint64_t Address,
308 raw_ostream &vStream,
309 raw_ostream &cStream) const {
310 uint32_t Insn;
311
312 DecodeStatus Result = readInstruction32(Region, Address, Size,
313 Insn, isBigEndian);
314 if (Result == MCDisassembler::Fail)
315 return MCDisassembler::Fail;
316
317 // Calling the auto-generated decoder function.
Jim Grosbachecaef492012-08-14 19:06:05 +0000318 Result = decodeInstruction(DecoderTableMips6432, instr, Insn, Address,
319 this, STI);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000320 if (Result != MCDisassembler::Fail) {
321 Size = 4;
322 return Result;
323 }
324 // If we fail to decode in Mips64 decoder space we can try in Mips32
Jim Grosbachecaef492012-08-14 19:06:05 +0000325 Result = decodeInstruction(DecoderTableMips32, instr, Insn, Address,
326 this, STI);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000327 if (Result != MCDisassembler::Fail) {
328 Size = 4;
329 return Result;
330 }
331
332 return MCDisassembler::Fail;
333}
334
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000335static unsigned getReg(const void *D, unsigned RC, unsigned RegNo) {
336 const MipsDisassemblerBase *Dis = static_cast<const MipsDisassemblerBase*>(D);
337 return *(Dis->getRegInfo()->getRegClass(RC).begin() + RegNo);
338}
339
Reed Kotlerec8a5492013-02-14 03:05:25 +0000340static DecodeStatus DecodeCPU16RegsRegisterClass(MCInst &Inst,
341 unsigned RegNo,
342 uint64_t Address,
343 const void *Decoder) {
344
345 return MCDisassembler::Fail;
346
347}
348
Akira Hatanaka71928e62012-04-17 18:03:21 +0000349static DecodeStatus DecodeCPU64RegsRegisterClass(MCInst &Inst,
350 unsigned RegNo,
351 uint64_t Address,
352 const void *Decoder) {
353
354 if (RegNo > 31)
355 return MCDisassembler::Fail;
356
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000357 unsigned Reg = getReg(Decoder, Mips::CPU64RegsRegClassID, RegNo);
358 Inst.addOperand(MCOperand::CreateReg(Reg));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000359 return MCDisassembler::Success;
360}
361
362static DecodeStatus DecodeCPURegsRegisterClass(MCInst &Inst,
363 unsigned RegNo,
364 uint64_t Address,
365 const void *Decoder) {
366 if (RegNo > 31)
367 return MCDisassembler::Fail;
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000368 unsigned Reg = getReg(Decoder, Mips::CPURegsRegClassID, RegNo);
369 Inst.addOperand(MCOperand::CreateReg(Reg));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000370 return MCDisassembler::Success;
371}
372
Akira Hatanakaecabd1a2012-09-27 02:01:10 +0000373static DecodeStatus DecodeDSPRegsRegisterClass(MCInst &Inst,
374 unsigned RegNo,
375 uint64_t Address,
376 const void *Decoder) {
377 return DecodeCPURegsRegisterClass(Inst, RegNo, Address, Decoder);
378}
379
Akira Hatanaka71928e62012-04-17 18:03:21 +0000380static DecodeStatus DecodeFGR64RegisterClass(MCInst &Inst,
381 unsigned RegNo,
382 uint64_t Address,
383 const void *Decoder) {
384 if (RegNo > 31)
385 return MCDisassembler::Fail;
386
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000387 unsigned Reg = getReg(Decoder, Mips::FGR64RegClassID, RegNo);
388 Inst.addOperand(MCOperand::CreateReg(Reg));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000389 return MCDisassembler::Success;
390}
391
392static DecodeStatus DecodeFGR32RegisterClass(MCInst &Inst,
393 unsigned RegNo,
394 uint64_t Address,
395 const void *Decoder) {
396 if (RegNo > 31)
397 return MCDisassembler::Fail;
398
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000399 unsigned Reg = getReg(Decoder, Mips::FGR32RegClassID, RegNo);
400 Inst.addOperand(MCOperand::CreateReg(Reg));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000401 return MCDisassembler::Success;
402}
403
404static DecodeStatus DecodeCCRRegisterClass(MCInst &Inst,
405 unsigned RegNo,
406 uint64_t Address,
407 const void *Decoder) {
Chad Rosier253777f2013-06-26 22:23:32 +0000408 if (RegNo > 31)
409 return MCDisassembler::Fail;
410 unsigned Reg = getReg(Decoder, Mips::CCRRegClassID, RegNo);
411 Inst.addOperand(MCOperand::CreateReg(Reg));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000412 return MCDisassembler::Success;
413}
414
415static DecodeStatus DecodeMem(MCInst &Inst,
416 unsigned Insn,
417 uint64_t Address,
418 const void *Decoder) {
419 int Offset = SignExtend32<16>(Insn & 0xffff);
Jim Grosbachecaef492012-08-14 19:06:05 +0000420 unsigned Reg = fieldFromInstruction(Insn, 16, 5);
421 unsigned Base = fieldFromInstruction(Insn, 21, 5);
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000422
423 Reg = getReg(Decoder, Mips::CPURegsRegClassID, Reg);
424 Base = getReg(Decoder, Mips::CPURegsRegClassID, Base);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000425
426 if(Inst.getOpcode() == Mips::SC){
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000427 Inst.addOperand(MCOperand::CreateReg(Reg));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000428 }
429
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000430 Inst.addOperand(MCOperand::CreateReg(Reg));
431 Inst.addOperand(MCOperand::CreateReg(Base));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000432 Inst.addOperand(MCOperand::CreateImm(Offset));
433
434 return MCDisassembler::Success;
435}
436
437static DecodeStatus DecodeFMem(MCInst &Inst,
438 unsigned Insn,
439 uint64_t Address,
440 const void *Decoder) {
441 int Offset = SignExtend32<16>(Insn & 0xffff);
Jim Grosbachecaef492012-08-14 19:06:05 +0000442 unsigned Reg = fieldFromInstruction(Insn, 16, 5);
443 unsigned Base = fieldFromInstruction(Insn, 21, 5);
Akira Hatanaka71928e62012-04-17 18:03:21 +0000444
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000445 Reg = getReg(Decoder, Mips::FGR64RegClassID, Reg);
446 Base = getReg(Decoder, Mips::CPURegsRegClassID, Base);
447
448 Inst.addOperand(MCOperand::CreateReg(Reg));
449 Inst.addOperand(MCOperand::CreateReg(Base));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000450 Inst.addOperand(MCOperand::CreateImm(Offset));
451
452 return MCDisassembler::Success;
453}
454
455
456static DecodeStatus DecodeHWRegsRegisterClass(MCInst &Inst,
457 unsigned RegNo,
458 uint64_t Address,
459 const void *Decoder) {
460 // Currently only hardware register 29 is supported.
461 if (RegNo != 29)
462 return MCDisassembler::Fail;
463 Inst.addOperand(MCOperand::CreateReg(Mips::HWR29));
464 return MCDisassembler::Success;
465}
466
467static DecodeStatus DecodeCondCode(MCInst &Inst,
468 unsigned Insn,
469 uint64_t Address,
470 const void *Decoder) {
471 int CondCode = Insn & 0xf;
472 Inst.addOperand(MCOperand::CreateImm(CondCode));
473 return MCDisassembler::Success;
474}
475
476static DecodeStatus DecodeAFGR64RegisterClass(MCInst &Inst,
477 unsigned RegNo,
478 uint64_t Address,
479 const void *Decoder) {
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000480 if (RegNo > 30 || RegNo %2)
Akira Hatanaka71928e62012-04-17 18:03:21 +0000481 return MCDisassembler::Fail;
482
Akira Hatanaka9bf2b562012-07-09 18:46:47 +0000483 ;
484 unsigned Reg = getReg(Decoder, Mips::AFGR64RegClassID, RegNo /2);
485 Inst.addOperand(MCOperand::CreateReg(Reg));
Akira Hatanaka71928e62012-04-17 18:03:21 +0000486 return MCDisassembler::Success;
487}
488
Jack Carter2a74a87b2013-01-17 00:28:20 +0000489static DecodeStatus DecodeHWRegs64RegisterClass(MCInst &Inst,
490 unsigned RegNo,
491 uint64_t Address,
492 const void *Decoder) {
493 //Currently only hardware register 29 is supported
494 if (RegNo != 29)
495 return MCDisassembler::Fail;
496 Inst.addOperand(MCOperand::CreateReg(Mips::HWR29_64));
497 return MCDisassembler::Success;
498}
499
Akira Hatanakafb221c12013-03-30 01:58:00 +0000500static DecodeStatus DecodeACRegsDSPRegisterClass(MCInst &Inst,
501 unsigned RegNo,
502 uint64_t Address,
503 const void *Decoder) {
Akira Hatanakaecabd1a2012-09-27 02:01:10 +0000504 if (RegNo >= 4)
505 return MCDisassembler::Fail;
506
Akira Hatanakafb221c12013-03-30 01:58:00 +0000507 unsigned Reg = getReg(Decoder, Mips::ACRegsDSPRegClassID, RegNo);
Akira Hatanakaecabd1a2012-09-27 02:01:10 +0000508 Inst.addOperand(MCOperand::CreateReg(Reg));
509 return MCDisassembler::Success;
510}
511
Akira Hatanaka59bfaf72013-04-18 00:52:44 +0000512static DecodeStatus DecodeHIRegsDSPRegisterClass(MCInst &Inst,
513 unsigned RegNo,
514 uint64_t Address,
515 const void *Decoder) {
516 if (RegNo >= 4)
517 return MCDisassembler::Fail;
518
519 unsigned Reg = getReg(Decoder, Mips::HIRegsDSPRegClassID, RegNo);
520 Inst.addOperand(MCOperand::CreateReg(Reg));
521 return MCDisassembler::Success;
522}
523
524static DecodeStatus DecodeLORegsDSPRegisterClass(MCInst &Inst,
525 unsigned RegNo,
526 uint64_t Address,
527 const void *Decoder) {
528 if (RegNo >= 4)
529 return MCDisassembler::Fail;
530
531 unsigned Reg = getReg(Decoder, Mips::LORegsDSPRegClassID, RegNo);
532 Inst.addOperand(MCOperand::CreateReg(Reg));
533 return MCDisassembler::Success;
534}
535
Akira Hatanaka71928e62012-04-17 18:03:21 +0000536static DecodeStatus DecodeBranchTarget(MCInst &Inst,
537 unsigned Offset,
538 uint64_t Address,
539 const void *Decoder) {
540 unsigned BranchOffset = Offset & 0xffff;
541 BranchOffset = SignExtend32<18>(BranchOffset << 2) + 4;
542 Inst.addOperand(MCOperand::CreateImm(BranchOffset));
543 return MCDisassembler::Success;
544}
545
546static DecodeStatus DecodeBC1(MCInst &Inst,
547 unsigned Insn,
548 uint64_t Address,
549 const void *Decoder) {
550 unsigned BranchOffset = Insn & 0xffff;
551 BranchOffset = SignExtend32<18>(BranchOffset << 2) + 4;
552 Inst.addOperand(MCOperand::CreateImm(BranchOffset));
553 return MCDisassembler::Success;
554}
555
556static DecodeStatus DecodeJumpTarget(MCInst &Inst,
557 unsigned Insn,
558 uint64_t Address,
559 const void *Decoder) {
560
Jim Grosbachecaef492012-08-14 19:06:05 +0000561 unsigned JumpOffset = fieldFromInstruction(Insn, 0, 26) << 2;
Akira Hatanaka71928e62012-04-17 18:03:21 +0000562 Inst.addOperand(MCOperand::CreateImm(JumpOffset));
563 return MCDisassembler::Success;
564}
565
566
567static DecodeStatus DecodeSimm16(MCInst &Inst,
568 unsigned Insn,
569 uint64_t Address,
570 const void *Decoder) {
571 Inst.addOperand(MCOperand::CreateImm(SignExtend32<16>(Insn)));
572 return MCDisassembler::Success;
573}
574
575static DecodeStatus DecodeInsSize(MCInst &Inst,
576 unsigned Insn,
577 uint64_t Address,
578 const void *Decoder) {
579 // First we need to grab the pos(lsb) from MCInst.
580 int Pos = Inst.getOperand(2).getImm();
581 int Size = (int) Insn - Pos + 1;
582 Inst.addOperand(MCOperand::CreateImm(SignExtend32<16>(Size)));
583 return MCDisassembler::Success;
584}
585
586static DecodeStatus DecodeExtSize(MCInst &Inst,
587 unsigned Insn,
588 uint64_t Address,
589 const void *Decoder) {
590 int Size = (int) Insn + 1;
591 Inst.addOperand(MCOperand::CreateImm(SignExtend32<16>(Size)));
592 return MCDisassembler::Success;
593}