1 /* Instruction printing code for the ARM
2 Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003,
3 2004, 2005, 2006, 2007, 2008, 2009 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 library is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3 of the License, or
12 (at your option) any later version.
14 It is distributed in the hope that it will be useful, but WITHOUT
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
16 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
17 License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
22 MA 02110-1301, USA. */
27 #include "opcode/arm.h"
29 #include "safe-ctype.h"
30 #include "floatformat.h"
32 /* FIXME: This shouldn't be done here. */
33 #include "coff/internal.h"
36 #include "elf/internal.h"
39 /* FIXME: Belongs in global header. */
41 #define strneq(a,b,n) (strncmp ((a), (b), (n)) == 0)
45 #define NUM_ELEM(a) (sizeof (a) / sizeof (a)[0])
50 unsigned long arch
; /* Architecture defining this insn. */
51 unsigned long value
; /* If arch == 0 then value is a sentinel. */
52 unsigned long mask
; /* Recognise insn if (op & mask) == value. */
53 const char * assembler
; /* How to disassemble this insn. */
58 unsigned long arch
; /* Architecture defining this insn. */
59 unsigned short value
, mask
; /* Recognise insn if (op & mask) == value. */
60 const char *assembler
; /* How to disassemble this insn. */
63 /* print_insn_coprocessor recognizes the following format control codes:
67 %c print condition code (always bits 28-31 in ARM mode)
68 %q print shifter argument
69 %u print condition code (unconditional in ARM mode)
70 %A print address for ldc/stc/ldf/stf instruction
71 %B print vstm/vldm register list
72 %I print cirrus signed shift immediate: bits 0..3|4..6
73 %F print the COUNT field of a LFM/SFM instruction.
74 %P print floating point precision in arithmetic insn
75 %Q print floating point precision in ldf/stf insn
76 %R print floating point rounding mode
78 %<bitfield>r print as an ARM register
79 %<bitfield>d print the bitfield in decimal
80 %<bitfield>k print immediate for VFPv3 conversion instruction
81 %<bitfield>x print the bitfield in hex
82 %<bitfield>X print the bitfield as 1 hex digit without leading "0x"
83 %<bitfield>f print a floating point constant if >7 else a
84 floating point register
85 %<bitfield>w print as an iWMMXt width field - [bhwd]ss/us
86 %<bitfield>g print as an iWMMXt 64-bit register
87 %<bitfield>G print as an iWMMXt general purpose or control register
88 %<bitfield>D print as a NEON D register
89 %<bitfield>Q print as a NEON Q register
91 %y<code> print a single precision VFP reg.
92 Codes: 0=>Sm, 1=>Sd, 2=>Sn, 3=>multi-list, 4=>Sm pair
93 %z<code> print a double precision VFP reg
94 Codes: 0=>Dm, 1=>Dd, 2=>Dn, 3=>multi-list
96 %<bitfield>'c print specified char iff bitfield is all ones
97 %<bitfield>`c print specified char iff bitfield is all zeroes
98 %<bitfield>?ab... select from array of values in big endian order
100 %L print as an iWMMXt N/M width field.
101 %Z print the Immediate of a WSHUFH instruction.
102 %l like 'A' except use byte offsets for 'B' & 'H'
104 %i print 5-bit immediate in bits 8,3..0
106 %r print register offset address for wldt/wstr instruction. */
108 enum opcode_sentinel_enum
110 SENTINEL_IWMMXT_START
= 1,
112 SENTINEL_GENERIC_START
115 #define UNDEFINED_INSTRUCTION "\t\t; <UNDEFINED> instruction: %0-31x"
116 #define UNPREDICTABLE_INSTRUCTION "\t; <UNPREDICTABLE>"
118 /* Common coprocessor opcodes shared between Arm and Thumb-2. */
120 static const struct opcode32 coprocessor_opcodes
[] =
122 /* XScale instructions. */
123 {ARM_CEXT_XSCALE
, 0x0e200010, 0x0fff0ff0, "mia%c\tacc0, %0-3r, %12-15r"},
124 {ARM_CEXT_XSCALE
, 0x0e280010, 0x0fff0ff0, "miaph%c\tacc0, %0-3r, %12-15r"},
125 {ARM_CEXT_XSCALE
, 0x0e2c0010, 0x0ffc0ff0, "mia%17'T%17`B%16'T%16`B%c\tacc0, %0-3r, %12-15r"},
126 {ARM_CEXT_XSCALE
, 0x0c400000, 0x0ff00fff, "mar%c\tacc0, %12-15r, %16-19r"},
127 {ARM_CEXT_XSCALE
, 0x0c500000, 0x0ff00fff, "mra%c\t%12-15r, %16-19r, acc0"},
129 /* Intel Wireless MMX technology instructions. */
130 { 0, SENTINEL_IWMMXT_START
, 0, "" },
131 {ARM_CEXT_IWMMXT
, 0x0e130130, 0x0f3f0fff, "tandc%22-23w%c\t%12-15r"},
132 {ARM_CEXT_XSCALE
, 0x0e400010, 0x0ff00f3f, "tbcst%6-7w%c\t%16-19g, %12-15r"},
133 {ARM_CEXT_XSCALE
, 0x0e130170, 0x0f3f0ff8, "textrc%22-23w%c\t%12-15r, #%0-2d"},
134 {ARM_CEXT_XSCALE
, 0x0e100070, 0x0f300ff0, "textrm%3?su%22-23w%c\t%12-15r, %16-19g, #%0-2d"},
135 {ARM_CEXT_XSCALE
, 0x0e600010, 0x0ff00f38, "tinsr%6-7w%c\t%16-19g, %12-15r, #%0-2d"},
136 {ARM_CEXT_XSCALE
, 0x0e000110, 0x0ff00fff, "tmcr%c\t%16-19G, %12-15r"},
137 {ARM_CEXT_XSCALE
, 0x0c400000, 0x0ff00ff0, "tmcrr%c\t%0-3g, %12-15r, %16-19r"},
138 {ARM_CEXT_XSCALE
, 0x0e2c0010, 0x0ffc0e10, "tmia%17?tb%16?tb%c\t%5-8g, %0-3r, %12-15r"},
139 {ARM_CEXT_XSCALE
, 0x0e200010, 0x0fff0e10, "tmia%c\t%5-8g, %0-3r, %12-15r"},
140 {ARM_CEXT_XSCALE
, 0x0e280010, 0x0fff0e10, "tmiaph%c\t%5-8g, %0-3r, %12-15r"},
141 {ARM_CEXT_XSCALE
, 0x0e100030, 0x0f300fff, "tmovmsk%22-23w%c\t%12-15r, %16-19g"},
142 {ARM_CEXT_XSCALE
, 0x0e100110, 0x0ff00ff0, "tmrc%c\t%12-15r, %16-19G"},
143 {ARM_CEXT_XSCALE
, 0x0c500000, 0x0ff00ff0, "tmrrc%c\t%12-15r, %16-19r, %0-3g"},
144 {ARM_CEXT_XSCALE
, 0x0e130150, 0x0f3f0fff, "torc%22-23w%c\t%12-15r"},
145 {ARM_CEXT_XSCALE
, 0x0e120190, 0x0f3f0fff, "torvsc%22-23w%c\t%12-15r"},
146 {ARM_CEXT_XSCALE
, 0x0e2001c0, 0x0f300fff, "wabs%22-23w%c\t%12-15g, %16-19g"},
147 {ARM_CEXT_XSCALE
, 0x0e0001c0, 0x0f300fff, "wacc%22-23w%c\t%12-15g, %16-19g"},
148 {ARM_CEXT_XSCALE
, 0x0e000180, 0x0f000ff0, "wadd%20-23w%c\t%12-15g, %16-19g, %0-3g"},
149 {ARM_CEXT_XSCALE
, 0x0e2001a0, 0x0fb00ff0, "waddbhus%22?ml%c\t%12-15g, %16-19g, %0-3g"},
150 {ARM_CEXT_XSCALE
, 0x0ea001a0, 0x0ff00ff0, "waddsubhx%c\t%12-15g, %16-19g, %0-3g"},
151 {ARM_CEXT_XSCALE
, 0x0e000020, 0x0f800ff0, "waligni%c\t%12-15g, %16-19g, %0-3g, #%20-22d"},
152 {ARM_CEXT_XSCALE
, 0x0e800020, 0x0fc00ff0, "walignr%20-21d%c\t%12-15g, %16-19g, %0-3g"},
153 {ARM_CEXT_XSCALE
, 0x0e200000, 0x0fe00ff0, "wand%20'n%c\t%12-15g, %16-19g, %0-3g"},
154 {ARM_CEXT_XSCALE
, 0x0e800000, 0x0fa00ff0, "wavg2%22?hb%20'r%c\t%12-15g, %16-19g, %0-3g"},
155 {ARM_CEXT_XSCALE
, 0x0e400000, 0x0fe00ff0, "wavg4%20'r%c\t%12-15g, %16-19g, %0-3g"},
156 {ARM_CEXT_XSCALE
, 0x0e000060, 0x0f300ff0, "wcmpeq%22-23w%c\t%12-15g, %16-19g, %0-3g"},
157 {ARM_CEXT_XSCALE
, 0x0e100060, 0x0f100ff0, "wcmpgt%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
158 {ARM_CEXT_XSCALE
, 0xfc500100, 0xfe500f00, "wldrd\t%12-15g, %r"},
159 {ARM_CEXT_XSCALE
, 0xfc100100, 0xfe500f00, "wldrw\t%12-15G, %A"},
160 {ARM_CEXT_XSCALE
, 0x0c100000, 0x0e100e00, "wldr%L%c\t%12-15g, %l"},
161 {ARM_CEXT_XSCALE
, 0x0e400100, 0x0fc00ff0, "wmac%21?su%20'z%c\t%12-15g, %16-19g, %0-3g"},
162 {ARM_CEXT_XSCALE
, 0x0e800100, 0x0fc00ff0, "wmadd%21?su%20'x%c\t%12-15g, %16-19g, %0-3g"},
163 {ARM_CEXT_XSCALE
, 0x0ec00100, 0x0fd00ff0, "wmadd%21?sun%c\t%12-15g, %16-19g, %0-3g"},
164 {ARM_CEXT_XSCALE
, 0x0e000160, 0x0f100ff0, "wmax%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
165 {ARM_CEXT_XSCALE
, 0x0e000080, 0x0f100fe0, "wmerge%c\t%12-15g, %16-19g, %0-3g, #%21-23d"},
166 {ARM_CEXT_XSCALE
, 0x0e0000a0, 0x0f800ff0, "wmia%21?tb%20?tb%22'n%c\t%12-15g, %16-19g, %0-3g"},
167 {ARM_CEXT_XSCALE
, 0x0e800120, 0x0f800ff0, "wmiaw%21?tb%20?tb%22'n%c\t%12-15g, %16-19g, %0-3g"},
168 {ARM_CEXT_XSCALE
, 0x0e100160, 0x0f100ff0, "wmin%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
169 {ARM_CEXT_XSCALE
, 0x0e000100, 0x0fc00ff0, "wmul%21?su%20?ml%23'r%c\t%12-15g, %16-19g, %0-3g"},
170 {ARM_CEXT_XSCALE
, 0x0ed00100, 0x0fd00ff0, "wmul%21?sumr%c\t%12-15g, %16-19g, %0-3g"},
171 {ARM_CEXT_XSCALE
, 0x0ee000c0, 0x0fe00ff0, "wmulwsm%20`r%c\t%12-15g, %16-19g, %0-3g"},
172 {ARM_CEXT_XSCALE
, 0x0ec000c0, 0x0fe00ff0, "wmulwum%20`r%c\t%12-15g, %16-19g, %0-3g"},
173 {ARM_CEXT_XSCALE
, 0x0eb000c0, 0x0ff00ff0, "wmulwl%c\t%12-15g, %16-19g, %0-3g"},
174 {ARM_CEXT_XSCALE
, 0x0e8000a0, 0x0f800ff0, "wqmia%21?tb%20?tb%22'n%c\t%12-15g, %16-19g, %0-3g"},
175 {ARM_CEXT_XSCALE
, 0x0e100080, 0x0fd00ff0, "wqmulm%21'r%c\t%12-15g, %16-19g, %0-3g"},
176 {ARM_CEXT_XSCALE
, 0x0ec000e0, 0x0fd00ff0, "wqmulwm%21'r%c\t%12-15g, %16-19g, %0-3g"},
177 {ARM_CEXT_XSCALE
, 0x0e000000, 0x0ff00ff0, "wor%c\t%12-15g, %16-19g, %0-3g"},
178 {ARM_CEXT_XSCALE
, 0x0e000080, 0x0f000ff0, "wpack%20-23w%c\t%12-15g, %16-19g, %0-3g"},
179 {ARM_CEXT_XSCALE
, 0xfe300040, 0xff300ef0, "wror%22-23w\t%12-15g, %16-19g, #%i"},
180 {ARM_CEXT_XSCALE
, 0x0e300040, 0x0f300ff0, "wror%22-23w%c\t%12-15g, %16-19g, %0-3g"},
181 {ARM_CEXT_XSCALE
, 0x0e300140, 0x0f300ff0, "wror%22-23wg%c\t%12-15g, %16-19g, %0-3G"},
182 {ARM_CEXT_XSCALE
, 0x0e000120, 0x0fa00ff0, "wsad%22?hb%20'z%c\t%12-15g, %16-19g, %0-3g"},
183 {ARM_CEXT_XSCALE
, 0x0e0001e0, 0x0f000ff0, "wshufh%c\t%12-15g, %16-19g, #%Z"},
184 {ARM_CEXT_XSCALE
, 0xfe100040, 0xff300ef0, "wsll%22-23w\t%12-15g, %16-19g, #%i"},
185 {ARM_CEXT_XSCALE
, 0x0e100040, 0x0f300ff0, "wsll%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
186 {ARM_CEXT_XSCALE
, 0x0e100148, 0x0f300ffc, "wsll%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
187 {ARM_CEXT_XSCALE
, 0xfe000040, 0xff300ef0, "wsra%22-23w\t%12-15g, %16-19g, #%i"},
188 {ARM_CEXT_XSCALE
, 0x0e000040, 0x0f300ff0, "wsra%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
189 {ARM_CEXT_XSCALE
, 0x0e000148, 0x0f300ffc, "wsra%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
190 {ARM_CEXT_XSCALE
, 0xfe200040, 0xff300ef0, "wsrl%22-23w\t%12-15g, %16-19g, #%i"},
191 {ARM_CEXT_XSCALE
, 0x0e200040, 0x0f300ff0, "wsrl%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
192 {ARM_CEXT_XSCALE
, 0x0e200148, 0x0f300ffc, "wsrl%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
193 {ARM_CEXT_XSCALE
, 0xfc400100, 0xfe500f00, "wstrd\t%12-15g, %r"},
194 {ARM_CEXT_XSCALE
, 0xfc000100, 0xfe500f00, "wstrw\t%12-15G, %A"},
195 {ARM_CEXT_XSCALE
, 0x0c000000, 0x0e100e00, "wstr%L%c\t%12-15g, %l"},
196 {ARM_CEXT_XSCALE
, 0x0e0001a0, 0x0f000ff0, "wsub%20-23w%c\t%12-15g, %16-19g, %0-3g"},
197 {ARM_CEXT_XSCALE
, 0x0ed001c0, 0x0ff00ff0, "wsubaddhx%c\t%12-15g, %16-19g, %0-3g"},
198 {ARM_CEXT_XSCALE
, 0x0e1001c0, 0x0f300ff0, "wabsdiff%22-23w%c\t%12-15g, %16-19g, %0-3g"},
199 {ARM_CEXT_XSCALE
, 0x0e0000c0, 0x0fd00fff, "wunpckeh%21?sub%c\t%12-15g, %16-19g"},
200 {ARM_CEXT_XSCALE
, 0x0e4000c0, 0x0fd00fff, "wunpckeh%21?suh%c\t%12-15g, %16-19g"},
201 {ARM_CEXT_XSCALE
, 0x0e8000c0, 0x0fd00fff, "wunpckeh%21?suw%c\t%12-15g, %16-19g"},
202 {ARM_CEXT_XSCALE
, 0x0e0000e0, 0x0f100fff, "wunpckel%21?su%22-23w%c\t%12-15g, %16-19g"},
203 {ARM_CEXT_XSCALE
, 0x0e1000c0, 0x0f300ff0, "wunpckih%22-23w%c\t%12-15g, %16-19g, %0-3g"},
204 {ARM_CEXT_XSCALE
, 0x0e1000e0, 0x0f300ff0, "wunpckil%22-23w%c\t%12-15g, %16-19g, %0-3g"},
205 {ARM_CEXT_XSCALE
, 0x0e100000, 0x0ff00ff0, "wxor%c\t%12-15g, %16-19g, %0-3g"},
206 { 0, SENTINEL_IWMMXT_END
, 0, "" },
208 /* Floating point coprocessor (FPA) instructions. */
209 {FPU_FPA_EXT_V1
, 0x0e000100, 0x0ff08f10, "adf%c%P%R\t%12-14f, %16-18f, %0-3f"},
210 {FPU_FPA_EXT_V1
, 0x0e100100, 0x0ff08f10, "muf%c%P%R\t%12-14f, %16-18f, %0-3f"},
211 {FPU_FPA_EXT_V1
, 0x0e200100, 0x0ff08f10, "suf%c%P%R\t%12-14f, %16-18f, %0-3f"},
212 {FPU_FPA_EXT_V1
, 0x0e300100, 0x0ff08f10, "rsf%c%P%R\t%12-14f, %16-18f, %0-3f"},
213 {FPU_FPA_EXT_V1
, 0x0e400100, 0x0ff08f10, "dvf%c%P%R\t%12-14f, %16-18f, %0-3f"},
214 {FPU_FPA_EXT_V1
, 0x0e500100, 0x0ff08f10, "rdf%c%P%R\t%12-14f, %16-18f, %0-3f"},
215 {FPU_FPA_EXT_V1
, 0x0e600100, 0x0ff08f10, "pow%c%P%R\t%12-14f, %16-18f, %0-3f"},
216 {FPU_FPA_EXT_V1
, 0x0e700100, 0x0ff08f10, "rpw%c%P%R\t%12-14f, %16-18f, %0-3f"},
217 {FPU_FPA_EXT_V1
, 0x0e800100, 0x0ff08f10, "rmf%c%P%R\t%12-14f, %16-18f, %0-3f"},
218 {FPU_FPA_EXT_V1
, 0x0e900100, 0x0ff08f10, "fml%c%P%R\t%12-14f, %16-18f, %0-3f"},
219 {FPU_FPA_EXT_V1
, 0x0ea00100, 0x0ff08f10, "fdv%c%P%R\t%12-14f, %16-18f, %0-3f"},
220 {FPU_FPA_EXT_V1
, 0x0eb00100, 0x0ff08f10, "frd%c%P%R\t%12-14f, %16-18f, %0-3f"},
221 {FPU_FPA_EXT_V1
, 0x0ec00100, 0x0ff08f10, "pol%c%P%R\t%12-14f, %16-18f, %0-3f"},
222 {FPU_FPA_EXT_V1
, 0x0e008100, 0x0ff08f10, "mvf%c%P%R\t%12-14f, %0-3f"},
223 {FPU_FPA_EXT_V1
, 0x0e108100, 0x0ff08f10, "mnf%c%P%R\t%12-14f, %0-3f"},
224 {FPU_FPA_EXT_V1
, 0x0e208100, 0x0ff08f10, "abs%c%P%R\t%12-14f, %0-3f"},
225 {FPU_FPA_EXT_V1
, 0x0e308100, 0x0ff08f10, "rnd%c%P%R\t%12-14f, %0-3f"},
226 {FPU_FPA_EXT_V1
, 0x0e408100, 0x0ff08f10, "sqt%c%P%R\t%12-14f, %0-3f"},
227 {FPU_FPA_EXT_V1
, 0x0e508100, 0x0ff08f10, "log%c%P%R\t%12-14f, %0-3f"},
228 {FPU_FPA_EXT_V1
, 0x0e608100, 0x0ff08f10, "lgn%c%P%R\t%12-14f, %0-3f"},
229 {FPU_FPA_EXT_V1
, 0x0e708100, 0x0ff08f10, "exp%c%P%R\t%12-14f, %0-3f"},
230 {FPU_FPA_EXT_V1
, 0x0e808100, 0x0ff08f10, "sin%c%P%R\t%12-14f, %0-3f"},
231 {FPU_FPA_EXT_V1
, 0x0e908100, 0x0ff08f10, "cos%c%P%R\t%12-14f, %0-3f"},
232 {FPU_FPA_EXT_V1
, 0x0ea08100, 0x0ff08f10, "tan%c%P%R\t%12-14f, %0-3f"},
233 {FPU_FPA_EXT_V1
, 0x0eb08100, 0x0ff08f10, "asn%c%P%R\t%12-14f, %0-3f"},
234 {FPU_FPA_EXT_V1
, 0x0ec08100, 0x0ff08f10, "acs%c%P%R\t%12-14f, %0-3f"},
235 {FPU_FPA_EXT_V1
, 0x0ed08100, 0x0ff08f10, "atn%c%P%R\t%12-14f, %0-3f"},
236 {FPU_FPA_EXT_V1
, 0x0ee08100, 0x0ff08f10, "urd%c%P%R\t%12-14f, %0-3f"},
237 {FPU_FPA_EXT_V1
, 0x0ef08100, 0x0ff08f10, "nrm%c%P%R\t%12-14f, %0-3f"},
238 {FPU_FPA_EXT_V1
, 0x0e000110, 0x0ff00f1f, "flt%c%P%R\t%16-18f, %12-15r"},
239 {FPU_FPA_EXT_V1
, 0x0e100110, 0x0fff0f98, "fix%c%R\t%12-15r, %0-2f"},
240 {FPU_FPA_EXT_V1
, 0x0e200110, 0x0fff0fff, "wfs%c\t%12-15r"},
241 {FPU_FPA_EXT_V1
, 0x0e300110, 0x0fff0fff, "rfs%c\t%12-15r"},
242 {FPU_FPA_EXT_V1
, 0x0e400110, 0x0fff0fff, "wfc%c\t%12-15r"},
243 {FPU_FPA_EXT_V1
, 0x0e500110, 0x0fff0fff, "rfc%c\t%12-15r"},
244 {FPU_FPA_EXT_V1
, 0x0e90f110, 0x0ff8fff0, "cmf%c\t%16-18f, %0-3f"},
245 {FPU_FPA_EXT_V1
, 0x0eb0f110, 0x0ff8fff0, "cnf%c\t%16-18f, %0-3f"},
246 {FPU_FPA_EXT_V1
, 0x0ed0f110, 0x0ff8fff0, "cmfe%c\t%16-18f, %0-3f"},
247 {FPU_FPA_EXT_V1
, 0x0ef0f110, 0x0ff8fff0, "cnfe%c\t%16-18f, %0-3f"},
248 {FPU_FPA_EXT_V1
, 0x0c000100, 0x0e100f00, "stf%c%Q\t%12-14f, %A"},
249 {FPU_FPA_EXT_V1
, 0x0c100100, 0x0e100f00, "ldf%c%Q\t%12-14f, %A"},
250 {FPU_FPA_EXT_V2
, 0x0c000200, 0x0e100f00, "sfm%c\t%12-14f, %F, %A"},
251 {FPU_FPA_EXT_V2
, 0x0c100200, 0x0e100f00, "lfm%c\t%12-14f, %F, %A"},
253 /* Register load/store. */
254 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0d2d0b00, 0x0fbf0f01, "vpush%c\t%B"},
255 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0d200b00, 0x0fb00f01, "vstmdb%c\t%16-19r!, %B"},
256 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0d300b00, 0x0fb00f01, "vldmdb%c\t%16-19r!, %B"},
257 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0c800b00, 0x0f900f01, "vstmia%c\t%16-19r%21'!, %B"},
258 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0cbd0b00, 0x0fbf0f01, "vpop%c\t%B"},
259 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0c900b00, 0x0f900f01, "vldmia%c\t%16-19r%21'!, %B"},
260 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0d000b00, 0x0f300f00, "vstr%c\t%12-15,22D, %A"},
261 {FPU_VFP_EXT_V1xD
| FPU_NEON_EXT_V1
, 0x0d100b00, 0x0f300f00, "vldr%c\t%12-15,22D, %A"},
262 {FPU_VFP_EXT_V1xD
, 0x0d2d0a00, 0x0fbf0f00, "vpush%c\t%y3"},
263 {FPU_VFP_EXT_V1xD
, 0x0d200a00, 0x0fb00f00, "vstmdb%c\t%16-19r!, %y3"},
264 {FPU_VFP_EXT_V1xD
, 0x0d300a00, 0x0fb00f00, "vldmdb%c\t%16-19r!, %y3"},
265 {FPU_VFP_EXT_V1xD
, 0x0c800a00, 0x0f900f00, "vstmia%c\t%16-19r%21'!, %y3"},
266 {FPU_VFP_EXT_V1xD
, 0x0cbd0a00, 0x0fbf0f00, "vpop%c\t%y3"},
267 {FPU_VFP_EXT_V1xD
, 0x0c900a00, 0x0f900f00, "vldmia%c\t%16-19r%21'!, %y3"},
268 {FPU_VFP_EXT_V1xD
, 0x0d000a00, 0x0f300f00, "vstr%c\t%y1, %A"},
269 {FPU_VFP_EXT_V1xD
, 0x0d100a00, 0x0f300f00, "vldr%c\t%y1, %A"},
271 {FPU_VFP_EXT_V1xD
, 0x0d200b01, 0x0fb00f01, "fstmdbx%c\t%16-19r!, %z3\t;@ Deprecated"},
272 {FPU_VFP_EXT_V1xD
, 0x0d300b01, 0x0fb00f01, "fldmdbx%c\t%16-19r!, %z3\t;@ Deprecated"},
273 {FPU_VFP_EXT_V1xD
, 0x0c800b01, 0x0f900f01, "fstmiax%c\t%16-19r%21'!, %z3\t;@ Deprecated"},
274 {FPU_VFP_EXT_V1xD
, 0x0c900b01, 0x0f900f01, "fldmiax%c\t%16-19r%21'!, %z3\t;@ Deprecated"},
276 /* Data transfer between ARM and NEON registers. */
277 {FPU_NEON_EXT_V1
, 0x0e800b10, 0x0ff00f70, "vdup%c.32\t%16-19,7D, %12-15r"},
278 {FPU_NEON_EXT_V1
, 0x0e800b30, 0x0ff00f70, "vdup%c.16\t%16-19,7D, %12-15r"},
279 {FPU_NEON_EXT_V1
, 0x0ea00b10, 0x0ff00f70, "vdup%c.32\t%16-19,7Q, %12-15r"},
280 {FPU_NEON_EXT_V1
, 0x0ea00b30, 0x0ff00f70, "vdup%c.16\t%16-19,7Q, %12-15r"},
281 {FPU_NEON_EXT_V1
, 0x0ec00b10, 0x0ff00f70, "vdup%c.8\t%16-19,7D, %12-15r"},
282 {FPU_NEON_EXT_V1
, 0x0ee00b10, 0x0ff00f70, "vdup%c.8\t%16-19,7Q, %12-15r"},
283 {FPU_NEON_EXT_V1
, 0x0c400b10, 0x0ff00fd0, "vmov%c\t%0-3,5D, %12-15r, %16-19r"},
284 {FPU_NEON_EXT_V1
, 0x0c500b10, 0x0ff00fd0, "vmov%c\t%12-15r, %16-19r, %0-3,5D"},
285 {FPU_NEON_EXT_V1
, 0x0e000b10, 0x0fd00f70, "vmov%c.32\t%16-19,7D[%21d], %12-15r"},
286 {FPU_NEON_EXT_V1
, 0x0e100b10, 0x0f500f70, "vmov%c.32\t%12-15r, %16-19,7D[%21d]"},
287 {FPU_NEON_EXT_V1
, 0x0e000b30, 0x0fd00f30, "vmov%c.16\t%16-19,7D[%6,21d], %12-15r"},
288 {FPU_NEON_EXT_V1
, 0x0e100b30, 0x0f500f30, "vmov%c.%23?us16\t%12-15r, %16-19,7D[%6,21d]"},
289 {FPU_NEON_EXT_V1
, 0x0e400b10, 0x0fd00f10, "vmov%c.8\t%16-19,7D[%5,6,21d], %12-15r"},
290 {FPU_NEON_EXT_V1
, 0x0e500b10, 0x0f500f10, "vmov%c.%23?us8\t%12-15r, %16-19,7D[%5,6,21d]"},
291 /* Half-precision conversion instructions. */
292 {FPU_VFP_EXT_FP16
, 0x0eb20a40, 0x0fbf0f50, "vcvt%7?tb%c.f32.f16\t%y1, %y0"},
293 {FPU_VFP_EXT_FP16
, 0x0eb30a40, 0x0fbf0f50, "vcvt%7?tb%c.f16.f32\t%y1, %y0"},
295 /* Floating point coprocessor (VFP) instructions. */
296 {FPU_VFP_EXT_V1xD
, 0x0ee00a10, 0x0fff0fff, "vmsr%c\tfpsid, %12-15r"},
297 {FPU_VFP_EXT_V1xD
, 0x0ee10a10, 0x0fff0fff, "vmsr%c\tfpscr, %12-15r"},
298 {FPU_VFP_EXT_V1xD
, 0x0ee60a10, 0x0fff0fff, "vmsr%c\tmvfr1, %12-15r"},
299 {FPU_VFP_EXT_V1xD
, 0x0ee70a10, 0x0fff0fff, "vmsr%c\tmvfr0, %12-15r"},
300 {FPU_VFP_EXT_V1xD
, 0x0ee80a10, 0x0fff0fff, "vmsr%c\tfpexc, %12-15r"},
301 {FPU_VFP_EXT_V1xD
, 0x0ee90a10, 0x0fff0fff, "vmsr%c\tfpinst, %12-15r\t@ Impl def"},
302 {FPU_VFP_EXT_V1xD
, 0x0eea0a10, 0x0fff0fff, "vmsr%c\tfpinst2, %12-15r\t@ Impl def"},
303 {FPU_VFP_EXT_V1xD
, 0x0ef00a10, 0x0fff0fff, "vmrs%c\t%12-15r, fpsid"},
304 {FPU_VFP_EXT_V1xD
, 0x0ef1fa10, 0x0fffffff, "vmrs%c\tAPSR_nzcv, fpscr"},
305 {FPU_VFP_EXT_V1xD
, 0x0ef10a10, 0x0fff0fff, "vmrs%c\t%12-15r, fpscr"},
306 {FPU_VFP_EXT_V1xD
, 0x0ef60a10, 0x0fff0fff, "vmrs%c\t%12-15r, mvfr1"},
307 {FPU_VFP_EXT_V1xD
, 0x0ef70a10, 0x0fff0fff, "vmrs%c\t%12-15r, mvfr0"},
308 {FPU_VFP_EXT_V1xD
, 0x0ef80a10, 0x0fff0fff, "vmrs%c\t%12-15r, fpexc"},
309 {FPU_VFP_EXT_V1xD
, 0x0ef90a10, 0x0fff0fff, "vmrs%c\t%12-15r, fpinst\t@ Impl def"},
310 {FPU_VFP_EXT_V1xD
, 0x0efa0a10, 0x0fff0fff, "vmrs%c\t%12-15r, fpinst2\t@ Impl def"},
311 {FPU_VFP_EXT_V1
, 0x0e000b10, 0x0fd00fff, "vmov%c.32\t%z2[%21d], %12-15r"},
312 {FPU_VFP_EXT_V1
, 0x0e100b10, 0x0fd00fff, "vmov%c.32\t%12-15r, %z2[%21d]"},
313 {FPU_VFP_EXT_V1xD
, 0x0ee00a10, 0x0ff00fff, "vmsr%c\t<impl def %16-19x>, %12-15r"},
314 {FPU_VFP_EXT_V1xD
, 0x0ef00a10, 0x0ff00fff, "vmrs%c\t%12-15r, <impl def %16-19x>"},
315 {FPU_VFP_EXT_V1xD
, 0x0e000a10, 0x0ff00f7f, "vmov%c\t%y2, %12-15r"},
316 {FPU_VFP_EXT_V1xD
, 0x0e100a10, 0x0ff00f7f, "vmov%c\t%12-15r, %y2"},
317 {FPU_VFP_EXT_V1xD
, 0x0eb50a40, 0x0fbf0f70, "vcmp%7'e%c.f32\t%y1, #0.0"},
318 {FPU_VFP_EXT_V1
, 0x0eb50b40, 0x0fbf0f70, "vcmp%7'e%c.f64\t%z1, #0.0"},
319 {FPU_VFP_EXT_V1xD
, 0x0eb00a40, 0x0fbf0fd0, "vmov%c.f32\t%y1, %y0"},
320 {FPU_VFP_EXT_V1xD
, 0x0eb00ac0, 0x0fbf0fd0, "vabs%c.f32\t%y1, %y0"},
321 {FPU_VFP_EXT_V1
, 0x0eb00b40, 0x0fbf0fd0, "vmov%c.f64\t%z1, %z0"},
322 {FPU_VFP_EXT_V1
, 0x0eb00bc0, 0x0fbf0fd0, "vabs%c.f64\t%z1, %z0"},
323 {FPU_VFP_EXT_V1xD
, 0x0eb10a40, 0x0fbf0fd0, "vneg%c.f32\t%y1, %y0"},
324 {FPU_VFP_EXT_V1xD
, 0x0eb10ac0, 0x0fbf0fd0, "vsqrt%c.f32\t%y1, %y0"},
325 {FPU_VFP_EXT_V1
, 0x0eb10b40, 0x0fbf0fd0, "vneg%c.f64\t%z1, %z0"},
326 {FPU_VFP_EXT_V1
, 0x0eb10bc0, 0x0fbf0fd0, "vsqrt%c.f64\t%z1, %z0"},
327 {FPU_VFP_EXT_V1
, 0x0eb70ac0, 0x0fbf0fd0, "vcvt%c.f64.f32\t%z1, %y0"},
328 {FPU_VFP_EXT_V1
, 0x0eb70bc0, 0x0fbf0fd0, "vcvt%c.f32.f64\t%y1, %z0"},
329 {FPU_VFP_EXT_V1xD
, 0x0eb80a40, 0x0fbf0f50, "vcvt%c.f32.%7?su32\t%y1, %y0"},
330 {FPU_VFP_EXT_V1
, 0x0eb80b40, 0x0fbf0f50, "vcvt%c.f64.%7?su32\t%z1, %y0"},
331 {FPU_VFP_EXT_V1xD
, 0x0eb40a40, 0x0fbf0f50, "vcmp%7'e%c.f32\t%y1, %y0"},
332 {FPU_VFP_EXT_V1
, 0x0eb40b40, 0x0fbf0f50, "vcmp%7'e%c.f64\t%z1, %z0"},
333 {FPU_VFP_EXT_V3xD
, 0x0eba0a40, 0x0fbe0f50, "vcvt%c.f32.%16?us%7?31%7?26\t%y1, %y1, #%5,0-3k"},
334 {FPU_VFP_EXT_V3
, 0x0eba0b40, 0x0fbe0f50, "vcvt%c.f64.%16?us%7?31%7?26\t%z1, %z1, #%5,0-3k"},
335 {FPU_VFP_EXT_V1xD
, 0x0ebc0a40, 0x0fbe0f50, "vcvt%7`r%c.%16?su32.f32\t%y1, %y0"},
336 {FPU_VFP_EXT_V1
, 0x0ebc0b40, 0x0fbe0f50, "vcvt%7`r%c.%16?su32.f64\t%y1, %z0"},
337 {FPU_VFP_EXT_V3xD
, 0x0ebe0a40, 0x0fbe0f50, "vcvt%c.%16?us%7?31%7?26.f32\t%y1, %y1, #%5,0-3k"},
338 {FPU_VFP_EXT_V3
, 0x0ebe0b40, 0x0fbe0f50, "vcvt%c.%16?us%7?31%7?26.f64\t%z1, %z1, #%5,0-3k"},
339 {FPU_VFP_EXT_V1
, 0x0c500b10, 0x0fb00ff0, "vmov%c\t%12-15r, %16-19r, %z0"},
340 {FPU_VFP_EXT_V3xD
, 0x0eb00a00, 0x0fb00ff0, "vmov%c.f32\t%y1, #%0-3,16-19d"},
341 {FPU_VFP_EXT_V3
, 0x0eb00b00, 0x0fb00ff0, "vmov%c.f64\t%z1, #%0-3,16-19d"},
342 {FPU_VFP_EXT_V2
, 0x0c400a10, 0x0ff00fd0, "vmov%c\t%y4, %12-15r, %16-19r"},
343 {FPU_VFP_EXT_V2
, 0x0c400b10, 0x0ff00fd0, "vmov%c\t%z0, %12-15r, %16-19r"},
344 {FPU_VFP_EXT_V2
, 0x0c500a10, 0x0ff00fd0, "vmov%c\t%12-15r, %16-19r, %y4"},
345 {FPU_VFP_EXT_V1xD
, 0x0e000a00, 0x0fb00f50, "vmla%c.f32\t%y1, %y2, %y0"},
346 {FPU_VFP_EXT_V1xD
, 0x0e000a40, 0x0fb00f50, "vmls%c.f32\t%y1, %y2, %y0"},
347 {FPU_VFP_EXT_V1
, 0x0e000b00, 0x0fb00f50, "vmla%c.f64\t%z1, %z2, %z0"},
348 {FPU_VFP_EXT_V1
, 0x0e000b40, 0x0fb00f50, "vmls%c.f64\t%z1, %z2, %z0"},
349 {FPU_VFP_EXT_V1xD
, 0x0e100a00, 0x0fb00f50, "vnmls%c.f32\t%y1, %y2, %y0"},
350 {FPU_VFP_EXT_V1xD
, 0x0e100a40, 0x0fb00f50, "vnmla%c.f32\t%y1, %y2, %y0"},
351 {FPU_VFP_EXT_V1
, 0x0e100b00, 0x0fb00f50, "vnmls%c.f64\t%z1, %z2, %z0"},
352 {FPU_VFP_EXT_V1
, 0x0e100b40, 0x0fb00f50, "vnmla%c.f64\t%z1, %z2, %z0"},
353 {FPU_VFP_EXT_V1xD
, 0x0e200a00, 0x0fb00f50, "vmul%c.f32\t%y1, %y2, %y0"},
354 {FPU_VFP_EXT_V1xD
, 0x0e200a40, 0x0fb00f50, "vnmul%c.f32\t%y1, %y2, %y0"},
355 {FPU_VFP_EXT_V1
, 0x0e200b00, 0x0fb00f50, "vmul%c.f64\t%z1, %z2, %z0"},
356 {FPU_VFP_EXT_V1
, 0x0e200b40, 0x0fb00f50, "vnmul%c.f64\t%z1, %z2, %z0"},
357 {FPU_VFP_EXT_V1xD
, 0x0e300a00, 0x0fb00f50, "vadd%c.f32\t%y1, %y2, %y0"},
358 {FPU_VFP_EXT_V1xD
, 0x0e300a40, 0x0fb00f50, "vsub%c.f32\t%y1, %y2, %y0"},
359 {FPU_VFP_EXT_V1
, 0x0e300b00, 0x0fb00f50, "vadd%c.f64\t%z1, %z2, %z0"},
360 {FPU_VFP_EXT_V1
, 0x0e300b40, 0x0fb00f50, "vsub%c.f64\t%z1, %z2, %z0"},
361 {FPU_VFP_EXT_V1xD
, 0x0e800a00, 0x0fb00f50, "vdiv%c.f32\t%y1, %y2, %y0"},
362 {FPU_VFP_EXT_V1
, 0x0e800b00, 0x0fb00f50, "vdiv%c.f64\t%z1, %z2, %z0"},
364 /* Cirrus coprocessor instructions. */
365 {ARM_CEXT_MAVERICK
, 0x0d100400, 0x0f500f00, "cfldrs%c\tmvf%12-15d, %A"},
366 {ARM_CEXT_MAVERICK
, 0x0c100400, 0x0f500f00, "cfldrs%c\tmvf%12-15d, %A"},
367 {ARM_CEXT_MAVERICK
, 0x0d500400, 0x0f500f00, "cfldrd%c\tmvd%12-15d, %A"},
368 {ARM_CEXT_MAVERICK
, 0x0c500400, 0x0f500f00, "cfldrd%c\tmvd%12-15d, %A"},
369 {ARM_CEXT_MAVERICK
, 0x0d100500, 0x0f500f00, "cfldr32%c\tmvfx%12-15d, %A"},
370 {ARM_CEXT_MAVERICK
, 0x0c100500, 0x0f500f00, "cfldr32%c\tmvfx%12-15d, %A"},
371 {ARM_CEXT_MAVERICK
, 0x0d500500, 0x0f500f00, "cfldr64%c\tmvdx%12-15d, %A"},
372 {ARM_CEXT_MAVERICK
, 0x0c500500, 0x0f500f00, "cfldr64%c\tmvdx%12-15d, %A"},
373 {ARM_CEXT_MAVERICK
, 0x0d000400, 0x0f500f00, "cfstrs%c\tmvf%12-15d, %A"},
374 {ARM_CEXT_MAVERICK
, 0x0c000400, 0x0f500f00, "cfstrs%c\tmvf%12-15d, %A"},
375 {ARM_CEXT_MAVERICK
, 0x0d400400, 0x0f500f00, "cfstrd%c\tmvd%12-15d, %A"},
376 {ARM_CEXT_MAVERICK
, 0x0c400400, 0x0f500f00, "cfstrd%c\tmvd%12-15d, %A"},
377 {ARM_CEXT_MAVERICK
, 0x0d000500, 0x0f500f00, "cfstr32%c\tmvfx%12-15d, %A"},
378 {ARM_CEXT_MAVERICK
, 0x0c000500, 0x0f500f00, "cfstr32%c\tmvfx%12-15d, %A"},
379 {ARM_CEXT_MAVERICK
, 0x0d400500, 0x0f500f00, "cfstr64%c\tmvdx%12-15d, %A"},
380 {ARM_CEXT_MAVERICK
, 0x0c400500, 0x0f500f00, "cfstr64%c\tmvdx%12-15d, %A"},
381 {ARM_CEXT_MAVERICK
, 0x0e000450, 0x0ff00ff0, "cfmvsr%c\tmvf%16-19d, %12-15r"},
382 {ARM_CEXT_MAVERICK
, 0x0e100450, 0x0ff00ff0, "cfmvrs%c\t%12-15r, mvf%16-19d"},
383 {ARM_CEXT_MAVERICK
, 0x0e000410, 0x0ff00ff0, "cfmvdlr%c\tmvd%16-19d, %12-15r"},
384 {ARM_CEXT_MAVERICK
, 0x0e100410, 0x0ff00ff0, "cfmvrdl%c\t%12-15r, mvd%16-19d"},
385 {ARM_CEXT_MAVERICK
, 0x0e000430, 0x0ff00ff0, "cfmvdhr%c\tmvd%16-19d, %12-15r"},
386 {ARM_CEXT_MAVERICK
, 0x0e100430, 0x0ff00fff, "cfmvrdh%c\t%12-15r, mvd%16-19d"},
387 {ARM_CEXT_MAVERICK
, 0x0e000510, 0x0ff00fff, "cfmv64lr%c\tmvdx%16-19d, %12-15r"},
388 {ARM_CEXT_MAVERICK
, 0x0e100510, 0x0ff00fff, "cfmvr64l%c\t%12-15r, mvdx%16-19d"},
389 {ARM_CEXT_MAVERICK
, 0x0e000530, 0x0ff00fff, "cfmv64hr%c\tmvdx%16-19d, %12-15r"},
390 {ARM_CEXT_MAVERICK
, 0x0e100530, 0x0ff00fff, "cfmvr64h%c\t%12-15r, mvdx%16-19d"},
391 {ARM_CEXT_MAVERICK
, 0x0e200440, 0x0ff00fff, "cfmval32%c\tmvax%12-15d, mvfx%16-19d"},
392 {ARM_CEXT_MAVERICK
, 0x0e100440, 0x0ff00fff, "cfmv32al%c\tmvfx%12-15d, mvax%16-19d"},
393 {ARM_CEXT_MAVERICK
, 0x0e200460, 0x0ff00fff, "cfmvam32%c\tmvax%12-15d, mvfx%16-19d"},
394 {ARM_CEXT_MAVERICK
, 0x0e100460, 0x0ff00fff, "cfmv32am%c\tmvfx%12-15d, mvax%16-19d"},
395 {ARM_CEXT_MAVERICK
, 0x0e200480, 0x0ff00fff, "cfmvah32%c\tmvax%12-15d, mvfx%16-19d"},
396 {ARM_CEXT_MAVERICK
, 0x0e100480, 0x0ff00fff, "cfmv32ah%c\tmvfx%12-15d, mvax%16-19d"},
397 {ARM_CEXT_MAVERICK
, 0x0e2004a0, 0x0ff00fff, "cfmva32%c\tmvax%12-15d, mvfx%16-19d"},
398 {ARM_CEXT_MAVERICK
, 0x0e1004a0, 0x0ff00fff, "cfmv32a%c\tmvfx%12-15d, mvax%16-19d"},
399 {ARM_CEXT_MAVERICK
, 0x0e2004c0, 0x0ff00fff, "cfmva64%c\tmvax%12-15d, mvdx%16-19d"},
400 {ARM_CEXT_MAVERICK
, 0x0e1004c0, 0x0ff00fff, "cfmv64a%c\tmvdx%12-15d, mvax%16-19d"},
401 {ARM_CEXT_MAVERICK
, 0x0e2004e0, 0x0fff0fff, "cfmvsc32%c\tdspsc, mvdx%12-15d"},
402 {ARM_CEXT_MAVERICK
, 0x0e1004e0, 0x0fff0fff, "cfmv32sc%c\tmvdx%12-15d, dspsc"},
403 {ARM_CEXT_MAVERICK
, 0x0e000400, 0x0ff00fff, "cfcpys%c\tmvf%12-15d, mvf%16-19d"},
404 {ARM_CEXT_MAVERICK
, 0x0e000420, 0x0ff00fff, "cfcpyd%c\tmvd%12-15d, mvd%16-19d"},
405 {ARM_CEXT_MAVERICK
, 0x0e000460, 0x0ff00fff, "cfcvtsd%c\tmvd%12-15d, mvf%16-19d"},
406 {ARM_CEXT_MAVERICK
, 0x0e000440, 0x0ff00fff, "cfcvtds%c\tmvf%12-15d, mvd%16-19d"},
407 {ARM_CEXT_MAVERICK
, 0x0e000480, 0x0ff00fff, "cfcvt32s%c\tmvf%12-15d, mvfx%16-19d"},
408 {ARM_CEXT_MAVERICK
, 0x0e0004a0, 0x0ff00fff, "cfcvt32d%c\tmvd%12-15d, mvfx%16-19d"},
409 {ARM_CEXT_MAVERICK
, 0x0e0004c0, 0x0ff00fff, "cfcvt64s%c\tmvf%12-15d, mvdx%16-19d"},
410 {ARM_CEXT_MAVERICK
, 0x0e0004e0, 0x0ff00fff, "cfcvt64d%c\tmvd%12-15d, mvdx%16-19d"},
411 {ARM_CEXT_MAVERICK
, 0x0e100580, 0x0ff00fff, "cfcvts32%c\tmvfx%12-15d, mvf%16-19d"},
412 {ARM_CEXT_MAVERICK
, 0x0e1005a0, 0x0ff00fff, "cfcvtd32%c\tmvfx%12-15d, mvd%16-19d"},
413 {ARM_CEXT_MAVERICK
, 0x0e1005c0, 0x0ff00fff, "cftruncs32%c\tmvfx%12-15d, mvf%16-19d"},
414 {ARM_CEXT_MAVERICK
, 0x0e1005e0, 0x0ff00fff, "cftruncd32%c\tmvfx%12-15d, mvd%16-19d"},
415 {ARM_CEXT_MAVERICK
, 0x0e000550, 0x0ff00ff0, "cfrshl32%c\tmvfx%16-19d, mvfx%0-3d, %12-15r"},
416 {ARM_CEXT_MAVERICK
, 0x0e000570, 0x0ff00ff0, "cfrshl64%c\tmvdx%16-19d, mvdx%0-3d, %12-15r"},
417 {ARM_CEXT_MAVERICK
, 0x0e000500, 0x0ff00f10, "cfsh32%c\tmvfx%12-15d, mvfx%16-19d, #%I"},
418 {ARM_CEXT_MAVERICK
, 0x0e200500, 0x0ff00f10, "cfsh64%c\tmvdx%12-15d, mvdx%16-19d, #%I"},
419 {ARM_CEXT_MAVERICK
, 0x0e100490, 0x0ff00ff0, "cfcmps%c\t%12-15r, mvf%16-19d, mvf%0-3d"},
420 {ARM_CEXT_MAVERICK
, 0x0e1004b0, 0x0ff00ff0, "cfcmpd%c\t%12-15r, mvd%16-19d, mvd%0-3d"},
421 {ARM_CEXT_MAVERICK
, 0x0e100590, 0x0ff00ff0, "cfcmp32%c\t%12-15r, mvfx%16-19d, mvfx%0-3d"},
422 {ARM_CEXT_MAVERICK
, 0x0e1005b0, 0x0ff00ff0, "cfcmp64%c\t%12-15r, mvdx%16-19d, mvdx%0-3d"},
423 {ARM_CEXT_MAVERICK
, 0x0e300400, 0x0ff00fff, "cfabss%c\tmvf%12-15d, mvf%16-19d"},
424 {ARM_CEXT_MAVERICK
, 0x0e300420, 0x0ff00fff, "cfabsd%c\tmvd%12-15d, mvd%16-19d"},
425 {ARM_CEXT_MAVERICK
, 0x0e300440, 0x0ff00fff, "cfnegs%c\tmvf%12-15d, mvf%16-19d"},
426 {ARM_CEXT_MAVERICK
, 0x0e300460, 0x0ff00fff, "cfnegd%c\tmvd%12-15d, mvd%16-19d"},
427 {ARM_CEXT_MAVERICK
, 0x0e300480, 0x0ff00ff0, "cfadds%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
428 {ARM_CEXT_MAVERICK
, 0x0e3004a0, 0x0ff00ff0, "cfaddd%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
429 {ARM_CEXT_MAVERICK
, 0x0e3004c0, 0x0ff00ff0, "cfsubs%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
430 {ARM_CEXT_MAVERICK
, 0x0e3004e0, 0x0ff00ff0, "cfsubd%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
431 {ARM_CEXT_MAVERICK
, 0x0e100400, 0x0ff00ff0, "cfmuls%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
432 {ARM_CEXT_MAVERICK
, 0x0e100420, 0x0ff00ff0, "cfmuld%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
433 {ARM_CEXT_MAVERICK
, 0x0e300500, 0x0ff00fff, "cfabs32%c\tmvfx%12-15d, mvfx%16-19d"},
434 {ARM_CEXT_MAVERICK
, 0x0e300520, 0x0ff00fff, "cfabs64%c\tmvdx%12-15d, mvdx%16-19d"},
435 {ARM_CEXT_MAVERICK
, 0x0e300540, 0x0ff00fff, "cfneg32%c\tmvfx%12-15d, mvfx%16-19d"},
436 {ARM_CEXT_MAVERICK
, 0x0e300560, 0x0ff00fff, "cfneg64%c\tmvdx%12-15d, mvdx%16-19d"},
437 {ARM_CEXT_MAVERICK
, 0x0e300580, 0x0ff00ff0, "cfadd32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
438 {ARM_CEXT_MAVERICK
, 0x0e3005a0, 0x0ff00ff0, "cfadd64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
439 {ARM_CEXT_MAVERICK
, 0x0e3005c0, 0x0ff00ff0, "cfsub32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
440 {ARM_CEXT_MAVERICK
, 0x0e3005e0, 0x0ff00ff0, "cfsub64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
441 {ARM_CEXT_MAVERICK
, 0x0e100500, 0x0ff00ff0, "cfmul32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
442 {ARM_CEXT_MAVERICK
, 0x0e100520, 0x0ff00ff0, "cfmul64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
443 {ARM_CEXT_MAVERICK
, 0x0e100540, 0x0ff00ff0, "cfmac32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
444 {ARM_CEXT_MAVERICK
, 0x0e100560, 0x0ff00ff0, "cfmsc32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
445 {ARM_CEXT_MAVERICK
, 0x0e000600, 0x0ff00f10, "cfmadd32%c\tmvax%5-7d, mvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
446 {ARM_CEXT_MAVERICK
, 0x0e100600, 0x0ff00f10, "cfmsub32%c\tmvax%5-7d, mvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
447 {ARM_CEXT_MAVERICK
, 0x0e200600, 0x0ff00f10, "cfmadda32%c\tmvax%5-7d, mvax%12-15d, mvfx%16-19d, mvfx%0-3d"},
448 {ARM_CEXT_MAVERICK
, 0x0e300600, 0x0ff00f10, "cfmsuba32%c\tmvax%5-7d, mvax%12-15d, mvfx%16-19d, mvfx%0-3d"},
450 /* VFP Fused multiply add instructions. */
451 {FPU_VFP_EXT_FMA
, 0x0ea00a00, 0x0fb00f50, "vfma%c.f32\t%y1, %y2, %y0"},
452 {FPU_VFP_EXT_FMA
, 0x0ea00b00, 0x0fb00f50, "vfma%c.f64\t%z1, %z2, %z0"},
453 {FPU_VFP_EXT_FMA
, 0x0ea00a40, 0x0fb00f50, "vfms%c.f32\t%y1, %y2, %y0"},
454 {FPU_VFP_EXT_FMA
, 0x0ea00b40, 0x0fb00f50, "vfms%c.f64\t%z1, %z2, %z0"},
455 {FPU_VFP_EXT_FMA
, 0x0e900a40, 0x0fb00f50, "vfnma%c.f32\t%y1, %y2, %y0"},
456 {FPU_VFP_EXT_FMA
, 0x0e900b40, 0x0fb00f50, "vfnma%c.f64\t%z1, %z2, %z0"},
457 {FPU_VFP_EXT_FMA
, 0x0e900a00, 0x0fb00f50, "vfnms%c.f32\t%y1, %y2, %y0"},
458 {FPU_VFP_EXT_FMA
, 0x0e900b00, 0x0fb00f50, "vfnms%c.f64\t%z1, %z2, %z0"},
460 /* Generic coprocessor instructions. */
461 { 0, SENTINEL_GENERIC_START
, 0, "" },
462 {ARM_EXT_V5E
, 0x0c400000, 0x0ff00000, "mcrr%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
463 {ARM_EXT_V5E
, 0x0c500000, 0x0ff00000, "mrrc%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
464 {ARM_EXT_V2
, 0x0e000000, 0x0f000010, "cdp%c\t%8-11d, %20-23d, cr%12-15d, cr%16-19d, cr%0-3d, {%5-7d}"},
465 {ARM_EXT_V2
, 0x0e100010, 0x0f100010, "mrc%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
466 {ARM_EXT_V2
, 0x0e000010, 0x0f100010, "mcr%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
467 {ARM_EXT_V2
, 0x0c000000, 0x0e100000, "stc%22'l%c\t%8-11d, cr%12-15d, %A"},
468 {ARM_EXT_V2
, 0x0c100000, 0x0e100000, "ldc%22'l%c\t%8-11d, cr%12-15d, %A"},
470 /* V6 coprocessor instructions. */
471 {ARM_EXT_V6
, 0xfc500000, 0xfff00000, "mrrc2%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
472 {ARM_EXT_V6
, 0xfc400000, 0xfff00000, "mcrr2%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
474 /* V5 coprocessor instructions. */
475 {ARM_EXT_V5
, 0xfc100000, 0xfe100000, "ldc2%22'l%c\t%8-11d, cr%12-15d, %A"},
476 {ARM_EXT_V5
, 0xfc000000, 0xfe100000, "stc2%22'l%c\t%8-11d, cr%12-15d, %A"},
477 {ARM_EXT_V5
, 0xfe000000, 0xff000010, "cdp2%c\t%8-11d, %20-23d, cr%12-15d, cr%16-19d, cr%0-3d, {%5-7d}"},
478 {ARM_EXT_V5
, 0xfe000010, 0xff100010, "mcr2%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
479 {ARM_EXT_V5
, 0xfe100010, 0xff100010, "mrc2%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
484 /* Neon opcode table: This does not encode the top byte -- that is
485 checked by the print_insn_neon routine, as it depends on whether we are
486 doing thumb32 or arm32 disassembly. */
488 /* print_insn_neon recognizes the following format control codes:
492 %c print condition code
493 %A print v{st,ld}[1234] operands
494 %B print v{st,ld}[1234] any one operands
495 %C print v{st,ld}[1234] single->all operands
497 %E print vmov, vmvn, vorr, vbic encoded constant
498 %F print vtbl,vtbx register list
500 %<bitfield>r print as an ARM register
501 %<bitfield>d print the bitfield in decimal
502 %<bitfield>e print the 2^N - bitfield in decimal
503 %<bitfield>D print as a NEON D register
504 %<bitfield>Q print as a NEON Q register
505 %<bitfield>R print as a NEON D or Q register
506 %<bitfield>Sn print byte scaled width limited by n
507 %<bitfield>Tn print short scaled width limited by n
508 %<bitfield>Un print long scaled width limited by n
510 %<bitfield>'c print specified char iff bitfield is all ones
511 %<bitfield>`c print specified char iff bitfield is all zeroes
512 %<bitfield>?ab... select from array of values in big endian order. */
514 static const struct opcode32 neon_opcodes
[] =
517 {FPU_NEON_EXT_V1
, 0xf2b00840, 0xffb00850, "vext%c.8\t%12-15,22R, %16-19,7R, %0-3,5R, #%8-11d"},
518 {FPU_NEON_EXT_V1
, 0xf2b00000, 0xffb00810, "vext%c.8\t%12-15,22R, %16-19,7R, %0-3,5R, #%8-11d"},
520 /* Move data element to all lanes. */
521 {FPU_NEON_EXT_V1
, 0xf3b40c00, 0xffb70f90, "vdup%c.32\t%12-15,22R, %0-3,5D[%19d]"},
522 {FPU_NEON_EXT_V1
, 0xf3b20c00, 0xffb30f90, "vdup%c.16\t%12-15,22R, %0-3,5D[%18-19d]"},
523 {FPU_NEON_EXT_V1
, 0xf3b10c00, 0xffb10f90, "vdup%c.8\t%12-15,22R, %0-3,5D[%17-19d]"},
526 {FPU_NEON_EXT_V1
, 0xf3b00800, 0xffb00c50, "vtbl%c.8\t%12-15,22D, %F, %0-3,5D"},
527 {FPU_NEON_EXT_V1
, 0xf3b00840, 0xffb00c50, "vtbx%c.8\t%12-15,22D, %F, %0-3,5D"},
529 /* Half-precision conversions. */
530 {FPU_VFP_EXT_FP16
, 0xf3b60600, 0xffbf0fd0, "vcvt%c.f16.f32\t%12-15,22D, %0-3,5Q"},
531 {FPU_VFP_EXT_FP16
, 0xf3b60700, 0xffbf0fd0, "vcvt%c.f32.f16\t%12-15,22Q, %0-3,5D"},
533 /* NEON fused multiply add instructions. */
534 {FPU_NEON_EXT_FMA
, 0xf2000c10, 0xffa00f10, "vfma%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
535 {FPU_NEON_EXT_FMA
, 0xf2200c10, 0xffa00f10, "vfms%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
537 /* Two registers, miscellaneous. */
538 {FPU_NEON_EXT_V1
, 0xf2880a10, 0xfebf0fd0, "vmovl%c.%24?us8\t%12-15,22Q, %0-3,5D"},
539 {FPU_NEON_EXT_V1
, 0xf2900a10, 0xfebf0fd0, "vmovl%c.%24?us16\t%12-15,22Q, %0-3,5D"},
540 {FPU_NEON_EXT_V1
, 0xf2a00a10, 0xfebf0fd0, "vmovl%c.%24?us32\t%12-15,22Q, %0-3,5D"},
541 {FPU_NEON_EXT_V1
, 0xf3b00500, 0xffbf0f90, "vcnt%c.8\t%12-15,22R, %0-3,5R"},
542 {FPU_NEON_EXT_V1
, 0xf3b00580, 0xffbf0f90, "vmvn%c\t%12-15,22R, %0-3,5R"},
543 {FPU_NEON_EXT_V1
, 0xf3b20000, 0xffbf0f90, "vswp%c\t%12-15,22R, %0-3,5R"},
544 {FPU_NEON_EXT_V1
, 0xf3b20200, 0xffb30fd0, "vmovn%c.i%18-19T2\t%12-15,22D, %0-3,5Q"},
545 {FPU_NEON_EXT_V1
, 0xf3b20240, 0xffb30fd0, "vqmovun%c.s%18-19T2\t%12-15,22D, %0-3,5Q"},
546 {FPU_NEON_EXT_V1
, 0xf3b20280, 0xffb30fd0, "vqmovn%c.s%18-19T2\t%12-15,22D, %0-3,5Q"},
547 {FPU_NEON_EXT_V1
, 0xf3b202c0, 0xffb30fd0, "vqmovn%c.u%18-19T2\t%12-15,22D, %0-3,5Q"},
548 {FPU_NEON_EXT_V1
, 0xf3b20300, 0xffb30fd0, "vshll%c.i%18-19S2\t%12-15,22Q, %0-3,5D, #%18-19S2"},
549 {FPU_NEON_EXT_V1
, 0xf3bb0400, 0xffbf0e90, "vrecpe%c.%8?fu%18-19S2\t%12-15,22R, %0-3,5R"},
550 {FPU_NEON_EXT_V1
, 0xf3bb0480, 0xffbf0e90, "vrsqrte%c.%8?fu%18-19S2\t%12-15,22R, %0-3,5R"},
551 {FPU_NEON_EXT_V1
, 0xf3b00000, 0xffb30f90, "vrev64%c.%18-19S2\t%12-15,22R, %0-3,5R"},
552 {FPU_NEON_EXT_V1
, 0xf3b00080, 0xffb30f90, "vrev32%c.%18-19S2\t%12-15,22R, %0-3,5R"},
553 {FPU_NEON_EXT_V1
, 0xf3b00100, 0xffb30f90, "vrev16%c.%18-19S2\t%12-15,22R, %0-3,5R"},
554 {FPU_NEON_EXT_V1
, 0xf3b00400, 0xffb30f90, "vcls%c.s%18-19S2\t%12-15,22R, %0-3,5R"},
555 {FPU_NEON_EXT_V1
, 0xf3b00480, 0xffb30f90, "vclz%c.i%18-19S2\t%12-15,22R, %0-3,5R"},
556 {FPU_NEON_EXT_V1
, 0xf3b00700, 0xffb30f90, "vqabs%c.s%18-19S2\t%12-15,22R, %0-3,5R"},
557 {FPU_NEON_EXT_V1
, 0xf3b00780, 0xffb30f90, "vqneg%c.s%18-19S2\t%12-15,22R, %0-3,5R"},
558 {FPU_NEON_EXT_V1
, 0xf3b20080, 0xffb30f90, "vtrn%c.%18-19S2\t%12-15,22R, %0-3,5R"},
559 {FPU_NEON_EXT_V1
, 0xf3b20100, 0xffb30f90, "vuzp%c.%18-19S2\t%12-15,22R, %0-3,5R"},
560 {FPU_NEON_EXT_V1
, 0xf3b20180, 0xffb30f90, "vzip%c.%18-19S2\t%12-15,22R, %0-3,5R"},
561 {FPU_NEON_EXT_V1
, 0xf3b10000, 0xffb30b90, "vcgt%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
562 {FPU_NEON_EXT_V1
, 0xf3b10080, 0xffb30b90, "vcge%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
563 {FPU_NEON_EXT_V1
, 0xf3b10100, 0xffb30b90, "vceq%c.%10?fi%18-19S2\t%12-15,22R, %0-3,5R, #0"},
564 {FPU_NEON_EXT_V1
, 0xf3b10180, 0xffb30b90, "vcle%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
565 {FPU_NEON_EXT_V1
, 0xf3b10200, 0xffb30b90, "vclt%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R, #0"},
566 {FPU_NEON_EXT_V1
, 0xf3b10300, 0xffb30b90, "vabs%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R"},
567 {FPU_NEON_EXT_V1
, 0xf3b10380, 0xffb30b90, "vneg%c.%10?fs%18-19S2\t%12-15,22R, %0-3,5R"},
568 {FPU_NEON_EXT_V1
, 0xf3b00200, 0xffb30f10, "vpaddl%c.%7?us%18-19S2\t%12-15,22R, %0-3,5R"},
569 {FPU_NEON_EXT_V1
, 0xf3b00600, 0xffb30f10, "vpadal%c.%7?us%18-19S2\t%12-15,22R, %0-3,5R"},
570 {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"},
572 /* Three registers of the same length. */
573 {FPU_NEON_EXT_V1
, 0xf2000110, 0xffb00f10, "vand%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
574 {FPU_NEON_EXT_V1
, 0xf2100110, 0xffb00f10, "vbic%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
575 {FPU_NEON_EXT_V1
, 0xf2200110, 0xffb00f10, "vorr%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
576 {FPU_NEON_EXT_V1
, 0xf2300110, 0xffb00f10, "vorn%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
577 {FPU_NEON_EXT_V1
, 0xf3000110, 0xffb00f10, "veor%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
578 {FPU_NEON_EXT_V1
, 0xf3100110, 0xffb00f10, "vbsl%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
579 {FPU_NEON_EXT_V1
, 0xf3200110, 0xffb00f10, "vbit%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
580 {FPU_NEON_EXT_V1
, 0xf3300110, 0xffb00f10, "vbif%c\t%12-15,22R, %16-19,7R, %0-3,5R"},
581 {FPU_NEON_EXT_V1
, 0xf2000d00, 0xffa00f10, "vadd%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
582 {FPU_NEON_EXT_V1
, 0xf2000d10, 0xffa00f10, "vmla%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
583 {FPU_NEON_EXT_V1
, 0xf2000e00, 0xffa00f10, "vceq%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
584 {FPU_NEON_EXT_V1
, 0xf2000f00, 0xffa00f10, "vmax%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
585 {FPU_NEON_EXT_V1
, 0xf2000f10, 0xffa00f10, "vrecps%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
586 {FPU_NEON_EXT_V1
, 0xf2200d00, 0xffa00f10, "vsub%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
587 {FPU_NEON_EXT_V1
, 0xf2200d10, 0xffa00f10, "vmls%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
588 {FPU_NEON_EXT_V1
, 0xf2200f00, 0xffa00f10, "vmin%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
589 {FPU_NEON_EXT_V1
, 0xf2200f10, 0xffa00f10, "vrsqrts%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
590 {FPU_NEON_EXT_V1
, 0xf3000d00, 0xffa00f10, "vpadd%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
591 {FPU_NEON_EXT_V1
, 0xf3000d10, 0xffa00f10, "vmul%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
592 {FPU_NEON_EXT_V1
, 0xf3000e00, 0xffa00f10, "vcge%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
593 {FPU_NEON_EXT_V1
, 0xf3000e10, 0xffa00f10, "vacge%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
594 {FPU_NEON_EXT_V1
, 0xf3000f00, 0xffa00f10, "vpmax%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
595 {FPU_NEON_EXT_V1
, 0xf3200d00, 0xffa00f10, "vabd%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
596 {FPU_NEON_EXT_V1
, 0xf3200e00, 0xffa00f10, "vcgt%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
597 {FPU_NEON_EXT_V1
, 0xf3200e10, 0xffa00f10, "vacgt%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
598 {FPU_NEON_EXT_V1
, 0xf3200f00, 0xffa00f10, "vpmin%c.f%20U0\t%12-15,22R, %16-19,7R, %0-3,5R"},
599 {FPU_NEON_EXT_V1
, 0xf2000800, 0xff800f10, "vadd%c.i%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
600 {FPU_NEON_EXT_V1
, 0xf2000810, 0xff800f10, "vtst%c.%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
601 {FPU_NEON_EXT_V1
, 0xf2000900, 0xff800f10, "vmla%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
602 {FPU_NEON_EXT_V1
, 0xf2000b00, 0xff800f10, "vqdmulh%c.s%20-21S6\t%12-15,22R, %16-19,7R, %0-3,5R"},
603 {FPU_NEON_EXT_V1
, 0xf2000b10, 0xff800f10, "vpadd%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
604 {FPU_NEON_EXT_V1
, 0xf3000800, 0xff800f10, "vsub%c.i%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
605 {FPU_NEON_EXT_V1
, 0xf3000810, 0xff800f10, "vceq%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
606 {FPU_NEON_EXT_V1
, 0xf3000900, 0xff800f10, "vmls%c.i%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
607 {FPU_NEON_EXT_V1
, 0xf3000b00, 0xff800f10, "vqrdmulh%c.s%20-21S6\t%12-15,22R, %16-19,7R, %0-3,5R"},
608 {FPU_NEON_EXT_V1
, 0xf2000000, 0xfe800f10, "vhadd%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
609 {FPU_NEON_EXT_V1
, 0xf2000010, 0xfe800f10, "vqadd%c.%24?us%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
610 {FPU_NEON_EXT_V1
, 0xf2000100, 0xfe800f10, "vrhadd%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
611 {FPU_NEON_EXT_V1
, 0xf2000200, 0xfe800f10, "vhsub%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
612 {FPU_NEON_EXT_V1
, 0xf2000210, 0xfe800f10, "vqsub%c.%24?us%20-21S3\t%12-15,22R, %16-19,7R, %0-3,5R"},
613 {FPU_NEON_EXT_V1
, 0xf2000300, 0xfe800f10, "vcgt%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
614 {FPU_NEON_EXT_V1
, 0xf2000310, 0xfe800f10, "vcge%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
615 {FPU_NEON_EXT_V1
, 0xf2000400, 0xfe800f10, "vshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
616 {FPU_NEON_EXT_V1
, 0xf2000410, 0xfe800f10, "vqshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
617 {FPU_NEON_EXT_V1
, 0xf2000500, 0xfe800f10, "vrshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
618 {FPU_NEON_EXT_V1
, 0xf2000510, 0xfe800f10, "vqrshl%c.%24?us%20-21S3\t%12-15,22R, %0-3,5R, %16-19,7R"},
619 {FPU_NEON_EXT_V1
, 0xf2000600, 0xfe800f10, "vmax%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
620 {FPU_NEON_EXT_V1
, 0xf2000610, 0xfe800f10, "vmin%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
621 {FPU_NEON_EXT_V1
, 0xf2000700, 0xfe800f10, "vabd%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
622 {FPU_NEON_EXT_V1
, 0xf2000710, 0xfe800f10, "vaba%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
623 {FPU_NEON_EXT_V1
, 0xf2000910, 0xfe800f10, "vmul%c.%24?pi%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
624 {FPU_NEON_EXT_V1
, 0xf2000a00, 0xfe800f10, "vpmax%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
625 {FPU_NEON_EXT_V1
, 0xf2000a10, 0xfe800f10, "vpmin%c.%24?us%20-21S2\t%12-15,22R, %16-19,7R, %0-3,5R"},
627 /* One register and an immediate value. */
628 {FPU_NEON_EXT_V1
, 0xf2800e10, 0xfeb80fb0, "vmov%c.i8\t%12-15,22R, %E"},
629 {FPU_NEON_EXT_V1
, 0xf2800e30, 0xfeb80fb0, "vmov%c.i64\t%12-15,22R, %E"},
630 {FPU_NEON_EXT_V1
, 0xf2800f10, 0xfeb80fb0, "vmov%c.f32\t%12-15,22R, %E"},
631 {FPU_NEON_EXT_V1
, 0xf2800810, 0xfeb80db0, "vmov%c.i16\t%12-15,22R, %E"},
632 {FPU_NEON_EXT_V1
, 0xf2800830, 0xfeb80db0, "vmvn%c.i16\t%12-15,22R, %E"},
633 {FPU_NEON_EXT_V1
, 0xf2800910, 0xfeb80db0, "vorr%c.i16\t%12-15,22R, %E"},
634 {FPU_NEON_EXT_V1
, 0xf2800930, 0xfeb80db0, "vbic%c.i16\t%12-15,22R, %E"},
635 {FPU_NEON_EXT_V1
, 0xf2800c10, 0xfeb80eb0, "vmov%c.i32\t%12-15,22R, %E"},
636 {FPU_NEON_EXT_V1
, 0xf2800c30, 0xfeb80eb0, "vmvn%c.i32\t%12-15,22R, %E"},
637 {FPU_NEON_EXT_V1
, 0xf2800110, 0xfeb809b0, "vorr%c.i32\t%12-15,22R, %E"},
638 {FPU_NEON_EXT_V1
, 0xf2800130, 0xfeb809b0, "vbic%c.i32\t%12-15,22R, %E"},
639 {FPU_NEON_EXT_V1
, 0xf2800010, 0xfeb808b0, "vmov%c.i32\t%12-15,22R, %E"},
640 {FPU_NEON_EXT_V1
, 0xf2800030, 0xfeb808b0, "vmvn%c.i32\t%12-15,22R, %E"},
642 /* Two registers and a shift amount. */
643 {FPU_NEON_EXT_V1
, 0xf2880810, 0xffb80fd0, "vshrn%c.i16\t%12-15,22D, %0-3,5Q, #%16-18e"},
644 {FPU_NEON_EXT_V1
, 0xf2880850, 0xffb80fd0, "vrshrn%c.i16\t%12-15,22D, %0-3,5Q, #%16-18e"},
645 {FPU_NEON_EXT_V1
, 0xf2880810, 0xfeb80fd0, "vqshrun%c.s16\t%12-15,22D, %0-3,5Q, #%16-18e"},
646 {FPU_NEON_EXT_V1
, 0xf2880850, 0xfeb80fd0, "vqrshrun%c.s16\t%12-15,22D, %0-3,5Q, #%16-18e"},
647 {FPU_NEON_EXT_V1
, 0xf2880910, 0xfeb80fd0, "vqshrn%c.%24?us16\t%12-15,22D, %0-3,5Q, #%16-18e"},
648 {FPU_NEON_EXT_V1
, 0xf2880950, 0xfeb80fd0, "vqrshrn%c.%24?us16\t%12-15,22D, %0-3,5Q, #%16-18e"},
649 {FPU_NEON_EXT_V1
, 0xf2880a10, 0xfeb80fd0, "vshll%c.%24?us8\t%12-15,22D, %0-3,5Q, #%16-18d"},
650 {FPU_NEON_EXT_V1
, 0xf2900810, 0xffb00fd0, "vshrn%c.i32\t%12-15,22D, %0-3,5Q, #%16-19e"},
651 {FPU_NEON_EXT_V1
, 0xf2900850, 0xffb00fd0, "vrshrn%c.i32\t%12-15,22D, %0-3,5Q, #%16-19e"},
652 {FPU_NEON_EXT_V1
, 0xf2880510, 0xffb80f90, "vshl%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18d"},
653 {FPU_NEON_EXT_V1
, 0xf3880410, 0xffb80f90, "vsri%c.8\t%12-15,22R, %0-3,5R, #%16-18e"},
654 {FPU_NEON_EXT_V1
, 0xf3880510, 0xffb80f90, "vsli%c.8\t%12-15,22R, %0-3,5R, #%16-18d"},
655 {FPU_NEON_EXT_V1
, 0xf3880610, 0xffb80f90, "vqshlu%c.s8\t%12-15,22R, %0-3,5R, #%16-18d"},
656 {FPU_NEON_EXT_V1
, 0xf2900810, 0xfeb00fd0, "vqshrun%c.s32\t%12-15,22D, %0-3,5Q, #%16-19e"},
657 {FPU_NEON_EXT_V1
, 0xf2900850, 0xfeb00fd0, "vqrshrun%c.s32\t%12-15,22D, %0-3,5Q, #%16-19e"},
658 {FPU_NEON_EXT_V1
, 0xf2900910, 0xfeb00fd0, "vqshrn%c.%24?us32\t%12-15,22D, %0-3,5Q, #%16-19e"},
659 {FPU_NEON_EXT_V1
, 0xf2900950, 0xfeb00fd0, "vqrshrn%c.%24?us32\t%12-15,22D, %0-3,5Q, #%16-19e"},
660 {FPU_NEON_EXT_V1
, 0xf2900a10, 0xfeb00fd0, "vshll%c.%24?us16\t%12-15,22D, %0-3,5Q, #%16-19d"},
661 {FPU_NEON_EXT_V1
, 0xf2880010, 0xfeb80f90, "vshr%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
662 {FPU_NEON_EXT_V1
, 0xf2880110, 0xfeb80f90, "vsra%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
663 {FPU_NEON_EXT_V1
, 0xf2880210, 0xfeb80f90, "vrshr%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
664 {FPU_NEON_EXT_V1
, 0xf2880310, 0xfeb80f90, "vrsra%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18e"},
665 {FPU_NEON_EXT_V1
, 0xf2880710, 0xfeb80f90, "vqshl%c.%24?us8\t%12-15,22R, %0-3,5R, #%16-18d"},
666 {FPU_NEON_EXT_V1
, 0xf2a00810, 0xffa00fd0, "vshrn%c.i64\t%12-15,22D, %0-3,5Q, #%16-20e"},
667 {FPU_NEON_EXT_V1
, 0xf2a00850, 0xffa00fd0, "vrshrn%c.i64\t%12-15,22D, %0-3,5Q, #%16-20e"},
668 {FPU_NEON_EXT_V1
, 0xf2900510, 0xffb00f90, "vshl%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19d"},
669 {FPU_NEON_EXT_V1
, 0xf3900410, 0xffb00f90, "vsri%c.16\t%12-15,22R, %0-3,5R, #%16-19e"},
670 {FPU_NEON_EXT_V1
, 0xf3900510, 0xffb00f90, "vsli%c.16\t%12-15,22R, %0-3,5R, #%16-19d"},
671 {FPU_NEON_EXT_V1
, 0xf3900610, 0xffb00f90, "vqshlu%c.s16\t%12-15,22R, %0-3,5R, #%16-19d"},
672 {FPU_NEON_EXT_V1
, 0xf2a00a10, 0xfea00fd0, "vshll%c.%24?us32\t%12-15,22D, %0-3,5Q, #%16-20d"},
673 {FPU_NEON_EXT_V1
, 0xf2900010, 0xfeb00f90, "vshr%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
674 {FPU_NEON_EXT_V1
, 0xf2900110, 0xfeb00f90, "vsra%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
675 {FPU_NEON_EXT_V1
, 0xf2900210, 0xfeb00f90, "vrshr%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
676 {FPU_NEON_EXT_V1
, 0xf2900310, 0xfeb00f90, "vrsra%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19e"},
677 {FPU_NEON_EXT_V1
, 0xf2900710, 0xfeb00f90, "vqshl%c.%24?us16\t%12-15,22R, %0-3,5R, #%16-19d"},
678 {FPU_NEON_EXT_V1
, 0xf2a00810, 0xfea00fd0, "vqshrun%c.s64\t%12-15,22D, %0-3,5Q, #%16-20e"},
679 {FPU_NEON_EXT_V1
, 0xf2a00850, 0xfea00fd0, "vqrshrun%c.s64\t%12-15,22D, %0-3,5Q, #%16-20e"},
680 {FPU_NEON_EXT_V1
, 0xf2a00910, 0xfea00fd0, "vqshrn%c.%24?us64\t%12-15,22D, %0-3,5Q, #%16-20e"},
681 {FPU_NEON_EXT_V1
, 0xf2a00950, 0xfea00fd0, "vqrshrn%c.%24?us64\t%12-15,22D, %0-3,5Q, #%16-20e"},
682 {FPU_NEON_EXT_V1
, 0xf2a00510, 0xffa00f90, "vshl%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20d"},
683 {FPU_NEON_EXT_V1
, 0xf3a00410, 0xffa00f90, "vsri%c.32\t%12-15,22R, %0-3,5R, #%16-20e"},
684 {FPU_NEON_EXT_V1
, 0xf3a00510, 0xffa00f90, "vsli%c.32\t%12-15,22R, %0-3,5R, #%16-20d"},
685 {FPU_NEON_EXT_V1
, 0xf3a00610, 0xffa00f90, "vqshlu%c.s32\t%12-15,22R, %0-3,5R, #%16-20d"},
686 {FPU_NEON_EXT_V1
, 0xf2a00010, 0xfea00f90, "vshr%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
687 {FPU_NEON_EXT_V1
, 0xf2a00110, 0xfea00f90, "vsra%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
688 {FPU_NEON_EXT_V1
, 0xf2a00210, 0xfea00f90, "vrshr%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
689 {FPU_NEON_EXT_V1
, 0xf2a00310, 0xfea00f90, "vrsra%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20e"},
690 {FPU_NEON_EXT_V1
, 0xf2a00710, 0xfea00f90, "vqshl%c.%24?us32\t%12-15,22R, %0-3,5R, #%16-20d"},
691 {FPU_NEON_EXT_V1
, 0xf2800590, 0xff800f90, "vshl%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21d"},
692 {FPU_NEON_EXT_V1
, 0xf3800490, 0xff800f90, "vsri%c.64\t%12-15,22R, %0-3,5R, #%16-21e"},
693 {FPU_NEON_EXT_V1
, 0xf3800590, 0xff800f90, "vsli%c.64\t%12-15,22R, %0-3,5R, #%16-21d"},
694 {FPU_NEON_EXT_V1
, 0xf3800690, 0xff800f90, "vqshlu%c.s64\t%12-15,22R, %0-3,5R, #%16-21d"},
695 {FPU_NEON_EXT_V1
, 0xf2800090, 0xfe800f90, "vshr%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
696 {FPU_NEON_EXT_V1
, 0xf2800190, 0xfe800f90, "vsra%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
697 {FPU_NEON_EXT_V1
, 0xf2800290, 0xfe800f90, "vrshr%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
698 {FPU_NEON_EXT_V1
, 0xf2800390, 0xfe800f90, "vrsra%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21e"},
699 {FPU_NEON_EXT_V1
, 0xf2800790, 0xfe800f90, "vqshl%c.%24?us64\t%12-15,22R, %0-3,5R, #%16-21d"},
700 {FPU_NEON_EXT_V1
, 0xf2a00e10, 0xfea00e90, "vcvt%c.%24,8?usff32.%24,8?ffus32\t%12-15,22R, %0-3,5R, #%16-20e"},
702 /* Three registers of different lengths. */
703 {FPU_NEON_EXT_V1
, 0xf2800e00, 0xfea00f50, "vmull%c.p%20S0\t%12-15,22Q, %16-19,7D, %0-3,5D"},
704 {FPU_NEON_EXT_V1
, 0xf2800400, 0xff800f50, "vaddhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
705 {FPU_NEON_EXT_V1
, 0xf2800600, 0xff800f50, "vsubhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
706 {FPU_NEON_EXT_V1
, 0xf2800900, 0xff800f50, "vqdmlal%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %0-3,5D"},
707 {FPU_NEON_EXT_V1
, 0xf2800b00, 0xff800f50, "vqdmlsl%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %0-3,5D"},
708 {FPU_NEON_EXT_V1
, 0xf2800d00, 0xff800f50, "vqdmull%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %0-3,5D"},
709 {FPU_NEON_EXT_V1
, 0xf3800400, 0xff800f50, "vraddhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
710 {FPU_NEON_EXT_V1
, 0xf3800600, 0xff800f50, "vrsubhn%c.i%20-21T2\t%12-15,22D, %16-19,7Q, %0-3,5Q"},
711 {FPU_NEON_EXT_V1
, 0xf2800000, 0xfe800f50, "vaddl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
712 {FPU_NEON_EXT_V1
, 0xf2800100, 0xfe800f50, "vaddw%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7Q, %0-3,5D"},
713 {FPU_NEON_EXT_V1
, 0xf2800200, 0xfe800f50, "vsubl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
714 {FPU_NEON_EXT_V1
, 0xf2800300, 0xfe800f50, "vsubw%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7Q, %0-3,5D"},
715 {FPU_NEON_EXT_V1
, 0xf2800500, 0xfe800f50, "vabal%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
716 {FPU_NEON_EXT_V1
, 0xf2800700, 0xfe800f50, "vabdl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
717 {FPU_NEON_EXT_V1
, 0xf2800800, 0xfe800f50, "vmlal%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
718 {FPU_NEON_EXT_V1
, 0xf2800a00, 0xfe800f50, "vmlsl%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
719 {FPU_NEON_EXT_V1
, 0xf2800c00, 0xfe800f50, "vmull%c.%24?us%20-21S2\t%12-15,22Q, %16-19,7D, %0-3,5D"},
721 /* Two registers and a scalar. */
722 {FPU_NEON_EXT_V1
, 0xf2800040, 0xff800f50, "vmla%c.i%20-21S6\t%12-15,22D, %16-19,7D, %D"},
723 {FPU_NEON_EXT_V1
, 0xf2800140, 0xff800f50, "vmla%c.f%20-21Sa\t%12-15,22D, %16-19,7D, %D"},
724 {FPU_NEON_EXT_V1
, 0xf2800340, 0xff800f50, "vqdmlal%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
725 {FPU_NEON_EXT_V1
, 0xf2800440, 0xff800f50, "vmls%c.i%20-21S6\t%12-15,22D, %16-19,7D, %D"},
726 {FPU_NEON_EXT_V1
, 0xf2800540, 0xff800f50, "vmls%c.f%20-21S6\t%12-15,22D, %16-19,7D, %D"},
727 {FPU_NEON_EXT_V1
, 0xf2800740, 0xff800f50, "vqdmlsl%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
728 {FPU_NEON_EXT_V1
, 0xf2800840, 0xff800f50, "vmul%c.i%20-21S6\t%12-15,22D, %16-19,7D, %D"},
729 {FPU_NEON_EXT_V1
, 0xf2800940, 0xff800f50, "vmul%c.f%20-21Sa\t%12-15,22D, %16-19,7D, %D"},
730 {FPU_NEON_EXT_V1
, 0xf2800b40, 0xff800f50, "vqdmull%c.s%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
731 {FPU_NEON_EXT_V1
, 0xf2800c40, 0xff800f50, "vqdmulh%c.s%20-21S6\t%12-15,22D, %16-19,7D, %D"},
732 {FPU_NEON_EXT_V1
, 0xf2800d40, 0xff800f50, "vqrdmulh%c.s%20-21S6\t%12-15,22D, %16-19,7D, %D"},
733 {FPU_NEON_EXT_V1
, 0xf3800040, 0xff800f50, "vmla%c.i%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
734 {FPU_NEON_EXT_V1
, 0xf3800140, 0xff800f50, "vmla%c.f%20-21Sa\t%12-15,22Q, %16-19,7Q, %D"},
735 {FPU_NEON_EXT_V1
, 0xf3800440, 0xff800f50, "vmls%c.i%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
736 {FPU_NEON_EXT_V1
, 0xf3800540, 0xff800f50, "vmls%c.f%20-21Sa\t%12-15,22Q, %16-19,7Q, %D"},
737 {FPU_NEON_EXT_V1
, 0xf3800840, 0xff800f50, "vmul%c.i%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
738 {FPU_NEON_EXT_V1
, 0xf3800940, 0xff800f50, "vmul%c.f%20-21Sa\t%12-15,22Q, %16-19,7Q, %D"},
739 {FPU_NEON_EXT_V1
, 0xf3800c40, 0xff800f50, "vqdmulh%c.s%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
740 {FPU_NEON_EXT_V1
, 0xf3800d40, 0xff800f50, "vqrdmulh%c.s%20-21S6\t%12-15,22Q, %16-19,7Q, %D"},
741 {FPU_NEON_EXT_V1
, 0xf2800240, 0xfe800f50, "vmlal%c.%24?us%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
742 {FPU_NEON_EXT_V1
, 0xf2800640, 0xfe800f50, "vmlsl%c.%24?us%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
743 {FPU_NEON_EXT_V1
, 0xf2800a40, 0xfe800f50, "vmull%c.%24?us%20-21S6\t%12-15,22Q, %16-19,7D, %D"},
745 /* Element and structure load/store. */
746 {FPU_NEON_EXT_V1
, 0xf4a00fc0, 0xffb00fc0, "vld4%c.32\t%C"},
747 {FPU_NEON_EXT_V1
, 0xf4a00c00, 0xffb00f00, "vld1%c.%6-7S2\t%C"},
748 {FPU_NEON_EXT_V1
, 0xf4a00d00, 0xffb00f00, "vld2%c.%6-7S2\t%C"},
749 {FPU_NEON_EXT_V1
, 0xf4a00e00, 0xffb00f00, "vld3%c.%6-7S2\t%C"},
750 {FPU_NEON_EXT_V1
, 0xf4a00f00, 0xffb00f00, "vld4%c.%6-7S2\t%C"},
751 {FPU_NEON_EXT_V1
, 0xf4000200, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
752 {FPU_NEON_EXT_V1
, 0xf4000300, 0xff900f00, "v%21?ls%21?dt2%c.%6-7S2\t%A"},
753 {FPU_NEON_EXT_V1
, 0xf4000400, 0xff900f00, "v%21?ls%21?dt3%c.%6-7S2\t%A"},
754 {FPU_NEON_EXT_V1
, 0xf4000500, 0xff900f00, "v%21?ls%21?dt3%c.%6-7S2\t%A"},
755 {FPU_NEON_EXT_V1
, 0xf4000600, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
756 {FPU_NEON_EXT_V1
, 0xf4000700, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
757 {FPU_NEON_EXT_V1
, 0xf4000800, 0xff900f00, "v%21?ls%21?dt2%c.%6-7S2\t%A"},
758 {FPU_NEON_EXT_V1
, 0xf4000900, 0xff900f00, "v%21?ls%21?dt2%c.%6-7S2\t%A"},
759 {FPU_NEON_EXT_V1
, 0xf4000a00, 0xff900f00, "v%21?ls%21?dt1%c.%6-7S3\t%A"},
760 {FPU_NEON_EXT_V1
, 0xf4000000, 0xff900e00, "v%21?ls%21?dt4%c.%6-7S2\t%A"},
761 {FPU_NEON_EXT_V1
, 0xf4800000, 0xff900300, "v%21?ls%21?dt1%c.%10-11S2\t%B"},
762 {FPU_NEON_EXT_V1
, 0xf4800100, 0xff900300, "v%21?ls%21?dt2%c.%10-11S2\t%B"},
763 {FPU_NEON_EXT_V1
, 0xf4800200, 0xff900300, "v%21?ls%21?dt3%c.%10-11S2\t%B"},
764 {FPU_NEON_EXT_V1
, 0xf4800300, 0xff900300, "v%21?ls%21?dt4%c.%10-11S2\t%B"},
769 /* Opcode tables: ARM, 16-bit Thumb, 32-bit Thumb. All three are partially
770 ordered: they must be searched linearly from the top to obtain a correct
773 /* print_insn_arm recognizes the following format control codes:
777 %a print address for ldr/str instruction
778 %s print address for ldr/str halfword/signextend instruction
779 %S like %s but allow UNPREDICTABLE addressing
780 %b print branch destination
781 %c print condition code (always bits 28-31)
782 %m print register mask for ldm/stm instruction
783 %o print operand2 (immediate or register + shift)
784 %p print 'p' iff bits 12-15 are 15
785 %t print 't' iff bit 21 set and bit 24 clear
786 %B print arm BLX(1) destination
787 %C print the PSR sub type.
788 %U print barrier type.
789 %P print address for pli instruction.
791 %<bitfield>r print as an ARM register
792 %<bitfield>d print the bitfield in decimal
793 %<bitfield>W print the bitfield plus one in decimal
794 %<bitfield>x print the bitfield in hex
795 %<bitfield>X print the bitfield as 1 hex digit without leading "0x"
797 %<bitfield>'c print specified char iff bitfield is all ones
798 %<bitfield>`c print specified char iff bitfield is all zeroes
799 %<bitfield>?ab... select from array of values in big endian order
801 %e print arm SMI operand (bits 0..7,8..19).
802 %E print the LSB and WIDTH fields of a BFI or BFC instruction.
803 %V print the 16-bit immediate field of a MOVT or MOVW instruction. */
805 static const struct opcode32 arm_opcodes
[] =
807 /* ARM instructions. */
808 {ARM_EXT_V1
, 0xe1a00000, 0xffffffff, "nop\t\t\t; (mov r0, r0)"},
809 {ARM_EXT_V4T
| ARM_EXT_V5
, 0x012FFF10, 0x0ffffff0, "bx%c\t%0-3r"},
810 {ARM_EXT_V2
, 0x00000090, 0x0fe000f0, "mul%20's%c\t%16-19r, %0-3r, %8-11r"},
811 {ARM_EXT_V2
, 0x00200090, 0x0fe000f0, "mla%20's%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
812 {ARM_EXT_V2S
, 0x01000090, 0x0fb00ff0, "swp%22'b%c\t%12-15r, %0-3r, [%16-19r]"},
813 {ARM_EXT_V3M
, 0x00800090, 0x0fa000f0, "%22?sumull%20's%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
814 {ARM_EXT_V3M
, 0x00a00090, 0x0fa000f0, "%22?sumlal%20's%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
816 /* V7 instructions. */
817 {ARM_EXT_V7
, 0xf450f000, 0xfd70f000, "pli\t%P"},
818 {ARM_EXT_V7
, 0x0320f0f0, 0x0ffffff0, "dbg%c\t#%0-3d"},
819 {ARM_EXT_V7
, 0xf57ff050, 0xfffffff0, "dmb\t%U"},
820 {ARM_EXT_V7
, 0xf57ff040, 0xfffffff0, "dsb\t%U"},
821 {ARM_EXT_V7
, 0xf57ff060, 0xfffffff0, "isb\t%U"},
823 /* ARM V6T2 instructions. */
824 {ARM_EXT_V6T2
, 0x07c0001f, 0x0fe0007f, "bfc%c\t%12-15r, %E"},
825 {ARM_EXT_V6T2
, 0x07c00010, 0x0fe00070, "bfi%c\t%12-15r, %0-3r, %E"},
826 {ARM_EXT_V6T2
, 0x00600090, 0x0ff000f0, "mls%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
827 {ARM_EXT_V6T2
, 0x006000b0, 0x0f7000f0, "strht%c\t%12-15r, %S"},
829 {ARM_EXT_V6T2
, 0x00300090, 0x0f3000f0, UNDEFINED_INSTRUCTION
},
830 {ARM_EXT_V6T2
, 0x00300090, 0x0f300090, "ldr%6's%5?hbt%c\t%12-15r, %S"},
832 {ARM_EXT_V6T2
, 0x03000000, 0x0ff00000, "movw%c\t%12-15r, %V"},
833 {ARM_EXT_V6T2
, 0x03400000, 0x0ff00000, "movt%c\t%12-15r, %V"},
834 {ARM_EXT_V6T2
, 0x06ff0f30, 0x0fff0ff0, "rbit%c\t%12-15r, %0-3r"},
835 {ARM_EXT_V6T2
, 0x07a00050, 0x0fa00070, "%22?usbfx%c\t%12-15r, %0-3r, #%7-11d, #%16-20W"},
837 /* ARM V6Z instructions. */
838 {ARM_EXT_V6Z
, 0x01600070, 0x0ff000f0, "smc%c\t%e"},
840 /* ARM V6K instructions. */
841 {ARM_EXT_V6K
, 0xf57ff01f, 0xffffffff, "clrex"},
842 {ARM_EXT_V6K
, 0x01d00f9f, 0x0ff00fff, "ldrexb%c\t%12-15r, [%16-19r]"},
843 {ARM_EXT_V6K
, 0x01b00f9f, 0x0ff00fff, "ldrexd%c\t%12-15r, [%16-19r]"},
844 {ARM_EXT_V6K
, 0x01f00f9f, 0x0ff00fff, "ldrexh%c\t%12-15r, [%16-19r]"},
845 {ARM_EXT_V6K
, 0x01c00f90, 0x0ff00ff0, "strexb%c\t%12-15r, %0-3r, [%16-19r]"},
846 {ARM_EXT_V6K
, 0x01a00f90, 0x0ff00ff0, "strexd%c\t%12-15r, %0-3r, [%16-19r]"},
847 {ARM_EXT_V6K
, 0x01e00f90, 0x0ff00ff0, "strexh%c\t%12-15r, %0-3r, [%16-19r]"},
849 /* ARM V6K NOP hints. */
850 {ARM_EXT_V6K
, 0x0320f001, 0x0fffffff, "yield%c"},
851 {ARM_EXT_V6K
, 0x0320f002, 0x0fffffff, "wfe%c"},
852 {ARM_EXT_V6K
, 0x0320f003, 0x0fffffff, "wfi%c"},
853 {ARM_EXT_V6K
, 0x0320f004, 0x0fffffff, "sev%c"},
854 {ARM_EXT_V6K
, 0x0320f000, 0x0fffff00, "nop%c\t{%0-7d}"},
856 /* ARM V6 instructions. */
857 {ARM_EXT_V6
, 0xf1080000, 0xfffffe3f, "cpsie\t%8'a%7'i%6'f"},
858 {ARM_EXT_V6
, 0xf10a0000, 0xfffffe20, "cpsie\t%8'a%7'i%6'f,#%0-4d"},
859 {ARM_EXT_V6
, 0xf10C0000, 0xfffffe3f, "cpsid\t%8'a%7'i%6'f"},
860 {ARM_EXT_V6
, 0xf10e0000, 0xfffffe20, "cpsid\t%8'a%7'i%6'f,#%0-4d"},
861 {ARM_EXT_V6
, 0xf1000000, 0xfff1fe20, "cps\t#%0-4d"},
862 {ARM_EXT_V6
, 0x06800010, 0x0ff00ff0, "pkhbt%c\t%12-15r, %16-19r, %0-3r"},
863 {ARM_EXT_V6
, 0x06800010, 0x0ff00070, "pkhbt%c\t%12-15r, %16-19r, %0-3r, lsl #%7-11d"},
864 {ARM_EXT_V6
, 0x06800050, 0x0ff00ff0, "pkhtb%c\t%12-15r, %16-19r, %0-3r, asr #32"},
865 {ARM_EXT_V6
, 0x06800050, 0x0ff00070, "pkhtb%c\t%12-15r, %16-19r, %0-3r, asr #%7-11d"},
866 {ARM_EXT_V6
, 0x01900f9f, 0x0ff00fff, "ldrex%c\tr%12-15d, [%16-19r]"},
867 {ARM_EXT_V6
, 0x06200f10, 0x0ff00ff0, "qadd16%c\t%12-15r, %16-19r, %0-3r"},
868 {ARM_EXT_V6
, 0x06200f90, 0x0ff00ff0, "qadd8%c\t%12-15r, %16-19r, %0-3r"},
869 {ARM_EXT_V6
, 0x06200f30, 0x0ff00ff0, "qaddsubx%c\t%12-15r, %16-19r, %0-3r"},
870 {ARM_EXT_V6
, 0x06200f70, 0x0ff00ff0, "qsub16%c\t%12-15r, %16-19r, %0-3r"},
871 {ARM_EXT_V6
, 0x06200ff0, 0x0ff00ff0, "qsub8%c\t%12-15r, %16-19r, %0-3r"},
872 {ARM_EXT_V6
, 0x06200f50, 0x0ff00ff0, "qsubaddx%c\t%12-15r, %16-19r, %0-3r"},
873 {ARM_EXT_V6
, 0x06100f10, 0x0ff00ff0, "sadd16%c\t%12-15r, %16-19r, %0-3r"},
874 {ARM_EXT_V6
, 0x06100f90, 0x0ff00ff0, "sadd8%c\t%12-15r, %16-19r, %0-3r"},
875 {ARM_EXT_V6
, 0x06100f30, 0x0ff00ff0, "saddaddx%c\t%12-15r, %16-19r, %0-3r"},
876 {ARM_EXT_V6
, 0x06300f10, 0x0ff00ff0, "shadd16%c\t%12-15r, %16-19r, %0-3r"},
877 {ARM_EXT_V6
, 0x06300f90, 0x0ff00ff0, "shadd8%c\t%12-15r, %16-19r, %0-3r"},
878 {ARM_EXT_V6
, 0x06300f30, 0x0ff00ff0, "shaddsubx%c\t%12-15r, %16-19r, %0-3r"},
879 {ARM_EXT_V6
, 0x06300f70, 0x0ff00ff0, "shsub16%c\t%12-15r, %16-19r, %0-3r"},
880 {ARM_EXT_V6
, 0x06300ff0, 0x0ff00ff0, "shsub8%c\t%12-15r, %16-19r, %0-3r"},
881 {ARM_EXT_V6
, 0x06300f50, 0x0ff00ff0, "shsubaddx%c\t%12-15r, %16-19r, %0-3r"},
882 {ARM_EXT_V6
, 0x06100f70, 0x0ff00ff0, "ssub16%c\t%12-15r, %16-19r, %0-3r"},
883 {ARM_EXT_V6
, 0x06100ff0, 0x0ff00ff0, "ssub8%c\t%12-15r, %16-19r, %0-3r"},
884 {ARM_EXT_V6
, 0x06100f50, 0x0ff00ff0, "ssubaddx%c\t%12-15r, %16-19r, %0-3r"},
885 {ARM_EXT_V6
, 0x06500f10, 0x0ff00ff0, "uadd16%c\t%12-15r, %16-19r, %0-3r"},
886 {ARM_EXT_V6
, 0x06500f90, 0x0ff00ff0, "uadd8%c\t%12-15r, %16-19r, %0-3r"},
887 {ARM_EXT_V6
, 0x06500f30, 0x0ff00ff0, "uaddsubx%c\t%12-15r, %16-19r, %0-3r"},
888 {ARM_EXT_V6
, 0x06700f10, 0x0ff00ff0, "uhadd16%c\t%12-15r, %16-19r, %0-3r"},
889 {ARM_EXT_V6
, 0x06700f90, 0x0ff00ff0, "uhadd8%c\t%12-15r, %16-19r, %0-3r"},
890 {ARM_EXT_V6
, 0x06700f30, 0x0ff00ff0, "uhaddsubx%c\t%12-15r, %16-19r, %0-3r"},
891 {ARM_EXT_V6
, 0x06700f70, 0x0ff00ff0, "uhsub16%c\t%12-15r, %16-19r, %0-3r"},
892 {ARM_EXT_V6
, 0x06700ff0, 0x0ff00ff0, "uhsub8%c\t%12-15r, %16-19r, %0-3r"},
893 {ARM_EXT_V6
, 0x06700f50, 0x0ff00ff0, "uhsubaddx%c\t%12-15r, %16-19r, %0-3r"},
894 {ARM_EXT_V6
, 0x06600f10, 0x0ff00ff0, "uqadd16%c\t%12-15r, %16-19r, %0-3r"},
895 {ARM_EXT_V6
, 0x06600f90, 0x0ff00ff0, "uqadd8%c\t%12-15r, %16-19r, %0-3r"},
896 {ARM_EXT_V6
, 0x06600f30, 0x0ff00ff0, "uqaddsubx%c\t%12-15r, %16-19r, %0-3r"},
897 {ARM_EXT_V6
, 0x06600f70, 0x0ff00ff0, "uqsub16%c\t%12-15r, %16-19r, %0-3r"},
898 {ARM_EXT_V6
, 0x06600ff0, 0x0ff00ff0, "uqsub8%c\t%12-15r, %16-19r, %0-3r"},
899 {ARM_EXT_V6
, 0x06600f50, 0x0ff00ff0, "uqsubaddx%c\t%12-15r, %16-19r, %0-3r"},
900 {ARM_EXT_V6
, 0x06500f70, 0x0ff00ff0, "usub16%c\t%12-15r, %16-19r, %0-3r"},
901 {ARM_EXT_V6
, 0x06500ff0, 0x0ff00ff0, "usub8%c\t%12-15r, %16-19r, %0-3r"},
902 {ARM_EXT_V6
, 0x06500f50, 0x0ff00ff0, "usubaddx%c\t%12-15r, %16-19r, %0-3r"},
903 {ARM_EXT_V6
, 0x06bf0f30, 0x0fff0ff0, "rev%c\t%12-15r, %0-3r"},
904 {ARM_EXT_V6
, 0x06bf0fb0, 0x0fff0ff0, "rev16%c\t%12-15r, %0-3r"},
905 {ARM_EXT_V6
, 0x06ff0fb0, 0x0fff0ff0, "revsh%c\t%12-15r, %0-3r"},
906 {ARM_EXT_V6
, 0xf8100a00, 0xfe50ffff, "rfe%23?id%24?ba\t%16-19r%21'!"},
907 {ARM_EXT_V6
, 0x06bf0070, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r"},
908 {ARM_EXT_V6
, 0x06bf0470, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r, ror #8"},
909 {ARM_EXT_V6
, 0x06bf0870, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r, ror #16"},
910 {ARM_EXT_V6
, 0x06bf0c70, 0x0fff0ff0, "sxth%c\t%12-15r, %0-3r, ror #24"},
911 {ARM_EXT_V6
, 0x068f0070, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r"},
912 {ARM_EXT_V6
, 0x068f0470, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r, ror #8"},
913 {ARM_EXT_V6
, 0x068f0870, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r, ror #16"},
914 {ARM_EXT_V6
, 0x068f0c70, 0x0fff0ff0, "sxtb16%c\t%12-15r, %0-3r, ror #24"},
915 {ARM_EXT_V6
, 0x06af0070, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r"},
916 {ARM_EXT_V6
, 0x06af0470, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r, ror #8"},
917 {ARM_EXT_V6
, 0x06af0870, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r, ror #16"},
918 {ARM_EXT_V6
, 0x06af0c70, 0x0fff0ff0, "sxtb%c\t%12-15r, %0-3r, ror #24"},
919 {ARM_EXT_V6
, 0x06ff0070, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r"},
920 {ARM_EXT_V6
, 0x06ff0470, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r, ror #8"},
921 {ARM_EXT_V6
, 0x06ff0870, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r, ror #16"},
922 {ARM_EXT_V6
, 0x06ff0c70, 0x0fff0ff0, "uxth%c\t%12-15r, %0-3r, ror #24"},
923 {ARM_EXT_V6
, 0x06cf0070, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r"},
924 {ARM_EXT_V6
, 0x06cf0470, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r, ror #8"},
925 {ARM_EXT_V6
, 0x06cf0870, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r, ror #16"},
926 {ARM_EXT_V6
, 0x06cf0c70, 0x0fff0ff0, "uxtb16%c\t%12-15r, %0-3r, ror #24"},
927 {ARM_EXT_V6
, 0x06ef0070, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r"},
928 {ARM_EXT_V6
, 0x06ef0470, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r, ror #8"},
929 {ARM_EXT_V6
, 0x06ef0870, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r, ror #16"},
930 {ARM_EXT_V6
, 0x06ef0c70, 0x0fff0ff0, "uxtb%c\t%12-15r, %0-3r, ror #24"},
931 {ARM_EXT_V6
, 0x06b00070, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r"},
932 {ARM_EXT_V6
, 0x06b00470, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ror #8"},
933 {ARM_EXT_V6
, 0x06b00870, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ror #16"},
934 {ARM_EXT_V6
, 0x06b00c70, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ror #24"},
935 {ARM_EXT_V6
, 0x06800070, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r"},
936 {ARM_EXT_V6
, 0x06800470, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ror #8"},
937 {ARM_EXT_V6
, 0x06800870, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ror #16"},
938 {ARM_EXT_V6
, 0x06800c70, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ror #24"},
939 {ARM_EXT_V6
, 0x06a00070, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r"},
940 {ARM_EXT_V6
, 0x06a00470, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ror #8"},
941 {ARM_EXT_V6
, 0x06a00870, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ror #16"},
942 {ARM_EXT_V6
, 0x06a00c70, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ror #24"},
943 {ARM_EXT_V6
, 0x06f00070, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r"},
944 {ARM_EXT_V6
, 0x06f00470, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ror #8"},
945 {ARM_EXT_V6
, 0x06f00870, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ror #16"},
946 {ARM_EXT_V6
, 0x06f00c70, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ror #24"},
947 {ARM_EXT_V6
, 0x06c00070, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r"},
948 {ARM_EXT_V6
, 0x06c00470, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ror #8"},
949 {ARM_EXT_V6
, 0x06c00870, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ror #16"},
950 {ARM_EXT_V6
, 0x06c00c70, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
951 {ARM_EXT_V6
, 0x06e00070, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r"},
952 {ARM_EXT_V6
, 0x06e00470, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ror #8"},
953 {ARM_EXT_V6
, 0x06e00870, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ror #16"},
954 {ARM_EXT_V6
, 0x06e00c70, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ror #24"},
955 {ARM_EXT_V6
, 0x06800fb0, 0x0ff00ff0, "sel%c\t%12-15r, %16-19r, %0-3r"},
956 {ARM_EXT_V6
, 0xf1010000, 0xfffffc00, "setend\t%9?ble"},
957 {ARM_EXT_V6
, 0x0700f010, 0x0ff0f0d0, "smuad%5'x%c\t%16-19r, %0-3r, %8-11r"},
958 {ARM_EXT_V6
, 0x0700f050, 0x0ff0f0d0, "smusd%5'x%c\t%16-19r, %0-3r, %8-11r"},
959 {ARM_EXT_V6
, 0x07000010, 0x0ff000d0, "smlad%5'x%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
960 {ARM_EXT_V6
, 0x07400010, 0x0ff000d0, "smlald%5'x%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
961 {ARM_EXT_V6
, 0x07000050, 0x0ff000d0, "smlsd%5'x%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
962 {ARM_EXT_V6
, 0x07400050, 0x0ff000d0, "smlsld%5'x%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
963 {ARM_EXT_V6
, 0x0750f010, 0x0ff0f0d0, "smmul%5'r%c\t%16-19r, %0-3r, %8-11r"},
964 {ARM_EXT_V6
, 0x07500010, 0x0ff000d0, "smmla%5'r%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
965 {ARM_EXT_V6
, 0x075000d0, 0x0ff000d0, "smmls%5'r%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
966 {ARM_EXT_V6
, 0xf84d0500, 0xfe5fffe0, "srs%23?id%24?ba\t%16-19r%21'!, #%0-4d"},
967 {ARM_EXT_V6
, 0x06a00010, 0x0fe00ff0, "ssat%c\t%12-15r, #%16-20W, %0-3r"},
968 {ARM_EXT_V6
, 0x06a00010, 0x0fe00070, "ssat%c\t%12-15r, #%16-20W, %0-3r, lsl #%7-11d"},
969 {ARM_EXT_V6
, 0x06a00050, 0x0fe00070, "ssat%c\t%12-15r, #%16-20W, %0-3r, asr #%7-11d"},
970 {ARM_EXT_V6
, 0x06a00f30, 0x0ff00ff0, "ssat16%c\t%12-15r, #%16-19W, %0-3r"},
971 {ARM_EXT_V6
, 0x01800f90, 0x0ff00ff0, "strex%c\t%12-15r, %0-3r, [%16-19r]"},
972 {ARM_EXT_V6
, 0x00400090, 0x0ff000f0, "umaal%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
973 {ARM_EXT_V6
, 0x0780f010, 0x0ff0f0f0, "usad8%c\t%16-19r, %0-3r, %8-11r"},
974 {ARM_EXT_V6
, 0x07800010, 0x0ff000f0, "usada8%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
975 {ARM_EXT_V6
, 0x06e00010, 0x0fe00ff0, "usat%c\t%12-15r, #%16-20d, %0-3r"},
976 {ARM_EXT_V6
, 0x06e00010, 0x0fe00070, "usat%c\t%12-15r, #%16-20d, %0-3r, lsl #%7-11d"},
977 {ARM_EXT_V6
, 0x06e00050, 0x0fe00070, "usat%c\t%12-15r, #%16-20d, %0-3r, asr #%7-11d"},
978 {ARM_EXT_V6
, 0x06e00f30, 0x0ff00ff0, "usat16%c\t%12-15r, #%16-19d, %0-3r"},
980 /* V5J instruction. */
981 {ARM_EXT_V5J
, 0x012fff20, 0x0ffffff0, "bxj%c\t%0-3r"},
983 /* V5 Instructions. */
984 {ARM_EXT_V5
, 0xe1200070, 0xfff000f0, "bkpt\t0x%16-19X%12-15X%8-11X%0-3X"},
985 {ARM_EXT_V5
, 0xfa000000, 0xfe000000, "blx\t%B"},
986 {ARM_EXT_V5
, 0x012fff30, 0x0ffffff0, "blx%c\t%0-3r"},
987 {ARM_EXT_V5
, 0x016f0f10, 0x0fff0ff0, "clz%c\t%12-15r, %0-3r"},
989 /* V5E "El Segundo" Instructions. */
990 {ARM_EXT_V5E
, 0x000000d0, 0x0e1000f0, "ldrd%c\t%12-15r, %s"},
991 {ARM_EXT_V5E
, 0x000000f0, 0x0e1000f0, "strd%c\t%12-15r, %s"},
992 {ARM_EXT_V5E
, 0xf450f000, 0xfc70f000, "pld\t%a"},
993 {ARM_EXT_V5ExP
, 0x01000080, 0x0ff000f0, "smlabb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
994 {ARM_EXT_V5ExP
, 0x010000a0, 0x0ff000f0, "smlatb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
995 {ARM_EXT_V5ExP
, 0x010000c0, 0x0ff000f0, "smlabt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
996 {ARM_EXT_V5ExP
, 0x010000e0, 0x0ff000f0, "smlatt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
998 {ARM_EXT_V5ExP
, 0x01200080, 0x0ff000f0, "smlawb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
999 {ARM_EXT_V5ExP
, 0x012000c0, 0x0ff000f0, "smlawt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
1001 {ARM_EXT_V5ExP
, 0x01400080, 0x0ff000f0, "smlalbb%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1002 {ARM_EXT_V5ExP
, 0x014000a0, 0x0ff000f0, "smlaltb%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1003 {ARM_EXT_V5ExP
, 0x014000c0, 0x0ff000f0, "smlalbt%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1004 {ARM_EXT_V5ExP
, 0x014000e0, 0x0ff000f0, "smlaltt%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
1006 {ARM_EXT_V5ExP
, 0x01600080, 0x0ff0f0f0, "smulbb%c\t%16-19r, %0-3r, %8-11r"},
1007 {ARM_EXT_V5ExP
, 0x016000a0, 0x0ff0f0f0, "smultb%c\t%16-19r, %0-3r, %8-11r"},
1008 {ARM_EXT_V5ExP
, 0x016000c0, 0x0ff0f0f0, "smulbt%c\t%16-19r, %0-3r, %8-11r"},
1009 {ARM_EXT_V5ExP
, 0x016000e0, 0x0ff0f0f0, "smultt%c\t%16-19r, %0-3r, %8-11r"},
1011 {ARM_EXT_V5ExP
, 0x012000a0, 0x0ff0f0f0, "smulwb%c\t%16-19r, %0-3r, %8-11r"},
1012 {ARM_EXT_V5ExP
, 0x012000e0, 0x0ff0f0f0, "smulwt%c\t%16-19r, %0-3r, %8-11r"},
1014 {ARM_EXT_V5ExP
, 0x01000050, 0x0ff00ff0, "qadd%c\t%12-15r, %0-3r, %16-19r"},
1015 {ARM_EXT_V5ExP
, 0x01400050, 0x0ff00ff0, "qdadd%c\t%12-15r, %0-3r, %16-19r"},
1016 {ARM_EXT_V5ExP
, 0x01200050, 0x0ff00ff0, "qsub%c\t%12-15r, %0-3r, %16-19r"},
1017 {ARM_EXT_V5ExP
, 0x01600050, 0x0ff00ff0, "qdsub%c\t%12-15r, %0-3r, %16-19r"},
1019 /* ARM Instructions. */
1020 {ARM_EXT_V1
, 0x052d0004, 0x0fff0fff, "push%c\t{%12-15r}\t\t; (str%c %12-15r, %a)"},
1021 {ARM_EXT_V1
, 0x04000000, 0x0e100000, "str%22'b%t%c\t%12-15r, %a"},
1022 {ARM_EXT_V1
, 0x06000000, 0x0e100ff0, "str%22'b%t%c\t%12-15r, %a"},
1023 {ARM_EXT_V1
, 0x04000000, 0x0c100010, "str%22'b%t%c\t%12-15r, %a"},
1024 {ARM_EXT_V1
, 0x04400000, 0x0e500000, "strb%c\t%12-15r, %a"},
1025 {ARM_EXT_V1
, 0x06400000, 0x0e500010, "strb%c\t%12-15r, %a"},
1026 {ARM_EXT_V1
, 0x004000b0, 0x0e5000f0, "strh%c\t%12-15r, %s"},
1027 {ARM_EXT_V1
, 0x000000b0, 0x0e500ff0, "strh%c\t%12-15r, %s"},
1029 {ARM_EXT_V1
, 0x00500090, 0x0e5000f0, UNDEFINED_INSTRUCTION
},
1030 {ARM_EXT_V1
, 0x00500090, 0x0e500090, "ldr%6's%5?hb%c\t%12-15r, %s"},
1031 {ARM_EXT_V1
, 0x00100090, 0x0e500ff0, UNDEFINED_INSTRUCTION
},
1032 {ARM_EXT_V1
, 0x00100090, 0x0e500f90, "ldr%6's%5?hb%c\t%12-15r, %s"},
1034 {ARM_EXT_V1
, 0x02000000, 0x0fe00000, "and%20's%c\t%12-15r, %16-19r, %o"},
1035 {ARM_EXT_V1
, 0x00000000, 0x0fe00010, "and%20's%c\t%12-15r, %16-19r, %o"},
1036 {ARM_EXT_V1
, 0x00000010, 0x0fe00090, "and%20's%c\t%12-15r, %16-19r, %o"},
1038 {ARM_EXT_V1
, 0x02200000, 0x0fe00000, "eor%20's%c\t%12-15r, %16-19r, %o"},
1039 {ARM_EXT_V1
, 0x00200000, 0x0fe00010, "eor%20's%c\t%12-15r, %16-19r, %o"},
1040 {ARM_EXT_V1
, 0x00200010, 0x0fe00090, "eor%20's%c\t%12-15r, %16-19r, %o"},
1042 {ARM_EXT_V1
, 0x02400000, 0x0fe00000, "sub%20's%c\t%12-15r, %16-19r, %o"},
1043 {ARM_EXT_V1
, 0x00400000, 0x0fe00010, "sub%20's%c\t%12-15r, %16-19r, %o"},
1044 {ARM_EXT_V1
, 0x00400010, 0x0fe00090, "sub%20's%c\t%12-15r, %16-19r, %o"},
1046 {ARM_EXT_V1
, 0x02600000, 0x0fe00000, "rsb%20's%c\t%12-15r, %16-19r, %o"},
1047 {ARM_EXT_V1
, 0x00600000, 0x0fe00010, "rsb%20's%c\t%12-15r, %16-19r, %o"},
1048 {ARM_EXT_V1
, 0x00600010, 0x0fe00090, "rsb%20's%c\t%12-15r, %16-19r, %o"},
1050 {ARM_EXT_V1
, 0x02800000, 0x0fe00000, "add%20's%c\t%12-15r, %16-19r, %o"},
1051 {ARM_EXT_V1
, 0x00800000, 0x0fe00010, "add%20's%c\t%12-15r, %16-19r, %o"},
1052 {ARM_EXT_V1
, 0x00800010, 0x0fe00090, "add%20's%c\t%12-15r, %16-19r, %o"},
1054 {ARM_EXT_V1
, 0x02a00000, 0x0fe00000, "adc%20's%c\t%12-15r, %16-19r, %o"},
1055 {ARM_EXT_V1
, 0x00a00000, 0x0fe00010, "adc%20's%c\t%12-15r, %16-19r, %o"},
1056 {ARM_EXT_V1
, 0x00a00010, 0x0fe00090, "adc%20's%c\t%12-15r, %16-19r, %o"},
1058 {ARM_EXT_V1
, 0x02c00000, 0x0fe00000, "sbc%20's%c\t%12-15r, %16-19r, %o"},
1059 {ARM_EXT_V1
, 0x00c00000, 0x0fe00010, "sbc%20's%c\t%12-15r, %16-19r, %o"},
1060 {ARM_EXT_V1
, 0x00c00010, 0x0fe00090, "sbc%20's%c\t%12-15r, %16-19r, %o"},
1062 {ARM_EXT_V1
, 0x02e00000, 0x0fe00000, "rsc%20's%c\t%12-15r, %16-19r, %o"},
1063 {ARM_EXT_V1
, 0x00e00000, 0x0fe00010, "rsc%20's%c\t%12-15r, %16-19r, %o"},
1064 {ARM_EXT_V1
, 0x00e00010, 0x0fe00090, "rsc%20's%c\t%12-15r, %16-19r, %o"},
1066 {ARM_EXT_V3
, 0x0120f000, 0x0db0f000, "msr%c\t%22?SCPSR%C, %o"},
1067 {ARM_EXT_V3
, 0x010f0000, 0x0fbf0fff, "mrs%c\t%12-15r, %22?SCPSR"},
1069 {ARM_EXT_V1
, 0x03000000, 0x0fe00000, "tst%p%c\t%16-19r, %o"},
1070 {ARM_EXT_V1
, 0x01000000, 0x0fe00010, "tst%p%c\t%16-19r, %o"},
1071 {ARM_EXT_V1
, 0x01000010, 0x0fe00090, "tst%p%c\t%16-19r, %o"},
1073 {ARM_EXT_V1
, 0x03200000, 0x0fe00000, "teq%p%c\t%16-19r, %o"},
1074 {ARM_EXT_V1
, 0x01200000, 0x0fe00010, "teq%p%c\t%16-19r, %o"},
1075 {ARM_EXT_V1
, 0x01200010, 0x0fe00090, "teq%p%c\t%16-19r, %o"},
1077 {ARM_EXT_V1
, 0x03400000, 0x0fe00000, "cmp%p%c\t%16-19r, %o"},
1078 {ARM_EXT_V3
, 0x01400000, 0x0ff00010, "mrs%c\t%12-15r, %22?SCPSR"},
1079 {ARM_EXT_V1
, 0x01400000, 0x0fe00010, "cmp%p%c\t%16-19r, %o"},
1080 {ARM_EXT_V1
, 0x01400010, 0x0fe00090, "cmp%p%c\t%16-19r, %o"},
1082 {ARM_EXT_V1
, 0x03600000, 0x0fe00000, "cmn%p%c\t%16-19r, %o"},
1083 {ARM_EXT_V1
, 0x01600000, 0x0fe00010, "cmn%p%c\t%16-19r, %o"},
1084 {ARM_EXT_V1
, 0x01600010, 0x0fe00090, "cmn%p%c\t%16-19r, %o"},
1086 {ARM_EXT_V1
, 0x03800000, 0x0fe00000, "orr%20's%c\t%12-15r, %16-19r, %o"},
1087 {ARM_EXT_V1
, 0x01800000, 0x0fe00010, "orr%20's%c\t%12-15r, %16-19r, %o"},
1088 {ARM_EXT_V1
, 0x01800010, 0x0fe00090, "orr%20's%c\t%12-15r, %16-19r, %o"},
1090 {ARM_EXT_V1
, 0x03a00000, 0x0fef0000, "mov%20's%c\t%12-15r, %o"},
1091 {ARM_EXT_V1
, 0x01a00000, 0x0def0ff0, "mov%20's%c\t%12-15r, %0-3r"},
1092 {ARM_EXT_V1
, 0x01a00000, 0x0def0060, "lsl%20's%c\t%12-15r, %q"},
1093 {ARM_EXT_V1
, 0x01a00020, 0x0def0060, "lsr%20's%c\t%12-15r, %q"},
1094 {ARM_EXT_V1
, 0x01a00040, 0x0def0060, "asr%20's%c\t%12-15r, %q"},
1095 {ARM_EXT_V1
, 0x01a00060, 0x0def0ff0, "rrx%20's%c\t%12-15r, %0-3r"},
1096 {ARM_EXT_V1
, 0x01a00060, 0x0def0060, "ror%20's%c\t%12-15r, %q"},
1098 {ARM_EXT_V1
, 0x03c00000, 0x0fe00000, "bic%20's%c\t%12-15r, %16-19r, %o"},
1099 {ARM_EXT_V1
, 0x01c00000, 0x0fe00010, "bic%20's%c\t%12-15r, %16-19r, %o"},
1100 {ARM_EXT_V1
, 0x01c00010, 0x0fe00090, "bic%20's%c\t%12-15r, %16-19r, %o"},
1102 {ARM_EXT_V1
, 0x03e00000, 0x0fe00000, "mvn%20's%c\t%12-15r, %o"},
1103 {ARM_EXT_V1
, 0x01e00000, 0x0fe00010, "mvn%20's%c\t%12-15r, %o"},
1104 {ARM_EXT_V1
, 0x01e00010, 0x0fe00090, "mvn%20's%c\t%12-15r, %o"},
1106 {ARM_EXT_V1
, 0x06000010, 0x0e000010, UNDEFINED_INSTRUCTION
},
1107 {ARM_EXT_V1
, 0x049d0004, 0x0fff0fff, "pop%c\t{%12-15r}\t\t; (ldr%c %12-15r, %a)"},
1108 {ARM_EXT_V1
, 0x04100000, 0x0c100000, "ldr%22'b%t%c\t%12-15r, %a"},
1109 {ARM_EXT_V1
, 0x092d0000, 0x0fff0000, "push%c\t%m"},
1110 {ARM_EXT_V1
, 0x08800000, 0x0ff00000, "stm%c\t%16-19r%21'!, %m%22'^"},
1111 {ARM_EXT_V1
, 0x08000000, 0x0e100000, "stm%23?id%24?ba%c\t%16-19r%21'!, %m%22'^"},
1112 {ARM_EXT_V1
, 0x08bd0000, 0x0fff0000, "pop%c\t%m"},
1113 {ARM_EXT_V1
, 0x08900000, 0x0f900000, "ldm%c\t%16-19r%21'!, %m%22'^"},
1114 {ARM_EXT_V1
, 0x08100000, 0x0e100000, "ldm%23?id%24?ba%c\t%16-19r%21'!, %m%22'^"},
1115 {ARM_EXT_V1
, 0x0a000000, 0x0e000000, "b%24'l%c\t%b"},
1116 {ARM_EXT_V1
, 0x0f000000, 0x0f000000, "svc%c\t%0-23x"},
1119 {ARM_EXT_V1
, 0x00000000, 0x00000000, UNDEFINED_INSTRUCTION
},
1120 {0, 0x00000000, 0x00000000, 0}
1123 /* print_insn_thumb16 recognizes the following format control codes:
1125 %S print Thumb register (bits 3..5 as high number if bit 6 set)
1126 %D print Thumb register (bits 0..2 as high number if bit 7 set)
1127 %<bitfield>I print bitfield as a signed decimal
1128 (top bit of range being the sign bit)
1129 %N print Thumb register mask (with LR)
1130 %O print Thumb register mask (with PC)
1131 %M print Thumb register mask
1132 %b print CZB's 6-bit unsigned branch destination
1133 %s print Thumb right-shift immediate (6..10; 0 == 32).
1134 %c print the condition code
1135 %C print the condition code, or "s" if not conditional
1136 %x print warning if conditional an not at end of IT block"
1137 %X print "\t; unpredictable <IT:code>" if conditional
1138 %I print IT instruction suffix and operands
1139 %<bitfield>r print bitfield as an ARM register
1140 %<bitfield>d print bitfield as a decimal
1141 %<bitfield>H print (bitfield * 2) as a decimal
1142 %<bitfield>W print (bitfield * 4) as a decimal
1143 %<bitfield>a print (bitfield * 4) as a pc-rel offset + decoded symbol
1144 %<bitfield>B print Thumb branch destination (signed displacement)
1145 %<bitfield>c print bitfield as a condition code
1146 %<bitnum>'c print specified char iff bit is one
1147 %<bitnum>?ab print a if bit is one else print b. */
1149 static const struct opcode16 thumb_opcodes
[] =
1151 /* Thumb instructions. */
1153 /* ARM V6K no-argument instructions. */
1154 {ARM_EXT_V6K
, 0xbf00, 0xffff, "nop%c"},
1155 {ARM_EXT_V6K
, 0xbf10, 0xffff, "yield%c"},
1156 {ARM_EXT_V6K
, 0xbf20, 0xffff, "wfe%c"},
1157 {ARM_EXT_V6K
, 0xbf30, 0xffff, "wfi%c"},
1158 {ARM_EXT_V6K
, 0xbf40, 0xffff, "sev%c"},
1159 {ARM_EXT_V6K
, 0xbf00, 0xff0f, "nop%c\t{%4-7d}"},
1161 /* ARM V6T2 instructions. */
1162 {ARM_EXT_V6T2
, 0xb900, 0xfd00, "cbnz\t%0-2r, %b%X"},
1163 {ARM_EXT_V6T2
, 0xb100, 0xfd00, "cbz\t%0-2r, %b%X"},
1164 {ARM_EXT_V6T2
, 0xbf00, 0xff00, "it%I%X"},
1167 {ARM_EXT_V6
, 0xb660, 0xfff8, "cpsie\t%2'a%1'i%0'f%X"},
1168 {ARM_EXT_V6
, 0xb670, 0xfff8, "cpsid\t%2'a%1'i%0'f%X"},
1169 {ARM_EXT_V6
, 0x4600, 0xffc0, "mov%c\t%0-2r, %3-5r"},
1170 {ARM_EXT_V6
, 0xba00, 0xffc0, "rev%c\t%0-2r, %3-5r"},
1171 {ARM_EXT_V6
, 0xba40, 0xffc0, "rev16%c\t%0-2r, %3-5r"},
1172 {ARM_EXT_V6
, 0xbac0, 0xffc0, "revsh%c\t%0-2r, %3-5r"},
1173 {ARM_EXT_V6
, 0xb650, 0xfff7, "setend\t%3?ble%X"},
1174 {ARM_EXT_V6
, 0xb200, 0xffc0, "sxth%c\t%0-2r, %3-5r"},
1175 {ARM_EXT_V6
, 0xb240, 0xffc0, "sxtb%c\t%0-2r, %3-5r"},
1176 {ARM_EXT_V6
, 0xb280, 0xffc0, "uxth%c\t%0-2r, %3-5r"},
1177 {ARM_EXT_V6
, 0xb2c0, 0xffc0, "uxtb%c\t%0-2r, %3-5r"},
1179 /* ARM V5 ISA extends Thumb. */
1180 {ARM_EXT_V5T
, 0xbe00, 0xff00, "bkpt\t%0-7x"}, /* Is always unconditional. */
1181 /* This is BLX(2). BLX(1) is a 32-bit instruction. */
1182 {ARM_EXT_V5T
, 0x4780, 0xff87, "blx%c\t%3-6r%x"}, /* note: 4 bit register number. */
1183 /* ARM V4T ISA (Thumb v1). */
1184 {ARM_EXT_V4T
, 0x46C0, 0xFFFF, "nop%c\t\t\t; (mov r8, r8)"},
1186 {ARM_EXT_V4T
, 0x4000, 0xFFC0, "and%C\t%0-2r, %3-5r"},
1187 {ARM_EXT_V4T
, 0x4040, 0xFFC0, "eor%C\t%0-2r, %3-5r"},
1188 {ARM_EXT_V4T
, 0x4080, 0xFFC0, "lsl%C\t%0-2r, %3-5r"},
1189 {ARM_EXT_V4T
, 0x40C0, 0xFFC0, "lsr%C\t%0-2r, %3-5r"},
1190 {ARM_EXT_V4T
, 0x4100, 0xFFC0, "asr%C\t%0-2r, %3-5r"},
1191 {ARM_EXT_V4T
, 0x4140, 0xFFC0, "adc%C\t%0-2r, %3-5r"},
1192 {ARM_EXT_V4T
, 0x4180, 0xFFC0, "sbc%C\t%0-2r, %3-5r"},
1193 {ARM_EXT_V4T
, 0x41C0, 0xFFC0, "ror%C\t%0-2r, %3-5r"},
1194 {ARM_EXT_V4T
, 0x4200, 0xFFC0, "tst%c\t%0-2r, %3-5r"},
1195 {ARM_EXT_V4T
, 0x4240, 0xFFC0, "neg%C\t%0-2r, %3-5r"},
1196 {ARM_EXT_V4T
, 0x4280, 0xFFC0, "cmp%c\t%0-2r, %3-5r"},
1197 {ARM_EXT_V4T
, 0x42C0, 0xFFC0, "cmn%c\t%0-2r, %3-5r"},
1198 {ARM_EXT_V4T
, 0x4300, 0xFFC0, "orr%C\t%0-2r, %3-5r"},
1199 {ARM_EXT_V4T
, 0x4340, 0xFFC0, "mul%C\t%0-2r, %3-5r"},
1200 {ARM_EXT_V4T
, 0x4380, 0xFFC0, "bic%C\t%0-2r, %3-5r"},
1201 {ARM_EXT_V4T
, 0x43C0, 0xFFC0, "mvn%C\t%0-2r, %3-5r"},
1203 {ARM_EXT_V4T
, 0xB000, 0xFF80, "add%c\tsp, #%0-6W"},
1204 {ARM_EXT_V4T
, 0xB080, 0xFF80, "sub%c\tsp, #%0-6W"},
1206 {ARM_EXT_V4T
, 0x4700, 0xFF80, "bx%c\t%S%x"},
1207 {ARM_EXT_V4T
, 0x4400, 0xFF00, "add%c\t%D, %S"},
1208 {ARM_EXT_V4T
, 0x4500, 0xFF00, "cmp%c\t%D, %S"},
1209 {ARM_EXT_V4T
, 0x4600, 0xFF00, "mov%c\t%D, %S"},
1211 {ARM_EXT_V4T
, 0xB400, 0xFE00, "push%c\t%N"},
1212 {ARM_EXT_V4T
, 0xBC00, 0xFE00, "pop%c\t%O"},
1214 {ARM_EXT_V4T
, 0x1800, 0xFE00, "add%C\t%0-2r, %3-5r, %6-8r"},
1215 {ARM_EXT_V4T
, 0x1A00, 0xFE00, "sub%C\t%0-2r, %3-5r, %6-8r"},
1216 {ARM_EXT_V4T
, 0x1C00, 0xFE00, "add%C\t%0-2r, %3-5r, #%6-8d"},
1217 {ARM_EXT_V4T
, 0x1E00, 0xFE00, "sub%C\t%0-2r, %3-5r, #%6-8d"},
1219 {ARM_EXT_V4T
, 0x5200, 0xFE00, "strh%c\t%0-2r, [%3-5r, %6-8r]"},
1220 {ARM_EXT_V4T
, 0x5A00, 0xFE00, "ldrh%c\t%0-2r, [%3-5r, %6-8r]"},
1221 {ARM_EXT_V4T
, 0x5600, 0xF600, "ldrs%11?hb%c\t%0-2r, [%3-5r, %6-8r]"},
1223 {ARM_EXT_V4T
, 0x5000, 0xFA00, "str%10'b%c\t%0-2r, [%3-5r, %6-8r]"},
1224 {ARM_EXT_V4T
, 0x5800, 0xFA00, "ldr%10'b%c\t%0-2r, [%3-5r, %6-8r]"},
1226 {ARM_EXT_V4T
, 0x0000, 0xF800, "lsl%C\t%0-2r, %3-5r, #%6-10d"},
1227 {ARM_EXT_V4T
, 0x0800, 0xF800, "lsr%C\t%0-2r, %3-5r, %s"},
1228 {ARM_EXT_V4T
, 0x1000, 0xF800, "asr%C\t%0-2r, %3-5r, %s"},
1230 {ARM_EXT_V4T
, 0x2000, 0xF800, "mov%C\t%8-10r, #%0-7d"},
1231 {ARM_EXT_V4T
, 0x2800, 0xF800, "cmp%c\t%8-10r, #%0-7d"},
1232 {ARM_EXT_V4T
, 0x3000, 0xF800, "add%C\t%8-10r, #%0-7d"},
1233 {ARM_EXT_V4T
, 0x3800, 0xF800, "sub%C\t%8-10r, #%0-7d"},
1235 {ARM_EXT_V4T
, 0x4800, 0xF800, "ldr%c\t%8-10r, [pc, #%0-7W]\t; (%0-7a)"}, /* TODO: Disassemble PC relative "LDR rD,=<symbolic>" */
1237 {ARM_EXT_V4T
, 0x6000, 0xF800, "str%c\t%0-2r, [%3-5r, #%6-10W]"},
1238 {ARM_EXT_V4T
, 0x6800, 0xF800, "ldr%c\t%0-2r, [%3-5r, #%6-10W]"},
1239 {ARM_EXT_V4T
, 0x7000, 0xF800, "strb%c\t%0-2r, [%3-5r, #%6-10d]"},
1240 {ARM_EXT_V4T
, 0x7800, 0xF800, "ldrb%c\t%0-2r, [%3-5r, #%6-10d]"},
1242 {ARM_EXT_V4T
, 0x8000, 0xF800, "strh%c\t%0-2r, [%3-5r, #%6-10H]"},
1243 {ARM_EXT_V4T
, 0x8800, 0xF800, "ldrh%c\t%0-2r, [%3-5r, #%6-10H]"},
1245 {ARM_EXT_V4T
, 0x9000, 0xF800, "str%c\t%8-10r, [sp, #%0-7W]"},
1246 {ARM_EXT_V4T
, 0x9800, 0xF800, "ldr%c\t%8-10r, [sp, #%0-7W]"},
1248 {ARM_EXT_V4T
, 0xA000, 0xF800, "add%c\t%8-10r, pc, #%0-7W\t; (adr %8-10r, %0-7a)"},
1249 {ARM_EXT_V4T
, 0xA800, 0xF800, "add%c\t%8-10r, sp, #%0-7W"},
1251 {ARM_EXT_V4T
, 0xC000, 0xF800, "stmia%c\t%8-10r!, %M"},
1252 {ARM_EXT_V4T
, 0xC800, 0xF800, "ldmia%c\t%8-10r!, %M"},
1254 {ARM_EXT_V4T
, 0xDF00, 0xFF00, "svc%c\t%0-7d"},
1256 {ARM_EXT_V4T
, 0xDE00, 0xFE00, UNDEFINED_INSTRUCTION
},
1257 {ARM_EXT_V4T
, 0xD000, 0xF000, "b%8-11c.n\t%0-7B%X"},
1259 {ARM_EXT_V4T
, 0xE000, 0xF800, "b%c.n\t%0-10B%x"},
1261 /* The E800 .. FFFF range is unconditionally redirected to the
1262 32-bit table, because even in pre-V6T2 ISAs, BL and BLX(1) pairs
1263 are processed via that table. Thus, we can never encounter a
1264 bare "second half of BL/BLX(1)" instruction here. */
1265 {ARM_EXT_V1
, 0x0000, 0x0000, UNDEFINED_INSTRUCTION
},
1269 /* Thumb32 opcodes use the same table structure as the ARM opcodes.
1270 We adopt the convention that hw1 is the high 16 bits of .value and
1271 .mask, hw2 the low 16 bits.
1273 print_insn_thumb32 recognizes the following format control codes:
1277 %I print a 12-bit immediate from hw1[10],hw2[14:12,7:0]
1278 %M print a modified 12-bit immediate (same location)
1279 %J print a 16-bit immediate from hw1[3:0,10],hw2[14:12,7:0]
1280 %K print a 16-bit immediate from hw2[3:0],hw1[3:0],hw2[11:4]
1281 %S print a possibly-shifted Rm
1283 %a print the address of a plain load/store
1284 %w print the width and signedness of a core load/store
1285 %m print register mask for ldm/stm
1287 %E print the lsb and width fields of a bfc/bfi instruction
1288 %F print the lsb and width fields of a sbfx/ubfx instruction
1289 %b print a conditional branch offset
1290 %B print an unconditional branch offset
1291 %s print the shift field of an SSAT instruction
1292 %R print the rotation field of an SXT instruction
1293 %U print barrier type.
1294 %P print address for pli instruction.
1295 %c print the condition code
1296 %x print warning if conditional an not at end of IT block"
1297 %X print "\t; unpredictable <IT:code>" if conditional
1299 %<bitfield>d print bitfield in decimal
1300 %<bitfield>W print bitfield*4 in decimal
1301 %<bitfield>r print bitfield as an ARM register
1302 %<bitfield>c print bitfield as a condition code
1304 %<bitfield>'c print specified char iff bitfield is all ones
1305 %<bitfield>`c print specified char iff bitfield is all zeroes
1306 %<bitfield>?ab... select from array of values in big endian order
1308 With one exception at the bottom (done because BL and BLX(1) need
1309 to come dead last), this table was machine-sorted first in
1310 decreasing order of number of bits set in the mask, then in
1311 increasing numeric order of mask, then in increasing numeric order
1312 of opcode. This order is not the clearest for a human reader, but
1313 is guaranteed never to catch a special-case bit pattern with a more
1314 general mask, which is important, because this instruction encoding
1315 makes heavy use of special-case bit patterns. */
1316 static const struct opcode32 thumb32_opcodes
[] =
1318 /* V7 instructions. */
1319 {ARM_EXT_V7
, 0xf910f000, 0xff70f000, "pli%c\t%a"},
1320 {ARM_EXT_V7
, 0xf3af80f0, 0xfffffff0, "dbg%c\t#%0-3d"},
1321 {ARM_EXT_V7
, 0xf3bf8f50, 0xfffffff0, "dmb%c\t%U"},
1322 {ARM_EXT_V7
, 0xf3bf8f40, 0xfffffff0, "dsb%c\t%U"},
1323 {ARM_EXT_V7
, 0xf3bf8f60, 0xfffffff0, "isb%c\t%U"},
1324 {ARM_EXT_DIV
, 0xfb90f0f0, 0xfff0f0f0, "sdiv%c\t%8-11r, %16-19r, %0-3r"},
1325 {ARM_EXT_DIV
, 0xfbb0f0f0, 0xfff0f0f0, "udiv%c\t%8-11r, %16-19r, %0-3r"},
1327 /* Instructions defined in the basic V6T2 set. */
1328 {ARM_EXT_V6T2
, 0xf3af8000, 0xffffffff, "nop%c.w"},
1329 {ARM_EXT_V6T2
, 0xf3af8001, 0xffffffff, "yield%c.w"},
1330 {ARM_EXT_V6T2
, 0xf3af8002, 0xffffffff, "wfe%c.w"},
1331 {ARM_EXT_V6T2
, 0xf3af8003, 0xffffffff, "wfi%c.w"},
1332 {ARM_EXT_V6T2
, 0xf3af8004, 0xffffffff, "sev%c.w"},
1333 {ARM_EXT_V6T2
, 0xf3af8000, 0xffffff00, "nop%c.w\t{%0-7d}"},
1335 {ARM_EXT_V6T2
, 0xf3bf8f2f, 0xffffffff, "clrex%c"},
1336 {ARM_EXT_V6T2
, 0xf3af8400, 0xffffff1f, "cpsie.w\t%7'a%6'i%5'f%X"},
1337 {ARM_EXT_V6T2
, 0xf3af8600, 0xffffff1f, "cpsid.w\t%7'a%6'i%5'f%X"},
1338 {ARM_EXT_V6T2
, 0xf3c08f00, 0xfff0ffff, "bxj%c\t%16-19r%x"},
1339 {ARM_EXT_V6T2
, 0xe810c000, 0xffd0ffff, "rfedb%c\t%16-19r%21'!"},
1340 {ARM_EXT_V6T2
, 0xe990c000, 0xffd0ffff, "rfeia%c\t%16-19r%21'!"},
1341 {ARM_EXT_V6T2
, 0xf3ef8000, 0xffeff000, "mrs%c\t%8-11r, %D"},
1342 {ARM_EXT_V6T2
, 0xf3af8100, 0xffffffe0, "cps\t#%0-4d%X"},
1343 {ARM_EXT_V6T2
, 0xe8d0f000, 0xfff0fff0, "tbb%c\t[%16-19r, %0-3r]%x"},
1344 {ARM_EXT_V6T2
, 0xe8d0f010, 0xfff0fff0, "tbh%c\t[%16-19r, %0-3r, lsl #1]%x"},
1345 {ARM_EXT_V6T2
, 0xf3af8500, 0xffffff00, "cpsie\t%7'a%6'i%5'f, #%0-4d%X"},
1346 {ARM_EXT_V6T2
, 0xf3af8700, 0xffffff00, "cpsid\t%7'a%6'i%5'f, #%0-4d%X"},
1347 {ARM_EXT_V6T2
, 0xf3de8f00, 0xffffff00, "subs%c\tpc, lr, #%0-7d"},
1348 {ARM_EXT_V6T2
, 0xf3808000, 0xffe0f000, "msr%c\t%C, %16-19r"},
1349 {ARM_EXT_V6T2
, 0xe8500f00, 0xfff00fff, "ldrex%c\t%12-15r, [%16-19r]"},
1350 {ARM_EXT_V6T2
, 0xe8d00f4f, 0xfff00fef, "ldrex%4?hb%c\t%12-15r, [%16-19r]"},
1351 {ARM_EXT_V6T2
, 0xe800c000, 0xffd0ffe0, "srsdb%c\t%16-19r%21'!, #%0-4d"},
1352 {ARM_EXT_V6T2
, 0xe980c000, 0xffd0ffe0, "srsia%c\t%16-19r%21'!, #%0-4d"},
1353 {ARM_EXT_V6T2
, 0xfa0ff080, 0xfffff0c0, "sxth%c.w\t%8-11r, %0-3r%R"},
1354 {ARM_EXT_V6T2
, 0xfa1ff080, 0xfffff0c0, "uxth%c.w\t%8-11r, %0-3r%R"},
1355 {ARM_EXT_V6T2
, 0xfa2ff080, 0xfffff0c0, "sxtb16%c\t%8-11r, %0-3r%R"},
1356 {ARM_EXT_V6T2
, 0xfa3ff080, 0xfffff0c0, "uxtb16%c\t%8-11r, %0-3r%R"},
1357 {ARM_EXT_V6T2
, 0xfa4ff080, 0xfffff0c0, "sxtb%c.w\t%8-11r, %0-3r%R"},
1358 {ARM_EXT_V6T2
, 0xfa5ff080, 0xfffff0c0, "uxtb%c.w\t%8-11r, %0-3r%R"},
1359 {ARM_EXT_V6T2
, 0xe8400000, 0xfff000ff, "strex%c\t%8-11r, %12-15r, [%16-19r]"},
1360 {ARM_EXT_V6T2
, 0xe8d0007f, 0xfff000ff, "ldrexd%c\t%12-15r, %8-11r, [%16-19r]"},
1361 {ARM_EXT_V6T2
, 0xfa80f000, 0xfff0f0f0, "sadd8%c\t%8-11r, %16-19r, %0-3r"},
1362 {ARM_EXT_V6T2
, 0xfa80f010, 0xfff0f0f0, "qadd8%c\t%8-11r, %16-19r, %0-3r"},
1363 {ARM_EXT_V6T2
, 0xfa80f020, 0xfff0f0f0, "shadd8%c\t%8-11r, %16-19r, %0-3r"},
1364 {ARM_EXT_V6T2
, 0xfa80f040, 0xfff0f0f0, "uadd8%c\t%8-11r, %16-19r, %0-3r"},
1365 {ARM_EXT_V6T2
, 0xfa80f050, 0xfff0f0f0, "uqadd8%c\t%8-11r, %16-19r, %0-3r"},
1366 {ARM_EXT_V6T2
, 0xfa80f060, 0xfff0f0f0, "uhadd8%c\t%8-11r, %16-19r, %0-3r"},
1367 {ARM_EXT_V6T2
, 0xfa80f080, 0xfff0f0f0, "qadd%c\t%8-11r, %0-3r, %16-19r"},
1368 {ARM_EXT_V6T2
, 0xfa80f090, 0xfff0f0f0, "qdadd%c\t%8-11r, %0-3r, %16-19r"},
1369 {ARM_EXT_V6T2
, 0xfa80f0a0, 0xfff0f0f0, "qsub%c\t%8-11r, %0-3r, %16-19r"},
1370 {ARM_EXT_V6T2
, 0xfa80f0b0, 0xfff0f0f0, "qdsub%c\t%8-11r, %0-3r, %16-19r"},
1371 {ARM_EXT_V6T2
, 0xfa90f000, 0xfff0f0f0, "sadd16%c\t%8-11r, %16-19r, %0-3r"},
1372 {ARM_EXT_V6T2
, 0xfa90f010, 0xfff0f0f0, "qadd16%c\t%8-11r, %16-19r, %0-3r"},
1373 {ARM_EXT_V6T2
, 0xfa90f020, 0xfff0f0f0, "shadd16%c\t%8-11r, %16-19r, %0-3r"},
1374 {ARM_EXT_V6T2
, 0xfa90f040, 0xfff0f0f0, "uadd16%c\t%8-11r, %16-19r, %0-3r"},
1375 {ARM_EXT_V6T2
, 0xfa90f050, 0xfff0f0f0, "uqadd16%c\t%8-11r, %16-19r, %0-3r"},
1376 {ARM_EXT_V6T2
, 0xfa90f060, 0xfff0f0f0, "uhadd16%c\t%8-11r, %16-19r, %0-3r"},
1377 {ARM_EXT_V6T2
, 0xfa90f080, 0xfff0f0f0, "rev%c.w\t%8-11r, %16-19r"},
1378 {ARM_EXT_V6T2
, 0xfa90f090, 0xfff0f0f0, "rev16%c.w\t%8-11r, %16-19r"},
1379 {ARM_EXT_V6T2
, 0xfa90f0a0, 0xfff0f0f0, "rbit%c\t%8-11r, %16-19r"},
1380 {ARM_EXT_V6T2
, 0xfa90f0b0, 0xfff0f0f0, "revsh%c.w\t%8-11r, %16-19r"},
1381 {ARM_EXT_V6T2
, 0xfaa0f000, 0xfff0f0f0, "saddsubx%c\t%8-11r, %16-19r, %0-3r"},
1382 {ARM_EXT_V6T2
, 0xfaa0f010, 0xfff0f0f0, "qaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1383 {ARM_EXT_V6T2
, 0xfaa0f020, 0xfff0f0f0, "shaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1384 {ARM_EXT_V6T2
, 0xfaa0f040, 0xfff0f0f0, "uaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1385 {ARM_EXT_V6T2
, 0xfaa0f050, 0xfff0f0f0, "uqaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1386 {ARM_EXT_V6T2
, 0xfaa0f060, 0xfff0f0f0, "uhaddsubx%c\t%8-11r, %16-19r, %0-3r"},
1387 {ARM_EXT_V6T2
, 0xfaa0f080, 0xfff0f0f0, "sel%c\t%8-11r, %16-19r, %0-3r"},
1388 {ARM_EXT_V6T2
, 0xfab0f080, 0xfff0f0f0, "clz%c\t%8-11r, %16-19r"},
1389 {ARM_EXT_V6T2
, 0xfac0f000, 0xfff0f0f0, "ssub8%c\t%8-11r, %16-19r, %0-3r"},
1390 {ARM_EXT_V6T2
, 0xfac0f010, 0xfff0f0f0, "qsub8%c\t%8-11r, %16-19r, %0-3r"},
1391 {ARM_EXT_V6T2
, 0xfac0f020, 0xfff0f0f0, "shsub8%c\t%8-11r, %16-19r, %0-3r"},
1392 {ARM_EXT_V6T2
, 0xfac0f040, 0xfff0f0f0, "usub8%c\t%8-11r, %16-19r, %0-3r"},
1393 {ARM_EXT_V6T2
, 0xfac0f050, 0xfff0f0f0, "uqsub8%c\t%8-11r, %16-19r, %0-3r"},
1394 {ARM_EXT_V6T2
, 0xfac0f060, 0xfff0f0f0, "uhsub8%c\t%8-11r, %16-19r, %0-3r"},
1395 {ARM_EXT_V6T2
, 0xfad0f000, 0xfff0f0f0, "ssub16%c\t%8-11r, %16-19r, %0-3r"},
1396 {ARM_EXT_V6T2
, 0xfad0f010, 0xfff0f0f0, "qsub16%c\t%8-11r, %16-19r, %0-3r"},
1397 {ARM_EXT_V6T2
, 0xfad0f020, 0xfff0f0f0, "shsub16%c\t%8-11r, %16-19r, %0-3r"},
1398 {ARM_EXT_V6T2
, 0xfad0f040, 0xfff0f0f0, "usub16%c\t%8-11r, %16-19r, %0-3r"},
1399 {ARM_EXT_V6T2
, 0xfad0f050, 0xfff0f0f0, "uqsub16%c\t%8-11r, %16-19r, %0-3r"},
1400 {ARM_EXT_V6T2
, 0xfad0f060, 0xfff0f0f0, "uhsub16%c\t%8-11r, %16-19r, %0-3r"},
1401 {ARM_EXT_V6T2
, 0xfae0f000, 0xfff0f0f0, "ssubaddx%c\t%8-11r, %16-19r, %0-3r"},
1402 {ARM_EXT_V6T2
, 0xfae0f010, 0xfff0f0f0, "qsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1403 {ARM_EXT_V6T2
, 0xfae0f020, 0xfff0f0f0, "shsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1404 {ARM_EXT_V6T2
, 0xfae0f040, 0xfff0f0f0, "usubaddx%c\t%8-11r, %16-19r, %0-3r"},
1405 {ARM_EXT_V6T2
, 0xfae0f050, 0xfff0f0f0, "uqsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1406 {ARM_EXT_V6T2
, 0xfae0f060, 0xfff0f0f0, "uhsubaddx%c\t%8-11r, %16-19r, %0-3r"},
1407 {ARM_EXT_V6T2
, 0xfb00f000, 0xfff0f0f0, "mul%c.w\t%8-11r, %16-19r, %0-3r"},
1408 {ARM_EXT_V6T2
, 0xfb70f000, 0xfff0f0f0, "usad8%c\t%8-11r, %16-19r, %0-3r"},
1409 {ARM_EXT_V6T2
, 0xfa00f000, 0xffe0f0f0, "lsl%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1410 {ARM_EXT_V6T2
, 0xfa20f000, 0xffe0f0f0, "lsr%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1411 {ARM_EXT_V6T2
, 0xfa40f000, 0xffe0f0f0, "asr%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1412 {ARM_EXT_V6T2
, 0xfa60f000, 0xffe0f0f0, "ror%20's%c.w\t%8-11r, %16-19r, %0-3r"},
1413 {ARM_EXT_V6T2
, 0xe8c00f40, 0xfff00fe0, "strex%4?hb%c\t%0-3r, %12-15r, [%16-19r]"},
1414 {ARM_EXT_V6T2
, 0xf3200000, 0xfff0f0e0, "ssat16%c\t%8-11r, #%0-4d, %16-19r"},
1415 {ARM_EXT_V6T2
, 0xf3a00000, 0xfff0f0e0, "usat16%c\t%8-11r, #%0-4d, %16-19r"},
1416 {ARM_EXT_V6T2
, 0xfb20f000, 0xfff0f0e0, "smuad%4'x%c\t%8-11r, %16-19r, %0-3r"},
1417 {ARM_EXT_V6T2
, 0xfb30f000, 0xfff0f0e0, "smulw%4?tb%c\t%8-11r, %16-19r, %0-3r"},
1418 {ARM_EXT_V6T2
, 0xfb40f000, 0xfff0f0e0, "smusd%4'x%c\t%8-11r, %16-19r, %0-3r"},
1419 {ARM_EXT_V6T2
, 0xfb50f000, 0xfff0f0e0, "smmul%4'r%c\t%8-11r, %16-19r, %0-3r"},
1420 {ARM_EXT_V6T2
, 0xfa00f080, 0xfff0f0c0, "sxtah%c\t%8-11r, %16-19r, %0-3r%R"},
1421 {ARM_EXT_V6T2
, 0xfa10f080, 0xfff0f0c0, "uxtah%c\t%8-11r, %16-19r, %0-3r%R"},
1422 {ARM_EXT_V6T2
, 0xfa20f080, 0xfff0f0c0, "sxtab16%c\t%8-11r, %16-19r, %0-3r%R"},
1423 {ARM_EXT_V6T2
, 0xfa30f080, 0xfff0f0c0, "uxtab16%c\t%8-11r, %16-19r, %0-3r%R"},
1424 {ARM_EXT_V6T2
, 0xfa40f080, 0xfff0f0c0, "sxtab%c\t%8-11r, %16-19r, %0-3r%R"},
1425 {ARM_EXT_V6T2
, 0xfa50f080, 0xfff0f0c0, "uxtab%c\t%8-11r, %16-19r, %0-3r%R"},
1426 {ARM_EXT_V6T2
, 0xfb10f000, 0xfff0f0c0, "smul%5?tb%4?tb%c\t%8-11r, %16-19r, %0-3r"},
1427 {ARM_EXT_V6T2
, 0xf36f0000, 0xffff8020, "bfc%c\t%8-11r, %E"},
1428 {ARM_EXT_V6T2
, 0xea100f00, 0xfff08f00, "tst%c.w\t%16-19r, %S"},
1429 {ARM_EXT_V6T2
, 0xea900f00, 0xfff08f00, "teq%c\t%16-19r, %S"},
1430 {ARM_EXT_V6T2
, 0xeb100f00, 0xfff08f00, "cmn%c.w\t%16-19r, %S"},
1431 {ARM_EXT_V6T2
, 0xebb00f00, 0xfff08f00, "cmp%c.w\t%16-19r, %S"},
1432 {ARM_EXT_V6T2
, 0xf0100f00, 0xfbf08f00, "tst%c.w\t%16-19r, %M"},
1433 {ARM_EXT_V6T2
, 0xf0900f00, 0xfbf08f00, "teq%c\t%16-19r, %M"},
1434 {ARM_EXT_V6T2
, 0xf1100f00, 0xfbf08f00, "cmn%c.w\t%16-19r, %M"},
1435 {ARM_EXT_V6T2
, 0xf1b00f00, 0xfbf08f00, "cmp%c.w\t%16-19r, %M"},
1436 {ARM_EXT_V6T2
, 0xea4f0000, 0xffef8000, "mov%20's%c.w\t%8-11r, %S"},
1437 {ARM_EXT_V6T2
, 0xea6f0000, 0xffef8000, "mvn%20's%c.w\t%8-11r, %S"},
1438 {ARM_EXT_V6T2
, 0xe8c00070, 0xfff000f0, "strexd%c\t%0-3r, %12-15r, %8-11r, [%16-19r]"},
1439 {ARM_EXT_V6T2
, 0xfb000000, 0xfff000f0, "mla%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1440 {ARM_EXT_V6T2
, 0xfb000010, 0xfff000f0, "mls%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1441 {ARM_EXT_V6T2
, 0xfb700000, 0xfff000f0, "usada8%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1442 {ARM_EXT_V6T2
, 0xfb800000, 0xfff000f0, "smull%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1443 {ARM_EXT_V6T2
, 0xfba00000, 0xfff000f0, "umull%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1444 {ARM_EXT_V6T2
, 0xfbc00000, 0xfff000f0, "smlal%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1445 {ARM_EXT_V6T2
, 0xfbe00000, 0xfff000f0, "umlal%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1446 {ARM_EXT_V6T2
, 0xfbe00060, 0xfff000f0, "umaal%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1447 {ARM_EXT_V6T2
, 0xe8500f00, 0xfff00f00, "ldrex%c\t%12-15r, [%16-19r, #%0-7W]"},
1448 {ARM_EXT_V6T2
, 0xf7f08000, 0xfff0f000, "smc%c\t%K"},
1449 {ARM_EXT_V6T2
, 0xf04f0000, 0xfbef8000, "mov%20's%c.w\t%8-11r, %M"},
1450 {ARM_EXT_V6T2
, 0xf06f0000, 0xfbef8000, "mvn%20's%c.w\t%8-11r, %M"},
1451 {ARM_EXT_V6T2
, 0xf810f000, 0xff70f000, "pld%c\t%a"},
1452 {ARM_EXT_V6T2
, 0xfb200000, 0xfff000e0, "smlad%4'x%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1453 {ARM_EXT_V6T2
, 0xfb300000, 0xfff000e0, "smlaw%4?tb%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1454 {ARM_EXT_V6T2
, 0xfb400000, 0xfff000e0, "smlsd%4'x%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1455 {ARM_EXT_V6T2
, 0xfb500000, 0xfff000e0, "smmla%4'r%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1456 {ARM_EXT_V6T2
, 0xfb600000, 0xfff000e0, "smmls%4'r%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1457 {ARM_EXT_V6T2
, 0xfbc000c0, 0xfff000e0, "smlald%4'x%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1458 {ARM_EXT_V6T2
, 0xfbd000c0, 0xfff000e0, "smlsld%4'x%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1459 {ARM_EXT_V6T2
, 0xeac00000, 0xfff08030, "pkhbt%c\t%8-11r, %16-19r, %S"},
1460 {ARM_EXT_V6T2
, 0xeac00020, 0xfff08030, "pkhtb%c\t%8-11r, %16-19r, %S"},
1461 {ARM_EXT_V6T2
, 0xf3400000, 0xfff08020, "sbfx%c\t%8-11r, %16-19r, %F"},
1462 {ARM_EXT_V6T2
, 0xf3c00000, 0xfff08020, "ubfx%c\t%8-11r, %16-19r, %F"},
1463 {ARM_EXT_V6T2
, 0xf8000e00, 0xff900f00, "str%wt%c\t%12-15r, %a"},
1464 {ARM_EXT_V6T2
, 0xfb100000, 0xfff000c0, "smla%5?tb%4?tb%c\t%8-11r, %16-19r, %0-3r, %12-15r"},
1465 {ARM_EXT_V6T2
, 0xfbc00080, 0xfff000c0, "smlal%5?tb%4?tb%c\t%12-15r, %8-11r, %16-19r, %0-3r"},
1466 {ARM_EXT_V6T2
, 0xf3600000, 0xfff08020, "bfi%c\t%8-11r, %16-19r, %E"},
1467 {ARM_EXT_V6T2
, 0xf8100e00, 0xfe900f00, "ldr%wt%c\t%12-15r, %a"},
1468 {ARM_EXT_V6T2
, 0xf3000000, 0xffd08020, "ssat%c\t%8-11r, #%0-4d, %16-19r%s"},
1469 {ARM_EXT_V6T2
, 0xf3800000, 0xffd08020, "usat%c\t%8-11r, #%0-4d, %16-19r%s"},
1470 {ARM_EXT_V6T2
, 0xf2000000, 0xfbf08000, "addw%c\t%8-11r, %16-19r, %I"},
1471 {ARM_EXT_V6T2
, 0xf2400000, 0xfbf08000, "movw%c\t%8-11r, %J"},
1472 {ARM_EXT_V6T2
, 0xf2a00000, 0xfbf08000, "subw%c\t%8-11r, %16-19r, %I"},
1473 {ARM_EXT_V6T2
, 0xf2c00000, 0xfbf08000, "movt%c\t%8-11r, %J"},
1474 {ARM_EXT_V6T2
, 0xea000000, 0xffe08000, "and%20's%c.w\t%8-11r, %16-19r, %S"},
1475 {ARM_EXT_V6T2
, 0xea200000, 0xffe08000, "bic%20's%c.w\t%8-11r, %16-19r, %S"},
1476 {ARM_EXT_V6T2
, 0xea400000, 0xffe08000, "orr%20's%c.w\t%8-11r, %16-19r, %S"},
1477 {ARM_EXT_V6T2
, 0xea600000, 0xffe08000, "orn%20's%c\t%8-11r, %16-19r, %S"},
1478 {ARM_EXT_V6T2
, 0xea800000, 0xffe08000, "eor%20's%c.w\t%8-11r, %16-19r, %S"},
1479 {ARM_EXT_V6T2
, 0xeb000000, 0xffe08000, "add%20's%c.w\t%8-11r, %16-19r, %S"},
1480 {ARM_EXT_V6T2
, 0xeb400000, 0xffe08000, "adc%20's%c.w\t%8-11r, %16-19r, %S"},
1481 {ARM_EXT_V6T2
, 0xeb600000, 0xffe08000, "sbc%20's%c.w\t%8-11r, %16-19r, %S"},
1482 {ARM_EXT_V6T2
, 0xeba00000, 0xffe08000, "sub%20's%c.w\t%8-11r, %16-19r, %S"},
1483 {ARM_EXT_V6T2
, 0xebc00000, 0xffe08000, "rsb%20's%c\t%8-11r, %16-19r, %S"},
1484 {ARM_EXT_V6T2
, 0xe8400000, 0xfff00000, "strex%c\t%8-11r, %12-15r, [%16-19r, #%0-7W]"},
1485 {ARM_EXT_V6T2
, 0xf0000000, 0xfbe08000, "and%20's%c.w\t%8-11r, %16-19r, %M"},
1486 {ARM_EXT_V6T2
, 0xf0200000, 0xfbe08000, "bic%20's%c.w\t%8-11r, %16-19r, %M"},
1487 {ARM_EXT_V6T2
, 0xf0400000, 0xfbe08000, "orr%20's%c.w\t%8-11r, %16-19r, %M"},
1488 {ARM_EXT_V6T2
, 0xf0600000, 0xfbe08000, "orn%20's%c\t%8-11r, %16-19r, %M"},
1489 {ARM_EXT_V6T2
, 0xf0800000, 0xfbe08000, "eor%20's%c.w\t%8-11r, %16-19r, %M"},
1490 {ARM_EXT_V6T2
, 0xf1000000, 0xfbe08000, "add%20's%c.w\t%8-11r, %16-19r, %M"},
1491 {ARM_EXT_V6T2
, 0xf1400000, 0xfbe08000, "adc%20's%c.w\t%8-11r, %16-19r, %M"},
1492 {ARM_EXT_V6T2
, 0xf1600000, 0xfbe08000, "sbc%20's%c.w\t%8-11r, %16-19r, %M"},
1493 {ARM_EXT_V6T2
, 0xf1a00000, 0xfbe08000, "sub%20's%c.w\t%8-11r, %16-19r, %M"},
1494 {ARM_EXT_V6T2
, 0xf1c00000, 0xfbe08000, "rsb%20's%c\t%8-11r, %16-19r, %M"},
1495 {ARM_EXT_V6T2
, 0xe8800000, 0xffd00000, "stmia%c.w\t%16-19r%21'!, %m"},
1496 {ARM_EXT_V6T2
, 0xe8900000, 0xffd00000, "ldmia%c.w\t%16-19r%21'!, %m"},
1497 {ARM_EXT_V6T2
, 0xe9000000, 0xffd00000, "stmdb%c\t%16-19r%21'!, %m"},
1498 {ARM_EXT_V6T2
, 0xe9100000, 0xffd00000, "ldmdb%c\t%16-19r%21'!, %m"},
1499 {ARM_EXT_V6T2
, 0xe9c00000, 0xffd000ff, "strd%c\t%12-15r, %8-11r, [%16-19r]"},
1500 {ARM_EXT_V6T2
, 0xe9d00000, 0xffd000ff, "ldrd%c\t%12-15r, %8-11r, [%16-19r]"},
1501 {ARM_EXT_V6T2
, 0xe9400000, 0xff500000, "strd%c\t%12-15r, %8-11r, [%16-19r, #%23`-%0-7W]%21'!"},
1502 {ARM_EXT_V6T2
, 0xe9500000, 0xff500000, "ldrd%c\t%12-15r, %8-11r, [%16-19r, #%23`-%0-7W]%21'!"},
1503 {ARM_EXT_V6T2
, 0xe8600000, 0xff700000, "strd%c\t%12-15r, %8-11r, [%16-19r], #%23`-%0-7W"},
1504 {ARM_EXT_V6T2
, 0xe8700000, 0xff700000, "ldrd%c\t%12-15r, %8-11r, [%16-19r], #%23`-%0-7W"},
1505 {ARM_EXT_V6T2
, 0xf8000000, 0xff100000, "str%w%c.w\t%12-15r, %a"},
1506 {ARM_EXT_V6T2
, 0xf8100000, 0xfe100000, "ldr%w%c.w\t%12-15r, %a"},
1508 /* Filter out Bcc with cond=E or F, which are used for other instructions. */
1509 {ARM_EXT_V6T2
, 0xf3c08000, 0xfbc0d000, "undefined (bcc, cond=0xF)"},
1510 {ARM_EXT_V6T2
, 0xf3808000, 0xfbc0d000, "undefined (bcc, cond=0xE)"},
1511 {ARM_EXT_V6T2
, 0xf0008000, 0xf800d000, "b%22-25c.w\t%b%X"},
1512 {ARM_EXT_V6T2
, 0xf0009000, 0xf800d000, "b%c.w\t%B%x"},
1514 /* These have been 32-bit since the invention of Thumb. */
1515 {ARM_EXT_V4T
, 0xf000c000, 0xf800d000, "blx%c\t%B%x"},
1516 {ARM_EXT_V4T
, 0xf000d000, 0xf800d000, "bl%c\t%B%x"},
1519 {ARM_EXT_V1
, 0x00000000, 0x00000000, UNDEFINED_INSTRUCTION
},
1523 static const char *const arm_conditional
[] =
1524 {"eq", "ne", "cs", "cc", "mi", "pl", "vs", "vc",
1525 "hi", "ls", "ge", "lt", "gt", "le", "al", "<und>", ""};
1527 static const char *const arm_fp_const
[] =
1528 {"0.0", "1.0", "2.0", "3.0", "4.0", "5.0", "0.5", "10.0"};
1530 static const char *const arm_shift
[] =
1531 {"lsl", "lsr", "asr", "ror"};
1536 const char *description
;
1537 const char *reg_names
[16];
1541 static const arm_regname regnames
[] =
1543 { "raw" , "Select raw register names",
1544 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"}},
1545 { "gcc", "Select register names used by GCC",
1546 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "sl", "fp", "ip", "sp", "lr", "pc" }},
1547 { "std", "Select register names used in ARM's ISA documentation",
1548 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "sp", "lr", "pc" }},
1549 { "apcs", "Select register names used in the APCS",
1550 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "sl", "fp", "ip", "sp", "lr", "pc" }},
1551 { "atpcs", "Select register names used in the ATPCS",
1552 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8", "IP", "SP", "LR", "PC" }},
1553 { "special-atpcs", "Select special register names used in the ATPCS",
1554 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "WR", "v5", "SB", "SL", "FP", "IP", "SP", "LR", "PC" }},
1557 static const char *const iwmmxt_wwnames
[] =
1558 {"b", "h", "w", "d"};
1560 static const char *const iwmmxt_wwssnames
[] =
1561 {"b", "bus", "bc", "bss",
1562 "h", "hus", "hc", "hss",
1563 "w", "wus", "wc", "wss",
1564 "d", "dus", "dc", "dss"
1567 static const char *const iwmmxt_regnames
[] =
1568 { "wr0", "wr1", "wr2", "wr3", "wr4", "wr5", "wr6", "wr7",
1569 "wr8", "wr9", "wr10", "wr11", "wr12", "wr13", "wr14", "wr15"
1572 static const char *const iwmmxt_cregnames
[] =
1573 { "wcid", "wcon", "wcssf", "wcasf", "reserved", "reserved", "reserved", "reserved",
1574 "wcgr0", "wcgr1", "wcgr2", "wcgr3", "reserved", "reserved", "reserved", "reserved"
1577 /* Default to GCC register name set. */
1578 static unsigned int regname_selected
= 1;
1580 #define NUM_ARM_REGNAMES NUM_ELEM (regnames)
1581 #define arm_regnames regnames[regname_selected].reg_names
1583 static bfd_boolean force_thumb
= FALSE
;
1585 /* Current IT instruction state. This contains the same state as the IT
1586 bits in the CPSR. */
1587 static unsigned int ifthen_state
;
1588 /* IT state for the next instruction. */
1589 static unsigned int ifthen_next_state
;
1590 /* The address of the insn for which the IT state is valid. */
1591 static bfd_vma ifthen_address
;
1592 #define IFTHEN_COND ((ifthen_state >> 4) & 0xf)
1594 /* Cached mapping symbol state. */
1602 enum map_type last_type
;
1603 int last_mapping_sym
= -1;
1604 bfd_vma last_mapping_addr
= 0;
1609 get_arm_regname_num_options (void)
1611 return NUM_ARM_REGNAMES
;
1615 set_arm_regname_option (int option
)
1617 int old
= regname_selected
;
1618 regname_selected
= option
;
1623 get_arm_regnames (int option
,
1624 const char **setname
,
1625 const char **setdescription
,
1626 const char *const **register_names
)
1628 *setname
= regnames
[option
].name
;
1629 *setdescription
= regnames
[option
].description
;
1630 *register_names
= regnames
[option
].reg_names
;
1634 /* Decode a bitfield of the form matching regexp (N(-N)?,)*N(-N)?.
1635 Returns pointer to following character of the format string and
1636 fills in *VALUEP and *WIDTHP with the extracted value and number of
1637 bits extracted. WIDTHP can be NULL. */
1640 arm_decode_bitfield (const char *ptr
,
1642 unsigned long *valuep
,
1645 unsigned long value
= 0;
1653 for (start
= 0; *ptr
>= '0' && *ptr
<= '9'; ptr
++)
1654 start
= start
* 10 + *ptr
- '0';
1656 for (end
= 0, ptr
++; *ptr
>= '0' && *ptr
<= '9'; ptr
++)
1657 end
= end
* 10 + *ptr
- '0';
1663 value
|= ((insn
>> start
) & ((2ul << bits
) - 1)) << width
;
1666 while (*ptr
++ == ',');
1674 arm_decode_shift (long given
, fprintf_ftype func
, void *stream
,
1675 bfd_boolean print_shift
)
1677 func (stream
, "%s", arm_regnames
[given
& 0xf]);
1679 if ((given
& 0xff0) != 0)
1681 if ((given
& 0x10) == 0)
1683 int amount
= (given
& 0xf80) >> 7;
1684 int shift
= (given
& 0x60) >> 5;
1690 func (stream
, ", rrx");
1698 func (stream
, ", %s #%d", arm_shift
[shift
], amount
);
1700 func (stream
, ", #%d", amount
);
1702 else if ((given
& 0x80) == 0x80)
1703 func (stream
, "\t; <illegal shifter operand>");
1704 else if (print_shift
)
1705 func (stream
, ", %s %s", arm_shift
[(given
& 0x60) >> 5],
1706 arm_regnames
[(given
& 0xf00) >> 8]);
1708 func (stream
, ", %s", arm_regnames
[(given
& 0xf00) >> 8]);
1717 #define WRITEBACK_BIT_SET (given & (1 << W_BIT))
1718 #define IMMEDIATE_BIT_SET (given & (1 << I_BIT))
1719 #define NEGATIVE_BIT_SET ((given & (1 << U_BIT)) == 0)
1720 #define PRE_BIT_SET (given & (1 << P_BIT))
1722 /* Print one coprocessor instruction on INFO->STREAM.
1723 Return TRUE if the instuction matched, FALSE if this is not a
1724 recognised coprocessor instruction. */
1727 print_insn_coprocessor (bfd_vma pc
,
1728 struct disassemble_info
*info
,
1732 const struct opcode32
*insn
;
1733 void *stream
= info
->stream
;
1734 fprintf_ftype func
= info
->fprintf_func
;
1736 unsigned long value
;
1737 unsigned long allowed_arches
= ((arm_feature_set
*) info
->private_data
)->coproc
;
1740 for (insn
= coprocessor_opcodes
; insn
->assembler
; insn
++)
1742 signed long value_in_comment
= 0;
1745 if (insn
->arch
== 0)
1746 switch (insn
->value
)
1748 case SENTINEL_IWMMXT_START
:
1749 if (info
->mach
!= bfd_mach_arm_XScale
1750 && info
->mach
!= bfd_mach_arm_iWMMXt
1751 && info
->mach
!= bfd_mach_arm_iWMMXt2
)
1754 while (insn
->arch
!= 0 && insn
->value
!= SENTINEL_IWMMXT_END
);
1757 case SENTINEL_IWMMXT_END
:
1760 case SENTINEL_GENERIC_START
:
1761 allowed_arches
= ((arm_feature_set
*) info
->private_data
)->core
;
1769 value
= insn
->value
;
1772 /* The high 4 bits are 0xe for Arm conditional instructions, and
1773 0xe for arm unconditional instructions. The rest of the
1774 encoding is the same. */
1776 value
|= 0xe0000000;
1784 /* Only match unconditional instuctions against unconditional
1786 if ((given
& 0xf0000000) == 0xf0000000)
1793 cond
= (given
>> 28) & 0xf;
1799 if ((given
& mask
) != value
)
1802 if ((insn
->arch
& allowed_arches
) == 0)
1805 for (c
= insn
->assembler
; *c
; c
++)
1812 func (stream
, "%%");
1817 int rn
= (given
>> 16) & 0xf;
1818 int offset
= given
& 0xff;
1820 func (stream
, "[%s", arm_regnames
[(given
>> 16) & 0xf]);
1822 if (PRE_BIT_SET
|| WRITEBACK_BIT_SET
)
1824 /* Not unindexed. The offset is scaled. */
1825 offset
= offset
* 4;
1826 if (NEGATIVE_BIT_SET
)
1829 value_in_comment
= offset
;
1835 func (stream
, ", #%d]%s",
1837 WRITEBACK_BIT_SET
? "!" : "");
1845 if (WRITEBACK_BIT_SET
)
1848 func (stream
, ", #%d", offset
);
1852 func (stream
, ", {%d}", offset
);
1853 value_in_comment
= offset
;
1856 if (rn
== 15 && (PRE_BIT_SET
|| WRITEBACK_BIT_SET
))
1858 func (stream
, "\t; ");
1859 info
->print_address_func (offset
+ pc
1860 + info
->bytes_per_chunk
* 2, info
);
1867 int regno
= ((given
>> 12) & 0xf) | ((given
>> (22 - 4)) & 0x10);
1868 int offset
= (given
>> 1) & 0x3f;
1871 func (stream
, "{d%d}", regno
);
1872 else if (regno
+ offset
> 32)
1873 func (stream
, "{d%d-<overflow reg d%d>}", regno
, regno
+ offset
- 1);
1875 func (stream
, "{d%d-d%d}", regno
, regno
+ offset
- 1);
1880 func (stream
, "%s", arm_conditional
[cond
]);
1884 /* Print a Cirrus/DSP shift immediate. */
1885 /* Immediates are 7bit signed ints with bits 0..3 in
1886 bits 0..3 of opcode and bits 4..6 in bits 5..7
1891 imm
= (given
& 0xf) | ((given
& 0xe0) >> 1);
1893 /* Is ``imm'' a negative number? */
1897 func (stream
, "%d", imm
);
1903 switch (given
& 0x00408000)
1920 switch (given
& 0x00080080)
1932 func (stream
, _("<illegal precision>"));
1938 switch (given
& 0x00408000)
1956 switch (given
& 0x60)
1972 case '0': case '1': case '2': case '3': case '4':
1973 case '5': case '6': case '7': case '8': case '9':
1976 unsigned long value
;
1978 c
= arm_decode_bitfield (c
, given
, &value
, &width
);
1983 func (stream
, "%s", arm_regnames
[value
]);
1986 func (stream
, "d%ld", value
);
1990 func (stream
, "<illegal reg q%ld.5>", value
>> 1);
1992 func (stream
, "q%ld", value
>> 1);
1995 func (stream
, "%ld", value
);
1996 value_in_comment
= value
;
2000 int from
= (given
& (1 << 7)) ? 32 : 16;
2001 func (stream
, "%ld", from
- value
);
2007 func (stream
, "#%s", arm_fp_const
[value
& 7]);
2009 func (stream
, "f%ld", value
);
2014 func (stream
, "%s", iwmmxt_wwnames
[value
]);
2016 func (stream
, "%s", iwmmxt_wwssnames
[value
]);
2020 func (stream
, "%s", iwmmxt_regnames
[value
]);
2023 func (stream
, "%s", iwmmxt_cregnames
[value
]);
2027 func (stream
, "0x%lx", (value
& 0xffffffffUL
));
2033 func (stream
, "%c", *c
);
2037 if (value
== ((1ul << width
) - 1))
2038 func (stream
, "%c", *c
);
2041 func (stream
, "%c", c
[(1 << width
) - (int) value
]);
2052 int single
= *c
++ == 'y';
2057 case '4': /* Sm pair */
2058 case '0': /* Sm, Dm */
2059 regno
= given
& 0x0000000f;
2063 regno
+= (given
>> 5) & 1;
2066 regno
+= ((given
>> 5) & 1) << 4;
2069 case '1': /* Sd, Dd */
2070 regno
= (given
>> 12) & 0x0000000f;
2074 regno
+= (given
>> 22) & 1;
2077 regno
+= ((given
>> 22) & 1) << 4;
2080 case '2': /* Sn, Dn */
2081 regno
= (given
>> 16) & 0x0000000f;
2085 regno
+= (given
>> 7) & 1;
2088 regno
+= ((given
>> 7) & 1) << 4;
2091 case '3': /* List */
2093 regno
= (given
>> 12) & 0x0000000f;
2097 regno
+= (given
>> 22) & 1;
2100 regno
+= ((given
>> 22) & 1) << 4;
2107 func (stream
, "%c%d", single
? 's' : 'd', regno
);
2111 int count
= given
& 0xff;
2118 func (stream
, "-%c%d",
2126 func (stream
, ", %c%d", single
? 's' : 'd',
2132 switch (given
& 0x00400100)
2134 case 0x00000000: func (stream
, "b"); break;
2135 case 0x00400000: func (stream
, "h"); break;
2136 case 0x00000100: func (stream
, "w"); break;
2137 case 0x00400100: func (stream
, "d"); break;
2146 /* given (20, 23) | given (0, 3) */
2147 value
= ((given
>> 16) & 0xf0) | (given
& 0xf);
2148 func (stream
, "%d", value
);
2153 /* This is like the 'A' operator, except that if
2154 the width field "M" is zero, then the offset is
2155 *not* multiplied by four. */
2157 int offset
= given
& 0xff;
2158 int multiplier
= (given
& 0x00000100) ? 4 : 1;
2160 func (stream
, "[%s", arm_regnames
[(given
>> 16) & 0xf]);
2164 value_in_comment
= offset
* multiplier
;
2165 if (NEGATIVE_BIT_SET
)
2166 value_in_comment
= - value_in_comment
;
2172 func (stream
, ", #%s%d]%s",
2173 NEGATIVE_BIT_SET
? "-" : "",
2174 offset
* multiplier
,
2175 WRITEBACK_BIT_SET
? "!" : "");
2177 func (stream
, "], #%s%d",
2178 NEGATIVE_BIT_SET
? "-" : "",
2179 offset
* multiplier
);
2188 int imm4
= (given
>> 4) & 0xf;
2189 int puw_bits
= ((given
>> 22) & 6) | ((given
>> W_BIT
) & 1);
2190 int ubit
= ! NEGATIVE_BIT_SET
;
2191 const char *rm
= arm_regnames
[given
& 0xf];
2192 const char *rn
= arm_regnames
[(given
>> 16) & 0xf];
2198 func (stream
, "[%s], %c%s", rn
, ubit
? '+' : '-', rm
);
2200 func (stream
, ", lsl #%d", imm4
);
2207 func (stream
, "[%s, %c%s", rn
, ubit
? '+' : '-', rm
);
2209 func (stream
, ", lsl #%d", imm4
);
2211 if (puw_bits
== 5 || puw_bits
== 7)
2216 func (stream
, "INVALID");
2224 imm5
= ((given
& 0x100) >> 4) | (given
& 0xf);
2225 func (stream
, "%ld", (imm5
== 0) ? 32 : imm5
);
2235 func (stream
, "%c", *c
);
2238 if (value_in_comment
> 32 || value_in_comment
< -16)
2239 func (stream
, "\t; 0x%lx", (value_in_comment
& 0xffffffffUL
));
2246 /* Decodes and prints ARM addressing modes. Returns the offset
2247 used in the address, if any, if it is worthwhile printing the
2248 offset as a hexadecimal value in a comment at the end of the
2249 line of disassembly. */
2252 print_arm_address (bfd_vma pc
, struct disassemble_info
*info
, long given
)
2254 void *stream
= info
->stream
;
2255 fprintf_ftype func
= info
->fprintf_func
;
2258 if (((given
& 0x000f0000) == 0x000f0000)
2259 && ((given
& 0x02000000) == 0))
2261 offset
= given
& 0xfff;
2263 func (stream
, "[pc");
2267 if (NEGATIVE_BIT_SET
)
2271 func (stream
, ", #%d]", offset
);
2275 /* Cope with the possibility of write-back
2276 being used. Probably a very dangerous thing
2277 for the programmer to do, but who are we to
2279 if (WRITEBACK_BIT_SET
)
2282 else /* Post indexed. */
2284 func (stream
, "], #%d", offset
);
2286 /* Ie ignore the offset. */
2290 func (stream
, "\t; ");
2291 info
->print_address_func (offset
, info
);
2296 func (stream
, "[%s",
2297 arm_regnames
[(given
>> 16) & 0xf]);
2301 if ((given
& 0x02000000) == 0)
2303 offset
= given
& 0xfff;
2305 func (stream
, ", #%s%d",
2306 NEGATIVE_BIT_SET
? "-" : "", offset
);
2310 func (stream
, ", %s",
2311 NEGATIVE_BIT_SET
? "-" : "");
2312 arm_decode_shift (given
, func
, stream
, TRUE
);
2315 func (stream
, "]%s",
2316 WRITEBACK_BIT_SET
? "!" : "");
2320 if ((given
& 0x02000000) == 0)
2322 offset
= given
& 0xfff;
2324 func (stream
, "], #%s%d",
2325 NEGATIVE_BIT_SET
? "-" : "", offset
);
2331 func (stream
, "], %s",
2332 NEGATIVE_BIT_SET
? "-" : "");
2333 arm_decode_shift (given
, func
, stream
, TRUE
);
2338 return (signed long) offset
;
2341 /* Print one neon instruction on INFO->STREAM.
2342 Return TRUE if the instuction matched, FALSE if this is not a
2343 recognised neon instruction. */
2346 print_insn_neon (struct disassemble_info
*info
, long given
, bfd_boolean thumb
)
2348 const struct opcode32
*insn
;
2349 void *stream
= info
->stream
;
2350 fprintf_ftype func
= info
->fprintf_func
;
2354 if ((given
& 0xef000000) == 0xef000000)
2356 /* Move bit 28 to bit 24 to translate Thumb2 to ARM encoding. */
2357 unsigned long bit28
= given
& (1 << 28);
2359 given
&= 0x00ffffff;
2361 given
|= 0xf3000000;
2363 given
|= 0xf2000000;
2365 else if ((given
& 0xff000000) == 0xf9000000)
2366 given
^= 0xf9000000 ^ 0xf4000000;
2371 for (insn
= neon_opcodes
; insn
->assembler
; insn
++)
2373 if ((given
& insn
->mask
) == insn
->value
)
2375 signed long value_in_comment
= 0;
2378 for (c
= insn
->assembler
; *c
; c
++)
2385 func (stream
, "%%");
2389 if (thumb
&& ifthen_state
)
2390 func (stream
, "%s", arm_conditional
[IFTHEN_COND
]);
2395 static const unsigned char enc
[16] =
2397 0x4, 0x14, /* st4 0,1 */
2409 int rd
= ((given
>> 12) & 0xf) | (((given
>> 22) & 1) << 4);
2410 int rn
= ((given
>> 16) & 0xf);
2411 int rm
= ((given
>> 0) & 0xf);
2412 int align
= ((given
>> 4) & 0x3);
2413 int type
= ((given
>> 8) & 0xf);
2414 int n
= enc
[type
] & 0xf;
2415 int stride
= (enc
[type
] >> 4) + 1;
2420 for (ix
= 0; ix
!= n
; ix
++)
2421 func (stream
, "%sd%d", ix
? "," : "", rd
+ ix
* stride
);
2423 func (stream
, "d%d", rd
);
2425 func (stream
, "d%d-d%d", rd
, rd
+ n
- 1);
2426 func (stream
, "}, [%s", arm_regnames
[rn
]);
2428 func (stream
, ", :%d", 32 << align
);
2433 func (stream
, ", %s", arm_regnames
[rm
]);
2439 int rd
= ((given
>> 12) & 0xf) | (((given
>> 22) & 1) << 4);
2440 int rn
= ((given
>> 16) & 0xf);
2441 int rm
= ((given
>> 0) & 0xf);
2442 int idx_align
= ((given
>> 4) & 0xf);
2444 int size
= ((given
>> 10) & 0x3);
2445 int idx
= idx_align
>> (size
+ 1);
2446 int length
= ((given
>> 8) & 3) + 1;
2450 if (length
> 1 && size
> 0)
2451 stride
= (idx_align
& (1 << size
)) ? 2 : 1;
2457 int amask
= (1 << size
) - 1;
2458 if ((idx_align
& (1 << size
)) != 0)
2462 if ((idx_align
& amask
) == amask
)
2464 else if ((idx_align
& amask
) != 0)
2471 if (size
== 2 && (idx_align
& 2) != 0)
2473 align
= (idx_align
& 1) ? 16 << size
: 0;
2477 if ((size
== 2 && (idx_align
& 3) != 0)
2478 || (idx_align
& 1) != 0)
2485 if ((idx_align
& 3) == 3)
2487 align
= (idx_align
& 3) * 64;
2490 align
= (idx_align
& 1) ? 32 << size
: 0;
2498 for (i
= 0; i
< length
; i
++)
2499 func (stream
, "%sd%d[%d]", (i
== 0) ? "" : ",",
2500 rd
+ i
* stride
, idx
);
2501 func (stream
, "}, [%s", arm_regnames
[rn
]);
2503 func (stream
, ", :%d", align
);
2508 func (stream
, ", %s", arm_regnames
[rm
]);
2514 int rd
= ((given
>> 12) & 0xf) | (((given
>> 22) & 1) << 4);
2515 int rn
= ((given
>> 16) & 0xf);
2516 int rm
= ((given
>> 0) & 0xf);
2517 int align
= ((given
>> 4) & 0x1);
2518 int size
= ((given
>> 6) & 0x3);
2519 int type
= ((given
>> 8) & 0x3);
2521 int stride
= ((given
>> 5) & 0x1);
2524 if (stride
&& (n
== 1))
2531 for (ix
= 0; ix
!= n
; ix
++)
2532 func (stream
, "%sd%d[]", ix
? "," : "", rd
+ ix
* stride
);
2534 func (stream
, "d%d[]", rd
);
2536 func (stream
, "d%d[]-d%d[]", rd
, rd
+ n
- 1);
2537 func (stream
, "}, [%s", arm_regnames
[rn
]);
2540 int align
= (8 * (type
+ 1)) << size
;
2542 align
= (size
> 1) ? align
>> 1 : align
;
2543 if (type
== 2 || (type
== 0 && !size
))
2544 func (stream
, ", :<bad align %d>", align
);
2546 func (stream
, ", :%d", align
);
2552 func (stream
, ", %s", arm_regnames
[rm
]);
2558 int raw_reg
= (given
& 0xf) | ((given
>> 1) & 0x10);
2559 int size
= (given
>> 20) & 3;
2560 int reg
= raw_reg
& ((4 << size
) - 1);
2561 int ix
= raw_reg
>> size
>> 2;
2563 func (stream
, "d%d[%d]", reg
, ix
);
2568 /* Neon encoded constant for mov, mvn, vorr, vbic. */
2571 int cmode
= (given
>> 8) & 0xf;
2572 int op
= (given
>> 5) & 0x1;
2573 unsigned long value
= 0, hival
= 0;
2578 bits
|= ((given
>> 24) & 1) << 7;
2579 bits
|= ((given
>> 16) & 7) << 4;
2580 bits
|= ((given
>> 0) & 15) << 0;
2584 shift
= (cmode
>> 1) & 3;
2585 value
= (unsigned long) bits
<< (8 * shift
);
2588 else if (cmode
< 12)
2590 shift
= (cmode
>> 1) & 1;
2591 value
= (unsigned long) bits
<< (8 * shift
);
2594 else if (cmode
< 14)
2596 shift
= (cmode
& 1) + 1;
2597 value
= (unsigned long) bits
<< (8 * shift
);
2598 value
|= (1ul << (8 * shift
)) - 1;
2601 else if (cmode
== 14)
2605 /* Bit replication into bytes. */
2611 for (ix
= 7; ix
>= 0; ix
--)
2613 mask
= ((bits
>> ix
) & 1) ? 0xff : 0;
2615 value
= (value
<< 8) | mask
;
2617 hival
= (hival
<< 8) | mask
;
2623 /* Byte replication. */
2624 value
= (unsigned long) bits
;
2630 /* Floating point encoding. */
2633 value
= (unsigned long) (bits
& 0x7f) << 19;
2634 value
|= (unsigned long) (bits
& 0x80) << 24;
2635 tmp
= bits
& 0x40 ? 0x3c : 0x40;
2636 value
|= (unsigned long) tmp
<< 24;
2642 func (stream
, "<illegal constant %.8x:%x:%x>",
2650 func (stream
, "#%ld\t; 0x%.2lx", value
, value
);
2654 func (stream
, "#%ld\t; 0x%.4lx", value
, value
);
2660 unsigned char valbytes
[4];
2663 /* Do this a byte at a time so we don't have to
2664 worry about the host's endianness. */
2665 valbytes
[0] = value
& 0xff;
2666 valbytes
[1] = (value
>> 8) & 0xff;
2667 valbytes
[2] = (value
>> 16) & 0xff;
2668 valbytes
[3] = (value
>> 24) & 0xff;
2670 floatformat_to_double
2671 (& floatformat_ieee_single_little
, valbytes
,
2674 func (stream
, "#%.7g\t; 0x%.8lx", fvalue
,
2678 func (stream
, "#%ld\t; 0x%.8lx",
2679 (long) (NEGATIVE_BIT_SET
? value
| ~0xffffffffL
: value
),
2684 func (stream
, "#0x%.8lx%.8lx", hival
, value
);
2695 int regno
= ((given
>> 16) & 0xf) | ((given
>> (7 - 4)) & 0x10);
2696 int num
= (given
>> 8) & 0x3;
2699 func (stream
, "{d%d}", regno
);
2700 else if (num
+ regno
>= 32)
2701 func (stream
, "{d%d-<overflow reg d%d}", regno
, regno
+ num
);
2703 func (stream
, "{d%d-d%d}", regno
, regno
+ num
);
2708 case '0': case '1': case '2': case '3': case '4':
2709 case '5': case '6': case '7': case '8': case '9':
2712 unsigned long value
;
2714 c
= arm_decode_bitfield (c
, given
, &value
, &width
);
2719 func (stream
, "%s", arm_regnames
[value
]);
2722 func (stream
, "%ld", value
);
2723 value_in_comment
= value
;
2726 func (stream
, "%ld", (1ul << width
) - value
);
2732 /* Various width encodings. */
2734 int base
= 8 << (*c
- 'S'); /* 8,16 or 32 */
2739 if (*c
>= '0' && *c
<= '9')
2741 else if (*c
>= 'a' && *c
<= 'f')
2742 limit
= *c
- 'a' + 10;
2748 if (value
< low
|| value
> high
)
2749 func (stream
, "<illegal width %d>", base
<< value
);
2751 func (stream
, "%d", base
<< value
);
2755 if (given
& (1 << 6))
2759 func (stream
, "d%ld", value
);
2764 func (stream
, "<illegal reg q%ld.5>", value
>> 1);
2766 func (stream
, "q%ld", value
>> 1);
2772 func (stream
, "%c", *c
);
2776 if (value
== ((1ul << width
) - 1))
2777 func (stream
, "%c", *c
);
2780 func (stream
, "%c", c
[(1 << width
) - (int) value
]);
2794 func (stream
, "%c", *c
);
2797 if (value_in_comment
> 32 || value_in_comment
< -16)
2798 func (stream
, "\t; 0x%lx", value_in_comment
);
2806 /* Print one ARM instruction from PC on INFO->STREAM. */
2809 print_insn_arm (bfd_vma pc
, struct disassemble_info
*info
, long given
)
2811 const struct opcode32
*insn
;
2812 void *stream
= info
->stream
;
2813 fprintf_ftype func
= info
->fprintf_func
;
2815 if (print_insn_coprocessor (pc
, info
, given
, FALSE
))
2818 if (print_insn_neon (info
, given
, FALSE
))
2821 for (insn
= arm_opcodes
; insn
->assembler
; insn
++)
2823 if ((given
& insn
->mask
) != insn
->value
)
2826 if ((insn
->arch
& ((arm_feature_set
*) info
->private_data
)->core
) == 0)
2829 /* Special case: an instruction with all bits set in the condition field
2830 (0xFnnn_nnnn) is only matched if all those bits are set in insn->mask,
2831 or by the catchall at the end of the table. */
2832 if ((given
& 0xF0000000) != 0xF0000000
2833 || (insn
->mask
& 0xF0000000) == 0xF0000000
2834 || (insn
->mask
== 0 && insn
->value
== 0))
2836 signed long value_in_comment
= 0;
2839 for (c
= insn
->assembler
; *c
; c
++)
2843 bfd_boolean allow_unpredictable
= FALSE
;
2848 func (stream
, "%%");
2852 value_in_comment
= print_arm_address (pc
, info
, given
);
2856 /* Set P address bit and use normal address
2857 printing routine. */
2858 value_in_comment
= print_arm_address (pc
, info
, given
| (1 << P_BIT
));
2862 allow_unpredictable
= TRUE
;
2864 if ((given
& 0x004f0000) == 0x004f0000)
2866 /* PC relative with immediate offset. */
2867 int offset
= ((given
& 0xf00) >> 4) | (given
& 0xf);
2869 if (NEGATIVE_BIT_SET
)
2875 func (stream
, "[pc, #%d]\t; ", offset
);
2877 func (stream
, "[pc]\t; ");
2878 info
->print_address_func (offset
+ pc
+ 8, info
);
2882 func (stream
, "[pc], #%d", offset
);
2883 func (stream
, UNPREDICTABLE_INSTRUCTION
);
2888 int offset
= ((given
& 0xf00) >> 4) | (given
& 0xf);
2890 if (NEGATIVE_BIT_SET
)
2893 func (stream
, "[%s",
2894 arm_regnames
[(given
>> 16) & 0xf]);
2898 if (IMMEDIATE_BIT_SET
)
2900 if (WRITEBACK_BIT_SET
)
2901 /* Immediate Pre-indexed. */
2902 /* PR 10924: Offset must be printed, even if it is zero. */
2903 func (stream
, ", #%d", offset
);
2905 /* Immediate Offset: printing zero offset is optional. */
2906 func (stream
, ", #%d", offset
);
2908 value_in_comment
= offset
;
2911 /* Register Offset or Register Pre-Indexed. */
2912 func (stream
, ", %s%s",
2913 NEGATIVE_BIT_SET
? "-" : "",
2914 arm_regnames
[given
& 0xf]);
2916 func (stream
, "]%s",
2917 WRITEBACK_BIT_SET
? "!" : "");
2921 if (IMMEDIATE_BIT_SET
)
2923 /* Immediate Post-indexed. */
2924 /* PR 10924: Offset must be printed, even if it is zero. */
2925 func (stream
, "], #%d", offset
);
2926 value_in_comment
= offset
;
2929 /* Register Post-indexed. */
2930 func (stream
, "], %s%s",
2931 NEGATIVE_BIT_SET
? "-" : "",
2932 arm_regnames
[given
& 0xf]);
2934 if (! allow_unpredictable
)
2936 /* Writeback is automatically implied by post- addressing.
2937 Setting the W bit is unnecessary and ARM specify it as
2938 being unpredictable. */
2939 if (WRITEBACK_BIT_SET
2940 /* Specifying the PC register as the post-indexed
2941 registers is also unpredictable. */
2942 || ((given
& 0xf) == 0xf))
2943 func (stream
, UNPREDICTABLE_INSTRUCTION
);
2951 int disp
= (((given
& 0xffffff) ^ 0x800000) - 0x800000);
2952 info
->print_address_func (disp
* 4 + pc
+ 8, info
);
2957 if (((given
>> 28) & 0xf) != 0xe)
2959 arm_conditional
[(given
>> 28) & 0xf]);
2968 for (reg
= 0; reg
< 16; reg
++)
2969 if ((given
& (1 << reg
)) != 0)
2972 func (stream
, ", ");
2974 func (stream
, "%s", arm_regnames
[reg
]);
2981 arm_decode_shift (given
, func
, stream
, FALSE
);
2985 if ((given
& 0x02000000) != 0)
2987 int rotate
= (given
& 0xf00) >> 7;
2988 int immed
= (given
& 0xff);
2990 immed
= (((immed
<< (32 - rotate
))
2991 | (immed
>> rotate
)) & 0xffffffff);
2992 func (stream
, "#%d", immed
);
2993 value_in_comment
= immed
;
2996 arm_decode_shift (given
, func
, stream
, TRUE
);
3000 if ((given
& 0x0000f000) == 0x0000f000)
3002 /* The p-variants of tst/cmp/cmn/teq are the pre-V6
3003 mechanism for setting PSR flag bits. They are
3004 obsolete in V6 onwards. */
3005 if (((((arm_feature_set
*) info
->private_data
)->core
) & ARM_EXT_V6
) == 0)
3011 if ((given
& 0x01200000) == 0x00200000)
3017 int offset
= given
& 0xff;
3019 value_in_comment
= offset
* 4;
3020 if (NEGATIVE_BIT_SET
)
3021 value_in_comment
= - value_in_comment
;
3023 func (stream
, "[%s", arm_regnames
[(given
>> 16) & 0xf]);
3028 func (stream
, ", #%d]%s",
3030 WRITEBACK_BIT_SET
? "!" : "");
3038 if (WRITEBACK_BIT_SET
)
3041 func (stream
, ", #%d", value_in_comment
);
3045 func (stream
, ", {%d}", offset
);
3046 value_in_comment
= offset
;
3053 /* Print ARM V5 BLX(1) address: pc+25 bits. */
3058 if (! NEGATIVE_BIT_SET
)
3059 /* Is signed, hi bits should be ones. */
3060 offset
= (-1) ^ 0x00ffffff;
3062 /* Offset is (SignExtend(offset field)<<2). */
3063 offset
+= given
& 0x00ffffff;
3065 address
= offset
+ pc
+ 8;
3067 if (given
& 0x01000000)
3068 /* H bit allows addressing to 2-byte boundaries. */
3071 info
->print_address_func (address
, info
);
3077 if (given
& 0x80000)
3079 if (given
& 0x40000)
3081 if (given
& 0x20000)
3083 if (given
& 0x10000)
3088 switch (given
& 0xf)
3090 case 0xf: func (stream
, "sy"); break;
3091 case 0x7: func (stream
, "un"); break;
3092 case 0xe: func (stream
, "st"); break;
3093 case 0x6: func (stream
, "unst"); break;
3095 func (stream
, "#%d", (int) given
& 0xf);
3100 case '0': case '1': case '2': case '3': case '4':
3101 case '5': case '6': case '7': case '8': case '9':
3104 unsigned long value
;
3106 c
= arm_decode_bitfield (c
, given
, &value
, &width
);
3111 func (stream
, "%s", arm_regnames
[value
]);
3114 func (stream
, "%ld", value
);
3115 value_in_comment
= value
;
3118 func (stream
, "%ld", value
* 8);
3119 value_in_comment
= value
* 8;
3122 func (stream
, "%ld", value
+ 1);
3123 value_in_comment
= value
+ 1;
3126 func (stream
, "0x%08lx", value
);
3128 /* Some SWI instructions have special
3130 if ((given
& 0x0fffffff) == 0x0FF00000)
3131 func (stream
, "\t; IMB");
3132 else if ((given
& 0x0fffffff) == 0x0FF00001)
3133 func (stream
, "\t; IMBRange");
3136 func (stream
, "%01lx", value
& 0xf);
3137 value_in_comment
= value
;
3142 func (stream
, "%c", *c
);
3146 if (value
== ((1ul << width
) - 1))
3147 func (stream
, "%c", *c
);
3150 func (stream
, "%c", c
[(1 << width
) - (int) value
]);
3162 imm
= (given
& 0xf) | ((given
& 0xfff00) >> 4);
3163 func (stream
, "%d", imm
);
3164 value_in_comment
= imm
;
3169 /* LSB and WIDTH fields of BFI or BFC. The machine-
3170 language instruction encodes LSB and MSB. */
3172 long msb
= (given
& 0x001f0000) >> 16;
3173 long lsb
= (given
& 0x00000f80) >> 7;
3174 long width
= msb
- lsb
+ 1;
3177 func (stream
, "#%lu, #%lu", lsb
, width
);
3179 func (stream
, "(invalid: %lu:%lu)", lsb
, msb
);
3184 /* 16-bit unsigned immediate from a MOVT or MOVW
3185 instruction, encoded in bits 0:11 and 15:19. */
3187 long hi
= (given
& 0x000f0000) >> 4;
3188 long lo
= (given
& 0x00000fff);
3189 long imm16
= hi
| lo
;
3191 func (stream
, "#%lu", imm16
);
3192 value_in_comment
= imm16
;
3202 func (stream
, "%c", *c
);
3205 if (value_in_comment
> 32 || value_in_comment
< -16)
3206 func (stream
, "\t; 0x%lx", (value_in_comment
& 0xffffffffUL
));
3213 /* Print one 16-bit Thumb instruction from PC on INFO->STREAM. */
3216 print_insn_thumb16 (bfd_vma pc
, struct disassemble_info
*info
, long given
)
3218 const struct opcode16
*insn
;
3219 void *stream
= info
->stream
;
3220 fprintf_ftype func
= info
->fprintf_func
;
3222 for (insn
= thumb_opcodes
; insn
->assembler
; insn
++)
3223 if ((given
& insn
->mask
) == insn
->value
)
3225 signed long value_in_comment
= 0;
3226 const char *c
= insn
->assembler
;
3235 func (stream
, "%c", *c
);
3242 func (stream
, "%%");
3247 func (stream
, "%s", arm_conditional
[IFTHEN_COND
]);
3252 func (stream
, "%s", arm_conditional
[IFTHEN_COND
]);
3261 ifthen_next_state
= given
& 0xff;
3262 for (tmp
= given
<< 1; tmp
& 0xf; tmp
<<= 1)
3263 func (stream
, ((given
^ tmp
) & 0x10) ? "e" : "t");
3264 func (stream
, "\t%s", arm_conditional
[(given
>> 4) & 0xf]);
3269 if (ifthen_next_state
)
3270 func (stream
, "\t; unpredictable branch in IT block\n");
3275 func (stream
, "\t; unpredictable <IT:%s>",
3276 arm_conditional
[IFTHEN_COND
]);
3283 reg
= (given
>> 3) & 0x7;
3284 if (given
& (1 << 6))
3287 func (stream
, "%s", arm_regnames
[reg
]);
3296 if (given
& (1 << 7))
3299 func (stream
, "%s", arm_regnames
[reg
]);
3304 if (given
& (1 << 8))
3308 if (*c
== 'O' && (given
& (1 << 8)))
3318 /* It would be nice if we could spot
3319 ranges, and generate the rS-rE format: */
3320 for (reg
= 0; (reg
< 8); reg
++)
3321 if ((given
& (1 << reg
)) != 0)
3324 func (stream
, ", ");
3326 func (stream
, "%s", arm_regnames
[reg
]);
3332 func (stream
, ", ");
3334 func (stream
, arm_regnames
[14] /* "lr" */);
3340 func (stream
, ", ");
3341 func (stream
, arm_regnames
[15] /* "pc" */);
3349 /* Print ARM V6T2 CZB address: pc+4+6 bits. */
3351 bfd_vma address
= (pc
+ 4
3352 + ((given
& 0x00f8) >> 2)
3353 + ((given
& 0x0200) >> 3));
3354 info
->print_address_func (address
, info
);
3359 /* Right shift immediate -- bits 6..10; 1-31 print
3360 as themselves, 0 prints as 32. */
3362 long imm
= (given
& 0x07c0) >> 6;
3365 func (stream
, "#%ld", imm
);
3369 case '0': case '1': case '2': case '3': case '4':
3370 case '5': case '6': case '7': case '8': case '9':
3372 int bitstart
= *c
++ - '0';
3375 while (*c
>= '0' && *c
<= '9')
3376 bitstart
= (bitstart
* 10) + *c
++ - '0';
3385 while (*c
>= '0' && *c
<= '9')
3386 bitend
= (bitend
* 10) + *c
++ - '0';
3389 reg
= given
>> bitstart
;
3390 reg
&= (2 << (bitend
- bitstart
)) - 1;
3394 func (stream
, "%s", arm_regnames
[reg
]);
3398 func (stream
, "%ld", reg
);
3399 value_in_comment
= reg
;
3403 func (stream
, "%ld", reg
<< 1);
3404 value_in_comment
= reg
<< 1;
3408 func (stream
, "%ld", reg
<< 2);
3409 value_in_comment
= reg
<< 2;
3413 /* PC-relative address -- the bottom two
3414 bits of the address are dropped
3415 before the calculation. */
3416 info
->print_address_func
3417 (((pc
+ 4) & ~3) + (reg
<< 2), info
);
3418 value_in_comment
= 0;
3422 func (stream
, "0x%04lx", reg
);
3426 reg
= ((reg
^ (1 << bitend
)) - (1 << bitend
));
3427 info
->print_address_func (reg
* 2 + pc
+ 4, info
);
3428 value_in_comment
= 0;
3432 func (stream
, "%s", arm_conditional
[reg
]);
3443 if ((given
& (1 << bitstart
)) != 0)
3444 func (stream
, "%c", *c
);
3449 if ((given
& (1 << bitstart
)) != 0)
3450 func (stream
, "%c", *c
++);
3452 func (stream
, "%c", *++c
);
3466 if (value_in_comment
> 32 || value_in_comment
< -16)
3467 func (stream
, "\t; 0x%lx", value_in_comment
);
3475 /* Return the name of an V7M special register. */
3478 psr_name (int regno
)
3482 case 0: return "APSR";
3483 case 1: return "IAPSR";
3484 case 2: return "EAPSR";
3485 case 3: return "PSR";
3486 case 5: return "IPSR";
3487 case 6: return "EPSR";
3488 case 7: return "IEPSR";
3489 case 8: return "MSP";
3490 case 9: return "PSP";
3491 case 16: return "PRIMASK";
3492 case 17: return "BASEPRI";
3493 case 18: return "BASEPRI_MASK";
3494 case 19: return "FAULTMASK";
3495 case 20: return "CONTROL";
3496 default: return "<unknown>";
3500 /* Print one 32-bit Thumb instruction from PC on INFO->STREAM. */
3503 print_insn_thumb32 (bfd_vma pc
, struct disassemble_info
*info
, long given
)
3505 const struct opcode32
*insn
;
3506 void *stream
= info
->stream
;
3507 fprintf_ftype func
= info
->fprintf_func
;
3509 if (print_insn_coprocessor (pc
, info
, given
, TRUE
))
3512 if (print_insn_neon (info
, given
, TRUE
))
3515 for (insn
= thumb32_opcodes
; insn
->assembler
; insn
++)
3516 if ((given
& insn
->mask
) == insn
->value
)
3518 signed long value_in_comment
= 0;
3519 const char *c
= insn
->assembler
;
3525 func (stream
, "%c", *c
);
3532 func (stream
, "%%");
3537 func (stream
, "%s", arm_conditional
[IFTHEN_COND
]);
3541 if (ifthen_next_state
)
3542 func (stream
, "\t; unpredictable branch in IT block\n");
3547 func (stream
, "\t; unpredictable <IT:%s>",
3548 arm_conditional
[IFTHEN_COND
]);
3553 unsigned int imm12
= 0;
3555 imm12
|= (given
& 0x000000ffu
);
3556 imm12
|= (given
& 0x00007000u
) >> 4;
3557 imm12
|= (given
& 0x04000000u
) >> 15;
3558 func (stream
, "#%u", imm12
);
3559 value_in_comment
= imm12
;
3565 unsigned int bits
= 0, imm
, imm8
, mod
;
3567 bits
|= (given
& 0x000000ffu
);
3568 bits
|= (given
& 0x00007000u
) >> 4;
3569 bits
|= (given
& 0x04000000u
) >> 15;
3570 imm8
= (bits
& 0x0ff);
3571 mod
= (bits
& 0xf00) >> 8;
3574 case 0: imm
= imm8
; break;
3575 case 1: imm
= ((imm8
<< 16) | imm8
); break;
3576 case 2: imm
= ((imm8
<< 24) | (imm8
<< 8)); break;
3577 case 3: imm
= ((imm8
<< 24) | (imm8
<< 16) | (imm8
<< 8) | imm8
); break;
3579 mod
= (bits
& 0xf80) >> 7;
3580 imm8
= (bits
& 0x07f) | 0x80;
3581 imm
= (((imm8
<< (32 - mod
)) | (imm8
>> mod
)) & 0xffffffff);
3583 func (stream
, "#%u", imm
);
3584 value_in_comment
= imm
;
3590 unsigned int imm
= 0;
3592 imm
|= (given
& 0x000000ffu
);
3593 imm
|= (given
& 0x00007000u
) >> 4;
3594 imm
|= (given
& 0x04000000u
) >> 15;
3595 imm
|= (given
& 0x000f0000u
) >> 4;
3596 func (stream
, "#%u", imm
);
3597 value_in_comment
= imm
;
3603 unsigned int imm
= 0;
3605 imm
|= (given
& 0x000f0000u
) >> 16;
3606 imm
|= (given
& 0x00000ff0u
) >> 0;
3607 imm
|= (given
& 0x0000000fu
) << 12;
3608 func (stream
, "#%u", imm
);
3609 value_in_comment
= imm
;
3615 unsigned int reg
= (given
& 0x0000000fu
);
3616 unsigned int stp
= (given
& 0x00000030u
) >> 4;
3617 unsigned int imm
= 0;
3618 imm
|= (given
& 0x000000c0u
) >> 6;
3619 imm
|= (given
& 0x00007000u
) >> 10;
3621 func (stream
, "%s", arm_regnames
[reg
]);
3626 func (stream
, ", lsl #%u", imm
);
3632 func (stream
, ", lsr #%u", imm
);
3638 func (stream
, ", asr #%u", imm
);
3643 func (stream
, ", rrx");
3645 func (stream
, ", ror #%u", imm
);
3652 unsigned int Rn
= (given
& 0x000f0000) >> 16;
3653 unsigned int U
= ! NEGATIVE_BIT_SET
;
3654 unsigned int op
= (given
& 0x00000f00) >> 8;
3655 unsigned int i12
= (given
& 0x00000fff);
3656 unsigned int i8
= (given
& 0x000000ff);
3657 bfd_boolean writeback
= FALSE
, postind
= FALSE
;
3660 func (stream
, "[%s", arm_regnames
[Rn
]);
3661 if (U
) /* 12-bit positive immediate offset. */
3665 value_in_comment
= offset
;
3667 else if (Rn
== 15) /* 12-bit negative immediate offset. */
3668 offset
= - (int) i12
;
3669 else if (op
== 0x0) /* Shifted register offset. */
3671 unsigned int Rm
= (i8
& 0x0f);
3672 unsigned int sh
= (i8
& 0x30) >> 4;
3674 func (stream
, ", %s", arm_regnames
[Rm
]);
3676 func (stream
, ", lsl #%u", sh
);
3682 case 0xE: /* 8-bit positive immediate offset. */
3686 case 0xC: /* 8-bit negative immediate offset. */
3690 case 0xF: /* 8-bit + preindex with wb. */
3695 case 0xD: /* 8-bit - preindex with wb. */
3700 case 0xB: /* 8-bit + postindex. */
3705 case 0x9: /* 8-bit - postindex. */
3711 func (stream
, ", <undefined>]");
3716 func (stream
, "], #%d", offset
);
3720 func (stream
, ", #%d", offset
);
3721 func (stream
, writeback
? "]!" : "]");
3726 func (stream
, "\t; ");
3727 info
->print_address_func (((pc
+ 4) & ~3) + offset
, info
);
3735 unsigned int U
= ! NEGATIVE_BIT_SET
;
3736 unsigned int W
= WRITEBACK_BIT_SET
;
3737 unsigned int Rn
= (given
& 0x000f0000) >> 16;
3738 unsigned int off
= (given
& 0x000000ff);
3740 func (stream
, "[%s", arm_regnames
[Rn
]);
3746 func (stream
, ", #%c%u", U
? '+' : '-', off
* 4);
3747 value_in_comment
= off
* 4 * U
? 1 : -1;
3755 func (stream
, "], ");
3758 func (stream
, "#%c%u", U
? '+' : '-', off
* 4);
3759 value_in_comment
= off
* 4 * U
? 1 : -1;
3763 func (stream
, "{%u}", off
);
3764 value_in_comment
= off
;
3772 unsigned int Sbit
= (given
& 0x01000000) >> 24;
3773 unsigned int type
= (given
& 0x00600000) >> 21;
3777 case 0: func (stream
, Sbit
? "sb" : "b"); break;
3778 case 1: func (stream
, Sbit
? "sh" : "h"); break;
3781 func (stream
, "??");
3784 func (stream
, "??");
3796 for (reg
= 0; reg
< 16; reg
++)
3797 if ((given
& (1 << reg
)) != 0)
3800 func (stream
, ", ");
3802 func (stream
, "%s", arm_regnames
[reg
]);
3810 unsigned int msb
= (given
& 0x0000001f);
3811 unsigned int lsb
= 0;
3813 lsb
|= (given
& 0x000000c0u
) >> 6;
3814 lsb
|= (given
& 0x00007000u
) >> 10;
3815 func (stream
, "#%u, #%u", lsb
, msb
- lsb
+ 1);
3821 unsigned int width
= (given
& 0x0000001f) + 1;
3822 unsigned int lsb
= 0;
3824 lsb
|= (given
& 0x000000c0u
) >> 6;
3825 lsb
|= (given
& 0x00007000u
) >> 10;
3826 func (stream
, "#%u, #%u", lsb
, width
);
3832 unsigned int S
= (given
& 0x04000000u
) >> 26;
3833 unsigned int J1
= (given
& 0x00002000u
) >> 13;
3834 unsigned int J2
= (given
& 0x00000800u
) >> 11;
3840 offset
|= (given
& 0x003f0000) >> 4;
3841 offset
|= (given
& 0x000007ff) << 1;
3842 offset
-= (1 << 20);
3844 info
->print_address_func (pc
+ 4 + offset
, info
);
3850 unsigned int S
= (given
& 0x04000000u
) >> 26;
3851 unsigned int I1
= (given
& 0x00002000u
) >> 13;
3852 unsigned int I2
= (given
& 0x00000800u
) >> 11;
3856 offset
|= !(I1
^ S
) << 23;
3857 offset
|= !(I2
^ S
) << 22;
3858 offset
|= (given
& 0x03ff0000u
) >> 4;
3859 offset
|= (given
& 0x000007ffu
) << 1;
3860 offset
-= (1 << 24);
3863 /* BLX target addresses are always word aligned. */
3864 if ((given
& 0x00001000u
) == 0)
3867 info
->print_address_func (offset
, info
);
3873 unsigned int shift
= 0;
3875 shift
|= (given
& 0x000000c0u
) >> 6;
3876 shift
|= (given
& 0x00007000u
) >> 10;
3877 if (WRITEBACK_BIT_SET
)
3878 func (stream
, ", asr #%u", shift
);
3880 func (stream
, ", lsl #%u", shift
);
3881 /* else print nothing - lsl #0 */
3887 unsigned int rot
= (given
& 0x00000030) >> 4;
3890 func (stream
, ", ror #%u", rot
* 8);
3895 switch (given
& 0xf)
3897 case 0xf: func (stream
, "sy"); break;
3898 case 0x7: func (stream
, "un"); break;
3899 case 0xe: func (stream
, "st"); break;
3900 case 0x6: func (stream
, "unst"); break;
3902 func (stream
, "#%d", (int) given
& 0xf);
3908 if ((given
& 0xff) == 0)
3910 func (stream
, "%cPSR_", (given
& 0x100000) ? 'S' : 'C');
3922 func (stream
, psr_name (given
& 0xff));
3927 if ((given
& 0xff) == 0)
3928 func (stream
, "%cPSR", (given
& 0x100000) ? 'S' : 'C');
3930 func (stream
, psr_name (given
& 0xff));
3933 case '0': case '1': case '2': case '3': case '4':
3934 case '5': case '6': case '7': case '8': case '9':
3939 c
= arm_decode_bitfield (c
, given
, &val
, &width
);
3944 func (stream
, "%lu", val
);
3945 value_in_comment
= val
;
3948 func (stream
, "%lu", val
* 4);
3949 value_in_comment
= val
* 4;
3951 case 'r': func (stream
, "%s", arm_regnames
[val
]); break;
3954 func (stream
, "%s", arm_conditional
[val
]);
3959 if (val
== ((1ul << width
) - 1))
3960 func (stream
, "%c", *c
);
3966 func (stream
, "%c", *c
);
3970 func (stream
, "%c", c
[(1 << width
) - (int) val
]);
3975 func (stream
, "0x%lx", val
& 0xffffffffUL
);
3989 if (value_in_comment
> 32 || value_in_comment
< -16)
3990 func (stream
, "\t; 0x%lx", value_in_comment
);
3998 /* Print data bytes on INFO->STREAM. */
4001 print_insn_data (bfd_vma pc ATTRIBUTE_UNUSED
,
4002 struct disassemble_info
*info
,
4005 switch (info
->bytes_per_chunk
)
4008 info
->fprintf_func (info
->stream
, ".byte\t0x%02lx", given
);
4011 info
->fprintf_func (info
->stream
, ".short\t0x%04lx", given
);
4014 info
->fprintf_func (info
->stream
, ".word\t0x%08lx", given
);
4021 /* Disallow mapping symbols ($a, $b, $d, $t etc) from
4022 being displayed in symbol relative addresses. */
4025 arm_symbol_is_valid (asymbol
* sym
,
4026 struct disassemble_info
* info ATTRIBUTE_UNUSED
)
4033 name
= bfd_asymbol_name (sym
);
4035 return (name
&& *name
!= '$');
4038 /* Parse an individual disassembler option. */
4041 parse_arm_disassembler_option (char *option
)
4046 if (CONST_STRNEQ (option
, "reg-names-"))
4052 for (i
= NUM_ARM_REGNAMES
; i
--;)
4053 if (strneq (option
, regnames
[i
].name
, strlen (regnames
[i
].name
)))
4055 regname_selected
= i
;
4060 /* XXX - should break 'option' at following delimiter. */
4061 fprintf (stderr
, _("Unrecognised register name set: %s\n"), option
);
4063 else if (CONST_STRNEQ (option
, "force-thumb"))
4065 else if (CONST_STRNEQ (option
, "no-force-thumb"))
4068 /* XXX - should break 'option' at following delimiter. */
4069 fprintf (stderr
, _("Unrecognised disassembler option: %s\n"), option
);
4074 /* Parse the string of disassembler options, spliting it at whitespaces
4075 or commas. (Whitespace separators supported for backwards compatibility). */
4078 parse_disassembler_options (char *options
)
4080 if (options
== NULL
)
4085 parse_arm_disassembler_option (options
);
4087 /* Skip forward to next seperator. */
4088 while ((*options
) && (! ISSPACE (*options
)) && (*options
!= ','))
4090 /* Skip forward past seperators. */
4091 while (ISSPACE (*options
) || (*options
== ','))
4096 /* Search back through the insn stream to determine if this instruction is
4097 conditionally executed. */
4100 find_ifthen_state (bfd_vma pc
,
4101 struct disassemble_info
*info
,
4107 /* COUNT is twice the number of instructions seen. It will be odd if we
4108 just crossed an instruction boundary. */
4111 unsigned int seen_it
;
4114 ifthen_address
= pc
;
4121 /* Scan backwards looking for IT instructions, keeping track of where
4122 instruction boundaries are. We don't know if something is actually an
4123 IT instruction until we find a definite instruction boundary. */
4126 if (addr
== 0 || info
->symbol_at_address_func (addr
, info
))
4128 /* A symbol must be on an instruction boundary, and will not
4129 be within an IT block. */
4130 if (seen_it
&& (count
& 1))
4136 status
= info
->read_memory_func (addr
, (bfd_byte
*) b
, 2, info
);
4141 insn
= (b
[0]) | (b
[1] << 8);
4143 insn
= (b
[1]) | (b
[0] << 8);
4146 if ((insn
& 0xf800) < 0xe800)
4148 /* Addr + 2 is an instruction boundary. See if this matches
4149 the expected boundary based on the position of the last
4156 if ((insn
& 0xff00) == 0xbf00 && (insn
& 0xf) != 0)
4158 /* This could be an IT instruction. */
4160 it_count
= count
>> 1;
4162 if ((insn
& 0xf800) >= 0xe800)
4165 count
= (count
+ 2) | 1;
4166 /* IT blocks contain at most 4 instructions. */
4167 if (count
>= 8 && !seen_it
)
4170 /* We found an IT instruction. */
4171 ifthen_state
= (seen_it
& 0xe0) | ((seen_it
<< it_count
) & 0x1f);
4172 if ((ifthen_state
& 0xf) == 0)
4176 /* Try to infer the code type (Arm or Thumb) from a symbol.
4177 Returns nonzero if *MAP_TYPE was set. */
4180 get_sym_code_type (struct disassemble_info
*info
,
4182 enum map_type
*map_type
)
4184 elf_symbol_type
*es
;
4188 es
= *(elf_symbol_type
**)(info
->symtab
+ n
);
4189 type
= ELF_ST_TYPE (es
->internal_elf_sym
.st_info
);
4191 /* If the symbol has function type then use that. */
4192 if (type
== STT_FUNC
|| type
== STT_ARM_TFUNC
)
4194 *map_type
= (type
== STT_ARM_TFUNC
) ? MAP_THUMB
: MAP_ARM
;
4198 /* Check for mapping symbols. */
4199 name
= bfd_asymbol_name (info
->symtab
[n
]);
4200 if (name
[0] == '$' && (name
[1] == 'a' || name
[1] == 't' || name
[1] == 'd')
4201 && (name
[2] == 0 || name
[2] == '.'))
4203 *map_type
= ((name
[1] == 'a') ? MAP_ARM
4204 : (name
[1] == 't') ? MAP_THUMB
4212 /* Given a bfd_mach_arm_XXX value, this function fills in the fields
4213 of the supplied arm_feature_set structure with bitmasks indicating
4214 the support base architectures and coprocessor extensions.
4216 FIXME: This could more efficiently implemented as a constant array,
4217 although it would also be less robust. */
4220 select_arm_features (unsigned long mach
,
4221 arm_feature_set
* features
)
4224 #define ARM_FEATURE(ARCH,CEXT) \
4225 features->core = (ARCH); \
4226 features->coproc = (CEXT) | FPU_FPA; \
4231 case bfd_mach_arm_2
: ARM_ARCH_V2
;
4232 case bfd_mach_arm_2a
: ARM_ARCH_V2S
;
4233 case bfd_mach_arm_3
: ARM_ARCH_V3
;
4234 case bfd_mach_arm_3M
: ARM_ARCH_V3M
;
4235 case bfd_mach_arm_4
: ARM_ARCH_V4
;
4236 case bfd_mach_arm_4T
: ARM_ARCH_V4T
;
4237 case bfd_mach_arm_5
: ARM_ARCH_V5
;
4238 case bfd_mach_arm_5T
: ARM_ARCH_V5T
;
4239 case bfd_mach_arm_5TE
: ARM_ARCH_V5TE
;
4240 case bfd_mach_arm_XScale
: ARM_ARCH_XSCALE
;
4241 case bfd_mach_arm_ep9312
: ARM_FEATURE (ARM_AEXT_V4T
, ARM_CEXT_MAVERICK
| FPU_MAVERICK
);
4242 case bfd_mach_arm_iWMMXt
: ARM_ARCH_IWMMXT
;
4243 case bfd_mach_arm_iWMMXt2
: ARM_ARCH_IWMMXT2
;
4244 /* If the machine type is unknown allow all
4245 architecture types and all extensions. */
4246 case bfd_mach_arm_unknown
: ARM_FEATURE (-1UL, -1UL);
4253 /* NOTE: There are no checks in these routines that
4254 the relevant number of data bytes exist. */
4257 print_insn (bfd_vma pc
, struct disassemble_info
*info
, bfd_boolean little
)
4262 int is_thumb
= FALSE
;
4263 int is_data
= FALSE
;
4265 unsigned int size
= 4;
4266 void (*printer
) (bfd_vma
, struct disassemble_info
*, long);
4267 bfd_boolean found
= FALSE
;
4269 if (info
->disassembler_options
)
4271 parse_disassembler_options (info
->disassembler_options
);
4273 /* To avoid repeated parsing of these options, we remove them here. */
4274 info
->disassembler_options
= NULL
;
4277 /* PR 10288: Control which instructions will be disassembled. */
4278 if (info
->private_data
== NULL
)
4280 static arm_feature_set features
;
4282 if ((info
->flags
& USER_SPECIFIED_MACHINE_TYPE
) == 0)
4283 /* If the user did not use the -m command line switch then default to
4284 disassembling all types of ARM instruction.
4286 The info->mach value has to be ignored as this will be based on
4287 the default archictecture for the target and/or hints in the notes
4288 section, but it will never be greater than the current largest arm
4289 machine value (iWMMXt2), which is only equivalent to the V5TE
4290 architecture. ARM architectures have advanced beyond the machine
4291 value encoding, and these newer architectures would be ignored if
4292 the machine value was used.
4294 Ie the -m switch is used to restrict which instructions will be
4295 disassembled. If it is necessary to use the -m switch to tell
4296 objdump that an ARM binary is being disassembled, eg because the
4297 input is a raw binary file, but it is also desired to disassemble
4298 all ARM instructions then use "-marm". This will select the
4299 "unknown" arm architecture which is compatible with any ARM
4301 info
->mach
= bfd_mach_arm_unknown
;
4303 /* Compute the architecture bitmask from the machine number.
4304 Note: This assumes that the machine number will not change
4305 during disassembly.... */
4306 select_arm_features (info
->mach
, & features
);
4308 info
->private_data
= & features
;
4311 /* Decide if our code is going to be little-endian, despite what the
4312 function argument might say. */
4313 little_code
= ((info
->endian_code
== BFD_ENDIAN_LITTLE
) || little
);
4315 /* First check the full symtab for a mapping symbol, even if there
4316 are no usable non-mapping symbols for this address. */
4317 if (info
->symtab_size
!= 0
4318 && bfd_asymbol_flavour (*info
->symtab
) == bfd_target_elf_flavour
)
4323 enum map_type type
= MAP_ARM
;
4325 if (pc
<= last_mapping_addr
)
4326 last_mapping_sym
= -1;
4327 is_thumb
= (last_type
== MAP_THUMB
);
4329 /* Start scanning at the start of the function, or wherever
4330 we finished last time. */
4331 n
= info
->symtab_pos
+ 1;
4332 if (n
< last_mapping_sym
)
4333 n
= last_mapping_sym
;
4335 /* Scan up to the location being disassembled. */
4336 for (; n
< info
->symtab_size
; n
++)
4338 addr
= bfd_asymbol_value (info
->symtab
[n
]);
4341 if ((info
->section
== NULL
4342 || info
->section
== info
->symtab
[n
]->section
)
4343 && get_sym_code_type (info
, n
, &type
))
4352 n
= info
->symtab_pos
;
4353 if (n
< last_mapping_sym
- 1)
4354 n
= last_mapping_sym
- 1;
4356 /* No mapping symbol found at this address. Look backwards
4357 for a preceeding one. */
4360 if ((info
->section
== NULL
4361 || info
->section
== info
->symtab
[n
]->section
)
4362 && get_sym_code_type (info
, n
, &type
))
4371 last_mapping_sym
= last_sym
;
4373 is_thumb
= (last_type
== MAP_THUMB
);
4374 is_data
= (last_type
== MAP_DATA
);
4376 /* Look a little bit ahead to see if we should print out
4377 two or four bytes of data. If there's a symbol,
4378 mapping or otherwise, after two bytes then don't
4382 size
= 4 - (pc
& 3);
4383 for (n
= last_sym
+ 1; n
< info
->symtab_size
; n
++)
4385 addr
= bfd_asymbol_value (info
->symtab
[n
]);
4388 if (addr
- pc
< size
)
4393 /* If the next symbol is after three bytes, we need to
4394 print only part of the data, so that we can use either
4397 size
= (pc
& 1) ? 1 : 2;
4401 if (info
->symbols
!= NULL
)
4403 if (bfd_asymbol_flavour (*info
->symbols
) == bfd_target_coff_flavour
)
4405 coff_symbol_type
* cs
;
4407 cs
= coffsymbol (*info
->symbols
);
4408 is_thumb
= ( cs
->native
->u
.syment
.n_sclass
== C_THUMBEXT
4409 || cs
->native
->u
.syment
.n_sclass
== C_THUMBSTAT
4410 || cs
->native
->u
.syment
.n_sclass
== C_THUMBLABEL
4411 || cs
->native
->u
.syment
.n_sclass
== C_THUMBEXTFUNC
4412 || cs
->native
->u
.syment
.n_sclass
== C_THUMBSTATFUNC
);
4414 else if (bfd_asymbol_flavour (*info
->symbols
) == bfd_target_elf_flavour
4417 /* If no mapping symbol has been found then fall back to the type
4418 of the function symbol. */
4419 elf_symbol_type
* es
;
4422 es
= *(elf_symbol_type
**)(info
->symbols
);
4423 type
= ELF_ST_TYPE (es
->internal_elf_sym
.st_info
);
4425 is_thumb
= (type
== STT_ARM_TFUNC
) || (type
== STT_ARM_16BIT
);
4433 info
->display_endian
= little
? BFD_ENDIAN_LITTLE
: BFD_ENDIAN_BIG
;
4435 info
->display_endian
= little_code
? BFD_ENDIAN_LITTLE
: BFD_ENDIAN_BIG
;
4437 info
->bytes_per_line
= 4;
4439 /* PR 10263: Disassemble data if requested to do so by the user. */
4440 if (is_data
&& ((info
->flags
& DISASSEMBLE_DATA
) == 0))
4444 /* Size was already set above. */
4445 info
->bytes_per_chunk
= size
;
4446 printer
= print_insn_data
;
4448 status
= info
->read_memory_func (pc
, (bfd_byte
*) b
, size
, info
);
4451 for (i
= size
- 1; i
>= 0; i
--)
4452 given
= b
[i
] | (given
<< 8);
4454 for (i
= 0; i
< (int) size
; i
++)
4455 given
= b
[i
] | (given
<< 8);
4459 /* In ARM mode endianness is a straightforward issue: the instruction
4460 is four bytes long and is either ordered 0123 or 3210. */
4461 printer
= print_insn_arm
;
4462 info
->bytes_per_chunk
= 4;
4465 status
= info
->read_memory_func (pc
, (bfd_byte
*) b
, 4, info
);
4467 given
= (b
[0]) | (b
[1] << 8) | (b
[2] << 16) | (b
[3] << 24);
4469 given
= (b
[3]) | (b
[2] << 8) | (b
[1] << 16) | (b
[0] << 24);
4473 /* In Thumb mode we have the additional wrinkle of two
4474 instruction lengths. Fortunately, the bits that determine
4475 the length of the current instruction are always to be found
4476 in the first two bytes. */
4477 printer
= print_insn_thumb16
;
4478 info
->bytes_per_chunk
= 2;
4481 status
= info
->read_memory_func (pc
, (bfd_byte
*) b
, 2, info
);
4483 given
= (b
[0]) | (b
[1] << 8);
4485 given
= (b
[1]) | (b
[0] << 8);
4489 /* These bit patterns signal a four-byte Thumb
4491 if ((given
& 0xF800) == 0xF800
4492 || (given
& 0xF800) == 0xF000
4493 || (given
& 0xF800) == 0xE800)
4495 status
= info
->read_memory_func (pc
+ 2, (bfd_byte
*) b
, 2, info
);
4497 given
= (b
[0]) | (b
[1] << 8) | (given
<< 16);
4499 given
= (b
[1]) | (b
[0] << 8) | (given
<< 16);
4501 printer
= print_insn_thumb32
;
4506 if (ifthen_address
!= pc
)
4507 find_ifthen_state (pc
, info
, little_code
);
4511 if ((ifthen_state
& 0xf) == 0x8)
4512 ifthen_next_state
= 0;
4514 ifthen_next_state
= (ifthen_state
& 0xe0)
4515 | ((ifthen_state
& 0xf) << 1);
4521 info
->memory_error_func (status
, pc
, info
);
4524 if (info
->flags
& INSN_HAS_RELOC
)
4525 /* If the instruction has a reloc associated with it, then
4526 the offset field in the instruction will actually be the
4527 addend for the reloc. (We are using REL type relocs).
4528 In such cases, we can ignore the pc when computing
4529 addresses, since the addend is not currently pc-relative. */
4532 printer (pc
, info
, given
);
4536 ifthen_state
= ifthen_next_state
;
4537 ifthen_address
+= size
;
4543 print_insn_big_arm (bfd_vma pc
, struct disassemble_info
*info
)
4545 /* Detect BE8-ness and record it in the disassembler info. */
4546 if (info
->flavour
== bfd_target_elf_flavour
4547 && info
->section
!= NULL
4548 && (elf_elfheader (info
->section
->owner
)->e_flags
& EF_ARM_BE8
))
4549 info
->endian_code
= BFD_ENDIAN_LITTLE
;
4551 return print_insn (pc
, info
, FALSE
);
4555 print_insn_little_arm (bfd_vma pc
, struct disassemble_info
*info
)
4557 return print_insn (pc
, info
, TRUE
);
4561 print_arm_disassembler_options (FILE *stream
)
4565 fprintf (stream
, _("\n\
4566 The following ARM specific disassembler options are supported for use with\n\
4567 the -M switch:\n"));
4569 for (i
= NUM_ARM_REGNAMES
; i
--;)
4570 fprintf (stream
, " reg-names-%s %*c%s\n",
4572 (int)(14 - strlen (regnames
[i
].name
)), ' ',
4573 regnames
[i
].description
);
4575 fprintf (stream
, " force-thumb Assume all insns are Thumb insns\n");
4576 fprintf (stream
, " no-force-thumb Examine preceeding label to determine an insn's type\n\n");