1*9a0e4156SSadaf Ebrahimi //===------ PPCDisassembler.cpp - Disassembler for PowerPC ------*- C++ -*-===//
2*9a0e4156SSadaf Ebrahimi //
3*9a0e4156SSadaf Ebrahimi // The LLVM Compiler Infrastructure
4*9a0e4156SSadaf Ebrahimi //
5*9a0e4156SSadaf Ebrahimi // This file is distributed under the University of Illinois Open Source
6*9a0e4156SSadaf Ebrahimi // License. See LICENSE.TXT for details.
7*9a0e4156SSadaf Ebrahimi //
8*9a0e4156SSadaf Ebrahimi //===----------------------------------------------------------------------===//
9*9a0e4156SSadaf Ebrahimi
10*9a0e4156SSadaf Ebrahimi /* Capstone Disassembly Engine */
11*9a0e4156SSadaf Ebrahimi /* By Nguyen Anh Quynh <[email protected]>, 2013-2015 */
12*9a0e4156SSadaf Ebrahimi
13*9a0e4156SSadaf Ebrahimi #ifdef CAPSTONE_HAS_POWERPC
14*9a0e4156SSadaf Ebrahimi
15*9a0e4156SSadaf Ebrahimi #include <stdio.h> // DEBUG
16*9a0e4156SSadaf Ebrahimi #include <stdlib.h>
17*9a0e4156SSadaf Ebrahimi #include <string.h>
18*9a0e4156SSadaf Ebrahimi
19*9a0e4156SSadaf Ebrahimi #include "../../cs_priv.h"
20*9a0e4156SSadaf Ebrahimi #include "../../utils.h"
21*9a0e4156SSadaf Ebrahimi
22*9a0e4156SSadaf Ebrahimi #include "PPCDisassembler.h"
23*9a0e4156SSadaf Ebrahimi
24*9a0e4156SSadaf Ebrahimi #include "../../MCInst.h"
25*9a0e4156SSadaf Ebrahimi #include "../../MCInstrDesc.h"
26*9a0e4156SSadaf Ebrahimi #include "../../MCFixedLenDisassembler.h"
27*9a0e4156SSadaf Ebrahimi #include "../../MCRegisterInfo.h"
28*9a0e4156SSadaf Ebrahimi #include "../../MCDisassembler.h"
29*9a0e4156SSadaf Ebrahimi #include "../../MathExtras.h"
30*9a0e4156SSadaf Ebrahimi
31*9a0e4156SSadaf Ebrahimi #define GET_REGINFO_ENUM
32*9a0e4156SSadaf Ebrahimi #include "PPCGenRegisterInfo.inc"
33*9a0e4156SSadaf Ebrahimi
34*9a0e4156SSadaf Ebrahimi
35*9a0e4156SSadaf Ebrahimi // FIXME: These can be generated by TableGen from the existing register
36*9a0e4156SSadaf Ebrahimi // encoding values!
37*9a0e4156SSadaf Ebrahimi
38*9a0e4156SSadaf Ebrahimi static const unsigned CRRegs[] = {
39*9a0e4156SSadaf Ebrahimi PPC_CR0, PPC_CR1, PPC_CR2, PPC_CR3,
40*9a0e4156SSadaf Ebrahimi PPC_CR4, PPC_CR5, PPC_CR6, PPC_CR7
41*9a0e4156SSadaf Ebrahimi };
42*9a0e4156SSadaf Ebrahimi
43*9a0e4156SSadaf Ebrahimi static const unsigned CRBITRegs[] = {
44*9a0e4156SSadaf Ebrahimi PPC_CR0LT, PPC_CR0GT, PPC_CR0EQ, PPC_CR0UN,
45*9a0e4156SSadaf Ebrahimi PPC_CR1LT, PPC_CR1GT, PPC_CR1EQ, PPC_CR1UN,
46*9a0e4156SSadaf Ebrahimi PPC_CR2LT, PPC_CR2GT, PPC_CR2EQ, PPC_CR2UN,
47*9a0e4156SSadaf Ebrahimi PPC_CR3LT, PPC_CR3GT, PPC_CR3EQ, PPC_CR3UN,
48*9a0e4156SSadaf Ebrahimi PPC_CR4LT, PPC_CR4GT, PPC_CR4EQ, PPC_CR4UN,
49*9a0e4156SSadaf Ebrahimi PPC_CR5LT, PPC_CR5GT, PPC_CR5EQ, PPC_CR5UN,
50*9a0e4156SSadaf Ebrahimi PPC_CR6LT, PPC_CR6GT, PPC_CR6EQ, PPC_CR6UN,
51*9a0e4156SSadaf Ebrahimi PPC_CR7LT, PPC_CR7GT, PPC_CR7EQ, PPC_CR7UN
52*9a0e4156SSadaf Ebrahimi };
53*9a0e4156SSadaf Ebrahimi
54*9a0e4156SSadaf Ebrahimi static const unsigned FRegs[] = {
55*9a0e4156SSadaf Ebrahimi PPC_F0, PPC_F1, PPC_F2, PPC_F3,
56*9a0e4156SSadaf Ebrahimi PPC_F4, PPC_F5, PPC_F6, PPC_F7,
57*9a0e4156SSadaf Ebrahimi PPC_F8, PPC_F9, PPC_F10, PPC_F11,
58*9a0e4156SSadaf Ebrahimi PPC_F12, PPC_F13, PPC_F14, PPC_F15,
59*9a0e4156SSadaf Ebrahimi PPC_F16, PPC_F17, PPC_F18, PPC_F19,
60*9a0e4156SSadaf Ebrahimi PPC_F20, PPC_F21, PPC_F22, PPC_F23,
61*9a0e4156SSadaf Ebrahimi PPC_F24, PPC_F25, PPC_F26, PPC_F27,
62*9a0e4156SSadaf Ebrahimi PPC_F28, PPC_F29, PPC_F30, PPC_F31
63*9a0e4156SSadaf Ebrahimi };
64*9a0e4156SSadaf Ebrahimi
65*9a0e4156SSadaf Ebrahimi static const unsigned VRegs[] = {
66*9a0e4156SSadaf Ebrahimi PPC_V0, PPC_V1, PPC_V2, PPC_V3,
67*9a0e4156SSadaf Ebrahimi PPC_V4, PPC_V5, PPC_V6, PPC_V7,
68*9a0e4156SSadaf Ebrahimi PPC_V8, PPC_V9, PPC_V10, PPC_V11,
69*9a0e4156SSadaf Ebrahimi PPC_V12, PPC_V13, PPC_V14, PPC_V15,
70*9a0e4156SSadaf Ebrahimi PPC_V16, PPC_V17, PPC_V18, PPC_V19,
71*9a0e4156SSadaf Ebrahimi PPC_V20, PPC_V21, PPC_V22, PPC_V23,
72*9a0e4156SSadaf Ebrahimi PPC_V24, PPC_V25, PPC_V26, PPC_V27,
73*9a0e4156SSadaf Ebrahimi PPC_V28, PPC_V29, PPC_V30, PPC_V31
74*9a0e4156SSadaf Ebrahimi };
75*9a0e4156SSadaf Ebrahimi
76*9a0e4156SSadaf Ebrahimi static const unsigned VSRegs[] = {
77*9a0e4156SSadaf Ebrahimi PPC_VSL0, PPC_VSL1, PPC_VSL2, PPC_VSL3,
78*9a0e4156SSadaf Ebrahimi PPC_VSL4, PPC_VSL5, PPC_VSL6, PPC_VSL7,
79*9a0e4156SSadaf Ebrahimi PPC_VSL8, PPC_VSL9, PPC_VSL10, PPC_VSL11,
80*9a0e4156SSadaf Ebrahimi PPC_VSL12, PPC_VSL13, PPC_VSL14, PPC_VSL15,
81*9a0e4156SSadaf Ebrahimi PPC_VSL16, PPC_VSL17, PPC_VSL18, PPC_VSL19,
82*9a0e4156SSadaf Ebrahimi PPC_VSL20, PPC_VSL21, PPC_VSL22, PPC_VSL23,
83*9a0e4156SSadaf Ebrahimi PPC_VSL24, PPC_VSL25, PPC_VSL26, PPC_VSL27,
84*9a0e4156SSadaf Ebrahimi PPC_VSL28, PPC_VSL29, PPC_VSL30, PPC_VSL31,
85*9a0e4156SSadaf Ebrahimi
86*9a0e4156SSadaf Ebrahimi PPC_VSH0, PPC_VSH1, PPC_VSH2, PPC_VSH3,
87*9a0e4156SSadaf Ebrahimi PPC_VSH4, PPC_VSH5, PPC_VSH6, PPC_VSH7,
88*9a0e4156SSadaf Ebrahimi PPC_VSH8, PPC_VSH9, PPC_VSH10, PPC_VSH11,
89*9a0e4156SSadaf Ebrahimi PPC_VSH12, PPC_VSH13, PPC_VSH14, PPC_VSH15,
90*9a0e4156SSadaf Ebrahimi PPC_VSH16, PPC_VSH17, PPC_VSH18, PPC_VSH19,
91*9a0e4156SSadaf Ebrahimi PPC_VSH20, PPC_VSH21, PPC_VSH22, PPC_VSH23,
92*9a0e4156SSadaf Ebrahimi PPC_VSH24, PPC_VSH25, PPC_VSH26, PPC_VSH27,
93*9a0e4156SSadaf Ebrahimi PPC_VSH28, PPC_VSH29, PPC_VSH30, PPC_VSH31
94*9a0e4156SSadaf Ebrahimi };
95*9a0e4156SSadaf Ebrahimi
96*9a0e4156SSadaf Ebrahimi static const unsigned VSFRegs[] = {
97*9a0e4156SSadaf Ebrahimi PPC_F0, PPC_F1, PPC_F2, PPC_F3,
98*9a0e4156SSadaf Ebrahimi PPC_F4, PPC_F5, PPC_F6, PPC_F7,
99*9a0e4156SSadaf Ebrahimi PPC_F8, PPC_F9, PPC_F10, PPC_F11,
100*9a0e4156SSadaf Ebrahimi PPC_F12, PPC_F13, PPC_F14, PPC_F15,
101*9a0e4156SSadaf Ebrahimi PPC_F16, PPC_F17, PPC_F18, PPC_F19,
102*9a0e4156SSadaf Ebrahimi PPC_F20, PPC_F21, PPC_F22, PPC_F23,
103*9a0e4156SSadaf Ebrahimi PPC_F24, PPC_F25, PPC_F26, PPC_F27,
104*9a0e4156SSadaf Ebrahimi PPC_F28, PPC_F29, PPC_F30, PPC_F31,
105*9a0e4156SSadaf Ebrahimi
106*9a0e4156SSadaf Ebrahimi PPC_VF0, PPC_VF1, PPC_VF2, PPC_VF3,
107*9a0e4156SSadaf Ebrahimi PPC_VF4, PPC_VF5, PPC_VF6, PPC_VF7,
108*9a0e4156SSadaf Ebrahimi PPC_VF8, PPC_VF9, PPC_VF10, PPC_VF11,
109*9a0e4156SSadaf Ebrahimi PPC_VF12, PPC_VF13, PPC_VF14, PPC_VF15,
110*9a0e4156SSadaf Ebrahimi PPC_VF16, PPC_VF17, PPC_VF18, PPC_VF19,
111*9a0e4156SSadaf Ebrahimi PPC_VF20, PPC_VF21, PPC_VF22, PPC_VF23,
112*9a0e4156SSadaf Ebrahimi PPC_VF24, PPC_VF25, PPC_VF26, PPC_VF27,
113*9a0e4156SSadaf Ebrahimi PPC_VF28, PPC_VF29, PPC_VF30, PPC_VF31
114*9a0e4156SSadaf Ebrahimi };
115*9a0e4156SSadaf Ebrahimi
116*9a0e4156SSadaf Ebrahimi static const unsigned GPRegs[] = {
117*9a0e4156SSadaf Ebrahimi PPC_R0, PPC_R1, PPC_R2, PPC_R3,
118*9a0e4156SSadaf Ebrahimi PPC_R4, PPC_R5, PPC_R6, PPC_R7,
119*9a0e4156SSadaf Ebrahimi PPC_R8, PPC_R9, PPC_R10, PPC_R11,
120*9a0e4156SSadaf Ebrahimi PPC_R12, PPC_R13, PPC_R14, PPC_R15,
121*9a0e4156SSadaf Ebrahimi PPC_R16, PPC_R17, PPC_R18, PPC_R19,
122*9a0e4156SSadaf Ebrahimi PPC_R20, PPC_R21, PPC_R22, PPC_R23,
123*9a0e4156SSadaf Ebrahimi PPC_R24, PPC_R25, PPC_R26, PPC_R27,
124*9a0e4156SSadaf Ebrahimi PPC_R28, PPC_R29, PPC_R30, PPC_R31
125*9a0e4156SSadaf Ebrahimi };
126*9a0e4156SSadaf Ebrahimi
127*9a0e4156SSadaf Ebrahimi static const unsigned GP0Regs[] = {
128*9a0e4156SSadaf Ebrahimi PPC_ZERO, PPC_R1, PPC_R2, PPC_R3,
129*9a0e4156SSadaf Ebrahimi PPC_R4, PPC_R5, PPC_R6, PPC_R7,
130*9a0e4156SSadaf Ebrahimi PPC_R8, PPC_R9, PPC_R10, PPC_R11,
131*9a0e4156SSadaf Ebrahimi PPC_R12, PPC_R13, PPC_R14, PPC_R15,
132*9a0e4156SSadaf Ebrahimi PPC_R16, PPC_R17, PPC_R18, PPC_R19,
133*9a0e4156SSadaf Ebrahimi PPC_R20, PPC_R21, PPC_R22, PPC_R23,
134*9a0e4156SSadaf Ebrahimi PPC_R24, PPC_R25, PPC_R26, PPC_R27,
135*9a0e4156SSadaf Ebrahimi PPC_R28, PPC_R29, PPC_R30, PPC_R31
136*9a0e4156SSadaf Ebrahimi };
137*9a0e4156SSadaf Ebrahimi
138*9a0e4156SSadaf Ebrahimi static const unsigned G8Regs[] = {
139*9a0e4156SSadaf Ebrahimi PPC_X0, PPC_X1, PPC_X2, PPC_X3,
140*9a0e4156SSadaf Ebrahimi PPC_X4, PPC_X5, PPC_X6, PPC_X7,
141*9a0e4156SSadaf Ebrahimi PPC_X8, PPC_X9, PPC_X10, PPC_X11,
142*9a0e4156SSadaf Ebrahimi PPC_X12, PPC_X13, PPC_X14, PPC_X15,
143*9a0e4156SSadaf Ebrahimi PPC_X16, PPC_X17, PPC_X18, PPC_X19,
144*9a0e4156SSadaf Ebrahimi PPC_X20, PPC_X21, PPC_X22, PPC_X23,
145*9a0e4156SSadaf Ebrahimi PPC_X24, PPC_X25, PPC_X26, PPC_X27,
146*9a0e4156SSadaf Ebrahimi PPC_X28, PPC_X29, PPC_X30, PPC_X31
147*9a0e4156SSadaf Ebrahimi };
148*9a0e4156SSadaf Ebrahimi
149*9a0e4156SSadaf Ebrahimi static const unsigned QFRegs[] = {
150*9a0e4156SSadaf Ebrahimi PPC_QF0, PPC_QF1, PPC_QF2, PPC_QF3,
151*9a0e4156SSadaf Ebrahimi PPC_QF4, PPC_QF5, PPC_QF6, PPC_QF7,
152*9a0e4156SSadaf Ebrahimi PPC_QF8, PPC_QF9, PPC_QF10, PPC_QF11,
153*9a0e4156SSadaf Ebrahimi PPC_QF12, PPC_QF13, PPC_QF14, PPC_QF15,
154*9a0e4156SSadaf Ebrahimi PPC_QF16, PPC_QF17, PPC_QF18, PPC_QF19,
155*9a0e4156SSadaf Ebrahimi PPC_QF20, PPC_QF21, PPC_QF22, PPC_QF23,
156*9a0e4156SSadaf Ebrahimi PPC_QF24, PPC_QF25, PPC_QF26, PPC_QF27,
157*9a0e4156SSadaf Ebrahimi PPC_QF28, PPC_QF29, PPC_QF30, PPC_QF31
158*9a0e4156SSadaf Ebrahimi };
159*9a0e4156SSadaf Ebrahimi
getFeatureBits(int feature)160*9a0e4156SSadaf Ebrahimi static uint64_t getFeatureBits(int feature)
161*9a0e4156SSadaf Ebrahimi {
162*9a0e4156SSadaf Ebrahimi // enable all features
163*9a0e4156SSadaf Ebrahimi return (uint64_t)-1;
164*9a0e4156SSadaf Ebrahimi }
165*9a0e4156SSadaf Ebrahimi
decodeRegisterClass(MCInst * Inst,uint64_t RegNo,const unsigned * Regs,size_t RegsLen)166*9a0e4156SSadaf Ebrahimi static DecodeStatus decodeRegisterClass(MCInst *Inst, uint64_t RegNo,
167*9a0e4156SSadaf Ebrahimi const unsigned *Regs, size_t RegsLen)
168*9a0e4156SSadaf Ebrahimi {
169*9a0e4156SSadaf Ebrahimi if (RegNo >= RegsLen / sizeof(unsigned)) {
170*9a0e4156SSadaf Ebrahimi return MCDisassembler_Fail;
171*9a0e4156SSadaf Ebrahimi }
172*9a0e4156SSadaf Ebrahimi MCOperand_CreateReg0(Inst, Regs[RegNo]);
173*9a0e4156SSadaf Ebrahimi return MCDisassembler_Success;
174*9a0e4156SSadaf Ebrahimi }
175*9a0e4156SSadaf Ebrahimi
DecodeCRRCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)176*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeCRRCRegisterClass(MCInst *Inst, uint64_t RegNo,
177*9a0e4156SSadaf Ebrahimi uint64_t Address,
178*9a0e4156SSadaf Ebrahimi const void *Decoder)
179*9a0e4156SSadaf Ebrahimi {
180*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, CRRegs, sizeof(CRRegs));
181*9a0e4156SSadaf Ebrahimi }
182*9a0e4156SSadaf Ebrahimi
DecodeCRBITRCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)183*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeCRBITRCRegisterClass(MCInst *Inst, uint64_t RegNo,
184*9a0e4156SSadaf Ebrahimi uint64_t Address,
185*9a0e4156SSadaf Ebrahimi const void *Decoder)
186*9a0e4156SSadaf Ebrahimi {
187*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, CRBITRegs, sizeof(CRBITRegs));
188*9a0e4156SSadaf Ebrahimi }
189*9a0e4156SSadaf Ebrahimi
DecodeF4RCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)190*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeF4RCRegisterClass(MCInst *Inst, uint64_t RegNo,
191*9a0e4156SSadaf Ebrahimi uint64_t Address,
192*9a0e4156SSadaf Ebrahimi const void *Decoder)
193*9a0e4156SSadaf Ebrahimi {
194*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, FRegs, sizeof(FRegs));
195*9a0e4156SSadaf Ebrahimi }
196*9a0e4156SSadaf Ebrahimi
DecodeF8RCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)197*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeF8RCRegisterClass(MCInst *Inst, uint64_t RegNo,
198*9a0e4156SSadaf Ebrahimi uint64_t Address,
199*9a0e4156SSadaf Ebrahimi const void *Decoder)
200*9a0e4156SSadaf Ebrahimi {
201*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, FRegs, sizeof(FRegs));
202*9a0e4156SSadaf Ebrahimi }
203*9a0e4156SSadaf Ebrahimi
DecodeVRRCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)204*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeVRRCRegisterClass(MCInst *Inst, uint64_t RegNo,
205*9a0e4156SSadaf Ebrahimi uint64_t Address,
206*9a0e4156SSadaf Ebrahimi const void *Decoder)
207*9a0e4156SSadaf Ebrahimi {
208*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, VRegs, sizeof(VRegs));
209*9a0e4156SSadaf Ebrahimi }
210*9a0e4156SSadaf Ebrahimi
DecodeVSRCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)211*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeVSRCRegisterClass(MCInst *Inst, uint64_t RegNo,
212*9a0e4156SSadaf Ebrahimi uint64_t Address,
213*9a0e4156SSadaf Ebrahimi const void *Decoder)
214*9a0e4156SSadaf Ebrahimi {
215*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, VSRegs, sizeof(VSRegs));
216*9a0e4156SSadaf Ebrahimi }
217*9a0e4156SSadaf Ebrahimi
DecodeVSFRCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)218*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeVSFRCRegisterClass(MCInst *Inst, uint64_t RegNo,
219*9a0e4156SSadaf Ebrahimi uint64_t Address,
220*9a0e4156SSadaf Ebrahimi const void *Decoder)
221*9a0e4156SSadaf Ebrahimi {
222*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, VSFRegs, sizeof(VSFRegs));
223*9a0e4156SSadaf Ebrahimi }
224*9a0e4156SSadaf Ebrahimi
DecodeGPRCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)225*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeGPRCRegisterClass(MCInst *Inst, uint64_t RegNo,
226*9a0e4156SSadaf Ebrahimi uint64_t Address,
227*9a0e4156SSadaf Ebrahimi const void *Decoder)
228*9a0e4156SSadaf Ebrahimi {
229*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, GPRegs, sizeof(GPRegs));
230*9a0e4156SSadaf Ebrahimi }
231*9a0e4156SSadaf Ebrahimi
DecodeGPRC_NOR0RegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)232*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeGPRC_NOR0RegisterClass(MCInst *Inst, uint64_t RegNo,
233*9a0e4156SSadaf Ebrahimi uint64_t Address,
234*9a0e4156SSadaf Ebrahimi const void *Decoder)
235*9a0e4156SSadaf Ebrahimi {
236*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, GP0Regs, sizeof(GP0Regs));
237*9a0e4156SSadaf Ebrahimi }
238*9a0e4156SSadaf Ebrahimi
DecodeG8RCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)239*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeG8RCRegisterClass(MCInst *Inst, uint64_t RegNo,
240*9a0e4156SSadaf Ebrahimi uint64_t Address,
241*9a0e4156SSadaf Ebrahimi const void *Decoder)
242*9a0e4156SSadaf Ebrahimi {
243*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, G8Regs, sizeof(G8Regs));
244*9a0e4156SSadaf Ebrahimi }
245*9a0e4156SSadaf Ebrahimi
246*9a0e4156SSadaf Ebrahimi #define DecodePointerLikeRegClass0 DecodeGPRCRegisterClass
247*9a0e4156SSadaf Ebrahimi #define DecodePointerLikeRegClass1 DecodeGPRC_NOR0RegisterClass
248*9a0e4156SSadaf Ebrahimi
DecodeQFRCRegisterClass(MCInst * Inst,uint64_t RegNo,uint64_t Address,const void * Decoder)249*9a0e4156SSadaf Ebrahimi static DecodeStatus DecodeQFRCRegisterClass(MCInst *Inst, uint64_t RegNo,
250*9a0e4156SSadaf Ebrahimi uint64_t Address,
251*9a0e4156SSadaf Ebrahimi const void *Decoder)
252*9a0e4156SSadaf Ebrahimi {
253*9a0e4156SSadaf Ebrahimi return decodeRegisterClass(Inst, RegNo, QFRegs, sizeof(QFRegs));
254*9a0e4156SSadaf Ebrahimi }
255*9a0e4156SSadaf Ebrahimi
256*9a0e4156SSadaf Ebrahimi #define DecodeQSRCRegisterClass DecodeQFRCRegisterClass
257*9a0e4156SSadaf Ebrahimi #define DecodeQBRCRegisterClass DecodeQFRCRegisterClass
258*9a0e4156SSadaf Ebrahimi
decodeUImmOperand(MCInst * Inst,uint64_t Imm,int64_t Address,const void * Decoder,unsigned N)259*9a0e4156SSadaf Ebrahimi static DecodeStatus decodeUImmOperand(MCInst *Inst, uint64_t Imm,
260*9a0e4156SSadaf Ebrahimi int64_t Address, const void *Decoder, unsigned N)
261*9a0e4156SSadaf Ebrahimi {
262*9a0e4156SSadaf Ebrahimi //assert(isUInt<N>(Imm) && "Invalid immediate");
263*9a0e4156SSadaf Ebrahimi MCOperand_CreateImm0(Inst, Imm);
264*9a0e4156SSadaf Ebrahimi return MCDisassembler_Success;
265*9a0e4156SSadaf Ebrahimi }
266*9a0e4156SSadaf Ebrahimi
decodeSImmOperand(MCInst * Inst,uint64_t Imm,int64_t Address,const void * Decoder,unsigned N)267*9a0e4156SSadaf Ebrahimi static DecodeStatus decodeSImmOperand(MCInst *Inst, uint64_t Imm,
268*9a0e4156SSadaf Ebrahimi int64_t Address, const void *Decoder, unsigned N)
269*9a0e4156SSadaf Ebrahimi {
270*9a0e4156SSadaf Ebrahimi // assert(isUInt<N>(Imm) && "Invalid immediate");
271*9a0e4156SSadaf Ebrahimi MCOperand_CreateImm0(Inst, SignExtend64(Imm, N));
272*9a0e4156SSadaf Ebrahimi return MCDisassembler_Success;
273*9a0e4156SSadaf Ebrahimi }
274*9a0e4156SSadaf Ebrahimi
275*9a0e4156SSadaf Ebrahimi
276*9a0e4156SSadaf Ebrahimi #define GET_INSTRINFO_ENUM
277*9a0e4156SSadaf Ebrahimi #include "PPCGenInstrInfo.inc"
278*9a0e4156SSadaf Ebrahimi
decodeMemRIOperands(MCInst * Inst,uint64_t Imm,int64_t Address,const void * Decoder)279*9a0e4156SSadaf Ebrahimi static DecodeStatus decodeMemRIOperands(MCInst *Inst, uint64_t Imm,
280*9a0e4156SSadaf Ebrahimi int64_t Address, const void *Decoder)
281*9a0e4156SSadaf Ebrahimi {
282*9a0e4156SSadaf Ebrahimi // Decode the memri field (imm, reg), which has the low 16-bits as the
283*9a0e4156SSadaf Ebrahimi // displacement and the next 5 bits as the register #.
284*9a0e4156SSadaf Ebrahimi
285*9a0e4156SSadaf Ebrahimi uint64_t Base = Imm >> 16;
286*9a0e4156SSadaf Ebrahimi uint64_t Disp = Imm & 0xFFFF;
287*9a0e4156SSadaf Ebrahimi
288*9a0e4156SSadaf Ebrahimi // assert(Base < 32 && "Invalid base register");
289*9a0e4156SSadaf Ebrahimi if (Base >= 32)
290*9a0e4156SSadaf Ebrahimi return MCDisassembler_Fail;
291*9a0e4156SSadaf Ebrahimi
292*9a0e4156SSadaf Ebrahimi switch (MCInst_getOpcode(Inst)) {
293*9a0e4156SSadaf Ebrahimi default: break;
294*9a0e4156SSadaf Ebrahimi case PPC_LBZU:
295*9a0e4156SSadaf Ebrahimi case PPC_LHAU:
296*9a0e4156SSadaf Ebrahimi case PPC_LHZU:
297*9a0e4156SSadaf Ebrahimi case PPC_LWZU:
298*9a0e4156SSadaf Ebrahimi case PPC_LFSU:
299*9a0e4156SSadaf Ebrahimi case PPC_LFDU:
300*9a0e4156SSadaf Ebrahimi // Add the tied output operand.
301*9a0e4156SSadaf Ebrahimi MCOperand_CreateReg0(Inst, GP0Regs[Base]);
302*9a0e4156SSadaf Ebrahimi break;
303*9a0e4156SSadaf Ebrahimi case PPC_STBU:
304*9a0e4156SSadaf Ebrahimi case PPC_STHU:
305*9a0e4156SSadaf Ebrahimi case PPC_STWU:
306*9a0e4156SSadaf Ebrahimi case PPC_STFSU:
307*9a0e4156SSadaf Ebrahimi case PPC_STFDU:
308*9a0e4156SSadaf Ebrahimi MCInst_insert0(Inst, 0, MCOperand_CreateReg1(Inst, GP0Regs[Base]));
309*9a0e4156SSadaf Ebrahimi break;
310*9a0e4156SSadaf Ebrahimi }
311*9a0e4156SSadaf Ebrahimi
312*9a0e4156SSadaf Ebrahimi MCOperand_CreateImm0(Inst, SignExtend64(Disp, 16));
313*9a0e4156SSadaf Ebrahimi MCOperand_CreateReg0(Inst, GP0Regs[Base]);
314*9a0e4156SSadaf Ebrahimi return MCDisassembler_Success;
315*9a0e4156SSadaf Ebrahimi }
316*9a0e4156SSadaf Ebrahimi
decodeMemRIXOperands(MCInst * Inst,uint64_t Imm,int64_t Address,const void * Decoder)317*9a0e4156SSadaf Ebrahimi static DecodeStatus decodeMemRIXOperands(MCInst *Inst, uint64_t Imm,
318*9a0e4156SSadaf Ebrahimi int64_t Address, const void *Decoder)
319*9a0e4156SSadaf Ebrahimi {
320*9a0e4156SSadaf Ebrahimi // Decode the memrix field (imm, reg), which has the low 14-bits as the
321*9a0e4156SSadaf Ebrahimi // displacement and the next 5 bits as the register #.
322*9a0e4156SSadaf Ebrahimi
323*9a0e4156SSadaf Ebrahimi uint64_t Base = Imm >> 14;
324*9a0e4156SSadaf Ebrahimi uint64_t Disp = Imm & 0x3FFF;
325*9a0e4156SSadaf Ebrahimi
326*9a0e4156SSadaf Ebrahimi // assert(Base < 32 && "Invalid base register");
327*9a0e4156SSadaf Ebrahimi
328*9a0e4156SSadaf Ebrahimi if (MCInst_getOpcode(Inst) == PPC_LDU)
329*9a0e4156SSadaf Ebrahimi // Add the tied output operand.
330*9a0e4156SSadaf Ebrahimi MCOperand_CreateReg0(Inst, GP0Regs[Base]);
331*9a0e4156SSadaf Ebrahimi else if (MCInst_getOpcode(Inst) == PPC_STDU)
332*9a0e4156SSadaf Ebrahimi MCInst_insert0(Inst, 0, MCOperand_CreateReg1(Inst, GP0Regs[Base]));
333*9a0e4156SSadaf Ebrahimi
334*9a0e4156SSadaf Ebrahimi MCOperand_CreateImm0(Inst, SignExtend64(Disp << 2, 16));
335*9a0e4156SSadaf Ebrahimi MCOperand_CreateReg0(Inst, GP0Regs[Base]);
336*9a0e4156SSadaf Ebrahimi return MCDisassembler_Success;
337*9a0e4156SSadaf Ebrahimi }
338*9a0e4156SSadaf Ebrahimi
decodeCRBitMOperand(MCInst * Inst,uint64_t Imm,int64_t Address,const void * Decoder)339*9a0e4156SSadaf Ebrahimi static DecodeStatus decodeCRBitMOperand(MCInst *Inst, uint64_t Imm,
340*9a0e4156SSadaf Ebrahimi int64_t Address, const void *Decoder)
341*9a0e4156SSadaf Ebrahimi {
342*9a0e4156SSadaf Ebrahimi // The cr bit encoding is 0x80 >> cr_reg_num.
343*9a0e4156SSadaf Ebrahimi
344*9a0e4156SSadaf Ebrahimi unsigned Zeros = CountTrailingZeros_64(Imm);
345*9a0e4156SSadaf Ebrahimi // assert(Zeros < 8 && "Invalid CR bit value");
346*9a0e4156SSadaf Ebrahimi if (Zeros >=8)
347*9a0e4156SSadaf Ebrahimi return MCDisassembler_Fail;
348*9a0e4156SSadaf Ebrahimi
349*9a0e4156SSadaf Ebrahimi MCOperand_CreateReg0(Inst, CRRegs[7 - Zeros]);
350*9a0e4156SSadaf Ebrahimi return MCDisassembler_Success;
351*9a0e4156SSadaf Ebrahimi }
352*9a0e4156SSadaf Ebrahimi
353*9a0e4156SSadaf Ebrahimi #include "PPCGenDisassemblerTables.inc"
354*9a0e4156SSadaf Ebrahimi
getInstruction(MCInst * MI,const uint8_t * code,size_t code_len,uint16_t * Size,uint64_t Address,MCRegisterInfo * MRI)355*9a0e4156SSadaf Ebrahimi static DecodeStatus getInstruction(MCInst *MI,
356*9a0e4156SSadaf Ebrahimi const uint8_t *code, size_t code_len,
357*9a0e4156SSadaf Ebrahimi uint16_t *Size,
358*9a0e4156SSadaf Ebrahimi uint64_t Address, MCRegisterInfo *MRI)
359*9a0e4156SSadaf Ebrahimi {
360*9a0e4156SSadaf Ebrahimi uint32_t insn;
361*9a0e4156SSadaf Ebrahimi DecodeStatus result;
362*9a0e4156SSadaf Ebrahimi // Get the four bytes of the instruction.
363*9a0e4156SSadaf Ebrahimi if (code_len < 4) {
364*9a0e4156SSadaf Ebrahimi // not enough data
365*9a0e4156SSadaf Ebrahimi *Size = 0;
366*9a0e4156SSadaf Ebrahimi return MCDisassembler_Fail;
367*9a0e4156SSadaf Ebrahimi }
368*9a0e4156SSadaf Ebrahimi
369*9a0e4156SSadaf Ebrahimi // The instruction is big-endian encoded.
370*9a0e4156SSadaf Ebrahimi if (MODE_IS_BIG_ENDIAN(MI->csh->mode))
371*9a0e4156SSadaf Ebrahimi insn = ((uint32_t) code[0] << 24) | (code[1] << 16) |
372*9a0e4156SSadaf Ebrahimi (code[2] << 8) | (code[3] << 0);
373*9a0e4156SSadaf Ebrahimi else
374*9a0e4156SSadaf Ebrahimi insn = ((uint32_t) code[3] << 24) | (code[2] << 16) |
375*9a0e4156SSadaf Ebrahimi (code[1] << 8) | (code[0] << 0);
376*9a0e4156SSadaf Ebrahimi
377*9a0e4156SSadaf Ebrahimi if (MI->flat_insn->detail) {
378*9a0e4156SSadaf Ebrahimi memset(MI->flat_insn->detail, 0, offsetof(cs_detail, ppc)+sizeof(cs_ppc));
379*9a0e4156SSadaf Ebrahimi }
380*9a0e4156SSadaf Ebrahimi
381*9a0e4156SSadaf Ebrahimi if (MI->csh->mode & CS_MODE_QPX) {
382*9a0e4156SSadaf Ebrahimi result = decodeInstruction_4(DecoderTableQPX32, MI, insn, Address, 4);
383*9a0e4156SSadaf Ebrahimi if (result != MCDisassembler_Fail) {
384*9a0e4156SSadaf Ebrahimi *Size = 4;
385*9a0e4156SSadaf Ebrahimi return result;
386*9a0e4156SSadaf Ebrahimi }
387*9a0e4156SSadaf Ebrahimi
388*9a0e4156SSadaf Ebrahimi MCInst_clear(MI);
389*9a0e4156SSadaf Ebrahimi }
390*9a0e4156SSadaf Ebrahimi
391*9a0e4156SSadaf Ebrahimi result = decodeInstruction_4(DecoderTable32, MI, insn, Address, 4);
392*9a0e4156SSadaf Ebrahimi if (result != MCDisassembler_Fail) {
393*9a0e4156SSadaf Ebrahimi *Size = 4;
394*9a0e4156SSadaf Ebrahimi return result;
395*9a0e4156SSadaf Ebrahimi }
396*9a0e4156SSadaf Ebrahimi
397*9a0e4156SSadaf Ebrahimi // report error
398*9a0e4156SSadaf Ebrahimi MCInst_clear(MI);
399*9a0e4156SSadaf Ebrahimi *Size = 0;
400*9a0e4156SSadaf Ebrahimi return MCDisassembler_Fail;
401*9a0e4156SSadaf Ebrahimi }
402*9a0e4156SSadaf Ebrahimi
PPC_getInstruction(csh ud,const uint8_t * code,size_t code_len,MCInst * instr,uint16_t * size,uint64_t address,void * info)403*9a0e4156SSadaf Ebrahimi bool PPC_getInstruction(csh ud, const uint8_t *code, size_t code_len,
404*9a0e4156SSadaf Ebrahimi MCInst *instr, uint16_t *size, uint64_t address, void *info)
405*9a0e4156SSadaf Ebrahimi {
406*9a0e4156SSadaf Ebrahimi DecodeStatus status = getInstruction(instr,
407*9a0e4156SSadaf Ebrahimi code, code_len,
408*9a0e4156SSadaf Ebrahimi size,
409*9a0e4156SSadaf Ebrahimi address, (MCRegisterInfo *)info);
410*9a0e4156SSadaf Ebrahimi
411*9a0e4156SSadaf Ebrahimi return status == MCDisassembler_Success;
412*9a0e4156SSadaf Ebrahimi }
413*9a0e4156SSadaf Ebrahimi
414*9a0e4156SSadaf Ebrahimi #define GET_REGINFO_MC_DESC
415*9a0e4156SSadaf Ebrahimi #include "PPCGenRegisterInfo.inc"
PPC_init(MCRegisterInfo * MRI)416*9a0e4156SSadaf Ebrahimi void PPC_init(MCRegisterInfo *MRI)
417*9a0e4156SSadaf Ebrahimi {
418*9a0e4156SSadaf Ebrahimi /*
419*9a0e4156SSadaf Ebrahimi InitMCRegisterInfo(PPCRegDesc, 310, RA, PC,
420*9a0e4156SSadaf Ebrahimi PPCMCRegisterClasses, 23,
421*9a0e4156SSadaf Ebrahimi PPCRegUnitRoots,
422*9a0e4156SSadaf Ebrahimi 138,
423*9a0e4156SSadaf Ebrahimi PPCRegDiffLists,
424*9a0e4156SSadaf Ebrahimi PPCLaneMaskLists,
425*9a0e4156SSadaf Ebrahimi PPCRegStrings,
426*9a0e4156SSadaf Ebrahimi PPCRegClassStrings,
427*9a0e4156SSadaf Ebrahimi PPCSubRegIdxLists,
428*9a0e4156SSadaf Ebrahimi 8,
429*9a0e4156SSadaf Ebrahimi PPCSubRegIdxRanges,
430*9a0e4156SSadaf Ebrahimi PPCRegEncodingTable);
431*9a0e4156SSadaf Ebrahimi */
432*9a0e4156SSadaf Ebrahimi
433*9a0e4156SSadaf Ebrahimi
434*9a0e4156SSadaf Ebrahimi MCRegisterInfo_InitMCRegisterInfo(MRI, PPCRegDesc, 310,
435*9a0e4156SSadaf Ebrahimi 0, 0,
436*9a0e4156SSadaf Ebrahimi PPCMCRegisterClasses, 23,
437*9a0e4156SSadaf Ebrahimi 0, 0,
438*9a0e4156SSadaf Ebrahimi PPCRegDiffLists,
439*9a0e4156SSadaf Ebrahimi 0,
440*9a0e4156SSadaf Ebrahimi PPCSubRegIdxLists, 8,
441*9a0e4156SSadaf Ebrahimi 0);
442*9a0e4156SSadaf Ebrahimi }
443*9a0e4156SSadaf Ebrahimi
444*9a0e4156SSadaf Ebrahimi #endif
445