xref: /aosp_15_r20/external/capstone/arch/ARM/ARMInstPrinter.c (revision 9a0e4156d50a75a99ec4f1653a0e9602a5d45c18)
1*9a0e4156SSadaf Ebrahimi //===-- ARMInstPrinter.cpp - Convert ARM MCInst to assembly syntax --------===//
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 // This class prints an ARM MCInst to a .s file.
11*9a0e4156SSadaf Ebrahimi //
12*9a0e4156SSadaf Ebrahimi //===----------------------------------------------------------------------===//
13*9a0e4156SSadaf Ebrahimi 
14*9a0e4156SSadaf Ebrahimi /* Capstone Disassembly Engine */
15*9a0e4156SSadaf Ebrahimi /* By Nguyen Anh Quynh <[email protected]>, 2013-2015 */
16*9a0e4156SSadaf Ebrahimi 
17*9a0e4156SSadaf Ebrahimi #ifdef CAPSTONE_HAS_ARM
18*9a0e4156SSadaf Ebrahimi 
19*9a0e4156SSadaf Ebrahimi #include <stdio.h>	// DEBUG
20*9a0e4156SSadaf Ebrahimi #include <stdlib.h>
21*9a0e4156SSadaf Ebrahimi #include <string.h>
22*9a0e4156SSadaf Ebrahimi #include <capstone/platform.h>
23*9a0e4156SSadaf Ebrahimi 
24*9a0e4156SSadaf Ebrahimi #include "ARMInstPrinter.h"
25*9a0e4156SSadaf Ebrahimi #include "ARMAddressingModes.h"
26*9a0e4156SSadaf Ebrahimi #include "ARMBaseInfo.h"
27*9a0e4156SSadaf Ebrahimi #include "ARMDisassembler.h"
28*9a0e4156SSadaf Ebrahimi #include "../../MCInst.h"
29*9a0e4156SSadaf Ebrahimi #include "../../SStream.h"
30*9a0e4156SSadaf Ebrahimi #include "../../MCRegisterInfo.h"
31*9a0e4156SSadaf Ebrahimi #include "../../utils.h"
32*9a0e4156SSadaf Ebrahimi #include "ARMMapping.h"
33*9a0e4156SSadaf Ebrahimi 
34*9a0e4156SSadaf Ebrahimi #define GET_SUBTARGETINFO_ENUM
35*9a0e4156SSadaf Ebrahimi #include "ARMGenSubtargetInfo.inc"
36*9a0e4156SSadaf Ebrahimi 
37*9a0e4156SSadaf Ebrahimi 
38*9a0e4156SSadaf Ebrahimi static void printRegName(cs_struct *h, SStream *OS, unsigned RegNo);
39*9a0e4156SSadaf Ebrahimi 
40*9a0e4156SSadaf Ebrahimi // Autogenerated by tblgen.
41*9a0e4156SSadaf Ebrahimi static void printInstruction(MCInst *MI, SStream *O, MCRegisterInfo *MRI);
42*9a0e4156SSadaf Ebrahimi static void printOperand(MCInst *MI, unsigned OpNo, SStream *O);
43*9a0e4156SSadaf Ebrahimi static void printSORegRegOperand(MCInst *MI, unsigned OpNum, SStream *O);
44*9a0e4156SSadaf Ebrahimi static void printSORegImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
45*9a0e4156SSadaf Ebrahimi 
46*9a0e4156SSadaf Ebrahimi static void printAddrModeTBB(MCInst *MI, unsigned OpNum, SStream *O);
47*9a0e4156SSadaf Ebrahimi static void printAddrModeTBH(MCInst *MI, unsigned OpNum, SStream *O);
48*9a0e4156SSadaf Ebrahimi static void printAddrMode2Operand(MCInst *MI, unsigned OpNum, SStream *O);
49*9a0e4156SSadaf Ebrahimi static void printAM2PreOrOffsetIndexOp(MCInst *MI, unsigned OpNum, SStream *O);
50*9a0e4156SSadaf Ebrahimi static void printAddrMode2OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O);
51*9a0e4156SSadaf Ebrahimi static void printAddrMode3Operand(MCInst *MI, unsigned OpNum, SStream *O, bool AlwaysPrintImm0);
52*9a0e4156SSadaf Ebrahimi static void printAddrMode3OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O);
53*9a0e4156SSadaf Ebrahimi static void printAM3PreOrOffsetIndexOp(MCInst *MI, unsigned Op, SStream *O, bool AlwaysPrintImm0);
54*9a0e4156SSadaf Ebrahimi static void printPostIdxImm8Operand(MCInst *MI, unsigned OpNum, SStream *O);
55*9a0e4156SSadaf Ebrahimi static void printPostIdxRegOperand(MCInst *MI, unsigned OpNum, SStream *O);
56*9a0e4156SSadaf Ebrahimi static void printPostIdxImm8s4Operand(MCInst *MI, unsigned OpNum, SStream *O);
57*9a0e4156SSadaf Ebrahimi static void printAddrMode5Operand(MCInst *MI, unsigned OpNum, SStream *O, bool AlwaysPrintImm0);
58*9a0e4156SSadaf Ebrahimi static void printAddrMode6Operand(MCInst *MI, unsigned OpNum, SStream *O);
59*9a0e4156SSadaf Ebrahimi static void printAddrMode7Operand(MCInst *MI, unsigned OpNum, SStream *O);
60*9a0e4156SSadaf Ebrahimi static void printAddrMode6OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O);
61*9a0e4156SSadaf Ebrahimi 
62*9a0e4156SSadaf Ebrahimi static void printBitfieldInvMaskImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
63*9a0e4156SSadaf Ebrahimi static void printMemBOption(MCInst *MI, unsigned OpNum, SStream *O);
64*9a0e4156SSadaf Ebrahimi static void printShiftImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
65*9a0e4156SSadaf Ebrahimi static void printPKHLSLShiftImm(MCInst *MI, unsigned OpNum, SStream *O);
66*9a0e4156SSadaf Ebrahimi static void printPKHASRShiftImm(MCInst *MI, unsigned OpNum, SStream *O);
67*9a0e4156SSadaf Ebrahimi static void printAdrLabelOperand(MCInst *MI, unsigned OpNum, SStream *O, unsigned);
68*9a0e4156SSadaf Ebrahimi static void printThumbS4ImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
69*9a0e4156SSadaf Ebrahimi static void printThumbSRImm(MCInst *MI, unsigned OpNum, SStream *O);
70*9a0e4156SSadaf Ebrahimi static void printThumbITMask(MCInst *MI, unsigned OpNum, SStream *O);
71*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeRROperand(MCInst *MI, unsigned OpNum, SStream *O);
72*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5SOperand(MCInst *MI, unsigned OpNum, SStream *O, unsigned Scale);
73*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5S1Operand(MCInst *MI, unsigned OpNum, SStream *O);
74*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5S2Operand(MCInst *MI, unsigned OpNum, SStream *O);
75*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5S4Operand(MCInst *MI, unsigned OpNum, SStream *O);
76*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeSPOperand(MCInst *MI, unsigned OpNum, SStream *O);
77*9a0e4156SSadaf Ebrahimi static void printT2SOOperand(MCInst *MI, unsigned OpNum, SStream *O);
78*9a0e4156SSadaf Ebrahimi static void printAddrModeImm12Operand(MCInst *MI, unsigned OpNum, SStream *O, bool AlwaysPrintImm0);
79*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8Operand(MCInst *MI, unsigned OpNum, SStream *O, bool);
80*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8s4Operand(MCInst *MI, unsigned OpNum, SStream *O, bool);
81*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm0_1020s4Operand(MCInst *MI, unsigned OpNum, SStream *O);
82*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O);
83*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8s4OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O);
84*9a0e4156SSadaf Ebrahimi static void printT2AddrModeSoRegOperand(MCInst *MI, unsigned OpNum, SStream *O);
85*9a0e4156SSadaf Ebrahimi static void printSetendOperand(MCInst *MI, unsigned OpNum, SStream *O);
86*9a0e4156SSadaf Ebrahimi static void printCPSIMod(MCInst *MI, unsigned OpNum, SStream *O);
87*9a0e4156SSadaf Ebrahimi static void printCPSIFlag(MCInst *MI, unsigned OpNum, SStream *O);
88*9a0e4156SSadaf Ebrahimi static void printMSRMaskOperand(MCInst *MI, unsigned OpNum, SStream *O);
89*9a0e4156SSadaf Ebrahimi static void printPredicateOperand(MCInst *MI, unsigned OpNum, SStream *O);
90*9a0e4156SSadaf Ebrahimi static void printMandatoryPredicateOperand(MCInst *MI, unsigned OpNum, SStream *O);
91*9a0e4156SSadaf Ebrahimi static void printSBitModifierOperand(MCInst *MI, unsigned OpNum, SStream *O);
92*9a0e4156SSadaf Ebrahimi static void printRegisterList(MCInst *MI, unsigned OpNum, SStream *O);
93*9a0e4156SSadaf Ebrahimi static void printNoHashImmediate(MCInst *MI, unsigned OpNum, SStream *O);
94*9a0e4156SSadaf Ebrahimi static void printPImmediate(MCInst *MI, unsigned OpNum, SStream *O);
95*9a0e4156SSadaf Ebrahimi static void printCImmediate(MCInst *MI, unsigned OpNum, SStream *O);
96*9a0e4156SSadaf Ebrahimi static void printCoprocOptionImm(MCInst *MI, unsigned OpNum, SStream *O);
97*9a0e4156SSadaf Ebrahimi static void printFPImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
98*9a0e4156SSadaf Ebrahimi static void printNEONModImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
99*9a0e4156SSadaf Ebrahimi static void printImmPlusOneOperand(MCInst *MI, unsigned OpNum, SStream *O);
100*9a0e4156SSadaf Ebrahimi static void printRotImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
101*9a0e4156SSadaf Ebrahimi static void printGPRPairOperand(MCInst *MI, unsigned OpNum, SStream *O, MCRegisterInfo *MRI);
102*9a0e4156SSadaf Ebrahimi static void printThumbLdrLabelOperand(MCInst *MI, unsigned OpNum, SStream *O);
103*9a0e4156SSadaf Ebrahimi static void printFBits16(MCInst *MI, unsigned OpNum, SStream *O);
104*9a0e4156SSadaf Ebrahimi static void printFBits32(MCInst *MI, unsigned OpNum, SStream *O);
105*9a0e4156SSadaf Ebrahimi static void printVectorIndex(MCInst *MI, unsigned OpNum, SStream *O);
106*9a0e4156SSadaf Ebrahimi static void printVectorListOne(MCInst *MI, unsigned OpNum, SStream *O);
107*9a0e4156SSadaf Ebrahimi static void printVectorListTwo(MCInst *MI, unsigned OpNum, SStream *O, MCRegisterInfo *MRI);
108*9a0e4156SSadaf Ebrahimi static void printVectorListTwoSpaced(MCInst *MI, unsigned OpNum, SStream *O, MCRegisterInfo *RI);
109*9a0e4156SSadaf Ebrahimi static void printVectorListThree(MCInst *MI, unsigned OpNum, SStream *O);
110*9a0e4156SSadaf Ebrahimi static void printVectorListFour(MCInst *MI, unsigned OpNum, SStream *O);
111*9a0e4156SSadaf Ebrahimi static void printVectorListOneAllLanes(MCInst *MI, unsigned OpNum, SStream *O);
112*9a0e4156SSadaf Ebrahimi static void printVectorListTwoAllLanes(MCInst *MI, unsigned OpNum, SStream *O, MCRegisterInfo *RI);
113*9a0e4156SSadaf Ebrahimi static void printVectorListThreeAllLanes(MCInst *MI, unsigned OpNum, SStream *O);
114*9a0e4156SSadaf Ebrahimi static void printVectorListFourAllLanes(MCInst *MI, unsigned OpNum, SStream *O);
115*9a0e4156SSadaf Ebrahimi static void printVectorListTwoSpacedAllLanes(MCInst *MI, unsigned OpNum, SStream *O, MCRegisterInfo *MRI);
116*9a0e4156SSadaf Ebrahimi static void printVectorListThreeSpacedAllLanes(MCInst *MI, unsigned OpNum, SStream *O);
117*9a0e4156SSadaf Ebrahimi static void printVectorListFourSpacedAllLanes(MCInst *MI, unsigned OpNum, SStream *O);
118*9a0e4156SSadaf Ebrahimi static void printVectorListThreeSpaced(MCInst *MI, unsigned OpNum, SStream *O);
119*9a0e4156SSadaf Ebrahimi static void printVectorListFourSpaced(MCInst *MI, unsigned OpNum, SStream *O);
120*9a0e4156SSadaf Ebrahimi static void printBankedRegOperand(MCInst *MI, unsigned OpNum, SStream *O);
121*9a0e4156SSadaf Ebrahimi static void printModImmOperand(MCInst *MI, unsigned OpNum, SStream *O);
122*9a0e4156SSadaf Ebrahimi 
123*9a0e4156SSadaf Ebrahimi static void printInstSyncBOption(MCInst *MI, unsigned OpNum, SStream *O);
124*9a0e4156SSadaf Ebrahimi 
125*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
126*9a0e4156SSadaf Ebrahimi // copy & normalize access info
get_op_access(cs_struct * h,unsigned int id,unsigned int index)127*9a0e4156SSadaf Ebrahimi static uint8_t get_op_access(cs_struct *h, unsigned int id, unsigned int index)
128*9a0e4156SSadaf Ebrahimi {
129*9a0e4156SSadaf Ebrahimi 	uint8_t *arr = ARM_get_op_access(h, id);
130*9a0e4156SSadaf Ebrahimi 
131*9a0e4156SSadaf Ebrahimi 	if (arr[index] == CS_AC_IGNORE)
132*9a0e4156SSadaf Ebrahimi 		return 0;
133*9a0e4156SSadaf Ebrahimi 
134*9a0e4156SSadaf Ebrahimi 	return arr[index];
135*9a0e4156SSadaf Ebrahimi }
136*9a0e4156SSadaf Ebrahimi #endif
137*9a0e4156SSadaf Ebrahimi 
set_mem_access(MCInst * MI,bool status)138*9a0e4156SSadaf Ebrahimi static void set_mem_access(MCInst *MI, bool status)
139*9a0e4156SSadaf Ebrahimi {
140*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail != CS_OPT_ON)
141*9a0e4156SSadaf Ebrahimi 		return;
142*9a0e4156SSadaf Ebrahimi 
143*9a0e4156SSadaf Ebrahimi 	MI->csh->doing_mem = status;
144*9a0e4156SSadaf Ebrahimi 	if (status) {
145*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
146*9a0e4156SSadaf Ebrahimi 		uint8_t access;
147*9a0e4156SSadaf Ebrahimi #endif
148*9a0e4156SSadaf Ebrahimi 
149*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_MEM;
150*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = ARM_REG_INVALID;
151*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = ARM_REG_INVALID;
152*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.scale = 1;
153*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = 0;
154*9a0e4156SSadaf Ebrahimi 
155*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
156*9a0e4156SSadaf Ebrahimi 		access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
157*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
158*9a0e4156SSadaf Ebrahimi 		MI->ac_idx++;
159*9a0e4156SSadaf Ebrahimi #endif
160*9a0e4156SSadaf Ebrahimi 	} else {
161*9a0e4156SSadaf Ebrahimi 		// done, create the next operand slot
162*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
163*9a0e4156SSadaf Ebrahimi 	}
164*9a0e4156SSadaf Ebrahimi }
165*9a0e4156SSadaf Ebrahimi 
op_addImm(MCInst * MI,int v)166*9a0e4156SSadaf Ebrahimi static void op_addImm(MCInst *MI, int v)
167*9a0e4156SSadaf Ebrahimi {
168*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
169*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
170*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = v;
171*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
172*9a0e4156SSadaf Ebrahimi 	}
173*9a0e4156SSadaf Ebrahimi }
174*9a0e4156SSadaf Ebrahimi 
175*9a0e4156SSadaf Ebrahimi #define GET_INSTRINFO_ENUM
176*9a0e4156SSadaf Ebrahimi #include "ARMGenInstrInfo.inc"
177*9a0e4156SSadaf Ebrahimi 
178*9a0e4156SSadaf Ebrahimi //#define PRINT_ALIAS_INSTR
179*9a0e4156SSadaf Ebrahimi #include "ARMGenAsmWriter.inc"
180*9a0e4156SSadaf Ebrahimi 
ARM_getRegName(cs_struct * handle,int value)181*9a0e4156SSadaf Ebrahimi void ARM_getRegName(cs_struct *handle, int value)
182*9a0e4156SSadaf Ebrahimi {
183*9a0e4156SSadaf Ebrahimi 	if (value == CS_OPT_SYNTAX_NOREGNAME) {
184*9a0e4156SSadaf Ebrahimi 		handle->get_regname = getRegisterName2;
185*9a0e4156SSadaf Ebrahimi 		handle->reg_name = ARM_reg_name2;;
186*9a0e4156SSadaf Ebrahimi 	} else {
187*9a0e4156SSadaf Ebrahimi 		handle->get_regname = getRegisterName;
188*9a0e4156SSadaf Ebrahimi 		handle->reg_name = ARM_reg_name;;
189*9a0e4156SSadaf Ebrahimi 	}
190*9a0e4156SSadaf Ebrahimi }
191*9a0e4156SSadaf Ebrahimi 
192*9a0e4156SSadaf Ebrahimi /// translateShiftImm - Convert shift immediate from 0-31 to 1-32 for printing.
193*9a0e4156SSadaf Ebrahimi ///
194*9a0e4156SSadaf Ebrahimi /// getSORegOffset returns an integer from 0-31, representing '32' as 0.
translateShiftImm(unsigned imm)195*9a0e4156SSadaf Ebrahimi static unsigned translateShiftImm(unsigned imm)
196*9a0e4156SSadaf Ebrahimi {
197*9a0e4156SSadaf Ebrahimi 	// lsr #32 and asr #32 exist, but should be encoded as a 0.
198*9a0e4156SSadaf Ebrahimi 	//assert((imm & ~0x1f) == 0 && "Invalid shift encoding");
199*9a0e4156SSadaf Ebrahimi 	if (imm == 0)
200*9a0e4156SSadaf Ebrahimi 		return 32;
201*9a0e4156SSadaf Ebrahimi 	return imm;
202*9a0e4156SSadaf Ebrahimi }
203*9a0e4156SSadaf Ebrahimi 
204*9a0e4156SSadaf Ebrahimi /// Prints the shift value with an immediate value.
printRegImmShift(MCInst * MI,SStream * O,ARM_AM_ShiftOpc ShOpc,unsigned ShImm)205*9a0e4156SSadaf Ebrahimi static void printRegImmShift(MCInst *MI, SStream *O, ARM_AM_ShiftOpc ShOpc, unsigned ShImm)
206*9a0e4156SSadaf Ebrahimi {
207*9a0e4156SSadaf Ebrahimi 	if (ShOpc == ARM_AM_no_shift || (ShOpc == ARM_AM_lsl && !ShImm))
208*9a0e4156SSadaf Ebrahimi 		return;
209*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
210*9a0e4156SSadaf Ebrahimi 
211*9a0e4156SSadaf Ebrahimi 	//assert (!(ShOpc == ARM_AM_ror && !ShImm) && "Cannot have ror #0");
212*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARM_AM_getShiftOpcStr(ShOpc));
213*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
214*9a0e4156SSadaf Ebrahimi 		if (MI->csh->doing_mem)
215*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.type = (arm_shifter)ShOpc;
216*9a0e4156SSadaf Ebrahimi 		else
217*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.type = (arm_shifter)ShOpc;
218*9a0e4156SSadaf Ebrahimi 	}
219*9a0e4156SSadaf Ebrahimi 
220*9a0e4156SSadaf Ebrahimi 	if (ShOpc != ARM_AM_rrx) {
221*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, " ");
222*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%u", translateShiftImm(ShImm));
223*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
224*9a0e4156SSadaf Ebrahimi 			if (MI->csh->doing_mem)
225*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.value = translateShiftImm(ShImm);
226*9a0e4156SSadaf Ebrahimi 			else
227*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = translateShiftImm(ShImm);
228*9a0e4156SSadaf Ebrahimi 		}
229*9a0e4156SSadaf Ebrahimi 	}
230*9a0e4156SSadaf Ebrahimi }
231*9a0e4156SSadaf Ebrahimi 
printRegName(cs_struct * h,SStream * OS,unsigned RegNo)232*9a0e4156SSadaf Ebrahimi static void printRegName(cs_struct *h, SStream *OS, unsigned RegNo)
233*9a0e4156SSadaf Ebrahimi {
234*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
235*9a0e4156SSadaf Ebrahimi 	SStream_concat0(OS, h->get_regname(RegNo));
236*9a0e4156SSadaf Ebrahimi #endif
237*9a0e4156SSadaf Ebrahimi }
238*9a0e4156SSadaf Ebrahimi 
239*9a0e4156SSadaf Ebrahimi static const name_map insn_update_flgs[] = {
240*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_CMN, "cmn" },
241*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_CMP, "cmp" },
242*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_TEQ, "teq" },
243*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_TST, "tst" },
244*9a0e4156SSadaf Ebrahimi 
245*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_ADC, "adcs" },
246*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_ADD, "adds" },
247*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_AND, "ands" },
248*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_ASR, "asrs" },
249*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_BIC, "bics" },
250*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_EOR, "eors" },
251*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_LSL, "lsls" },
252*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_LSR, "lsrs" },
253*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_MLA, "mlas" },
254*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_MOV, "movs" },
255*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_MUL, "muls" },
256*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_MVN, "mvns" },
257*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_ORN, "orns" },
258*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_ORR, "orrs" },
259*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_ROR, "rors" },
260*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_RRX, "rrxs" },
261*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_RSB, "rsbs" },
262*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_RSC, "rscs" },
263*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_SBC, "sbcs" },
264*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_SMLAL, "smlals" },
265*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_SMULL, "smulls" },
266*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_SUB, "subs" },
267*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_UMLAL, "umlals" },
268*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_UMULL, "umulls" },
269*9a0e4156SSadaf Ebrahimi 
270*9a0e4156SSadaf Ebrahimi 	{ ARM_INS_UADD8, "uadd8" },
271*9a0e4156SSadaf Ebrahimi };
272*9a0e4156SSadaf Ebrahimi 
ARM_post_printer(csh ud,cs_insn * insn,char * insn_asm,MCInst * mci)273*9a0e4156SSadaf Ebrahimi void ARM_post_printer(csh ud, cs_insn *insn, char *insn_asm, MCInst *mci)
274*9a0e4156SSadaf Ebrahimi {
275*9a0e4156SSadaf Ebrahimi 	if (((cs_struct *)ud)->detail != CS_OPT_ON)
276*9a0e4156SSadaf Ebrahimi 		return;
277*9a0e4156SSadaf Ebrahimi 
278*9a0e4156SSadaf Ebrahimi 	// check if this insn requests write-back
279*9a0e4156SSadaf Ebrahimi 	if (mci->writeback || (strrchr(insn_asm, '!')) != NULL) {
280*9a0e4156SSadaf Ebrahimi 		insn->detail->arm.writeback = true;
281*9a0e4156SSadaf Ebrahimi 	} else if (mci->csh->mode & CS_MODE_THUMB) {
282*9a0e4156SSadaf Ebrahimi 		// handle some special instructions with writeback
283*9a0e4156SSadaf Ebrahimi         //printf(">> Opcode = %u\n", mci->Opcode);
284*9a0e4156SSadaf Ebrahimi 		switch(mci->Opcode) {
285*9a0e4156SSadaf Ebrahimi 			default:
286*9a0e4156SSadaf Ebrahimi 				break;
287*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDC2L_PRE:
288*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDC2_PRE:
289*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDCL_PRE:
290*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDC_PRE:
291*9a0e4156SSadaf Ebrahimi 
292*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRB_PRE:
293*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRD_PRE:
294*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRH_PRE:
295*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRSB_PRE:
296*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRSH_PRE:
297*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDR_PRE:
298*9a0e4156SSadaf Ebrahimi 
299*9a0e4156SSadaf Ebrahimi 			case ARM_t2STC2L_PRE:
300*9a0e4156SSadaf Ebrahimi 			case ARM_t2STC2_PRE:
301*9a0e4156SSadaf Ebrahimi 			case ARM_t2STCL_PRE:
302*9a0e4156SSadaf Ebrahimi 			case ARM_t2STC_PRE:
303*9a0e4156SSadaf Ebrahimi 
304*9a0e4156SSadaf Ebrahimi 			case ARM_t2STRB_PRE:
305*9a0e4156SSadaf Ebrahimi 			case ARM_t2STRD_PRE:
306*9a0e4156SSadaf Ebrahimi 			case ARM_t2STRH_PRE:
307*9a0e4156SSadaf Ebrahimi 			case ARM_t2STR_PRE:
308*9a0e4156SSadaf Ebrahimi 
309*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDC2L_POST:
310*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDC2_POST:
311*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDCL_POST:
312*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDC_POST:
313*9a0e4156SSadaf Ebrahimi 
314*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRB_POST:
315*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRD_POST:
316*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRH_POST:
317*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRSB_POST:
318*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDRSH_POST:
319*9a0e4156SSadaf Ebrahimi 			case ARM_t2LDR_POST:
320*9a0e4156SSadaf Ebrahimi 
321*9a0e4156SSadaf Ebrahimi 			case ARM_t2STC2L_POST:
322*9a0e4156SSadaf Ebrahimi 			case ARM_t2STC2_POST:
323*9a0e4156SSadaf Ebrahimi 			case ARM_t2STCL_POST:
324*9a0e4156SSadaf Ebrahimi 			case ARM_t2STC_POST:
325*9a0e4156SSadaf Ebrahimi 
326*9a0e4156SSadaf Ebrahimi 			case ARM_t2STRB_POST:
327*9a0e4156SSadaf Ebrahimi 			case ARM_t2STRD_POST:
328*9a0e4156SSadaf Ebrahimi 			case ARM_t2STRH_POST:
329*9a0e4156SSadaf Ebrahimi 			case ARM_t2STR_POST:
330*9a0e4156SSadaf Ebrahimi 				insn->detail->arm.writeback = true;
331*9a0e4156SSadaf Ebrahimi 				break;
332*9a0e4156SSadaf Ebrahimi 		}
333*9a0e4156SSadaf Ebrahimi 	} else {	// ARM mode
334*9a0e4156SSadaf Ebrahimi 		// handle some special instructions with writeback
335*9a0e4156SSadaf Ebrahimi         //printf(">> Opcode = %u\n", mci->Opcode);
336*9a0e4156SSadaf Ebrahimi 		switch(mci->Opcode) {
337*9a0e4156SSadaf Ebrahimi 			default:
338*9a0e4156SSadaf Ebrahimi 				break;
339*9a0e4156SSadaf Ebrahimi 			case ARM_LDC2L_PRE:
340*9a0e4156SSadaf Ebrahimi 			case ARM_LDC2_PRE:
341*9a0e4156SSadaf Ebrahimi 			case ARM_LDCL_PRE:
342*9a0e4156SSadaf Ebrahimi 			case ARM_LDC_PRE:
343*9a0e4156SSadaf Ebrahimi 
344*9a0e4156SSadaf Ebrahimi 			case ARM_LDRD_PRE:
345*9a0e4156SSadaf Ebrahimi 			case ARM_LDRH_PRE:
346*9a0e4156SSadaf Ebrahimi 			case ARM_LDRSB_PRE:
347*9a0e4156SSadaf Ebrahimi 			case ARM_LDRSH_PRE:
348*9a0e4156SSadaf Ebrahimi 
349*9a0e4156SSadaf Ebrahimi 			case ARM_STC2L_PRE:
350*9a0e4156SSadaf Ebrahimi 			case ARM_STC2_PRE:
351*9a0e4156SSadaf Ebrahimi 			case ARM_STCL_PRE:
352*9a0e4156SSadaf Ebrahimi 			case ARM_STC_PRE:
353*9a0e4156SSadaf Ebrahimi 
354*9a0e4156SSadaf Ebrahimi 			case ARM_STRD_PRE:
355*9a0e4156SSadaf Ebrahimi 			case ARM_STRH_PRE:
356*9a0e4156SSadaf Ebrahimi 
357*9a0e4156SSadaf Ebrahimi 			case ARM_LDC2L_POST:
358*9a0e4156SSadaf Ebrahimi 			case ARM_LDC2_POST:
359*9a0e4156SSadaf Ebrahimi 			case ARM_LDCL_POST:
360*9a0e4156SSadaf Ebrahimi 			case ARM_LDC_POST:
361*9a0e4156SSadaf Ebrahimi 
362*9a0e4156SSadaf Ebrahimi 			case ARM_LDRBT_POST:
363*9a0e4156SSadaf Ebrahimi 			case ARM_LDRD_POST:
364*9a0e4156SSadaf Ebrahimi 			case ARM_LDRH_POST:
365*9a0e4156SSadaf Ebrahimi 			case ARM_LDRSB_POST:
366*9a0e4156SSadaf Ebrahimi 			case ARM_LDRSH_POST:
367*9a0e4156SSadaf Ebrahimi 
368*9a0e4156SSadaf Ebrahimi 			case ARM_STC2L_POST:
369*9a0e4156SSadaf Ebrahimi 			case ARM_STC2_POST:
370*9a0e4156SSadaf Ebrahimi 			case ARM_STCL_POST:
371*9a0e4156SSadaf Ebrahimi 			case ARM_STC_POST:
372*9a0e4156SSadaf Ebrahimi 
373*9a0e4156SSadaf Ebrahimi 			case ARM_STRBT_POST:
374*9a0e4156SSadaf Ebrahimi 			case ARM_STRD_POST:
375*9a0e4156SSadaf Ebrahimi 			case ARM_STRH_POST:
376*9a0e4156SSadaf Ebrahimi 
377*9a0e4156SSadaf Ebrahimi 			case ARM_LDRB_POST_IMM:
378*9a0e4156SSadaf Ebrahimi 			case ARM_LDR_POST_IMM:
379*9a0e4156SSadaf Ebrahimi 			case ARM_LDR_POST_REG:
380*9a0e4156SSadaf Ebrahimi 			case ARM_STRB_POST_IMM:
381*9a0e4156SSadaf Ebrahimi 
382*9a0e4156SSadaf Ebrahimi 			case ARM_STR_POST_IMM:
383*9a0e4156SSadaf Ebrahimi 			case ARM_STR_POST_REG:
384*9a0e4156SSadaf Ebrahimi 
385*9a0e4156SSadaf Ebrahimi 				insn->detail->arm.writeback = true;
386*9a0e4156SSadaf Ebrahimi 				break;
387*9a0e4156SSadaf Ebrahimi 		}
388*9a0e4156SSadaf Ebrahimi 	}
389*9a0e4156SSadaf Ebrahimi 
390*9a0e4156SSadaf Ebrahimi 	// check if this insn requests update flags
391*9a0e4156SSadaf Ebrahimi 	if (insn->detail->arm.update_flags == false) {
392*9a0e4156SSadaf Ebrahimi 		// some insn still update flags, regardless of tabgen info
393*9a0e4156SSadaf Ebrahimi 		unsigned int i, j;
394*9a0e4156SSadaf Ebrahimi 
395*9a0e4156SSadaf Ebrahimi 		for (i = 0; i < ARR_SIZE(insn_update_flgs); i++) {
396*9a0e4156SSadaf Ebrahimi 			if (insn->id == insn_update_flgs[i].id &&
397*9a0e4156SSadaf Ebrahimi 					!strncmp(insn_asm, insn_update_flgs[i].name,
398*9a0e4156SSadaf Ebrahimi 						strlen(insn_update_flgs[i].name))) {
399*9a0e4156SSadaf Ebrahimi 				insn->detail->arm.update_flags = true;
400*9a0e4156SSadaf Ebrahimi 				// we have to update regs_write array as well
401*9a0e4156SSadaf Ebrahimi 				for (j = 0; j < ARR_SIZE(insn->detail->regs_write); j++) {
402*9a0e4156SSadaf Ebrahimi 					if (insn->detail->regs_write[j] == 0) {
403*9a0e4156SSadaf Ebrahimi 						insn->detail->regs_write[j] = ARM_REG_CPSR;
404*9a0e4156SSadaf Ebrahimi 						break;
405*9a0e4156SSadaf Ebrahimi 					}
406*9a0e4156SSadaf Ebrahimi 				}
407*9a0e4156SSadaf Ebrahimi 				break;
408*9a0e4156SSadaf Ebrahimi 			}
409*9a0e4156SSadaf Ebrahimi 		}
410*9a0e4156SSadaf Ebrahimi 	}
411*9a0e4156SSadaf Ebrahimi 
412*9a0e4156SSadaf Ebrahimi 	// instruction should not have invalid CC
413*9a0e4156SSadaf Ebrahimi 	if (insn->detail->arm.cc == ARM_CC_INVALID) {
414*9a0e4156SSadaf Ebrahimi 		insn->detail->arm.cc = ARM_CC_AL;
415*9a0e4156SSadaf Ebrahimi 	}
416*9a0e4156SSadaf Ebrahimi 
417*9a0e4156SSadaf Ebrahimi 	// manual fix for some special instructions
418*9a0e4156SSadaf Ebrahimi 	// printf(">>> id: %u, mcid: %u\n", insn->id, mci->Opcode);
419*9a0e4156SSadaf Ebrahimi 	switch(mci->Opcode) {
420*9a0e4156SSadaf Ebrahimi 		default:
421*9a0e4156SSadaf Ebrahimi 			break;
422*9a0e4156SSadaf Ebrahimi 		case ARM_MOVPCLR:
423*9a0e4156SSadaf Ebrahimi 			insn->detail->arm.operands[0].type = ARM_OP_REG;
424*9a0e4156SSadaf Ebrahimi 			insn->detail->arm.operands[0].reg = ARM_REG_PC;
425*9a0e4156SSadaf Ebrahimi 			insn->detail->arm.operands[0].access = CS_AC_WRITE;
426*9a0e4156SSadaf Ebrahimi 			insn->detail->arm.operands[1].type = ARM_OP_REG;
427*9a0e4156SSadaf Ebrahimi 			insn->detail->arm.operands[1].reg = ARM_REG_LR;
428*9a0e4156SSadaf Ebrahimi 			insn->detail->arm.operands[1].access = CS_AC_READ;
429*9a0e4156SSadaf Ebrahimi 			insn->detail->arm.op_count = 2;
430*9a0e4156SSadaf Ebrahimi 			break;
431*9a0e4156SSadaf Ebrahimi 	}
432*9a0e4156SSadaf Ebrahimi }
433*9a0e4156SSadaf Ebrahimi 
ARM_printInst(MCInst * MI,SStream * O,void * Info)434*9a0e4156SSadaf Ebrahimi void ARM_printInst(MCInst *MI, SStream *O, void *Info)
435*9a0e4156SSadaf Ebrahimi {
436*9a0e4156SSadaf Ebrahimi 	MCRegisterInfo *MRI = (MCRegisterInfo *)Info;
437*9a0e4156SSadaf Ebrahimi 	unsigned Opcode = MCInst_getOpcode(MI), tmp, i, pubOpcode;
438*9a0e4156SSadaf Ebrahimi 
439*9a0e4156SSadaf Ebrahimi 
440*9a0e4156SSadaf Ebrahimi 	// printf(">>> Opcode 0: %u\n", MCInst_getOpcode(MI));
441*9a0e4156SSadaf Ebrahimi 	switch(Opcode) {
442*9a0e4156SSadaf Ebrahimi 		// Check for HINT instructions w/ canonical names.
443*9a0e4156SSadaf Ebrahimi 		case ARM_HINT:
444*9a0e4156SSadaf Ebrahimi 		case ARM_tHINT:
445*9a0e4156SSadaf Ebrahimi 		case ARM_t2HINT:
446*9a0e4156SSadaf Ebrahimi 			switch (MCOperand_getImm(MCInst_getOperand(MI, 0))) {
447*9a0e4156SSadaf Ebrahimi 				case 0: SStream_concat0(O, "nop"); pubOpcode = ARM_INS_NOP; break;
448*9a0e4156SSadaf Ebrahimi 				case 1: SStream_concat0(O, "yield"); pubOpcode = ARM_INS_YIELD; break;
449*9a0e4156SSadaf Ebrahimi 				case 2: SStream_concat0(O, "wfe"); pubOpcode = ARM_INS_WFE; break;
450*9a0e4156SSadaf Ebrahimi 				case 3: SStream_concat0(O, "wfi"); pubOpcode = ARM_INS_WFI; break;
451*9a0e4156SSadaf Ebrahimi 				case 4: SStream_concat0(O, "sev"); pubOpcode = ARM_INS_SEV; break;
452*9a0e4156SSadaf Ebrahimi 				case 5:
453*9a0e4156SSadaf Ebrahimi 						if ((ARM_getFeatureBits(MI->csh->mode) & ARM_HasV8Ops)) {
454*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "sevl");
455*9a0e4156SSadaf Ebrahimi 							pubOpcode = ARM_INS_SEVL;
456*9a0e4156SSadaf Ebrahimi 							break;
457*9a0e4156SSadaf Ebrahimi 						}
458*9a0e4156SSadaf Ebrahimi 						// Fallthrough for non-v8
459*9a0e4156SSadaf Ebrahimi 				default:
460*9a0e4156SSadaf Ebrahimi 						// Anything else should just print normally.
461*9a0e4156SSadaf Ebrahimi 						printInstruction(MI, O, MRI);
462*9a0e4156SSadaf Ebrahimi 						return;
463*9a0e4156SSadaf Ebrahimi 			}
464*9a0e4156SSadaf Ebrahimi 			printPredicateOperand(MI, 1, O);
465*9a0e4156SSadaf Ebrahimi 			if (Opcode == ARM_t2HINT)
466*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, ".w");
467*9a0e4156SSadaf Ebrahimi 
468*9a0e4156SSadaf Ebrahimi 			MCInst_setOpcodePub(MI, pubOpcode);
469*9a0e4156SSadaf Ebrahimi 
470*9a0e4156SSadaf Ebrahimi 			return;
471*9a0e4156SSadaf Ebrahimi 
472*9a0e4156SSadaf Ebrahimi 			// Check for MOVs and print canonical forms, instead.
473*9a0e4156SSadaf Ebrahimi 		case ARM_MOVsr: {
474*9a0e4156SSadaf Ebrahimi 							// FIXME: Thumb variants?
475*9a0e4156SSadaf Ebrahimi 							unsigned int opc;
476*9a0e4156SSadaf Ebrahimi 							MCOperand *Dst = MCInst_getOperand(MI, 0);
477*9a0e4156SSadaf Ebrahimi 							MCOperand *MO1 = MCInst_getOperand(MI, 1);
478*9a0e4156SSadaf Ebrahimi 							MCOperand *MO2 = MCInst_getOperand(MI, 2);
479*9a0e4156SSadaf Ebrahimi 							MCOperand *MO3 = MCInst_getOperand(MI, 3);
480*9a0e4156SSadaf Ebrahimi 
481*9a0e4156SSadaf Ebrahimi 							opc = ARM_AM_getSORegShOp((unsigned int)MCOperand_getImm(MO3));
482*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, ARM_AM_getShiftOpcStr(opc));
483*9a0e4156SSadaf Ebrahimi 							switch(opc) {
484*9a0e4156SSadaf Ebrahimi 								default:
485*9a0e4156SSadaf Ebrahimi 									break;
486*9a0e4156SSadaf Ebrahimi 								case ARM_AM_asr:
487*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_ASR);
488*9a0e4156SSadaf Ebrahimi 									break;
489*9a0e4156SSadaf Ebrahimi 								case ARM_AM_lsl:
490*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_LSL);
491*9a0e4156SSadaf Ebrahimi 									break;
492*9a0e4156SSadaf Ebrahimi 								case ARM_AM_lsr:
493*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_LSR);
494*9a0e4156SSadaf Ebrahimi 									break;
495*9a0e4156SSadaf Ebrahimi 								case ARM_AM_ror:
496*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_ROR);
497*9a0e4156SSadaf Ebrahimi 									break;
498*9a0e4156SSadaf Ebrahimi 								case ARM_AM_rrx:
499*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_RRX);
500*9a0e4156SSadaf Ebrahimi 									break;
501*9a0e4156SSadaf Ebrahimi 							}
502*9a0e4156SSadaf Ebrahimi 							printSBitModifierOperand(MI, 6, O);
503*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 4, O);
504*9a0e4156SSadaf Ebrahimi 
505*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "\t");
506*9a0e4156SSadaf Ebrahimi 							printRegName(MI->csh, O, MCOperand_getReg(Dst));
507*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
508*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
509*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(Dst);
510*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_WRITE;
511*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.op_count++;
512*9a0e4156SSadaf Ebrahimi 							}
513*9a0e4156SSadaf Ebrahimi 
514*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, ", ");
515*9a0e4156SSadaf Ebrahimi 							printRegName(MI->csh, O, MCOperand_getReg(MO1));
516*9a0e4156SSadaf Ebrahimi 
517*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
518*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
519*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO1);
520*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
521*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.op_count++;
522*9a0e4156SSadaf Ebrahimi 							}
523*9a0e4156SSadaf Ebrahimi 
524*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, ", ");
525*9a0e4156SSadaf Ebrahimi 							printRegName(MI->csh, O, MCOperand_getReg(MO2));
526*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
527*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
528*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO2);
529*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
530*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.op_count++;
531*9a0e4156SSadaf Ebrahimi 							}
532*9a0e4156SSadaf Ebrahimi 							//assert(ARM_AM_getSORegOffset(MO3.getImm()) == 0);
533*9a0e4156SSadaf Ebrahimi 							return;
534*9a0e4156SSadaf Ebrahimi 						}
535*9a0e4156SSadaf Ebrahimi 
536*9a0e4156SSadaf Ebrahimi 		case ARM_MOVsi: {
537*9a0e4156SSadaf Ebrahimi 							// FIXME: Thumb variants?
538*9a0e4156SSadaf Ebrahimi 							unsigned int opc;
539*9a0e4156SSadaf Ebrahimi 							MCOperand *Dst = MCInst_getOperand(MI, 0);
540*9a0e4156SSadaf Ebrahimi 							MCOperand *MO1 = MCInst_getOperand(MI, 1);
541*9a0e4156SSadaf Ebrahimi 							MCOperand *MO2 = MCInst_getOperand(MI, 2);
542*9a0e4156SSadaf Ebrahimi 
543*9a0e4156SSadaf Ebrahimi 							opc = ARM_AM_getSORegShOp((unsigned int)MCOperand_getImm(MO2));
544*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, ARM_AM_getShiftOpcStr(opc));
545*9a0e4156SSadaf Ebrahimi 							switch(opc) {
546*9a0e4156SSadaf Ebrahimi 								default:
547*9a0e4156SSadaf Ebrahimi 									break;
548*9a0e4156SSadaf Ebrahimi 								case ARM_AM_asr:
549*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_ASR);
550*9a0e4156SSadaf Ebrahimi 									break;
551*9a0e4156SSadaf Ebrahimi 								case ARM_AM_lsl:
552*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_LSL);
553*9a0e4156SSadaf Ebrahimi 									break;
554*9a0e4156SSadaf Ebrahimi 								case ARM_AM_lsr:
555*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_LSR);
556*9a0e4156SSadaf Ebrahimi 									break;
557*9a0e4156SSadaf Ebrahimi 								case ARM_AM_ror:
558*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_ROR);
559*9a0e4156SSadaf Ebrahimi 									break;
560*9a0e4156SSadaf Ebrahimi 								case ARM_AM_rrx:
561*9a0e4156SSadaf Ebrahimi 									MCInst_setOpcodePub(MI, ARM_INS_RRX);
562*9a0e4156SSadaf Ebrahimi 									break;
563*9a0e4156SSadaf Ebrahimi 							}
564*9a0e4156SSadaf Ebrahimi 							printSBitModifierOperand(MI, 5, O);
565*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 3, O);
566*9a0e4156SSadaf Ebrahimi 
567*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "\t");
568*9a0e4156SSadaf Ebrahimi 							printRegName(MI->csh, O, MCOperand_getReg(Dst));
569*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
570*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
571*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(Dst);
572*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_WRITE;
573*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.op_count++;
574*9a0e4156SSadaf Ebrahimi 							}
575*9a0e4156SSadaf Ebrahimi 
576*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, ", ");
577*9a0e4156SSadaf Ebrahimi 							printRegName(MI->csh, O, MCOperand_getReg(MO1));
578*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
579*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
580*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO1);
581*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
582*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.op_count++;
583*9a0e4156SSadaf Ebrahimi 							}
584*9a0e4156SSadaf Ebrahimi 
585*9a0e4156SSadaf Ebrahimi 							if (opc == ARM_AM_rrx) {
586*9a0e4156SSadaf Ebrahimi 								//printAnnotation(O, Annot);
587*9a0e4156SSadaf Ebrahimi 								return;
588*9a0e4156SSadaf Ebrahimi 							}
589*9a0e4156SSadaf Ebrahimi 
590*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, ", ");
591*9a0e4156SSadaf Ebrahimi 							tmp = translateShiftImm(getSORegOffset((unsigned int)MCOperand_getImm(MO2)));
592*9a0e4156SSadaf Ebrahimi 							printUInt32Bang(O, tmp);
593*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
594*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.type =
595*9a0e4156SSadaf Ebrahimi 									(arm_shifter)opc;
596*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = tmp;
597*9a0e4156SSadaf Ebrahimi 							}
598*9a0e4156SSadaf Ebrahimi 							return;
599*9a0e4156SSadaf Ebrahimi 						}
600*9a0e4156SSadaf Ebrahimi 
601*9a0e4156SSadaf Ebrahimi 						// A8.6.123 PUSH
602*9a0e4156SSadaf Ebrahimi 		case ARM_STMDB_UPD:
603*9a0e4156SSadaf Ebrahimi 		case ARM_t2STMDB_UPD:
604*9a0e4156SSadaf Ebrahimi 						if (MCOperand_getReg(MCInst_getOperand(MI, 0)) == ARM_SP &&
605*9a0e4156SSadaf Ebrahimi 								MCInst_getNumOperands(MI) > 5) {
606*9a0e4156SSadaf Ebrahimi 							// Should only print PUSH if there are at least two registers in the list.
607*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "push");
608*9a0e4156SSadaf Ebrahimi 							MCInst_setOpcodePub(MI, ARM_INS_PUSH);
609*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 2, O);
610*9a0e4156SSadaf Ebrahimi 							if (Opcode == ARM_t2STMDB_UPD)
611*9a0e4156SSadaf Ebrahimi 								SStream_concat0(O, ".w");
612*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "\t");
613*9a0e4156SSadaf Ebrahimi 
614*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
615*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_read[MI->flat_insn->detail->regs_read_count] = ARM_REG_SP;
616*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_read_count++;
617*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_write[MI->flat_insn->detail->regs_write_count] = ARM_REG_SP;
618*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_write_count++;
619*9a0e4156SSadaf Ebrahimi 							}
620*9a0e4156SSadaf Ebrahimi 
621*9a0e4156SSadaf Ebrahimi 							printRegisterList(MI, 4, O);
622*9a0e4156SSadaf Ebrahimi 							return;
623*9a0e4156SSadaf Ebrahimi 						}
624*9a0e4156SSadaf Ebrahimi 						break;
625*9a0e4156SSadaf Ebrahimi 
626*9a0e4156SSadaf Ebrahimi 		case ARM_STR_PRE_IMM:
627*9a0e4156SSadaf Ebrahimi 						if (MCOperand_getReg(MCInst_getOperand(MI, 2)) == ARM_SP &&
628*9a0e4156SSadaf Ebrahimi 								MCOperand_getImm(MCInst_getOperand(MI, 3)) == -4) {
629*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "push");
630*9a0e4156SSadaf Ebrahimi 							MCInst_setOpcodePub(MI, ARM_INS_PUSH);
631*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 4, O);
632*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "\t{");
633*9a0e4156SSadaf Ebrahimi 							printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, 1)));
634*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
635*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
636*9a0e4156SSadaf Ebrahimi 								uint8_t access;
637*9a0e4156SSadaf Ebrahimi #endif
638*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
639*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, 1));
640*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
641*9a0e4156SSadaf Ebrahimi 								access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
642*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
643*9a0e4156SSadaf Ebrahimi 								MI->ac_idx++;
644*9a0e4156SSadaf Ebrahimi #endif
645*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->arm.op_count++;
646*9a0e4156SSadaf Ebrahimi 							}
647*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "}");
648*9a0e4156SSadaf Ebrahimi 							return;
649*9a0e4156SSadaf Ebrahimi 						}
650*9a0e4156SSadaf Ebrahimi 						break;
651*9a0e4156SSadaf Ebrahimi 
652*9a0e4156SSadaf Ebrahimi 						// A8.6.122 POP
653*9a0e4156SSadaf Ebrahimi 		case ARM_LDMIA_UPD:
654*9a0e4156SSadaf Ebrahimi 		case ARM_t2LDMIA_UPD:
655*9a0e4156SSadaf Ebrahimi 						if (MCOperand_getReg(MCInst_getOperand(MI, 0)) == ARM_SP &&
656*9a0e4156SSadaf Ebrahimi 								MCInst_getNumOperands(MI) > 5) {
657*9a0e4156SSadaf Ebrahimi 							// Should only print POP if there are at least two registers in the list.
658*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "pop");
659*9a0e4156SSadaf Ebrahimi 							MCInst_setOpcodePub(MI, ARM_INS_POP);
660*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 2, O);
661*9a0e4156SSadaf Ebrahimi 							if (Opcode == ARM_t2LDMIA_UPD)
662*9a0e4156SSadaf Ebrahimi 								SStream_concat0(O, ".w");
663*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "\t");
664*9a0e4156SSadaf Ebrahimi 							// unlike LDM, POP only write to registers, so skip the 1st access code
665*9a0e4156SSadaf Ebrahimi 							MI->ac_idx = 1;
666*9a0e4156SSadaf Ebrahimi 							if (MI->csh->detail) {
667*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_read[MI->flat_insn->detail->regs_read_count] = ARM_REG_SP;
668*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_read_count++;
669*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_write[MI->flat_insn->detail->regs_write_count] = ARM_REG_SP;
670*9a0e4156SSadaf Ebrahimi 								MI->flat_insn->detail->regs_write_count++;
671*9a0e4156SSadaf Ebrahimi 							}
672*9a0e4156SSadaf Ebrahimi 
673*9a0e4156SSadaf Ebrahimi 							printRegisterList(MI, 4, O);
674*9a0e4156SSadaf Ebrahimi 							return;
675*9a0e4156SSadaf Ebrahimi 						}
676*9a0e4156SSadaf Ebrahimi 						break;
677*9a0e4156SSadaf Ebrahimi 
678*9a0e4156SSadaf Ebrahimi 		case ARM_LDR_POST_IMM:
679*9a0e4156SSadaf Ebrahimi 						if (MCOperand_getReg(MCInst_getOperand(MI, 2)) == ARM_SP) {
680*9a0e4156SSadaf Ebrahimi 							MCOperand *MO2 = MCInst_getOperand(MI, 4);
681*9a0e4156SSadaf Ebrahimi 							if ((getAM2Op((unsigned int)MCOperand_getImm(MO2)) == ARM_AM_add &&
682*9a0e4156SSadaf Ebrahimi 										getAM2Offset((unsigned int)MCOperand_getImm(MO2)) == 4) ||
683*9a0e4156SSadaf Ebrahimi 									MCOperand_getImm(MO2) == 4) {
684*9a0e4156SSadaf Ebrahimi 								SStream_concat0(O, "pop");
685*9a0e4156SSadaf Ebrahimi 								MCInst_setOpcodePub(MI, ARM_INS_POP);
686*9a0e4156SSadaf Ebrahimi 								printPredicateOperand(MI, 5, O);
687*9a0e4156SSadaf Ebrahimi 								SStream_concat0(O, "\t{");
688*9a0e4156SSadaf Ebrahimi 								printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, 0)));
689*9a0e4156SSadaf Ebrahimi 								if (MI->csh->detail) {
690*9a0e4156SSadaf Ebrahimi 									MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
691*9a0e4156SSadaf Ebrahimi 									MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, 0));
692*9a0e4156SSadaf Ebrahimi 									MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_WRITE;
693*9a0e4156SSadaf Ebrahimi 									MI->flat_insn->detail->arm.op_count++;
694*9a0e4156SSadaf Ebrahimi                                     // this instruction implicitly read/write SP register
695*9a0e4156SSadaf Ebrahimi                                     MI->flat_insn->detail->regs_read[MI->flat_insn->detail->regs_read_count] = ARM_REG_SP;
696*9a0e4156SSadaf Ebrahimi                                     MI->flat_insn->detail->regs_read_count++;
697*9a0e4156SSadaf Ebrahimi                                     MI->flat_insn->detail->regs_write[MI->flat_insn->detail->regs_write_count] = ARM_REG_SP;
698*9a0e4156SSadaf Ebrahimi                                     MI->flat_insn->detail->regs_write_count++;
699*9a0e4156SSadaf Ebrahimi 								}
700*9a0e4156SSadaf Ebrahimi 								SStream_concat0(O, "}");
701*9a0e4156SSadaf Ebrahimi 								return;
702*9a0e4156SSadaf Ebrahimi 							}
703*9a0e4156SSadaf Ebrahimi 						}
704*9a0e4156SSadaf Ebrahimi 						break;
705*9a0e4156SSadaf Ebrahimi 
706*9a0e4156SSadaf Ebrahimi 						// A8.6.355 VPUSH
707*9a0e4156SSadaf Ebrahimi 		case ARM_VSTMSDB_UPD:
708*9a0e4156SSadaf Ebrahimi 		case ARM_VSTMDDB_UPD:
709*9a0e4156SSadaf Ebrahimi 						if (MCOperand_getReg(MCInst_getOperand(MI, 0)) == ARM_SP) {
710*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "vpush");
711*9a0e4156SSadaf Ebrahimi 							MCInst_setOpcodePub(MI, ARM_INS_VPUSH);
712*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 2, O);
713*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "\t");
714*9a0e4156SSadaf Ebrahimi 							printRegisterList(MI, 4, O);
715*9a0e4156SSadaf Ebrahimi 							return;
716*9a0e4156SSadaf Ebrahimi 						}
717*9a0e4156SSadaf Ebrahimi 						break;
718*9a0e4156SSadaf Ebrahimi 
719*9a0e4156SSadaf Ebrahimi 						// A8.6.354 VPOP
720*9a0e4156SSadaf Ebrahimi 		case ARM_VLDMSIA_UPD:
721*9a0e4156SSadaf Ebrahimi 		case ARM_VLDMDIA_UPD:
722*9a0e4156SSadaf Ebrahimi 						if (MCOperand_getReg(MCInst_getOperand(MI, 0)) == ARM_SP) {
723*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "vpop");
724*9a0e4156SSadaf Ebrahimi 							MCInst_setOpcodePub(MI, ARM_INS_VPOP);
725*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 2, O);
726*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "\t");
727*9a0e4156SSadaf Ebrahimi 							printRegisterList(MI, 4, O);
728*9a0e4156SSadaf Ebrahimi 							return;
729*9a0e4156SSadaf Ebrahimi 						}
730*9a0e4156SSadaf Ebrahimi 						break;
731*9a0e4156SSadaf Ebrahimi 
732*9a0e4156SSadaf Ebrahimi 		case ARM_tLDMIA: {
733*9a0e4156SSadaf Ebrahimi 							 bool Writeback = true;
734*9a0e4156SSadaf Ebrahimi 							 unsigned BaseReg = MCOperand_getReg(MCInst_getOperand(MI, 0));
735*9a0e4156SSadaf Ebrahimi 							 unsigned i;
736*9a0e4156SSadaf Ebrahimi 							 for (i = 3; i < MCInst_getNumOperands(MI); ++i) {
737*9a0e4156SSadaf Ebrahimi 								 if (MCOperand_getReg(MCInst_getOperand(MI, i)) == BaseReg)
738*9a0e4156SSadaf Ebrahimi 									 Writeback = false;
739*9a0e4156SSadaf Ebrahimi 							 }
740*9a0e4156SSadaf Ebrahimi 
741*9a0e4156SSadaf Ebrahimi 							 SStream_concat0(O, "ldm");
742*9a0e4156SSadaf Ebrahimi 							 MCInst_setOpcodePub(MI, ARM_INS_LDM);
743*9a0e4156SSadaf Ebrahimi 
744*9a0e4156SSadaf Ebrahimi 							 printPredicateOperand(MI, 1, O);
745*9a0e4156SSadaf Ebrahimi 							 SStream_concat0(O, "\t");
746*9a0e4156SSadaf Ebrahimi 							 printRegName(MI->csh, O, BaseReg);
747*9a0e4156SSadaf Ebrahimi 							 if (MI->csh->detail) {
748*9a0e4156SSadaf Ebrahimi 								 MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
749*9a0e4156SSadaf Ebrahimi 								 MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = BaseReg;
750*9a0e4156SSadaf Ebrahimi 								 MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ | CS_AC_WRITE;
751*9a0e4156SSadaf Ebrahimi 								 MI->flat_insn->detail->arm.op_count++;
752*9a0e4156SSadaf Ebrahimi 							 }
753*9a0e4156SSadaf Ebrahimi 							 if (Writeback) {
754*9a0e4156SSadaf Ebrahimi 								 MI->writeback = true;
755*9a0e4156SSadaf Ebrahimi 								 SStream_concat0(O, "!");
756*9a0e4156SSadaf Ebrahimi 							 }
757*9a0e4156SSadaf Ebrahimi 							 SStream_concat0(O, ", ");
758*9a0e4156SSadaf Ebrahimi 							 printRegisterList(MI, 3, O);
759*9a0e4156SSadaf Ebrahimi 							 return;
760*9a0e4156SSadaf Ebrahimi 						 }
761*9a0e4156SSadaf Ebrahimi 
762*9a0e4156SSadaf Ebrahimi 						 // Combine 2 GPRs from disassember into a GPRPair to match with instr def.
763*9a0e4156SSadaf Ebrahimi 						 // ldrexd/strexd require even/odd GPR pair. To enforce this constraint,
764*9a0e4156SSadaf Ebrahimi 						 // a single GPRPair reg operand is used in the .td file to replace the two
765*9a0e4156SSadaf Ebrahimi 						 // GPRs. However, when decoding them, the two GRPs cannot be automatically
766*9a0e4156SSadaf Ebrahimi 						 // expressed as a GPRPair, so we have to manually merge them.
767*9a0e4156SSadaf Ebrahimi 						 // FIXME: We would really like to be able to tablegen'erate this.
768*9a0e4156SSadaf Ebrahimi 		case ARM_LDREXD:
769*9a0e4156SSadaf Ebrahimi 		case ARM_STREXD:
770*9a0e4156SSadaf Ebrahimi 		case ARM_LDAEXD:
771*9a0e4156SSadaf Ebrahimi 		case ARM_STLEXD: {
772*9a0e4156SSadaf Ebrahimi 				const MCRegisterClass* MRC = MCRegisterInfo_getRegClass(MRI, ARM_GPRRegClassID);
773*9a0e4156SSadaf Ebrahimi 				bool isStore = Opcode == ARM_STREXD || Opcode == ARM_STLEXD;
774*9a0e4156SSadaf Ebrahimi 				unsigned Reg = MCOperand_getReg(MCInst_getOperand(MI, isStore ? 1 : 0));
775*9a0e4156SSadaf Ebrahimi 
776*9a0e4156SSadaf Ebrahimi 				if (MCRegisterClass_contains(MRC, Reg)) {
777*9a0e4156SSadaf Ebrahimi 				    MCInst NewMI;
778*9a0e4156SSadaf Ebrahimi 
779*9a0e4156SSadaf Ebrahimi 				    MCInst_Init(&NewMI);
780*9a0e4156SSadaf Ebrahimi 				    MCInst_setOpcode(&NewMI, Opcode);
781*9a0e4156SSadaf Ebrahimi 
782*9a0e4156SSadaf Ebrahimi 				    if (isStore)
783*9a0e4156SSadaf Ebrahimi 						MCInst_addOperand2(&NewMI, MCInst_getOperand(MI, 0));
784*9a0e4156SSadaf Ebrahimi 
785*9a0e4156SSadaf Ebrahimi 				    MCOperand_CreateReg0(&NewMI, MCRegisterInfo_getMatchingSuperReg(MRI, Reg, ARM_gsub_0,
786*9a0e4156SSadaf Ebrahimi 								MCRegisterInfo_getRegClass(MRI, ARM_GPRPairRegClassID)));
787*9a0e4156SSadaf Ebrahimi 
788*9a0e4156SSadaf Ebrahimi 				    // Copy the rest operands into NewMI.
789*9a0e4156SSadaf Ebrahimi 				    for(i = isStore ? 3 : 2; i < MCInst_getNumOperands(MI); ++i)
790*9a0e4156SSadaf Ebrahimi 						MCInst_addOperand2(&NewMI, MCInst_getOperand(MI, i));
791*9a0e4156SSadaf Ebrahimi 
792*9a0e4156SSadaf Ebrahimi 				    printInstruction(&NewMI, O, MRI);
793*9a0e4156SSadaf Ebrahimi 				    return;
794*9a0e4156SSadaf Ebrahimi 				}
795*9a0e4156SSadaf Ebrahimi 				break;
796*9a0e4156SSadaf Ebrahimi 		 }
797*9a0e4156SSadaf Ebrahimi 		 // B9.3.3 ERET (Thumb)
798*9a0e4156SSadaf Ebrahimi 		 // For a target that has Virtualization Extensions, ERET is the preferred
799*9a0e4156SSadaf Ebrahimi 		 // disassembly of SUBS PC, LR, #0
800*9a0e4156SSadaf Ebrahimi 		case ARM_t2SUBS_PC_LR: {
801*9a0e4156SSadaf Ebrahimi 						MCOperand *opc = MCInst_getOperand(MI, 0);
802*9a0e4156SSadaf Ebrahimi 						if (MCInst_getNumOperands(MI) == 3 &&
803*9a0e4156SSadaf Ebrahimi 							MCOperand_isImm(opc) &&
804*9a0e4156SSadaf Ebrahimi 							MCOperand_getImm(opc) == 0 &&
805*9a0e4156SSadaf Ebrahimi 							(ARM_getFeatureBits(MI->csh->mode) & ARM_FeatureVirtualization)) {
806*9a0e4156SSadaf Ebrahimi 							SStream_concat0(O, "eret");
807*9a0e4156SSadaf Ebrahimi 							MCInst_setOpcodePub(MI, ARM_INS_ERET);
808*9a0e4156SSadaf Ebrahimi 							printPredicateOperand(MI, 1, O);
809*9a0e4156SSadaf Ebrahimi 							return;
810*9a0e4156SSadaf Ebrahimi 						}
811*9a0e4156SSadaf Ebrahimi 						break;
812*9a0e4156SSadaf Ebrahimi 				}
813*9a0e4156SSadaf Ebrahimi 	}
814*9a0e4156SSadaf Ebrahimi 
815*9a0e4156SSadaf Ebrahimi 	//if (printAliasInstr(MI, O, MRI))
816*9a0e4156SSadaf Ebrahimi 	//	printInstruction(MI, O, MRI);
817*9a0e4156SSadaf Ebrahimi 	printInstruction(MI, O, MRI);
818*9a0e4156SSadaf Ebrahimi }
819*9a0e4156SSadaf Ebrahimi 
printOperand(MCInst * MI,unsigned OpNo,SStream * O)820*9a0e4156SSadaf Ebrahimi static void printOperand(MCInst *MI, unsigned OpNo, SStream *O)
821*9a0e4156SSadaf Ebrahimi {
822*9a0e4156SSadaf Ebrahimi 	int32_t imm;
823*9a0e4156SSadaf Ebrahimi 	MCOperand *Op = MCInst_getOperand(MI, OpNo);
824*9a0e4156SSadaf Ebrahimi 	if (MCOperand_isReg(Op)) {
825*9a0e4156SSadaf Ebrahimi 		unsigned Reg = MCOperand_getReg(Op);
826*9a0e4156SSadaf Ebrahimi 		printRegName(MI->csh, O, Reg);
827*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
828*9a0e4156SSadaf Ebrahimi 			if (MI->csh->doing_mem) {
829*9a0e4156SSadaf Ebrahimi 				if (MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base == ARM_REG_INVALID)
830*9a0e4156SSadaf Ebrahimi 					MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = Reg;
831*9a0e4156SSadaf Ebrahimi 				else
832*9a0e4156SSadaf Ebrahimi 					MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = Reg;
833*9a0e4156SSadaf Ebrahimi 			} else {
834*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
835*9a0e4156SSadaf Ebrahimi 				uint8_t access;
836*9a0e4156SSadaf Ebrahimi #endif
837*9a0e4156SSadaf Ebrahimi 
838*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
839*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg;
840*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
841*9a0e4156SSadaf Ebrahimi 				access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
842*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
843*9a0e4156SSadaf Ebrahimi 				MI->ac_idx++;
844*9a0e4156SSadaf Ebrahimi #endif
845*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.op_count++;
846*9a0e4156SSadaf Ebrahimi 			}
847*9a0e4156SSadaf Ebrahimi 		}
848*9a0e4156SSadaf Ebrahimi 	} else if (MCOperand_isImm(Op)) {
849*9a0e4156SSadaf Ebrahimi 		unsigned int opc = MCInst_getOpcode(MI);
850*9a0e4156SSadaf Ebrahimi 
851*9a0e4156SSadaf Ebrahimi 		imm = (int32_t)MCOperand_getImm(Op);
852*9a0e4156SSadaf Ebrahimi 
853*9a0e4156SSadaf Ebrahimi 		// relative branch only has relative offset, so we have to update it
854*9a0e4156SSadaf Ebrahimi 		// to reflect absolute address.
855*9a0e4156SSadaf Ebrahimi 		// Note: in ARM, PC is always 2 instructions ahead, so we have to
856*9a0e4156SSadaf Ebrahimi 		// add 8 in ARM mode, or 4 in Thumb mode
857*9a0e4156SSadaf Ebrahimi 		// printf(">> opcode: %u\n", MCInst_getOpcode(MI));
858*9a0e4156SSadaf Ebrahimi 		if (ARM_rel_branch(MI->csh, opc)) {
859*9a0e4156SSadaf Ebrahimi 			uint32_t address;
860*9a0e4156SSadaf Ebrahimi 
861*9a0e4156SSadaf Ebrahimi 			// only do this for relative branch
862*9a0e4156SSadaf Ebrahimi 			if (MI->csh->mode & CS_MODE_THUMB) {
863*9a0e4156SSadaf Ebrahimi 				address = (uint32_t)MI->address + 4;
864*9a0e4156SSadaf Ebrahimi 				if (ARM_blx_to_arm_mode(MI->csh, opc)) {
865*9a0e4156SSadaf Ebrahimi 					// here need to align down to the nearest 4-byte address
866*9a0e4156SSadaf Ebrahimi #define _ALIGN_DOWN(v, align_width) ((v/align_width)*align_width)
867*9a0e4156SSadaf Ebrahimi 					address = _ALIGN_DOWN(address, 4);
868*9a0e4156SSadaf Ebrahimi #undef _ALIGN_DOWN
869*9a0e4156SSadaf Ebrahimi 				}
870*9a0e4156SSadaf Ebrahimi 			} else {
871*9a0e4156SSadaf Ebrahimi 				address = (uint32_t)MI->address + 8;
872*9a0e4156SSadaf Ebrahimi 			}
873*9a0e4156SSadaf Ebrahimi 
874*9a0e4156SSadaf Ebrahimi 			imm += address;
875*9a0e4156SSadaf Ebrahimi 			printUInt32Bang(O, imm);
876*9a0e4156SSadaf Ebrahimi 		} else {
877*9a0e4156SSadaf Ebrahimi 			switch(MI->flat_insn->id) {
878*9a0e4156SSadaf Ebrahimi 				default:
879*9a0e4156SSadaf Ebrahimi 					if (MI->csh->imm_unsigned)
880*9a0e4156SSadaf Ebrahimi 						printUInt32Bang(O, imm);
881*9a0e4156SSadaf Ebrahimi 					else
882*9a0e4156SSadaf Ebrahimi 						printInt32Bang(O, imm);
883*9a0e4156SSadaf Ebrahimi 					break;
884*9a0e4156SSadaf Ebrahimi 				case ARM_INS_AND:
885*9a0e4156SSadaf Ebrahimi 				case ARM_INS_ORR:
886*9a0e4156SSadaf Ebrahimi 				case ARM_INS_EOR:
887*9a0e4156SSadaf Ebrahimi 				case ARM_INS_BIC:
888*9a0e4156SSadaf Ebrahimi 				case ARM_INS_MVN:
889*9a0e4156SSadaf Ebrahimi 					// do not print number in negative form
890*9a0e4156SSadaf Ebrahimi 					printUInt32Bang(O, imm);
891*9a0e4156SSadaf Ebrahimi 					break;
892*9a0e4156SSadaf Ebrahimi 			}
893*9a0e4156SSadaf Ebrahimi 		}
894*9a0e4156SSadaf Ebrahimi 
895*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
896*9a0e4156SSadaf Ebrahimi 			if (MI->csh->doing_mem)
897*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = imm;
898*9a0e4156SSadaf Ebrahimi 			else {
899*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
900*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = imm;
901*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.op_count++;
902*9a0e4156SSadaf Ebrahimi 			}
903*9a0e4156SSadaf Ebrahimi 		}
904*9a0e4156SSadaf Ebrahimi 	}
905*9a0e4156SSadaf Ebrahimi }
906*9a0e4156SSadaf Ebrahimi 
printThumbLdrLabelOperand(MCInst * MI,unsigned OpNum,SStream * O)907*9a0e4156SSadaf Ebrahimi static void printThumbLdrLabelOperand(MCInst *MI, unsigned OpNum, SStream *O)
908*9a0e4156SSadaf Ebrahimi {
909*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
910*9a0e4156SSadaf Ebrahimi 	int32_t OffImm;
911*9a0e4156SSadaf Ebrahimi 	bool isSub;
912*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[pc, ");
913*9a0e4156SSadaf Ebrahimi 
914*9a0e4156SSadaf Ebrahimi 	OffImm = (int32_t)MCOperand_getImm(MO1);
915*9a0e4156SSadaf Ebrahimi 	isSub = OffImm < 0;
916*9a0e4156SSadaf Ebrahimi 
917*9a0e4156SSadaf Ebrahimi 	// Special value for #-0. All others are normal.
918*9a0e4156SSadaf Ebrahimi 	if (OffImm == INT32_MIN)
919*9a0e4156SSadaf Ebrahimi 		OffImm = 0;
920*9a0e4156SSadaf Ebrahimi 	if (isSub) {
921*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#-0x%x", -OffImm);
922*9a0e4156SSadaf Ebrahimi 	} else {
923*9a0e4156SSadaf Ebrahimi 		printUInt32Bang(O, OffImm);
924*9a0e4156SSadaf Ebrahimi 	}
925*9a0e4156SSadaf Ebrahimi 
926*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
927*9a0e4156SSadaf Ebrahimi 
928*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
929*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_MEM;
930*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = ARM_REG_PC;
931*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = ARM_REG_INVALID;
932*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.scale = 1;
933*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = OffImm;
934*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
935*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
936*9a0e4156SSadaf Ebrahimi 	}
937*9a0e4156SSadaf Ebrahimi }
938*9a0e4156SSadaf Ebrahimi 
939*9a0e4156SSadaf Ebrahimi // so_reg is a 4-operand unit corresponding to register forms of the A5.1
940*9a0e4156SSadaf Ebrahimi // "Addressing Mode 1 - Data-processing operands" forms.  This includes:
941*9a0e4156SSadaf Ebrahimi //    REG 0   0           - e.g. R5
942*9a0e4156SSadaf Ebrahimi //    REG REG 0,SH_OPC    - e.g. R5, ROR R3
943*9a0e4156SSadaf Ebrahimi //    REG 0   IMM,SH_OPC  - e.g. R5, LSL #3
printSORegRegOperand(MCInst * MI,unsigned OpNum,SStream * O)944*9a0e4156SSadaf Ebrahimi static void printSORegRegOperand(MCInst *MI, unsigned OpNum, SStream *O)
945*9a0e4156SSadaf Ebrahimi {
946*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
947*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
948*9a0e4156SSadaf Ebrahimi 	MCOperand *MO3 = MCInst_getOperand(MI, OpNum+2);
949*9a0e4156SSadaf Ebrahimi 	ARM_AM_ShiftOpc ShOpc;
950*9a0e4156SSadaf Ebrahimi 
951*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
952*9a0e4156SSadaf Ebrahimi 
953*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
954*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
955*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO1);
956*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
957*9a0e4156SSadaf Ebrahimi 
958*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.type = (MCOperand_getImm(MO3) & 7) + ARM_SFT_ASR_REG - 1;
959*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
960*9a0e4156SSadaf Ebrahimi 	}
961*9a0e4156SSadaf Ebrahimi 
962*9a0e4156SSadaf Ebrahimi 	// Print the shift opc.
963*9a0e4156SSadaf Ebrahimi 	ShOpc = ARM_AM_getSORegShOp((unsigned int)MCOperand_getImm(MO3));
964*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
965*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARM_AM_getShiftOpcStr(ShOpc));
966*9a0e4156SSadaf Ebrahimi 	if (ShOpc == ARM_AM_rrx)
967*9a0e4156SSadaf Ebrahimi 		return;
968*9a0e4156SSadaf Ebrahimi 
969*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, " ");
970*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO2));
971*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
972*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = MCOperand_getReg(MO2);
973*9a0e4156SSadaf Ebrahimi 	//assert(ARM_AM_getSORegOffset(MO3.getImm()) == 0);
974*9a0e4156SSadaf Ebrahimi }
975*9a0e4156SSadaf Ebrahimi 
printSORegImmOperand(MCInst * MI,unsigned OpNum,SStream * O)976*9a0e4156SSadaf Ebrahimi static void printSORegImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
977*9a0e4156SSadaf Ebrahimi {
978*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
979*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
980*9a0e4156SSadaf Ebrahimi 
981*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
982*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
983*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
984*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO1);
985*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
986*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.type = MCOperand_getImm(MO2) & 7;
987*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.value = (unsigned int)MCOperand_getImm(MO2) >> 3;
988*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
989*9a0e4156SSadaf Ebrahimi 	}
990*9a0e4156SSadaf Ebrahimi 
991*9a0e4156SSadaf Ebrahimi 	// Print the shift opc.
992*9a0e4156SSadaf Ebrahimi 	printRegImmShift(MI, O, ARM_AM_getSORegShOp((unsigned int)MCOperand_getImm(MO2)),
993*9a0e4156SSadaf Ebrahimi 			getSORegOffset((unsigned int)MCOperand_getImm(MO2)));
994*9a0e4156SSadaf Ebrahimi }
995*9a0e4156SSadaf Ebrahimi 
996*9a0e4156SSadaf Ebrahimi //===--------------------------------------------------------------------===//
997*9a0e4156SSadaf Ebrahimi // Addressing Mode #2
998*9a0e4156SSadaf Ebrahimi //===--------------------------------------------------------------------===//
999*9a0e4156SSadaf Ebrahimi 
printAM2PreOrOffsetIndexOp(MCInst * MI,unsigned Op,SStream * O)1000*9a0e4156SSadaf Ebrahimi static void printAM2PreOrOffsetIndexOp(MCInst *MI, unsigned Op, SStream *O)
1001*9a0e4156SSadaf Ebrahimi {
1002*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1003*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, Op + 1);
1004*9a0e4156SSadaf Ebrahimi 	MCOperand *MO3 = MCInst_getOperand(MI, Op + 2);
1005*9a0e4156SSadaf Ebrahimi 	ARM_AM_AddrOpc subtracted = getAM2Op((unsigned int)MCOperand_getImm(MO3));
1006*9a0e4156SSadaf Ebrahimi 
1007*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1008*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1009*9a0e4156SSadaf Ebrahimi 
1010*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1011*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1012*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1013*9a0e4156SSadaf Ebrahimi 	}
1014*9a0e4156SSadaf Ebrahimi 
1015*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_getReg(MO2)) {
1016*9a0e4156SSadaf Ebrahimi 		unsigned tmp = getAM2Offset((unsigned int)MCOperand_getImm(MO3));
1017*9a0e4156SSadaf Ebrahimi 		if (tmp) { // Don't print +0.
1018*9a0e4156SSadaf Ebrahimi 			subtracted = getAM2Op((unsigned int)MCOperand_getImm(MO3));
1019*9a0e4156SSadaf Ebrahimi 
1020*9a0e4156SSadaf Ebrahimi 			SStream_concat0(O, ", ");
1021*9a0e4156SSadaf Ebrahimi 			if (tmp > HEX_THRESHOLD)
1022*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#%s0x%x", ARM_AM_getAddrOpcStr(subtracted), tmp);
1023*9a0e4156SSadaf Ebrahimi 			else
1024*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#%s%u", ARM_AM_getAddrOpcStr(subtracted), tmp);
1025*9a0e4156SSadaf Ebrahimi 			if (MI->csh->detail) {
1026*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.type = (arm_shifter)getAM2Op((unsigned int)MCOperand_getImm(MO3));
1027*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.value = tmp;
1028*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = subtracted == ARM_AM_sub;
1029*9a0e4156SSadaf Ebrahimi 			}
1030*9a0e4156SSadaf Ebrahimi 		}
1031*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "]");
1032*9a0e4156SSadaf Ebrahimi 		set_mem_access(MI, false);
1033*9a0e4156SSadaf Ebrahimi 		return;
1034*9a0e4156SSadaf Ebrahimi 	}
1035*9a0e4156SSadaf Ebrahimi 
1036*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
1037*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARM_AM_getAddrOpcStr(subtracted));
1038*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO2));
1039*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1040*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = MCOperand_getReg(MO2);
1041*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = subtracted == ARM_AM_sub;
1042*9a0e4156SSadaf Ebrahimi 	}
1043*9a0e4156SSadaf Ebrahimi 
1044*9a0e4156SSadaf Ebrahimi 	printRegImmShift(MI, O, getAM2ShiftOpc((unsigned int)MCOperand_getImm(MO3)),
1045*9a0e4156SSadaf Ebrahimi 			getAM2Offset((unsigned int)MCOperand_getImm(MO3)));
1046*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1047*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1048*9a0e4156SSadaf Ebrahimi }
1049*9a0e4156SSadaf Ebrahimi 
printAddrModeTBB(MCInst * MI,unsigned Op,SStream * O)1050*9a0e4156SSadaf Ebrahimi static void printAddrModeTBB(MCInst *MI, unsigned Op, SStream *O)
1051*9a0e4156SSadaf Ebrahimi {
1052*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1053*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, Op+1);
1054*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1055*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1056*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1057*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1058*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1059*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
1060*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO2));
1061*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1062*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = MCOperand_getReg(MO2);
1063*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1064*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1065*9a0e4156SSadaf Ebrahimi }
1066*9a0e4156SSadaf Ebrahimi 
printAddrModeTBH(MCInst * MI,unsigned Op,SStream * O)1067*9a0e4156SSadaf Ebrahimi static void printAddrModeTBH(MCInst *MI, unsigned Op, SStream *O)
1068*9a0e4156SSadaf Ebrahimi {
1069*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1070*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, Op+1);
1071*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1072*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1073*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1074*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1075*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1076*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
1077*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO2));
1078*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1079*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = MCOperand_getReg(MO2);
1080*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", lsl #1]");
1081*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1082*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.type = ARM_SFT_LSL;
1083*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.value = 1;
1084*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.lshift = 1;
1085*9a0e4156SSadaf Ebrahimi 	}
1086*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1087*9a0e4156SSadaf Ebrahimi }
1088*9a0e4156SSadaf Ebrahimi 
printAddrMode2Operand(MCInst * MI,unsigned Op,SStream * O)1089*9a0e4156SSadaf Ebrahimi static void printAddrMode2Operand(MCInst *MI, unsigned Op, SStream *O)
1090*9a0e4156SSadaf Ebrahimi {
1091*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1092*9a0e4156SSadaf Ebrahimi 
1093*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_isReg(MO1)) {   // FIXME: This is for CP entries, but isn't right.
1094*9a0e4156SSadaf Ebrahimi 		printOperand(MI, Op, O);
1095*9a0e4156SSadaf Ebrahimi 		return;
1096*9a0e4156SSadaf Ebrahimi 	}
1097*9a0e4156SSadaf Ebrahimi 
1098*9a0e4156SSadaf Ebrahimi 	printAM2PreOrOffsetIndexOp(MI, Op, O);
1099*9a0e4156SSadaf Ebrahimi }
1100*9a0e4156SSadaf Ebrahimi 
printAddrMode2OffsetOperand(MCInst * MI,unsigned OpNum,SStream * O)1101*9a0e4156SSadaf Ebrahimi static void printAddrMode2OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O)
1102*9a0e4156SSadaf Ebrahimi {
1103*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
1104*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
1105*9a0e4156SSadaf Ebrahimi 	ARM_AM_AddrOpc subtracted = getAM2Op((unsigned int)MCOperand_getImm(MO2));
1106*9a0e4156SSadaf Ebrahimi 
1107*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_getReg(MO1)) {
1108*9a0e4156SSadaf Ebrahimi 		unsigned ImmOffs = getAM2Offset((unsigned int)MCOperand_getImm(MO2));
1109*9a0e4156SSadaf Ebrahimi 		if (ImmOffs > HEX_THRESHOLD)
1110*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, "#%s0x%x",
1111*9a0e4156SSadaf Ebrahimi 					ARM_AM_getAddrOpcStr(subtracted), ImmOffs);
1112*9a0e4156SSadaf Ebrahimi 		else
1113*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, "#%s%u",
1114*9a0e4156SSadaf Ebrahimi 					ARM_AM_getAddrOpcStr(subtracted), ImmOffs);
1115*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1116*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1117*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = ImmOffs;
1118*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = subtracted == ARM_AM_sub;
1119*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1120*9a0e4156SSadaf Ebrahimi 		}
1121*9a0e4156SSadaf Ebrahimi 		return;
1122*9a0e4156SSadaf Ebrahimi 	}
1123*9a0e4156SSadaf Ebrahimi 
1124*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARM_AM_getAddrOpcStr(subtracted));
1125*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1126*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1127*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
1128*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO1);
1129*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
1130*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = subtracted == ARM_AM_sub;
1131*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1132*9a0e4156SSadaf Ebrahimi 	}
1133*9a0e4156SSadaf Ebrahimi 
1134*9a0e4156SSadaf Ebrahimi 	printRegImmShift(MI, O, getAM2ShiftOpc((unsigned int)MCOperand_getImm(MO2)),
1135*9a0e4156SSadaf Ebrahimi 			getAM2Offset((unsigned int)MCOperand_getImm(MO2)));
1136*9a0e4156SSadaf Ebrahimi }
1137*9a0e4156SSadaf Ebrahimi 
1138*9a0e4156SSadaf Ebrahimi //===--------------------------------------------------------------------===//
1139*9a0e4156SSadaf Ebrahimi // Addressing Mode #3
1140*9a0e4156SSadaf Ebrahimi //===--------------------------------------------------------------------===//
1141*9a0e4156SSadaf Ebrahimi 
printAM3PreOrOffsetIndexOp(MCInst * MI,unsigned Op,SStream * O,bool AlwaysPrintImm0)1142*9a0e4156SSadaf Ebrahimi static void printAM3PreOrOffsetIndexOp(MCInst *MI, unsigned Op, SStream *O,
1143*9a0e4156SSadaf Ebrahimi 		bool AlwaysPrintImm0)
1144*9a0e4156SSadaf Ebrahimi {
1145*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1146*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, Op+1);
1147*9a0e4156SSadaf Ebrahimi 	MCOperand *MO3 = MCInst_getOperand(MI, Op+2);
1148*9a0e4156SSadaf Ebrahimi 	ARM_AM_AddrOpc sign = getAM3Op((unsigned int)MCOperand_getImm(MO3));
1149*9a0e4156SSadaf Ebrahimi 	unsigned ImmOffs;
1150*9a0e4156SSadaf Ebrahimi 
1151*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1152*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1153*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1154*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1155*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1156*9a0e4156SSadaf Ebrahimi 
1157*9a0e4156SSadaf Ebrahimi 	if (MCOperand_getReg(MO2)) {
1158*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ", ");
1159*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ARM_AM_getAddrOpcStr(sign));
1160*9a0e4156SSadaf Ebrahimi 		printRegName(MI->csh, O, MCOperand_getReg(MO2));
1161*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1162*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = MCOperand_getReg(MO2);
1163*9a0e4156SSadaf Ebrahimi 			if (sign == ARM_AM_sub) {
1164*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.scale = -1;
1165*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = true;
1166*9a0e4156SSadaf Ebrahimi 			}
1167*9a0e4156SSadaf Ebrahimi 		}
1168*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "]");
1169*9a0e4156SSadaf Ebrahimi 		set_mem_access(MI, false);
1170*9a0e4156SSadaf Ebrahimi 		return;
1171*9a0e4156SSadaf Ebrahimi 	}
1172*9a0e4156SSadaf Ebrahimi 
1173*9a0e4156SSadaf Ebrahimi 	//If the op is sub we have to print the immediate even if it is 0
1174*9a0e4156SSadaf Ebrahimi 	ImmOffs = getAM3Offset((unsigned int)MCOperand_getImm(MO3));
1175*9a0e4156SSadaf Ebrahimi 
1176*9a0e4156SSadaf Ebrahimi 	if (AlwaysPrintImm0 || ImmOffs || (sign == ARM_AM_sub)) {
1177*9a0e4156SSadaf Ebrahimi 		if (ImmOffs > HEX_THRESHOLD)
1178*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #%s0x%x", ARM_AM_getAddrOpcStr(sign), ImmOffs);
1179*9a0e4156SSadaf Ebrahimi 		else
1180*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #%s%u", ARM_AM_getAddrOpcStr(sign), ImmOffs);
1181*9a0e4156SSadaf Ebrahimi 	}
1182*9a0e4156SSadaf Ebrahimi 
1183*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1184*9a0e4156SSadaf Ebrahimi 		if (sign == ARM_AM_sub) {
1185*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = -(int)ImmOffs;
1186*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = true;
1187*9a0e4156SSadaf Ebrahimi 		} else
1188*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = (int)ImmOffs;
1189*9a0e4156SSadaf Ebrahimi 	}
1190*9a0e4156SSadaf Ebrahimi 
1191*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1192*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1193*9a0e4156SSadaf Ebrahimi }
1194*9a0e4156SSadaf Ebrahimi 
printAddrMode3Operand(MCInst * MI,unsigned Op,SStream * O,bool AlwaysPrintImm0)1195*9a0e4156SSadaf Ebrahimi static void printAddrMode3Operand(MCInst *MI, unsigned Op, SStream *O,
1196*9a0e4156SSadaf Ebrahimi 		bool AlwaysPrintImm0)
1197*9a0e4156SSadaf Ebrahimi {
1198*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1199*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_isReg(MO1)) {   //  For label symbolic references.
1200*9a0e4156SSadaf Ebrahimi 		printOperand(MI, Op, O);
1201*9a0e4156SSadaf Ebrahimi 		return;
1202*9a0e4156SSadaf Ebrahimi 	}
1203*9a0e4156SSadaf Ebrahimi 
1204*9a0e4156SSadaf Ebrahimi 	printAM3PreOrOffsetIndexOp(MI, Op, O, AlwaysPrintImm0);
1205*9a0e4156SSadaf Ebrahimi }
1206*9a0e4156SSadaf Ebrahimi 
printAddrMode3OffsetOperand(MCInst * MI,unsigned OpNum,SStream * O)1207*9a0e4156SSadaf Ebrahimi static void printAddrMode3OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O)
1208*9a0e4156SSadaf Ebrahimi {
1209*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
1210*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
1211*9a0e4156SSadaf Ebrahimi 	ARM_AM_AddrOpc subtracted = getAM3Op((unsigned int)MCOperand_getImm(MO2));
1212*9a0e4156SSadaf Ebrahimi 	unsigned ImmOffs;
1213*9a0e4156SSadaf Ebrahimi 
1214*9a0e4156SSadaf Ebrahimi 	if (MCOperand_getReg(MO1)) {
1215*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ARM_AM_getAddrOpcStr(subtracted));
1216*9a0e4156SSadaf Ebrahimi 		printRegName(MI->csh, O, MCOperand_getReg(MO1));
1217*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1218*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
1219*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO1);
1220*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
1221*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = subtracted == ARM_AM_sub;
1222*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1223*9a0e4156SSadaf Ebrahimi 		}
1224*9a0e4156SSadaf Ebrahimi 		return;
1225*9a0e4156SSadaf Ebrahimi 	}
1226*9a0e4156SSadaf Ebrahimi 
1227*9a0e4156SSadaf Ebrahimi 	ImmOffs = getAM3Offset((unsigned int)MCOperand_getImm(MO2));
1228*9a0e4156SSadaf Ebrahimi 	if (ImmOffs > HEX_THRESHOLD)
1229*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%s0x%x", ARM_AM_getAddrOpcStr(subtracted), ImmOffs);
1230*9a0e4156SSadaf Ebrahimi 	else
1231*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%s%u", ARM_AM_getAddrOpcStr(subtracted), ImmOffs);
1232*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1233*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1234*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = ImmOffs;
1235*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].subtracted = subtracted == ARM_AM_sub;
1236*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1237*9a0e4156SSadaf Ebrahimi 	}
1238*9a0e4156SSadaf Ebrahimi }
1239*9a0e4156SSadaf Ebrahimi 
printPostIdxImm8Operand(MCInst * MI,unsigned OpNum,SStream * O)1240*9a0e4156SSadaf Ebrahimi static void printPostIdxImm8Operand(MCInst *MI, unsigned OpNum, SStream *O)
1241*9a0e4156SSadaf Ebrahimi {
1242*9a0e4156SSadaf Ebrahimi 	MCOperand *MO = MCInst_getOperand(MI, OpNum);
1243*9a0e4156SSadaf Ebrahimi 	unsigned Imm = (unsigned int)MCOperand_getImm(MO);
1244*9a0e4156SSadaf Ebrahimi 	if ((Imm & 0xff) > HEX_THRESHOLD)
1245*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%s0x%x", ((Imm & 256) ? "" : "-"), (Imm & 0xff));
1246*9a0e4156SSadaf Ebrahimi 	else
1247*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%s%u", ((Imm & 256) ? "" : "-"), (Imm & 0xff));
1248*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1249*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1250*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = Imm & 0xff;
1251*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1252*9a0e4156SSadaf Ebrahimi 	}
1253*9a0e4156SSadaf Ebrahimi }
1254*9a0e4156SSadaf Ebrahimi 
printPostIdxRegOperand(MCInst * MI,unsigned OpNum,SStream * O)1255*9a0e4156SSadaf Ebrahimi static void printPostIdxRegOperand(MCInst *MI, unsigned OpNum, SStream *O)
1256*9a0e4156SSadaf Ebrahimi {
1257*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
1258*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
1259*9a0e4156SSadaf Ebrahimi 
1260*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, (MCOperand_getImm(MO2) ? "" : "-"));
1261*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1262*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1263*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
1264*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO1);
1265*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
1266*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1267*9a0e4156SSadaf Ebrahimi 	}
1268*9a0e4156SSadaf Ebrahimi }
1269*9a0e4156SSadaf Ebrahimi 
printPostIdxImm8s4Operand(MCInst * MI,unsigned OpNum,SStream * O)1270*9a0e4156SSadaf Ebrahimi static void printPostIdxImm8s4Operand(MCInst *MI, unsigned OpNum, SStream *O)
1271*9a0e4156SSadaf Ebrahimi {
1272*9a0e4156SSadaf Ebrahimi 	MCOperand *MO = MCInst_getOperand(MI, OpNum);
1273*9a0e4156SSadaf Ebrahimi 	int Imm = (int)MCOperand_getImm(MO);
1274*9a0e4156SSadaf Ebrahimi 
1275*9a0e4156SSadaf Ebrahimi 	if (((Imm & 0xff) << 2) > HEX_THRESHOLD) {
1276*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%s0x%x", ((Imm & 256) ? "" : "-"), ((Imm & 0xff) << 2));
1277*9a0e4156SSadaf Ebrahimi 	} else {
1278*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%s%u", ((Imm & 256) ? "" : "-"), ((Imm & 0xff) << 2));
1279*9a0e4156SSadaf Ebrahimi 	}
1280*9a0e4156SSadaf Ebrahimi 
1281*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1282*9a0e4156SSadaf Ebrahimi 		int v = (Imm & 256) ? ((Imm & 0xff) << 2) : -((Imm & 0xff) << 2);
1283*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1284*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = v;
1285*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1286*9a0e4156SSadaf Ebrahimi 	}
1287*9a0e4156SSadaf Ebrahimi }
1288*9a0e4156SSadaf Ebrahimi 
printAddrMode5Operand(MCInst * MI,unsigned OpNum,SStream * O,bool AlwaysPrintImm0)1289*9a0e4156SSadaf Ebrahimi static void printAddrMode5Operand(MCInst *MI, unsigned OpNum, SStream *O,
1290*9a0e4156SSadaf Ebrahimi 		bool AlwaysPrintImm0)
1291*9a0e4156SSadaf Ebrahimi {
1292*9a0e4156SSadaf Ebrahimi 	unsigned ImmOffs;
1293*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
1294*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
1295*9a0e4156SSadaf Ebrahimi 	ARM_AM_AddrOpc subtracted = ARM_AM_getAM5Op((unsigned int)MCOperand_getImm(MO2));
1296*9a0e4156SSadaf Ebrahimi 
1297*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_isReg(MO1)) {   // FIXME: This is for CP entries, but isn't right.
1298*9a0e4156SSadaf Ebrahimi 		printOperand(MI, OpNum, O);
1299*9a0e4156SSadaf Ebrahimi 		return;
1300*9a0e4156SSadaf Ebrahimi 	}
1301*9a0e4156SSadaf Ebrahimi 
1302*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1303*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1304*9a0e4156SSadaf Ebrahimi 
1305*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1306*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_MEM;
1307*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1308*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = ARM_REG_INVALID;
1309*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.scale = 1;
1310*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = 0;
1311*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
1312*9a0e4156SSadaf Ebrahimi 	}
1313*9a0e4156SSadaf Ebrahimi 
1314*9a0e4156SSadaf Ebrahimi 	ImmOffs = ARM_AM_getAM5Offset((unsigned int)MCOperand_getImm(MO2));
1315*9a0e4156SSadaf Ebrahimi 	if (AlwaysPrintImm0 || ImmOffs || subtracted == ARM_AM_sub) {
1316*9a0e4156SSadaf Ebrahimi 		if (ImmOffs * 4 > HEX_THRESHOLD)
1317*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #%s0x%x",
1318*9a0e4156SSadaf Ebrahimi 					ARM_AM_getAddrOpcStr(subtracted),
1319*9a0e4156SSadaf Ebrahimi 					ImmOffs * 4);
1320*9a0e4156SSadaf Ebrahimi 		else
1321*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #%s%u",
1322*9a0e4156SSadaf Ebrahimi 					ARM_AM_getAddrOpcStr(subtracted),
1323*9a0e4156SSadaf Ebrahimi 					ImmOffs * 4);
1324*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1325*9a0e4156SSadaf Ebrahimi 			if (subtracted)
1326*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = ImmOffs * 4;
1327*9a0e4156SSadaf Ebrahimi 			else
1328*9a0e4156SSadaf Ebrahimi 				MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = -(int)ImmOffs * 4;
1329*9a0e4156SSadaf Ebrahimi 		}
1330*9a0e4156SSadaf Ebrahimi 	}
1331*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1332*9a0e4156SSadaf Ebrahimi 
1333*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1334*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1335*9a0e4156SSadaf Ebrahimi 	}
1336*9a0e4156SSadaf Ebrahimi }
1337*9a0e4156SSadaf Ebrahimi 
printAddrMode6Operand(MCInst * MI,unsigned OpNum,SStream * O)1338*9a0e4156SSadaf Ebrahimi static void printAddrMode6Operand(MCInst *MI, unsigned OpNum, SStream *O)
1339*9a0e4156SSadaf Ebrahimi {
1340*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
1341*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
1342*9a0e4156SSadaf Ebrahimi 	unsigned tmp;
1343*9a0e4156SSadaf Ebrahimi 
1344*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1345*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1346*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1347*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1348*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1349*9a0e4156SSadaf Ebrahimi 	tmp = (unsigned int)MCOperand_getImm(MO2);
1350*9a0e4156SSadaf Ebrahimi 	if (tmp) {
1351*9a0e4156SSadaf Ebrahimi 		if (tmp << 3 > HEX_THRESHOLD)
1352*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ":0x%x", (tmp << 3));
1353*9a0e4156SSadaf Ebrahimi 		else
1354*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ":%u", (tmp << 3));
1355*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail)
1356*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = tmp << 3;
1357*9a0e4156SSadaf Ebrahimi 	}
1358*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1359*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1360*9a0e4156SSadaf Ebrahimi }
1361*9a0e4156SSadaf Ebrahimi 
printAddrMode7Operand(MCInst * MI,unsigned OpNum,SStream * O)1362*9a0e4156SSadaf Ebrahimi static void printAddrMode7Operand(MCInst *MI, unsigned OpNum, SStream *O)
1363*9a0e4156SSadaf Ebrahimi {
1364*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
1365*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1366*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1367*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1368*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1369*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1370*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1371*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1372*9a0e4156SSadaf Ebrahimi }
1373*9a0e4156SSadaf Ebrahimi 
printAddrMode6OffsetOperand(MCInst * MI,unsigned OpNum,SStream * O)1374*9a0e4156SSadaf Ebrahimi static void printAddrMode6OffsetOperand(MCInst *MI, unsigned OpNum, SStream *O)
1375*9a0e4156SSadaf Ebrahimi {
1376*9a0e4156SSadaf Ebrahimi 	MCOperand *MO = MCInst_getOperand(MI, OpNum);
1377*9a0e4156SSadaf Ebrahimi 	if (MCOperand_getReg(MO) == 0) {
1378*9a0e4156SSadaf Ebrahimi 		MI->writeback = true;
1379*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "!");
1380*9a0e4156SSadaf Ebrahimi 	} else {
1381*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ", ");
1382*9a0e4156SSadaf Ebrahimi 		printRegName(MI->csh, O, MCOperand_getReg(MO));
1383*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1384*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
1385*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MO);
1386*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
1387*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1388*9a0e4156SSadaf Ebrahimi 		}
1389*9a0e4156SSadaf Ebrahimi 	}
1390*9a0e4156SSadaf Ebrahimi }
1391*9a0e4156SSadaf Ebrahimi 
printBitfieldInvMaskImmOperand(MCInst * MI,unsigned OpNum,SStream * O)1392*9a0e4156SSadaf Ebrahimi static void printBitfieldInvMaskImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
1393*9a0e4156SSadaf Ebrahimi {
1394*9a0e4156SSadaf Ebrahimi 	MCOperand *MO = MCInst_getOperand(MI, OpNum);
1395*9a0e4156SSadaf Ebrahimi 	uint32_t v = ~(uint32_t)MCOperand_getImm(MO);
1396*9a0e4156SSadaf Ebrahimi 	int32_t lsb = CountTrailingZeros_32(v);
1397*9a0e4156SSadaf Ebrahimi 	int32_t width = (32 - CountLeadingZeros_32 (v)) - lsb;
1398*9a0e4156SSadaf Ebrahimi 
1399*9a0e4156SSadaf Ebrahimi 	//assert(MO.isImm() && "Not a valid bf_inv_mask_imm value!");
1400*9a0e4156SSadaf Ebrahimi 	printUInt32Bang(O, lsb);
1401*9a0e4156SSadaf Ebrahimi 
1402*9a0e4156SSadaf Ebrahimi 	if (width > HEX_THRESHOLD)
1403*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", #0x%x", width);
1404*9a0e4156SSadaf Ebrahimi 	else
1405*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", #%u", width);
1406*9a0e4156SSadaf Ebrahimi 
1407*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1408*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1409*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = lsb;
1410*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1411*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1412*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = width;
1413*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1414*9a0e4156SSadaf Ebrahimi 	}
1415*9a0e4156SSadaf Ebrahimi }
1416*9a0e4156SSadaf Ebrahimi 
printMemBOption(MCInst * MI,unsigned OpNum,SStream * O)1417*9a0e4156SSadaf Ebrahimi static void printMemBOption(MCInst *MI, unsigned OpNum, SStream *O)
1418*9a0e4156SSadaf Ebrahimi {
1419*9a0e4156SSadaf Ebrahimi 	unsigned val = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1420*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARM_MB_MemBOptToString(val + 1,
1421*9a0e4156SSadaf Ebrahimi 				(ARM_getFeatureBits(MI->csh->mode) & ARM_HasV8Ops) != 0));
1422*9a0e4156SSadaf Ebrahimi 
1423*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1424*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.mem_barrier = (arm_mem_barrier)(val + 1);
1425*9a0e4156SSadaf Ebrahimi 	}
1426*9a0e4156SSadaf Ebrahimi }
1427*9a0e4156SSadaf Ebrahimi 
printInstSyncBOption(MCInst * MI,unsigned OpNum,SStream * O)1428*9a0e4156SSadaf Ebrahimi void printInstSyncBOption(MCInst *MI, unsigned OpNum, SStream *O)
1429*9a0e4156SSadaf Ebrahimi {
1430*9a0e4156SSadaf Ebrahimi 	unsigned val = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1431*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARM_ISB_InstSyncBOptToString(val));
1432*9a0e4156SSadaf Ebrahimi }
1433*9a0e4156SSadaf Ebrahimi 
printShiftImmOperand(MCInst * MI,unsigned OpNum,SStream * O)1434*9a0e4156SSadaf Ebrahimi static void printShiftImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
1435*9a0e4156SSadaf Ebrahimi {
1436*9a0e4156SSadaf Ebrahimi 	unsigned ShiftOp = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1437*9a0e4156SSadaf Ebrahimi 	bool isASR = (ShiftOp & (1 << 5)) != 0;
1438*9a0e4156SSadaf Ebrahimi 	unsigned Amt = ShiftOp & 0x1f;
1439*9a0e4156SSadaf Ebrahimi 	if (isASR) {
1440*9a0e4156SSadaf Ebrahimi 		unsigned tmp = Amt == 0 ? 32 : Amt;
1441*9a0e4156SSadaf Ebrahimi 		if (tmp > HEX_THRESHOLD)
1442*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", asr #0x%x", tmp);
1443*9a0e4156SSadaf Ebrahimi 		else
1444*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", asr #%u", tmp);
1445*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1446*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.type = ARM_SFT_ASR;
1447*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = tmp;
1448*9a0e4156SSadaf Ebrahimi 		}
1449*9a0e4156SSadaf Ebrahimi 	} else if (Amt) {
1450*9a0e4156SSadaf Ebrahimi 		if (Amt > HEX_THRESHOLD)
1451*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", lsl #0x%x", Amt);
1452*9a0e4156SSadaf Ebrahimi 		else
1453*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", lsl #%u", Amt);
1454*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1455*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.type = ARM_SFT_LSL;
1456*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = Amt;
1457*9a0e4156SSadaf Ebrahimi 		}
1458*9a0e4156SSadaf Ebrahimi 	}
1459*9a0e4156SSadaf Ebrahimi }
1460*9a0e4156SSadaf Ebrahimi 
printPKHLSLShiftImm(MCInst * MI,unsigned OpNum,SStream * O)1461*9a0e4156SSadaf Ebrahimi static void printPKHLSLShiftImm(MCInst *MI, unsigned OpNum, SStream *O)
1462*9a0e4156SSadaf Ebrahimi {
1463*9a0e4156SSadaf Ebrahimi 	unsigned Imm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1464*9a0e4156SSadaf Ebrahimi 	if (Imm == 0)
1465*9a0e4156SSadaf Ebrahimi 		return;
1466*9a0e4156SSadaf Ebrahimi 	//assert(Imm > 0 && Imm < 32 && "Invalid PKH shift immediate value!");
1467*9a0e4156SSadaf Ebrahimi 	if (Imm > HEX_THRESHOLD)
1468*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", lsl #0x%x", Imm);
1469*9a0e4156SSadaf Ebrahimi 	else
1470*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", lsl #%u", Imm);
1471*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1472*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.type = ARM_SFT_LSL;
1473*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = Imm;
1474*9a0e4156SSadaf Ebrahimi 	}
1475*9a0e4156SSadaf Ebrahimi }
1476*9a0e4156SSadaf Ebrahimi 
printPKHASRShiftImm(MCInst * MI,unsigned OpNum,SStream * O)1477*9a0e4156SSadaf Ebrahimi static void printPKHASRShiftImm(MCInst *MI, unsigned OpNum, SStream *O)
1478*9a0e4156SSadaf Ebrahimi {
1479*9a0e4156SSadaf Ebrahimi 	unsigned Imm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1480*9a0e4156SSadaf Ebrahimi 	// A shift amount of 32 is encoded as 0.
1481*9a0e4156SSadaf Ebrahimi 	if (Imm == 0)
1482*9a0e4156SSadaf Ebrahimi 		Imm = 32;
1483*9a0e4156SSadaf Ebrahimi 	//assert(Imm > 0 && Imm <= 32 && "Invalid PKH shift immediate value!");
1484*9a0e4156SSadaf Ebrahimi 	if (Imm > HEX_THRESHOLD)
1485*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", asr #0x%x", Imm);
1486*9a0e4156SSadaf Ebrahimi 	else
1487*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", asr #%u", Imm);
1488*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1489*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.type = ARM_SFT_ASR;
1490*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = Imm;
1491*9a0e4156SSadaf Ebrahimi 	}
1492*9a0e4156SSadaf Ebrahimi }
1493*9a0e4156SSadaf Ebrahimi 
1494*9a0e4156SSadaf Ebrahimi // FIXME: push {r1, r2, r3, ...} can exceed the number of operands in MCInst struct
printRegisterList(MCInst * MI,unsigned OpNum,SStream * O)1495*9a0e4156SSadaf Ebrahimi static void printRegisterList(MCInst *MI, unsigned OpNum, SStream *O)
1496*9a0e4156SSadaf Ebrahimi {
1497*9a0e4156SSadaf Ebrahimi 	unsigned i, e;
1498*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
1499*9a0e4156SSadaf Ebrahimi 	uint8_t access = 0;
1500*9a0e4156SSadaf Ebrahimi #endif
1501*9a0e4156SSadaf Ebrahimi 
1502*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
1503*9a0e4156SSadaf Ebrahimi 
1504*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
1505*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1506*9a0e4156SSadaf Ebrahimi 		access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
1507*9a0e4156SSadaf Ebrahimi 	}
1508*9a0e4156SSadaf Ebrahimi #endif
1509*9a0e4156SSadaf Ebrahimi 
1510*9a0e4156SSadaf Ebrahimi 	for (i = OpNum, e = MCInst_getNumOperands(MI); i != e; ++i) {
1511*9a0e4156SSadaf Ebrahimi 		if (i != OpNum) SStream_concat0(O, ", ");
1512*9a0e4156SSadaf Ebrahimi 		printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, i)));
1513*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1514*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
1515*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, i));
1516*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
1517*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
1518*9a0e4156SSadaf Ebrahimi #endif
1519*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1520*9a0e4156SSadaf Ebrahimi 		}
1521*9a0e4156SSadaf Ebrahimi 	}
1522*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
1523*9a0e4156SSadaf Ebrahimi 
1524*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
1525*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1526*9a0e4156SSadaf Ebrahimi 		MI->ac_idx++;
1527*9a0e4156SSadaf Ebrahimi 	}
1528*9a0e4156SSadaf Ebrahimi #endif
1529*9a0e4156SSadaf Ebrahimi }
1530*9a0e4156SSadaf Ebrahimi 
printGPRPairOperand(MCInst * MI,unsigned OpNum,SStream * O,MCRegisterInfo * MRI)1531*9a0e4156SSadaf Ebrahimi static void printGPRPairOperand(MCInst *MI, unsigned OpNum, SStream *O,
1532*9a0e4156SSadaf Ebrahimi 		MCRegisterInfo *MRI)
1533*9a0e4156SSadaf Ebrahimi {
1534*9a0e4156SSadaf Ebrahimi 	unsigned Reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
1535*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCRegisterInfo_getSubReg(MRI, Reg, ARM_gsub_0));
1536*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1537*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
1538*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCRegisterInfo_getSubReg(MRI, Reg, ARM_gsub_0);
1539*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1540*9a0e4156SSadaf Ebrahimi 	}
1541*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
1542*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCRegisterInfo_getSubReg(MRI, Reg, ARM_gsub_1));
1543*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1544*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
1545*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCRegisterInfo_getSubReg(MRI, Reg, ARM_gsub_1);
1546*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1547*9a0e4156SSadaf Ebrahimi 	}
1548*9a0e4156SSadaf Ebrahimi }
1549*9a0e4156SSadaf Ebrahimi 
1550*9a0e4156SSadaf Ebrahimi // SETEND BE/LE
printSetendOperand(MCInst * MI,unsigned OpNum,SStream * O)1551*9a0e4156SSadaf Ebrahimi static void printSetendOperand(MCInst *MI, unsigned OpNum, SStream *O)
1552*9a0e4156SSadaf Ebrahimi {
1553*9a0e4156SSadaf Ebrahimi 	MCOperand *Op = MCInst_getOperand(MI, OpNum);
1554*9a0e4156SSadaf Ebrahimi 	if (MCOperand_getImm(Op)) {
1555*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "be");
1556*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1557*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_SETEND;
1558*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].setend = ARM_SETEND_BE;
1559*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1560*9a0e4156SSadaf Ebrahimi 		}
1561*9a0e4156SSadaf Ebrahimi 	} else {
1562*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "le");
1563*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1564*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_SETEND;
1565*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].setend = ARM_SETEND_LE;
1566*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1567*9a0e4156SSadaf Ebrahimi 		}
1568*9a0e4156SSadaf Ebrahimi 	}
1569*9a0e4156SSadaf Ebrahimi }
1570*9a0e4156SSadaf Ebrahimi 
printCPSIMod(MCInst * MI,unsigned OpNum,SStream * O)1571*9a0e4156SSadaf Ebrahimi static void printCPSIMod(MCInst *MI, unsigned OpNum, SStream *O)
1572*9a0e4156SSadaf Ebrahimi {
1573*9a0e4156SSadaf Ebrahimi 	MCOperand *Op = MCInst_getOperand(MI, OpNum);
1574*9a0e4156SSadaf Ebrahimi 	unsigned int mode = (unsigned int)MCOperand_getImm(Op);
1575*9a0e4156SSadaf Ebrahimi 
1576*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARM_PROC_IModToString(mode));
1577*9a0e4156SSadaf Ebrahimi 
1578*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1579*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.cps_mode = mode;
1580*9a0e4156SSadaf Ebrahimi 	}
1581*9a0e4156SSadaf Ebrahimi }
1582*9a0e4156SSadaf Ebrahimi 
printCPSIFlag(MCInst * MI,unsigned OpNum,SStream * O)1583*9a0e4156SSadaf Ebrahimi static void printCPSIFlag(MCInst *MI, unsigned OpNum, SStream *O)
1584*9a0e4156SSadaf Ebrahimi {
1585*9a0e4156SSadaf Ebrahimi 	MCOperand *Op = MCInst_getOperand(MI, OpNum);
1586*9a0e4156SSadaf Ebrahimi 	unsigned IFlags = (unsigned int)MCOperand_getImm(Op);
1587*9a0e4156SSadaf Ebrahimi 	int i;
1588*9a0e4156SSadaf Ebrahimi 
1589*9a0e4156SSadaf Ebrahimi 	for (i = 2; i >= 0; --i)
1590*9a0e4156SSadaf Ebrahimi 		if (IFlags & (1 << i)) {
1591*9a0e4156SSadaf Ebrahimi 			SStream_concat0(O, ARM_PROC_IFlagsToString(1 << i));
1592*9a0e4156SSadaf Ebrahimi 		}
1593*9a0e4156SSadaf Ebrahimi 
1594*9a0e4156SSadaf Ebrahimi 	if (IFlags == 0) {
1595*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "none");
1596*9a0e4156SSadaf Ebrahimi 		IFlags = ARM_CPSFLAG_NONE;
1597*9a0e4156SSadaf Ebrahimi 	}
1598*9a0e4156SSadaf Ebrahimi 
1599*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1600*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.cps_flag = IFlags;
1601*9a0e4156SSadaf Ebrahimi 	}
1602*9a0e4156SSadaf Ebrahimi }
1603*9a0e4156SSadaf Ebrahimi 
printMSRMaskOperand(MCInst * MI,unsigned OpNum,SStream * O)1604*9a0e4156SSadaf Ebrahimi static void printMSRMaskOperand(MCInst *MI, unsigned OpNum, SStream *O)
1605*9a0e4156SSadaf Ebrahimi {
1606*9a0e4156SSadaf Ebrahimi 	MCOperand *Op = MCInst_getOperand(MI, OpNum);
1607*9a0e4156SSadaf Ebrahimi 	unsigned SpecRegRBit = (unsigned)MCOperand_getImm(Op) >> 4;
1608*9a0e4156SSadaf Ebrahimi 	unsigned Mask = (unsigned)MCOperand_getImm(Op) & 0xf;
1609*9a0e4156SSadaf Ebrahimi 	unsigned reg;
1610*9a0e4156SSadaf Ebrahimi 	uint64_t FeatureBits = ARM_getFeatureBits(MI->csh->mode);
1611*9a0e4156SSadaf Ebrahimi 
1612*9a0e4156SSadaf Ebrahimi 	if (FeatureBits & ARM_FeatureMClass) {
1613*9a0e4156SSadaf Ebrahimi 		unsigned SYSm = (unsigned)MCOperand_getImm(Op);
1614*9a0e4156SSadaf Ebrahimi 		unsigned Opcode = MCInst_getOpcode(MI);
1615*9a0e4156SSadaf Ebrahimi 
1616*9a0e4156SSadaf Ebrahimi 		// For writes, handle extended mask bits if the DSP extension is present.
1617*9a0e4156SSadaf Ebrahimi 		if (Opcode == ARM_t2MSR_M && (FeatureBits & ARM_FeatureDSPThumb2)) {
1618*9a0e4156SSadaf Ebrahimi 			switch (SYSm) {
1619*9a0e4156SSadaf Ebrahimi 				case 0x400: SStream_concat0(O, "apsr_g"); ARM_addSysReg(MI, ARM_SYSREG_APSR_G); return;
1620*9a0e4156SSadaf Ebrahimi 				case 0xc00: SStream_concat0(O, "apsr_nzcvqg"); ARM_addSysReg(MI, ARM_SYSREG_APSR_NZCVQG); return;
1621*9a0e4156SSadaf Ebrahimi 				case 0x401: SStream_concat0(O, "iapsr_g"); ARM_addSysReg(MI, ARM_SYSREG_IAPSR_G); return;
1622*9a0e4156SSadaf Ebrahimi 				case 0xc01: SStream_concat0(O, "iapsr_nzcvqg"); ARM_addSysReg(MI, ARM_SYSREG_IAPSR_NZCVQG); return;
1623*9a0e4156SSadaf Ebrahimi 				case 0x402: SStream_concat0(O, "eapsr_g"); ARM_addSysReg(MI, ARM_SYSREG_EAPSR_G); return;
1624*9a0e4156SSadaf Ebrahimi 				case 0xc02: SStream_concat0(O, "eapsr_nzcvqg"); ARM_addSysReg(MI, ARM_SYSREG_EAPSR_NZCVQG); return;
1625*9a0e4156SSadaf Ebrahimi 				case 0x403: SStream_concat0(O, "xpsr_g"); ARM_addSysReg(MI, ARM_SYSREG_XPSR_G); return;
1626*9a0e4156SSadaf Ebrahimi 				case 0xc03: SStream_concat0(O, "xpsr_nzcvqg"); ARM_addSysReg(MI, ARM_SYSREG_XPSR_NZCVQG); return;
1627*9a0e4156SSadaf Ebrahimi 			}
1628*9a0e4156SSadaf Ebrahimi 		}
1629*9a0e4156SSadaf Ebrahimi 
1630*9a0e4156SSadaf Ebrahimi 		// Handle the basic 8-bit mask.
1631*9a0e4156SSadaf Ebrahimi 		SYSm &= 0xff;
1632*9a0e4156SSadaf Ebrahimi 
1633*9a0e4156SSadaf Ebrahimi 		if (Opcode == ARM_t2MSR_M && (FeatureBits & ARM_HasV7Ops)) {
1634*9a0e4156SSadaf Ebrahimi 			// ARMv7-M deprecates using MSR APSR without a _<bits> qualifier as an
1635*9a0e4156SSadaf Ebrahimi 			// alias for MSR APSR_nzcvq.
1636*9a0e4156SSadaf Ebrahimi 			switch (SYSm) {
1637*9a0e4156SSadaf Ebrahimi 				case 0: SStream_concat0(O, "apsr_nzcvq"); ARM_addSysReg(MI, ARM_SYSREG_APSR_NZCVQ); return;
1638*9a0e4156SSadaf Ebrahimi 				case 1: SStream_concat0(O, "iapsr_nzcvq"); ARM_addSysReg(MI, ARM_SYSREG_IAPSR_NZCVQ); return;
1639*9a0e4156SSadaf Ebrahimi 				case 2: SStream_concat0(O, "eapsr_nzcvq"); ARM_addSysReg(MI, ARM_SYSREG_EAPSR_NZCVQ); return;
1640*9a0e4156SSadaf Ebrahimi 				case 3: SStream_concat0(O, "xpsr_nzcvq"); ARM_addSysReg(MI, ARM_SYSREG_XPSR_NZCVQ); return;
1641*9a0e4156SSadaf Ebrahimi 			}
1642*9a0e4156SSadaf Ebrahimi 		}
1643*9a0e4156SSadaf Ebrahimi 
1644*9a0e4156SSadaf Ebrahimi 
1645*9a0e4156SSadaf Ebrahimi 		switch (SYSm) {
1646*9a0e4156SSadaf Ebrahimi 			default: //llvm_unreachable("Unexpected mask value!");
1647*9a0e4156SSadaf Ebrahimi 			case  0: SStream_concat0(O, "apsr"); ARM_addSysReg(MI, ARM_SYSREG_APSR); return;
1648*9a0e4156SSadaf Ebrahimi 			case  1: SStream_concat0(O, "iapsr"); ARM_addSysReg(MI, ARM_SYSREG_IAPSR); return;
1649*9a0e4156SSadaf Ebrahimi 			case  2: SStream_concat0(O, "eapsr"); ARM_addSysReg(MI, ARM_SYSREG_EAPSR); return;
1650*9a0e4156SSadaf Ebrahimi 			case  3: SStream_concat0(O, "xpsr"); ARM_addSysReg(MI, ARM_SYSREG_XPSR); return;
1651*9a0e4156SSadaf Ebrahimi 			case  5: SStream_concat0(O, "ipsr"); ARM_addSysReg(MI, ARM_SYSREG_IPSR); return;
1652*9a0e4156SSadaf Ebrahimi 			case  6: SStream_concat0(O, "epsr"); ARM_addSysReg(MI, ARM_SYSREG_EPSR); return;
1653*9a0e4156SSadaf Ebrahimi 			case  7: SStream_concat0(O, "iepsr"); ARM_addSysReg(MI, ARM_SYSREG_IEPSR); return;
1654*9a0e4156SSadaf Ebrahimi 			case  8: SStream_concat0(O, "msp"); ARM_addSysReg(MI, ARM_SYSREG_MSP); return;
1655*9a0e4156SSadaf Ebrahimi 			case  9: SStream_concat0(O, "psp"); ARM_addSysReg(MI, ARM_SYSREG_PSP); return;
1656*9a0e4156SSadaf Ebrahimi 			case 16: SStream_concat0(O, "primask"); ARM_addSysReg(MI, ARM_SYSREG_PRIMASK); return;
1657*9a0e4156SSadaf Ebrahimi 			case 17: SStream_concat0(O, "basepri"); ARM_addSysReg(MI, ARM_SYSREG_BASEPRI); return;
1658*9a0e4156SSadaf Ebrahimi 			case 18: SStream_concat0(O, "basepri_max"); ARM_addSysReg(MI, ARM_SYSREG_BASEPRI_MAX); return;
1659*9a0e4156SSadaf Ebrahimi 			case 19: SStream_concat0(O, "faultmask"); ARM_addSysReg(MI, ARM_SYSREG_FAULTMASK); return;
1660*9a0e4156SSadaf Ebrahimi 			case 20: SStream_concat0(O, "control"); ARM_addSysReg(MI, ARM_SYSREG_CONTROL); return;
1661*9a0e4156SSadaf Ebrahimi 		}
1662*9a0e4156SSadaf Ebrahimi 	}
1663*9a0e4156SSadaf Ebrahimi 
1664*9a0e4156SSadaf Ebrahimi 	// As special cases, CPSR_f, CPSR_s and CPSR_fs prefer printing as
1665*9a0e4156SSadaf Ebrahimi 	// APSR_nzcvq, APSR_g and APSRnzcvqg, respectively.
1666*9a0e4156SSadaf Ebrahimi 	if (!SpecRegRBit && (Mask == 8 || Mask == 4 || Mask == 12)) {
1667*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "apsr_");
1668*9a0e4156SSadaf Ebrahimi 		switch (Mask) {
1669*9a0e4156SSadaf Ebrahimi 			default: // llvm_unreachable("Unexpected mask value!");
1670*9a0e4156SSadaf Ebrahimi 			case 4:  SStream_concat0(O, "g"); ARM_addSysReg(MI, ARM_SYSREG_APSR_G); return;
1671*9a0e4156SSadaf Ebrahimi 			case 8:  SStream_concat0(O, "nzcvq"); ARM_addSysReg(MI, ARM_SYSREG_APSR_NZCVQ); return;
1672*9a0e4156SSadaf Ebrahimi 			case 12: SStream_concat0(O, "nzcvqg"); ARM_addSysReg(MI, ARM_SYSREG_APSR_NZCVQG); return;
1673*9a0e4156SSadaf Ebrahimi 		}
1674*9a0e4156SSadaf Ebrahimi 	}
1675*9a0e4156SSadaf Ebrahimi 
1676*9a0e4156SSadaf Ebrahimi 	reg = 0;
1677*9a0e4156SSadaf Ebrahimi 	if (SpecRegRBit) {
1678*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "spsr");
1679*9a0e4156SSadaf Ebrahimi 		if (Mask) {
1680*9a0e4156SSadaf Ebrahimi 			SStream_concat0(O, "_");
1681*9a0e4156SSadaf Ebrahimi 			if (Mask & 8) {
1682*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "f");
1683*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_SPSR_F;
1684*9a0e4156SSadaf Ebrahimi 			}
1685*9a0e4156SSadaf Ebrahimi 
1686*9a0e4156SSadaf Ebrahimi 			if (Mask & 4) {
1687*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "s");
1688*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_SPSR_S;
1689*9a0e4156SSadaf Ebrahimi 			}
1690*9a0e4156SSadaf Ebrahimi 
1691*9a0e4156SSadaf Ebrahimi 			if (Mask & 2) {
1692*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "x");
1693*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_SPSR_X;
1694*9a0e4156SSadaf Ebrahimi 			}
1695*9a0e4156SSadaf Ebrahimi 
1696*9a0e4156SSadaf Ebrahimi 			if (Mask & 1) {
1697*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "c");
1698*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_SPSR_C;
1699*9a0e4156SSadaf Ebrahimi 			}
1700*9a0e4156SSadaf Ebrahimi 			ARM_addSysReg(MI, reg);
1701*9a0e4156SSadaf Ebrahimi 		}
1702*9a0e4156SSadaf Ebrahimi 	} else {
1703*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "cpsr");
1704*9a0e4156SSadaf Ebrahimi 		if (Mask) {
1705*9a0e4156SSadaf Ebrahimi 			SStream_concat0(O, "_");
1706*9a0e4156SSadaf Ebrahimi 			if (Mask & 8) {
1707*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "f");
1708*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_CPSR_F;
1709*9a0e4156SSadaf Ebrahimi 			}
1710*9a0e4156SSadaf Ebrahimi 
1711*9a0e4156SSadaf Ebrahimi 			if (Mask & 4) {
1712*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "s");
1713*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_CPSR_S;
1714*9a0e4156SSadaf Ebrahimi 			}
1715*9a0e4156SSadaf Ebrahimi 
1716*9a0e4156SSadaf Ebrahimi 			if (Mask & 2) {
1717*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "x");
1718*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_CPSR_X;
1719*9a0e4156SSadaf Ebrahimi 			}
1720*9a0e4156SSadaf Ebrahimi 
1721*9a0e4156SSadaf Ebrahimi 			if (Mask & 1) {
1722*9a0e4156SSadaf Ebrahimi 				SStream_concat0(O, "c");
1723*9a0e4156SSadaf Ebrahimi 				reg += ARM_SYSREG_CPSR_C;
1724*9a0e4156SSadaf Ebrahimi 			}
1725*9a0e4156SSadaf Ebrahimi 			ARM_addSysReg(MI, reg);
1726*9a0e4156SSadaf Ebrahimi 		}
1727*9a0e4156SSadaf Ebrahimi 	}
1728*9a0e4156SSadaf Ebrahimi }
1729*9a0e4156SSadaf Ebrahimi 
printBankedRegOperand(MCInst * MI,unsigned OpNum,SStream * O)1730*9a0e4156SSadaf Ebrahimi static void printBankedRegOperand(MCInst *MI, unsigned OpNum, SStream *O)
1731*9a0e4156SSadaf Ebrahimi {
1732*9a0e4156SSadaf Ebrahimi 	uint32_t Banked = (uint32_t)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1733*9a0e4156SSadaf Ebrahimi 	uint32_t R = (Banked & 0x20) >> 5;
1734*9a0e4156SSadaf Ebrahimi 	uint32_t SysM = Banked & 0x1f;
1735*9a0e4156SSadaf Ebrahimi 	const char *RegNames[] = {
1736*9a0e4156SSadaf Ebrahimi 		"r8_usr", "r9_usr", "r10_usr", "r11_usr", "r12_usr", "sp_usr", "lr_usr", "",
1737*9a0e4156SSadaf Ebrahimi 		"r8_fiq", "r9_fiq", "r10_fiq", "r11_fiq", "r12_fiq", "sp_fiq", "lr_fiq", "",
1738*9a0e4156SSadaf Ebrahimi 		"lr_irq", "sp_irq", "lr_svc",  "sp_svc",  "lr_abt",  "sp_abt", "lr_und", "sp_und",
1739*9a0e4156SSadaf Ebrahimi 		"",       "",       "",        "",        "lr_mon",  "sp_mon", "elr_hyp", "sp_hyp"
1740*9a0e4156SSadaf Ebrahimi 	};
1741*9a0e4156SSadaf Ebrahimi 	arm_sysreg RegIds[] = {
1742*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_R8_USR, ARM_SYSREG_R9_USR, ARM_SYSREG_R10_USR,
1743*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_R11_USR, ARM_SYSREG_R12_USR, ARM_SYSREG_SP_USR,
1744*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_LR_USR, 0, ARM_SYSREG_R8_FIQ, ARM_SYSREG_R9_FIQ,
1745*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_R10_FIQ, ARM_SYSREG_R11_FIQ, ARM_SYSREG_R12_FIQ,
1746*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_SP_FIQ, ARM_SYSREG_LR_FIQ, 0, ARM_SYSREG_LR_IRQ,
1747*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_SP_IRQ, ARM_SYSREG_LR_SVC, ARM_SYSREG_SP_SVC,
1748*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_LR_ABT, ARM_SYSREG_SP_ABT, ARM_SYSREG_LR_UND,
1749*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_SP_UND, 0, 0, 0, 0, ARM_SYSREG_LR_MON, ARM_SYSREG_SP_MON,
1750*9a0e4156SSadaf Ebrahimi 		ARM_SYSREG_ELR_HYP, ARM_SYSREG_SP_HYP,
1751*9a0e4156SSadaf Ebrahimi 	};
1752*9a0e4156SSadaf Ebrahimi 	const char *Name = RegNames[SysM];
1753*9a0e4156SSadaf Ebrahimi 
1754*9a0e4156SSadaf Ebrahimi 	// Nothing much we can do about this, the encodings are specified in B9.2.3 of
1755*9a0e4156SSadaf Ebrahimi 	// the ARM ARM v7C, and are all over the shop.
1756*9a0e4156SSadaf Ebrahimi 	if (R) {
1757*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "SPSR_");
1758*9a0e4156SSadaf Ebrahimi 
1759*9a0e4156SSadaf Ebrahimi 		switch(SysM) {
1760*9a0e4156SSadaf Ebrahimi 			default: // llvm_unreachable("Invalid banked SPSR register");
1761*9a0e4156SSadaf Ebrahimi 			case 0x0e: SStream_concat0(O, "fiq"); ARM_addSysReg(MI, ARM_SYSREG_SPSR_FIQ); return;
1762*9a0e4156SSadaf Ebrahimi 			case 0x10: SStream_concat0(O, "irq"); ARM_addSysReg(MI, ARM_SYSREG_SPSR_IRQ); return;
1763*9a0e4156SSadaf Ebrahimi 			case 0x12: SStream_concat0(O, "svc"); ARM_addSysReg(MI, ARM_SYSREG_SPSR_SVC); return;
1764*9a0e4156SSadaf Ebrahimi 			case 0x14: SStream_concat0(O, "abt"); ARM_addSysReg(MI, ARM_SYSREG_SPSR_ABT); return;
1765*9a0e4156SSadaf Ebrahimi 			case 0x16: SStream_concat0(O, "und"); ARM_addSysReg(MI, ARM_SYSREG_SPSR_UND); return;
1766*9a0e4156SSadaf Ebrahimi 			case 0x1c: SStream_concat0(O, "mon"); ARM_addSysReg(MI, ARM_SYSREG_SPSR_MON); return;
1767*9a0e4156SSadaf Ebrahimi 			case 0x1e: SStream_concat0(O, "hyp"); ARM_addSysReg(MI, ARM_SYSREG_SPSR_HYP); return;
1768*9a0e4156SSadaf Ebrahimi 		}
1769*9a0e4156SSadaf Ebrahimi 	}
1770*9a0e4156SSadaf Ebrahimi 
1771*9a0e4156SSadaf Ebrahimi 	//assert(!R && "should have dealt with SPSR regs");
1772*9a0e4156SSadaf Ebrahimi 	//assert(Name[0] && "invalid banked register operand");
1773*9a0e4156SSadaf Ebrahimi 
1774*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, Name);
1775*9a0e4156SSadaf Ebrahimi 	ARM_addSysReg(MI, RegIds[SysM]);
1776*9a0e4156SSadaf Ebrahimi }
1777*9a0e4156SSadaf Ebrahimi 
printPredicateOperand(MCInst * MI,unsigned OpNum,SStream * O)1778*9a0e4156SSadaf Ebrahimi static void printPredicateOperand(MCInst *MI, unsigned OpNum, SStream *O)
1779*9a0e4156SSadaf Ebrahimi {
1780*9a0e4156SSadaf Ebrahimi 	ARMCC_CondCodes CC = (ARMCC_CondCodes)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1781*9a0e4156SSadaf Ebrahimi 	// Handle the undefined 15 CC value here for printing so we don't abort().
1782*9a0e4156SSadaf Ebrahimi 	if ((unsigned)CC == 15) {
1783*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "<und>");
1784*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail)
1785*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.cc = ARM_CC_INVALID;
1786*9a0e4156SSadaf Ebrahimi 	} else {
1787*9a0e4156SSadaf Ebrahimi 		if (CC != ARMCC_AL) {
1788*9a0e4156SSadaf Ebrahimi 			SStream_concat0(O, ARMCC_ARMCondCodeToString(CC));
1789*9a0e4156SSadaf Ebrahimi 		}
1790*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail)
1791*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.cc = CC + 1;
1792*9a0e4156SSadaf Ebrahimi 	}
1793*9a0e4156SSadaf Ebrahimi }
1794*9a0e4156SSadaf Ebrahimi 
1795*9a0e4156SSadaf Ebrahimi // TODO: test this
printMandatoryPredicateOperand(MCInst * MI,unsigned OpNum,SStream * O)1796*9a0e4156SSadaf Ebrahimi static void printMandatoryPredicateOperand(MCInst *MI, unsigned OpNum, SStream *O)
1797*9a0e4156SSadaf Ebrahimi {
1798*9a0e4156SSadaf Ebrahimi 	ARMCC_CondCodes CC = (ARMCC_CondCodes)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1799*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ARMCC_ARMCondCodeToString(CC));
1800*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1801*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.cc = CC + 1;
1802*9a0e4156SSadaf Ebrahimi }
1803*9a0e4156SSadaf Ebrahimi 
printSBitModifierOperand(MCInst * MI,unsigned OpNum,SStream * O)1804*9a0e4156SSadaf Ebrahimi static void printSBitModifierOperand(MCInst *MI, unsigned OpNum, SStream *O)
1805*9a0e4156SSadaf Ebrahimi {
1806*9a0e4156SSadaf Ebrahimi 	if (MCOperand_getReg(MCInst_getOperand(MI, OpNum))) {
1807*9a0e4156SSadaf Ebrahimi 		//assert(MCOperand_getReg(MCInst_getOperand(MI, OpNum)) == ARM_CPSR &&
1808*9a0e4156SSadaf Ebrahimi 		//       "Expect ARM CPSR register!");
1809*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "s");
1810*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail)
1811*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.update_flags = true;
1812*9a0e4156SSadaf Ebrahimi 	}
1813*9a0e4156SSadaf Ebrahimi }
1814*9a0e4156SSadaf Ebrahimi 
printNoHashImmediate(MCInst * MI,unsigned OpNum,SStream * O)1815*9a0e4156SSadaf Ebrahimi static void printNoHashImmediate(MCInst *MI, unsigned OpNum, SStream *O)
1816*9a0e4156SSadaf Ebrahimi {
1817*9a0e4156SSadaf Ebrahimi 	unsigned tmp = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1818*9a0e4156SSadaf Ebrahimi 	printUInt32(O, tmp);
1819*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1820*9a0e4156SSadaf Ebrahimi 		if (MI->csh->doing_mem) {
1821*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count--;
1822*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].neon_lane = (int8_t)tmp;
1823*9a0e4156SSadaf Ebrahimi 			MI->ac_idx--;	// consecutive operands share the same access right
1824*9a0e4156SSadaf Ebrahimi 		} else {
1825*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1826*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = tmp;
1827*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1828*9a0e4156SSadaf Ebrahimi 		}
1829*9a0e4156SSadaf Ebrahimi 	}
1830*9a0e4156SSadaf Ebrahimi }
1831*9a0e4156SSadaf Ebrahimi 
printPImmediate(MCInst * MI,unsigned OpNum,SStream * O)1832*9a0e4156SSadaf Ebrahimi static void printPImmediate(MCInst *MI, unsigned OpNum, SStream *O)
1833*9a0e4156SSadaf Ebrahimi {
1834*9a0e4156SSadaf Ebrahimi 	unsigned imm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1835*9a0e4156SSadaf Ebrahimi 
1836*9a0e4156SSadaf Ebrahimi 	SStream_concat(O, "p%u", imm);
1837*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1838*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_PIMM;
1839*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = imm;
1840*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1841*9a0e4156SSadaf Ebrahimi 	}
1842*9a0e4156SSadaf Ebrahimi }
1843*9a0e4156SSadaf Ebrahimi 
printCImmediate(MCInst * MI,unsigned OpNum,SStream * O)1844*9a0e4156SSadaf Ebrahimi static void printCImmediate(MCInst *MI, unsigned OpNum, SStream *O)
1845*9a0e4156SSadaf Ebrahimi {
1846*9a0e4156SSadaf Ebrahimi 	unsigned imm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1847*9a0e4156SSadaf Ebrahimi 
1848*9a0e4156SSadaf Ebrahimi 	SStream_concat(O, "c%u", imm);
1849*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1850*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_CIMM;
1851*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = imm;
1852*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1853*9a0e4156SSadaf Ebrahimi 	}
1854*9a0e4156SSadaf Ebrahimi }
1855*9a0e4156SSadaf Ebrahimi 
printCoprocOptionImm(MCInst * MI,unsigned OpNum,SStream * O)1856*9a0e4156SSadaf Ebrahimi static void printCoprocOptionImm(MCInst *MI, unsigned OpNum, SStream *O)
1857*9a0e4156SSadaf Ebrahimi {
1858*9a0e4156SSadaf Ebrahimi 	unsigned tmp = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1859*9a0e4156SSadaf Ebrahimi 	if (tmp > HEX_THRESHOLD)
1860*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "{0x%x}", tmp);
1861*9a0e4156SSadaf Ebrahimi 	else
1862*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "{%u}", tmp);
1863*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1864*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1865*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = tmp;
1866*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1867*9a0e4156SSadaf Ebrahimi 	}
1868*9a0e4156SSadaf Ebrahimi }
1869*9a0e4156SSadaf Ebrahimi 
printAdrLabelOperand(MCInst * MI,unsigned OpNum,SStream * O,unsigned scale)1870*9a0e4156SSadaf Ebrahimi static void printAdrLabelOperand(MCInst *MI, unsigned OpNum, SStream *O, unsigned scale)
1871*9a0e4156SSadaf Ebrahimi {
1872*9a0e4156SSadaf Ebrahimi 	MCOperand *MO = MCInst_getOperand(MI, OpNum);
1873*9a0e4156SSadaf Ebrahimi 
1874*9a0e4156SSadaf Ebrahimi 	int32_t OffImm = (int32_t)MCOperand_getImm(MO) << scale;
1875*9a0e4156SSadaf Ebrahimi 
1876*9a0e4156SSadaf Ebrahimi 	if (OffImm == INT32_MIN) {
1877*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "#-0");
1878*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1879*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1880*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = 0;
1881*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1882*9a0e4156SSadaf Ebrahimi 		}
1883*9a0e4156SSadaf Ebrahimi 	} else {
1884*9a0e4156SSadaf Ebrahimi 		if (OffImm < 0)
1885*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, "#-0x%x", -OffImm);
1886*9a0e4156SSadaf Ebrahimi 		else {
1887*9a0e4156SSadaf Ebrahimi 			if (OffImm > HEX_THRESHOLD)
1888*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#0x%x", OffImm);
1889*9a0e4156SSadaf Ebrahimi 			else
1890*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#%u", OffImm);
1891*9a0e4156SSadaf Ebrahimi 		}
1892*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
1893*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1894*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = OffImm;
1895*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
1896*9a0e4156SSadaf Ebrahimi 		}
1897*9a0e4156SSadaf Ebrahimi 	}
1898*9a0e4156SSadaf Ebrahimi }
1899*9a0e4156SSadaf Ebrahimi 
printThumbS4ImmOperand(MCInst * MI,unsigned OpNum,SStream * O)1900*9a0e4156SSadaf Ebrahimi static void printThumbS4ImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
1901*9a0e4156SSadaf Ebrahimi {
1902*9a0e4156SSadaf Ebrahimi 	unsigned tmp = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum)) * 4;
1903*9a0e4156SSadaf Ebrahimi 
1904*9a0e4156SSadaf Ebrahimi 	printUInt32Bang(O, tmp);
1905*9a0e4156SSadaf Ebrahimi 
1906*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1907*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1908*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = tmp;
1909*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1910*9a0e4156SSadaf Ebrahimi 	}
1911*9a0e4156SSadaf Ebrahimi }
1912*9a0e4156SSadaf Ebrahimi 
printThumbSRImm(MCInst * MI,unsigned OpNum,SStream * O)1913*9a0e4156SSadaf Ebrahimi static void printThumbSRImm(MCInst *MI, unsigned OpNum, SStream *O)
1914*9a0e4156SSadaf Ebrahimi {
1915*9a0e4156SSadaf Ebrahimi 	unsigned Imm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1916*9a0e4156SSadaf Ebrahimi 	unsigned tmp = Imm == 0 ? 32 : Imm;
1917*9a0e4156SSadaf Ebrahimi 
1918*9a0e4156SSadaf Ebrahimi 	printUInt32Bang(O, tmp);
1919*9a0e4156SSadaf Ebrahimi 
1920*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
1921*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
1922*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = tmp;
1923*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
1924*9a0e4156SSadaf Ebrahimi 	}
1925*9a0e4156SSadaf Ebrahimi }
1926*9a0e4156SSadaf Ebrahimi 
printThumbITMask(MCInst * MI,unsigned OpNum,SStream * O)1927*9a0e4156SSadaf Ebrahimi static void printThumbITMask(MCInst *MI, unsigned OpNum, SStream *O)
1928*9a0e4156SSadaf Ebrahimi {
1929*9a0e4156SSadaf Ebrahimi 	// (3 - the number of trailing zeros) is the number of then / else.
1930*9a0e4156SSadaf Ebrahimi 	unsigned Mask = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
1931*9a0e4156SSadaf Ebrahimi 	unsigned Firstcond = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum-1));
1932*9a0e4156SSadaf Ebrahimi 	unsigned CondBit0 = Firstcond & 1;
1933*9a0e4156SSadaf Ebrahimi 	unsigned NumTZ = CountTrailingZeros_32(Mask);
1934*9a0e4156SSadaf Ebrahimi 	//assert(NumTZ <= 3 && "Invalid IT mask!");
1935*9a0e4156SSadaf Ebrahimi 	unsigned Pos, e;
1936*9a0e4156SSadaf Ebrahimi 	for (Pos = 3, e = NumTZ; Pos > e; --Pos) {
1937*9a0e4156SSadaf Ebrahimi 		bool T = ((Mask >> Pos) & 1) == CondBit0;
1938*9a0e4156SSadaf Ebrahimi 		if (T)
1939*9a0e4156SSadaf Ebrahimi 			SStream_concat0(O, "t");
1940*9a0e4156SSadaf Ebrahimi 		else
1941*9a0e4156SSadaf Ebrahimi 			SStream_concat0(O, "e");
1942*9a0e4156SSadaf Ebrahimi 	}
1943*9a0e4156SSadaf Ebrahimi }
1944*9a0e4156SSadaf Ebrahimi 
printThumbAddrModeRROperand(MCInst * MI,unsigned Op,SStream * O)1945*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeRROperand(MCInst *MI, unsigned Op, SStream *O)
1946*9a0e4156SSadaf Ebrahimi {
1947*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1948*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, Op + 1);
1949*9a0e4156SSadaf Ebrahimi 	unsigned RegNum;
1950*9a0e4156SSadaf Ebrahimi 
1951*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_isReg(MO1)) {   // FIXME: This is for CP entries, but isn't right.
1952*9a0e4156SSadaf Ebrahimi 		printOperand(MI, Op, O);
1953*9a0e4156SSadaf Ebrahimi 		return;
1954*9a0e4156SSadaf Ebrahimi 	}
1955*9a0e4156SSadaf Ebrahimi 
1956*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1957*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1958*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1959*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1960*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1961*9a0e4156SSadaf Ebrahimi 	RegNum = MCOperand_getReg(MO2);
1962*9a0e4156SSadaf Ebrahimi 	if (RegNum) {
1963*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ", ");
1964*9a0e4156SSadaf Ebrahimi 		printRegName(MI->csh, O, RegNum);
1965*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail)
1966*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = RegNum;
1967*9a0e4156SSadaf Ebrahimi 	}
1968*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1969*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1970*9a0e4156SSadaf Ebrahimi }
1971*9a0e4156SSadaf Ebrahimi 
printThumbAddrModeImm5SOperand(MCInst * MI,unsigned Op,SStream * O,unsigned Scale)1972*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5SOperand(MCInst *MI, unsigned Op, SStream *O,
1973*9a0e4156SSadaf Ebrahimi 		unsigned Scale)
1974*9a0e4156SSadaf Ebrahimi {
1975*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, Op);
1976*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, Op + 1);
1977*9a0e4156SSadaf Ebrahimi 	unsigned ImmOffs, tmp;
1978*9a0e4156SSadaf Ebrahimi 
1979*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_isReg(MO1)) {   // FIXME: This is for CP entries, but isn't right.
1980*9a0e4156SSadaf Ebrahimi 		printOperand(MI, Op, O);
1981*9a0e4156SSadaf Ebrahimi 		return;
1982*9a0e4156SSadaf Ebrahimi 	}
1983*9a0e4156SSadaf Ebrahimi 
1984*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
1985*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
1986*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
1987*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
1988*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
1989*9a0e4156SSadaf Ebrahimi 	ImmOffs = (unsigned int)MCOperand_getImm(MO2);
1990*9a0e4156SSadaf Ebrahimi 	if (ImmOffs) {
1991*9a0e4156SSadaf Ebrahimi 		tmp = ImmOffs * Scale;
1992*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ", ");
1993*9a0e4156SSadaf Ebrahimi 		printUInt32Bang(O, tmp);
1994*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail)
1995*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = tmp;
1996*9a0e4156SSadaf Ebrahimi 	}
1997*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
1998*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
1999*9a0e4156SSadaf Ebrahimi }
2000*9a0e4156SSadaf Ebrahimi 
printThumbAddrModeImm5S1Operand(MCInst * MI,unsigned Op,SStream * O)2001*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5S1Operand(MCInst *MI, unsigned Op, SStream *O)
2002*9a0e4156SSadaf Ebrahimi {
2003*9a0e4156SSadaf Ebrahimi 	printThumbAddrModeImm5SOperand(MI, Op, O, 1);
2004*9a0e4156SSadaf Ebrahimi }
2005*9a0e4156SSadaf Ebrahimi 
printThumbAddrModeImm5S2Operand(MCInst * MI,unsigned Op,SStream * O)2006*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5S2Operand(MCInst *MI, unsigned Op, SStream *O)
2007*9a0e4156SSadaf Ebrahimi {
2008*9a0e4156SSadaf Ebrahimi 	printThumbAddrModeImm5SOperand(MI, Op, O, 2);
2009*9a0e4156SSadaf Ebrahimi }
2010*9a0e4156SSadaf Ebrahimi 
printThumbAddrModeImm5S4Operand(MCInst * MI,unsigned Op,SStream * O)2011*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeImm5S4Operand(MCInst *MI, unsigned Op, SStream *O)
2012*9a0e4156SSadaf Ebrahimi {
2013*9a0e4156SSadaf Ebrahimi 	printThumbAddrModeImm5SOperand(MI, Op, O, 4);
2014*9a0e4156SSadaf Ebrahimi }
2015*9a0e4156SSadaf Ebrahimi 
printThumbAddrModeSPOperand(MCInst * MI,unsigned Op,SStream * O)2016*9a0e4156SSadaf Ebrahimi static void printThumbAddrModeSPOperand(MCInst *MI, unsigned Op, SStream *O)
2017*9a0e4156SSadaf Ebrahimi {
2018*9a0e4156SSadaf Ebrahimi 	printThumbAddrModeImm5SOperand(MI, Op, O, 4);
2019*9a0e4156SSadaf Ebrahimi }
2020*9a0e4156SSadaf Ebrahimi 
2021*9a0e4156SSadaf Ebrahimi // Constant shifts t2_so_reg is a 2-operand unit corresponding to the Thumb2
2022*9a0e4156SSadaf Ebrahimi // register with shift forms.
2023*9a0e4156SSadaf Ebrahimi // REG 0   0           - e.g. R5
2024*9a0e4156SSadaf Ebrahimi // REG IMM, SH_OPC     - e.g. R5, LSL #3
printT2SOOperand(MCInst * MI,unsigned OpNum,SStream * O)2025*9a0e4156SSadaf Ebrahimi static void printT2SOOperand(MCInst *MI, unsigned OpNum, SStream *O)
2026*9a0e4156SSadaf Ebrahimi {
2027*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2028*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
2029*9a0e4156SSadaf Ebrahimi 
2030*9a0e4156SSadaf Ebrahimi 	unsigned Reg = MCOperand_getReg(MO1);
2031*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg);
2032*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2033*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2034*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg;
2035*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = CS_AC_READ;
2036*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2037*9a0e4156SSadaf Ebrahimi 	}
2038*9a0e4156SSadaf Ebrahimi 
2039*9a0e4156SSadaf Ebrahimi 	// Print the shift opc.
2040*9a0e4156SSadaf Ebrahimi 	//assert(MO2.isImm() && "Not a valid t2_so_reg value!");
2041*9a0e4156SSadaf Ebrahimi 	printRegImmShift(MI, O, ARM_AM_getSORegShOp((unsigned int)MCOperand_getImm(MO2)),
2042*9a0e4156SSadaf Ebrahimi 			getSORegOffset((unsigned int)MCOperand_getImm(MO2)));
2043*9a0e4156SSadaf Ebrahimi }
2044*9a0e4156SSadaf Ebrahimi 
printAddrModeImm12Operand(MCInst * MI,unsigned OpNum,SStream * O,bool AlwaysPrintImm0)2045*9a0e4156SSadaf Ebrahimi static void printAddrModeImm12Operand(MCInst *MI, unsigned OpNum,
2046*9a0e4156SSadaf Ebrahimi 		SStream *O, bool AlwaysPrintImm0)
2047*9a0e4156SSadaf Ebrahimi {
2048*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2049*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
2050*9a0e4156SSadaf Ebrahimi 	int32_t OffImm;
2051*9a0e4156SSadaf Ebrahimi 	bool isSub;
2052*9a0e4156SSadaf Ebrahimi 
2053*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_isReg(MO1)) {   // FIXME: This is for CP entries, but isn't right.
2054*9a0e4156SSadaf Ebrahimi 		printOperand(MI, OpNum, O);
2055*9a0e4156SSadaf Ebrahimi 		return;
2056*9a0e4156SSadaf Ebrahimi 	}
2057*9a0e4156SSadaf Ebrahimi 
2058*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
2059*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
2060*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
2061*9a0e4156SSadaf Ebrahimi 
2062*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2063*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
2064*9a0e4156SSadaf Ebrahimi 
2065*9a0e4156SSadaf Ebrahimi 	OffImm = (int32_t)MCOperand_getImm(MO2);
2066*9a0e4156SSadaf Ebrahimi 	isSub = OffImm < 0;
2067*9a0e4156SSadaf Ebrahimi 	// Special value for #-0. All others are normal.
2068*9a0e4156SSadaf Ebrahimi 	if (OffImm == INT32_MIN)
2069*9a0e4156SSadaf Ebrahimi 		OffImm = 0;
2070*9a0e4156SSadaf Ebrahimi 	if (isSub) {
2071*9a0e4156SSadaf Ebrahimi 		if (OffImm < -HEX_THRESHOLD)
2072*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #-0x%x", -OffImm);
2073*9a0e4156SSadaf Ebrahimi 		else
2074*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #-%u", -OffImm);
2075*9a0e4156SSadaf Ebrahimi 	} else if (AlwaysPrintImm0 || OffImm > 0) {
2076*9a0e4156SSadaf Ebrahimi 		if (OffImm >= 0) {
2077*9a0e4156SSadaf Ebrahimi 			if (OffImm > HEX_THRESHOLD)
2078*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, ", #0x%x", OffImm);
2079*9a0e4156SSadaf Ebrahimi 			else
2080*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, ", #%u", OffImm);
2081*9a0e4156SSadaf Ebrahimi 		} else {
2082*9a0e4156SSadaf Ebrahimi 			if (OffImm < -HEX_THRESHOLD)
2083*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, ", #-0x%x", -OffImm);
2084*9a0e4156SSadaf Ebrahimi 			else
2085*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, ", #-%u", -OffImm);
2086*9a0e4156SSadaf Ebrahimi 		}
2087*9a0e4156SSadaf Ebrahimi 	}
2088*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2089*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = OffImm;
2090*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
2091*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
2092*9a0e4156SSadaf Ebrahimi }
2093*9a0e4156SSadaf Ebrahimi 
printT2AddrModeImm8Operand(MCInst * MI,unsigned OpNum,SStream * O,bool AlwaysPrintImm0)2094*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8Operand(MCInst *MI, unsigned OpNum, SStream *O,
2095*9a0e4156SSadaf Ebrahimi 		bool AlwaysPrintImm0)
2096*9a0e4156SSadaf Ebrahimi {
2097*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2098*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
2099*9a0e4156SSadaf Ebrahimi 	int32_t OffImm;
2100*9a0e4156SSadaf Ebrahimi 	bool isSub;
2101*9a0e4156SSadaf Ebrahimi 
2102*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
2103*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
2104*9a0e4156SSadaf Ebrahimi 
2105*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
2106*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2107*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
2108*9a0e4156SSadaf Ebrahimi 
2109*9a0e4156SSadaf Ebrahimi 	OffImm = (int32_t)MCOperand_getImm(MO2);
2110*9a0e4156SSadaf Ebrahimi 	isSub = OffImm < 0;
2111*9a0e4156SSadaf Ebrahimi 	// Don't print +0.
2112*9a0e4156SSadaf Ebrahimi 	if (OffImm == INT32_MIN)
2113*9a0e4156SSadaf Ebrahimi 		OffImm = 0;
2114*9a0e4156SSadaf Ebrahimi 
2115*9a0e4156SSadaf Ebrahimi 	if (isSub)
2116*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", #-0x%x", -OffImm);
2117*9a0e4156SSadaf Ebrahimi 	else if (AlwaysPrintImm0 || OffImm > 0) {
2118*9a0e4156SSadaf Ebrahimi 		if (OffImm > HEX_THRESHOLD)
2119*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #0x%x", OffImm);
2120*9a0e4156SSadaf Ebrahimi 		else
2121*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #%u", OffImm);
2122*9a0e4156SSadaf Ebrahimi 	}
2123*9a0e4156SSadaf Ebrahimi 
2124*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2125*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = OffImm;
2126*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
2127*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
2128*9a0e4156SSadaf Ebrahimi }
2129*9a0e4156SSadaf Ebrahimi 
printT2AddrModeImm8s4Operand(MCInst * MI,unsigned OpNum,SStream * O,bool AlwaysPrintImm0)2130*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8s4Operand(MCInst *MI,
2131*9a0e4156SSadaf Ebrahimi 		unsigned OpNum, SStream *O, bool AlwaysPrintImm0)
2132*9a0e4156SSadaf Ebrahimi {
2133*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2134*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
2135*9a0e4156SSadaf Ebrahimi 	int32_t OffImm;
2136*9a0e4156SSadaf Ebrahimi 	bool isSub;
2137*9a0e4156SSadaf Ebrahimi 
2138*9a0e4156SSadaf Ebrahimi 	if (!MCOperand_isReg(MO1)) {   //  For label symbolic references.
2139*9a0e4156SSadaf Ebrahimi 		printOperand(MI, OpNum, O);
2140*9a0e4156SSadaf Ebrahimi 		return;
2141*9a0e4156SSadaf Ebrahimi 	}
2142*9a0e4156SSadaf Ebrahimi 
2143*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
2144*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
2145*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
2146*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2147*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
2148*9a0e4156SSadaf Ebrahimi 
2149*9a0e4156SSadaf Ebrahimi 	OffImm = (int32_t)MCOperand_getImm(MO2);
2150*9a0e4156SSadaf Ebrahimi 	isSub = OffImm < 0;
2151*9a0e4156SSadaf Ebrahimi 
2152*9a0e4156SSadaf Ebrahimi 	//assert(((OffImm & 0x3) == 0) && "Not a valid immediate!");
2153*9a0e4156SSadaf Ebrahimi 
2154*9a0e4156SSadaf Ebrahimi 	// Don't print +0.
2155*9a0e4156SSadaf Ebrahimi 	if (OffImm == INT32_MIN)
2156*9a0e4156SSadaf Ebrahimi 		OffImm = 0;
2157*9a0e4156SSadaf Ebrahimi 	if (isSub) {
2158*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, ", #-0x%x", -OffImm);
2159*9a0e4156SSadaf Ebrahimi 	} else if (AlwaysPrintImm0 || OffImm > 0) {
2160*9a0e4156SSadaf Ebrahimi 		if (OffImm > HEX_THRESHOLD)
2161*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #0x%x", OffImm);
2162*9a0e4156SSadaf Ebrahimi 		else
2163*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, ", #%u", OffImm);
2164*9a0e4156SSadaf Ebrahimi 	}
2165*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2166*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = OffImm;
2167*9a0e4156SSadaf Ebrahimi 
2168*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
2169*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
2170*9a0e4156SSadaf Ebrahimi }
2171*9a0e4156SSadaf Ebrahimi 
printT2AddrModeImm0_1020s4Operand(MCInst * MI,unsigned OpNum,SStream * O)2172*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm0_1020s4Operand(MCInst *MI, unsigned OpNum, SStream *O)
2173*9a0e4156SSadaf Ebrahimi {
2174*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2175*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
2176*9a0e4156SSadaf Ebrahimi 	unsigned tmp;
2177*9a0e4156SSadaf Ebrahimi 
2178*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
2179*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
2180*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
2181*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2182*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
2183*9a0e4156SSadaf Ebrahimi 	if (MCOperand_getImm(MO2)) {
2184*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ", ");
2185*9a0e4156SSadaf Ebrahimi 		tmp = (unsigned int)MCOperand_getImm(MO2) * 4;
2186*9a0e4156SSadaf Ebrahimi 		printUInt32Bang(O, tmp);
2187*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail)
2188*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.disp = tmp;
2189*9a0e4156SSadaf Ebrahimi 	}
2190*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
2191*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
2192*9a0e4156SSadaf Ebrahimi }
2193*9a0e4156SSadaf Ebrahimi 
printT2AddrModeImm8OffsetOperand(MCInst * MI,unsigned OpNum,SStream * O)2194*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8OffsetOperand(MCInst *MI,
2195*9a0e4156SSadaf Ebrahimi 		unsigned OpNum, SStream *O)
2196*9a0e4156SSadaf Ebrahimi {
2197*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2198*9a0e4156SSadaf Ebrahimi 	int32_t OffImm = (int32_t)MCOperand_getImm(MO1);
2199*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2200*9a0e4156SSadaf Ebrahimi 	if (OffImm == INT32_MIN) {
2201*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "#-0");
2202*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
2203*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2204*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = 0;
2205*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
2206*9a0e4156SSadaf Ebrahimi 		}
2207*9a0e4156SSadaf Ebrahimi 	} else {
2208*9a0e4156SSadaf Ebrahimi 		printInt32Bang(O, OffImm);
2209*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
2210*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2211*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = OffImm;
2212*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
2213*9a0e4156SSadaf Ebrahimi 		}
2214*9a0e4156SSadaf Ebrahimi 	}
2215*9a0e4156SSadaf Ebrahimi }
2216*9a0e4156SSadaf Ebrahimi 
printT2AddrModeImm8s4OffsetOperand(MCInst * MI,unsigned OpNum,SStream * O)2217*9a0e4156SSadaf Ebrahimi static void printT2AddrModeImm8s4OffsetOperand(MCInst *MI,
2218*9a0e4156SSadaf Ebrahimi 		unsigned OpNum, SStream *O)
2219*9a0e4156SSadaf Ebrahimi {
2220*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2221*9a0e4156SSadaf Ebrahimi 	int32_t OffImm = (int32_t)MCOperand_getImm(MO1);
2222*9a0e4156SSadaf Ebrahimi 
2223*9a0e4156SSadaf Ebrahimi 	//assert(((OffImm & 0x3) == 0) && "Not a valid immediate!");
2224*9a0e4156SSadaf Ebrahimi 
2225*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2226*9a0e4156SSadaf Ebrahimi 	if (OffImm == INT32_MIN) {
2227*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, "#-0");
2228*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
2229*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2230*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = 0;
2231*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
2232*9a0e4156SSadaf Ebrahimi 		}
2233*9a0e4156SSadaf Ebrahimi 	} else {
2234*9a0e4156SSadaf Ebrahimi 		printInt32Bang(O, OffImm);
2235*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
2236*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2237*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = OffImm;
2238*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
2239*9a0e4156SSadaf Ebrahimi 		}
2240*9a0e4156SSadaf Ebrahimi 	}
2241*9a0e4156SSadaf Ebrahimi }
2242*9a0e4156SSadaf Ebrahimi 
printT2AddrModeSoRegOperand(MCInst * MI,unsigned OpNum,SStream * O)2243*9a0e4156SSadaf Ebrahimi static void printT2AddrModeSoRegOperand(MCInst *MI,
2244*9a0e4156SSadaf Ebrahimi 		unsigned OpNum, SStream *O)
2245*9a0e4156SSadaf Ebrahimi {
2246*9a0e4156SSadaf Ebrahimi 	MCOperand *MO1 = MCInst_getOperand(MI, OpNum);
2247*9a0e4156SSadaf Ebrahimi 	MCOperand *MO2 = MCInst_getOperand(MI, OpNum+1);
2248*9a0e4156SSadaf Ebrahimi 	MCOperand *MO3 = MCInst_getOperand(MI, OpNum+2);
2249*9a0e4156SSadaf Ebrahimi 	unsigned ShAmt;
2250*9a0e4156SSadaf Ebrahimi 
2251*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[");
2252*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, true);
2253*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO1));
2254*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2255*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.base = MCOperand_getReg(MO1);
2256*9a0e4156SSadaf Ebrahimi 
2257*9a0e4156SSadaf Ebrahimi 	//assert(MCOperand_getReg(MO2.getReg() && "Invalid so_reg load / store address!");
2258*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2259*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MO2));
2260*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail)
2261*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].mem.index = MCOperand_getReg(MO2);
2262*9a0e4156SSadaf Ebrahimi 
2263*9a0e4156SSadaf Ebrahimi 	ShAmt = (unsigned int)MCOperand_getImm(MO3);
2264*9a0e4156SSadaf Ebrahimi 	if (ShAmt) {
2265*9a0e4156SSadaf Ebrahimi 		//assert(ShAmt <= 3 && "Not a valid Thumb2 addressing mode!");
2266*9a0e4156SSadaf Ebrahimi 		SStream_concat0(O, ", lsl ");
2267*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%d", ShAmt);
2268*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
2269*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.type = ARM_SFT_LSL;
2270*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].shift.value = ShAmt;
2271*9a0e4156SSadaf Ebrahimi 		}
2272*9a0e4156SSadaf Ebrahimi 	}
2273*9a0e4156SSadaf Ebrahimi 
2274*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "]");
2275*9a0e4156SSadaf Ebrahimi 	set_mem_access(MI, false);
2276*9a0e4156SSadaf Ebrahimi }
2277*9a0e4156SSadaf Ebrahimi 
printFPImmOperand(MCInst * MI,unsigned OpNum,SStream * O)2278*9a0e4156SSadaf Ebrahimi static void printFPImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
2279*9a0e4156SSadaf Ebrahimi {
2280*9a0e4156SSadaf Ebrahimi 	MCOperand *MO = MCInst_getOperand(MI, OpNum);
2281*9a0e4156SSadaf Ebrahimi 
2282*9a0e4156SSadaf Ebrahimi #if defined(_KERNEL_MODE)
2283*9a0e4156SSadaf Ebrahimi 	// Issue #681: Windows kernel does not support formatting float point
2284*9a0e4156SSadaf Ebrahimi 	SStream_concat(O, "#<float_point_unsupported>");
2285*9a0e4156SSadaf Ebrahimi #else
2286*9a0e4156SSadaf Ebrahimi 	SStream_concat(O, "#%e", getFPImmFloat((unsigned int)MCOperand_getImm(MO)));
2287*9a0e4156SSadaf Ebrahimi #endif
2288*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2289*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_FP;
2290*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].fp = getFPImmFloat((unsigned int)MCOperand_getImm(MO));
2291*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2292*9a0e4156SSadaf Ebrahimi 	}
2293*9a0e4156SSadaf Ebrahimi }
2294*9a0e4156SSadaf Ebrahimi 
printNEONModImmOperand(MCInst * MI,unsigned OpNum,SStream * O)2295*9a0e4156SSadaf Ebrahimi static void printNEONModImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
2296*9a0e4156SSadaf Ebrahimi {
2297*9a0e4156SSadaf Ebrahimi 	unsigned EncodedImm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
2298*9a0e4156SSadaf Ebrahimi 	unsigned EltBits;
2299*9a0e4156SSadaf Ebrahimi 	uint64_t Val = ARM_AM_decodeNEONModImm(EncodedImm, &EltBits);
2300*9a0e4156SSadaf Ebrahimi 	if (Val > HEX_THRESHOLD)
2301*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#0x%"PRIx64, Val);
2302*9a0e4156SSadaf Ebrahimi 	else
2303*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "#%"PRIu64, Val);
2304*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2305*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2306*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = (unsigned int)Val;
2307*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2308*9a0e4156SSadaf Ebrahimi 	}
2309*9a0e4156SSadaf Ebrahimi }
2310*9a0e4156SSadaf Ebrahimi 
printImmPlusOneOperand(MCInst * MI,unsigned OpNum,SStream * O)2311*9a0e4156SSadaf Ebrahimi static void printImmPlusOneOperand(MCInst *MI, unsigned OpNum, SStream *O)
2312*9a0e4156SSadaf Ebrahimi {
2313*9a0e4156SSadaf Ebrahimi 	unsigned Imm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
2314*9a0e4156SSadaf Ebrahimi 	printUInt32Bang(O, Imm + 1);
2315*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2316*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2317*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = Imm + 1;
2318*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2319*9a0e4156SSadaf Ebrahimi 	}
2320*9a0e4156SSadaf Ebrahimi }
2321*9a0e4156SSadaf Ebrahimi 
printRotImmOperand(MCInst * MI,unsigned OpNum,SStream * O)2322*9a0e4156SSadaf Ebrahimi static void printRotImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
2323*9a0e4156SSadaf Ebrahimi {
2324*9a0e4156SSadaf Ebrahimi 	unsigned Imm = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
2325*9a0e4156SSadaf Ebrahimi 	if (Imm == 0)
2326*9a0e4156SSadaf Ebrahimi 		return;
2327*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ror #");
2328*9a0e4156SSadaf Ebrahimi 	switch (Imm) {
2329*9a0e4156SSadaf Ebrahimi 		default: //assert (0 && "illegal ror immediate!");
2330*9a0e4156SSadaf Ebrahimi 		case 1: SStream_concat0(O, "8"); break;
2331*9a0e4156SSadaf Ebrahimi 		case 2: SStream_concat0(O, "16"); break;
2332*9a0e4156SSadaf Ebrahimi 		case 3: SStream_concat0(O, "24"); break;
2333*9a0e4156SSadaf Ebrahimi 	}
2334*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2335*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.type = ARM_SFT_ROR;
2336*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].shift.value = Imm * 8;
2337*9a0e4156SSadaf Ebrahimi 	}
2338*9a0e4156SSadaf Ebrahimi }
2339*9a0e4156SSadaf Ebrahimi 
printModImmOperand(MCInst * MI,unsigned OpNum,SStream * O)2340*9a0e4156SSadaf Ebrahimi static void printModImmOperand(MCInst *MI, unsigned OpNum, SStream *O)
2341*9a0e4156SSadaf Ebrahimi {
2342*9a0e4156SSadaf Ebrahimi 	MCOperand *Op = MCInst_getOperand(MI, OpNum);
2343*9a0e4156SSadaf Ebrahimi 	unsigned Bits = MCOperand_getImm(Op) & 0xFF;
2344*9a0e4156SSadaf Ebrahimi 	unsigned Rot = (MCOperand_getImm(Op) & 0xF00) >> 7;
2345*9a0e4156SSadaf Ebrahimi 	int32_t Rotated;
2346*9a0e4156SSadaf Ebrahimi 
2347*9a0e4156SSadaf Ebrahimi 	bool  PrintUnsigned = false;
2348*9a0e4156SSadaf Ebrahimi 	switch (MCInst_getOpcode(MI)) {
2349*9a0e4156SSadaf Ebrahimi 		case ARM_MOVi:
2350*9a0e4156SSadaf Ebrahimi 			// Movs to PC should be treated unsigned
2351*9a0e4156SSadaf Ebrahimi 			PrintUnsigned = (MCOperand_getReg(MCInst_getOperand(MI, OpNum - 1)) == ARM_PC);
2352*9a0e4156SSadaf Ebrahimi 			break;
2353*9a0e4156SSadaf Ebrahimi 		case ARM_MSRi:
2354*9a0e4156SSadaf Ebrahimi 			// Movs to special registers should be treated unsigned
2355*9a0e4156SSadaf Ebrahimi 			PrintUnsigned = true;
2356*9a0e4156SSadaf Ebrahimi 			break;
2357*9a0e4156SSadaf Ebrahimi 	}
2358*9a0e4156SSadaf Ebrahimi 
2359*9a0e4156SSadaf Ebrahimi 	Rotated = rotr32(Bits, Rot);
2360*9a0e4156SSadaf Ebrahimi 	if (getSOImmVal(Rotated) == MCOperand_getImm(Op)) {
2361*9a0e4156SSadaf Ebrahimi 		// #rot has the least possible value
2362*9a0e4156SSadaf Ebrahimi 		if (PrintUnsigned) {
2363*9a0e4156SSadaf Ebrahimi 			if (Rotated > HEX_THRESHOLD || Rotated < -HEX_THRESHOLD)
2364*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#0x%x", Rotated);
2365*9a0e4156SSadaf Ebrahimi 			else
2366*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#%u", Rotated);
2367*9a0e4156SSadaf Ebrahimi 		} else if (Rotated >= 0) {
2368*9a0e4156SSadaf Ebrahimi 			if (Rotated > HEX_THRESHOLD)
2369*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#0x%x", Rotated);
2370*9a0e4156SSadaf Ebrahimi 			else
2371*9a0e4156SSadaf Ebrahimi 				SStream_concat(O, "#%u", Rotated);
2372*9a0e4156SSadaf Ebrahimi 		} else {
2373*9a0e4156SSadaf Ebrahimi 			SStream_concat(O, "#0x%x", Rotated);
2374*9a0e4156SSadaf Ebrahimi 		}
2375*9a0e4156SSadaf Ebrahimi 		if (MI->csh->detail) {
2376*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2377*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = Rotated;
2378*9a0e4156SSadaf Ebrahimi 			MI->flat_insn->detail->arm.op_count++;
2379*9a0e4156SSadaf Ebrahimi 		}
2380*9a0e4156SSadaf Ebrahimi 		return;
2381*9a0e4156SSadaf Ebrahimi 	}
2382*9a0e4156SSadaf Ebrahimi 
2383*9a0e4156SSadaf Ebrahimi 	// Explicit #bits, #rot implied
2384*9a0e4156SSadaf Ebrahimi 	SStream_concat(O, "#%u, #%u", Bits, Rot);
2385*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2386*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2387*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = Bits;
2388*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2389*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2390*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = Rot;
2391*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2392*9a0e4156SSadaf Ebrahimi 	}
2393*9a0e4156SSadaf Ebrahimi }
2394*9a0e4156SSadaf Ebrahimi 
printFBits16(MCInst * MI,unsigned OpNum,SStream * O)2395*9a0e4156SSadaf Ebrahimi static void printFBits16(MCInst *MI, unsigned OpNum, SStream *O)
2396*9a0e4156SSadaf Ebrahimi {
2397*9a0e4156SSadaf Ebrahimi 	unsigned tmp;
2398*9a0e4156SSadaf Ebrahimi 
2399*9a0e4156SSadaf Ebrahimi 	tmp = 16 - (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
2400*9a0e4156SSadaf Ebrahimi 	printUInt32Bang(O, tmp);
2401*9a0e4156SSadaf Ebrahimi 
2402*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2403*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2404*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = tmp;
2405*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2406*9a0e4156SSadaf Ebrahimi 	}
2407*9a0e4156SSadaf Ebrahimi }
2408*9a0e4156SSadaf Ebrahimi 
printFBits32(MCInst * MI,unsigned OpNum,SStream * O)2409*9a0e4156SSadaf Ebrahimi static void printFBits32(MCInst *MI, unsigned OpNum, SStream *O)
2410*9a0e4156SSadaf Ebrahimi {
2411*9a0e4156SSadaf Ebrahimi 	unsigned tmp;
2412*9a0e4156SSadaf Ebrahimi 
2413*9a0e4156SSadaf Ebrahimi 	tmp = 32 - (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
2414*9a0e4156SSadaf Ebrahimi 	printUInt32Bang(O, tmp);
2415*9a0e4156SSadaf Ebrahimi 
2416*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2417*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_IMM;
2418*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].imm = tmp;
2419*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2420*9a0e4156SSadaf Ebrahimi 	}
2421*9a0e4156SSadaf Ebrahimi }
2422*9a0e4156SSadaf Ebrahimi 
printVectorIndex(MCInst * MI,unsigned OpNum,SStream * O)2423*9a0e4156SSadaf Ebrahimi static void printVectorIndex(MCInst *MI, unsigned OpNum, SStream *O)
2424*9a0e4156SSadaf Ebrahimi {
2425*9a0e4156SSadaf Ebrahimi 	unsigned tmp = (unsigned int)MCOperand_getImm(MCInst_getOperand(MI, OpNum));
2426*9a0e4156SSadaf Ebrahimi 	if (tmp > HEX_THRESHOLD)
2427*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "[0x%x]", tmp);
2428*9a0e4156SSadaf Ebrahimi 	else
2429*9a0e4156SSadaf Ebrahimi 		SStream_concat(O, "[%u]", tmp);
2430*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2431*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count - 1].vector_index = tmp;
2432*9a0e4156SSadaf Ebrahimi 	}
2433*9a0e4156SSadaf Ebrahimi }
2434*9a0e4156SSadaf Ebrahimi 
printVectorListOne(MCInst * MI,unsigned OpNum,SStream * O)2435*9a0e4156SSadaf Ebrahimi static void printVectorListOne(MCInst *MI, unsigned OpNum, SStream *O)
2436*9a0e4156SSadaf Ebrahimi {
2437*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2438*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2439*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2440*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2441*9a0e4156SSadaf Ebrahimi 		uint8_t access;
2442*9a0e4156SSadaf Ebrahimi 
2443*9a0e4156SSadaf Ebrahimi 		access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2444*9a0e4156SSadaf Ebrahimi #endif
2445*9a0e4156SSadaf Ebrahimi 
2446*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2447*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2448*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2449*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2450*9a0e4156SSadaf Ebrahimi #endif
2451*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2452*9a0e4156SSadaf Ebrahimi 
2453*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2454*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2455*9a0e4156SSadaf Ebrahimi #endif
2456*9a0e4156SSadaf Ebrahimi 	}
2457*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
2458*9a0e4156SSadaf Ebrahimi }
2459*9a0e4156SSadaf Ebrahimi 
printVectorListTwo(MCInst * MI,unsigned OpNum,SStream * O,MCRegisterInfo * MRI)2460*9a0e4156SSadaf Ebrahimi static void printVectorListTwo(MCInst *MI, unsigned OpNum,
2461*9a0e4156SSadaf Ebrahimi 		SStream *O, MCRegisterInfo *MRI)
2462*9a0e4156SSadaf Ebrahimi {
2463*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2464*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2465*9a0e4156SSadaf Ebrahimi #endif
2466*9a0e4156SSadaf Ebrahimi 	unsigned Reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2467*9a0e4156SSadaf Ebrahimi 	unsigned Reg0 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_0);
2468*9a0e4156SSadaf Ebrahimi 	unsigned Reg1 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_1);
2469*9a0e4156SSadaf Ebrahimi 
2470*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2471*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2472*9a0e4156SSadaf Ebrahimi #endif
2473*9a0e4156SSadaf Ebrahimi 
2474*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2475*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg0);
2476*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2477*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2478*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg0;
2479*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2480*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2481*9a0e4156SSadaf Ebrahimi #endif
2482*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2483*9a0e4156SSadaf Ebrahimi 	}
2484*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2485*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg1);
2486*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2487*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2488*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg1;
2489*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2490*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2491*9a0e4156SSadaf Ebrahimi #endif
2492*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2493*9a0e4156SSadaf Ebrahimi 	}
2494*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
2495*9a0e4156SSadaf Ebrahimi 
2496*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2497*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2498*9a0e4156SSadaf Ebrahimi #endif
2499*9a0e4156SSadaf Ebrahimi }
2500*9a0e4156SSadaf Ebrahimi 
printVectorListTwoSpaced(MCInst * MI,unsigned OpNum,SStream * O,MCRegisterInfo * MRI)2501*9a0e4156SSadaf Ebrahimi static void printVectorListTwoSpaced(MCInst *MI, unsigned OpNum,
2502*9a0e4156SSadaf Ebrahimi 		SStream *O, MCRegisterInfo *MRI)
2503*9a0e4156SSadaf Ebrahimi {
2504*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2505*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2506*9a0e4156SSadaf Ebrahimi #endif
2507*9a0e4156SSadaf Ebrahimi 	unsigned Reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2508*9a0e4156SSadaf Ebrahimi 	unsigned Reg0 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_0);
2509*9a0e4156SSadaf Ebrahimi 	unsigned Reg1 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_2);
2510*9a0e4156SSadaf Ebrahimi 
2511*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2512*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2513*9a0e4156SSadaf Ebrahimi #endif
2514*9a0e4156SSadaf Ebrahimi 
2515*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2516*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg0);
2517*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2518*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2519*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg0;
2520*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2521*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2522*9a0e4156SSadaf Ebrahimi #endif
2523*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2524*9a0e4156SSadaf Ebrahimi 	}
2525*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2526*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg1);
2527*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2528*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2529*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg1;
2530*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2531*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2532*9a0e4156SSadaf Ebrahimi #endif
2533*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2534*9a0e4156SSadaf Ebrahimi 	}
2535*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
2536*9a0e4156SSadaf Ebrahimi 
2537*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2538*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2539*9a0e4156SSadaf Ebrahimi #endif
2540*9a0e4156SSadaf Ebrahimi }
2541*9a0e4156SSadaf Ebrahimi 
printVectorListThree(MCInst * MI,unsigned OpNum,SStream * O)2542*9a0e4156SSadaf Ebrahimi static void printVectorListThree(MCInst *MI, unsigned OpNum, SStream *O)
2543*9a0e4156SSadaf Ebrahimi {
2544*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2545*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2546*9a0e4156SSadaf Ebrahimi 
2547*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2548*9a0e4156SSadaf Ebrahimi #endif
2549*9a0e4156SSadaf Ebrahimi 
2550*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
2551*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
2552*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
2553*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2554*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2555*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2556*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2557*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2558*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2559*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2560*9a0e4156SSadaf Ebrahimi #endif
2561*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2562*9a0e4156SSadaf Ebrahimi 	}
2563*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2564*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1);
2565*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2566*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2567*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1;
2568*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2569*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2570*9a0e4156SSadaf Ebrahimi #endif
2571*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2572*9a0e4156SSadaf Ebrahimi 	}
2573*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2574*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
2575*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2576*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2577*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
2578*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2579*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2580*9a0e4156SSadaf Ebrahimi #endif
2581*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2582*9a0e4156SSadaf Ebrahimi 	}
2583*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
2584*9a0e4156SSadaf Ebrahimi 
2585*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2586*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2587*9a0e4156SSadaf Ebrahimi #endif
2588*9a0e4156SSadaf Ebrahimi }
2589*9a0e4156SSadaf Ebrahimi 
printVectorListFour(MCInst * MI,unsigned OpNum,SStream * O)2590*9a0e4156SSadaf Ebrahimi static void printVectorListFour(MCInst *MI, unsigned OpNum, SStream *O)
2591*9a0e4156SSadaf Ebrahimi {
2592*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2593*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2594*9a0e4156SSadaf Ebrahimi 
2595*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2596*9a0e4156SSadaf Ebrahimi #endif
2597*9a0e4156SSadaf Ebrahimi 
2598*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
2599*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
2600*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
2601*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2602*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2603*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2604*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2605*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2606*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2607*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2608*9a0e4156SSadaf Ebrahimi #endif
2609*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2610*9a0e4156SSadaf Ebrahimi 	}
2611*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2612*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1);
2613*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2614*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2615*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1;
2616*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2617*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2618*9a0e4156SSadaf Ebrahimi #endif
2619*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2620*9a0e4156SSadaf Ebrahimi 	}
2621*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2622*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
2623*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2624*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2625*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
2626*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2627*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2628*9a0e4156SSadaf Ebrahimi #endif
2629*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2630*9a0e4156SSadaf Ebrahimi 	}
2631*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2632*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 3);
2633*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2634*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2635*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 3;
2636*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2637*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2638*9a0e4156SSadaf Ebrahimi #endif
2639*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2640*9a0e4156SSadaf Ebrahimi 	}
2641*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
2642*9a0e4156SSadaf Ebrahimi 
2643*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2644*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2645*9a0e4156SSadaf Ebrahimi #endif
2646*9a0e4156SSadaf Ebrahimi }
2647*9a0e4156SSadaf Ebrahimi 
printVectorListOneAllLanes(MCInst * MI,unsigned OpNum,SStream * O)2648*9a0e4156SSadaf Ebrahimi static void printVectorListOneAllLanes(MCInst *MI, unsigned OpNum, SStream *O)
2649*9a0e4156SSadaf Ebrahimi {
2650*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2651*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2652*9a0e4156SSadaf Ebrahimi 
2653*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2654*9a0e4156SSadaf Ebrahimi #endif
2655*9a0e4156SSadaf Ebrahimi 
2656*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2657*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2658*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2659*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2660*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2661*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2662*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2663*9a0e4156SSadaf Ebrahimi #endif
2664*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2665*9a0e4156SSadaf Ebrahimi 	}
2666*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[]}");
2667*9a0e4156SSadaf Ebrahimi 
2668*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2669*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2670*9a0e4156SSadaf Ebrahimi #endif
2671*9a0e4156SSadaf Ebrahimi }
2672*9a0e4156SSadaf Ebrahimi 
printVectorListTwoAllLanes(MCInst * MI,unsigned OpNum,SStream * O,MCRegisterInfo * MRI)2673*9a0e4156SSadaf Ebrahimi static void printVectorListTwoAllLanes(MCInst *MI, unsigned OpNum,
2674*9a0e4156SSadaf Ebrahimi 		SStream *O, MCRegisterInfo *MRI)
2675*9a0e4156SSadaf Ebrahimi {
2676*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2677*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2678*9a0e4156SSadaf Ebrahimi #endif
2679*9a0e4156SSadaf Ebrahimi 	unsigned Reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2680*9a0e4156SSadaf Ebrahimi 	unsigned Reg0 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_0);
2681*9a0e4156SSadaf Ebrahimi 	unsigned Reg1 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_1);
2682*9a0e4156SSadaf Ebrahimi 
2683*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2684*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2685*9a0e4156SSadaf Ebrahimi #endif
2686*9a0e4156SSadaf Ebrahimi 
2687*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2688*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg0);
2689*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2690*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2691*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg0;
2692*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2693*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2694*9a0e4156SSadaf Ebrahimi #endif
2695*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2696*9a0e4156SSadaf Ebrahimi 	}
2697*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2698*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg1);
2699*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2700*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2701*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg1;
2702*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2703*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2704*9a0e4156SSadaf Ebrahimi #endif
2705*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2706*9a0e4156SSadaf Ebrahimi 	}
2707*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[]}");
2708*9a0e4156SSadaf Ebrahimi 
2709*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2710*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2711*9a0e4156SSadaf Ebrahimi #endif
2712*9a0e4156SSadaf Ebrahimi }
2713*9a0e4156SSadaf Ebrahimi 
printVectorListThreeAllLanes(MCInst * MI,unsigned OpNum,SStream * O)2714*9a0e4156SSadaf Ebrahimi static void printVectorListThreeAllLanes(MCInst *MI, unsigned OpNum, SStream *O)
2715*9a0e4156SSadaf Ebrahimi {
2716*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2717*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2718*9a0e4156SSadaf Ebrahimi 
2719*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2720*9a0e4156SSadaf Ebrahimi #endif
2721*9a0e4156SSadaf Ebrahimi 
2722*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
2723*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
2724*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
2725*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2726*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2727*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2728*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2729*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2730*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2731*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2732*9a0e4156SSadaf Ebrahimi #endif
2733*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2734*9a0e4156SSadaf Ebrahimi 	}
2735*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2736*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1);
2737*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2738*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2739*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1;
2740*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2741*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2742*9a0e4156SSadaf Ebrahimi #endif
2743*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2744*9a0e4156SSadaf Ebrahimi 	}
2745*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2746*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
2747*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2748*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2749*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
2750*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2751*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2752*9a0e4156SSadaf Ebrahimi #endif
2753*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2754*9a0e4156SSadaf Ebrahimi 	}
2755*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[]}");
2756*9a0e4156SSadaf Ebrahimi 
2757*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2758*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2759*9a0e4156SSadaf Ebrahimi #endif
2760*9a0e4156SSadaf Ebrahimi }
2761*9a0e4156SSadaf Ebrahimi 
printVectorListFourAllLanes(MCInst * MI,unsigned OpNum,SStream * O)2762*9a0e4156SSadaf Ebrahimi static void printVectorListFourAllLanes(MCInst *MI, unsigned OpNum, SStream *O)
2763*9a0e4156SSadaf Ebrahimi {
2764*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2765*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2766*9a0e4156SSadaf Ebrahimi 
2767*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2768*9a0e4156SSadaf Ebrahimi #endif
2769*9a0e4156SSadaf Ebrahimi 
2770*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
2771*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
2772*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
2773*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2774*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2775*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2776*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2777*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2778*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2779*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2780*9a0e4156SSadaf Ebrahimi #endif
2781*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2782*9a0e4156SSadaf Ebrahimi 	}
2783*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2784*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1);
2785*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2786*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2787*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 1;
2788*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2789*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2790*9a0e4156SSadaf Ebrahimi #endif
2791*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2792*9a0e4156SSadaf Ebrahimi 	}
2793*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2794*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
2795*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2796*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2797*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
2798*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2799*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2800*9a0e4156SSadaf Ebrahimi #endif
2801*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2802*9a0e4156SSadaf Ebrahimi 	}
2803*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2804*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 3);
2805*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2806*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2807*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 3;
2808*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2809*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2810*9a0e4156SSadaf Ebrahimi #endif
2811*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2812*9a0e4156SSadaf Ebrahimi 	}
2813*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[]}");
2814*9a0e4156SSadaf Ebrahimi 
2815*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2816*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2817*9a0e4156SSadaf Ebrahimi #endif
2818*9a0e4156SSadaf Ebrahimi }
2819*9a0e4156SSadaf Ebrahimi 
printVectorListTwoSpacedAllLanes(MCInst * MI,unsigned OpNum,SStream * O,MCRegisterInfo * MRI)2820*9a0e4156SSadaf Ebrahimi static void printVectorListTwoSpacedAllLanes(MCInst *MI,
2821*9a0e4156SSadaf Ebrahimi 		unsigned OpNum, SStream *O, MCRegisterInfo *MRI)
2822*9a0e4156SSadaf Ebrahimi {
2823*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2824*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2825*9a0e4156SSadaf Ebrahimi #endif
2826*9a0e4156SSadaf Ebrahimi 	unsigned Reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2827*9a0e4156SSadaf Ebrahimi 	unsigned Reg0 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_0);
2828*9a0e4156SSadaf Ebrahimi 	unsigned Reg1 = MCRegisterInfo_getSubReg(MRI, Reg, ARM_dsub_2);
2829*9a0e4156SSadaf Ebrahimi 
2830*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2831*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2832*9a0e4156SSadaf Ebrahimi #endif
2833*9a0e4156SSadaf Ebrahimi 
2834*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2835*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg0);
2836*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2837*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2838*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg0;
2839*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2840*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2841*9a0e4156SSadaf Ebrahimi #endif
2842*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2843*9a0e4156SSadaf Ebrahimi 	}
2844*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2845*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, Reg1);
2846*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2847*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2848*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = Reg1;
2849*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2850*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2851*9a0e4156SSadaf Ebrahimi #endif
2852*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2853*9a0e4156SSadaf Ebrahimi 	}
2854*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[]}");
2855*9a0e4156SSadaf Ebrahimi 
2856*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2857*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2858*9a0e4156SSadaf Ebrahimi #endif
2859*9a0e4156SSadaf Ebrahimi }
2860*9a0e4156SSadaf Ebrahimi 
printVectorListThreeSpacedAllLanes(MCInst * MI,unsigned OpNum,SStream * O)2861*9a0e4156SSadaf Ebrahimi static void printVectorListThreeSpacedAllLanes(MCInst *MI,
2862*9a0e4156SSadaf Ebrahimi 		unsigned OpNum, SStream *O)
2863*9a0e4156SSadaf Ebrahimi {
2864*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2865*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2866*9a0e4156SSadaf Ebrahimi 
2867*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2868*9a0e4156SSadaf Ebrahimi #endif
2869*9a0e4156SSadaf Ebrahimi 
2870*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
2871*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
2872*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
2873*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2874*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2875*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2876*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2877*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2878*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2879*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2880*9a0e4156SSadaf Ebrahimi #endif
2881*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2882*9a0e4156SSadaf Ebrahimi 	}
2883*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2884*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
2885*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2886*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2887*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
2888*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2889*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2890*9a0e4156SSadaf Ebrahimi #endif
2891*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2892*9a0e4156SSadaf Ebrahimi 	}
2893*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2894*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4);
2895*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2896*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2897*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4;
2898*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2899*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2900*9a0e4156SSadaf Ebrahimi #endif
2901*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2902*9a0e4156SSadaf Ebrahimi 	}
2903*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[]}");
2904*9a0e4156SSadaf Ebrahimi 
2905*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2906*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2907*9a0e4156SSadaf Ebrahimi #endif
2908*9a0e4156SSadaf Ebrahimi }
2909*9a0e4156SSadaf Ebrahimi 
printVectorListFourSpacedAllLanes(MCInst * MI,unsigned OpNum,SStream * O)2910*9a0e4156SSadaf Ebrahimi static void printVectorListFourSpacedAllLanes(MCInst *MI,
2911*9a0e4156SSadaf Ebrahimi 		unsigned OpNum, SStream *O)
2912*9a0e4156SSadaf Ebrahimi {
2913*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2914*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2915*9a0e4156SSadaf Ebrahimi 
2916*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2917*9a0e4156SSadaf Ebrahimi #endif
2918*9a0e4156SSadaf Ebrahimi 
2919*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
2920*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
2921*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
2922*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2923*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2924*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2925*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2926*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2927*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2928*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2929*9a0e4156SSadaf Ebrahimi #endif
2930*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2931*9a0e4156SSadaf Ebrahimi 	}
2932*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2933*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
2934*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2935*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2936*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
2937*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2938*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2939*9a0e4156SSadaf Ebrahimi #endif
2940*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2941*9a0e4156SSadaf Ebrahimi 	}
2942*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2943*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4);
2944*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2945*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2946*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4;
2947*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2948*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2949*9a0e4156SSadaf Ebrahimi #endif
2950*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2951*9a0e4156SSadaf Ebrahimi 	}
2952*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[], ");
2953*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 6);
2954*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2955*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2956*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 6;
2957*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2958*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2959*9a0e4156SSadaf Ebrahimi #endif
2960*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2961*9a0e4156SSadaf Ebrahimi 	}
2962*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "[]}");
2963*9a0e4156SSadaf Ebrahimi 
2964*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2965*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
2966*9a0e4156SSadaf Ebrahimi #endif
2967*9a0e4156SSadaf Ebrahimi }
2968*9a0e4156SSadaf Ebrahimi 
printVectorListThreeSpaced(MCInst * MI,unsigned OpNum,SStream * O)2969*9a0e4156SSadaf Ebrahimi static void printVectorListThreeSpaced(MCInst *MI, unsigned OpNum, SStream *O)
2970*9a0e4156SSadaf Ebrahimi {
2971*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2972*9a0e4156SSadaf Ebrahimi 	uint8_t access;
2973*9a0e4156SSadaf Ebrahimi 
2974*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
2975*9a0e4156SSadaf Ebrahimi #endif
2976*9a0e4156SSadaf Ebrahimi 
2977*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
2978*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
2979*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
2980*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
2981*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
2982*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2983*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2984*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
2985*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2986*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2987*9a0e4156SSadaf Ebrahimi #endif
2988*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2989*9a0e4156SSadaf Ebrahimi 	}
2990*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
2991*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
2992*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
2993*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
2994*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
2995*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
2996*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
2997*9a0e4156SSadaf Ebrahimi #endif
2998*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
2999*9a0e4156SSadaf Ebrahimi 	}
3000*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
3001*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4);
3002*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3003*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
3004*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4;
3005*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3006*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
3007*9a0e4156SSadaf Ebrahimi #endif
3008*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
3009*9a0e4156SSadaf Ebrahimi 	}
3010*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
3011*9a0e4156SSadaf Ebrahimi 
3012*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3013*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
3014*9a0e4156SSadaf Ebrahimi #endif
3015*9a0e4156SSadaf Ebrahimi }
3016*9a0e4156SSadaf Ebrahimi 
printVectorListFourSpaced(MCInst * MI,unsigned OpNum,SStream * O)3017*9a0e4156SSadaf Ebrahimi static void printVectorListFourSpaced(MCInst *MI, unsigned OpNum, SStream *O)
3018*9a0e4156SSadaf Ebrahimi {
3019*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3020*9a0e4156SSadaf Ebrahimi 	uint8_t access;
3021*9a0e4156SSadaf Ebrahimi 
3022*9a0e4156SSadaf Ebrahimi 	access = get_op_access(MI->csh, MCInst_getOpcode(MI), MI->ac_idx);
3023*9a0e4156SSadaf Ebrahimi #endif
3024*9a0e4156SSadaf Ebrahimi 
3025*9a0e4156SSadaf Ebrahimi 	// Normally, it's not safe to use register enum values directly with
3026*9a0e4156SSadaf Ebrahimi 	// addition to get the next register, but for VFP registers, the
3027*9a0e4156SSadaf Ebrahimi 	// sort order is guaranteed because they're all of the form D<n>.
3028*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "{");
3029*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)));
3030*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3031*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
3032*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum));
3033*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3034*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
3035*9a0e4156SSadaf Ebrahimi #endif
3036*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
3037*9a0e4156SSadaf Ebrahimi 	}
3038*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
3039*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2);
3040*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3041*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
3042*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 2;
3043*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3044*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
3045*9a0e4156SSadaf Ebrahimi #endif
3046*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
3047*9a0e4156SSadaf Ebrahimi 	}
3048*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
3049*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4);
3050*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3051*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
3052*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 4;
3053*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3054*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
3055*9a0e4156SSadaf Ebrahimi #endif
3056*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
3057*9a0e4156SSadaf Ebrahimi 	}
3058*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, ", ");
3059*9a0e4156SSadaf Ebrahimi 	printRegName(MI->csh, O, MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 6);
3060*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3061*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
3062*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = MCOperand_getReg(MCInst_getOperand(MI, OpNum)) + 6;
3063*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3064*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].access = access;
3065*9a0e4156SSadaf Ebrahimi #endif
3066*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
3067*9a0e4156SSadaf Ebrahimi 	}
3068*9a0e4156SSadaf Ebrahimi 	SStream_concat0(O, "}");
3069*9a0e4156SSadaf Ebrahimi 
3070*9a0e4156SSadaf Ebrahimi #ifndef CAPSTONE_DIET
3071*9a0e4156SSadaf Ebrahimi 	MI->ac_idx++;
3072*9a0e4156SSadaf Ebrahimi #endif
3073*9a0e4156SSadaf Ebrahimi }
3074*9a0e4156SSadaf Ebrahimi 
ARM_addVectorDataType(MCInst * MI,arm_vectordata_type vd)3075*9a0e4156SSadaf Ebrahimi void ARM_addVectorDataType(MCInst *MI, arm_vectordata_type vd)
3076*9a0e4156SSadaf Ebrahimi {
3077*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3078*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.vector_data = vd;
3079*9a0e4156SSadaf Ebrahimi 	}
3080*9a0e4156SSadaf Ebrahimi }
3081*9a0e4156SSadaf Ebrahimi 
ARM_addVectorDataSize(MCInst * MI,int size)3082*9a0e4156SSadaf Ebrahimi void ARM_addVectorDataSize(MCInst *MI, int size)
3083*9a0e4156SSadaf Ebrahimi {
3084*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3085*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.vector_size = size;
3086*9a0e4156SSadaf Ebrahimi 	}
3087*9a0e4156SSadaf Ebrahimi }
3088*9a0e4156SSadaf Ebrahimi 
ARM_addReg(MCInst * MI,int reg)3089*9a0e4156SSadaf Ebrahimi void ARM_addReg(MCInst *MI, int reg)
3090*9a0e4156SSadaf Ebrahimi {
3091*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3092*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_REG;
3093*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = reg;
3094*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
3095*9a0e4156SSadaf Ebrahimi 	}
3096*9a0e4156SSadaf Ebrahimi }
3097*9a0e4156SSadaf Ebrahimi 
ARM_addUserMode(MCInst * MI)3098*9a0e4156SSadaf Ebrahimi void ARM_addUserMode(MCInst *MI)
3099*9a0e4156SSadaf Ebrahimi {
3100*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3101*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.usermode = true;
3102*9a0e4156SSadaf Ebrahimi 	}
3103*9a0e4156SSadaf Ebrahimi }
3104*9a0e4156SSadaf Ebrahimi 
ARM_addSysReg(MCInst * MI,arm_sysreg reg)3105*9a0e4156SSadaf Ebrahimi void ARM_addSysReg(MCInst *MI, arm_sysreg reg)
3106*9a0e4156SSadaf Ebrahimi {
3107*9a0e4156SSadaf Ebrahimi 	if (MI->csh->detail) {
3108*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].type = ARM_OP_SYSREG;
3109*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.operands[MI->flat_insn->detail->arm.op_count].reg = reg;
3110*9a0e4156SSadaf Ebrahimi 		MI->flat_insn->detail->arm.op_count++;
3111*9a0e4156SSadaf Ebrahimi 	}
3112*9a0e4156SSadaf Ebrahimi }
3113*9a0e4156SSadaf Ebrahimi 
3114*9a0e4156SSadaf Ebrahimi #endif
3115