qemu-char: make tcp_chr_disconnect() reentrant-safe
[qemu/ar7.git] / disas / arm.c
blob70da5298a086610e0a1de5890d81c6fdc37d8e5e
1 /* Instruction printing code for the ARM
2 Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004
3 2007, Free Software Foundation, Inc.
4 Contributed by Richard Earnshaw (rwe@pegasus.esprit.ec.org)
5 Modification by James G. Smith (jsmith@cygnus.co.uk)
7 This file is part of libopcodes.
9 This program is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free
11 Software Foundation; either version 2 of the License, or (at your option)
12 any later version.
14 This program is distributed in the hope that it will be useful, but WITHOUT
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
17 more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, see <http://www.gnu.org/licenses/>. */
22 /* Start of qemu specific additions. Mostly this is stub definitions
23 for things we don't care about. */
25 #include "qemu/osdep.h"
26 #include "disas/bfd.h"
27 #define ATTRIBUTE_UNUSED __attribute__((unused))
28 #define ISSPACE(x) ((x) == ' ' || (x) == '\t' || (x) == '\n')
30 #define ARM_EXT_V1 0
31 #define ARM_EXT_V2 0
32 #define ARM_EXT_V2S 0
33 #define ARM_EXT_V3 0
34 #define ARM_EXT_V3M 0
35 #define ARM_EXT_V4 0
36 #define ARM_EXT_V4T 0
37 #define ARM_EXT_V5 0
38 #define ARM_EXT_V5T 0
39 #define ARM_EXT_V5ExP 0
40 #define ARM_EXT_V5E 0
41 #define ARM_EXT_V5J 0
42 #define ARM_EXT_V6 0
43 #define ARM_EXT_V6K 0
44 #define ARM_EXT_V6Z 0
45 #define ARM_EXT_V6T2 0
46 #define ARM_EXT_V7 0
47 #define ARM_EXT_DIV 0
49 /* Co-processor space extensions. */
50 #define ARM_CEXT_XSCALE 0
51 #define ARM_CEXT_MAVERICK 0
52 #define ARM_CEXT_IWMMXT 0
54 #define FPU_FPA_EXT_V1 0
55 #define FPU_FPA_EXT_V2 0
56 #define FPU_VFP_EXT_NONE 0
57 #define FPU_VFP_EXT_V1xD 0
58 #define FPU_VFP_EXT_V1 0
59 #define FPU_VFP_EXT_V2 0
60 #define FPU_MAVERICK 0
61 #define FPU_VFP_EXT_V3 0
62 #define FPU_NEON_EXT_V1 0
64 /* Assume host uses ieee float. */
65 static void floatformat_to_double (unsigned char *data, double *dest)
67 union {
68 uint32_t i;
69 float f;
70 } u;
71 u.i = data[0] | (data[1] << 8) | (data[2] << 16) | (data[3] << 24);
72 *dest = u.f;
75 /* End of qemu specific additions. */
77 /* FIXME: Belongs in global header. */
78 #ifndef strneq
79 #define strneq(a,b,n) (strncmp ((a), (b), (n)) == 0)
80 #endif
82 #ifndef NUM_ELEM
83 #define NUM_ELEM(a) (sizeof (a) / sizeof (a)[0])
84 #endif
86 struct opcode32
88 unsigned long arch; /* Architecture defining this insn. */
89 unsigned long value, mask; /* Recognise insn if (op&mask)==value. */
90 const char *assembler; /* How to disassemble this insn. */
93 struct opcode16
95 unsigned long arch; /* Architecture defining this insn. */
96 unsigned short value, mask; /* Recognise insn if (op&mask)==value. */
97 const char *assembler; /* How to disassemble this insn. */
100 /* print_insn_coprocessor recognizes the following format control codes:
102 %% %
104 %c print condition code (always bits 28-31 in ARM mode)
105 %q print shifter argument
106 %u print condition code (unconditional in ARM mode)
107 %A print address for ldc/stc/ldf/stf instruction
108 %B print vstm/vldm register list
109 %C print vstr/vldr address operand
110 %I print cirrus signed shift immediate: bits 0..3|4..6
111 %F print the COUNT field of a LFM/SFM instruction.
112 %P print floating point precision in arithmetic insn
113 %Q print floating point precision in ldf/stf insn
114 %R print floating point rounding mode
116 %<bitfield>r print as an ARM register
117 %<bitfield>d print the bitfield in decimal
118 %<bitfield>k print immediate for VFPv3 conversion instruction
119 %<bitfield>x print the bitfield in hex
120 %<bitfield>X print the bitfield as 1 hex digit without leading "0x"
121 %<bitfield>f print a floating point constant if >7 else a
122 floating point register
123 %<bitfield>w print as an iWMMXt width field - [bhwd]ss/us
124 %<bitfield>g print as an iWMMXt 64-bit register
125 %<bitfield>G print as an iWMMXt general purpose or control register
126 %<bitfield>D print as a NEON D register
127 %<bitfield>Q print as a NEON Q register
129 %y<code> print a single precision VFP reg.
130 Codes: 0=>Sm, 1=>Sd, 2=>Sn, 3=>multi-list, 4=>Sm pair
131 %z<code> print a double precision VFP reg
132 Codes: 0=>Dm, 1=>Dd, 2=>Dn, 3=>multi-list
134 %<bitfield>'c print specified char iff bitfield is all ones
135 %<bitfield>`c print specified char iff bitfield is all zeroes
136 %<bitfield>?ab... select from array of values in big endian order
138 %L print as an iWMMXt N/M width field.
139 %Z print the Immediate of a WSHUFH instruction.
140 %l like 'A' except use byte offsets for 'B' & 'H'
141 versions.
142 %i print 5-bit immediate in bits 8,3..0
143 (print "32" when 0)
144 %r print register offset address for wldt/wstr instruction
147 /* Common coprocessor opcodes shared between Arm and Thumb-2. */
149 static const struct opcode32 coprocessor_opcodes[] =
151 /* XScale instructions. */
152 {ARM_CEXT_XSCALE, 0x0e200010, 0x0fff0ff0, "mia%c\tacc0, %0-3r, %12-15r"},
153 {ARM_CEXT_XSCALE, 0x0e280010, 0x0fff0ff0, "miaph%c\tacc0, %0-3r, %12-15r"},
154 {ARM_CEXT_XSCALE, 0x0e2c0010, 0x0ffc0ff0, "mia%17'T%17`B%16'T%16`B%c\tacc0, %0-3r, %12-15r"},
155 {ARM_CEXT_XSCALE, 0x0c400000, 0x0ff00fff, "mar%c\tacc0, %12-15r, %16-19r"},
156 {ARM_CEXT_XSCALE, 0x0c500000, 0x0ff00fff, "mra%c\t%12-15r, %16-19r, acc0"},
158 /* Intel Wireless MMX technology instructions. */
159 #define FIRST_IWMMXT_INSN 0x0e130130
160 #define IWMMXT_INSN_COUNT 73
161 {ARM_CEXT_IWMMXT, 0x0e130130, 0x0f3f0fff, "tandc%22-23w%c\t%12-15r"},
162 {ARM_CEXT_XSCALE, 0x0e400010, 0x0ff00f3f, "tbcst%6-7w%c\t%16-19g, %12-15r"},
163 {ARM_CEXT_XSCALE, 0x0e130170, 0x0f3f0ff8, "textrc%22-23w%c\t%12-15r, #%0-2d"},
164 {ARM_CEXT_XSCALE, 0x0e100070, 0x0f300ff0, "textrm%3?su%22-23w%c\t%12-15r, %16-19g, #%0-2d"},
165 {ARM_CEXT_XSCALE, 0x0e600010, 0x0ff00f38, "tinsr%6-7w%c\t%16-19g, %12-15r, #%0-2d"},
166 {ARM_CEXT_XSCALE, 0x0e000110, 0x0ff00fff, "tmcr%c\t%16-19G, %12-15r"},
167 {ARM_CEXT_XSCALE, 0x0c400000, 0x0ff00ff0, "tmcrr%c\t%0-3g, %12-15r, %16-19r"},
168 {ARM_CEXT_XSCALE, 0x0e2c0010, 0x0ffc0e10, "tmia%17?tb%16?tb%c\t%5-8g, %0-3r, %12-15r"},
169 {ARM_CEXT_XSCALE, 0x0e200010, 0x0fff0e10, "tmia%c\t%5-8g, %0-3r, %12-15r"},
170 {ARM_CEXT_XSCALE, 0x0e280010, 0x0fff0e10, "tmiaph%c\t%5-8g, %0-3r, %12-15r"},
171 {ARM_CEXT_XSCALE, 0x0e100030, 0x0f300fff, "tmovmsk%22-23w%c\t%12-15r, %16-19g"},
172 {ARM_CEXT_XSCALE, 0x0e100110, 0x0ff00ff0, "tmrc%c\t%12-15r, %16-19G"},
173 {ARM_CEXT_XSCALE, 0x0c500000, 0x0ff00ff0, "tmrrc%c\t%12-15r, %16-19r, %0-3g"},
174 {ARM_CEXT_XSCALE, 0x0e130150, 0x0f3f0fff, "torc%22-23w%c\t%12-15r"},
175 {ARM_CEXT_XSCALE, 0x0e130190, 0x0f3f0fff, "torvsc%22-23w%c\t%12-15r"},
176 {ARM_CEXT_XSCALE, 0x0e2001c0, 0x0f300fff, "wabs%22-23w%c\t%12-15g, %16-19g"},
177 {ARM_CEXT_XSCALE, 0x0e0001c0, 0x0f300fff, "wacc%22-23w%c\t%12-15g, %16-19g"},
178 {ARM_CEXT_XSCALE, 0x0e000180, 0x0f000ff0, "wadd%20-23w%c\t%12-15g, %16-19g, %0-3g"},
179 {ARM_CEXT_XSCALE, 0x0e2001a0, 0x0f300ff0, "waddbhus%22?ml%c\t%12-15g, %16-19g, %0-3g"},
180 {ARM_CEXT_XSCALE, 0x0ea001a0, 0x0ff00ff0, "waddsubhx%c\t%12-15g, %16-19g, %0-3g"},
181 {ARM_CEXT_XSCALE, 0x0e000020, 0x0f800ff0, "waligni%c\t%12-15g, %16-19g, %0-3g, #%20-22d"},
182 {ARM_CEXT_XSCALE, 0x0e800020, 0x0fc00ff0, "walignr%20-21d%c\t%12-15g, %16-19g, %0-3g"},
183 {ARM_CEXT_XSCALE, 0x0e200000, 0x0fe00ff0, "wand%20'n%c\t%12-15g, %16-19g, %0-3g"},
184 {ARM_CEXT_XSCALE, 0x0e800000, 0x0fa00ff0, "wavg2%22?hb%20'r%c\t%12-15g, %16-19g, %0-3g"},
185 {ARM_CEXT_XSCALE, 0x0e400000, 0x0fe00ff0, "wavg4%20'r%c\t%12-15g, %16-19g, %0-3g"},
186 {ARM_CEXT_XSCALE, 0x0e000060, 0x0f300ff0, "wcmpeq%22-23w%c\t%12-15g, %16-19g, %0-3g"},
187 {ARM_CEXT_XSCALE, 0x0e100060, 0x0f100ff0, "wcmpgt%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
188 {ARM_CEXT_XSCALE, 0xfc500100, 0xfe500f00, "wldrd\t%12-15g, %r"},
189 {ARM_CEXT_XSCALE, 0xfc100100, 0xfe500f00, "wldrw\t%12-15G, %A"},
190 {ARM_CEXT_XSCALE, 0x0c100000, 0x0e100e00, "wldr%L%c\t%12-15g, %l"},
191 {ARM_CEXT_XSCALE, 0x0e400100, 0x0fc00ff0, "wmac%21?su%20'z%c\t%12-15g, %16-19g, %0-3g"},
192 {ARM_CEXT_XSCALE, 0x0e800100, 0x0fc00ff0, "wmadd%21?su%20'x%c\t%12-15g, %16-19g, %0-3g"},
193 {ARM_CEXT_XSCALE, 0x0ec00100, 0x0fd00ff0, "wmadd%21?sun%c\t%12-15g, %16-19g, %0-3g"},
194 {ARM_CEXT_XSCALE, 0x0e000160, 0x0f100ff0, "wmax%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
195 {ARM_CEXT_XSCALE, 0x0e000080, 0x0f100fe0, "wmerge%c\t%12-15g, %16-19g, %0-3g, #%21-23d"},
196 {ARM_CEXT_XSCALE, 0x0e0000a0, 0x0f800ff0, "wmia%21?tb%20?tb%22'n%c\t%12-15g, %16-19g, %0-3g"},
197 {ARM_CEXT_XSCALE, 0x0e800120, 0x0f800ff0, "wmiaw%21?tb%20?tb%22'n%c\t%12-15g, %16-19g, %0-3g"},
198 {ARM_CEXT_XSCALE, 0x0e100160, 0x0f100ff0, "wmin%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
199 {ARM_CEXT_XSCALE, 0x0e000100, 0x0fc00ff0, "wmul%21?su%20?ml%23'r%c\t%12-15g, %16-19g, %0-3g"},
200 {ARM_CEXT_XSCALE, 0x0ed00100, 0x0fd00ff0, "wmul%21?sumr%c\t%12-15g, %16-19g, %0-3g"},
201 {ARM_CEXT_XSCALE, 0x0ee000c0, 0x0fe00ff0, "wmulwsm%20`r%c\t%12-15g, %16-19g, %0-3g"},
202 {ARM_CEXT_XSCALE, 0x0ec000c0, 0x0fe00ff0, "wmulwum%20`r%c\t%12-15g, %16-19g, %0-3g"},
203 {ARM_CEXT_XSCALE, 0x0eb000c0, 0x0ff00ff0, "wmulwl%c\t%12-15g, %16-19g, %0-3g"},
204 {ARM_CEXT_XSCALE, 0x0e8000a0, 0x0f800ff0, "wqmia%21?tb%20?tb%22'n%c\t%12-15g, %16-19g, %0-3g"},
205 {ARM_CEXT_XSCALE, 0x0e100080, 0x0fd00ff0, "wqmulm%21'r%c\t%12-15g, %16-19g, %0-3g"},
206 {ARM_CEXT_XSCALE, 0x0ec000e0, 0x0fd00ff0, "wqmulwm%21'r%c\t%12-15g, %16-19g, %0-3g"},
207 {ARM_CEXT_XSCALE, 0x0e000000, 0x0ff00ff0, "wor%c\t%12-15g, %16-19g, %0-3g"},
208 {ARM_CEXT_XSCALE, 0x0e000080, 0x0f000ff0, "wpack%20-23w%c\t%12-15g, %16-19g, %0-3g"},
209 {ARM_CEXT_XSCALE, 0xfe300040, 0xff300ef0, "wror%22-23w\t%12-15g, %16-19g, #%i"},
210 {ARM_CEXT_XSCALE, 0x0e300040, 0x0f300ff0, "wror%22-23w%c\t%12-15g, %16-19g, %0-3g"},
211 {ARM_CEXT_XSCALE, 0x0e300140, 0x0f300ff0, "wror%22-23wg%c\t%12-15g, %16-19g, %0-3G"},
212 {ARM_CEXT_XSCALE, 0x0e000120, 0x0fa00ff0, "wsad%22?hb%20'z%c\t%12-15g, %16-19g, %0-3g"},
213 {ARM_CEXT_XSCALE, 0x0e0001e0, 0x0f000ff0, "wshufh%c\t%12-15g, %16-19g, #%Z"},
214 {ARM_CEXT_XSCALE, 0xfe100040, 0xff300ef0, "wsll%22-23w\t%12-15g, %16-19g, #%i"},
215 {ARM_CEXT_XSCALE, 0x0e100040, 0x0f300ff0, "wsll%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
216 {ARM_CEXT_XSCALE, 0x0e100148, 0x0f300ffc, "wsll%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
217 {ARM_CEXT_XSCALE, 0xfe000040, 0xff300ef0, "wsra%22-23w\t%12-15g, %16-19g, #%i"},
218 {ARM_CEXT_XSCALE, 0x0e000040, 0x0f300ff0, "wsra%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
219 {ARM_CEXT_XSCALE, 0x0e000148, 0x0f300ffc, "wsra%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
220 {ARM_CEXT_XSCALE, 0xfe200040, 0xff300ef0, "wsrl%22-23w\t%12-15g, %16-19g, #%i"},
221 {ARM_CEXT_XSCALE, 0x0e200040, 0x0f300ff0, "wsrl%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
222 {ARM_CEXT_XSCALE, 0x0e200148, 0x0f300ffc, "wsrl%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
223 {ARM_CEXT_XSCALE, 0xfc400100, 0xfe500f00, "wstrd\t%12-15g, %r"},
224 {ARM_CEXT_XSCALE, 0xfc000100, 0xfe500f00, "wstrw\t%12-15G, %A"},
225 {ARM_CEXT_XSCALE, 0x0c000000, 0x0e100e00, "wstr%L%c\t%12-15g, %l"},
226 {ARM_CEXT_XSCALE, 0x0e0001a0, 0x0f000ff0, "wsub%20-23w%c\t%12-15g, %16-19g, %0-3g"},
227 {ARM_CEXT_XSCALE, 0x0ed001c0, 0x0ff00ff0, "wsubaddhx%c\t%12-15g, %16-19g, %0-3g"},
228 {ARM_CEXT_XSCALE, 0x0e1001c0, 0x0f300ff0, "wabsdiff%22-23w%c\t%12-15g, %16-19g, %0-3g"},
229 {ARM_CEXT_XSCALE, 0x0e0000c0, 0x0fd00fff, "wunpckeh%21?sub%c\t%12-15g, %16-19g"},
230 {ARM_CEXT_XSCALE, 0x0e4000c0, 0x0fd00fff, "wunpckeh%21?suh%c\t%12-15g, %16-19g"},
231 {ARM_CEXT_XSCALE, 0x0e8000c0, 0x0fd00fff, "wunpckeh%21?suw%c\t%12-15g, %16-19g"},
232 {ARM_CEXT_XSCALE, 0x0e0000e0, 0x0f100fff, "wunpckel%21?su%22-23w%c\t%12-15g, %16-19g"},
233 {ARM_CEXT_XSCALE, 0x0e1000c0, 0x0f300ff0, "wunpckih%22-23w%c\t%12-15g, %16-19g, %0-3g"},
234 {ARM_CEXT_XSCALE, 0x0e1000e0, 0x0f300ff0, "wunpckil%22-23w%c\t%12-15g, %16-19g, %0-3g"},
235 {ARM_CEXT_XSCALE, 0x0e100000, 0x0ff00ff0, "wxor%c\t%12-15g, %16-19g, %0-3g"},
237 /* Floating point coprocessor (FPA) instructions */
238 {FPU_FPA_EXT_V1, 0x0e000100, 0x0ff08f10, "adf%c%P%R\t%12-14f, %16-18f, %0-3f"},
239 {FPU_FPA_EXT_V1, 0x0e100100, 0x0ff08f10, "muf%c%P%R\t%12-14f, %16-18f, %0-3f"},
240 {FPU_FPA_EXT_V1, 0x0e200100, 0x0ff08f10, "suf%c%P%R\t%12-14f, %16-18f, %0-3f"},
241 {FPU_FPA_EXT_V1, 0x0e300100, 0x0ff08f10, "rsf%c%P%R\t%12-14f, %16-18f, %0-3f"},
242 {FPU_FPA_EXT_V1, 0x0e400100, 0x0ff08f10, "dvf%c%P%R\t%12-14f, %16-18f, %0-3f"},
243 {FPU_FPA_EXT_V1, 0x0e500100, 0x0ff08f10, "rdf%c%P%R\t%12-14f, %16-18f, %0-3f"},
244 {FPU_FPA_EXT_V1, 0x0e600100, 0x0ff08f10, "pow%c%P%R\t%12-14f, %16-18f, %0-3f"},
245 {FPU_FPA_EXT_V1, 0x0e700100, 0x0ff08f10, "rpw%c%P%R\t%12-14f, %16-18f, %0-3f"},
246 {FPU_FPA_EXT_V1, 0x0e800100, 0x0ff08f10, "rmf%c%P%R\t%12-14f, %16-18f, %0-3f"},
247 {FPU_FPA_EXT_V1, 0x0e900100, 0x0ff08f10, "fml%c%P%R\t%12-14f, %16-18f, %0-3f"},
248 {FPU_FPA_EXT_V1, 0x0ea00100, 0x0ff08f10, "fdv%c%P%R\t%12-14f, %16-18f, %0-3f"},
249 {FPU_FPA_EXT_V1, 0x0eb00100, 0x0ff08f10, "frd%c%P%R\t%12-14f, %16-18f, %0-3f"},
250 {FPU_FPA_EXT_V1, 0x0ec00100, 0x0ff08f10, "pol%c%P%R\t%12-14f, %16-18f, %0-3f"},
251 {FPU_FPA_EXT_V1, 0x0e008100, 0x0ff08f10, "mvf%c%P%R\t%12-14f, %0-3f"},
252 {FPU_FPA_EXT_V1, 0x0e108100, 0x0ff08f10, "mnf%c%P%R\t%12-14f, %0-3f"},
253 {FPU_FPA_EXT_V1, 0x0e208100, 0x0ff08f10, "abs%c%P%R\t%12-14f, %0-3f"},
254 {FPU_FPA_EXT_V1, 0x0e308100, 0x0ff08f10, "rnd%c%P%R\t%12-14f, %0-3f"},
255 {FPU_FPA_EXT_V1, 0x0e408100, 0x0ff08f10, "sqt%c%P%R\t%12-14f, %0-3f"},
256 {FPU_FPA_EXT_V1, 0x0e508100, 0x0ff08f10, "log%c%P%R\t%12-14f, %0-3f"},
257 {FPU_FPA_EXT_V1, 0x0e608100, 0x0ff08f10, "lgn%c%P%R\t%12-14f, %0-3f"},
258 {FPU_FPA_EXT_V1, 0x0e708100, 0x0ff08f10, "exp%c%P%R\t%12-14f, %0-3f"},
259 {FPU_FPA_EXT_V1, 0x0e808100, 0x0ff08f10, "sin%c%P%R\t%12-14f, %0-3f"},
260 {FPU_FPA_EXT_V1, 0x0e908100, 0x0ff08f10, "cos%c%P%R\t%12-14f, %0-3f"},
261 {FPU_FPA_EXT_V1, 0x0ea08100, 0x0ff08f10, "tan%c%P%R\t%12-14f, %0-3f"},
262 {FPU_FPA_EXT_V1, 0x0eb08100, 0x0ff08f10, "asn%c%P%R\t%12-14f, %0-3f"},
263 {FPU_FPA_EXT_V1, 0x0ec08100, 0x0ff08f10, "acs%c%P%R\t%12-14f, %0-3f"},
264 {FPU_FPA_EXT_V1, 0x0ed08100, 0x0ff08f10, "atn%c%P%R\t%12-14f, %0-3f"},
265 {FPU_FPA_EXT_V1, 0x0ee08100, 0x0ff08f10, "urd%c%P%R\t%12-14f, %0-3f"},
266 {FPU_FPA_EXT_V1, 0x0ef08100, 0x0ff08f10, "nrm%c%P%R\t%12-14f, %0-3f"},
267 {FPU_FPA_EXT_V1, 0x0e000110, 0x0ff00f1f, "flt%c%P%R\t%16-18f, %12-15r"},
268 {FPU_FPA_EXT_V1, 0x0e100110, 0x0fff0f98, "fix%c%R\t%12-15r, %0-2f"},
269 {FPU_FPA_EXT_V1, 0x0e200110, 0x0fff0fff, "wfs%c\t%12-15r"},
270 {FPU_FPA_EXT_V1, 0x0e300110, 0x0fff0fff, "rfs%c\t%12-15r"},
271 {FPU_FPA_EXT_V1, 0x0e400110, 0x0fff0fff, "wfc%c\t%12-15r"},
272 {FPU_FPA_EXT_V1, 0x0e500110, 0x0fff0fff, "rfc%c\t%12-15r"},
273 {FPU_FPA_EXT_V1, 0x0e90f110, 0x0ff8fff0, "cmf%c\t%16-18f, %0-3f"},
274 {FPU_FPA_EXT_V1, 0x0eb0f110, 0x0ff8fff0, "cnf%c\t%16-18f, %0-3f"},
275 {FPU_FPA_EXT_V1, 0x0ed0f110, 0x0ff8fff0, "cmfe%c\t%16-18f, %0-3f"},
276 {FPU_FPA_EXT_V1, 0x0ef0f110, 0x0ff8fff0, "cnfe%c\t%16-18f, %0-3f"},
277 {FPU_FPA_EXT_V1, 0x0c000100, 0x0e100f00, "stf%c%Q\t%12-14f, %A"},
278 {FPU_FPA_EXT_V1, 0x0c100100, 0x0e100f00, "ldf%c%Q\t%12-14f, %A"},
279 {FPU_FPA_EXT_V2, 0x0c000200, 0x0e100f00, "sfm%c\t%12-14f, %F, %A"},
280 {FPU_FPA_EXT_V2, 0x0c100200, 0x0e100f00, "lfm%c\t%12-14f, %F, %A"},
282 /* Register load/store */
283 {FPU_NEON_EXT_V1, 0x0d200b00, 0x0fb00f01, "vstmdb%c\t%16-19r%21'!, %B"},
284 {FPU_NEON_EXT_V1, 0x0d300b00, 0x0fb00f01, "vldmdb%c\t%16-19r%21'!, %B"},
285 {FPU_NEON_EXT_V1, 0x0c800b00, 0x0f900f01, "vstmia%c\t%16-19r%21'!, %B"},
286 {FPU_NEON_EXT_V1, 0x0c900b00, 0x0f900f01, "vldmia%c\t%16-19r%21'!, %B"},
287 {FPU_NEON_EXT_V1, 0x0d000b00, 0x0f300f00, "vstr%c\t%12-15,22D, %C"},
288 {FPU_NEON_EXT_V1, 0x0d100b00, 0x0f300f00, "vldr%c\t%12-15,22D, %C"},
290 /* Data transfer between ARM and NEON registers */
291 {FPU_NEON_EXT_V1, 0x0e800b10, 0x0ff00f70, "vdup%c.32\t%16-19,7D, %12-15r"},
292 {FPU_NEON_EXT_V1, 0x0e800b30, 0x0ff00f70, "vdup%c.16\t%16-19,7D, %12-15r"},
293 {FPU_NEON_EXT_V1, 0x0ea00b10, 0x0ff00f70, "vdup%c.32\t%16-19,7Q, %12-15r"},
294 {FPU_NEON_EXT_V1, 0x0ea00b30, 0x0ff00f70, "vdup%c.16\t%16-19,7Q, %12-15r"},
295 {FPU_NEON_EXT_V1, 0x0ec00b10, 0x0ff00f70, "vdup%c.8\t%16-19,7D, %12-15r"},
296 {FPU_NEON_EXT_V1, 0x0ee00b10, 0x0ff00f70, "vdup%c.8\t%16-19,7Q, %12-15r"},
297 {FPU_NEON_EXT_V1, 0x0c400b10, 0x0ff00fd0, "vmov%c\t%0-3,5D, %12-15r, %16-19r"},
298 {FPU_NEON_EXT_V1, 0x0c500b10, 0x0ff00fd0, "vmov%c\t%12-15r, %16-19r, %0-3,5D"},
299 {FPU_NEON_EXT_V1, 0x0e000b10, 0x0fd00f70, "vmov%c.32\t%16-19,7D[%21d], %12-15r"},
300 {FPU_NEON_EXT_V1, 0x0e100b10, 0x0f500f70, "vmov%c.32\t%12-15r, %16-19,7D[%21d]"},
301 {FPU_NEON_EXT_V1, 0x0e000b30, 0x0fd00f30, "vmov%c.16\t%16-19,7D[%6,21d], %12-15r"},
302 {FPU_NEON_EXT_V1, 0x0e100b30, 0x0f500f30, "vmov%c.%23?us16\t%12-15r, %16-19,7D[%6,21d]"},
303 {FPU_NEON_EXT_V1, 0x0e400b10, 0x0fd00f10, "vmov%c.8\t%16-19,7D[%5,6,21d], %12-15r"},
304 {FPU_NEON_EXT_V1, 0x0e500b10, 0x0f500f10, "vmov%c.%23?us8\t%12-15r, %16-19,7D[%5,6,21d]"},
306 /* Floating point coprocessor (VFP) instructions */
307 {FPU_VFP_EXT_V1xD, 0x0ef1fa10, 0x0fffffff, "fmstat%c"},
308 {FPU_VFP_EXT_V1xD, 0x0ee00a10, 0x0fff0fff, "fmxr%c\tfpsid, %12-15r"},
309 {FPU_VFP_EXT_V1xD, 0x0ee10a10, 0x0fff0fff, "fmxr%c\tfpscr, %12-15r"},
310 {FPU_VFP_EXT_V1xD, 0x0ee60a10, 0x0fff0fff, "fmxr%c\tmvfr1, %12-15r"},
311 {FPU_VFP_EXT_V1xD, 0x0ee70a10, 0x0fff0fff, "fmxr%c\tmvfr0, %12-15r"},
312 {FPU_VFP_EXT_V1xD, 0x0ee80a10, 0x0fff0fff, "fmxr%c\tfpexc, %12-15r"},
313 {FPU_VFP_EXT_V1xD, 0x0ee90a10, 0x0fff0fff, "fmxr%c\tfpinst, %12-15r\t@ Impl def"},
314 {FPU_VFP_EXT_V1xD, 0x0eea0a10, 0x0fff0fff, "fmxr%c\tfpinst2, %12-15r\t@ Impl def"},
315 {FPU_VFP_EXT_V1xD, 0x0ef00a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpsid"},
316 {FPU_VFP_EXT_V1xD, 0x0ef10a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpscr"},
317 {FPU_VFP_EXT_V1xD, 0x0ef60a10, 0x0fff0fff, "fmrx%c\t%12-15r, mvfr1"},
318 {FPU_VFP_EXT_V1xD, 0x0ef70a10, 0x0fff0fff, "fmrx%c\t%12-15r, mvfr0"},
319 {FPU_VFP_EXT_V1xD, 0x0ef80a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpexc"},
320 {FPU_VFP_EXT_V1xD, 0x0ef90a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpinst\t@ Impl def"},
321 {FPU_VFP_EXT_V1xD, 0x0efa0a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpinst2\t@ Impl def"},
322 {FPU_VFP_EXT_V1, 0x0e000b10, 0x0ff00fff, "fmdlr%c\t%z2, %12-15r"},
323 {FPU_VFP_EXT_V1, 0x0e100b10, 0x0ff00fff, "fmrdl%c\t%12-15r, %z2"},
324 {FPU_VFP_EXT_V1, 0x0e200b10, 0x0ff00fff, "fmdhr%c\t%z2, %12-15r"},
325 {FPU_VFP_EXT_V1, 0x0e300b10, 0x0ff00fff, "fmrdh%c\t%12-15r, %z2"},
326 {FPU_VFP_EXT_V1xD, 0x0ee00a10, 0x0ff00fff, "fmxr%c\t<impl def %16-19x>, %12-15r"},
327 {FPU_VFP_EXT_V1xD, 0x0ef00a10, 0x0ff00fff, "fmrx%c\t%12-15r, <impl def %16-19x>"},
328 {FPU_VFP_EXT_V1xD, 0x0e000a10, 0x0ff00f7f, "fmsr%c\t%y2, %12-15r"},
329 {FPU_VFP_EXT_V1xD, 0x0e100a10, 0x0ff00f7f, "fmrs%c\t%12-15r, %y2"},
330 {FPU_VFP_EXT_V1xD, 0x0eb50a40, 0x0fbf0f70, "fcmp%7'ezs%c\t%y1"},
331 {FPU_VFP_EXT_V1, 0x0eb50b40, 0x0fbf0f70, "fcmp%7'ezd%c\t%z1"},
332 {FPU_VFP_EXT_V1xD, 0x0eb00a40, 0x0fbf0fd0, "fcpys%c\t%y1, %y0"},
333 {FPU_VFP_EXT_V1xD, 0x0eb00ac0, 0x0fbf0fd0, "fabss%c\t%y1, %y0"},
334 {FPU_VFP_EXT_V1, 0x0eb00b40, 0x0fbf0fd0, "fcpyd%c\t%z1, %z0"},
335 {FPU_VFP_EXT_V1, 0x0eb00bc0, 0x0fbf0fd0, "fabsd%c\t%z1, %z0"},
336 {FPU_VFP_EXT_V1xD, 0x0eb10a40, 0x0fbf0fd0, "fnegs%c\t%y1, %y0"},
337 {FPU_VFP_EXT_V1xD, 0x0eb10ac0, 0x0fbf0fd0, "fsqrts%c\t%y1, %y0"},
338 {FPU_VFP_EXT_V1, 0x0eb10b40, 0x0fbf0fd0, "fnegd%c\t%z1, %z0"},
339 {FPU_VFP_EXT_V1, 0x0eb10bc0, 0x0fbf0fd0, "fsqrtd%c\t%z1, %z0"},
340 {FPU_VFP_EXT_V1, 0x0eb70ac0, 0x0fbf0fd0, "fcvtds%c\t%z1, %y0"},
341 {FPU_VFP_EXT_V1, 0x0eb70bc0, 0x0fbf0fd0, "fcvtsd%c\t%y1, %z0"},
342 {FPU_VFP_EXT_V1xD, 0x0eb80a40, 0x0fbf0fd0, "fuitos%c\t%y1, %y0"},
343 {FPU_VFP_EXT_V1xD, 0x0eb80ac0, 0x0fbf0fd0, "fsitos%c\t%y1, %y0"},
344 {FPU_VFP_EXT_V1, 0x0eb80b40, 0x0fbf0fd0, "fuitod%c\t%z1, %y0"},
345 {FPU_VFP_EXT_V1, 0x0eb80bc0, 0x0fbf0fd0, "fsitod%c\t%z1, %y0"},
346 {FPU_VFP_EXT_V1xD, 0x0eb40a40, 0x0fbf0f50, "fcmp%7'es%c\t%y1, %y0"},
347 {FPU_VFP_EXT_V1, 0x0eb40b40, 0x0fbf0f50, "fcmp%7'ed%c\t%z1, %z0"},
348 {FPU_VFP_EXT_V3, 0x0eba0a40, 0x0fbe0f50, "f%16?us%7?lhtos%c\t%y1, #%5,0-3k"},
349 {FPU_VFP_EXT_V3, 0x0eba0b40, 0x0fbe0f50, "f%16?us%7?lhtod%c\t%z1, #%5,0-3k"},
350 {FPU_VFP_EXT_V1xD, 0x0ebc0a40, 0x0fbe0f50, "fto%16?sui%7'zs%c\t%y1, %y0"},
351 {FPU_VFP_EXT_V1, 0x0ebc0b40, 0x0fbe0f50, "fto%16?sui%7'zd%c\t%y1, %z0"},
352 {FPU_VFP_EXT_V3, 0x0ebe0a40, 0x0fbe0f50, "fto%16?us%7?lhs%c\t%y1, #%5,0-3k"},
353 {FPU_VFP_EXT_V3, 0x0ebe0b40, 0x0fbe0f50, "fto%16?us%7?lhd%c\t%z1, #%5,0-3k"},
354 {FPU_VFP_EXT_V1, 0x0c500b10, 0x0fb00ff0, "fmrrd%c\t%12-15r, %16-19r, %z0"},
355 {FPU_VFP_EXT_V3, 0x0eb00a00, 0x0fb00ff0, "fconsts%c\t%y1, #%0-3,16-19d"},
356 {FPU_VFP_EXT_V3, 0x0eb00b00, 0x0fb00ff0, "fconstd%c\t%z1, #%0-3,16-19d"},
357 {FPU_VFP_EXT_V2, 0x0c400a10, 0x0ff00fd0, "fmsrr%c\t%y4, %12-15r, %16-19r"},
358 {FPU_VFP_EXT_V2, 0x0c400b10, 0x0ff00fd0, "fmdrr%c\t%z0, %12-15r, %16-19r"},
359 {FPU_VFP_EXT_V2, 0x0c500a10, 0x0ff00fd0, "fmrrs%c\t%12-15r, %16-19r, %y4"},
360 {FPU_VFP_EXT_V1xD, 0x0e000a00, 0x0fb00f50, "fmacs%c\t%y1, %y2, %y0"},
361 {FPU_VFP_EXT_V1xD, 0x0e000a40, 0x0fb00f50, "fnmacs%c\t%y1, %y2, %y0"},
362 {FPU_VFP_EXT_V1, 0x0e000b00, 0x0fb00f50, "fmacd%c\t%z1, %z2, %z0"},
363 {FPU_VFP_EXT_V1, 0x0e000b40, 0x0fb00f50, "fnmacd%c\t%z1, %z2, %z0"},
364 {FPU_VFP_EXT_V1xD, 0x0e100a00, 0x0fb00f50, "fmscs%c\t%y1, %y2, %y0"},
365 {FPU_VFP_EXT_V1xD, 0x0e100a40, 0x0fb00f50, "fnmscs%c\t%y1, %y2, %y0"},
366 {FPU_VFP_EXT_V1, 0x0e100b00, 0x0fb00f50, "fmscd%c\t%z1, %z2, %z0"},
367 {FPU_VFP_EXT_V1, 0x0e100b40, 0x0fb00f50, "fnmscd%c\t%z1, %z2, %z0"},
368 {FPU_VFP_EXT_V1xD, 0x0e200a00, 0x0fb00f50, "fmuls%c\t%y1, %y2, %y0"},
369 {FPU_VFP_EXT_V1xD, 0x0e200a40, 0x0fb00f50, "fnmuls%c\t%y1, %y2, %y0"},
370 {FPU_VFP_EXT_V1, 0x0e200b00, 0x0fb00f50, "fmuld%c\t%z1, %z2, %z0"},
371 {FPU_VFP_EXT_V1, 0x0e200b40, 0x0fb00f50, "fnmuld%c\t%z1, %z2, %z0"},
372 {FPU_VFP_EXT_V1xD, 0x0e300a00, 0x0fb00f50, "fadds%c\t%y1, %y2, %y0"},
373 {FPU_VFP_EXT_V1xD, 0x0e300a40, 0x0fb00f50, "fsubs%c\t%y1, %y2, %y0"},
374 {FPU_VFP_EXT_V1, 0x0e300b00, 0x0fb00f50, "faddd%c\t%z1, %z2, %z0"},
375 {FPU_VFP_EXT_V1, 0x0e300b40, 0x0fb00f50, "fsubd%c\t%z1, %z2, %z0"},
376 {FPU_VFP_EXT_V1xD, 0x0e800a00, 0x0fb00f50, "fdivs%c\t%y1, %y2, %y0"},
377 {FPU_VFP_EXT_V1, 0x0e800b00, 0x0fb00f50, "fdivd%c\t%z1, %z2, %z0"},
378 {FPU_VFP_EXT_V1xD, 0x0d200a00, 0x0fb00f00, "fstmdbs%c\t%16-19r!, %y3"},
379 {FPU_VFP_EXT_V1xD, 0x0d200b00, 0x0fb00f00, "fstmdb%0?xd%c\t%16-19r!, %z3"},
380 {FPU_VFP_EXT_V1xD, 0x0d300a00, 0x0fb00f00, "fldmdbs%c\t%16-19r!, %y3"},
381 {FPU_VFP_EXT_V1xD, 0x0d300b00, 0x0fb00f00, "fldmdb%0?xd%c\t%16-19r!, %z3"},
382 {FPU_VFP_EXT_V1xD, 0x0d000a00, 0x0f300f00, "fsts%c\t%y1, %A"},
383 {FPU_VFP_EXT_V1, 0x0d000b00, 0x0f300f00, "fstd%c\t%z1, %A"},
384 {FPU_VFP_EXT_V1xD, 0x0d100a00, 0x0f300f00, "flds%c\t%y1, %A"},
385 {FPU_VFP_EXT_V1, 0x0d100b00, 0x0f300f00, "fldd%c\t%z1, %A"},
386 {FPU_VFP_EXT_V1xD, 0x0c800a00, 0x0f900f00, "fstmias%c\t%16-19r%21'!, %y3"},
387 {FPU_VFP_EXT_V1xD, 0x0c800b00, 0x0f900f00, "fstmia%0?xd%c\t%16-19r%21'!, %z3"},
388 {FPU_VFP_EXT_V1xD, 0x0c900a00, 0x0f900f00, "fldmias%c\t%16-19r%21'!, %y3"},
389 {FPU_VFP_EXT_V1xD, 0x0c900b00, 0x0f900f00, "fldmia%0?xd%c\t%16-19r%21'!, %z3"},
391 /* Cirrus coprocessor instructions. */
392 {ARM_CEXT_MAVERICK, 0x0d100400, 0x0f500f00, "cfldrs%c\tmvf%12-15d, %A"},
393 {ARM_CEXT_MAVERICK, 0x0c100400, 0x0f500f00, "cfldrs%c\tmvf%12-15d, %A"},
394 {ARM_CEXT_MAVERICK, 0x0d500400, 0x0f500f00, "cfldrd%c\tmvd%12-15d, %A"},
395 {ARM_CEXT_MAVERICK, 0x0c500400, 0x0f500f00, "cfldrd%c\tmvd%12-15d, %A"},
396 {ARM_CEXT_MAVERICK, 0x0d100500, 0x0f500f00, "cfldr32%c\tmvfx%12-15d, %A"},
397 {ARM_CEXT_MAVERICK, 0x0c100500, 0x0f500f00, "cfldr32%c\tmvfx%12-15d, %A"},
398 {ARM_CEXT_MAVERICK, 0x0d500500, 0x0f500f00, "cfldr64%c\tmvdx%12-15d, %A"},
399 {ARM_CEXT_MAVERICK, 0x0c500500, 0x0f500f00, "cfldr64%c\tmvdx%12-15d, %A"},
400 {ARM_CEXT_MAVERICK, 0x0d000400, 0x0f500f00, "cfstrs%c\tmvf%12-15d, %A"},
401 {ARM_CEXT_MAVERICK, 0x0c000400, 0x0f500f00, "cfstrs%c\tmvf%12-15d, %A"},
402 {ARM_CEXT_MAVERICK, 0x0d400400, 0x0f500f00, "cfstrd%c\tmvd%12-15d, %A"},
403 {ARM_CEXT_MAVERICK, 0x0c400400, 0x0f500f00, "cfstrd%c\tmvd%12-15d, %A"},
404 {ARM_CEXT_MAVERICK, 0x0d000500, 0x0f500f00, "cfstr32%c\tmvfx%12-15d, %A"},
405 {ARM_CEXT_MAVERICK, 0x0c000500, 0x0f500f00, "cfstr32%c\tmvfx%12-15d, %A"},
406 {ARM_CEXT_MAVERICK, 0x0d400500, 0x0f500f00, "cfstr64%c\tmvdx%12-15d, %A"},
407 {ARM_CEXT_MAVERICK, 0x0c400500, 0x0f500f00, "cfstr64%c\tmvdx%12-15d, %A"},
408 {ARM_CEXT_MAVERICK, 0x0e000450, 0x0ff00ff0, "cfmvsr%c\tmvf%16-19d, %12-15r"},
409 {ARM_CEXT_MAVERICK, 0x0e100450, 0x0ff00ff0, "cfmvrs%c\t%12-15r, mvf%16-19d"},
410 {ARM_CEXT_MAVERICK, 0x0e000410, 0x0ff00ff0, "cfmvdlr%c\tmvd%16-19d, %12-15r"},
411 {ARM_CEXT_MAVERICK, 0x0e100410, 0x0ff00ff0, "cfmvrdl%c\t%12-15r, mvd%16-19d"},
412 {ARM_CEXT_MAVERICK, 0x0e000430, 0x0ff00ff0, "cfmvdhr%c\tmvd%16-19d, %12-15r"},
413 {ARM_CEXT_MAVERICK, 0x0e100430, 0x0ff00fff, "cfmvrdh%c\t%12-15r, mvd%16-19d"},
414 {ARM_CEXT_MAVERICK, 0x0e000510, 0x0ff00fff, "cfmv64lr%c\tmvdx%16-19d, %12-15r"},
415 {ARM_CEXT_MAVERICK, 0x0e100510, 0x0ff00fff, "cfmvr64l%c\t%12-15r, mvdx%16-19d"},
416 {ARM_CEXT_MAVERICK, 0x0e000530, 0x0ff00fff, "cfmv64hr%c\tmvdx%16-19d, %12-15r"},
417 {ARM_CEXT_MAVERICK, 0x0e100530, 0x0ff00fff, "cfmvr64h%c\t%12-15r, mvdx%16-19d"},
418 {ARM_CEXT_MAVERICK, 0x0e200440, 0x0ff00fff, "cfmval32%c\tmvax%12-15d, mvfx%16-19d"},
419 {ARM_CEXT_MAVERICK, 0x0e100440, 0x0ff00fff, "cfmv32al%c\tmvfx%12-15d, mvax%16-19d"},
420 {ARM_CEXT_MAVERICK, 0x0e200460, 0x0ff00fff, "cfmvam32%c\tmvax%12-15d, mvfx%16-19d"},
421 {ARM_CEXT_MAVERICK, 0x0e100460, 0x0ff00fff, "cfmv32am%c\tmvfx%12-15d, mvax%16-19d"},
422 {ARM_CEXT_MAVERICK, 0x0e200480, 0x0ff00fff, "cfmvah32%c\tmvax%12-15d, mvfx%16-19d"},
423 {ARM_CEXT_MAVERICK, 0x0e100480, 0x0ff00fff, "cfmv32ah%c\tmvfx%12-15d, mvax%16-19d"},
424 {ARM_CEXT_MAVERICK, 0x0e2004a0, 0x0ff00fff, "cfmva32%c\tmvax%12-15d, mvfx%16-19d"},
425 {ARM_CEXT_MAVERICK, 0x0e1004a0, 0x0ff00fff, "cfmv32a%c\tmvfx%12-15d, mvax%16-19d"},
426 {ARM_CEXT_MAVERICK, 0x0e2004c0, 0x0ff00fff, "cfmva64%c\tmvax%12-15d, mvdx%16-19d"},
427 {ARM_CEXT_MAVERICK, 0x0e1004c0, 0x0ff00fff, "cfmv64a%c\tmvdx%12-15d, mvax%16-19d"},
428 {ARM_CEXT_MAVERICK, 0x0e2004e0, 0x0fff0fff, "cfmvsc32%c\tdspsc, mvdx%12-15d"},
429 {ARM_CEXT_MAVERICK, 0x0e1004e0, 0x0fff0fff, "cfmv32sc%c\tmvdx%12-15d, dspsc"},
430 {ARM_CEXT_MAVERICK, 0x0e000400, 0x0ff00fff, "cfcpys%c\tmvf%12-15d, mvf%16-19d"},
431 {ARM_CEXT_MAVERICK, 0x0e000420, 0x0ff00fff, "cfcpyd%c\tmvd%12-15d, mvd%16-19d"},
432 {ARM_CEXT_MAVERICK, 0x0e000460, 0x0ff00fff, "cfcvtsd%c\tmvd%12-15d, mvf%16-19d"},
433 {ARM_CEXT_MAVERICK, 0x0e000440, 0x0ff00fff, "cfcvtds%c\tmvf%12-15d, mvd%16-19d"},
434 {ARM_CEXT_MAVERICK, 0x0e000480, 0x0ff00fff, "cfcvt32s%c\tmvf%12-15d, mvfx%16-19d"},
435 {ARM_CEXT_MAVERICK, 0x0e0004a0, 0x0ff00fff, "cfcvt32d%c\tmvd%12-15d, mvfx%16-19d"},
436 {ARM_CEXT_MAVERICK, 0x0e0004c0, 0x0ff00fff, "cfcvt64s%c\tmvf%12-15d, mvdx%16-19d"},
437 {ARM_CEXT_MAVERICK, 0x0e0004e0, 0x0ff00fff, "cfcvt64d%c\tmvd%12-15d, mvdx%16-19d"},
438 {ARM_CEXT_MAVERICK, 0x0e100580, 0x0ff00fff, "cfcvts32%c\tmvfx%12-15d, mvf%16-19d"},
439 {ARM_CEXT_MAVERICK, 0x0e1005a0, 0x0ff00fff, "cfcvtd32%c\tmvfx%12-15d, mvd%16-19d"},
440 {ARM_CEXT_MAVERICK, 0x0e1005c0, 0x0ff00fff, "cftruncs32%c\tmvfx%12-15d, mvf%16-19d"},
441 {ARM_CEXT_MAVERICK, 0x0e1005e0, 0x0ff00fff, "cftruncd32%c\tmvfx%12-15d, mvd%16-19d"},
442 {ARM_CEXT_MAVERICK, 0x0e000550, 0x0ff00ff0, "cfrshl32%c\tmvfx%16-19d, mvfx%0-3d, %12-15r"},
443 {ARM_CEXT_MAVERICK, 0x0e000570, 0x0ff00ff0, "cfrshl64%c\tmvdx%16-19d, mvdx%0-3d, %12-15r"},
444 {ARM_CEXT_MAVERICK, 0x0e000500, 0x0ff00f10, "cfsh32%c\tmvfx%12-15d, mvfx%16-19d, #%I"},
445 {ARM_CEXT_MAVERICK, 0x0e200500, 0x0ff00f10, "cfsh64%c\tmvdx%12-15d, mvdx%16-19d, #%I"},
446 {ARM_CEXT_MAVERICK, 0x0e100490, 0x0ff00ff0, "cfcmps%c\t%12-15r, mvf%16-19d, mvf%0-3d"},
447 {ARM_CEXT_MAVERICK, 0x0e1004b0, 0x0ff00ff0, "cfcmpd%c\t%12-15r, mvd%16-19d, mvd%0-3d"},
448 {ARM_CEXT_MAVERICK, 0x0e100590, 0x0ff00ff0, "cfcmp32%c\t%12-15r, mvfx%16-19d, mvfx%0-3d"},
449 {ARM_CEXT_MAVERICK, 0x0e1005b0, 0x0ff00ff0, "cfcmp64%c\t%12-15r, mvdx%16-19d, mvdx%0-3d"},
450 {ARM_CEXT_MAVERICK, 0x0e300400, 0x0ff00fff, "cfabss%c\tmvf%12-15d, mvf%16-19d"},
451 {ARM_CEXT_MAVERICK, 0x0e300420, 0x0ff00fff, "cfabsd%c\tmvd%12-15d, mvd%16-19d"},
452 {ARM_CEXT_MAVERICK, 0x0e300440, 0x0ff00fff, "cfnegs%c\tmvf%12-15d, mvf%16-19d"},
453 {ARM_CEXT_MAVERICK, 0x0e300460, 0x0ff00fff, "cfnegd%c\tmvd%12-15d, mvd%16-19d"},
454 {ARM_CEXT_MAVERICK, 0x0e300480, 0x0ff00ff0, "cfadds%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
455 {ARM_CEXT_MAVERICK, 0x0e3004a0, 0x0ff00ff0, "cfaddd%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
456 {ARM_CEXT_MAVERICK, 0x0e3004c0, 0x0ff00ff0, "cfsubs%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
457 {ARM_CEXT_MAVERICK, 0x0e3004e0, 0x0ff00ff0, "cfsubd%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
458 {ARM_CEXT_MAVERICK, 0x0e100400, 0x0ff00ff0, "cfmuls%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
459 {ARM_CEXT_MAVERICK, 0x0e100420, 0x0ff00ff0, "cfmuld%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
460 {ARM_CEXT_MAVERICK, 0x0e300500, 0x0ff00fff, "cfabs32%c\tmvfx%12-15d, mvfx%16-19d"},
461 {ARM_CEXT_MAVERICK, 0x0e300520, 0x0ff00fff, "cfabs64%c\tmvdx%12-15d, mvdx%16-19d"},
462 {ARM_CEXT_MAVERICK, 0x0e300540, 0x0ff00fff, "cfneg32%c\tmvfx%12-15d, mvfx%16-19d"},
463 {ARM_CEXT_MAVERICK, 0x0e300560, 0x0ff00fff, "cfneg64%c\tmvdx%12-15d, mvdx%16-19d"},
464 {ARM_CEXT_MAVERICK, 0x0e300580, 0x0ff00ff0, "cfadd32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
465 {ARM_CEXT_MAVERICK, 0x0e3005a0, 0x0ff00ff0, "cfadd64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
466 {ARM_CEXT_MAVERICK, 0x0e3005c0, 0x0ff00ff0, "cfsub32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
467 {ARM_CEXT_MAVERICK, 0x0e3005e0, 0x0ff00ff0, "cfsub64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
468 {ARM_CEXT_MAVERICK, 0x0e100500, 0x0ff00ff0, "cfmul32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
469 {ARM_CEXT_MAVERICK, 0x0e100520, 0x0ff00ff0, "cfmul64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
470 {ARM_CEXT_MAVERICK, 0x0e100540, 0x0ff00ff0, "cfmac32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
471 {ARM_CEXT_MAVERICK, 0x0e100560, 0x0ff00ff0, "cfmsc32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
472 {ARM_CEXT_MAVERICK, 0x0e000600, 0x0ff00f10, "cfmadd32%c\tmvax%5-7d, mvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
473 {ARM_CEXT_MAVERICK, 0x0e100600, 0x0ff00f10, "cfmsub32%c\tmvax%5-7d, mvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
474 {ARM_CEXT_MAVERICK, 0x0e200600, 0x0ff00f10, "cfmadda32%c\tmvax%5-7d, mvax%12-15d, mvfx%16-19d, mvfx%0-3d"},
475 {ARM_CEXT_MAVERICK, 0x0e300600, 0x0ff00f10, "cfmsuba32%c\tmvax%5-7d, mvax%12-15d, mvfx%16-19d, mvfx%0-3d"},
477 /* Generic coprocessor instructions */
478 {ARM_EXT_V2, 0x0c400000, 0x0ff00000, "mcrr%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
479 {ARM_EXT_V2, 0x0c500000, 0x0ff00000, "mrrc%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
480 {ARM_EXT_V2, 0x0e000000, 0x0f000010, "cdp%c\t%8-11d, %20-23d, cr%12-15d, cr%16-19d, cr%0-3d, {%5-7d}"},
481 {ARM_EXT_V2, 0x0e100010, 0x0f100010, "mrc%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
482 {ARM_EXT_V2, 0x0e000010, 0x0f100010, "mcr%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
483 {ARM_EXT_V2, 0x0c000000, 0x0e100000, "stc%22'l%c\t%8-11d, cr%12-15d, %A"},
484 {ARM_EXT_V2, 0x0c100000, 0x0e100000, "ldc%22'l%c\t%8-11d, cr%12-15d, %A"},
486 /* V6 coprocessor instructions */
487 {ARM_EXT_V6, 0xfc500000, 0xfff00000, "mrrc2%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
488 {ARM_EXT_V6, 0xfc400000, 0xfff00000, "mcrr2%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
490 /* V5 coprocessor instructions */
491 {ARM_EXT_V5, 0xfc100000, 0xfe100000, "ldc2%22'l%c\t%8-11d, cr%12-15d, %A"},
492 {ARM_EXT_V5, 0xfc000000, 0xfe100000, "stc2%22'l%c\t%8-11d, cr%12-15d, %A"},
493 {ARM_EXT_V5, 0xfe000000, 0xff000010, "cdp2%c\t%8-11d, %20-23d, cr%12-15d, cr%16-19d, cr%0-3d, {%5-7d}"},
494 {ARM_EXT_V5, 0xfe000010, 0xff100010, "mcr2%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
495 {ARM_EXT_V5, 0xfe100010, 0xff100010, "mrc2%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
497 {0, 0, 0, 0}
500 /* Neon opcode table: This does not encode the top byte -- that is
501 checked by the print_insn_neon routine, as it depends on whether we are
502 doing thumb32 or arm32 disassembly. */
504 /* print_insn_neon recognizes the following format control codes:
506 %% %
508 %c print condition code
509 %A print v{st,ld}[1234] operands
510 %B print v{st,ld}[1234] any one operands
511 %C print v{st,ld}[1234] single->all operands
512 %D print scalar
513 %E print vmov, vmvn, vorr, vbic encoded constant
514 %F print vtbl,vtbx register list
516 %<bitfield>r print as an ARM register
517 %<bitfield>d print the bitfield in decimal
518 %<bitfield>e print the 2^N - bitfield in decimal
519 %<bitfield>D print as a NEON D register
520 %<bitfield>Q print as a NEON Q register
521 %<bitfield>R print as a NEON D or Q register
522 %<bitfield>Sn print byte scaled width limited by n
523 %<bitfield>Tn print short scaled width limited by n
524 %<bitfield>Un print long scaled width limited by n
526 %<bitfield>'c print specified char iff bitfield is all ones
527 %<bitfield>`c print specified char iff bitfield is all zeroes
528 %<bitfield>?ab... select from array of values in big endian order */
530 static const struct opcode32 neon_opcodes[] =
532 /* Extract */
533 {FPU_NEON_EXT_V1, 0xf2b00840, 0xffb00850, "vext%c.8\t%12-15,22R, %16-19,7R, %0-3,5R, #%8-11d"},
534 {FPU_NEON_EXT_V1, 0xf2b00000, 0xffb00810, "vext%c.8\t%12-15,22R, %16-19,7R, %0-3,5R, #%8-11d"},
536 /* Move data element to all lanes */
537 {FPU_NEON_EXT_V1, 0xf3b40c00, 0xffb70f90, "vdup%c.32\t%12-15,22R, %0-3,5D[%19d]"},
538 {FPU_NEON_EXT_V1, 0xf3b20c00, 0xffb30f90, "vdup%c.16\t%12-15,22R, %0-3,5D[%18-19d]"},
539 {FPU_NEON_EXT_V1, 0xf3b10c00, 0xffb10f90, "vdup%c.8\t%12-15,22R, %0-3,5D[%17-19d]"},
541 /* Table lookup */
542 {FPU_NEON_EXT_V1, 0xf3b00800, 0xffb00c50, "vtbl%c.8\t%12-15,22D, %F, %0-3,5D"},
543 {FPU_NEON_EXT_V1, 0xf3b00840, 0xffb00c50, "vtbx%c.8\t%12-15,22D, %F, %0-3,5D"},
545 /* Two registers, miscellaneous */
546 {FPU_NEON_EXT_V1, 0xf2880a10, 0xfebf0fd0, "vmovl%c.%24?us8\t%12-15,22Q, %0-3,5D"},
547 {FPU_NEON_EXT_V1, 0xf2900a10, 0xfebf0fd0, "vmovl%c.%24?us16\t%12-15,22Q, %0-3,5D"},
548 {FPU_NEON_EXT_V1, 0xf2a00a10, 0xfebf0fd0, "vmovl%c.%24?us32\t%12-15,22Q, %0-3,5D"},
549 {FPU_NEON_EXT_V1, 0xf3b00500, 0xffbf0f90, "vcnt%c.8\t%12-15,22R, %0-3,5R"},
550 {FPU_NEON_EXT_V1, 0xf3b00580, 0xffbf0f90, "vmvn%c\t%12-15,22R, %0-3,5R"},
551 {FPU_NEON_EXT_V1, 0xf3b20000, 0xffbf0f90, "vswp%c\t%12-15,22R, %0-3,5R"},
552 {FPU_NEON_EXT_V1, 0xf3b20200, 0xffb30fd0, "vmovn%c.i%18-19T2\t%12-15,22D, %0-3,5Q"},
553 {FPU_NEON_EXT_V1, 0xf3b20240, 0xffb30fd0, "vqmovun%c.s%18-19T2\t%12-15,22D, %0-3,5Q"},
554 {FPU_NEON_EXT_V1, 0xf3b20280, 0xffb30fd0, "vqmovn%c.s%18-19T2\t%12-15,22D, %0-3,5Q"},
555 {FPU_NEON_EXT_V1, 0xf3b202c0, 0xffb30fd0, "vqmovn%c.u%18-19T2\t%12-15,22D, %0-3,5Q"},
556 {FPU_NEON_EXT_V1, 0xf3b20300, 0xffb30fd0, "vshll%c.i%18-19S2\t%12-15,22Q, %0-3,5D, #%18-19S2"},
557 {FPU_NEON_EXT_V1, 0xf3bb0400, 0xffbf0e90, "vrecpe%c.%8?fu%18-19S2\t%12-15,22R, %0-3,5R"},
558 {FPU_NEON_EXT_V1, 0xf3bb0480, 0xffbf0e90, "vrsqrte%c.%8?fu%18-19S2\t%12-15,22R, %0-3,5R"},
559 {FPU_NEON_EXT_V1, 0xf3b00000, 0xffb30f90, "vrev64%c.%18-19S2\t%12-15,22R, %0-3,5R"},
560 {FPU_NEON_EXT_V1, 0xf3b00080, 0xffb30f90, "vrev32%c.%18-19S2\t%12-15,22R, %0-3,5R"},
561 {FPU_NEON_EXT_V1, 0xf3b00100, 0xffb30f90, "vrev16%c.%18-19S2\t%12-15,22R, %0-3,5R"},
562 {FPU_NEON_EXT_V1, 0xf3b00400, 0xffb30f90, "vcls%c.s%18-19S2\t%12-15,22R, %0-3,5R"},
563 {FPU_NEON_EXT_V1, 0xf3b00480, 0xffb30f90, "vclz%c.i%18-19S2\t%12-15,22R, %0-3,5R"},
564 {FPU_NEON_EXT_V1, 0xf3b00700, 0xffb30f90, "vqabs%c.s%18-19S2\t%12-15,22R, %0-3,5R"},
565 {FPU_NEON_EXT_V1, 0xf3b00780, 0xffb30f90, "vqneg%c.s%18-19S2\t%12-15,22R, %0-3,5R"},
566 {FPU_NEON_EXT_V1, 0xf3b20080, 0xffb30f90, "vtrn%c.%18-19S2\t%12-15,22R, %0-3,5R"},
567 {FPU_NEON_EXT_V1, 0xf3b20100, 0xffb30f90, "vuzp%c.%18-19S2\t%12-15,22R, %0-3,5R"},
568 {FPU_NEON_EXT_V1, 0xf3b20180, 0xffb30f90, "vzip%c.%18-19S2\t%12-15,22R, %0-3,5R"},
569 {FPU_NEON_EXT_V1, 0xf3b10000, 0xffb30b90, "vcgt%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
570 {FPU_NEON_EXT_V1, 0xf3b10080, 0xffb30b90, "vcge%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
571 {FPU_NEON_EXT_V1, 0xf3b10100, 0xffb30b90, "vceq%c.%10?fi%18-19S2\t%12-15,22R, %0-3,5R, #0"},
572 {FPU_NEON_EXT_V1, 0xf3b10180, 0xffb30b90, "vcle%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
573 {FPU_NEON_EXT_V1, 0xf3b10200, 0xffb30b90, "vclt%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
574 {FPU_NEON_EXT_V1, 0xf3b10300, 0xffb30b90, "vabs%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R"},
575 {FPU_NEON_EXT_V1, 0xf3b10380, 0xffb30b90, "vneg%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R"},
576 {FPU_NEON_EXT_V1, 0xf3b00200, 0xffb30f10, "vpaddl%c.%7?us%18-19S2\t%12-15,22R, %0-3,5R"},
577 {FPU_NEON_EXT_V1, 0xf3b00600, 0xffb30f10, "vpadal%c.%7?us%18-19S2\t%12-15,22R, %0-3,5R"},
578 {FPU_NEON_EXT_V1, 0xf3b30600, 0xffb30e10, "vcvt%c.%7-8?usff%18-19Sa.%7-8?ffus%18-19Sa\t%12-15,22R, %0-3,5R"},
580 /* Three registers of the same length */
581 {FPU_NEON_EXT_V1, 0xf2000110, 0xffb00f10, "vand%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
582 {FPU_NEON_EXT_V1, 0xf2100110, 0xffb00f10, "vbic%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
583 {FPU_NEON_EXT_V1, 0xf2200110, 0xffb00f10, "vorr%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
584 {FPU_NEON_EXT_V1, 0xf2300110, 0xffb00f10, "vorn%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
585 {FPU_NEON_EXT_V1, 0xf3000110, 0xffb00f10, "veor%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
586 {FPU_NEON_EXT_V1, 0xf3100110, 0xffb00f10, "vbsl%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
587 {FPU_NEON_EXT_V1, 0xf3200110, 0xffb00f10, "vbit%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
588 {FPU_NEON_EXT_V1, 0xf3300110, 0xffb00f10, "vbif%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
589 {FPU_NEON_EXT_V1, 0xf2000d00, 0xffa00f10, "vadd%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
590 {FPU_NEON_EXT_V1, 0xf2000d10, 0xffa00f10, "vmla%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
591 {FPU_NEON_EXT_V1, 0xf2000e00, 0xffa00f10, "vceq%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
592 {FPU_NEON_EXT_V1, 0xf2000f00, 0xffa00f10, "vmax%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
593 {FPU_NEON_EXT_V1, 0xf2000f10, 0xffa00f10, "vrecps%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
594 {FPU_NEON_EXT_V1, 0xf2200d00, 0xffa00f10, "vsub%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
595 {FPU_NEON_EXT_V1, 0xf2200d10, 0xffa00f10, "vmls%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
596 {FPU_NEON_EXT_V1, 0xf2200f00, 0xffa00f10, "vmin%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
597 {FPU_NEON_EXT_V1, 0xf2200f10, 0xffa00f10, "vrsqrts%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
598 {FPU_NEON_EXT_V1, 0xf3000d00, 0xffa00f10, "vpadd%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
599 {FPU_NEON_EXT_V1, 0xf3000d10, 0xffa00f10, "vmul%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
600 {FPU_NEON_EXT_V1, 0xf3000e00, 0xffa00f10, "vcge%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
601 {FPU_NEON_EXT_V1, 0xf3000e10, 0xffa00f10, "vacge%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
602 {FPU_NEON_EXT_V1, 0xf3000f00, 0xffa00f10, "vpmax%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
603 {FPU_NEON_EXT_V1, 0xf3200d00, 0xffa00f10, "vabd%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
604 {FPU_NEON_EXT_V1, 0xf3200e00, 0xffa00f10, "vcgt%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
605 {FPU_NEON_EXT_V1, 0xf3200e10, 0xffa00f10, "vacgt%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
606 {FPU_NEON_EXT_V1, 0xf3200f00, 0xffa00f10, "vpmin%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
607 {FPU_NEON_EXT_V1, 0xf2000800, 0xff800f10, "vadd%c.i%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
608 {FPU_NEON_EXT_V1, 0xf2000810, 0xff800f10, "vtst%c.%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
609 {FPU_NEON_EXT_V1, 0xf2000900, 0xff800f10, "vmla%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
610 {FPU_NEON_EXT_V1, 0xf2000b00, 0xff800f10, "vqdmulh%c.s%20-21S6\t%12-15,22R, %16-19,7R, %0-3,5R"},
611 {FPU_NEON_EXT_V1, 0xf2000b10, 0xff800f10, "vpadd%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
612 {FPU_NEON_EXT_V1, 0xf3000800, 0xff800f10, "vsub%c.i%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
613 {FPU_NEON_EXT_V1, 0xf3000810, 0xff800f10, "vceq%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
614 {FPU_NEON_EXT_V1, 0xf3000900, 0xff800f10, "vmls%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
615 {FPU_NEON_EXT_V1, 0xf3000b00, 0xff800f10, "vqrdmulh%c.s%20-21S6\t%12-15,22R, %16-19,7R, %0-3,5R"},
616 {FPU_NEON_EXT_V1, 0xf2000000, 0xfe800f10, "vhadd%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
617 {FPU_NEON_EXT_V1, 0xf2000010, 0xfe800f10, "vqadd%c.%24?us%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
618 {FPU_NEON_EXT_V1, 0xf2000100, 0xfe800f10, "vrhadd%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
619 {FPU_NEON_EXT_V1, 0xf2000200, 0xfe800f10, "vhsub%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
620 {FPU_NEON_EXT_V1, 0xf2000210, 0xfe800f10, "vqsub%c.%24?us%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
621 {FPU_NEON_EXT_V1, 0xf2000300, 0xfe800f10, "vcgt%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
622 {FPU_NEON_EXT_V1, 0xf2000310, 0xfe800f10, "vcge%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
623 {FPU_NEON_EXT_V1, 0xf2000400, 0xfe800f10, "vshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
624 {FPU_NEON_EXT_V1, 0xf2000410, 0xfe800f10, "vqshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
625 {FPU_NEON_EXT_V1, 0xf2000500, 0xfe800f10, "vrshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
626 {FPU_NEON_EXT_V1, 0xf2000510, 0xfe800f10, "vqrshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
627 {FPU_NEON_EXT_V1, 0xf2000600, 0xfe800f10, "vmax%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
628 {FPU_NEON_EXT_V1, 0xf2000610, 0xfe800f10, "vmin%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
629 {FPU_NEON_EXT_V1, 0xf2000700, 0xfe800f10, "vabd%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
630 {FPU_NEON_EXT_V1, 0xf2000710, 0xfe800f10, "vaba%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
631 {FPU_NEON_EXT_V1, 0xf2000910, 0xfe800f10, "vmul%c.%24?pi%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
632 {FPU_NEON_EXT_V1, 0xf2000a00, 0xfe800f10, "vpmax%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
633 {FPU_NEON_EXT_V1, 0xf2000a10, 0xfe800f10, "vpmin%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
635 /* One register and an immediate value */
636 {FPU_NEON_EXT_V1, 0xf2800e10, 0xfeb80fb0, "vmov%c.i8\t%12-15,22R, %E"},
637 {FPU_NEON_EXT_V1, 0xf2800e30, 0xfeb80fb0, "vmov%c.i64\t%12-15,22R, %E"},
638 {FPU_NEON_EXT_V1, 0xf2800f10, 0xfeb80fb0, "vmov%c.f32\t%12-15,22R, %E"},
639 {FPU_NEON_EXT_V1, 0xf2800810, 0xfeb80db0, "vmov%c.i16\t%12-15,22R, %E"},
640 {FPU_NEON_EXT_V1, 0xf2800830, 0xfeb80db0, "vmvn%c.i16\t%12-15,22R, %E"},
641 {FPU_NEON_EXT_V1, 0xf2800910, 0xfeb80db0, "vorr%c.i16\t%12-15,22R, %E"},
642 {FPU_NEON_EXT_V1, 0xf2800930, 0xfeb80db0, "vbic%c.i16\t%12-15,22R, %E"},
643 {FPU_NEON_EXT_V1, 0xf2800c10, 0xfeb80eb0, "vmov%c.i32\t%12-15,22R, %E"},
644 {FPU_NEON_EXT_V1, 0xf2800c30, 0xfeb80eb0, "vmvn%c.i32\t%12-15,22R, %E"},
645 {FPU_NEON_EXT_V1, 0xf2800110, 0xfeb809b0, "vorr%c.i32\t%12-15,22R, %E"},
646 {FPU_NEON_EXT_V1, 0xf2800130, 0xfeb809b0, "vbic%c.i32\t%12-15,22R, %E"},
647 {FPU_NEON_EXT_V1, 0xf2800010, 0xfeb808b0, "vmov%c.i32\t%12-15,22R, %E"},
648 {FPU_NEON_EXT_V1, 0xf2800030, 0xfeb808b0, "vmvn%c.i32\t%12-15,22R, %E"},
650 /* Two registers and a shift amount */
651 {FPU_NEON_EXT_V1, 0xf2880810, 0xffb80fd0, "vshrn%c.i16\t%12-15,22D, %0-3,5Q, #%16-18e"},
652 {FPU_NEON_EXT_V1, 0xf2880850, 0xffb80fd0, "vrshrn%c.i16\t%12-15,22D, %0-3,5Q, #%16-18e"},
653 {FPU_NEON_EXT_V1, 0xf2880810, 0xfeb80fd0, "vqshrun%c.s16\t%12-15,22D, %0-3,5Q, #%16-18e"},
654 {FPU_NEON_EXT_V1, 0xf2880850, 0xfeb80fd0, "vqrshrun%c.s16\t%12-15,22D, %0-3,5Q, #%16-18e"},
655 {FPU_NEON_EXT_V1, 0xf2880910, 0xfeb80fd0, "vqshrn%c.%24?us16\t%12-15,22D, %0-3,5Q, #%16-18e"},
656 {FPU_NEON_EXT_V1, 0xf2880950, 0xfeb80fd0, "vqrshrn%c.%24?us16\t%12-15,22D, %0-3,5Q, #%16-18e"},
657 {FPU_NEON_EXT_V1, 0xf2880a10, 0xfeb80fd0, "vshll%c.%24?us8\t%12-15,22D, %0-3,5Q, #%16-18d"},
658 {FPU_NEON_EXT_V1, 0xf2900810, 0xffb00fd0, "vshrn%c.i32\t%12-15,22D, %0-3,5Q, #%16-19e"},
659 {FPU_NEON_EXT_V1, 0xf2900850, 0xffb00fd0, "vrshrn%c.i32\t%12-15,22D, %0-3,5Q, #%16-19e"},
660 {FPU_NEON_EXT_V1, 0xf2880510, 0xffb80f90, "vshl%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18d"},
661 {FPU_NEON_EXT_V1, 0xf3880410, 0xffb80f90, "vsri%c.8\t%12-15,22R, %0-3,5R, #%16-18e"},
662 {FPU_NEON_EXT_V1, 0xf3880510, 0xffb80f90, "vsli%c.8\t%12-15,22R, %0-3,5R, #%16-18d"},
663 {FPU_NEON_EXT_V1, 0xf3880610, 0xffb80f90, "vqshlu%c.s8\t%12-15,22R, %0-3,5R, #%16-18d"},
664 {FPU_NEON_EXT_V1, 0xf2900810, 0xfeb00fd0, "vqshrun%c.s32\t%12-15,22D, %0-3,5Q, #%16-19e"},
665 {FPU_NEON_EXT_V1, 0xf2900850, 0xfeb00fd0, "vqrshrun%c.s32\t%12-15,22D, %0-3,5Q, #%16-19e"},
666 {FPU_NEON_EXT_V1, 0xf2900910, 0xfeb00fd0, "vqshrn%c.%24?us32\t%12-15,22D, %0-3,5Q, #%16-19e"},
667 {FPU_NEON_EXT_V1, 0xf2900950, 0xfeb00fd0, "vqrshrn%c.%24?us32\t%12-15,22D, %0-3,5Q, #%16-19e"},
668 {FPU_NEON_EXT_V1, 0xf2900a10, 0xfeb00fd0, "vshll%c.%24?us16\t%12-15,22D, %0-3,5Q, #%16-19d"},
669 {FPU_NEON_EXT_V1, 0xf2880010, 0xfeb80f90, "vshr%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
670 {FPU_NEON_EXT_V1, 0xf2880110, 0xfeb80f90, "vsra%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
671 {FPU_NEON_EXT_V1, 0xf2880210, 0xfeb80f90, "vrshr%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
672 {FPU_NEON_EXT_V1, 0xf2880310, 0xfeb80f90, "vrsra%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
673 {FPU_NEON_EXT_V1, 0xf2880710, 0xfeb80f90, "vqshl%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18d"},
674 {FPU_NEON_EXT_V1, 0xf2a00810, 0xffa00fd0, "vshrn%c.i64\t%12-15,22D, %0-3,5Q, #%16-20e"},
675 {FPU_NEON_EXT_V1, 0xf2a00850, 0xffa00fd0, "vrshrn%c.i64\t%12-15,22D, %0-3,5Q, #%16-20e"},
676 {FPU_NEON_EXT_V1, 0xf2900510, 0xffb00f90, "vshl%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19d"},
677 {FPU_NEON_EXT_V1, 0xf3900410, 0xffb00f90, "vsri%c.16\t%12-15,22R, %0-3,5R, #%16-19e"},
678 {FPU_NEON_EXT_V1, 0xf3900510, 0xffb00f90, "vsli%c.16\t%12-15,22R, %0-3,5R, #%16-19d"},
679 {FPU_NEON_EXT_V1, 0xf3900610, 0xffb00f90, "vqshlu%c.s16\t%12-15,22R, %0-3,5R, #%16-19d"},
680 {FPU_NEON_EXT_V1, 0xf2a00a10, 0xfea00fd0, "vshll%c.%24?us32\t%12-15,22D, %0-3,5Q, #%16-20d"},
681 {FPU_NEON_EXT_V1, 0xf2900010, 0xfeb00f90, "vshr%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
682 {FPU_NEON_EXT_V1, 0xf2900110, 0xfeb00f90, "vsra%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
683 {FPU_NEON_EXT_V1, 0xf2900210, 0xfeb00f90, "vrshr%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
684 {FPU_NEON_EXT_V1, 0xf2900310, 0xfeb00f90, "vrsra%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
685 {FPU_NEON_EXT_V1, 0xf2900710, 0xfeb00f90, "vqshl%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19d"},
686 {FPU_NEON_EXT_V1, 0xf2800810, 0xfec00fd0, "vqshrun%c.s64\t%12-15,22D, %0-3,5Q, #%16-20e"},
687 {FPU_NEON_EXT_V1, 0xf2800850, 0xfec00fd0, "vqrshrun%c.s64\t%12-15,22D, %0-3,5Q, #%16-20e"},
688 {FPU_NEON_EXT_V1, 0xf2800910, 0xfec00fd0, "vqshrn%c.%24?us64\t%12-15,22D, %0-3,5Q, #%16-20e"},
689 {FPU_NEON_EXT_V1, 0xf2800950, 0xfec00fd0, "vqrshrn%c.%24?us64\t%12-15,22D, %0-3,5Q, #%16-20e"},
690 {FPU_NEON_EXT_V1, 0xf2a00510, 0xffa00f90, "vshl%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20d"},
691 {FPU_NEON_EXT_V1, 0xf3a00410, 0xffa00f90, "vsri%c.32\t%12-15,22R, %0-3,5R, #%16-20e"},
692 {FPU_NEON_EXT_V1, 0xf3a00510, 0xffa00f90, "vsli%c.32\t%12-15,22R, %0-3,5R, #%16-20d"},
693 {FPU_NEON_EXT_V1, 0xf3a00610, 0xffa00f90, "vqshlu%c.s32\t%12-15,22R, %0-3,5R, #%16-20d"},
694 {FPU_NEON_EXT_V1, 0xf2a00010, 0xfea00f90, "vshr%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
695 {FPU_NEON_EXT_V1, 0xf2a00110, 0xfea00f90, "vsra%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
696 {FPU_NEON_EXT_V1, 0xf2a00210, 0xfea00f90, "vrshr%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
697 {FPU_NEON_EXT_V1, 0xf2a00310, 0xfea00f90, "vrsra%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
698 {FPU_NEON_EXT_V1, 0xf2a00710, 0xfea00f90, "vqshl%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20d"},
699 {FPU_NEON_EXT_V1, 0xf2800590, 0xff800f90, "vshl%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21d"},
700 {FPU_NEON_EXT_V1, 0xf3800490, 0xff800f90, "vsri%c.64\t%12-15,22R, %0-3,5R, #%16-21e"},
701 {FPU_NEON_EXT_V1, 0xf3800590, 0xff800f90, "vsli%c.64\t%12-15,22R, %0-3,5R, #%16-21d"},
702 {FPU_NEON_EXT_V1, 0xf3800690, 0xff800f90, "vqshlu%c.s64\t%12-15,22R, %0-3,5R, #%16-21d"},
703 {FPU_NEON_EXT_V1, 0xf2800090, 0xfe800f90, "vshr%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
704 {FPU_NEON_EXT_V1, 0xf2800190, 0xfe800f90, "vsra%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
705 {FPU_NEON_EXT_V1, 0xf2800290, 0xfe800f90, "vrshr%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
706 {FPU_NEON_EXT_V1, 0xf2800390, 0xfe800f90, "vrsra%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
707 {FPU_NEON_EXT_V1, 0xf2800790, 0xfe800f90, "vqshl%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21d"},
708 {FPU_NEON_EXT_V1, 0xf2a00e10, 0xfea00e90, "vcvt%c.%24,8?usff32.%24,8?ffus32\t%12-15,22R, %0-3,5R, #%16-20e"},
710 /* Three registers of different lengths */
711 {FPU_NEON_EXT_V1, 0xf2800e00, 0xfea00f50, "vmull%c.p%20S0\t%12-15,22Q, %16-19,7D, %0-3,5D"},
712 {FPU_NEON_EXT_V1, 0xf2800400, 0xff800f50, "vaddhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
713 {FPU_NEON_EXT_V1, 0xf2800600, 0xff800f50, "vsubhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
714 {FPU_NEON_EXT_V1, 0xf2800900, 0xff800f50, "vqdmlal%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %0-3,5D"},
715 {FPU_NEON_EXT_V1, 0xf2800b00, 0xff800f50, "vqdmlsl%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %0-3,5D"},
716 {FPU_NEON_EXT_V1, 0xf2800d00, 0xff800f50, "vqdmull%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %0-3,5D"},
717 {FPU_NEON_EXT_V1, 0xf3800400, 0xff800f50, "vraddhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
718 {FPU_NEON_EXT_V1, 0xf3800600, 0xff800f50, "vrsubhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
719 {FPU_NEON_EXT_V1, 0xf2800000, 0xfe800f50, "vaddl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
720 {FPU_NEON_EXT_V1, 0xf2800100, 0xfe800f50, "vaddw%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7Q, %0-3,5D"},
721 {FPU_NEON_EXT_V1, 0xf2800200, 0xfe800f50, "vsubl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
722 {FPU_NEON_EXT_V1, 0xf2800300, 0xfe800f50, "vsubw%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7Q, %0-3,5D"},
723 {FPU_NEON_EXT_V1, 0xf2800500, 0xfe800f50, "vabal%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
724 {FPU_NEON_EXT_V1, 0xf2800700, 0xfe800f50, "vabdl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
725 {FPU_NEON_EXT_V1, 0xf2800800, 0xfe800f50, "vmlal%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
726 {FPU_NEON_EXT_V1, 0xf2800a00, 0xfe800f50, "vmlsl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
727 {FPU_NEON_EXT_V1, 0xf2800c00, 0xfe800f50, "vmull%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
729 /* Two registers and a scalar */
730 {FPU_NEON_EXT_V1, 0xf2800040, 0xff800f50, "vmla%c.i%20-21S6\t%12-15,22D, %16-19,7D, %D"},
731 {FPU_NEON_EXT_V1, 0xf2800140, 0xff800f50, "vmla%c.f%20-21Sa\t%12-15,22D, %16-19,7D, %D"},
732 {FPU_NEON_EXT_V1, 0xf2800340, 0xff800f50, "vqdmlal%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
733 {FPU_NEON_EXT_V1, 0xf2800440, 0xff800f50, "vmls%c.i%20-21S6\t%12-15,22D, %16-19,7D, %D"},
734 {FPU_NEON_EXT_V1, 0xf2800540, 0xff800f50, "vmls%c.f%20-21S6\t%12-15,22D, %16-19,7D, %D"},
735 {FPU_NEON_EXT_V1, 0xf2800740, 0xff800f50, "vqdmlsl%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
736 {FPU_NEON_EXT_V1, 0xf2800840, 0xff800f50, "vmul%c.i%20-21S6\t%12-15,22D, %16-19,7D, %D"},
737 {FPU_NEON_EXT_V1, 0xf2800940, 0xff800f50, "vmul%c.f%20-21Sa\t%12-15,22D, %16-19,7D, %D"},
738 {FPU_NEON_EXT_V1, 0xf2800b40, 0xff800f50, "vqdmull%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
739 {FPU_NEON_EXT_V1, 0xf2800c40, 0xff800f50, "vqdmulh%c.s%20-21S6\t%12-15,22D, %16-19,7D, %D"},
740 {FPU_NEON_EXT_V1, 0xf2800d40, 0xff800f50, "vqrdmulh%c.s%20-21S6\t%12-15,22D, %16-19,7D, %D"},
741 {FPU_NEON_EXT_V1, 0xf3800040, 0xff800f50, "vmla%c.i%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
742 {FPU_NEON_EXT_V1, 0xf3800140, 0xff800f50, "vmla%c.f%20-21Sa\t%12-15,22Q, %16-19,7Q, %D"},
743 {FPU_NEON_EXT_V1, 0xf3800440, 0xff800f50, "vmls%c.i%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
744 {FPU_NEON_EXT_V1, 0xf3800540, 0xff800f50, "vmls%c.f%20-21Sa\t%12-15,22Q, %16-19,7Q, %D"},
745 {FPU_NEON_EXT_V1, 0xf3800840, 0xff800f50, "vmul%c.i%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
746 {FPU_NEON_EXT_V1, 0xf3800940, 0xff800f50, "vmul%c.f%20-21Sa\t%12-15,22Q, %16-19,7Q, %D"},
747 {FPU_NEON_EXT_V1, 0xf3800c40, 0xff800f50, "vqdmulh%c.s%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
748 {FPU_NEON_EXT_V1, 0xf3800d40, 0xff800f50, "vqrdmulh%c.s%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
749 {FPU_NEON_EXT_V1, 0xf2800240, 0xfe800f50, "vmlal%c.%24?us%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
750 {FPU_NEON_EXT_V1, 0xf2800640, 0xfe800f50, "vmlsl%c.%24?us%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
751 {FPU_NEON_EXT_V1, 0xf2800a40, 0xfe800f50, "vmull%c.%24?us%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
753 /* Element and structure load/store */
754 {FPU_NEON_EXT_V1, 0xf4a00fc0, 0xffb00fc0, "vld4%c.32\t%C"},
755 {FPU_NEON_EXT_V1, 0xf4a00c00, 0xffb00f00, "vld1%c.%6-7S2\t%C"},
756 {FPU_NEON_EXT_V1, 0xf4a00d00, 0xffb00f00, "vld2%c.%6-7S2\t%C"},
757 {FPU_NEON_EXT_V1, 0xf4a00e00, 0xffb00f00, "vld3%c.%6-7S2\t%C"},
758 {FPU_NEON_EXT_V1, 0xf4a00f00, 0xffb00f00, "vld4%c.%6-7S2\t%C"},
759 {FPU_NEON_EXT_V1, 0xf4000200, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
760 {FPU_NEON_EXT_V1, 0xf4000300, 0xff900f00, "v%21?ls%21?dt2%c.%6-7S2\t%A"},
761 {FPU_NEON_EXT_V1, 0xf4000400, 0xff900f00, "v%21?ls%21?dt3%c.%6-7S2\t%A"},
762 {FPU_NEON_EXT_V1, 0xf4000500, 0xff900f00, "v%21?ls%21?dt3%c.%6-7S2\t%A"},
763 {FPU_NEON_EXT_V1, 0xf4000600, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
764 {FPU_NEON_EXT_V1, 0xf4000700, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
765 {FPU_NEON_EXT_V1, 0xf4000800, 0xff900f00, "v%21?ls%21?dt2%c.%6-7S2\t%A"},
766 {FPU_NEON_EXT_V1, 0xf4000900, 0xff900f00, "v%21?ls%21?dt2%c.%6-7S2\t%A"},
767 {FPU_NEON_EXT_V1, 0xf4000a00, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
768 {FPU_NEON_EXT_V1, 0xf4000000, 0xff900e00, "v%21?ls%21?dt4%c.%6-7S2\t%A"},
769 {FPU_NEON_EXT_V1, 0xf4800000, 0xff900300, "v%21?ls%21?dt1%c.%10-11S2\t%B"},
770 {FPU_NEON_EXT_V1, 0xf4800100, 0xff900300, "v%21?ls%21?dt2%c.%10-11S2\t%B"},
771 {FPU_NEON_EXT_V1, 0xf4800200, 0xff900300, "v%21?ls%21?dt3%c.%10-11S2\t%B"},
772 {FPU_NEON_EXT_V1, 0xf4800300, 0xff900300, "v%21?ls%21?dt4%c.%10-11S2\t%B"},
774 {0,0 ,0, 0}
777 /* Opcode tables: ARM, 16-bit Thumb, 32-bit Thumb. All three are partially
778 ordered: they must be searched linearly from the top to obtain a correct
779 match. */
781 /* print_insn_arm recognizes the following format control codes:
783 %% %
785 %a print address for ldr/str instruction
786 %s print address for ldr/str halfword/signextend instruction
787 %b print branch destination
788 %c print condition code (always bits 28-31)
789 %m print register mask for ldm/stm instruction
790 %o print operand2 (immediate or register + shift)
791 %p print 'p' iff bits 12-15 are 15
792 %t print 't' iff bit 21 set and bit 24 clear
793 %B print arm BLX(1) destination
794 %C print the PSR sub type.
795 %U print barrier type.
796 %P print address for pli instruction.
798 %<bitfield>r print as an ARM register
799 %<bitfield>d print the bitfield in decimal
800 %<bitfield>W print the bitfield plus one in decimal
801 %<bitfield>x print the bitfield in hex
802 %<bitfield>X print the bitfield as 1 hex digit without leading "0x"
804 %<bitfield>'c print specified char iff bitfield is all ones
805 %<bitfield>`c print specified char iff bitfield is all zeroes
806 %<bitfield>?ab... select from array of values in big endian order
808 %e print arm SMI operand (bits 0..7,8..19).
809 %E print the LSB and WIDTH fields of a BFI or BFC instruction.
810 %V print the 16-bit immediate field of a MOVT or MOVW instruction. */
812 static const struct opcode32 arm_opcodes[] =
814 /* ARM instructions. */
815 {ARM_EXT_V1, 0xe1a00000, 0xffffffff, "nop\t\t\t(mov r0,r0)"},
816 {ARM_EXT_V4T | ARM_EXT_V5, 0x012FFF10, 0x0ffffff0, "bx%c\t%0-3r"},
817 {ARM_EXT_V2, 0x00000090, 0x0fe000f0, "mul%20's%c\t%16-19r, %0-3r, %8-11r"},
818 {ARM_EXT_V2, 0x00200090, 0x0fe000f0, "mla%20's%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
819 {ARM_EXT_V2S, 0x01000090, 0x0fb00ff0, "swp%22'b%c\t%12-15r, %0-3r, [%16-19r]"},
820 {ARM_EXT_V3M, 0x00800090, 0x0fa000f0, "%22?sumull%20's%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
821 {ARM_EXT_V3M, 0x00a00090, 0x0fa000f0, "%22?sumlal%20's%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
823 /* IDIV instructions. */
824 {ARM_EXT_DIV, 0x0710f010, 0x0ff0f0f0, "sdiv%c\t%16-19r, %0-3r, %8-11r"},
825 {ARM_EXT_DIV, 0x0730f010, 0x0ff0f0f0, "udiv%c\t%16-19r, %0-3r, %8-11r"},
827 /* V7 instructions. */
828 {ARM_EXT_V7, 0xf450f000, 0xfd70f000, "pli\t%P"},
829 {ARM_EXT_V7, 0x0320f0f0, 0x0ffffff0, "dbg%c\t#%0-3d"},
830 {ARM_EXT_V7, 0xf57ff050, 0xfffffff0, "dmb\t%U"},
831 {ARM_EXT_V7, 0xf57ff040, 0xfffffff0, "dsb\t%U"},
832 {ARM_EXT_V7, 0xf57ff060, 0xfffffff0, "isb\t%U"},
834 /* ARM V6T2 instructions. */
835 {ARM_EXT_V6T2, 0x07c0001f, 0x0fe0007f, "bfc%c\t%12-15r, %E"},
836 {ARM_EXT_V6T2, 0x07c00010, 0x0fe00070, "bfi%c\t%12-15r, %0-3r, %E"},
837 {ARM_EXT_V6T2, 0x00600090, 0x0ff000f0, "mls%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
838 {ARM_EXT_V6T2, 0x006000b0, 0x0f7000f0, "strht%c\t%12-15r, %s"},
839 {ARM_EXT_V6T2, 0x00300090, 0x0f300090, "ldr%6's%5?hbt%c\t%12-15r, %s"},
840 {ARM_EXT_V6T2, 0x03000000, 0x0ff00000, "movw%c\t%12-15r, %V"},
841 {ARM_EXT_V6T2, 0x03400000, 0x0ff00000, "movt%c\t%12-15r, %V"},
842 {ARM_EXT_V6T2, 0x06ff0f30, 0x0fff0ff0, "rbit%c\t%12-15r, %0-3r"},
843 {ARM_EXT_V6T2, 0x07a00050, 0x0fa00070, "%22?usbfx%c\t%12-15r, %0-3r, #%7-11d, #%16-20W"},
845 /* ARM V6Z instructions. */
846 {ARM_EXT_V6Z, 0x01600070, 0x0ff000f0, "smc%c\t%e"},
848 /* ARM V6K instructions. */
849 {ARM_EXT_V6K, 0xf57ff01f, 0xffffffff, "clrex"},
850 {ARM_EXT_V6K, 0x01d00f9f, 0x0ff00fff, "ldrexb%c\t%12-15r, [%16-19r]"},
851 {ARM_EXT_V6K, 0x01b00f9f, 0x0ff00fff, "ldrexd%c\t%12-15r, [%16-19r]"},
852 {ARM_EXT_V6K, 0x01f00f9f, 0x0ff00fff, "ldrexh%c\t%12-15r, [%16-19r]"},
853 {ARM_EXT_V6K, 0x01c00f90, 0x0ff00ff0, "strexb%c\t%12-15r, %0-3r, [%16-19r]"},
854 {ARM_EXT_V6K, 0x01a00f90, 0x0ff00ff0, "strexd%c\t%12-15r, %0-3r, [%16-19r]"},
855 {ARM_EXT_V6K, 0x01e00f90, 0x0ff00ff0, "strexh%c\t%12-15r, %0-3r, [%16-19r]"},
857 /* ARM V6K NOP hints. */
858 {ARM_EXT_V6K, 0x0320f001, 0x0fffffff, "yield%c"},
859 {ARM_EXT_V6K, 0x0320f002, 0x0fffffff, "wfe%c"},
860 {ARM_EXT_V6K, 0x0320f003, 0x0fffffff, "wfi%c"},
861 {ARM_EXT_V6K, 0x0320f004, 0x0fffffff, "sev%c"},
862 {ARM_EXT_V6K, 0x0320f000, 0x0fffff00, "nop%c\t{%0-7d}"},
864 /* ARM V6 instructions. */
865 {ARM_EXT_V6, 0xf1080000, 0xfffffe3f, "cpsie\t%8'a%7'i%6'f"},
866 {ARM_EXT_V6, 0xf10a0000, 0xfffffe20, "cpsie\t%8'a%7'i%6'f,#%0-4d"},
867 {ARM_EXT_V6, 0xf10C0000, 0xfffffe3f, "cpsid\t%8'a%7'i%6'f"},
868 {ARM_EXT_V6, 0xf10e0000, 0xfffffe20, "cpsid\t%8'a%7'i%6'f,#%0-4d"},
869 {ARM_EXT_V6, 0xf1000000, 0xfff1fe20, "cps\t#%0-4d"},
870 {ARM_EXT_V6, 0x06800010, 0x0ff00ff0, "pkhbt%c\t%12-15r, %16-19r, %0-3r"},
871 {ARM_EXT_V6, 0x06800010, 0x0ff00070, "pkhbt%c\t%12-15r, %16-19r, %0-3r, lsl #%7-11d"},
872 {ARM_EXT_V6, 0x06800050, 0x0ff00ff0, "pkhtb%c\t%12-15r, %16-19r, %0-3r, asr #32"},
873 {ARM_EXT_V6, 0x06800050, 0x0ff00070, "pkhtb%c\t%12-15r, %16-19r, %0-3r, asr #%7-11d"},
874 {ARM_EXT_V6, 0x01900f9f, 0x0ff00fff, "ldrex%c\tr%12-15d, [%16-19r]"},
875 {ARM_EXT_V6, 0x06200f10, 0x0ff00ff0, "qadd16%c\t%12-15r, %16-19r, %0-3r"},
876 {ARM_EXT_V6, 0x06200f90, 0x0ff00ff0, "qadd8%c\t%12-15r, %16-19r, %0-3r"},
877 {ARM_EXT_V6, 0x06200f30, 0x0ff00ff0, "qaddsubx%c\t%12-15r, %16-19r, %0-3r"},
878 {ARM_EXT_V6, 0x06200f70, 0x0ff00ff0, "qsub16%c\t%12-15r, %16-19r, %0-3r"},
879 {ARM_EXT_V6, 0x06200ff0, 0x0ff00ff0, "qsub8%c\t%12-15r, %16-19r, %0-3r"},
880 {ARM_EXT_V6, 0x06200f50, 0x0ff00ff0, "qsubaddx%c\t%12-15r, %16-19r, %0-3r"},
881 {ARM_EXT_V6, 0x06100f10, 0x0ff00ff0, "sadd16%c\t%12-15r, %16-19r, %0-3r"},
882 {ARM_EXT_V6, 0x06100f90, 0x0ff00ff0, "sadd8%c\t%12-15r, %16-19r, %0-3r"},
883 {ARM_EXT_V6, 0x06100f30, 0x0ff00ff0, "saddaddx%c\t%12-15r, %16-19r, %0-3r"},
884 {ARM_EXT_V6, 0x06300f10, 0x0ff00ff0, "shadd16%c\t%12-15r, %16-19r, %0-3r"},
885 {ARM_EXT_V6, 0x06300f90, 0x0ff00ff0, "shadd8%c\t%12-15r, %16-19r, %0-3r"},
886 {ARM_EXT_V6, 0x06300f30, 0x0ff00ff0, "shaddsubx%c\t%12-15r, %16-19r, %0-3r"},
887 {ARM_EXT_V6, 0x06300f70, 0x0ff00ff0, "shsub16%c\t%12-15r, %16-19r, %0-3r"},
888 {ARM_EXT_V6, 0x06300ff0, 0x0ff00ff0, "shsub8%c\t%12-15r, %16-19r, %0-3r"},
889 {ARM_EXT_V6, 0x06300f50, 0x0ff00ff0, "shsubaddx%c\t%12-15r, %16-19r, %0-3r"},
890 {ARM_EXT_V6, 0x06100f70, 0x0ff00ff0, "ssub16%c\t%12-15r, %16-19r, %0-3r"},
891 {ARM_EXT_V6, 0x06100ff0, 0x0ff00ff0, "ssub8%c\t%12-15r, %16-19r, %0-3r"},
892 {ARM_EXT_V6, 0x06100f50, 0x0ff00ff0, "ssubaddx%c\t%12-15r, %16-19r, %0-3r"},
893 {ARM_EXT_V6, 0x06500f10, 0x0ff00ff0, "uadd16%c\t%12-15r, %16-19r, %0-3r"},
894 {ARM_EXT_V6, 0x06500f90, 0x0ff00ff0, "uadd8%c\t%12-15r, %16-19r, %0-3r"},
895 {ARM_EXT_V6, 0x06500f30, 0x0ff00ff0, "uaddsubx%c\t%12-15r, %16-19r, %0-3r"},
896 {ARM_EXT_V6, 0x06700f10, 0x0ff00ff0, "uhadd16%c\t%12-15r, %16-19r, %0-3r"},
897 {ARM_EXT_V6, 0x06700f90, 0x0ff00ff0, "uhadd8%c\t%12-15r, %16-19r, %0-3r"},
898 {ARM_EXT_V6, 0x06700f30, 0x0ff00ff0, "uhaddsubx%c\t%12-15r, %16-19r, %0-3r"},
899 {ARM_EXT_V6, 0x06700f70, 0x0ff00ff0, "uhsub16%c\t%12-15r, %16-19r, %0-3r"},
900 {ARM_EXT_V6, 0x06700ff0, 0x0ff00ff0, "uhsub8%c\t%12-15r, %16-19r, %0-3r"},
901 {ARM_EXT_V6, 0x06700f50, 0x0ff00ff0, "uhsubaddx%c\t%12-15r, %16-19r, %0-3r"},
902 {ARM_EXT_V6, 0x06600f10, 0x0ff00ff0, "uqadd16%c\t%12-15r, %16-19r, %0-3r"},
903 {ARM_EXT_V6, 0x06600f90, 0x0ff00ff0, "uqadd8%c\t%12-15r, %16-19r, %0-3r"},
904 {ARM_EXT_V6, 0x06600f30, 0x0ff00ff0, "uqaddsubx%c\t%12-15r, %16-19r, %0-3r"},
905 {ARM_EXT_V6, 0x06600f70, 0x0ff00ff0, "uqsub16%c\t%12-15r, %16-19r, %0-3r"},
906 {ARM_EXT_V6, 0x06600ff0, 0x0ff00ff0, "uqsub8%c\t%12-15r, %16-19r, %0-3r"},
907 {ARM_EXT_V6, 0x06600f50, 0x0ff00ff0, "uqsubaddx%c\t%12-15r, %16-19r, %0-3r"},
908 {ARM_EXT_V6, 0x06500f70, 0x0ff00ff0, "usub16%c\t%12-15r, %16-19r, %0-3r"},
909 {ARM_EXT_V6, 0x06500ff0, 0x0ff00ff0, "usub8%c\t%12-15r, %16-19r, %0-3r"},
910 {ARM_EXT_V6, 0x06500f50, 0x0ff00ff0, "usubaddx%c\t%12-15r, %16-19r, %0-3r"},
911 {ARM_EXT_V6, 0x06bf0f30, 0x0fff0ff0, "rev%c\t\%12-15r, %0-3r"},
912 {ARM_EXT_V6, 0x06bf0fb0, 0x0fff0ff0, "rev16%c\t\%12-15r, %0-3r"},
913 {ARM_EXT_V6, 0x06ff0fb0, 0x0fff0ff0, "revsh%c\t\%12-15r, %0-3r"},
914 {ARM_EXT_V6, 0xf8100a00, 0xfe50ffff, "rfe%23?id%24?ba\t\%16-19r%21'!"},
915 {ARM_EXT_V6, 0x06bf0070, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r"},
916 {ARM_EXT_V6, 0x06bf0470, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r, ror #8"},
917 {ARM_EXT_V6, 0x06bf0870, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r, ror #16"},
918 {ARM_EXT_V6, 0x06bf0c70, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r, ror #24"},
919 {ARM_EXT_V6, 0x068f0070, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r"},
920 {ARM_EXT_V6, 0x068f0470, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r, ror #8"},
921 {ARM_EXT_V6, 0x068f0870, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r, ror #16"},
922 {ARM_EXT_V6, 0x068f0c70, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r, ror #24"},
923 {ARM_EXT_V6, 0x06af0070, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r"},
924 {ARM_EXT_V6, 0x06af0470, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r, ror #8"},
925 {ARM_EXT_V6, 0x06af0870, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r, ror #16"},
926 {ARM_EXT_V6, 0x06af0c70, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r, ror #24"},
927 {ARM_EXT_V6, 0x06ff0070, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r"},
928 {ARM_EXT_V6, 0x06ff0470, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r, ror #8"},
929 {ARM_EXT_V6, 0x06ff0870, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r, ror #16"},
930 {ARM_EXT_V6, 0x06ff0c70, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r, ror #24"},
931 {ARM_EXT_V6, 0x06cf0070, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r"},
932 {ARM_EXT_V6, 0x06cf0470, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r, ror #8"},
933 {ARM_EXT_V6, 0x06cf0870, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r, ror #16"},
934 {ARM_EXT_V6, 0x06cf0c70, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r, ror #24"},
935 {ARM_EXT_V6, 0x06ef0070, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r"},
936 {ARM_EXT_V6, 0x06ef0470, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r, ror #8"},
937 {ARM_EXT_V6, 0x06ef0870, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r, ror #16"},
938 {ARM_EXT_V6, 0x06ef0c70, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r, ror #24"},
939 {ARM_EXT_V6, 0x06b00070, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r"},
940 {ARM_EXT_V6, 0x06b00470, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ror #8"},
941 {ARM_EXT_V6, 0x06b00870, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ror #16"},
942 {ARM_EXT_V6, 0x06b00c70, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ror #24"},
943 {ARM_EXT_V6, 0x06800070, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r"},
944 {ARM_EXT_V6, 0x06800470, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ror #8"},
945 {ARM_EXT_V6, 0x06800870, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ror #16"},
946 {ARM_EXT_V6, 0x06800c70, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ror #24"},
947 {ARM_EXT_V6, 0x06a00070, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r"},
948 {ARM_EXT_V6, 0x06a00470, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ror #8"},
949 {ARM_EXT_V6, 0x06a00870, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ror #16"},
950 {ARM_EXT_V6, 0x06a00c70, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ror #24"},
951 {ARM_EXT_V6, 0x06f00070, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r"},
952 {ARM_EXT_V6, 0x06f00470, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ror #8"},
953 {ARM_EXT_V6, 0x06f00870, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ror #16"},
954 {ARM_EXT_V6, 0x06f00c70, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ror #24"},
955 {ARM_EXT_V6, 0x06c00070, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r"},
956 {ARM_EXT_V6, 0x06c00470, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ror #8"},
957 {ARM_EXT_V6, 0x06c00870, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ror #16"},
958 {ARM_EXT_V6, 0x06c00c70, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
959 {ARM_EXT_V6, 0x06e00070, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r"},
960 {ARM_EXT_V6, 0x06e00470, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ror #8"},
961 {ARM_EXT_V6, 0x06e00870, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ror #16"},
962 {ARM_EXT_V6, 0x06e00c70, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ror #24"},
963 {ARM_EXT_V6, 0x06800fb0, 0x0ff00ff0, "sel%c\t%12-15r, %16-19r, %0-3r"},
964 {ARM_EXT_V6, 0xf1010000, 0xfffffc00, "setend\t%9?ble"},
965 {ARM_EXT_V6, 0x0700f010, 0x0ff0f0d0, "smuad%5'x%c\t%16-19r, %0-3r, %8-11r"},
966 {ARM_EXT_V6, 0x0700f050, 0x0ff0f0d0, "smusd%5'x%c\t%16-19r, %0-3r, %8-11r"},
967 {ARM_EXT_V6, 0x07000010, 0x0ff000d0, "smlad%5'x%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
968 {ARM_EXT_V6, 0x07400010, 0x0ff000d0, "smlald%5'x%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
969 {ARM_EXT_V6, 0x07000050, 0x0ff000d0, "smlsd%5'x%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
970 {ARM_EXT_V6, 0x07400050, 0x0ff000d0, "smlsld%5'x%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
971 {ARM_EXT_V6, 0x0750f010, 0x0ff0f0d0, "smmul%5'r%c\t%16-19r, %0-3r, %8-11r"},
972 {ARM_EXT_V6, 0x07500010, 0x0ff000d0, "smmla%5'r%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
973 {ARM_EXT_V6, 0x075000d0, 0x0ff000d0, "smmls%5'r%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
974 {ARM_EXT_V6, 0xf84d0500, 0xfe5fffe0, "srs%23?id%24?ba\t%16-19r%21'!, #%0-4d"},
975 {ARM_EXT_V6, 0x06a00010, 0x0fe00ff0, "ssat%c\t%12-15r, #%16-20W, %0-3r"},
976 {ARM_EXT_V6, 0x06a00010, 0x0fe00070, "ssat%c\t%12-15r, #%16-20W, %0-3r, lsl #%7-11d"},
977 {ARM_EXT_V6, 0x06a00050, 0x0fe00070, "ssat%c\t%12-15r, #%16-20W, %0-3r, asr #%7-11d"},
978 {ARM_EXT_V6, 0x06a00f30, 0x0ff00ff0, "ssat16%c\t%12-15r, #%16-19W, %0-3r"},
979 {ARM_EXT_V6, 0x01800f90, 0x0ff00ff0, "strex%c\t%12-15r, %0-3r, [%16-19r]"},
980 {ARM_EXT_V6, 0x00400090, 0x0ff000f0, "umaal%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
981 {ARM_EXT_V6, 0x0780f010, 0x0ff0f0f0, "usad8%c\t%16-19r, %0-3r, %8-11r"},
982 {ARM_EXT_V6, 0x07800010, 0x0ff000f0, "usada8%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
983 {ARM_EXT_V6, 0x06e00010, 0x0fe00ff0, "usat%c\t%12-15r, #%16-20d, %0-3r"},
984 {ARM_EXT_V6, 0x06e00010, 0x0fe00070, "usat%c\t%12-15r, #%16-20d, %0-3r, lsl #%7-11d"},
985 {ARM_EXT_V6, 0x06e00050, 0x0fe00070, "usat%c\t%12-15r, #%16-20d, %0-3r, asr #%7-11d"},
986 {ARM_EXT_V6, 0x06e00f30, 0x0ff00ff0, "usat16%c\t%12-15r, #%16-19d, %0-3r"},
988 /* V5J instruction. */
989 {ARM_EXT_V5J, 0x012fff20, 0x0ffffff0, "bxj%c\t%0-3r"},
991 /* V5 Instructions. */
992 {ARM_EXT_V5, 0xe1200070, 0xfff000f0, "bkpt\t0x%16-19X%12-15X%8-11X%0-3X"},
993 {ARM_EXT_V5, 0xfa000000, 0xfe000000, "blx\t%B"},
994 {ARM_EXT_V5, 0x012fff30, 0x0ffffff0, "blx%c\t%0-3r"},
995 {ARM_EXT_V5, 0x016f0f10, 0x0fff0ff0, "clz%c\t%12-15r, %0-3r"},
997 /* V5E "El Segundo" Instructions. */
998 {ARM_EXT_V5E, 0x000000d0, 0x0e1000f0, "ldrd%c\t%12-15r, %s"},
999 {ARM_EXT_V5E, 0x000000f0, 0x0e1000f0, "strd%c\t%12-15r, %s"},
1000 {ARM_EXT_V5E, 0xf450f000, 0xfc70f000, "pld\t%a"},
1001 {ARM_EXT_V5ExP, 0x01000080, 0x0ff000f0, "smlabb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
1002 {ARM_EXT_V5ExP, 0x010000a0, 0x0ff000f0, "smlatb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
1003 {ARM_EXT_V5ExP, 0x010000c0, 0x0ff000f0, "smlabt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
1004 {ARM_EXT_V5ExP, 0x010000e0, 0x0ff000f0, "smlatt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
1006 {ARM_EXT_V5ExP, 0x01200080, 0x0ff000f0, "smlawb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
1007 {ARM_EXT_V5ExP, 0x012000c0, 0x0ff000f0, "smlawt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
1009 {ARM_EXT_V5ExP, 0x01400080, 0x0ff000f0, "smlalbb%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1010 {ARM_EXT_V5ExP, 0x014000a0, 0x0ff000f0, "smlaltb%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1011 {ARM_EXT_V5ExP, 0x014000c0, 0x0ff000f0, "smlalbt%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1012 {ARM_EXT_V5ExP, 0x014000e0, 0x0ff000f0, "smlaltt%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1014 {ARM_EXT_V5ExP, 0x01600080, 0x0ff0f0f0, "smulbb%c\t%16-19r, %0-3r, %8-11r"},
1015 {ARM_EXT_V5ExP, 0x016000a0, 0x0ff0f0f0, "smultb%c\t%16-19r, %0-3r, %8-11r"},
1016 {ARM_EXT_V5ExP, 0x016000c0, 0x0ff0f0f0, "smulbt%c\t%16-19r, %0-3r, %8-11r"},
1017 {ARM_EXT_V5ExP, 0x016000e0, 0x0ff0f0f0, "smultt%c\t%16-19r, %0-3r, %8-11r"},
1019 {ARM_EXT_V5ExP, 0x012000a0, 0x0ff0f0f0, "smulwb%c\t%16-19r, %0-3r, %8-11r"},
1020 {ARM_EXT_V5ExP, 0x012000e0, 0x0ff0f0f0, "smulwt%c\t%16-19r, %0-3r, %8-11r"},
1022 {ARM_EXT_V5ExP, 0x01000050, 0x0ff00ff0, "qadd%c\t%12-15r, %0-3r, %16-19r"},
1023 {ARM_EXT_V5ExP, 0x01400050, 0x0ff00ff0, "qdadd%c\t%12-15r, %0-3r, %16-19r"},
1024 {ARM_EXT_V5ExP, 0x01200050, 0x0ff00ff0, "qsub%c\t%12-15r, %0-3r, %16-19r"},
1025 {ARM_EXT_V5ExP, 0x01600050, 0x0ff00ff0, "qdsub%c\t%12-15r, %0-3r, %16-19r"},
1027 /* ARM Instructions. */
1028 {ARM_EXT_V1, 0x00000090, 0x0e100090, "str%6's%5?hb%c\t%12-15r, %s"},
1029 {ARM_EXT_V1, 0x00100090, 0x0e100090, "ldr%6's%5?hb%c\t%12-15r, %s"},
1030 {ARM_EXT_V1, 0x00000000, 0x0de00000, "and%20's%c\t%12-15r, %16-19r, %o"},
1031 {ARM_EXT_V1, 0x00200000, 0x0de00000, "eor%20's%c\t%12-15r, %16-19r, %o"},
1032 {ARM_EXT_V1, 0x00400000, 0x0de00000, "sub%20's%c\t%12-15r, %16-19r, %o"},
1033 {ARM_EXT_V1, 0x00600000, 0x0de00000, "rsb%20's%c\t%12-15r, %16-19r, %o"},
1034 {ARM_EXT_V1, 0x00800000, 0x0de00000, "add%20's%c\t%12-15r, %16-19r, %o"},
1035 {ARM_EXT_V1, 0x00a00000, 0x0de00000, "adc%20's%c\t%12-15r, %16-19r, %o"},
1036 {ARM_EXT_V1, 0x00c00000, 0x0de00000, "sbc%20's%c\t%12-15r, %16-19r, %o"},
1037 {ARM_EXT_V1, 0x00e00000, 0x0de00000, "rsc%20's%c\t%12-15r, %16-19r, %o"},
1038 {ARM_EXT_V3, 0x0120f000, 0x0db0f000, "msr%c\t%22?SCPSR%C, %o"},
1039 {ARM_EXT_V3, 0x010f0000, 0x0fbf0fff, "mrs%c\t%12-15r, %22?SCPSR"},
1040 {ARM_EXT_V1, 0x01000000, 0x0de00000, "tst%p%c\t%16-19r, %o"},
1041 {ARM_EXT_V1, 0x01200000, 0x0de00000, "teq%p%c\t%16-19r, %o"},
1042 {ARM_EXT_V1, 0x01400000, 0x0de00000, "cmp%p%c\t%16-19r, %o"},
1043 {ARM_EXT_V1, 0x01600000, 0x0de00000, "cmn%p%c\t%16-19r, %o"},
1044 {ARM_EXT_V1, 0x01800000, 0x0de00000, "orr%20's%c\t%12-15r, %16-19r, %o"},
1045 {ARM_EXT_V1, 0x03a00000, 0x0fef0000, "mov%20's%c\t%12-15r, %o"},
1046 {ARM_EXT_V1, 0x01a00000, 0x0def0ff0, "mov%20's%c\t%12-15r, %0-3r"},
1047 {ARM_EXT_V1, 0x01a00000, 0x0def0060, "lsl%20's%c\t%12-15r, %q"},
1048 {ARM_EXT_V1, 0x01a00020, 0x0def0060, "lsr%20's%c\t%12-15r, %q"},
1049 {ARM_EXT_V1, 0x01a00040, 0x0def0060, "asr%20's%c\t%12-15r, %q"},
1050 {ARM_EXT_V1, 0x01a00060, 0x0def0ff0, "rrx%20's%c\t%12-15r, %0-3r"},
1051 {ARM_EXT_V1, 0x01a00060, 0x0def0060, "ror%20's%c\t%12-15r, %q"},
1052 {ARM_EXT_V1, 0x01c00000, 0x0de00000, "bic%20's%c\t%12-15r, %16-19r, %o"},
1053 {ARM_EXT_V1, 0x01e00000, 0x0de00000, "mvn%20's%c\t%12-15r, %o"},
1054 {ARM_EXT_V1, 0x052d0004, 0x0fff0fff, "push%c\t{%12-15r}\t\t; (str%c %12-15r, %a)"},
1055 {ARM_EXT_V1, 0x04000000, 0x0e100000, "str%22'b%t%c\t%12-15r, %a"},
1056 {ARM_EXT_V1, 0x06000000, 0x0e100ff0, "str%22'b%t%c\t%12-15r, %a"},
1057 {ARM_EXT_V1, 0x04000000, 0x0c100010, "str%22'b%t%c\t%12-15r, %a"},
1058 {ARM_EXT_V1, 0x06000010, 0x0e000010, "undefined"},
1059 {ARM_EXT_V1, 0x049d0004, 0x0fff0fff, "pop%c\t{%12-15r}\t\t; (ldr%c %12-15r, %a)"},
1060 {ARM_EXT_V1, 0x04100000, 0x0c100000, "ldr%22'b%t%c\t%12-15r, %a"},
1061 {ARM_EXT_V1, 0x092d0000, 0x0fff0000, "push%c\t%m"},
1062 {ARM_EXT_V1, 0x08800000, 0x0ff00000, "stm%c\t%16-19r%21'!, %m%22'^"},
1063 {ARM_EXT_V1, 0x08000000, 0x0e100000, "stm%23?id%24?ba%c\t%16-19r%21'!, %m%22'^"},
1064 {ARM_EXT_V1, 0x08bd0000, 0x0fff0000, "pop%c\t%m"},
1065 {ARM_EXT_V1, 0x08900000, 0x0f900000, "ldm%c\t%16-19r%21'!, %m%22'^"},
1066 {ARM_EXT_V1, 0x08100000, 0x0e100000, "ldm%23?id%24?ba%c\t%16-19r%21'!, %m%22'^"},
1067 {ARM_EXT_V1, 0x0a000000, 0x0e000000, "b%24'l%c\t%b"},
1068 {ARM_EXT_V1, 0x0f000000, 0x0f000000, "svc%c\t%0-23x"},
1070 /* The rest. */
1071 {ARM_EXT_V1, 0x00000000, 0x00000000, "undefined instruction %0-31x"},
1072 {0, 0x00000000, 0x00000000, 0}
1075 /* print_insn_thumb16 recognizes the following format control codes:
1077 %S print Thumb register (bits 3..5 as high number if bit 6 set)
1078 %D print Thumb register (bits 0..2 as high number if bit 7 set)
1079 %<bitfield>I print bitfield as a signed decimal
1080 (top bit of range being the sign bit)
1081 %N print Thumb register mask (with LR)
1082 %O print Thumb register mask (with PC)
1083 %M print Thumb register mask
1084 %b print CZB's 6-bit unsigned branch destination
1085 %s print Thumb right-shift immediate (6..10; 0 == 32).
1086 %c print the condition code
1087 %C print the condition code, or "s" if not conditional
1088 %x print warning if conditional an not at end of IT block"
1089 %X print "\t; unpredictable <IT:code>" if conditional
1090 %I print IT instruction suffix and operands
1091 %<bitfield>r print bitfield as an ARM register
1092 %<bitfield>d print bitfield as a decimal
1093 %<bitfield>H print (bitfield * 2) as a decimal
1094 %<bitfield>W print (bitfield * 4) as a decimal
1095 %<bitfield>a print (bitfield * 4) as a pc-rel offset + decoded symbol
1096 %<bitfield>B print Thumb branch destination (signed displacement)
1097 %<bitfield>c print bitfield as a condition code
1098 %<bitnum>'c print specified char iff bit is one
1099 %<bitnum>?ab print a if bit is one else print b. */
1101 static const struct opcode16 thumb_opcodes[] =
1103 /* Thumb instructions. */
1105 /* ARM V6K no-argument instructions. */
1106 {ARM_EXT_V6K, 0xbf00, 0xffff, "nop%c"},
1107 {ARM_EXT_V6K, 0xbf10, 0xffff, "yield%c"},
1108 {ARM_EXT_V6K, 0xbf20, 0xffff, "wfe%c"},
1109 {ARM_EXT_V6K, 0xbf30, 0xffff, "wfi%c"},
1110 {ARM_EXT_V6K, 0xbf40, 0xffff, "sev%c"},
1111 {ARM_EXT_V6K, 0xbf00, 0xff0f, "nop%c\t{%4-7d}"},
1113 /* ARM V6T2 instructions. */
1114 {ARM_EXT_V6T2, 0xb900, 0xfd00, "cbnz\t%0-2r, %b%X"},
1115 {ARM_EXT_V6T2, 0xb100, 0xfd00, "cbz\t%0-2r, %b%X"},
1116 {ARM_EXT_V6T2, 0xbf00, 0xff00, "it%I%X"},
1118 /* ARM V6. */
1119 {ARM_EXT_V6, 0xb660, 0xfff8, "cpsie\t%2'a%1'i%0'f%X"},
1120 {ARM_EXT_V6, 0xb670, 0xfff8, "cpsid\t%2'a%1'i%0'f%X"},
1121 {ARM_EXT_V6, 0x4600, 0xffc0, "mov%c\t%0-2r, %3-5r"},
1122 {ARM_EXT_V6, 0xba00, 0xffc0, "rev%c\t%0-2r, %3-5r"},
1123 {ARM_EXT_V6, 0xba40, 0xffc0, "rev16%c\t%0-2r, %3-5r"},
1124 {ARM_EXT_V6, 0xbac0, 0xffc0, "revsh%c\t%0-2r, %3-5r"},
1125 {ARM_EXT_V6, 0xb650, 0xfff7, "setend\t%3?ble%X"},
1126 {ARM_EXT_V6, 0xb200, 0xffc0, "sxth%c\t%0-2r, %3-5r"},
1127 {ARM_EXT_V6, 0xb240, 0xffc0, "sxtb%c\t%0-2r, %3-5r"},
1128 {ARM_EXT_V6, 0xb280, 0xffc0, "uxth%c\t%0-2r, %3-5r"},
1129 {ARM_EXT_V6, 0xb2c0, 0xffc0, "uxtb%c\t%0-2r, %3-5r"},
1131 /* ARM V5 ISA extends Thumb. */
1132 {ARM_EXT_V5T, 0xbe00, 0xff00, "bkpt\t%0-7x"}, /* Is always unconditional. */
1133 /* This is BLX(2). BLX(1) is a 32-bit instruction. */
1134 {ARM_EXT_V5T, 0x4780, 0xff87, "blx%c\t%3-6r%x"}, /* note: 4 bit register number. */
1135 /* ARM V4T ISA (Thumb v1). */
1136 {ARM_EXT_V4T, 0x46C0, 0xFFFF, "nop%c\t\t\t(mov r8, r8)"},
1137 /* Format 4. */
1138 {ARM_EXT_V4T, 0x4000, 0xFFC0, "and%C\t%0-2r, %3-5r"},
1139 {ARM_EXT_V4T, 0x4040, 0xFFC0, "eor%C\t%0-2r, %3-5r"},
1140 {ARM_EXT_V4T, 0x4080, 0xFFC0, "lsl%C\t%0-2r, %3-5r"},
1141 {ARM_EXT_V4T, 0x40C0, 0xFFC0, "lsr%C\t%0-2r, %3-5r"},
1142 {ARM_EXT_V4T, 0x4100, 0xFFC0, "asr%C\t%0-2r, %3-5r"},
1143 {ARM_EXT_V4T, 0x4140, 0xFFC0, "adc%C\t%0-2r, %3-5r"},
1144 {ARM_EXT_V4T, 0x4180, 0xFFC0, "sbc%C\t%0-2r, %3-5r"},
1145 {ARM_EXT_V4T, 0x41C0, 0xFFC0, "ror%C\t%0-2r, %3-5r"},
1146 {ARM_EXT_V4T, 0x4200, 0xFFC0, "tst%c\t%0-2r, %3-5r"},
1147 {ARM_EXT_V4T, 0x4240, 0xFFC0, "neg%C\t%0-2r, %3-5r"},
1148 {ARM_EXT_V4T, 0x4280, 0xFFC0, "cmp%c\t%0-2r, %3-5r"},
1149 {ARM_EXT_V4T, 0x42C0, 0xFFC0, "cmn%c\t%0-2r, %3-5r"},
1150 {ARM_EXT_V4T, 0x4300, 0xFFC0, "orr%C\t%0-2r, %3-5r"},
1151 {ARM_EXT_V4T, 0x4340, 0xFFC0, "mul%C\t%0-2r, %3-5r"},
1152 {ARM_EXT_V4T, 0x4380, 0xFFC0, "bic%C\t%0-2r, %3-5r"},
1153 {ARM_EXT_V4T, 0x43C0, 0xFFC0, "mvn%C\t%0-2r, %3-5r"},
1154 /* format 13 */
1155 {ARM_EXT_V4T, 0xB000, 0xFF80, "add%c\tsp, #%0-6W"},
1156 {ARM_EXT_V4T, 0xB080, 0xFF80, "sub%c\tsp, #%0-6W"},
1157 /* format 5 */
1158 {ARM_EXT_V4T, 0x4700, 0xFF80, "bx%c\t%S%x"},
1159 {ARM_EXT_V4T, 0x4400, 0xFF00, "add%c\t%D, %S"},
1160 {ARM_EXT_V4T, 0x4500, 0xFF00, "cmp%c\t%D, %S"},
1161 {ARM_EXT_V4T, 0x4600, 0xFF00, "mov%c\t%D, %S"},
1162 /* format 14 */
1163 {ARM_EXT_V4T, 0xB400, 0xFE00, "push%c\t%N"},
1164 {ARM_EXT_V4T, 0xBC00, 0xFE00, "pop%c\t%O"},
1165 /* format 2 */
1166 {ARM_EXT_V4T, 0x1800, 0xFE00, "add%C\t%0-2r, %3-5r, %6-8r"},
1167 {ARM_EXT_V4T, 0x1A00, 0xFE00, "sub%C\t%0-2r, %3-5r, %6-8r"},
1168 {ARM_EXT_V4T, 0x1C00, 0xFE00, "add%C\t%0-2r, %3-5r, #%6-8d"},
1169 {ARM_EXT_V4T, 0x1E00, 0xFE00, "sub%C\t%0-2r, %3-5r, #%6-8d"},
1170 /* format 8 */
1171 {ARM_EXT_V4T, 0x5200, 0xFE00, "strh%c\t%0-2r, [%3-5r, %6-8r]"},
1172 {ARM_EXT_V4T, 0x5A00, 0xFE00, "ldrh%c\t%0-2r, [%3-5r, %6-8r]"},
1173 {ARM_EXT_V4T, 0x5600, 0xF600, "ldrs%11?hb%c\t%0-2r, [%3-5r, %6-8r]"},
1174 /* format 7 */
1175 {ARM_EXT_V4T, 0x5000, 0xFA00, "str%10'b%c\t%0-2r, [%3-5r, %6-8r]"},
1176 {ARM_EXT_V4T, 0x5800, 0xFA00, "ldr%10'b%c\t%0-2r, [%3-5r, %6-8r]"},
1177 /* format 1 */
1178 {ARM_EXT_V4T, 0x0000, 0xF800, "lsl%C\t%0-2r, %3-5r, #%6-10d"},
1179 {ARM_EXT_V4T, 0x0800, 0xF800, "lsr%C\t%0-2r, %3-5r, %s"},
1180 {ARM_EXT_V4T, 0x1000, 0xF800, "asr%C\t%0-2r, %3-5r, %s"},
1181 /* format 3 */
1182 {ARM_EXT_V4T, 0x2000, 0xF800, "mov%C\t%8-10r, #%0-7d"},
1183 {ARM_EXT_V4T, 0x2800, 0xF800, "cmp%c\t%8-10r, #%0-7d"},
1184 {ARM_EXT_V4T, 0x3000, 0xF800, "add%C\t%8-10r, #%0-7d"},
1185 {ARM_EXT_V4T, 0x3800, 0xF800, "sub%C\t%8-10r, #%0-7d"},
1186 /* format 6 */
1187 {ARM_EXT_V4T, 0x4800, 0xF800, "ldr%c\t%8-10r, [pc, #%0-7W]\t(%0-7a)"}, /* TODO: Disassemble PC relative "LDR rD,=<symbolic>" */
1188 /* format 9 */
1189 {ARM_EXT_V4T, 0x6000, 0xF800, "str%c\t%0-2r, [%3-5r, #%6-10W]"},
1190 {ARM_EXT_V4T, 0x6800, 0xF800, "ldr%c\t%0-2r, [%3-5r, #%6-10W]"},
1191 {ARM_EXT_V4T, 0x7000, 0xF800, "strb%c\t%0-2r, [%3-5r, #%6-10d]"},
1192 {ARM_EXT_V4T, 0x7800, 0xF800, "ldrb%c\t%0-2r, [%3-5r, #%6-10d]"},
1193 /* format 10 */
1194 {ARM_EXT_V4T, 0x8000, 0xF800, "strh%c\t%0-2r, [%3-5r, #%6-10H]"},
1195 {ARM_EXT_V4T, 0x8800, 0xF800, "ldrh%c\t%0-2r, [%3-5r, #%6-10H]"},
1196 /* format 11 */
1197 {ARM_EXT_V4T, 0x9000, 0xF800, "str%c\t%8-10r, [sp, #%0-7W]"},
1198 {ARM_EXT_V4T, 0x9800, 0xF800, "ldr%c\t%8-10r, [sp, #%0-7W]"},
1199 /* format 12 */
1200 {ARM_EXT_V4T, 0xA000, 0xF800, "add%c\t%8-10r, pc, #%0-7W\t(adr %8-10r, %0-7a)"},
1201 {ARM_EXT_V4T, 0xA800, 0xF800, "add%c\t%8-10r, sp, #%0-7W"},
1202 /* format 15 */
1203 {ARM_EXT_V4T, 0xC000, 0xF800, "stmia%c\t%8-10r!, %M"},
1204 {ARM_EXT_V4T, 0xC800, 0xF800, "ldmia%c\t%8-10r!, %M"},
1205 /* format 17 */
1206 {ARM_EXT_V4T, 0xDF00, 0xFF00, "svc%c\t%0-7d"},
1207 /* format 16 */
1208 {ARM_EXT_V4T, 0xDE00, 0xFE00, "undefined"},
1209 {ARM_EXT_V4T, 0xD000, 0xF000, "b%8-11c.n\t%0-7B%X"},
1210 /* format 18 */
1211 {ARM_EXT_V4T, 0xE000, 0xF800, "b%c.n\t%0-10B%x"},
1213 /* The E800 .. FFFF range is unconditionally redirected to the
1214 32-bit table, because even in pre-V6T2 ISAs, BL and BLX(1) pairs
1215 are processed via that table. Thus, we can never encounter a
1216 bare "second half of BL/BLX(1)" instruction here. */
1217 {ARM_EXT_V1, 0x0000, 0x0000, "undefined"},
1218 {0, 0, 0, 0}
1221 /* Thumb32 opcodes use the same table structure as the ARM opcodes.
1222 We adopt the convention that hw1 is the high 16 bits of .value and
1223 .mask, hw2 the low 16 bits.
1225 print_insn_thumb32 recognizes the following format control codes:
1227 %% %
1229 %I print a 12-bit immediate from hw1[10],hw2[14:12,7:0]
1230 %M print a modified 12-bit immediate (same location)
1231 %J print a 16-bit immediate from hw1[3:0,10],hw2[14:12,7:0]
1232 %K print a 16-bit immediate from hw2[3:0],hw1[3:0],hw2[11:4]
1233 %S print a possibly-shifted Rm
1235 %a print the address of a plain load/store
1236 %w print the width and signedness of a core load/store
1237 %m print register mask for ldm/stm
1239 %E print the lsb and width fields of a bfc/bfi instruction
1240 %F print the lsb and width fields of a sbfx/ubfx instruction
1241 %b print a conditional branch offset
1242 %B print an unconditional branch offset
1243 %s print the shift field of an SSAT instruction
1244 %R print the rotation field of an SXT instruction
1245 %U print barrier type.
1246 %P print address for pli instruction.
1247 %c print the condition code
1248 %x print warning if conditional an not at end of IT block"
1249 %X print "\t; unpredictable <IT:code>" if conditional
1251 %<bitfield>d print bitfield in decimal
1252 %<bitfield>W print bitfield*4 in decimal
1253 %<bitfield>r print bitfield as an ARM register
1254 %<bitfield>c print bitfield as a condition code
1256 %<bitfield>'c print specified char iff bitfield is all ones
1257 %<bitfield>`c print specified char iff bitfield is all zeroes
1258 %<bitfield>?ab... select from array of values in big endian order
1260 With one exception at the bottom (done because BL and BLX(1) need
1261 to come dead last), this table was machine-sorted first in
1262 decreasing order of number of bits set in the mask, then in
1263 increasing numeric order of mask, then in increasing numeric order
1264 of opcode. This order is not the clearest for a human reader, but
1265 is guaranteed never to catch a special-case bit pattern with a more
1266 general mask, which is important, because this instruction encoding
1267 makes heavy use of special-case bit patterns. */
1268 static const struct opcode32 thumb32_opcodes[] =
1270 /* V7 instructions. */
1271 {ARM_EXT_V7, 0xf910f000, 0xff70f000, "pli%c\t%a"},
1272 {ARM_EXT_V7, 0xf3af80f0, 0xfffffff0, "dbg%c\t#%0-3d"},
1273 {ARM_EXT_V7, 0xf3bf8f50, 0xfffffff0, "dmb%c\t%U"},
1274 {ARM_EXT_V7, 0xf3bf8f40, 0xfffffff0, "dsb%c\t%U"},
1275 {ARM_EXT_V7, 0xf3bf8f60, 0xfffffff0, "isb%c\t%U"},
1276 {ARM_EXT_DIV, 0xfb90f0f0, 0xfff0f0f0, "sdiv%c\t%8-11r, %16-19r, %0-3r"},
1277 {ARM_EXT_DIV, 0xfbb0f0f0, 0xfff0f0f0, "udiv%c\t%8-11r, %16-19r, %0-3r"},
1279 /* Instructions defined in the basic V6T2 set. */
1280 {ARM_EXT_V6T2, 0xf3af8000, 0xffffffff, "nop%c.w"},
1281 {ARM_EXT_V6T2, 0xf3af8001, 0xffffffff, "yield%c.w"},
1282 {ARM_EXT_V6T2, 0xf3af8002, 0xffffffff, "wfe%c.w"},
1283 {ARM_EXT_V6T2, 0xf3af8003, 0xffffffff, "wfi%c.w"},
1284 {ARM_EXT_V6T2, 0xf3af9004, 0xffffffff, "sev%c.w"},
1285 {ARM_EXT_V6T2, 0xf3af8000, 0xffffff00, "nop%c.w\t{%0-7d}"},
1287 {ARM_EXT_V6T2, 0xf3bf8f2f, 0xffffffff, "clrex%c"},
1288 {ARM_EXT_V6T2, 0xf3af8400, 0xffffff1f, "cpsie.w\t%7'a%6'i%5'f%X"},
1289 {ARM_EXT_V6T2, 0xf3af8600, 0xffffff1f, "cpsid.w\t%7'a%6'i%5'f%X"},
1290 {ARM_EXT_V6T2, 0xf3c08f00, 0xfff0ffff, "bxj%c\t%16-19r%x"},
1291 {ARM_EXT_V6T2, 0xe810c000, 0xffd0ffff, "rfedb%c\t%16-19r%21'!"},
1292 {ARM_EXT_V6T2, 0xe990c000, 0xffd0ffff, "rfeia%c\t%16-19r%21'!"},
1293 {ARM_EXT_V6T2, 0xf3ef8000, 0xffeff000, "mrs%c\t%8-11r, %D"},
1294 {ARM_EXT_V6T2, 0xf3af8100, 0xffffffe0, "cps\t#%0-4d%X"},
1295 {ARM_EXT_V6T2, 0xe8d0f000, 0xfff0fff0, "tbb%c\t[%16-19r, %0-3r]%x"},
1296 {ARM_EXT_V6T2, 0xe8d0f010, 0xfff0fff0, "tbh%c\t[%16-19r, %0-3r, lsl #1]%x"},
1297 {ARM_EXT_V6T2, 0xf3af8500, 0xffffff00, "cpsie\t%7'a%6'i%5'f, #%0-4d%X"},
1298 {ARM_EXT_V6T2, 0xf3af8700, 0xffffff00, "cpsid\t%7'a%6'i%5'f, #%0-4d%X"},
1299 {ARM_EXT_V6T2, 0xf3de8f00, 0xffffff00, "subs%c\tpc, lr, #%0-7d"},
1300 {ARM_EXT_V6T2, 0xf3808000, 0xffe0f000, "msr%c\t%C, %16-19r"},
1301 {ARM_EXT_V6T2, 0xe8500f00, 0xfff00fff, "ldrex%c\t%12-15r, [%16-19r]"},
1302 {ARM_EXT_V6T2, 0xe8d00f4f, 0xfff00fef, "ldrex%4?hb%c\t%12-15r, [%16-19r]"},
1303 {ARM_EXT_V6T2, 0xe800c000, 0xffd0ffe0, "srsdb%c\t%16-19r%21'!, #%0-4d"},
1304 {ARM_EXT_V6T2, 0xe980c000, 0xffd0ffe0, "srsia%c\t%16-19r%21'!, #%0-4d"},
1305 {ARM_EXT_V6T2, 0xfa0ff080, 0xfffff0c0, "sxth%c.w\t%8-11r, %0-3r%R"},
1306 {ARM_EXT_V6T2, 0xfa1ff080, 0xfffff0c0, "uxth%c.w\t%8-11r, %0-3r%R"},
1307 {ARM_EXT_V6T2, 0xfa2ff080, 0xfffff0c0, "sxtb16%c\t%8-11r, %0-3r%R"},
1308 {ARM_EXT_V6T2, 0xfa3ff080, 0xfffff0c0, "uxtb16%c\t%8-11r, %0-3r%R"},
1309 {ARM_EXT_V6T2, 0xfa4ff080, 0xfffff0c0, "sxtb%c.w\t%8-11r, %0-3r%R"},
1310 {ARM_EXT_V6T2, 0xfa5ff080, 0xfffff0c0, "uxtb%c.w\t%8-11r, %0-3r%R"},
1311 {ARM_EXT_V6T2, 0xe8400000, 0xfff000ff, "strex%c\t%8-11r, %12-15r, [%16-19r]"},
1312 {ARM_EXT_V6T2, 0xe8d0007f, 0xfff000ff, "ldrexd%c\t%12-15r, %8-11r, [%16-19r]"},
1313 {ARM_EXT_V6T2, 0xfa80f000, 0xfff0f0f0, "sadd8%c\t%8-11r, %16-19r, %0-3r"},
1314 {ARM_EXT_V6T2, 0xfa80f010, 0xfff0f0f0, "qadd8%c\t%8-11r, %16-19r, %0-3r"},
1315 {ARM_EXT_V6T2, 0xfa80f020, 0xfff0f0f0, "shadd8%c\t%8-11r, %16-19r, %0-3r"},
1316 {ARM_EXT_V6T2, 0xfa80f040, 0xfff0f0f0, "uadd8%c\t%8-11r, %16-19r, %0-3r"},
1317 {ARM_EXT_V6T2, 0xfa80f050, 0xfff0f0f0, "uqadd8%c\t%8-11r, %16-19r, %0-3r"},
1318 {ARM_EXT_V6T2, 0xfa80f060, 0xfff0f0f0, "uhadd8%c\t%8-11r, %16-19r, %0-3r"},
1319 {ARM_EXT_V6T2, 0xfa80f080, 0xfff0f0f0, "qadd%c\t%8-11r, %0-3r, %16-19r"},
1320 {ARM_EXT_V6T2, 0xfa80f090, 0xfff0f0f0, "qdadd%c\t%8-11r, %0-3r, %16-19r"},
1321 {ARM_EXT_V6T2, 0xfa80f0a0, 0xfff0f0f0, "qsub%c\t%8-11r, %0-3r, %16-19r"},
1322 {ARM_EXT_V6T2, 0xfa80f0b0, 0xfff0f0f0, "qdsub%c\t%8-11r, %0-3r, %16-19r"},
1323 {ARM_EXT_V6T2, 0xfa90f000, 0xfff0f0f0, "sadd16%c\t%8-11r, %16-19r, %0-3r"},
1324 {ARM_EXT_V6T2, 0xfa90f010, 0xfff0f0f0, "qadd16%c\t%8-11r, %16-19r, %0-3r"},
1325 {ARM_EXT_V6T2, 0xfa90f020, 0xfff0f0f0, "shadd16%c\t%8-11r, %16-19r, %0-3r"},
1326 {ARM_EXT_V6T2, 0xfa90f040, 0xfff0f0f0, "uadd16%c\t%8-11r, %16-19r, %0-3r"},
1327 {ARM_EXT_V6T2, 0xfa90f050, 0xfff0f0f0, "uqadd16%c\t%8-11r, %16-19r, %0-3r"},
1328 {ARM_EXT_V6T2, 0xfa90f060, 0xfff0f0f0, "uhadd16%c\t%8-11r, %16-19r, %0-3r"},
1329 {ARM_EXT_V6T2, 0xfa90f080, 0xfff0f0f0, "rev%c.w\t%8-11r, %16-19r"},
1330 {ARM_EXT_V6T2, 0xfa90f090, 0xfff0f0f0, "rev16%c.w\t%8-11r, %16-19r"},
1331 {ARM_EXT_V6T2, 0xfa90f0a0, 0xfff0f0f0, "rbit%c\t%8-11r, %16-19r"},
1332 {ARM_EXT_V6T2, 0xfa90f0b0, 0xfff0f0f0, "revsh%c.w\t%8-11r, %16-19r"},
1333 {ARM_EXT_V6T2, 0xfaa0f000, 0xfff0f0f0, "saddsubx%c\t%8-11r, %16-19r, %0-3r"},
1334 {ARM_EXT_V6T2, 0xfaa0f010, 0xfff0f0f0, "qaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1335 {ARM_EXT_V6T2, 0xfaa0f020, 0xfff0f0f0, "shaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1336 {ARM_EXT_V6T2, 0xfaa0f040, 0xfff0f0f0, "uaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1337 {ARM_EXT_V6T2, 0xfaa0f050, 0xfff0f0f0, "uqaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1338 {ARM_EXT_V6T2, 0xfaa0f060, 0xfff0f0f0, "uhaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1339 {ARM_EXT_V6T2, 0xfaa0f080, 0xfff0f0f0, "sel%c\t%8-11r, %16-19r, %0-3r"},
1340 {ARM_EXT_V6T2, 0xfab0f080, 0xfff0f0f0, "clz%c\t%8-11r, %16-19r"},
1341 {ARM_EXT_V6T2, 0xfac0f000, 0xfff0f0f0, "ssub8%c\t%8-11r, %16-19r, %0-3r"},
1342 {ARM_EXT_V6T2, 0xfac0f010, 0xfff0f0f0, "qsub8%c\t%8-11r, %16-19r, %0-3r"},
1343 {ARM_EXT_V6T2, 0xfac0f020, 0xfff0f0f0, "shsub8%c\t%8-11r, %16-19r, %0-3r"},
1344 {ARM_EXT_V6T2, 0xfac0f040, 0xfff0f0f0, "usub8%c\t%8-11r, %16-19r, %0-3r"},
1345 {ARM_EXT_V6T2, 0xfac0f050, 0xfff0f0f0, "uqsub8%c\t%8-11r, %16-19r, %0-3r"},
1346 {ARM_EXT_V6T2, 0xfac0f060, 0xfff0f0f0, "uhsub8%c\t%8-11r, %16-19r, %0-3r"},
1347 {ARM_EXT_V6T2, 0xfad0f000, 0xfff0f0f0, "ssub16%c\t%8-11r, %16-19r, %0-3r"},
1348 {ARM_EXT_V6T2, 0xfad0f010, 0xfff0f0f0, "qsub16%c\t%8-11r, %16-19r, %0-3r"},
1349 {ARM_EXT_V6T2, 0xfad0f020, 0xfff0f0f0, "shsub16%c\t%8-11r, %16-19r, %0-3r"},
1350 {ARM_EXT_V6T2, 0xfad0f040, 0xfff0f0f0, "usub16%c\t%8-11r, %16-19r, %0-3r"},
1351 {ARM_EXT_V6T2, 0xfad0f050, 0xfff0f0f0, "uqsub16%c\t%8-11r, %16-19r, %0-3r"},
1352 {ARM_EXT_V6T2, 0xfad0f060, 0xfff0f0f0, "uhsub16%c\t%8-11r, %16-19r, %0-3r"},
1353 {ARM_EXT_V6T2, 0xfae0f000, 0xfff0f0f0, "ssubaddx%c\t%8-11r, %16-19r, %0-3r"},
1354 {ARM_EXT_V6T2, 0xfae0f010, 0xfff0f0f0, "qsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1355 {ARM_EXT_V6T2, 0xfae0f020, 0xfff0f0f0, "shsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1356 {ARM_EXT_V6T2, 0xfae0f040, 0xfff0f0f0, "usubaddx%c\t%8-11r, %16-19r, %0-3r"},
1357 {ARM_EXT_V6T2, 0xfae0f050, 0xfff0f0f0, "uqsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1358 {ARM_EXT_V6T2, 0xfae0f060, 0xfff0f0f0, "uhsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1359 {ARM_EXT_V6T2, 0xfb00f000, 0xfff0f0f0, "mul%c.w\t%8-11r, %16-19r, %0-3r"},
1360 {ARM_EXT_V6T2, 0xfb70f000, 0xfff0f0f0, "usad8%c\t%8-11r, %16-19r, %0-3r"},
1361 {ARM_EXT_V6T2, 0xfa00f000, 0xffe0f0f0, "lsl%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1362 {ARM_EXT_V6T2, 0xfa20f000, 0xffe0f0f0, "lsr%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1363 {ARM_EXT_V6T2, 0xfa40f000, 0xffe0f0f0, "asr%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1364 {ARM_EXT_V6T2, 0xfa60f000, 0xffe0f0f0, "ror%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1365 {ARM_EXT_V6T2, 0xe8c00f40, 0xfff00fe0, "strex%4?hb%c\t%0-3r, %12-15r, [%16-19r]"},
1366 {ARM_EXT_V6T2, 0xf3200000, 0xfff0f0e0, "ssat16%c\t%8-11r, #%0-4d, %16-19r"},
1367 {ARM_EXT_V6T2, 0xf3a00000, 0xfff0f0e0, "usat16%c\t%8-11r, #%0-4d, %16-19r"},
1368 {ARM_EXT_V6T2, 0xfb20f000, 0xfff0f0e0, "smuad%4'x%c\t%8-11r, %16-19r, %0-3r"},
1369 {ARM_EXT_V6T2, 0xfb30f000, 0xfff0f0e0, "smulw%4?tb%c\t%8-11r, %16-19r, %0-3r"},
1370 {ARM_EXT_V6T2, 0xfb40f000, 0xfff0f0e0, "smusd%4'x%c\t%8-11r, %16-19r, %0-3r"},
1371 {ARM_EXT_V6T2, 0xfb50f000, 0xfff0f0e0, "smmul%4'r%c\t%8-11r, %16-19r, %0-3r"},
1372 {ARM_EXT_V6T2, 0xfa00f080, 0xfff0f0c0, "sxtah%c\t%8-11r, %16-19r, %0-3r%R"},
1373 {ARM_EXT_V6T2, 0xfa10f080, 0xfff0f0c0, "uxtah%c\t%8-11r, %16-19r, %0-3r%R"},
1374 {ARM_EXT_V6T2, 0xfa20f080, 0xfff0f0c0, "sxtab16%c\t%8-11r, %16-19r, %0-3r%R"},
1375 {ARM_EXT_V6T2, 0xfa30f080, 0xfff0f0c0, "uxtab16%c\t%8-11r, %16-19r, %0-3r%R"},
1376 {ARM_EXT_V6T2, 0xfa40f080, 0xfff0f0c0, "sxtab%c\t%8-11r, %16-19r, %0-3r%R"},
1377 {ARM_EXT_V6T2, 0xfa50f080, 0xfff0f0c0, "uxtab%c\t%8-11r, %16-19r, %0-3r%R"},
1378 {ARM_EXT_V6T2, 0xfb10f000, 0xfff0f0c0, "smul%5?tb%4?tb%c\t%8-11r, %16-19r, %0-3r"},
1379 {ARM_EXT_V6T2, 0xf36f0000, 0xffff8020, "bfc%c\t%8-11r, %E"},
1380 {ARM_EXT_V6T2, 0xea100f00, 0xfff08f00, "tst%c.w\t%16-19r, %S"},
1381 {ARM_EXT_V6T2, 0xea900f00, 0xfff08f00, "teq%c\t%16-19r, %S"},
1382 {ARM_EXT_V6T2, 0xeb100f00, 0xfff08f00, "cmn%c.w\t%16-19r, %S"},
1383 {ARM_EXT_V6T2, 0xebb00f00, 0xfff08f00, "cmp%c.w\t%16-19r, %S"},
1384 {ARM_EXT_V6T2, 0xf0100f00, 0xfbf08f00, "tst%c.w\t%16-19r, %M"},
1385 {ARM_EXT_V6T2, 0xf0900f00, 0xfbf08f00, "teq%c\t%16-19r, %M"},
1386 {ARM_EXT_V6T2, 0xf1100f00, 0xfbf08f00, "cmn%c.w\t%16-19r, %M"},
1387 {ARM_EXT_V6T2, 0xf1b00f00, 0xfbf08f00, "cmp%c.w\t%16-19r, %M"},
1388 {ARM_EXT_V6T2, 0xea4f0000, 0xffef8000, "mov%20's%c.w\t%8-11r, %S"},
1389 {ARM_EXT_V6T2, 0xea6f0000, 0xffef8000, "mvn%20's%c.w\t%8-11r, %S"},
1390 {ARM_EXT_V6T2, 0xe8c00070, 0xfff000f0, "strexd%c\t%0-3r, %12-15r, %8-11r, [%16-19r]"},
1391 {ARM_EXT_V6T2, 0xfb000000, 0xfff000f0, "mla%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1392 {ARM_EXT_V6T2, 0xfb000010, 0xfff000f0, "mls%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1393 {ARM_EXT_V6T2, 0xfb700000, 0xfff000f0, "usada8%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1394 {ARM_EXT_V6T2, 0xfb800000, 0xfff000f0, "smull%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1395 {ARM_EXT_V6T2, 0xfba00000, 0xfff000f0, "umull%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1396 {ARM_EXT_V6T2, 0xfbc00000, 0xfff000f0, "smlal%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1397 {ARM_EXT_V6T2, 0xfbe00000, 0xfff000f0, "umlal%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1398 {ARM_EXT_V6T2, 0xfbe00060, 0xfff000f0, "umaal%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1399 {ARM_EXT_V6T2, 0xe8500f00, 0xfff00f00, "ldrex%c\t%12-15r, [%16-19r, #%0-7W]"},
1400 {ARM_EXT_V6T2, 0xf7f08000, 0xfff0f000, "smc%c\t%K"},
1401 {ARM_EXT_V6T2, 0xf04f0000, 0xfbef8000, "mov%20's%c.w\t%8-11r, %M"},
1402 {ARM_EXT_V6T2, 0xf06f0000, 0xfbef8000, "mvn%20's%c.w\t%8-11r, %M"},
1403 {ARM_EXT_V6T2, 0xf810f000, 0xff70f000, "pld%c\t%a"},
1404 {ARM_EXT_V6T2, 0xfb200000, 0xfff000e0, "smlad%4'x%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1405 {ARM_EXT_V6T2, 0xfb300000, 0xfff000e0, "smlaw%4?tb%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1406 {ARM_EXT_V6T2, 0xfb400000, 0xfff000e0, "smlsd%4'x%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1407 {ARM_EXT_V6T2, 0xfb500000, 0xfff000e0, "smmla%4'r%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1408 {ARM_EXT_V6T2, 0xfb600000, 0xfff000e0, "smmls%4'r%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1409 {ARM_EXT_V6T2, 0xfbc000c0, 0xfff000e0, "smlald%4'x%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1410 {ARM_EXT_V6T2, 0xfbd000c0, 0xfff000e0, "smlsld%4'x%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1411 {ARM_EXT_V6T2, 0xeac00000, 0xfff08030, "pkhbt%c\t%8-11r, %16-19r, %S"},
1412 {ARM_EXT_V6T2, 0xeac00020, 0xfff08030, "pkhtb%c\t%8-11r, %16-19r, %S"},
1413 {ARM_EXT_V6T2, 0xf3400000, 0xfff08020, "sbfx%c\t%8-11r, %16-19r, %F"},
1414 {ARM_EXT_V6T2, 0xf3c00000, 0xfff08020, "ubfx%c\t%8-11r, %16-19r, %F"},
1415 {ARM_EXT_V6T2, 0xf8000e00, 0xff900f00, "str%wt%c\t%12-15r, %a"},
1416 {ARM_EXT_V6T2, 0xfb100000, 0xfff000c0, "smla%5?tb%4?tb%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1417 {ARM_EXT_V6T2, 0xfbc00080, 0xfff000c0, "smlal%5?tb%4?tb%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1418 {ARM_EXT_V6T2, 0xf3600000, 0xfff08020, "bfi%c\t%8-11r, %16-19r, %E"},
1419 {ARM_EXT_V6T2, 0xf8100e00, 0xfe900f00, "ldr%wt%c\t%12-15r, %a"},
1420 {ARM_EXT_V6T2, 0xf3000000, 0xffd08020, "ssat%c\t%8-11r, #%0-4d, %16-19r%s"},
1421 {ARM_EXT_V6T2, 0xf3800000, 0xffd08020, "usat%c\t%8-11r, #%0-4d, %16-19r%s"},
1422 {ARM_EXT_V6T2, 0xf2000000, 0xfbf08000, "addw%c\t%8-11r, %16-19r, %I"},
1423 {ARM_EXT_V6T2, 0xf2400000, 0xfbf08000, "movw%c\t%8-11r, %J"},
1424 {ARM_EXT_V6T2, 0xf2a00000, 0xfbf08000, "subw%c\t%8-11r, %16-19r, %I"},
1425 {ARM_EXT_V6T2, 0xf2c00000, 0xfbf08000, "movt%c\t%8-11r, %J"},
1426 {ARM_EXT_V6T2, 0xea000000, 0xffe08000, "and%20's%c.w\t%8-11r, %16-19r, %S"},
1427 {ARM_EXT_V6T2, 0xea200000, 0xffe08000, "bic%20's%c.w\t%8-11r, %16-19r, %S"},
1428 {ARM_EXT_V6T2, 0xea400000, 0xffe08000, "orr%20's%c.w\t%8-11r, %16-19r, %S"},
1429 {ARM_EXT_V6T2, 0xea600000, 0xffe08000, "orn%20's%c\t%8-11r, %16-19r, %S"},
1430 {ARM_EXT_V6T2, 0xea800000, 0xffe08000, "eor%20's%c.w\t%8-11r, %16-19r, %S"},
1431 {ARM_EXT_V6T2, 0xeb000000, 0xffe08000, "add%20's%c.w\t%8-11r, %16-19r, %S"},
1432 {ARM_EXT_V6T2, 0xeb400000, 0xffe08000, "adc%20's%c.w\t%8-11r, %16-19r, %S"},
1433 {ARM_EXT_V6T2, 0xeb600000, 0xffe08000, "sbc%20's%c.w\t%8-11r, %16-19r, %S"},
1434 {ARM_EXT_V6T2, 0xeba00000, 0xffe08000, "sub%20's%c.w\t%8-11r, %16-19r, %S"},
1435 {ARM_EXT_V6T2, 0xebc00000, 0xffe08000, "rsb%20's%c\t%8-11r, %16-19r, %S"},
1436 {ARM_EXT_V6T2, 0xe8400000, 0xfff00000, "strex%c\t%8-11r, %12-15r, [%16-19r, #%0-7W]"},
1437 {ARM_EXT_V6T2, 0xf0000000, 0xfbe08000, "and%20's%c.w\t%8-11r, %16-19r, %M"},
1438 {ARM_EXT_V6T2, 0xf0200000, 0xfbe08000, "bic%20's%c.w\t%8-11r, %16-19r, %M"},
1439 {ARM_EXT_V6T2, 0xf0400000, 0xfbe08000, "orr%20's%c.w\t%8-11r, %16-19r, %M"},
1440 {ARM_EXT_V6T2, 0xf0600000, 0xfbe08000, "orn%20's%c\t%8-11r, %16-19r, %M"},
1441 {ARM_EXT_V6T2, 0xf0800000, 0xfbe08000, "eor%20's%c.w\t%8-11r, %16-19r, %M"},
1442 {ARM_EXT_V6T2, 0xf1000000, 0xfbe08000, "add%20's%c.w\t%8-11r, %16-19r, %M"},
1443 {ARM_EXT_V6T2, 0xf1400000, 0xfbe08000, "adc%20's%c.w\t%8-11r, %16-19r, %M"},
1444 {ARM_EXT_V6T2, 0xf1600000, 0xfbe08000, "sbc%20's%c.w\t%8-11r, %16-19r, %M"},
1445 {ARM_EXT_V6T2, 0xf1a00000, 0xfbe08000, "sub%20's%c.w\t%8-11r, %16-19r, %M"},
1446 {ARM_EXT_V6T2, 0xf1c00000, 0xfbe08000, "rsb%20's%c\t%8-11r, %16-19r, %M"},
1447 {ARM_EXT_V6T2, 0xe8800000, 0xffd00000, "stmia%c.w\t%16-19r%21'!, %m"},
1448 {ARM_EXT_V6T2, 0xe8900000, 0xffd00000, "ldmia%c.w\t%16-19r%21'!, %m"},
1449 {ARM_EXT_V6T2, 0xe9000000, 0xffd00000, "stmdb%c\t%16-19r%21'!, %m"},
1450 {ARM_EXT_V6T2, 0xe9100000, 0xffd00000, "ldmdb%c\t%16-19r%21'!, %m"},
1451 {ARM_EXT_V6T2, 0xe9c00000, 0xffd000ff, "strd%c\t%12-15r, %8-11r, [%16-19r]"},
1452 {ARM_EXT_V6T2, 0xe9d00000, 0xffd000ff, "ldrd%c\t%12-15r, %8-11r, [%16-19r]"},
1453 {ARM_EXT_V6T2, 0xe9400000, 0xff500000, "strd%c\t%12-15r, %8-11r, [%16-19r, #%23`-%0-7W]%21'!"},
1454 {ARM_EXT_V6T2, 0xe9500000, 0xff500000, "ldrd%c\t%12-15r, %8-11r, [%16-19r, #%23`-%0-7W]%21'!"},
1455 {ARM_EXT_V6T2, 0xe8600000, 0xff700000, "strd%c\t%12-15r, %8-11r, [%16-19r], #%23`-%0-7W"},
1456 {ARM_EXT_V6T2, 0xe8700000, 0xff700000, "ldrd%c\t%12-15r, %8-11r, [%16-19r], #%23`-%0-7W"},
1457 {ARM_EXT_V6T2, 0xf8000000, 0xff100000, "str%w%c.w\t%12-15r, %a"},
1458 {ARM_EXT_V6T2, 0xf8100000, 0xfe100000, "ldr%w%c.w\t%12-15r, %a"},
1460 /* Filter out Bcc with cond=E or F, which are used for other instructions. */
1461 {ARM_EXT_V6T2, 0xf3c08000, 0xfbc0d000, "undefined (bcc, cond=0xF)"},
1462 {ARM_EXT_V6T2, 0xf3808000, 0xfbc0d000, "undefined (bcc, cond=0xE)"},
1463 {ARM_EXT_V6T2, 0xf0008000, 0xf800d000, "b%22-25c.w\t%b%X"},
1464 {ARM_EXT_V6T2, 0xf0009000, 0xf800d000, "b%c.w\t%B%x"},
1466 /* These have been 32-bit since the invention of Thumb. */
1467 {ARM_EXT_V4T, 0xf000c000, 0xf800d000, "blx%c\t%B%x"},
1468 {ARM_EXT_V4T, 0xf000d000, 0xf800d000, "bl%c\t%B%x"},
1470 /* Fallback. */
1471 {ARM_EXT_V1, 0x00000000, 0x00000000, "undefined"},
1472 {0, 0, 0, 0}
1475 static const char *const arm_conditional[] =
1476 {"eq", "ne", "cs", "cc", "mi", "pl", "vs", "vc",
1477 "hi", "ls", "ge", "lt", "gt", "le", "al", "<und>", ""};
1479 static const char *const arm_fp_const[] =
1480 {"0.0", "1.0", "2.0", "3.0", "4.0", "5.0", "0.5", "10.0"};
1482 static const char *const arm_shift[] =
1483 {"lsl", "lsr", "asr", "ror"};
1485 typedef struct
1487 const char *name;
1488 const char *description;
1489 const char *reg_names[16];
1491 arm_regname;
1493 static const arm_regname regnames[] =
1495 { "raw" , "Select raw register names",
1496 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"}},
1497 { "gcc", "Select register names used by GCC",
1498 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "sl", "fp", "ip", "sp", "lr", "pc" }},
1499 { "std", "Select register names used in ARM's ISA documentation",
1500 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "sp", "lr", "pc" }},
1501 { "apcs", "Select register names used in the APCS",
1502 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "sl", "fp", "ip", "sp", "lr", "pc" }},
1503 { "atpcs", "Select register names used in the ATPCS",
1504 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8", "IP", "SP", "LR", "PC" }},
1505 { "special-atpcs", "Select special register names used in the ATPCS",
1506 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "WR", "v5", "SB", "SL", "FP", "IP", "SP", "LR", "PC" }},
1509 static const char *const iwmmxt_wwnames[] =
1510 {"b", "h", "w", "d"};
1512 static const char *const iwmmxt_wwssnames[] =
1513 {"b", "bus", "bc", "bss",
1514 "h", "hus", "hc", "hss",
1515 "w", "wus", "wc", "wss",
1516 "d", "dus", "dc", "dss"
1519 static const char *const iwmmxt_regnames[] =
1520 { "wr0", "wr1", "wr2", "wr3", "wr4", "wr5", "wr6", "wr7",
1521 "wr8", "wr9", "wr10", "wr11", "wr12", "wr13", "wr14", "wr15"
1524 static const char *const iwmmxt_cregnames[] =
1525 { "wcid", "wcon", "wcssf", "wcasf", "reserved", "reserved", "reserved", "reserved",
1526 "wcgr0", "wcgr1", "wcgr2", "wcgr3", "reserved", "reserved", "reserved", "reserved"
1529 /* Default to GCC register name set. */
1530 static unsigned int regname_selected = 1;
1532 #define NUM_ARM_REGNAMES NUM_ELEM (regnames)
1533 #define arm_regnames regnames[regname_selected].reg_names
1535 static bfd_boolean force_thumb = false;
1537 /* Current IT instruction state. This contains the same state as the IT
1538 bits in the CPSR. */
1539 static unsigned int ifthen_state;
1540 /* IT state for the next instruction. */
1541 static unsigned int ifthen_next_state;
1542 /* The address of the insn for which the IT state is valid. */
1543 static bfd_vma ifthen_address;
1544 #define IFTHEN_COND ((ifthen_state >> 4) & 0xf)
1546 /* Cached mapping symbol state. */
1547 enum map_type {
1548 MAP_ARM,
1549 MAP_THUMB,
1550 MAP_DATA
1553 /* Decode a bitfield of the form matching regexp (N(-N)?,)*N(-N)?.
1554 Returns pointer to following character of the format string and
1555 fills in *VALUEP and *WIDTHP with the extracted value and number of
1556 bits extracted. WIDTHP can be NULL. */
1558 static const char *
1559 arm_decode_bitfield (const char *ptr, unsigned long insn,
1560 unsigned long *valuep, int *widthp)
1562 unsigned long value = 0;
1563 int width = 0;
1567 int start, end;
1568 int bits;
1570 for (start = 0; *ptr >= '0' && *ptr <= '9'; ptr++)
1571 start = start * 10 + *ptr - '0';
1572 if (*ptr == '-')
1573 for (end = 0, ptr++; *ptr >= '0' && *ptr <= '9'; ptr++)
1574 end = end * 10 + *ptr - '0';
1575 else
1576 end = start;
1577 bits = end - start;
1578 if (bits < 0)
1579 abort ();
1580 value |= ((insn >> start) & ((2ul << bits) - 1)) << width;
1581 width += bits + 1;
1583 while (*ptr++ == ',');
1584 *valuep = value;
1585 if (widthp)
1586 *widthp = width;
1587 return ptr - 1;
1590 static void
1591 arm_decode_shift (long given, fprintf_function func, void *stream,
1592 int print_shift)
1594 func (stream, "%s", arm_regnames[given & 0xf]);
1596 if ((given & 0xff0) != 0)
1598 if ((given & 0x10) == 0)
1600 int amount = (given & 0xf80) >> 7;
1601 int shift = (given & 0x60) >> 5;
1603 if (amount == 0)
1605 if (shift == 3)
1607 func (stream, ", rrx");
1608 return;
1611 amount = 32;
1614 if (print_shift)
1615 func (stream, ", %s #%d", arm_shift[shift], amount);
1616 else
1617 func (stream, ", #%d", amount);
1619 else if (print_shift)
1620 func (stream, ", %s %s", arm_shift[(given & 0x60) >> 5],
1621 arm_regnames[(given & 0xf00) >> 8]);
1622 else
1623 func (stream, ", %s", arm_regnames[(given & 0xf00) >> 8]);
1627 /* Print one coprocessor instruction on INFO->STREAM.
1628 Return true if the instruction matched, false if this is not a
1629 recognised coprocessor instruction. */
1631 static bfd_boolean
1632 print_insn_coprocessor (bfd_vma pc, struct disassemble_info *info, long given,
1633 bfd_boolean thumb)
1635 const struct opcode32 *insn;
1636 void *stream = info->stream;
1637 fprintf_function func = info->fprintf_func;
1638 unsigned long mask;
1639 unsigned long value;
1640 int cond;
1642 for (insn = coprocessor_opcodes; insn->assembler; insn++)
1644 if (insn->value == FIRST_IWMMXT_INSN
1645 && info->mach != bfd_mach_arm_XScale
1646 && info->mach != bfd_mach_arm_iWMMXt
1647 && info->mach != bfd_mach_arm_iWMMXt2)
1648 insn = insn + IWMMXT_INSN_COUNT;
1650 mask = insn->mask;
1651 value = insn->value;
1652 if (thumb)
1654 /* The high 4 bits are 0xe for Arm conditional instructions, and
1655 0xe for arm unconditional instructions. The rest of the
1656 encoding is the same. */
1657 mask |= 0xf0000000;
1658 value |= 0xe0000000;
1659 if (ifthen_state)
1660 cond = IFTHEN_COND;
1661 else
1662 cond = 16;
1664 else
1666 /* Only match unconditional instuctions against unconditional
1667 patterns. */
1668 if ((given & 0xf0000000) == 0xf0000000)
1670 mask |= 0xf0000000;
1671 cond = 16;
1673 else
1675 cond = (given >> 28) & 0xf;
1676 if (cond == 0xe)
1677 cond = 16;
1680 if ((given & mask) == value)
1682 const char *c;
1684 for (c = insn->assembler; *c; c++)
1686 if (*c == '%')
1688 switch (*++c)
1690 case '%':
1691 func (stream, "%%");
1692 break;
1694 case 'A':
1695 func (stream, "[%s", arm_regnames [(given >> 16) & 0xf]);
1697 if ((given & (1 << 24)) != 0)
1699 int offset = given & 0xff;
1701 if (offset)
1702 func (stream, ", #%s%d]%s",
1703 ((given & 0x00800000) == 0 ? "-" : ""),
1704 offset * 4,
1705 ((given & 0x00200000) != 0 ? "!" : ""));
1706 else
1707 func (stream, "]");
1709 else
1711 int offset = given & 0xff;
1713 func (stream, "]");
1715 if (given & (1 << 21))
1717 if (offset)
1718 func (stream, ", #%s%d",
1719 ((given & 0x00800000) == 0 ? "-" : ""),
1720 offset * 4);
1722 else
1723 func (stream, ", {%d}", offset);
1725 break;
1727 case 'B':
1729 int regno = ((given >> 12) & 0xf) | ((given >> (22 - 4)) & 0x10);
1730 int offset = (given >> 1) & 0x3f;
1732 if (offset == 1)
1733 func (stream, "{d%d}", regno);
1734 else if (regno + offset > 32)
1735 func (stream, "{d%d-<overflow reg d%d>}", regno, regno + offset - 1);
1736 else
1737 func (stream, "{d%d-d%d}", regno, regno + offset - 1);
1739 break;
1741 case 'C':
1743 int rn = (given >> 16) & 0xf;
1744 int offset = (given & 0xff) * 4;
1745 int add = (given >> 23) & 1;
1747 func (stream, "[%s", arm_regnames[rn]);
1749 if (offset)
1751 if (!add)
1752 offset = -offset;
1753 func (stream, ", #%d", offset);
1755 func (stream, "]");
1756 if (rn == 15)
1758 func (stream, "\t; ");
1759 /* FIXME: Unsure if info->bytes_per_chunk is the
1760 right thing to use here. */
1761 info->print_address_func (offset + pc
1762 + info->bytes_per_chunk * 2, info);
1765 break;
1767 case 'c':
1768 func (stream, "%s", arm_conditional[cond]);
1769 break;
1771 case 'I':
1772 /* Print a Cirrus/DSP shift immediate. */
1773 /* Immediates are 7bit signed ints with bits 0..3 in
1774 bits 0..3 of opcode and bits 4..6 in bits 5..7
1775 of opcode. */
1777 int imm;
1779 imm = (given & 0xf) | ((given & 0xe0) >> 1);
1781 /* Is ``imm'' a negative number? */
1782 if (imm & 0x40)
1783 imm |= (~0u << 7);
1785 func (stream, "%d", imm);
1788 break;
1790 case 'F':
1791 switch (given & 0x00408000)
1793 case 0:
1794 func (stream, "4");
1795 break;
1796 case 0x8000:
1797 func (stream, "1");
1798 break;
1799 case 0x00400000:
1800 func (stream, "2");
1801 break;
1802 default:
1803 func (stream, "3");
1805 break;
1807 case 'P':
1808 switch (given & 0x00080080)
1810 case 0:
1811 func (stream, "s");
1812 break;
1813 case 0x80:
1814 func (stream, "d");
1815 break;
1816 case 0x00080000:
1817 func (stream, "e");
1818 break;
1819 default:
1820 func (stream, _("<illegal precision>"));
1821 break;
1823 break;
1824 case 'Q':
1825 switch (given & 0x00408000)
1827 case 0:
1828 func (stream, "s");
1829 break;
1830 case 0x8000:
1831 func (stream, "d");
1832 break;
1833 case 0x00400000:
1834 func (stream, "e");
1835 break;
1836 default:
1837 func (stream, "p");
1838 break;
1840 break;
1841 case 'R':
1842 switch (given & 0x60)
1844 case 0:
1845 break;
1846 case 0x20:
1847 func (stream, "p");
1848 break;
1849 case 0x40:
1850 func (stream, "m");
1851 break;
1852 default:
1853 func (stream, "z");
1854 break;
1856 break;
1858 case '0': case '1': case '2': case '3': case '4':
1859 case '5': case '6': case '7': case '8': case '9':
1861 int width;
1862 unsigned long value;
1864 c = arm_decode_bitfield (c, given, &value, &width);
1866 switch (*c)
1868 case 'r':
1869 func (stream, "%s", arm_regnames[value]);
1870 break;
1871 case 'D':
1872 func (stream, "d%ld", value);
1873 break;
1874 case 'Q':
1875 if (value & 1)
1876 func (stream, "<illegal reg q%ld.5>", value >> 1);
1877 else
1878 func (stream, "q%ld", value >> 1);
1879 break;
1880 case 'd':
1881 func (stream, "%ld", value);
1882 break;
1883 case 'k':
1885 int from = (given & (1 << 7)) ? 32 : 16;
1886 func (stream, "%ld", from - value);
1888 break;
1890 case 'f':
1891 if (value > 7)
1892 func (stream, "#%s", arm_fp_const[value & 7]);
1893 else
1894 func (stream, "f%ld", value);
1895 break;
1897 case 'w':
1898 if (width == 2)
1899 func (stream, "%s", iwmmxt_wwnames[value]);
1900 else
1901 func (stream, "%s", iwmmxt_wwssnames[value]);
1902 break;
1904 case 'g':
1905 func (stream, "%s", iwmmxt_regnames[value]);
1906 break;
1907 case 'G':
1908 func (stream, "%s", iwmmxt_cregnames[value]);
1909 break;
1911 case 'x':
1912 func (stream, "0x%lx", value);
1913 break;
1915 case '`':
1916 c++;
1917 if (value == 0)
1918 func (stream, "%c", *c);
1919 break;
1920 case '\'':
1921 c++;
1922 if (value == ((1ul << width) - 1))
1923 func (stream, "%c", *c);
1924 break;
1925 case '?':
1926 func (stream, "%c", c[(1 << width) - (int)value]);
1927 c += 1 << width;
1928 break;
1929 default:
1930 abort ();
1932 break;
1934 case 'y':
1935 case 'z':
1937 int single = *c++ == 'y';
1938 int regno;
1940 switch (*c)
1942 case '4': /* Sm pair */
1943 func (stream, "{");
1944 /* Fall through. */
1945 case '0': /* Sm, Dm */
1946 regno = given & 0x0000000f;
1947 if (single)
1949 regno <<= 1;
1950 regno += (given >> 5) & 1;
1952 else
1953 regno += ((given >> 5) & 1) << 4;
1954 break;
1956 case '1': /* Sd, Dd */
1957 regno = (given >> 12) & 0x0000000f;
1958 if (single)
1960 regno <<= 1;
1961 regno += (given >> 22) & 1;
1963 else
1964 regno += ((given >> 22) & 1) << 4;
1965 break;
1967 case '2': /* Sn, Dn */
1968 regno = (given >> 16) & 0x0000000f;
1969 if (single)
1971 regno <<= 1;
1972 regno += (given >> 7) & 1;
1974 else
1975 regno += ((given >> 7) & 1) << 4;
1976 break;
1978 case '3': /* List */
1979 func (stream, "{");
1980 regno = (given >> 12) & 0x0000000f;
1981 if (single)
1983 regno <<= 1;
1984 regno += (given >> 22) & 1;
1986 else
1987 regno += ((given >> 22) & 1) << 4;
1988 break;
1990 default:
1991 abort ();
1994 func (stream, "%c%d", single ? 's' : 'd', regno);
1996 if (*c == '3')
1998 int count = given & 0xff;
2000 if (single == 0)
2001 count >>= 1;
2003 if (--count)
2005 func (stream, "-%c%d",
2006 single ? 's' : 'd',
2007 regno + count);
2010 func (stream, "}");
2012 else if (*c == '4')
2013 func (stream, ", %c%d}", single ? 's' : 'd',
2014 regno + 1);
2016 break;
2018 case 'L':
2019 switch (given & 0x00400100)
2021 case 0x00000000: func (stream, "b"); break;
2022 case 0x00400000: func (stream, "h"); break;
2023 case 0x00000100: func (stream, "w"); break;
2024 case 0x00400100: func (stream, "d"); break;
2025 default:
2026 break;
2028 break;
2030 case 'Z':
2032 int value;
2033 /* given (20, 23) | given (0, 3) */
2034 value = ((given >> 16) & 0xf0) | (given & 0xf);
2035 func (stream, "%d", value);
2037 break;
2039 case 'l':
2040 /* This is like the 'A' operator, except that if
2041 the width field "M" is zero, then the offset is
2042 *not* multiplied by four. */
2044 int offset = given & 0xff;
2045 int multiplier = (given & 0x00000100) ? 4 : 1;
2047 func (stream, "[%s", arm_regnames [(given >> 16) & 0xf]);
2049 if (offset)
2051 if ((given & 0x01000000) != 0)
2052 func (stream, ", #%s%d]%s",
2053 ((given & 0x00800000) == 0 ? "-" : ""),
2054 offset * multiplier,
2055 ((given & 0x00200000) != 0 ? "!" : ""));
2056 else
2057 func (stream, "], #%s%d",
2058 ((given & 0x00800000) == 0 ? "-" : ""),
2059 offset * multiplier);
2061 else
2062 func (stream, "]");
2064 break;
2066 case 'r':
2068 int imm4 = (given >> 4) & 0xf;
2069 int puw_bits = ((given >> 22) & 6) | ((given >> 21) & 1);
2070 int ubit = (given >> 23) & 1;
2071 const char *rm = arm_regnames [given & 0xf];
2072 const char *rn = arm_regnames [(given >> 16) & 0xf];
2074 switch (puw_bits)
2076 case 1:
2077 /* fall through */
2078 case 3:
2079 func (stream, "[%s], %c%s", rn, ubit ? '+' : '-', rm);
2080 if (imm4)
2081 func (stream, ", lsl #%d", imm4);
2082 break;
2084 case 4:
2085 /* fall through */
2086 case 5:
2087 /* fall through */
2088 case 6:
2089 /* fall through */
2090 case 7:
2091 func (stream, "[%s, %c%s", rn, ubit ? '+' : '-', rm);
2092 if (imm4 > 0)
2093 func (stream, ", lsl #%d", imm4);
2094 func (stream, "]");
2095 if (puw_bits == 5 || puw_bits == 7)
2096 func (stream, "!");
2097 break;
2099 default:
2100 func (stream, "INVALID");
2103 break;
2105 case 'i':
2107 long imm5;
2108 imm5 = ((given & 0x100) >> 4) | (given & 0xf);
2109 func (stream, "%ld", (imm5 == 0) ? 32 : imm5);
2111 break;
2113 default:
2114 abort ();
2118 else
2119 func (stream, "%c", *c);
2121 return true;
2124 return false;
2127 static void
2128 print_arm_address (bfd_vma pc, struct disassemble_info *info, long given)
2130 void *stream = info->stream;
2131 fprintf_function func = info->fprintf_func;
2133 if (((given & 0x000f0000) == 0x000f0000)
2134 && ((given & 0x02000000) == 0))
2136 int offset = given & 0xfff;
2138 func (stream, "[pc");
2140 if (given & 0x01000000)
2142 if ((given & 0x00800000) == 0)
2143 offset = - offset;
2145 /* Pre-indexed. */
2146 func (stream, ", #%d]", offset);
2148 offset += pc + 8;
2150 /* Cope with the possibility of write-back
2151 being used. Probably a very dangerous thing
2152 for the programmer to do, but who are we to
2153 argue ? */
2154 if (given & 0x00200000)
2155 func (stream, "!");
2157 else
2159 /* Post indexed. */
2160 func (stream, "], #%d", offset);
2162 /* ie ignore the offset. */
2163 offset = pc + 8;
2166 func (stream, "\t; ");
2167 info->print_address_func (offset, info);
2169 else
2171 func (stream, "[%s",
2172 arm_regnames[(given >> 16) & 0xf]);
2173 if ((given & 0x01000000) != 0)
2175 if ((given & 0x02000000) == 0)
2177 int offset = given & 0xfff;
2178 if (offset)
2179 func (stream, ", #%s%d",
2180 (((given & 0x00800000) == 0)
2181 ? "-" : ""), offset);
2183 else
2185 func (stream, ", %s",
2186 (((given & 0x00800000) == 0)
2187 ? "-" : ""));
2188 arm_decode_shift (given, func, stream, 1);
2191 func (stream, "]%s",
2192 ((given & 0x00200000) != 0) ? "!" : "");
2194 else
2196 if ((given & 0x02000000) == 0)
2198 int offset = given & 0xfff;
2199 if (offset)
2200 func (stream, "], #%s%d",
2201 (((given & 0x00800000) == 0)
2202 ? "-" : ""), offset);
2203 else
2204 func (stream, "]");
2206 else
2208 func (stream, "], %s",
2209 (((given & 0x00800000) == 0)
2210 ? "-" : ""));
2211 arm_decode_shift (given, func, stream, 1);
2217 /* Print one neon instruction on INFO->STREAM.
2218 Return true if the instruction matched, false if this is not a
2219 recognised neon instruction. */
2221 static bfd_boolean
2222 print_insn_neon (struct disassemble_info *info, long given, bfd_boolean thumb)
2224 const struct opcode32 *insn;
2225 void *stream = info->stream;
2226 fprintf_function func = info->fprintf_func;
2228 if (thumb)
2230 if ((given & 0xef000000) == 0xef000000)
2232 /* move bit 28 to bit 24 to translate Thumb2 to ARM encoding. */
2233 unsigned long bit28 = given & (1 << 28);
2235 given &= 0x00ffffff;
2236 if (bit28)
2237 given |= 0xf3000000;
2238 else
2239 given |= 0xf2000000;
2241 else if ((given & 0xff000000) == 0xf9000000)
2242 given ^= 0xf9000000 ^ 0xf4000000;
2243 else
2244 return false;
2247 for (insn = neon_opcodes; insn->assembler; insn++)
2249 if ((given & insn->mask) == insn->value)
2251 const char *c;
2253 for (c = insn->assembler; *c; c++)
2255 if (*c == '%')
2257 switch (*++c)
2259 case '%':
2260 func (stream, "%%");
2261 break;
2263 case 'c':
2264 if (thumb && ifthen_state)
2265 func (stream, "%s", arm_conditional[IFTHEN_COND]);
2266 break;
2268 case 'A':
2270 static const unsigned char enc[16] =
2272 0x4, 0x14, /* st4 0,1 */
2273 0x4, /* st1 2 */
2274 0x4, /* st2 3 */
2275 0x3, /* st3 4 */
2276 0x13, /* st3 5 */
2277 0x3, /* st1 6 */
2278 0x1, /* st1 7 */
2279 0x2, /* st2 8 */
2280 0x12, /* st2 9 */
2281 0x2, /* st1 10 */
2282 0, 0, 0, 0, 0
2284 int rd = ((given >> 12) & 0xf) | (((given >> 22) & 1) << 4);
2285 int rn = ((given >> 16) & 0xf);
2286 int rm = ((given >> 0) & 0xf);
2287 int align = ((given >> 4) & 0x3);
2288 int type = ((given >> 8) & 0xf);
2289 int n = enc[type] & 0xf;
2290 int stride = (enc[type] >> 4) + 1;
2291 int ix;
2293 func (stream, "{");
2294 if (stride > 1)
2295 for (ix = 0; ix != n; ix++)
2296 func (stream, "%sd%d", ix ? "," : "", rd + ix * stride);
2297 else if (n == 1)
2298 func (stream, "d%d", rd);
2299 else
2300 func (stream, "d%d-d%d", rd, rd + n - 1);
2301 func (stream, "}, [%s", arm_regnames[rn]);
2302 if (align)
2303 func (stream, ", :%d", 32 << align);
2304 func (stream, "]");
2305 if (rm == 0xd)
2306 func (stream, "!");
2307 else if (rm != 0xf)
2308 func (stream, ", %s", arm_regnames[rm]);
2310 break;
2312 case 'B':
2314 int rd = ((given >> 12) & 0xf) | (((given >> 22) & 1) << 4);
2315 int rn = ((given >> 16) & 0xf);
2316 int rm = ((given >> 0) & 0xf);
2317 int idx_align = ((given >> 4) & 0xf);
2318 int align = 0;
2319 int size = ((given >> 10) & 0x3);
2320 int idx = idx_align >> (size + 1);
2321 int length = ((given >> 8) & 3) + 1;
2322 int stride = 1;
2323 int i;
2325 if (length > 1 && size > 0)
2326 stride = (idx_align & (1 << size)) ? 2 : 1;
2328 switch (length)
2330 case 1:
2332 int amask = (1 << size) - 1;
2333 if ((idx_align & (1 << size)) != 0)
2334 return false;
2335 if (size > 0)
2337 if ((idx_align & amask) == amask)
2338 align = 8 << size;
2339 else if ((idx_align & amask) != 0)
2340 return false;
2343 break;
2345 case 2:
2346 if (size == 2 && (idx_align & 2) != 0)
2347 return false;
2348 align = (idx_align & 1) ? 16 << size : 0;
2349 break;
2351 case 3:
2352 if ((size == 2 && (idx_align & 3) != 0)
2353 || (idx_align & 1) != 0)
2354 return false;
2355 break;
2357 case 4:
2358 if (size == 2)
2360 if ((idx_align & 3) == 3)
2361 return false;
2362 align = (idx_align & 3) * 64;
2364 else
2365 align = (idx_align & 1) ? 32 << size : 0;
2366 break;
2368 default:
2369 abort ();
2372 func (stream, "{");
2373 for (i = 0; i < length; i++)
2374 func (stream, "%sd%d[%d]", (i == 0) ? "" : ",",
2375 rd + i * stride, idx);
2376 func (stream, "}, [%s", arm_regnames[rn]);
2377 if (align)
2378 func (stream, ", :%d", align);
2379 func (stream, "]");
2380 if (rm == 0xd)
2381 func (stream, "!");
2382 else if (rm != 0xf)
2383 func (stream, ", %s", arm_regnames[rm]);
2385 break;
2387 case 'C':
2389 int rd = ((given >> 12) & 0xf) | (((given >> 22) & 1) << 4);
2390 int rn = ((given >> 16) & 0xf);
2391 int rm = ((given >> 0) & 0xf);
2392 int align = ((given >> 4) & 0x1);
2393 int size = ((given >> 6) & 0x3);
2394 int type = ((given >> 8) & 0x3);
2395 int n = type + 1;
2396 int stride = ((given >> 5) & 0x1);
2397 int ix;
2399 if (stride && (n == 1))
2400 n++;
2401 else
2402 stride++;
2404 func (stream, "{");
2405 if (stride > 1)
2406 for (ix = 0; ix != n; ix++)
2407 func (stream, "%sd%d[]", ix ? "," : "", rd + ix * stride);
2408 else if (n == 1)
2409 func (stream, "d%d[]", rd);
2410 else
2411 func (stream, "d%d[]-d%d[]", rd, rd + n - 1);
2412 func (stream, "}, [%s", arm_regnames[rn]);
2413 if (align)
2415 int align = (8 * (type + 1)) << size;
2416 if (type == 3)
2417 align = (size > 1) ? align >> 1 : align;
2418 if (type == 2 || (type == 0 && !size))
2419 func (stream, ", :<bad align %d>", align);
2420 else
2421 func (stream, ", :%d", align);
2423 func (stream, "]");
2424 if (rm == 0xd)
2425 func (stream, "!");
2426 else if (rm != 0xf)
2427 func (stream, ", %s", arm_regnames[rm]);
2429 break;
2431 case 'D':
2433 int raw_reg = (given & 0xf) | ((given >> 1) & 0x10);
2434 int size = (given >> 20) & 3;
2435 int reg = raw_reg & ((4 << size) - 1);
2436 int ix = raw_reg >> size >> 2;
2438 func (stream, "d%d[%d]", reg, ix);
2440 break;
2442 case 'E':
2443 /* Neon encoded constant for mov, mvn, vorr, vbic */
2445 int bits = 0;
2446 int cmode = (given >> 8) & 0xf;
2447 int op = (given >> 5) & 0x1;
2448 unsigned long value = 0, hival = 0;
2449 unsigned shift;
2450 int size = 0;
2451 int isfloat = 0;
2453 bits |= ((given >> 24) & 1) << 7;
2454 bits |= ((given >> 16) & 7) << 4;
2455 bits |= ((given >> 0) & 15) << 0;
2457 if (cmode < 8)
2459 shift = (cmode >> 1) & 3;
2460 value = (unsigned long)bits << (8 * shift);
2461 size = 32;
2463 else if (cmode < 12)
2465 shift = (cmode >> 1) & 1;
2466 value = (unsigned long)bits << (8 * shift);
2467 size = 16;
2469 else if (cmode < 14)
2471 shift = (cmode & 1) + 1;
2472 value = (unsigned long)bits << (8 * shift);
2473 value |= (1ul << (8 * shift)) - 1;
2474 size = 32;
2476 else if (cmode == 14)
2478 if (op)
2480 /* bit replication into bytes */
2481 int ix;
2482 unsigned long mask;
2484 value = 0;
2485 hival = 0;
2486 for (ix = 7; ix >= 0; ix--)
2488 mask = ((bits >> ix) & 1) ? 0xff : 0;
2489 if (ix <= 3)
2490 value = (value << 8) | mask;
2491 else
2492 hival = (hival << 8) | mask;
2494 size = 64;
2496 else
2498 /* byte replication */
2499 value = (unsigned long)bits;
2500 size = 8;
2503 else if (!op)
2505 /* floating point encoding */
2506 int tmp;
2508 value = (unsigned long)(bits & 0x7f) << 19;
2509 value |= (unsigned long)(bits & 0x80) << 24;
2510 tmp = bits & 0x40 ? 0x3c : 0x40;
2511 value |= (unsigned long)tmp << 24;
2512 size = 32;
2513 isfloat = 1;
2515 else
2517 func (stream, "<illegal constant %.8x:%x:%x>",
2518 bits, cmode, op);
2519 break;
2521 switch (size)
2523 case 8:
2524 func (stream, "#%ld\t; 0x%.2lx", value, value);
2525 break;
2527 case 16:
2528 func (stream, "#%ld\t; 0x%.4lx", value, value);
2529 break;
2531 case 32:
2532 if (isfloat)
2534 unsigned char valbytes[4];
2535 double fvalue;
2537 /* Do this a byte at a time so we don't have to
2538 worry about the host's endianness. */
2539 valbytes[0] = value & 0xff;
2540 valbytes[1] = (value >> 8) & 0xff;
2541 valbytes[2] = (value >> 16) & 0xff;
2542 valbytes[3] = (value >> 24) & 0xff;
2544 floatformat_to_double (valbytes, &fvalue);
2546 func (stream, "#%.7g\t; 0x%.8lx", fvalue,
2547 value);
2549 else
2550 func (stream, "#%ld\t; 0x%.8lx",
2551 (long) ((value & 0x80000000)
2552 ? value | ~0xffffffffl : value), value);
2553 break;
2555 case 64:
2556 func (stream, "#0x%.8lx%.8lx", hival, value);
2557 break;
2559 default:
2560 abort ();
2563 break;
2565 case 'F':
2567 int regno = ((given >> 16) & 0xf) | ((given >> (7 - 4)) & 0x10);
2568 int num = (given >> 8) & 0x3;
2570 if (!num)
2571 func (stream, "{d%d}", regno);
2572 else if (num + regno >= 32)
2573 func (stream, "{d%d-<overflow reg d%d}", regno, regno + num);
2574 else
2575 func (stream, "{d%d-d%d}", regno, regno + num);
2577 break;
2580 case '0': case '1': case '2': case '3': case '4':
2581 case '5': case '6': case '7': case '8': case '9':
2583 int width;
2584 unsigned long value;
2586 c = arm_decode_bitfield (c, given, &value, &width);
2588 switch (*c)
2590 case 'r':
2591 func (stream, "%s", arm_regnames[value]);
2592 break;
2593 case 'd':
2594 func (stream, "%ld", value);
2595 break;
2596 case 'e':
2597 func (stream, "%ld", (1ul << width) - value);
2598 break;
2600 case 'S':
2601 case 'T':
2602 case 'U':
2603 /* various width encodings */
2605 int base = 8 << (*c - 'S'); /* 8,16 or 32 */
2606 int limit;
2607 unsigned low, high;
2609 c++;
2610 if (*c >= '0' && *c <= '9')
2611 limit = *c - '0';
2612 else if (*c >= 'a' && *c <= 'f')
2613 limit = *c - 'a' + 10;
2614 else
2615 abort ();
2616 low = limit >> 2;
2617 high = limit & 3;
2619 if (value < low || value > high)
2620 func (stream, "<illegal width %d>", base << value);
2621 else
2622 func (stream, "%d", base << value);
2624 break;
2625 case 'R':
2626 if (given & (1 << 6))
2627 goto Q;
2628 /* FALLTHROUGH */
2629 case 'D':
2630 func (stream, "d%ld", value);
2631 break;
2632 case 'Q':
2634 if (value & 1)
2635 func (stream, "<illegal reg q%ld.5>", value >> 1);
2636 else
2637 func (stream, "q%ld", value >> 1);
2638 break;
2640 case '`':
2641 c++;
2642 if (value == 0)
2643 func (stream, "%c", *c);
2644 break;
2645 case '\'':
2646 c++;
2647 if (value == ((1ul << width) - 1))
2648 func (stream, "%c", *c);
2649 break;
2650 case '?':
2651 func (stream, "%c", c[(1 << width) - (int)value]);
2652 c += 1 << width;
2653 break;
2654 default:
2655 abort ();
2657 break;
2659 default:
2660 abort ();
2664 else
2665 func (stream, "%c", *c);
2667 return true;
2670 return false;
2673 /* Print one ARM instruction from PC on INFO->STREAM. */
2675 static void
2676 print_insn_arm_internal (bfd_vma pc, struct disassemble_info *info, long given)
2678 const struct opcode32 *insn;
2679 void *stream = info->stream;
2680 fprintf_function func = info->fprintf_func;
2682 if (print_insn_coprocessor (pc, info, given, false))
2683 return;
2685 if (print_insn_neon (info, given, false))
2686 return;
2688 for (insn = arm_opcodes; insn->assembler; insn++)
2690 if (insn->value == FIRST_IWMMXT_INSN
2691 && info->mach != bfd_mach_arm_XScale
2692 && info->mach != bfd_mach_arm_iWMMXt)
2693 insn = insn + IWMMXT_INSN_COUNT;
2695 if ((given & insn->mask) == insn->value
2696 /* Special case: an instruction with all bits set in the condition field
2697 (0xFnnn_nnnn) is only matched if all those bits are set in insn->mask,
2698 or by the catchall at the end of the table. */
2699 && ((given & 0xF0000000) != 0xF0000000
2700 || (insn->mask & 0xF0000000) == 0xF0000000
2701 || (insn->mask == 0 && insn->value == 0)))
2703 const char *c;
2705 for (c = insn->assembler; *c; c++)
2707 if (*c == '%')
2709 switch (*++c)
2711 case '%':
2712 func (stream, "%%");
2713 break;
2715 case 'a':
2716 print_arm_address (pc, info, given);
2717 break;
2719 case 'P':
2720 /* Set P address bit and use normal address
2721 printing routine. */
2722 print_arm_address (pc, info, given | (1 << 24));
2723 break;
2725 case 's':
2726 if ((given & 0x004f0000) == 0x004f0000)
2728 /* PC relative with immediate offset. */
2729 int offset = ((given & 0xf00) >> 4) | (given & 0xf);
2731 if ((given & 0x00800000) == 0)
2732 offset = -offset;
2734 func (stream, "[pc, #%d]\t; ", offset);
2735 info->print_address_func (offset + pc + 8, info);
2737 else
2739 func (stream, "[%s",
2740 arm_regnames[(given >> 16) & 0xf]);
2741 if ((given & 0x01000000) != 0)
2743 /* Pre-indexed. */
2744 if ((given & 0x00400000) == 0x00400000)
2746 /* Immediate. */
2747 int offset = ((given & 0xf00) >> 4) | (given & 0xf);
2748 if (offset)
2749 func (stream, ", #%s%d",
2750 (((given & 0x00800000) == 0)
2751 ? "-" : ""), offset);
2753 else
2755 /* Register. */
2756 func (stream, ", %s%s",
2757 (((given & 0x00800000) == 0)
2758 ? "-" : ""),
2759 arm_regnames[given & 0xf]);
2762 func (stream, "]%s",
2763 ((given & 0x00200000) != 0) ? "!" : "");
2765 else
2767 /* Post-indexed. */
2768 if ((given & 0x00400000) == 0x00400000)
2770 /* Immediate. */
2771 int offset = ((given & 0xf00) >> 4) | (given & 0xf);
2772 if (offset)
2773 func (stream, "], #%s%d",
2774 (((given & 0x00800000) == 0)
2775 ? "-" : ""), offset);
2776 else
2777 func (stream, "]");
2779 else
2781 /* Register. */
2782 func (stream, "], %s%s",
2783 (((given & 0x00800000) == 0)
2784 ? "-" : ""),
2785 arm_regnames[given & 0xf]);
2789 break;
2791 case 'b':
2793 int disp = (((given & 0xffffff) ^ 0x800000) - 0x800000);
2794 info->print_address_func (disp*4 + pc + 8, info);
2796 break;
2798 case 'c':
2799 if (((given >> 28) & 0xf) != 0xe)
2800 func (stream, "%s",
2801 arm_conditional [(given >> 28) & 0xf]);
2802 break;
2804 case 'm':
2806 int started = 0;
2807 int reg;
2809 func (stream, "{");
2810 for (reg = 0; reg < 16; reg++)
2811 if ((given & (1 << reg)) != 0)
2813 if (started)
2814 func (stream, ", ");
2815 started = 1;
2816 func (stream, "%s", arm_regnames[reg]);
2818 func (stream, "}");
2820 break;
2822 case 'q':
2823 arm_decode_shift (given, func, stream, 0);
2824 break;
2826 case 'o':
2827 if ((given & 0x02000000) != 0)
2829 int rotate = (given & 0xf00) >> 7;
2830 int immed = (given & 0xff);
2831 immed = (((immed << (32 - rotate))
2832 | (immed >> rotate)) & 0xffffffff);
2833 func (stream, "#%d\t; 0x%x", immed, immed);
2835 else
2836 arm_decode_shift (given, func, stream, 1);
2837 break;
2839 case 'p':
2840 if ((given & 0x0000f000) == 0x0000f000)
2841 func (stream, "p");
2842 break;
2844 case 't':
2845 if ((given & 0x01200000) == 0x00200000)
2846 func (stream, "t");
2847 break;
2849 case 'A':
2850 func (stream, "[%s", arm_regnames [(given >> 16) & 0xf]);
2852 if ((given & (1 << 24)) != 0)
2854 int offset = given & 0xff;
2856 if (offset)
2857 func (stream, ", #%s%d]%s",
2858 ((given & 0x00800000) == 0 ? "-" : ""),
2859 offset * 4,
2860 ((given & 0x00200000) != 0 ? "!" : ""));
2861 else
2862 func (stream, "]");
2864 else
2866 int offset = given & 0xff;
2868 func (stream, "]");
2870 if (given & (1 << 21))
2872 if (offset)
2873 func (stream, ", #%s%d",
2874 ((given & 0x00800000) == 0 ? "-" : ""),
2875 offset * 4);
2877 else
2878 func (stream, ", {%d}", offset);
2880 break;
2882 case 'B':
2883 /* Print ARM V5 BLX(1) address: pc+25 bits. */
2885 bfd_vma address;
2886 bfd_vma offset = 0;
2888 if (given & 0x00800000)
2889 /* Is signed, hi bits should be ones. */
2890 offset = (-1) ^ 0x00ffffff;
2892 /* Offset is (SignExtend(offset field)<<2). */
2893 offset += given & 0x00ffffff;
2894 offset <<= 2;
2895 address = offset + pc + 8;
2897 if (given & 0x01000000)
2898 /* H bit allows addressing to 2-byte boundaries. */
2899 address += 2;
2901 info->print_address_func (address, info);
2903 break;
2905 case 'C':
2906 func (stream, "_");
2907 if (given & 0x80000)
2908 func (stream, "f");
2909 if (given & 0x40000)
2910 func (stream, "s");
2911 if (given & 0x20000)
2912 func (stream, "x");
2913 if (given & 0x10000)
2914 func (stream, "c");
2915 break;
2917 case 'U':
2918 switch (given & 0xf)
2920 case 0xf: func(stream, "sy"); break;
2921 case 0x7: func(stream, "un"); break;
2922 case 0xe: func(stream, "st"); break;
2923 case 0x6: func(stream, "unst"); break;
2924 default:
2925 func(stream, "#%d", (int)given & 0xf);
2926 break;
2928 break;
2930 case '0': case '1': case '2': case '3': case '4':
2931 case '5': case '6': case '7': case '8': case '9':
2933 int width;
2934 unsigned long value;
2936 c = arm_decode_bitfield (c, given, &value, &width);
2938 switch (*c)
2940 case 'r':
2941 func (stream, "%s", arm_regnames[value]);
2942 break;
2943 case 'd':
2944 func (stream, "%ld", value);
2945 break;
2946 case 'b':
2947 func (stream, "%ld", value * 8);
2948 break;
2949 case 'W':
2950 func (stream, "%ld", value + 1);
2951 break;
2952 case 'x':
2953 func (stream, "0x%08lx", value);
2955 /* Some SWI instructions have special
2956 meanings. */
2957 if ((given & 0x0fffffff) == 0x0FF00000)
2958 func (stream, "\t; IMB");
2959 else if ((given & 0x0fffffff) == 0x0FF00001)
2960 func (stream, "\t; IMBRange");
2961 break;
2962 case 'X':
2963 func (stream, "%01lx", value & 0xf);
2964 break;
2965 case '`':
2966 c++;
2967 if (value == 0)
2968 func (stream, "%c", *c);
2969 break;
2970 case '\'':
2971 c++;
2972 if (value == ((1ul << width) - 1))
2973 func (stream, "%c", *c);
2974 break;
2975 case '?':
2976 func (stream, "%c", c[(1 << width) - (int)value]);
2977 c += 1 << width;
2978 break;
2979 default:
2980 abort ();
2982 break;
2984 case 'e':
2986 int imm;
2988 imm = (given & 0xf) | ((given & 0xfff00) >> 4);
2989 func (stream, "%d", imm);
2991 break;
2993 case 'E':
2994 /* LSB and WIDTH fields of BFI or BFC. The machine-
2995 language instruction encodes LSB and MSB. */
2997 long msb = (given & 0x001f0000) >> 16;
2998 long lsb = (given & 0x00000f80) >> 7;
3000 long width = msb - lsb + 1;
3001 if (width > 0)
3002 func (stream, "#%lu, #%lu", lsb, width);
3003 else
3004 func (stream, "(invalid: %lu:%lu)", lsb, msb);
3006 break;
3008 case 'V':
3009 /* 16-bit unsigned immediate from a MOVT or MOVW
3010 instruction, encoded in bits 0:11 and 15:19. */
3012 long hi = (given & 0x000f0000) >> 4;
3013 long lo = (given & 0x00000fff);
3014 long imm16 = hi | lo;
3015 func (stream, "#%lu\t; 0x%lx", imm16, imm16);
3017 break;
3019 default:
3020 abort ();
3024 else
3025 func (stream, "%c", *c);
3027 return;
3030 abort ();
3033 /* Print one 16-bit Thumb instruction from PC on INFO->STREAM. */
3035 static void
3036 print_insn_thumb16 (bfd_vma pc, struct disassemble_info *info, long given)
3038 const struct opcode16 *insn;
3039 void *stream = info->stream;
3040 fprintf_function func = info->fprintf_func;
3042 for (insn = thumb_opcodes; insn->assembler; insn++)
3043 if ((given & insn->mask) == insn->value)
3045 const char *c = insn->assembler;
3046 for (; *c; c++)
3048 int domaskpc = 0;
3049 int domasklr = 0;
3051 if (*c != '%')
3053 func (stream, "%c", *c);
3054 continue;
3057 switch (*++c)
3059 case '%':
3060 func (stream, "%%");
3061 break;
3063 case 'c':
3064 if (ifthen_state)
3065 func (stream, "%s", arm_conditional[IFTHEN_COND]);
3066 break;
3068 case 'C':
3069 if (ifthen_state)
3070 func (stream, "%s", arm_conditional[IFTHEN_COND]);
3071 else
3072 func (stream, "s");
3073 break;
3075 case 'I':
3077 unsigned int tmp;
3079 ifthen_next_state = given & 0xff;
3080 for (tmp = given << 1; tmp & 0xf; tmp <<= 1)
3081 func (stream, ((given ^ tmp) & 0x10) ? "e" : "t");
3082 func (stream, "\t%s", arm_conditional[(given >> 4) & 0xf]);
3084 break;
3086 case 'x':
3087 if (ifthen_next_state)
3088 func (stream, "\t; unpredictable branch in IT block\n");
3089 break;
3091 case 'X':
3092 if (ifthen_state)
3093 func (stream, "\t; unpredictable <IT:%s>",
3094 arm_conditional[IFTHEN_COND]);
3095 break;
3097 case 'S':
3099 long reg;
3101 reg = (given >> 3) & 0x7;
3102 if (given & (1 << 6))
3103 reg += 8;
3105 func (stream, "%s", arm_regnames[reg]);
3107 break;
3109 case 'D':
3111 long reg;
3113 reg = given & 0x7;
3114 if (given & (1 << 7))
3115 reg += 8;
3117 func (stream, "%s", arm_regnames[reg]);
3119 break;
3121 case 'N':
3122 if (given & (1 << 8))
3123 domasklr = 1;
3124 /* Fall through. */
3125 case 'O':
3126 if (*c == 'O' && (given & (1 << 8)))
3127 domaskpc = 1;
3128 /* Fall through. */
3129 case 'M':
3131 int started = 0;
3132 int reg;
3134 func (stream, "{");
3136 /* It would be nice if we could spot
3137 ranges, and generate the rS-rE format: */
3138 for (reg = 0; (reg < 8); reg++)
3139 if ((given & (1 << reg)) != 0)
3141 if (started)
3142 func (stream, ", ");
3143 started = 1;
3144 func (stream, "%s", arm_regnames[reg]);
3147 if (domasklr)
3149 if (started)
3150 func (stream, ", ");
3151 started = 1;
3152 func (stream, "%s", arm_regnames[14] /* "lr" */);
3155 if (domaskpc)
3157 if (started)
3158 func (stream, ", ");
3159 func (stream, "%s", arm_regnames[15] /* "pc" */);
3162 func (stream, "}");
3164 break;
3166 case 'b':
3167 /* Print ARM V6T2 CZB address: pc+4+6 bits. */
3169 bfd_vma address = (pc + 4
3170 + ((given & 0x00f8) >> 2)
3171 + ((given & 0x0200) >> 3));
3172 info->print_address_func (address, info);
3174 break;
3176 case 's':
3177 /* Right shift immediate -- bits 6..10; 1-31 print
3178 as themselves, 0 prints as 32. */
3180 long imm = (given & 0x07c0) >> 6;
3181 if (imm == 0)
3182 imm = 32;
3183 func (stream, "#%ld", imm);
3185 break;
3187 case '0': case '1': case '2': case '3': case '4':
3188 case '5': case '6': case '7': case '8': case '9':
3190 int bitstart = *c++ - '0';
3191 int bitend = 0;
3193 while (*c >= '0' && *c <= '9')
3194 bitstart = (bitstart * 10) + *c++ - '0';
3196 switch (*c)
3198 case '-':
3200 long reg;
3202 c++;
3203 while (*c >= '0' && *c <= '9')
3204 bitend = (bitend * 10) + *c++ - '0';
3205 if (!bitend)
3206 abort ();
3207 reg = given >> bitstart;
3208 reg &= (2 << (bitend - bitstart)) - 1;
3209 switch (*c)
3211 case 'r':
3212 func (stream, "%s", arm_regnames[reg]);
3213 break;
3215 case 'd':
3216 func (stream, "%ld", reg);
3217 break;
3219 case 'H':
3220 func (stream, "%ld", reg << 1);
3221 break;
3223 case 'W':
3224 func (stream, "%ld", reg << 2);
3225 break;
3227 case 'a':
3228 /* PC-relative address -- the bottom two
3229 bits of the address are dropped
3230 before the calculation. */
3231 info->print_address_func
3232 (((pc + 4) & ~3) + (reg << 2), info);
3233 break;
3235 case 'x':
3236 func (stream, "0x%04lx", reg);
3237 break;
3239 case 'B':
3240 reg = ((reg ^ (1 << bitend)) - (1 << bitend));
3241 info->print_address_func (reg * 2 + pc + 4, info);
3242 break;
3244 case 'c':
3245 func (stream, "%s", arm_conditional [reg]);
3246 break;
3248 default:
3249 abort ();
3252 break;
3254 case '\'':
3255 c++;
3256 if ((given & (1 << bitstart)) != 0)
3257 func (stream, "%c", *c);
3258 break;
3260 case '?':
3261 ++c;
3262 if ((given & (1 << bitstart)) != 0)
3263 func (stream, "%c", *c++);
3264 else
3265 func (stream, "%c", *++c);
3266 break;
3268 default:
3269 abort ();
3272 break;
3274 default:
3275 abort ();
3278 return;
3281 /* No match. */
3282 abort ();
3285 /* Return the name of an V7M special register. */
3286 static const char *
3287 psr_name (int regno)
3289 switch (regno)
3291 case 0: return "APSR";
3292 case 1: return "IAPSR";
3293 case 2: return "EAPSR";
3294 case 3: return "PSR";
3295 case 5: return "IPSR";
3296 case 6: return "EPSR";
3297 case 7: return "IEPSR";
3298 case 8: return "MSP";
3299 case 9: return "PSP";
3300 case 16: return "PRIMASK";
3301 case 17: return "BASEPRI";
3302 case 18: return "BASEPRI_MASK";
3303 case 19: return "FAULTMASK";
3304 case 20: return "CONTROL";
3305 default: return "<unknown>";
3309 /* Print one 32-bit Thumb instruction from PC on INFO->STREAM. */
3311 static void
3312 print_insn_thumb32 (bfd_vma pc, struct disassemble_info *info, long given)
3314 const struct opcode32 *insn;
3315 void *stream = info->stream;
3316 fprintf_function func = info->fprintf_func;
3318 if (print_insn_coprocessor (pc, info, given, true))
3319 return;
3321 if (print_insn_neon (info, given, true))
3322 return;
3324 for (insn = thumb32_opcodes; insn->assembler; insn++)
3325 if ((given & insn->mask) == insn->value)
3327 const char *c = insn->assembler;
3328 for (; *c; c++)
3330 if (*c != '%')
3332 func (stream, "%c", *c);
3333 continue;
3336 switch (*++c)
3338 case '%':
3339 func (stream, "%%");
3340 break;
3342 case 'c':
3343 if (ifthen_state)
3344 func (stream, "%s", arm_conditional[IFTHEN_COND]);
3345 break;
3347 case 'x':
3348 if (ifthen_next_state)
3349 func (stream, "\t; unpredictable branch in IT block\n");
3350 break;
3352 case 'X':
3353 if (ifthen_state)
3354 func (stream, "\t; unpredictable <IT:%s>",
3355 arm_conditional[IFTHEN_COND]);
3356 break;
3358 case 'I':
3360 unsigned int imm12 = 0;
3361 imm12 |= (given & 0x000000ffu);
3362 imm12 |= (given & 0x00007000u) >> 4;
3363 imm12 |= (given & 0x04000000u) >> 15;
3364 func (stream, "#%u\t; 0x%x", imm12, imm12);
3366 break;
3368 case 'M':
3370 unsigned int bits = 0, imm, imm8, mod;
3371 bits |= (given & 0x000000ffu);
3372 bits |= (given & 0x00007000u) >> 4;
3373 bits |= (given & 0x04000000u) >> 15;
3374 imm8 = (bits & 0x0ff);
3375 mod = (bits & 0xf00) >> 8;
3376 switch (mod)
3378 case 0: imm = imm8; break;
3379 case 1: imm = ((imm8<<16) | imm8); break;
3380 case 2: imm = ((imm8<<24) | (imm8 << 8)); break;
3381 case 3: imm = ((imm8<<24) | (imm8 << 16) | (imm8 << 8) | imm8); break;
3382 default:
3383 mod = (bits & 0xf80) >> 7;
3384 imm8 = (bits & 0x07f) | 0x80;
3385 imm = (((imm8 << (32 - mod)) | (imm8 >> mod)) & 0xffffffff);
3387 func (stream, "#%u\t; 0x%x", imm, imm);
3389 break;
3391 case 'J':
3393 unsigned int imm = 0;
3394 imm |= (given & 0x000000ffu);
3395 imm |= (given & 0x00007000u) >> 4;
3396 imm |= (given & 0x04000000u) >> 15;
3397 imm |= (given & 0x000f0000u) >> 4;
3398 func (stream, "#%u\t; 0x%x", imm, imm);
3400 break;
3402 case 'K':
3404 unsigned int imm = 0;
3405 imm |= (given & 0x000f0000u) >> 16;
3406 imm |= (given & 0x00000ff0u) >> 0;
3407 imm |= (given & 0x0000000fu) << 12;
3408 func (stream, "#%u\t; 0x%x", imm, imm);
3410 break;
3412 case 'S':
3414 unsigned int reg = (given & 0x0000000fu);
3415 unsigned int stp = (given & 0x00000030u) >> 4;
3416 unsigned int imm = 0;
3417 imm |= (given & 0x000000c0u) >> 6;
3418 imm |= (given & 0x00007000u) >> 10;
3420 func (stream, "%s", arm_regnames[reg]);
3421 switch (stp)
3423 case 0:
3424 if (imm > 0)
3425 func (stream, ", lsl #%u", imm);
3426 break;
3428 case 1:
3429 if (imm == 0)
3430 imm = 32;
3431 func (stream, ", lsr #%u", imm);
3432 break;
3434 case 2:
3435 if (imm == 0)
3436 imm = 32;
3437 func (stream, ", asr #%u", imm);
3438 break;
3440 case 3:
3441 if (imm == 0)
3442 func (stream, ", rrx");
3443 else
3444 func (stream, ", ror #%u", imm);
3447 break;
3449 case 'a':
3451 unsigned int Rn = (given & 0x000f0000) >> 16;
3452 unsigned int U = (given & 0x00800000) >> 23;
3453 unsigned int op = (given & 0x00000f00) >> 8;
3454 unsigned int i12 = (given & 0x00000fff);
3455 unsigned int i8 = (given & 0x000000ff);
3456 bfd_boolean writeback = false, postind = false;
3457 int offset = 0;
3459 func (stream, "[%s", arm_regnames[Rn]);
3460 if (U) /* 12-bit positive immediate offset */
3461 offset = i12;
3462 else if (Rn == 15) /* 12-bit negative immediate offset */
3463 offset = -(int)i12;
3464 else if (op == 0x0) /* shifted register offset */
3466 unsigned int Rm = (i8 & 0x0f);
3467 unsigned int sh = (i8 & 0x30) >> 4;
3468 func (stream, ", %s", arm_regnames[Rm]);
3469 if (sh)
3470 func (stream, ", lsl #%u", sh);
3471 func (stream, "]");
3472 break;
3474 else switch (op)
3476 case 0xE: /* 8-bit positive immediate offset */
3477 offset = i8;
3478 break;
3480 case 0xC: /* 8-bit negative immediate offset */
3481 offset = -i8;
3482 break;
3484 case 0xF: /* 8-bit + preindex with wb */
3485 offset = i8;
3486 writeback = true;
3487 break;
3489 case 0xD: /* 8-bit - preindex with wb */
3490 offset = -i8;
3491 writeback = true;
3492 break;
3494 case 0xB: /* 8-bit + postindex */
3495 offset = i8;
3496 postind = true;
3497 break;
3499 case 0x9: /* 8-bit - postindex */
3500 offset = -i8;
3501 postind = true;
3502 break;
3504 default:
3505 func (stream, ", <undefined>]");
3506 goto skip;
3509 if (postind)
3510 func (stream, "], #%d", offset);
3511 else
3513 if (offset)
3514 func (stream, ", #%d", offset);
3515 func (stream, writeback ? "]!" : "]");
3518 if (Rn == 15)
3520 func (stream, "\t; ");
3521 info->print_address_func (((pc + 4) & ~3) + offset, info);
3524 skip:
3525 break;
3527 case 'A':
3529 unsigned int P = (given & 0x01000000) >> 24;
3530 unsigned int U = (given & 0x00800000) >> 23;
3531 unsigned int W = (given & 0x00400000) >> 21;
3532 unsigned int Rn = (given & 0x000f0000) >> 16;
3533 unsigned int off = (given & 0x000000ff);
3535 func (stream, "[%s", arm_regnames[Rn]);
3536 if (P)
3538 if (off || !U)
3539 func (stream, ", #%c%u", U ? '+' : '-', off * 4);
3540 func (stream, "]");
3541 if (W)
3542 func (stream, "!");
3544 else
3546 func (stream, "], ");
3547 if (W)
3548 func (stream, "#%c%u", U ? '+' : '-', off * 4);
3549 else
3550 func (stream, "{%u}", off);
3553 break;
3555 case 'w':
3557 unsigned int Sbit = (given & 0x01000000) >> 24;
3558 unsigned int type = (given & 0x00600000) >> 21;
3559 switch (type)
3561 case 0: func (stream, Sbit ? "sb" : "b"); break;
3562 case 1: func (stream, Sbit ? "sh" : "h"); break;
3563 case 2:
3564 if (Sbit)
3565 func (stream, "??");
3566 break;
3567 case 3:
3568 func (stream, "??");
3569 break;
3572 break;
3574 case 'm':
3576 int started = 0;
3577 int reg;
3579 func (stream, "{");
3580 for (reg = 0; reg < 16; reg++)
3581 if ((given & (1 << reg)) != 0)
3583 if (started)
3584 func (stream, ", ");
3585 started = 1;
3586 func (stream, "%s", arm_regnames[reg]);
3588 func (stream, "}");
3590 break;
3592 case 'E':
3594 unsigned int msb = (given & 0x0000001f);
3595 unsigned int lsb = 0;
3596 lsb |= (given & 0x000000c0u) >> 6;
3597 lsb |= (given & 0x00007000u) >> 10;
3598 func (stream, "#%u, #%u", lsb, msb - lsb + 1);
3600 break;
3602 case 'F':
3604 unsigned int width = (given & 0x0000001f) + 1;
3605 unsigned int lsb = 0;
3606 lsb |= (given & 0x000000c0u) >> 6;
3607 lsb |= (given & 0x00007000u) >> 10;
3608 func (stream, "#%u, #%u", lsb, width);
3610 break;
3612 case 'b':
3614 unsigned int S = (given & 0x04000000u) >> 26;
3615 unsigned int J1 = (given & 0x00002000u) >> 13;
3616 unsigned int J2 = (given & 0x00000800u) >> 11;
3617 int offset = 0;
3619 offset |= !S << 20;
3620 offset |= J2 << 19;
3621 offset |= J1 << 18;
3622 offset |= (given & 0x003f0000) >> 4;
3623 offset |= (given & 0x000007ff) << 1;
3624 offset -= (1 << 20);
3626 info->print_address_func (pc + 4 + offset, info);
3628 break;
3630 case 'B':
3632 unsigned int S = (given & 0x04000000u) >> 26;
3633 unsigned int I1 = (given & 0x00002000u) >> 13;
3634 unsigned int I2 = (given & 0x00000800u) >> 11;
3635 int offset = 0;
3637 offset |= !S << 24;
3638 offset |= !(I1 ^ S) << 23;
3639 offset |= !(I2 ^ S) << 22;
3640 offset |= (given & 0x03ff0000u) >> 4;
3641 offset |= (given & 0x000007ffu) << 1;
3642 offset -= (1 << 24);
3643 offset += pc + 4;
3645 /* BLX target addresses are always word aligned. */
3646 if ((given & 0x00001000u) == 0)
3647 offset &= ~2u;
3649 info->print_address_func (offset, info);
3651 break;
3653 case 's':
3655 unsigned int shift = 0;
3656 shift |= (given & 0x000000c0u) >> 6;
3657 shift |= (given & 0x00007000u) >> 10;
3658 if (given & 0x00200000u)
3659 func (stream, ", asr #%u", shift);
3660 else if (shift)
3661 func (stream, ", lsl #%u", shift);
3662 /* else print nothing - lsl #0 */
3664 break;
3666 case 'R':
3668 unsigned int rot = (given & 0x00000030) >> 4;
3669 if (rot)
3670 func (stream, ", ror #%u", rot * 8);
3672 break;
3674 case 'U':
3675 switch (given & 0xf)
3677 case 0xf: func(stream, "sy"); break;
3678 case 0x7: func(stream, "un"); break;
3679 case 0xe: func(stream, "st"); break;
3680 case 0x6: func(stream, "unst"); break;
3681 default:
3682 func(stream, "#%d", (int)given & 0xf);
3683 break;
3685 break;
3687 case 'C':
3688 if ((given & 0xff) == 0)
3690 func (stream, "%cPSR_", (given & 0x100000) ? 'S' : 'C');
3691 if (given & 0x800)
3692 func (stream, "f");
3693 if (given & 0x400)
3694 func (stream, "s");
3695 if (given & 0x200)
3696 func (stream, "x");
3697 if (given & 0x100)
3698 func (stream, "c");
3700 else
3702 func (stream, "%s", psr_name (given & 0xff));
3704 break;
3706 case 'D':
3707 if ((given & 0xff) == 0)
3708 func (stream, "%cPSR", (given & 0x100000) ? 'S' : 'C');
3709 else
3710 func (stream, "%s", psr_name (given & 0xff));
3711 break;
3713 case '0': case '1': case '2': case '3': case '4':
3714 case '5': case '6': case '7': case '8': case '9':
3716 int width;
3717 unsigned long val;
3719 c = arm_decode_bitfield (c, given, &val, &width);
3721 switch (*c)
3723 case 'd': func (stream, "%lu", val); break;
3724 case 'W': func (stream, "%lu", val * 4); break;
3725 case 'r': func (stream, "%s", arm_regnames[val]); break;
3727 case 'c':
3728 func (stream, "%s", arm_conditional[val]);
3729 break;
3731 case '\'':
3732 c++;
3733 if (val == ((1ul << width) - 1))
3734 func (stream, "%c", *c);
3735 break;
3737 case '`':
3738 c++;
3739 if (val == 0)
3740 func (stream, "%c", *c);
3741 break;
3743 case '?':
3744 func (stream, "%c", c[(1 << width) - (int)val]);
3745 c += 1 << width;
3746 break;
3748 default:
3749 abort ();
3752 break;
3754 default:
3755 abort ();
3758 return;
3761 /* No match. */
3762 abort ();
3765 /* Print data bytes on INFO->STREAM. */
3767 static void
3768 print_insn_data (bfd_vma pc ATTRIBUTE_UNUSED, struct disassemble_info *info,
3769 long given)
3771 switch (info->bytes_per_chunk)
3773 case 1:
3774 info->fprintf_func (info->stream, ".byte\t0x%02lx", given);
3775 break;
3776 case 2:
3777 info->fprintf_func (info->stream, ".short\t0x%04lx", given);
3778 break;
3779 case 4:
3780 info->fprintf_func (info->stream, ".word\t0x%08lx", given);
3781 break;
3782 default:
3783 abort ();
3787 /* Search back through the insn stream to determine if this instruction is
3788 conditionally executed. */
3789 static void
3790 find_ifthen_state (bfd_vma pc, struct disassemble_info *info,
3791 bfd_boolean little)
3793 unsigned char b[2];
3794 unsigned int insn;
3795 int status;
3796 /* COUNT is twice the number of instructions seen. It will be odd if we
3797 just crossed an instruction boundary. */
3798 int count;
3799 int it_count;
3800 unsigned int seen_it;
3801 bfd_vma addr;
3803 ifthen_address = pc;
3804 ifthen_state = 0;
3806 addr = pc;
3807 count = 1;
3808 it_count = 0;
3809 seen_it = 0;
3810 /* Scan backwards looking for IT instructions, keeping track of where
3811 instruction boundaries are. We don't know if something is actually an
3812 IT instruction until we find a definite instruction boundary. */
3813 for (;;)
3815 if (addr == 0 || info->symbol_at_address_func(addr, info))
3817 /* A symbol must be on an instruction boundary, and will not
3818 be within an IT block. */
3819 if (seen_it && (count & 1))
3820 break;
3822 return;
3824 addr -= 2;
3825 status = info->read_memory_func (addr, (bfd_byte *)b, 2, info);
3826 if (status)
3827 return;
3829 if (little)
3830 insn = (b[0]) | (b[1] << 8);
3831 else
3832 insn = (b[1]) | (b[0] << 8);
3833 if (seen_it)
3835 if ((insn & 0xf800) < 0xe800)
3837 /* Addr + 2 is an instruction boundary. See if this matches
3838 the expected boundary based on the position of the last
3839 IT candidate. */
3840 if (count & 1)
3841 break;
3842 seen_it = 0;
3845 if ((insn & 0xff00) == 0xbf00 && (insn & 0xf) != 0)
3847 /* This could be an IT instruction. */
3848 seen_it = insn;
3849 it_count = count >> 1;
3851 if ((insn & 0xf800) >= 0xe800)
3852 count++;
3853 else
3854 count = (count + 2) | 1;
3855 /* IT blocks contain at most 4 instructions. */
3856 if (count >= 8 && !seen_it)
3857 return;
3859 /* We found an IT instruction. */
3860 ifthen_state = (seen_it & 0xe0) | ((seen_it << it_count) & 0x1f);
3861 if ((ifthen_state & 0xf) == 0)
3862 ifthen_state = 0;
3865 /* NOTE: There are no checks in these routines that
3866 the relevant number of data bytes exist. */
3869 print_insn_arm (bfd_vma pc, struct disassemble_info *info)
3871 unsigned char b[4];
3872 long given;
3873 int status;
3874 int is_thumb = false;
3875 int is_data = false;
3876 unsigned int size = 4;
3877 void (*printer) (bfd_vma, struct disassemble_info *, long);
3878 int little;
3880 little = (info->endian == BFD_ENDIAN_LITTLE);
3881 is_thumb |= (pc & 1);
3882 pc &= ~(bfd_vma)1;
3884 if (force_thumb)
3885 is_thumb = true;
3887 info->bytes_per_line = 4;
3889 if (is_data)
3891 int i;
3893 /* size was already set above. */
3894 info->bytes_per_chunk = size;
3895 printer = print_insn_data;
3897 status = info->read_memory_func (pc, (bfd_byte *)b, size, info);
3898 given = 0;
3899 if (little)
3900 for (i = size - 1; i >= 0; i--)
3901 given = b[i] | (given << 8);
3902 else
3903 for (i = 0; i < (int) size; i++)
3904 given = b[i] | (given << 8);
3906 else if (!is_thumb)
3908 /* In ARM mode endianness is a straightforward issue: the instruction
3909 is four bytes long and is either ordered 0123 or 3210. */
3910 printer = print_insn_arm_internal;
3911 info->bytes_per_chunk = 4;
3912 size = 4;
3914 status = info->read_memory_func (pc, (bfd_byte *)b, 4, info);
3915 if (little)
3916 given = (b[0]) | (b[1] << 8) | (b[2] << 16) | (b[3] << 24);
3917 else
3918 given = (b[3]) | (b[2] << 8) | (b[1] << 16) | (b[0] << 24);
3920 else
3922 /* In Thumb mode we have the additional wrinkle of two
3923 instruction lengths. Fortunately, the bits that determine
3924 the length of the current instruction are always to be found
3925 in the first two bytes. */
3926 printer = print_insn_thumb16;
3927 info->bytes_per_chunk = 2;
3928 size = 2;
3930 status = info->read_memory_func (pc, (bfd_byte *)b, 2, info);
3931 if (little)
3932 given = (b[0]) | (b[1] << 8);
3933 else
3934 given = (b[1]) | (b[0] << 8);
3936 if (!status)
3938 /* These bit patterns signal a four-byte Thumb
3939 instruction. */
3940 if ((given & 0xF800) == 0xF800
3941 || (given & 0xF800) == 0xF000
3942 || (given & 0xF800) == 0xE800)
3944 status = info->read_memory_func (pc + 2, (bfd_byte *)b, 2, info);
3945 if (little)
3946 given = (b[0]) | (b[1] << 8) | (given << 16);
3947 else
3948 given = (b[1]) | (b[0] << 8) | (given << 16);
3950 printer = print_insn_thumb32;
3951 size = 4;
3955 if (ifthen_address != pc)
3956 find_ifthen_state(pc, info, little);
3958 if (ifthen_state)
3960 if ((ifthen_state & 0xf) == 0x8)
3961 ifthen_next_state = 0;
3962 else
3963 ifthen_next_state = (ifthen_state & 0xe0)
3964 | ((ifthen_state & 0xf) << 1);
3968 if (status)
3970 info->memory_error_func (status, pc, info);
3971 return -1;
3973 if (info->flags & INSN_HAS_RELOC)
3974 /* If the instruction has a reloc associated with it, then
3975 the offset field in the instruction will actually be the
3976 addend for the reloc. (We are using REL type relocs).
3977 In such cases, we can ignore the pc when computing
3978 addresses, since the addend is not currently pc-relative. */
3979 pc = 0;
3981 /* We include the hexdump of the instruction. The format here
3982 matches that used by objdump and the ARM ARM (in particular,
3983 32 bit Thumb instructions are displayed as pairs of halfwords,
3984 not as a single word.) */
3985 if (is_thumb)
3987 if (size == 2)
3989 info->fprintf_func(info->stream, "%04lx ",
3990 ((unsigned long)given) & 0xffff);
3992 else
3994 info->fprintf_func(info->stream, "%04lx %04lx ",
3995 (((unsigned long)given) >> 16) & 0xffff,
3996 ((unsigned long)given) & 0xffff);
3999 else
4001 info->fprintf_func(info->stream, "%08lx ",
4002 ((unsigned long)given) & 0xffffffff);
4005 printer (pc, info, given);
4007 if (is_thumb)
4009 ifthen_state = ifthen_next_state;
4010 ifthen_address += size;
4012 return size;