Revert accidental commit of V6K ops
[deliverable/binutils-gdb.git] / opcodes / arm-dis.c
CommitLineData
252b5132 1/* Instruction printing code for the ARM
0dd132b6 2 Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004
060d22b0 3 Free Software Foundation, Inc.
252b5132
RH
4 Contributed by Richard Earnshaw (rwe@pegasus.esprit.ec.org)
5 Modification by James G. Smith (jsmith@cygnus.co.uk)
6
e16bb312 7 This file is part of libopcodes.
252b5132 8
e16bb312
NC
9 This program is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free
11 Software Foundation; either version 2 of the License, or (at your option)
12 any later version.
252b5132 13
e16bb312
NC
14 This program is distributed in the hope that it will be useful, but WITHOUT
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
17 more details.
252b5132 18
e16bb312
NC
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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
252b5132 22
cb6a5892 23#include "sysdep.h"
2fbad815 24
252b5132 25#include "dis-asm.h"
2fbad815 26#include "opcode/arm.h"
252b5132
RH
27#include "arm-opc.h"
28#include "coff/internal.h"
29#include "libcoff.h"
30#include "opintl.h"
31e0f3cd 31#include "safe-ctype.h"
252b5132 32
baf0cc5e 33/* FIXME: This shouldn't be done here. */
252b5132
RH
34#include "elf-bfd.h"
35#include "elf/internal.h"
36#include "elf/arm.h"
37
01c7f630 38#ifndef streq
58efb6c0 39#define streq(a,b) (strcmp ((a), (b)) == 0)
01c7f630 40#endif
58efb6c0 41
01c7f630 42#ifndef strneq
58efb6c0
NC
43#define strneq(a,b,n) (strncmp ((a), (b), (n)) == 0)
44#endif
45
46#ifndef NUM_ELEM
47#define NUM_ELEM(a) (sizeof (a) / sizeof (a)[0])
01c7f630
NC
48#endif
49
b7693d02
DJ
50#define WORD_ADDRESS(pc) ((pc) & ~0x3)
51
6255809c 52/* Format of the disassembler control string :
2fbad815
RE
53
54 %% %
55 %<bitfield>d print the bitfield in decimal
56 %<bitfield>x print the bitfield in hex
57 %<bitfield>X print the bitfield as 1 hex digit without leading "0x"
58 %<bitfield>W print the bitfield plus one in decimal
59 %<bitfield>r print as an ARM register
60 %<bitfield>f print a floating point constant if >7 else a
61 floating point register
62 %<code>y print a single precision VFP reg.
63 Codes: 0=>Sm, 1=>Sd, 2=>Sn, 3=>multi-list, 4=>Sm pair
64 %<code>z print a double precision VFP reg
65 Codes: 0=>Dm, 1=>Dd, 2=>Dn, 3=>multi-list
66 %c print condition code (always bits 28-31)
67 %P print floating point precision in arithmetic insn
68 %Q print floating point precision in ldf/stf insn
69 %R print floating point rounding mode
70 %<bitnum>'c print specified char iff bit is one
71 %<bitnum>`c print specified char iff bit is zero
72 %<bitnum>?ab print a if bit is one else print b
73 %p print 'p' iff bits 12-15 are 15
74 %t print 't' iff bit 21 set and bit 24 clear
75 %o print operand2 (immediate or register + shift)
76 %a print address for ldr/str instruction
77 %s print address for ldr/str halfword/signextend instruction
78 %b print branch destination
79 %B print arm BLX(1) destination
80 %A print address for ldc/stc/ldf/stf instruction
81 %m print register mask for ldm/stm instruction
82 %C print the PSR sub type.
83 %F print the COUNT field of a LFM/SFM instruction.
0a003adc
ZW
84 %E print the LSB and WIDTH fields of a BFI or BFC instruction.
85 %V print the 16-bit immediate field of a MOVT or MOVW instruction.
2fbad815
RE
86IWMMXT specific format options:
87 %<bitfield>g print as an iWMMXt 64-bit register
88 %<bitfield>G print as an iWMMXt general purpose or control register
89 %<bitfield>w print as an iWMMXt width field - [bhwd]ss/us
90 %Z print the Immediate of a WSHUFH instruction.
91 %L print as an iWMMXt N/M width field.
92 %l like 'A' except use byte offsets for 'B' & 'H' versions
93Thumb specific format options:
94 %D print Thumb register (bits 0..2 as high number if bit 7 set)
95 %S print Thumb register (bits 3..5 as high number if bit 6 set)
96 %<bitfield>I print bitfield as a signed decimal
97 (top bit of range being the sign bit)
98 %M print Thumb register mask
99 %N print Thumb register mask (with LR)
100 %O print Thumb register mask (with PC)
101 %T print Thumb condition code (always bits 8-11)
102 %I print cirrus signed shift immediate: bits 0..3|4..6
103 %<bitfield>B print Thumb branch destination (signed displacement)
104 %<bitfield>W print (bitfield * 4) as a decimal
105 %<bitfield>H print (bitfield * 2) as a decimal
106 %<bitfield>a print (bitfield * 4) as a pc-rel offset + decoded symbol
107 %e print arm SMI operand (bits 0..7,8..19). */
108
109/* Note: There is a partial ordering in this table - it must be searched from
110 the top to obtain a correct match. */
111
112static const struct arm_opcode arm_opcodes[] =
113{
114 /* ARM instructions. */
115 {ARM_EXT_V1, 0xe1a00000, 0xffffffff, "nop\t\t\t(mov r0,r0)"},
116 {ARM_EXT_V4T | ARM_EXT_V5, 0x012FFF10, 0x0ffffff0, "bx%c\t%0-3r"},
117 {ARM_EXT_V2, 0x00000090, 0x0fe000f0, "mul%c%20's\t%16-19r, %0-3r, %8-11r"},
118 {ARM_EXT_V2, 0x00200090, 0x0fe000f0, "mla%c%20's\t%16-19r, %0-3r, %8-11r, %12-15r"},
119 {ARM_EXT_V2S, 0x01000090, 0x0fb00ff0, "swp%c%22'b\t%12-15r, %0-3r, [%16-19r]"},
120 {ARM_EXT_V3M, 0x00800090, 0x0fa000f0, "%22?sumull%c%20's\t%12-15r, %16-19r, %0-3r, %8-11r"},
121 {ARM_EXT_V3M, 0x00a00090, 0x0fa000f0, "%22?sumlal%c%20's\t%12-15r, %16-19r, %0-3r, %8-11r"},
122
0a003adc
ZW
123 /* ARM V6T2 instructions. */
124 {ARM_EXT_V6T2, 0x07c0001f, 0x0fe0007f, "bfc%c\t%12-15r, %E"},
125 {ARM_EXT_V6T2, 0x07c00010, 0x0fe00070, "bfi%c\t%12-15r, %0-3r, %E"},
126 {ARM_EXT_V6T2, 0x00600090, 0x0ff000f0, "mls%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
127 {ARM_EXT_V6T2, 0x006000b0, 0x0f7000f0, "str%cht\t%12-15r, %s"},
128 {ARM_EXT_V6T2, 0x00300090, 0x0f300090, "ldr%c%6's%5?hbt\t%12-15r, %s"},
129 {ARM_EXT_V6T2, 0x03000000, 0x0ff00000, "movw%c\t%12-15r, %V"},
130 {ARM_EXT_V6T2, 0x03400000, 0x0ff00000, "movt%c\t%12-15r, %V"},
131 {ARM_EXT_V6T2, 0x03ff0f30, 0x0fff0ff0, "rbit%c\t%12-15r, %0-3r"},
132 {ARM_EXT_V6T2, 0x07a00050, 0x0fa00070, "%22?usbfx%c\t%12-15r, %0-3r, #%7-11d, #%16-20W"},
133
2fbad815
RE
134 /* ARM V6Z instructions. */
135 {ARM_EXT_V6Z, 0x01600070, 0x0ff000f0, "smi%c\t%e"},
136
137 /* ARM V6K instructions. */
138 {ARM_EXT_V6K, 0xf57ff01f, 0xffffffff, "clrex"},
139 {ARM_EXT_V6K, 0x01d00f9f, 0x0ff00fff, "ldrexb%c\t%12-15r, [%16-19r]"},
140 {ARM_EXT_V6K, 0x01b00f9f, 0x0ff00fff, "ldrexd%c\t%12-15r, [%16-19r]"},
141 {ARM_EXT_V6K, 0x01f00f9f, 0x0ff00fff, "ldrexh%c\t%12-15r, [%16-19r]"},
142 {ARM_EXT_V6K, 0x01c00f90, 0x0ff00ff0, "strexb%c\t%12-15r, %0-3r, [%16-19r]"},
143 {ARM_EXT_V6K, 0x01a00f90, 0x0ff00ff0, "strexd%c\t%12-15r, %0-3r, [%16-19r]"},
144 {ARM_EXT_V6K, 0x01e00f90, 0x0ff00ff0, "strexh%c\t%12-15r, %0-3r, [%16-19r]"},
145
146 /* ARM V6K NOP hints. */
147 {ARM_EXT_V6K, 0x0320f001, 0x0fffffff, "yield%c"},
148 {ARM_EXT_V6K, 0x0320f002, 0x0fffffff, "wfe%c"},
149 {ARM_EXT_V6K, 0x0320f003, 0x0fffffff, "wfi%c"},
150 {ARM_EXT_V6K, 0x0320f004, 0x0fffffff, "sev%c"},
151 {ARM_EXT_V6K, 0x0320f000, 0x0fffff00, "nop%c\t{%0-7d}"},
152
153 /* ARM V6 instructions. */
154 {ARM_EXT_V6, 0xfc500000, 0xfff00000, "mrrc2\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
155 {ARM_EXT_V6, 0xfc400000, 0xfff00000, "mcrr2\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
156 {ARM_EXT_V6, 0xf1080000, 0xfffdfe3f, "cpsie\t%8'a%7'i%6'f"},
157 {ARM_EXT_V6, 0xf1080000, 0xfffdfe20, "cpsie\t%8'a%7'i%6'f,#%0-4d"},
158 {ARM_EXT_V6, 0xf10C0000, 0xfffdfe3f, "cpsid\t%8'a%7'i%6'f"},
159 {ARM_EXT_V6, 0xf10C0000, 0xfffdfe20, "cpsid\t%8'a%7'i%6'f,#%0-4d"},
160 {ARM_EXT_V6, 0xf1000000, 0xfff1fe20, "cps\t#%0-4d"},
161 {ARM_EXT_V6, 0x06800010, 0x0ff00ff0, "pkhbt%c\t%12-15r, %16-19r, %0-3r"},
162 {ARM_EXT_V6, 0x06800010, 0x0ff00070, "pkhbt%c\t%12-15r, %16-19r, %0-3r, LSL #%7-11d"},
163 {ARM_EXT_V6, 0x06800050, 0x0ff00ff0, "pkhtb%c\t%12-15r, %16-19r, %0-3r, ASR #32"},
164 {ARM_EXT_V6, 0x06800050, 0x0ff00070, "pkhtb%c\t%12-15r, %16-19r, %0-3r, ASR #%7-11d"},
165 {ARM_EXT_V6, 0x01900f9f, 0x0ff00fff, "ldrex%c\tr%12-15d, [%16-19r]"},
166 {ARM_EXT_V6, 0x06200f10, 0x0ff00ff0, "qadd16%c\t%12-15r, %16-19r, %0-3r"},
167 {ARM_EXT_V6, 0x06200f90, 0x0ff00ff0, "qadd8%c\t%12-15r, %16-19r, %0-3r"},
168 {ARM_EXT_V6, 0x06200f30, 0x0ff00ff0, "qaddsubx%c\t%12-15r, %16-19r, %0-3r"},
169 {ARM_EXT_V6, 0x06200f70, 0x0ff00ff0, "qsub16%c\t%12-15r, %16-19r, %0-3r"},
170 {ARM_EXT_V6, 0x06200ff0, 0x0ff00ff0, "qsub8%c\t%12-15r, %16-19r, %0-3r"},
171 {ARM_EXT_V6, 0x06200f50, 0x0ff00ff0, "qsubaddx%c\t%12-15r, %16-19r, %0-3r"},
172 {ARM_EXT_V6, 0x06100f10, 0x0ff00ff0, "sadd16%c\t%12-15r, %16-19r, %0-3r"},
173 {ARM_EXT_V6, 0x06100f90, 0x0ff00ff0, "sadd8%c\t%12-15r, %16-19r, %0-3r"},
174 {ARM_EXT_V6, 0x06100f30, 0x0ff00ff0, "saddaddx%c\t%12-15r, %16-19r, %0-3r"},
175 {ARM_EXT_V6, 0x06300f10, 0x0ff00ff0, "shadd16%c\t%12-15r, %16-19r, %0-3r"},
176 {ARM_EXT_V6, 0x06300f90, 0x0ff00ff0, "shadd8%c\t%12-15r, %16-19r, %0-3r"},
177 {ARM_EXT_V6, 0x06300f30, 0x0ff00ff0, "shaddsubx%c\t%12-15r, %16-19r, %0-3r"},
178 {ARM_EXT_V6, 0x06300f70, 0x0ff00ff0, "shsub16%c\t%12-15r, %16-19r, %0-3r"},
179 {ARM_EXT_V6, 0x06300ff0, 0x0ff00ff0, "shsub8%c\t%12-15r, %16-19r, %0-3r"},
180 {ARM_EXT_V6, 0x06300f50, 0x0ff00ff0, "shsubaddx%c\t%12-15r, %16-19r, %0-3r"},
181 {ARM_EXT_V6, 0x06100f70, 0x0ff00ff0, "ssub16%c\t%12-15r, %16-19r, %0-3r"},
182 {ARM_EXT_V6, 0x06100ff0, 0x0ff00ff0, "ssub8%c\t%12-15r, %16-19r, %0-3r"},
183 {ARM_EXT_V6, 0x06100f50, 0x0ff00ff0, "ssubaddx%c\t%12-15r, %16-19r, %0-3r"},
184 {ARM_EXT_V6, 0x06500f10, 0x0ff00ff0, "uadd16%c\t%12-15r, %16-19r, %0-3r"},
185 {ARM_EXT_V6, 0x06500f90, 0x0ff00ff0, "uadd8%c\t%12-15r, %16-19r, %0-3r"},
186 {ARM_EXT_V6, 0x06500f30, 0x0ff00ff0, "uaddsubx%c\t%12-15r, %16-19r, %0-3r"},
187 {ARM_EXT_V6, 0x06700f10, 0x0ff00ff0, "uhadd16%c\t%12-15r, %16-19r, %0-3r"},
188 {ARM_EXT_V6, 0x06700f90, 0x0ff00ff0, "uhadd8%c\t%12-15r, %16-19r, %0-3r"},
189 {ARM_EXT_V6, 0x06700f30, 0x0ff00ff0, "uhaddsubx%c\t%12-15r, %16-19r, %0-3r"},
190 {ARM_EXT_V6, 0x06700f70, 0x0ff00ff0, "uhsub16%c\t%12-15r, %16-19r, %0-3r"},
191 {ARM_EXT_V6, 0x06700ff0, 0x0ff00ff0, "uhsub8%c\t%12-15r, %16-19r, %0-3r"},
192 {ARM_EXT_V6, 0x06700f50, 0x0ff00ff0, "uhsubaddx%c\t%12-15r, %16-19r, %0-3r"},
193 {ARM_EXT_V6, 0x06600f10, 0x0ff00ff0, "uqadd16%c\t%12-15r, %16-19r, %0-3r"},
194 {ARM_EXT_V6, 0x06600f90, 0x0ff00ff0, "uqadd8%c\t%12-15r, %16-19r, %0-3r"},
195 {ARM_EXT_V6, 0x06600f30, 0x0ff00ff0, "uqaddsubx%c\t%12-15r, %16-19r, %0-3r"},
196 {ARM_EXT_V6, 0x06600f70, 0x0ff00ff0, "uqsub16%c\t%12-15r, %16-19r, %0-3r"},
197 {ARM_EXT_V6, 0x06600ff0, 0x0ff00ff0, "uqsub8%c\t%12-15r, %16-19r, %0-3r"},
198 {ARM_EXT_V6, 0x06600f50, 0x0ff00ff0, "uqsubaddx%c\t%12-15r, %16-19r, %0-3r"},
199 {ARM_EXT_V6, 0x06500f70, 0x0ff00ff0, "usub16%c\t%12-15r, %16-19r, %0-3r"},
200 {ARM_EXT_V6, 0x06500ff0, 0x0ff00ff0, "usub8%c\t%12-15r, %16-19r, %0-3r"},
201 {ARM_EXT_V6, 0x06500f50, 0x0ff00ff0, "usubaddx%c\t%12-15r, %16-19r, %0-3r"},
202 {ARM_EXT_V6, 0x06bf0f30, 0x0fff0ff0, "rev%c\t\%12-15r, %0-3r"},
203 {ARM_EXT_V6, 0x06bf0fb0, 0x0fff0ff0, "rev16%c\t\%12-15r, %0-3r"},
204 {ARM_EXT_V6, 0x06ff0fb0, 0x0fff0ff0, "revsh%c\t\%12-15r, %0-3r"},
205 {ARM_EXT_V6, 0xf8100a00, 0xfe50ffff, "rfe%23?id%24?ba\t\%16-19r%21'!"},
206 {ARM_EXT_V6, 0x06bf0070, 0x0fff0ff0, "sxth%c %12-15r,%0-3r"},
207 {ARM_EXT_V6, 0x06bf0470, 0x0fff0ff0, "sxth%c %12-15r,%0-3r, ROR #8"},
208 {ARM_EXT_V6, 0x06bf0870, 0x0fff0ff0, "sxth%c %12-15r,%0-3r, ROR #16"},
209 {ARM_EXT_V6, 0x06bf0c70, 0x0fff0ff0, "sxth%c %12-15r,%0-3r, ROR #24"},
210 {ARM_EXT_V6, 0x068f0070, 0x0fff0ff0, "sxtb16%c %12-15r,%0-3r"},
211 {ARM_EXT_V6, 0x068f0470, 0x0fff0ff0, "sxtb16%c %12-15r,%0-3r, ROR #8"},
212 {ARM_EXT_V6, 0x068f0870, 0x0fff0ff0, "sxtb16%c %12-15r,%0-3r, ROR #16"},
213 {ARM_EXT_V6, 0x068f0c70, 0x0fff0ff0, "sxtb16%c %12-15r,%0-3r, ROR #24"},
214 {ARM_EXT_V6, 0x06af0070, 0x0fff0ff0, "sxtb%c %12-15r,%0-3r"},
215 {ARM_EXT_V6, 0x06af0470, 0x0fff0ff0, "sxtb%c %12-15r,%0-3r, ROR #8"},
216 {ARM_EXT_V6, 0x06af0870, 0x0fff0ff0, "sxtb%c %12-15r,%0-3r, ROR #16"},
217 {ARM_EXT_V6, 0x06af0c70, 0x0fff0ff0, "sxtb%c %12-15r,%0-3r, ROR #24"},
218 {ARM_EXT_V6, 0x06ff0070, 0x0fff0ff0, "uxth%c %12-15r,%0-3r"},
219 {ARM_EXT_V6, 0x06ff0470, 0x0fff0ff0, "uxth%c %12-15r,%0-3r, ROR #8"},
220 {ARM_EXT_V6, 0x06ff0870, 0x0fff0ff0, "uxth%c %12-15r,%0-3r, ROR #16"},
221 {ARM_EXT_V6, 0x06ff0c70, 0x0fff0ff0, "uxth%c %12-15r,%0-3r, ROR #24"},
222 {ARM_EXT_V6, 0x06cf0070, 0x0fff0ff0, "uxtb16%c %12-15r,%0-3r"},
223 {ARM_EXT_V6, 0x06cf0470, 0x0fff0ff0, "uxtb16%c %12-15r,%0-3r, ROR #8"},
224 {ARM_EXT_V6, 0x06cf0870, 0x0fff0ff0, "uxtb16%c %12-15r,%0-3r, ROR #16"},
225 {ARM_EXT_V6, 0x06cf0c70, 0x0fff0ff0, "uxtb16%c %12-15r,%0-3r, ROR #24"},
226 {ARM_EXT_V6, 0x06ef0070, 0x0fff0ff0, "uxtb%c %12-15r,%0-3r"},
227 {ARM_EXT_V6, 0x06ef0470, 0x0fff0ff0, "uxtb%c %12-15r,%0-3r, ROR #8"},
228 {ARM_EXT_V6, 0x06ef0870, 0x0fff0ff0, "uxtb%c %12-15r,%0-3r, ROR #16"},
229 {ARM_EXT_V6, 0x06ef0c70, 0x0fff0ff0, "uxtb%c %12-15r,%0-3r, ROR #24"},
230 {ARM_EXT_V6, 0x06b00070, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r"},
231 {ARM_EXT_V6, 0x06b00470, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ROR #8"},
232 {ARM_EXT_V6, 0x06b00870, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ROR #16"},
233 {ARM_EXT_V6, 0x06b00c70, 0x0ff00ff0, "sxtah%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
234 {ARM_EXT_V6, 0x06800070, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r"},
235 {ARM_EXT_V6, 0x06800470, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #8"},
236 {ARM_EXT_V6, 0x06800870, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #16"},
237 {ARM_EXT_V6, 0x06800c70, 0x0ff00ff0, "sxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
238 {ARM_EXT_V6, 0x06a00070, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r"},
239 {ARM_EXT_V6, 0x06a00470, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ROR #8"},
240 {ARM_EXT_V6, 0x06a00870, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ROR #16"},
241 {ARM_EXT_V6, 0x06a00c70, 0x0ff00ff0, "sxtab%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
242 {ARM_EXT_V6, 0x06f00070, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r"},
243 {ARM_EXT_V6, 0x06f00470, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ROR #8"},
244 {ARM_EXT_V6, 0x06f00870, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ROR #16"},
245 {ARM_EXT_V6, 0x06f00c70, 0x0ff00ff0, "uxtah%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
246 {ARM_EXT_V6, 0x06c00070, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r"},
247 {ARM_EXT_V6, 0x06c00470, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #8"},
248 {ARM_EXT_V6, 0x06c00870, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #16"},
249 {ARM_EXT_V6, 0x06c00c70, 0x0ff00ff0, "uxtab16%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
250 {ARM_EXT_V6, 0x06e00070, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r"},
251 {ARM_EXT_V6, 0x06e00470, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ROR #8"},
252 {ARM_EXT_V6, 0x06e00870, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ROR #16"},
253 {ARM_EXT_V6, 0x06e00c70, 0x0ff00ff0, "uxtab%c\t%12-15r, %16-19r, %0-3r, ROR #24"},
254 {ARM_EXT_V6, 0x068000b0, 0x0ff00ff0, "sel%c\t%12-15r, %16-19r, %0-3r"},
255 {ARM_EXT_V6, 0xf1010000, 0xfffffc00, "setend\t%9?ble"},
256 {ARM_EXT_V6, 0x0700f010, 0x0ff0f0d0, "smuad%5'x%c\t%16-19r, %0-3r, %8-11r"},
257 {ARM_EXT_V6, 0x0700f050, 0x0ff0f0d0, "smusd%5'x%c\t%16-19r, %0-3r, %8-11r"},
258 {ARM_EXT_V6, 0x07000010, 0x0ff000d0, "smlad%5'x%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
259 {ARM_EXT_V6, 0x07400010, 0x0ff000d0, "smlald%5'x%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
260 {ARM_EXT_V6, 0x07000050, 0x0ff000d0, "smlsd%5'x%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
261 {ARM_EXT_V6, 0x07400050, 0x0ff000d0, "smlsld%5'x%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
262 {ARM_EXT_V6, 0x0750f010, 0x0ff0f0d0, "smmul%5'r%c\t%16-19r, %0-3r, %8-11r"},
263 {ARM_EXT_V6, 0x07500010, 0x0ff000d0, "smmla%5'r%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
264 {ARM_EXT_V6, 0x075000d0, 0x0ff000d0, "smmls%5'r%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
265 {ARM_EXT_V6, 0xf84d0500, 0xfe5fffe0, "srs%23?id%24?ba\t#%0-4d%21'!"},
266 {ARM_EXT_V6, 0x06a00010, 0x0fe00ff0, "ssat%c\t%12-15r, #%16-20W, %0-3r"},
267 {ARM_EXT_V6, 0x06a00010, 0x0fe00070, "ssat%c\t%12-15r, #%16-20W, %0-3r, LSL #%7-11d"},
268 {ARM_EXT_V6, 0x06a00050, 0x0fe00070, "ssat%c\t%12-15r, #%16-20W, %0-3r, ASR #%7-11d"},
269 {ARM_EXT_V6, 0x06a00f30, 0x0ff00ff0, "ssat16%c\t%12-15r, #%16-19W, %0-3r"},
270 {ARM_EXT_V6, 0x01800f90, 0x0ff00ff0, "strex%c\t%12-15r, %0-3r, [%16-19r]"},
271 {ARM_EXT_V6, 0x00400090, 0x0ff000f0, "umaal%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
272 {ARM_EXT_V6, 0x0780f010, 0x0ff0f0f0, "usad8%c\t%16-19r, %0-3r, %8-11r"},
273 {ARM_EXT_V6, 0x07800010, 0x0ff000f0, "usada8%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
274 {ARM_EXT_V6, 0x06e00010, 0x0fe00ff0, "usat%c\t%12-15r, #%16-20d, %0-3r"},
275 {ARM_EXT_V6, 0x06e00010, 0x0fe00070, "usat%c\t%12-15r, #%16-20d, %0-3r, LSL #%7-11d"},
276 {ARM_EXT_V6, 0x06e00050, 0x0fe00070, "usat%c\t%12-15r, #%16-20d, %0-3r, ASR #%7-11d"},
277 {ARM_EXT_V6, 0x06e00f30, 0x0ff00ff0, "usat16%c\t%12-15r, #%16-19d, %0-3r"},
278
279 /* V5J instruction. */
280 {ARM_EXT_V5J, 0x012fff20, 0x0ffffff0, "bxj%c\t%0-3r"},
281
282 /* XScale instructions. */
283 {ARM_CEXT_XSCALE, 0x0e200010, 0x0fff0ff0, "mia%c\tacc0, %0-3r, %12-15r"},
284 {ARM_CEXT_XSCALE, 0x0e280010, 0x0fff0ff0, "miaph%c\tacc0, %0-3r, %12-15r"},
285 {ARM_CEXT_XSCALE, 0x0e2c0010, 0x0ffc0ff0, "mia%17'T%17`B%16'T%16`B%c\tacc0, %0-3r, %12-15r"},
286 {ARM_CEXT_XSCALE, 0x0c400000, 0x0ff00fff, "mar%c\tacc0, %12-15r, %16-19r"},
287 {ARM_CEXT_XSCALE, 0x0c500000, 0x0ff00fff, "mra%c\t%12-15r, %16-19r, acc0"},
288
289 /* Intel Wireless MMX technology instructions. */
290#define FIRST_IWMMXT_INSN 0x0e130130
291#define IWMMXT_INSN_COUNT 47
292 {ARM_CEXT_IWMMXT, 0x0e130130, 0x0f3f0fff, "tandc%22-23w%c\t%12-15r"},
293 {ARM_CEXT_XSCALE, 0x0e400010, 0x0ff00f3f, "tbcst%6-7w%c\t%16-19g, %12-15r"},
294 {ARM_CEXT_XSCALE, 0x0e130170, 0x0f3f0ff8, "textrc%22-23w%c\t%12-15r, #%0-2d"},
295 {ARM_CEXT_XSCALE, 0x0e100070, 0x0f300ff0, "textrm%3?su%22-23w%c\t%12-15r, %16-19g, #%0-2d"},
296 {ARM_CEXT_XSCALE, 0x0e600010, 0x0ff00f38, "tinsr%6-7w%c\t%16-19g, %12-15r, #%0-2d"},
297 {ARM_CEXT_XSCALE, 0x0e000110, 0x0ff00fff, "tmcr%c\t%16-19G, %12-15r"},
298 {ARM_CEXT_XSCALE, 0x0c400000, 0x0ff00ff0, "tmcrr%c\t%0-3g, %12-15r, %16-19r"},
299 {ARM_CEXT_XSCALE, 0x0e2c0010, 0x0ffc0e10, "tmia%17?tb%16?tb%c\t%5-8g, %0-3r, %12-15r"},
300 {ARM_CEXT_XSCALE, 0x0e200010, 0x0fff0e10, "tmia%c\t%5-8g, %0-3r, %12-15r"},
301 {ARM_CEXT_XSCALE, 0x0e280010, 0x0fff0e10, "tmiaph%c\t%5-8g, %0-3r, %12-15r"},
302 {ARM_CEXT_XSCALE, 0x0e100030, 0x0f300fff, "tmovmsk%22-23w%c\t%12-15r, %16-19g"},
303 {ARM_CEXT_XSCALE, 0x0e100110, 0x0ff00ff0, "tmrc%c\t%12-15r, %16-19G"},
304 {ARM_CEXT_XSCALE, 0x0c500000, 0x0ff00ff0, "tmrrc%c\t%12-15r, %16-19r, %0-3g"},
305 {ARM_CEXT_XSCALE, 0x0e130150, 0x0f3f0fff, "torc%22-23w%c\t%12-15r"},
306 {ARM_CEXT_XSCALE, 0x0e0001c0, 0x0f300fff, "wacc%22-23w%c\t%12-15g, %16-19g"},
307 {ARM_CEXT_XSCALE, 0x0e000180, 0x0f000ff0, "wadd%20-23w%c\t%12-15g, %16-19g, %0-3g"},
308 {ARM_CEXT_XSCALE, 0x0e000020, 0x0f800ff0, "waligni%c\t%12-15g, %16-19g, %0-3g, #%20-22d"},
309 {ARM_CEXT_XSCALE, 0x0e800020, 0x0fc00ff0, "walignr%20-21d%c\t%12-15g, %16-19g, %0-3g"},
310 {ARM_CEXT_XSCALE, 0x0e200000, 0x0fe00ff0, "wand%20'n%c\t%12-15g, %16-19g, %0-3g"},
311 {ARM_CEXT_XSCALE, 0x0e800000, 0x0fa00ff0, "wavg2%22?hb%20'r%c\t%12-15g, %16-19g, %0-3g"},
312 {ARM_CEXT_XSCALE, 0x0e000060, 0x0f300ff0, "wcmpeq%22-23w%c\t%12-15g, %16-19g, %0-3g"},
313 {ARM_CEXT_XSCALE, 0x0e100060, 0x0f100ff0, "wcmpgt%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
314 {ARM_CEXT_XSCALE, 0xfc100100, 0xfe500f00, "wldrw\t%12-15G, %A"},
315 {ARM_CEXT_XSCALE, 0x0c100000, 0x0e100e00, "wldr%L%c\t%12-15g, %l"},
316 {ARM_CEXT_XSCALE, 0x0e400100, 0x0fc00ff0, "wmac%21?su%20'z%c\t%12-15g, %16-19g, %0-3g"},
317 {ARM_CEXT_XSCALE, 0x0e800100, 0x0fd00ff0, "wmadd%21?su%c\t%12-15g, %16-19g, %0-3g"},
318 {ARM_CEXT_XSCALE, 0x0e000160, 0x0f100ff0, "wmax%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
319 {ARM_CEXT_XSCALE, 0x0e100160, 0x0f100ff0, "wmin%21?su%22-23w%c\t%12-15g, %16-19g, %0-3g"},
320 {ARM_CEXT_XSCALE, 0x0e000100, 0x0fc00ff0, "wmul%21?su%20?ml%c\t%12-15g, %16-19g, %0-3g"},
321 {ARM_CEXT_XSCALE, 0x0e000000, 0x0ff00ff0, "wor%c\t%12-15g, %16-19g, %0-3g"},
322 {ARM_CEXT_XSCALE, 0x0e000080, 0x0f000ff0, "wpack%20-23w%c\t%12-15g, %16-19g, %0-3g"},
323 {ARM_CEXT_XSCALE, 0x0e300040, 0x0f300ff0, "wror%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
324 {ARM_CEXT_XSCALE, 0x0e300148, 0x0f300ffc, "wror%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
325 {ARM_CEXT_XSCALE, 0x0e000120, 0x0fa00ff0, "wsad%22?hb%20'z%c\t%12-15g, %16-19g, %0-3g"},
326 {ARM_CEXT_XSCALE, 0x0e0001e0, 0x0f000ff0, "wshufh%c\t%12-15g, %16-19g, #%Z"},
327 {ARM_CEXT_XSCALE, 0x0e100040, 0x0f300ff0, "wsll%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
328 {ARM_CEXT_XSCALE, 0x0e100148, 0x0f300ffc, "wsll%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
329 {ARM_CEXT_XSCALE, 0x0e000040, 0x0f300ff0, "wsra%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
330 {ARM_CEXT_XSCALE, 0x0e000148, 0x0f300ffc, "wsra%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
331 {ARM_CEXT_XSCALE, 0x0e200040, 0x0f300ff0, "wsrl%22-23w%8'g%c\t%12-15g, %16-19g, %0-3g"},
332 {ARM_CEXT_XSCALE, 0x0e200148, 0x0f300ffc, "wsrl%22-23w%8'g%c\t%12-15g, %16-19g, %0-3G"},
333 {ARM_CEXT_XSCALE, 0xfc000100, 0xfe500f00, "wstrw\t%12-15G, %A"},
334 {ARM_CEXT_XSCALE, 0x0c000000, 0x0e100e00, "wstr%L%c\t%12-15g, %l"},
335 {ARM_CEXT_XSCALE, 0x0e0001a0, 0x0f000ff0, "wsub%20-23w%c\t%12-15g, %16-19g, %0-3g"},
336 {ARM_CEXT_XSCALE, 0x0e0000c0, 0x0f100fff, "wunpckeh%21?su%22-23w%c\t%12-15g, %16-19g"},
337 {ARM_CEXT_XSCALE, 0x0e0000e0, 0x0f100fff, "wunpckel%21?su%22-23w%c\t%12-15g, %16-19g"},
338 {ARM_CEXT_XSCALE, 0x0e1000c0, 0x0f300ff0, "wunpckih%22-23w%c\t%12-15g, %16-19g, %0-3g"},
339 {ARM_CEXT_XSCALE, 0x0e1000e0, 0x0f300ff0, "wunpckil%22-23w%c\t%12-15g, %16-19g, %0-3g"},
340 {ARM_CEXT_XSCALE, 0x0e100000, 0x0ff00ff0, "wxor%c\t%12-15g, %16-19g, %0-3g"},
341
342 /* V5 Instructions. */
343 {ARM_EXT_V5, 0xe1200070, 0xfff000f0, "bkpt\t0x%16-19X%12-15X%8-11X%0-3X"},
344 {ARM_EXT_V5, 0xfa000000, 0xfe000000, "blx\t%B"},
345 {ARM_EXT_V5, 0x012fff30, 0x0ffffff0, "blx%c\t%0-3r"},
346 {ARM_EXT_V5, 0x016f0f10, 0x0fff0ff0, "clz%c\t%12-15r, %0-3r"},
347 {ARM_EXT_V5, 0xfc100000, 0xfe100000, "ldc2%22'l\t%8-11d, cr%12-15d, %A"},
348 {ARM_EXT_V5, 0xfc000000, 0xfe100000, "stc2%22'l\t%8-11d, cr%12-15d, %A"},
349 {ARM_EXT_V5, 0xfe000000, 0xff000010, "cdp2\t%8-11d, %20-23d, cr%12-15d, cr%16-19d, cr%0-3d, {%5-7d}"},
350 {ARM_EXT_V5, 0xfe000010, 0xff100010, "mcr2\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
351 {ARM_EXT_V5, 0xfe100010, 0xff100010, "mrc2\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
352
353 /* V5E "El Segundo" Instructions. */
354 {ARM_EXT_V5E, 0x000000d0, 0x0e1000f0, "ldr%cd\t%12-15r, %s"},
355 {ARM_EXT_V5E, 0x000000f0, 0x0e1000f0, "str%cd\t%12-15r, %s"},
356 {ARM_EXT_V5E, 0xf450f000, 0xfc70f000, "pld\t%a"},
357 {ARM_EXT_V5ExP, 0x01000080, 0x0ff000f0, "smlabb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
358 {ARM_EXT_V5ExP, 0x010000a0, 0x0ff000f0, "smlatb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
359 {ARM_EXT_V5ExP, 0x010000c0, 0x0ff000f0, "smlabt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
360 {ARM_EXT_V5ExP, 0x010000e0, 0x0ff000f0, "smlatt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
361
362 {ARM_EXT_V5ExP, 0x01200080, 0x0ff000f0, "smlawb%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
363 {ARM_EXT_V5ExP, 0x012000c0, 0x0ff000f0, "smlawt%c\t%16-19r, %0-3r, %8-11r, %12-15r"},
364
365 {ARM_EXT_V5ExP, 0x01400080, 0x0ff000f0, "smlalbb%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
366 {ARM_EXT_V5ExP, 0x014000a0, 0x0ff000f0, "smlaltb%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
367 {ARM_EXT_V5ExP, 0x014000c0, 0x0ff000f0, "smlalbt%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
368 {ARM_EXT_V5ExP, 0x014000e0, 0x0ff000f0, "smlaltt%c\t%12-15r, %16-19r, %0-3r, %8-11r"},
369
370 {ARM_EXT_V5ExP, 0x01600080, 0x0ff0f0f0, "smulbb%c\t%16-19r, %0-3r, %8-11r"},
371 {ARM_EXT_V5ExP, 0x016000a0, 0x0ff0f0f0, "smultb%c\t%16-19r, %0-3r, %8-11r"},
372 {ARM_EXT_V5ExP, 0x016000c0, 0x0ff0f0f0, "smulbt%c\t%16-19r, %0-3r, %8-11r"},
373 {ARM_EXT_V5ExP, 0x016000e0, 0x0ff0f0f0, "smultt%c\t%16-19r, %0-3r, %8-11r"},
374
375 {ARM_EXT_V5ExP, 0x012000a0, 0x0ff0f0f0, "smulwb%c\t%16-19r, %0-3r, %8-11r"},
376 {ARM_EXT_V5ExP, 0x012000e0, 0x0ff0f0f0, "smulwt%c\t%16-19r, %0-3r, %8-11r"},
377
378 {ARM_EXT_V5ExP, 0x01000050, 0x0ff00ff0, "qadd%c\t%12-15r, %0-3r, %16-19r"},
379 {ARM_EXT_V5ExP, 0x01400050, 0x0ff00ff0, "qdadd%c\t%12-15r, %0-3r, %16-19r"},
380 {ARM_EXT_V5ExP, 0x01200050, 0x0ff00ff0, "qsub%c\t%12-15r, %0-3r, %16-19r"},
381 {ARM_EXT_V5ExP, 0x01600050, 0x0ff00ff0, "qdsub%c\t%12-15r, %0-3r, %16-19r"},
382
383 /* ARM Instructions. */
384 {ARM_EXT_V1, 0x00000090, 0x0e100090, "str%c%6's%5?hb\t%12-15r, %s"},
385 {ARM_EXT_V1, 0x00100090, 0x0e100090, "ldr%c%6's%5?hb\t%12-15r, %s"},
386 {ARM_EXT_V1, 0x00000000, 0x0de00000, "and%c%20's\t%12-15r, %16-19r, %o"},
387 {ARM_EXT_V1, 0x00200000, 0x0de00000, "eor%c%20's\t%12-15r, %16-19r, %o"},
388 {ARM_EXT_V1, 0x00400000, 0x0de00000, "sub%c%20's\t%12-15r, %16-19r, %o"},
389 {ARM_EXT_V1, 0x00600000, 0x0de00000, "rsb%c%20's\t%12-15r, %16-19r, %o"},
390 {ARM_EXT_V1, 0x00800000, 0x0de00000, "add%c%20's\t%12-15r, %16-19r, %o"},
391 {ARM_EXT_V1, 0x00a00000, 0x0de00000, "adc%c%20's\t%12-15r, %16-19r, %o"},
392 {ARM_EXT_V1, 0x00c00000, 0x0de00000, "sbc%c%20's\t%12-15r, %16-19r, %o"},
393 {ARM_EXT_V1, 0x00e00000, 0x0de00000, "rsc%c%20's\t%12-15r, %16-19r, %o"},
394 {ARM_EXT_V3, 0x0120f000, 0x0db0f000, "msr%c\t%22?SCPSR%C, %o"},
395 {ARM_EXT_V3, 0x010f0000, 0x0fbf0fff, "mrs%c\t%12-15r, %22?SCPSR"},
396 {ARM_EXT_V1, 0x01000000, 0x0de00000, "tst%c%p\t%16-19r, %o"},
397 {ARM_EXT_V1, 0x01200000, 0x0de00000, "teq%c%p\t%16-19r, %o"},
398 {ARM_EXT_V1, 0x01400000, 0x0de00000, "cmp%c%p\t%16-19r, %o"},
399 {ARM_EXT_V1, 0x01600000, 0x0de00000, "cmn%c%p\t%16-19r, %o"},
400 {ARM_EXT_V1, 0x01800000, 0x0de00000, "orr%c%20's\t%12-15r, %16-19r, %o"},
401 {ARM_EXT_V1, 0x01a00000, 0x0de00000, "mov%c%20's\t%12-15r, %o"},
402 {ARM_EXT_V1, 0x01c00000, 0x0de00000, "bic%c%20's\t%12-15r, %16-19r, %o"},
403 {ARM_EXT_V1, 0x01e00000, 0x0de00000, "mvn%c%20's\t%12-15r, %o"},
404 {ARM_EXT_V1, 0x04000000, 0x0e100000, "str%c%22'b%t\t%12-15r, %a"},
405 {ARM_EXT_V1, 0x06000000, 0x0e100ff0, "str%c%22'b%t\t%12-15r, %a"},
406 {ARM_EXT_V1, 0x04000000, 0x0c100010, "str%c%22'b%t\t%12-15r, %a"},
407 {ARM_EXT_V1, 0x06000010, 0x0e000010, "undefined"},
408 {ARM_EXT_V1, 0x04100000, 0x0c100000, "ldr%c%22'b%t\t%12-15r, %a"},
409 {ARM_EXT_V1, 0x08000000, 0x0e100000, "stm%c%23?id%24?ba\t%16-19r%21'!, %m%22'^"},
410 {ARM_EXT_V1, 0x08100000, 0x0e100000, "ldm%c%23?id%24?ba\t%16-19r%21'!, %m%22'^"},
411 {ARM_EXT_V1, 0x0a000000, 0x0e000000, "b%24'l%c\t%b"},
412 {ARM_EXT_V1, 0x0f000000, 0x0f000000, "swi%c\t%0-23x"},
413
414 /* Floating point coprocessor (FPA) instructions */
415 {FPU_FPA_EXT_V1, 0x0e000100, 0x0ff08f10, "adf%c%P%R\t%12-14f, %16-18f, %0-3f"},
416 {FPU_FPA_EXT_V1, 0x0e100100, 0x0ff08f10, "muf%c%P%R\t%12-14f, %16-18f, %0-3f"},
417 {FPU_FPA_EXT_V1, 0x0e200100, 0x0ff08f10, "suf%c%P%R\t%12-14f, %16-18f, %0-3f"},
418 {FPU_FPA_EXT_V1, 0x0e300100, 0x0ff08f10, "rsf%c%P%R\t%12-14f, %16-18f, %0-3f"},
419 {FPU_FPA_EXT_V1, 0x0e400100, 0x0ff08f10, "dvf%c%P%R\t%12-14f, %16-18f, %0-3f"},
420 {FPU_FPA_EXT_V1, 0x0e500100, 0x0ff08f10, "rdf%c%P%R\t%12-14f, %16-18f, %0-3f"},
421 {FPU_FPA_EXT_V1, 0x0e600100, 0x0ff08f10, "pow%c%P%R\t%12-14f, %16-18f, %0-3f"},
422 {FPU_FPA_EXT_V1, 0x0e700100, 0x0ff08f10, "rpw%c%P%R\t%12-14f, %16-18f, %0-3f"},
423 {FPU_FPA_EXT_V1, 0x0e800100, 0x0ff08f10, "rmf%c%P%R\t%12-14f, %16-18f, %0-3f"},
424 {FPU_FPA_EXT_V1, 0x0e900100, 0x0ff08f10, "fml%c%P%R\t%12-14f, %16-18f, %0-3f"},
425 {FPU_FPA_EXT_V1, 0x0ea00100, 0x0ff08f10, "fdv%c%P%R\t%12-14f, %16-18f, %0-3f"},
426 {FPU_FPA_EXT_V1, 0x0eb00100, 0x0ff08f10, "frd%c%P%R\t%12-14f, %16-18f, %0-3f"},
427 {FPU_FPA_EXT_V1, 0x0ec00100, 0x0ff08f10, "pol%c%P%R\t%12-14f, %16-18f, %0-3f"},
428 {FPU_FPA_EXT_V1, 0x0e008100, 0x0ff08f10, "mvf%c%P%R\t%12-14f, %0-3f"},
429 {FPU_FPA_EXT_V1, 0x0e108100, 0x0ff08f10, "mnf%c%P%R\t%12-14f, %0-3f"},
430 {FPU_FPA_EXT_V1, 0x0e208100, 0x0ff08f10, "abs%c%P%R\t%12-14f, %0-3f"},
431 {FPU_FPA_EXT_V1, 0x0e308100, 0x0ff08f10, "rnd%c%P%R\t%12-14f, %0-3f"},
432 {FPU_FPA_EXT_V1, 0x0e408100, 0x0ff08f10, "sqt%c%P%R\t%12-14f, %0-3f"},
433 {FPU_FPA_EXT_V1, 0x0e508100, 0x0ff08f10, "log%c%P%R\t%12-14f, %0-3f"},
434 {FPU_FPA_EXT_V1, 0x0e608100, 0x0ff08f10, "lgn%c%P%R\t%12-14f, %0-3f"},
435 {FPU_FPA_EXT_V1, 0x0e708100, 0x0ff08f10, "exp%c%P%R\t%12-14f, %0-3f"},
436 {FPU_FPA_EXT_V1, 0x0e808100, 0x0ff08f10, "sin%c%P%R\t%12-14f, %0-3f"},
437 {FPU_FPA_EXT_V1, 0x0e908100, 0x0ff08f10, "cos%c%P%R\t%12-14f, %0-3f"},
438 {FPU_FPA_EXT_V1, 0x0ea08100, 0x0ff08f10, "tan%c%P%R\t%12-14f, %0-3f"},
439 {FPU_FPA_EXT_V1, 0x0eb08100, 0x0ff08f10, "asn%c%P%R\t%12-14f, %0-3f"},
440 {FPU_FPA_EXT_V1, 0x0ec08100, 0x0ff08f10, "acs%c%P%R\t%12-14f, %0-3f"},
441 {FPU_FPA_EXT_V1, 0x0ed08100, 0x0ff08f10, "atn%c%P%R\t%12-14f, %0-3f"},
442 {FPU_FPA_EXT_V1, 0x0ee08100, 0x0ff08f10, "urd%c%P%R\t%12-14f, %0-3f"},
443 {FPU_FPA_EXT_V1, 0x0ef08100, 0x0ff08f10, "nrm%c%P%R\t%12-14f, %0-3f"},
444 {FPU_FPA_EXT_V1, 0x0e000110, 0x0ff00f1f, "flt%c%P%R\t%16-18f, %12-15r"},
445 {FPU_FPA_EXT_V1, 0x0e100110, 0x0fff0f98, "fix%c%R\t%12-15r, %0-2f"},
446 {FPU_FPA_EXT_V1, 0x0e200110, 0x0fff0fff, "wfs%c\t%12-15r"},
447 {FPU_FPA_EXT_V1, 0x0e300110, 0x0fff0fff, "rfs%c\t%12-15r"},
448 {FPU_FPA_EXT_V1, 0x0e400110, 0x0fff0fff, "wfc%c\t%12-15r"},
449 {FPU_FPA_EXT_V1, 0x0e500110, 0x0fff0fff, "rfc%c\t%12-15r"},
450 {FPU_FPA_EXT_V1, 0x0e90f110, 0x0ff8fff0, "cmf%c\t%16-18f, %0-3f"},
451 {FPU_FPA_EXT_V1, 0x0eb0f110, 0x0ff8fff0, "cnf%c\t%16-18f, %0-3f"},
452 {FPU_FPA_EXT_V1, 0x0ed0f110, 0x0ff8fff0, "cmfe%c\t%16-18f, %0-3f"},
453 {FPU_FPA_EXT_V1, 0x0ef0f110, 0x0ff8fff0, "cnfe%c\t%16-18f, %0-3f"},
454 {FPU_FPA_EXT_V1, 0x0c000100, 0x0e100f00, "stf%c%Q\t%12-14f, %A"},
455 {FPU_FPA_EXT_V1, 0x0c100100, 0x0e100f00, "ldf%c%Q\t%12-14f, %A"},
456 {FPU_FPA_EXT_V2, 0x0c000200, 0x0e100f00, "sfm%c\t%12-14f, %F, %A"},
457 {FPU_FPA_EXT_V2, 0x0c100200, 0x0e100f00, "lfm%c\t%12-14f, %F, %A"},
458
459 /* Floating point coprocessor (VFP) instructions */
460 {FPU_VFP_EXT_V1, 0x0eb00bc0, 0x0fff0ff0, "fabsd%c\t%1z, %0z"},
461 {FPU_VFP_EXT_V1xD, 0x0eb00ac0, 0x0fbf0fd0, "fabss%c\t%1y, %0y"},
462 {FPU_VFP_EXT_V1, 0x0e300b00, 0x0ff00ff0, "faddd%c\t%1z, %2z, %0z"},
463 {FPU_VFP_EXT_V1xD, 0x0e300a00, 0x0fb00f50, "fadds%c\t%1y, %2y, %1y"},
464 {FPU_VFP_EXT_V1, 0x0eb40b40, 0x0fff0f70, "fcmp%7'ed%c\t%1z, %0z"},
465 {FPU_VFP_EXT_V1xD, 0x0eb40a40, 0x0fbf0f50, "fcmp%7'es%c\t%1y, %0y"},
466 {FPU_VFP_EXT_V1, 0x0eb50b40, 0x0fff0f70, "fcmp%7'ezd%c\t%1z"},
467 {FPU_VFP_EXT_V1xD, 0x0eb50a40, 0x0fbf0f70, "fcmp%7'ezs%c\t%1y"},
468 {FPU_VFP_EXT_V1, 0x0eb00b40, 0x0fff0ff0, "fcpyd%c\t%1z, %0z"},
469 {FPU_VFP_EXT_V1xD, 0x0eb00a40, 0x0fbf0fd0, "fcpys%c\t%1y, %0y"},
470 {FPU_VFP_EXT_V1, 0x0eb70ac0, 0x0fff0fd0, "fcvtds%c\t%1z, %0y"},
471 {FPU_VFP_EXT_V1, 0x0eb70bc0, 0x0fbf0ff0, "fcvtsd%c\t%1y, %0z"},
472 {FPU_VFP_EXT_V1, 0x0e800b00, 0x0ff00ff0, "fdivd%c\t%1z, %2z, %0z"},
473 {FPU_VFP_EXT_V1xD, 0x0e800a00, 0x0fb00f50, "fdivs%c\t%1y, %2y, %0y"},
474 {FPU_VFP_EXT_V1, 0x0d100b00, 0x0f700f00, "fldd%c\t%1z, %A"},
475 {FPU_VFP_EXT_V1xD, 0x0c900b00, 0x0fd00f00, "fldmia%0?xd%c\t%16-19r%21'!, %3z"},
476 {FPU_VFP_EXT_V1xD, 0x0d300b00, 0x0ff00f00, "fldmdb%0?xd%c\t%16-19r!, %3z"},
477 {FPU_VFP_EXT_V1xD, 0x0d100a00, 0x0f300f00, "flds%c\t%1y, %A"},
478 {FPU_VFP_EXT_V1xD, 0x0c900a00, 0x0f900f00, "fldmias%c\t%16-19r%21'!, %3y"},
479 {FPU_VFP_EXT_V1xD, 0x0d300a00, 0x0fb00f00, "fldmdbs%c\t%16-19r!, %3y"},
480 {FPU_VFP_EXT_V1, 0x0e000b00, 0x0ff00ff0, "fmacd%c\t%1z, %2z, %0z"},
481 {FPU_VFP_EXT_V1xD, 0x0e000a00, 0x0fb00f50, "fmacs%c\t%1y, %2y, %0y"},
482 {FPU_VFP_EXT_V1, 0x0e200b10, 0x0ff00fff, "fmdhr%c\t%2z, %12-15r"},
483 {FPU_VFP_EXT_V1, 0x0e000b10, 0x0ff00fff, "fmdlr%c\t%2z, %12-15r"},
484 {FPU_VFP_EXT_V2, 0x0c400b10, 0x0ff00ff0, "fmdrr%c\t%0z, %12-15r, %16-19r"},
485 {FPU_VFP_EXT_V1, 0x0e300b10, 0x0ff00fff, "fmrdh%c\t%12-15r, %2z"},
486 {FPU_VFP_EXT_V1, 0x0e100b10, 0x0ff00fff, "fmrdl%c\t%12-15r, %2z"},
487 {FPU_VFP_EXT_V1, 0x0c500b10, 0x0ff00ff0, "fmrrd%c\t%12-15r, %16-19r, %0z"},
488 {FPU_VFP_EXT_V2, 0x0c500a10, 0x0ff00fd0, "fmrrs%c\t%12-15r, %16-19r, %4y"},
489 {FPU_VFP_EXT_V1xD, 0x0e100a10, 0x0ff00f7f, "fmrs%c\t%12-15r, %2y"},
490 {FPU_VFP_EXT_V1xD, 0x0ef1fa10, 0x0fffffff, "fmstat%c"},
491 {FPU_VFP_EXT_V1xD, 0x0ef00a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpsid"},
492 {FPU_VFP_EXT_V1xD, 0x0ef10a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpscr"},
493 {FPU_VFP_EXT_V1xD, 0x0ef80a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpexc"},
494 {FPU_VFP_EXT_V1xD, 0x0ef90a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpinst\t@ Impl def"},
495 {FPU_VFP_EXT_V1xD, 0x0efa0a10, 0x0fff0fff, "fmrx%c\t%12-15r, fpinst2\t@ Impl def"},
496 {FPU_VFP_EXT_V1xD, 0x0ef00a10, 0x0ff00fff, "fmrx%c\t%12-15r, <impl def 0x%16-19x>"},
497 {FPU_VFP_EXT_V1, 0x0e100b00, 0x0ff00ff0, "fmscd%c\t%1z, %2z, %0z"},
498 {FPU_VFP_EXT_V1xD, 0x0e100a00, 0x0fb00f50, "fmscs%c\t%1y, %2y, %0y"},
499 {FPU_VFP_EXT_V1xD, 0x0e000a10, 0x0ff00f7f, "fmsr%c\t%2y, %12-15r"},
500 {FPU_VFP_EXT_V2, 0x0c400a10, 0x0ff00fd0, "fmsrr%c\t%12-15r, %16-19r, %4y"},
501 {FPU_VFP_EXT_V1, 0x0e200b00, 0x0ff00ff0, "fmuld%c\t%1z, %2z, %0z"},
502 {FPU_VFP_EXT_V1xD, 0x0e200a00, 0x0fb00f50, "fmuls%c\t%1y, %2y, %0y"},
503 {FPU_VFP_EXT_V1xD, 0x0ee00a10, 0x0fff0fff, "fmxr%c\tfpsid, %12-15r"},
504 {FPU_VFP_EXT_V1xD, 0x0ee10a10, 0x0fff0fff, "fmxr%c\tfpscr, %12-15r"},
505 {FPU_VFP_EXT_V1xD, 0x0ee80a10, 0x0fff0fff, "fmxr%c\tfpexc, %12-15r"},
506 {FPU_VFP_EXT_V1xD, 0x0ee90a10, 0x0fff0fff, "fmxr%c\tfpinst, %12-15r\t@ Impl def"},
507 {FPU_VFP_EXT_V1xD, 0x0eea0a10, 0x0fff0fff, "fmxr%c\tfpinst2, %12-15r\t@ Impl def"},
508 {FPU_VFP_EXT_V1xD, 0x0ee00a10, 0x0ff00fff, "fmxr%c\t<impl def 0x%16-19x>, %12-15r"},
509 {FPU_VFP_EXT_V1, 0x0eb10b40, 0x0fff0ff0, "fnegd%c\t%1z, %0z"},
510 {FPU_VFP_EXT_V1xD, 0x0eb10a40, 0x0fbf0fd0, "fnegs%c\t%1y, %0y"},
511 {FPU_VFP_EXT_V1, 0x0e000b40, 0x0ff00ff0, "fnmacd%c\t%1z, %2z, %0z"},
512 {FPU_VFP_EXT_V1xD, 0x0e000a40, 0x0fb00f50, "fnmacs%c\t%1y, %2y, %0y"},
513 {FPU_VFP_EXT_V1, 0x0e100b40, 0x0ff00ff0, "fnmscd%c\t%1z, %2z, %0z"},
514 {FPU_VFP_EXT_V1xD, 0x0e100a40, 0x0fb00f50, "fnmscs%c\t%1y, %2y, %0y"},
515 {FPU_VFP_EXT_V1, 0x0e200b40, 0x0ff00ff0, "fnmuld%c\t%1z, %2z, %0z"},
516 {FPU_VFP_EXT_V1xD, 0x0e200a40, 0x0fb00f50, "fnmuls%c\t%1y, %2y, %0y"},
517 {FPU_VFP_EXT_V1, 0x0eb80bc0, 0x0fff0fd0, "fsitod%c\t%1z, %0y"},
518 {FPU_VFP_EXT_V1xD, 0x0eb80ac0, 0x0fbf0fd0, "fsitos%c\t%1y, %0y"},
519 {FPU_VFP_EXT_V1, 0x0eb10bc0, 0x0fff0ff0, "fsqrtd%c\t%1z, %0z"},
520 {FPU_VFP_EXT_V1xD, 0x0eb10ac0, 0x0fbf0fd0, "fsqrts%c\t%1y, %0y"},
521 {FPU_VFP_EXT_V1, 0x0d000b00, 0x0f700f00, "fstd%c\t%1z, %A"},
522 {FPU_VFP_EXT_V1xD, 0x0c800b00, 0x0fd00f00, "fstmia%0?xd%c\t%16-19r%21'!, %3z"},
523 {FPU_VFP_EXT_V1xD, 0x0d200b00, 0x0ff00f00, "fstmdb%0?xd%c\t%16-19r!, %3z"},
524 {FPU_VFP_EXT_V1xD, 0x0d000a00, 0x0f300f00, "fsts%c\t%1y, %A"},
525 {FPU_VFP_EXT_V1xD, 0x0c800a00, 0x0f900f00, "fstmias%c\t%16-19r%21'!, %3y"},
526 {FPU_VFP_EXT_V1xD, 0x0d200a00, 0x0fb00f00, "fstmdbs%c\t%16-19r!, %3y"},
527 {FPU_VFP_EXT_V1, 0x0e300b40, 0x0ff00ff0, "fsubd%c\t%1z, %2z, %0z"},
528 {FPU_VFP_EXT_V1xD, 0x0e300a40, 0x0fb00f50, "fsubs%c\t%1y, %2y, %0y"},
529 {FPU_VFP_EXT_V1, 0x0ebc0b40, 0x0fbe0f70, "fto%16?sui%7'zd%c\t%1y, %0z"},
530 {FPU_VFP_EXT_V1xD, 0x0ebc0a40, 0x0fbe0f50, "fto%16?sui%7'zs%c\t%1y, %0y"},
531 {FPU_VFP_EXT_V1, 0x0eb80b40, 0x0fff0fd0, "fuitod%c\t%1z, %0y"},
532 {FPU_VFP_EXT_V1xD, 0x0eb80a40, 0x0fbf0fd0, "fuitos%c\t%1y, %0y"},
533
534 /* Cirrus coprocessor instructions. */
535 {ARM_CEXT_MAVERICK, 0x0d100400, 0x0f500f00, "cfldrs%c\tmvf%12-15d, %A"},
536 {ARM_CEXT_MAVERICK, 0x0c100400, 0x0f500f00, "cfldrs%c\tmvf%12-15d, %A"},
537 {ARM_CEXT_MAVERICK, 0x0d500400, 0x0f500f00, "cfldrd%c\tmvd%12-15d, %A"},
538 {ARM_CEXT_MAVERICK, 0x0c500400, 0x0f500f00, "cfldrd%c\tmvd%12-15d, %A"},
539 {ARM_CEXT_MAVERICK, 0x0d100500, 0x0f500f00, "cfldr32%c\tmvfx%12-15d, %A"},
540 {ARM_CEXT_MAVERICK, 0x0c100500, 0x0f500f00, "cfldr32%c\tmvfx%12-15d, %A"},
541 {ARM_CEXT_MAVERICK, 0x0d500500, 0x0f500f00, "cfldr64%c\tmvdx%12-15d, %A"},
542 {ARM_CEXT_MAVERICK, 0x0c500500, 0x0f500f00, "cfldr64%c\tmvdx%12-15d, %A"},
543 {ARM_CEXT_MAVERICK, 0x0d000400, 0x0f500f00, "cfstrs%c\tmvf%12-15d, %A"},
544 {ARM_CEXT_MAVERICK, 0x0c000400, 0x0f500f00, "cfstrs%c\tmvf%12-15d, %A"},
545 {ARM_CEXT_MAVERICK, 0x0d400400, 0x0f500f00, "cfstrd%c\tmvd%12-15d, %A"},
546 {ARM_CEXT_MAVERICK, 0x0c400400, 0x0f500f00, "cfstrd%c\tmvd%12-15d, %A"},
547 {ARM_CEXT_MAVERICK, 0x0d000500, 0x0f500f00, "cfstr32%c\tmvfx%12-15d, %A"},
548 {ARM_CEXT_MAVERICK, 0x0c000500, 0x0f500f00, "cfstr32%c\tmvfx%12-15d, %A"},
549 {ARM_CEXT_MAVERICK, 0x0d400500, 0x0f500f00, "cfstr64%c\tmvdx%12-15d, %A"},
550 {ARM_CEXT_MAVERICK, 0x0c400500, 0x0f500f00, "cfstr64%c\tmvdx%12-15d, %A"},
551 {ARM_CEXT_MAVERICK, 0x0e000450, 0x0ff00ff0, "cfmvsr%c\tmvf%16-19d, %12-15r"},
552 {ARM_CEXT_MAVERICK, 0x0e100450, 0x0ff00ff0, "cfmvrs%c\t%12-15r, mvf%16-19d"},
553 {ARM_CEXT_MAVERICK, 0x0e000410, 0x0ff00ff0, "cfmvdlr%c\tmvd%16-19d, %12-15r"},
554 {ARM_CEXT_MAVERICK, 0x0e100410, 0x0ff00ff0, "cfmvrdl%c\t%12-15r, mvd%16-19d"},
555 {ARM_CEXT_MAVERICK, 0x0e000430, 0x0ff00ff0, "cfmvdhr%c\tmvd%16-19d, %12-15r"},
556 {ARM_CEXT_MAVERICK, 0x0e100430, 0x0ff00fff, "cfmvrdh%c\t%12-15r, mvd%16-19d"},
557 {ARM_CEXT_MAVERICK, 0x0e000510, 0x0ff00fff, "cfmv64lr%c\tmvdx%16-19d, %12-15r"},
558 {ARM_CEXT_MAVERICK, 0x0e100510, 0x0ff00fff, "cfmvr64l%c\t%12-15r, mvdx%16-19d"},
559 {ARM_CEXT_MAVERICK, 0x0e000530, 0x0ff00fff, "cfmv64hr%c\tmvdx%16-19d, %12-15r"},
560 {ARM_CEXT_MAVERICK, 0x0e100530, 0x0ff00fff, "cfmvr64h%c\t%12-15r, mvdx%16-19d"},
561 {ARM_CEXT_MAVERICK, 0x0e200440, 0x0ff00fff, "cfmval32%c\tmvax%12-15d, mvfx%16-19d"},
562 {ARM_CEXT_MAVERICK, 0x0e100440, 0x0ff00fff, "cfmv32al%c\tmvfx%12-15d, mvax%16-19d"},
563 {ARM_CEXT_MAVERICK, 0x0e200460, 0x0ff00fff, "cfmvam32%c\tmvax%12-15d, mvfx%16-19d"},
564 {ARM_CEXT_MAVERICK, 0x0e100460, 0x0ff00fff, "cfmv32am%c\tmvfx%12-15d, mvax%16-19d"},
565 {ARM_CEXT_MAVERICK, 0x0e200480, 0x0ff00fff, "cfmvah32%c\tmvax%12-15d, mvfx%16-19d"},
566 {ARM_CEXT_MAVERICK, 0x0e100480, 0x0ff00fff, "cfmv32ah%c\tmvfx%12-15d, mvax%16-19d"},
567 {ARM_CEXT_MAVERICK, 0x0e2004a0, 0x0ff00fff, "cfmva32%c\tmvax%12-15d, mvfx%16-19d"},
568 {ARM_CEXT_MAVERICK, 0x0e1004a0, 0x0ff00fff, "cfmv32a%c\tmvfx%12-15d, mvax%16-19d"},
569 {ARM_CEXT_MAVERICK, 0x0e2004c0, 0x0ff00fff, "cfmva64%c\tmvax%12-15d, mvdx%16-19d"},
570 {ARM_CEXT_MAVERICK, 0x0e1004c0, 0x0ff00fff, "cfmv64a%c\tmvdx%12-15d, mvax%16-19d"},
571 {ARM_CEXT_MAVERICK, 0x0e2004e0, 0x0fff0fff, "cfmvsc32%c\tdspsc, mvdx%12-15d"},
572 {ARM_CEXT_MAVERICK, 0x0e1004e0, 0x0fff0fff, "cfmv32sc%c\tmvdx%12-15d, dspsc"},
573 {ARM_CEXT_MAVERICK, 0x0e000400, 0x0ff00fff, "cfcpys%c\tmvf%12-15d, mvf%16-19d"},
574 {ARM_CEXT_MAVERICK, 0x0e000420, 0x0ff00fff, "cfcpyd%c\tmvd%12-15d, mvd%16-19d"},
575 {ARM_CEXT_MAVERICK, 0x0e000460, 0x0ff00fff, "cfcvtsd%c\tmvd%12-15d, mvf%16-19d"},
576 {ARM_CEXT_MAVERICK, 0x0e000440, 0x0ff00fff, "cfcvtds%c\tmvf%12-15d, mvd%16-19d"},
577 {ARM_CEXT_MAVERICK, 0x0e000480, 0x0ff00fff, "cfcvt32s%c\tmvf%12-15d, mvfx%16-19d"},
578 {ARM_CEXT_MAVERICK, 0x0e0004a0, 0x0ff00fff, "cfcvt32d%c\tmvd%12-15d, mvfx%16-19d"},
579 {ARM_CEXT_MAVERICK, 0x0e0004c0, 0x0ff00fff, "cfcvt64s%c\tmvf%12-15d, mvdx%16-19d"},
580 {ARM_CEXT_MAVERICK, 0x0e0004e0, 0x0ff00fff, "cfcvt64d%c\tmvd%12-15d, mvdx%16-19d"},
581 {ARM_CEXT_MAVERICK, 0x0e100580, 0x0ff00fff, "cfcvts32%c\tmvfx%12-15d, mvf%16-19d"},
582 {ARM_CEXT_MAVERICK, 0x0e1005a0, 0x0ff00fff, "cfcvtd32%c\tmvfx%12-15d, mvd%16-19d"},
583 {ARM_CEXT_MAVERICK, 0x0e1005c0, 0x0ff00fff, "cftruncs32%c\tmvfx%12-15d, mvf%16-19d"},
584 {ARM_CEXT_MAVERICK, 0x0e1005e0, 0x0ff00fff, "cftruncd32%c\tmvfx%12-15d, mvd%16-19d"},
585 {ARM_CEXT_MAVERICK, 0x0e000550, 0x0ff00ff0, "cfrshl32%c\tmvfx%16-19d, mvfx%0-3d, %12-15r"},
586 {ARM_CEXT_MAVERICK, 0x0e000570, 0x0ff00ff0, "cfrshl64%c\tmvdx%16-19d, mvdx%0-3d, %12-15r"},
587 {ARM_CEXT_MAVERICK, 0x0e000500, 0x0ff00f00, "cfsh32%c\tmvfx%12-15d, mvfx%16-19d, #%I"},
588 {ARM_CEXT_MAVERICK, 0x0e200500, 0x0ff00f00, "cfsh64%c\tmvdx%12-15d, mvdx%16-19d, #%I"},
589 {ARM_CEXT_MAVERICK, 0x0e100490, 0x0ff00ff0, "cfcmps%c\t%12-15r, mvf%16-19d, mvf%0-3d"},
590 {ARM_CEXT_MAVERICK, 0x0e1004b0, 0x0ff00ff0, "cfcmpd%c\t%12-15r, mvd%16-19d, mvd%0-3d"},
591 {ARM_CEXT_MAVERICK, 0x0e100590, 0x0ff00ff0, "cfcmp32%c\t%12-15r, mvfx%16-19d, mvfx%0-3d"},
592 {ARM_CEXT_MAVERICK, 0x0e1005b0, 0x0ff00ff0, "cfcmp64%c\t%12-15r, mvdx%16-19d, mvdx%0-3d"},
593 {ARM_CEXT_MAVERICK, 0x0e300400, 0x0ff00fff, "cfabss%c\tmvf%12-15d, mvf%16-19d"},
594 {ARM_CEXT_MAVERICK, 0x0e300420, 0x0ff00fff, "cfabsd%c\tmvd%12-15d, mvd%16-19d"},
595 {ARM_CEXT_MAVERICK, 0x0e300440, 0x0ff00fff, "cfnegs%c\tmvf%12-15d, mvf%16-19d"},
596 {ARM_CEXT_MAVERICK, 0x0e300460, 0x0ff00fff, "cfnegd%c\tmvd%12-15d, mvd%16-19d"},
597 {ARM_CEXT_MAVERICK, 0x0e300480, 0x0ff00ff0, "cfadds%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
598 {ARM_CEXT_MAVERICK, 0x0e3004a0, 0x0ff00ff0, "cfaddd%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
599 {ARM_CEXT_MAVERICK, 0x0e3004c0, 0x0ff00ff0, "cfsubs%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
600 {ARM_CEXT_MAVERICK, 0x0e3004e0, 0x0ff00ff0, "cfsubd%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
601 {ARM_CEXT_MAVERICK, 0x0e100400, 0x0ff00ff0, "cfmuls%c\tmvf%12-15d, mvf%16-19d, mvf%0-3d"},
602 {ARM_CEXT_MAVERICK, 0x0e100420, 0x0ff00ff0, "cfmuld%c\tmvd%12-15d, mvd%16-19d, mvd%0-3d"},
603 {ARM_CEXT_MAVERICK, 0x0e300500, 0x0ff00fff, "cfabs32%c\tmvfx%12-15d, mvfx%16-19d"},
604 {ARM_CEXT_MAVERICK, 0x0e300520, 0x0ff00fff, "cfabs64%c\tmvdx%12-15d, mvdx%16-19d"},
605 {ARM_CEXT_MAVERICK, 0x0e300540, 0x0ff00fff, "cfneg32%c\tmvfx%12-15d, mvfx%16-19d"},
606 {ARM_CEXT_MAVERICK, 0x0e300560, 0x0ff00fff, "cfneg64%c\tmvdx%12-15d, mvdx%16-19d"},
607 {ARM_CEXT_MAVERICK, 0x0e300580, 0x0ff00ff0, "cfadd32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
608 {ARM_CEXT_MAVERICK, 0x0e3005a0, 0x0ff00ff0, "cfadd64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
609 {ARM_CEXT_MAVERICK, 0x0e3005c0, 0x0ff00ff0, "cfsub32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
610 {ARM_CEXT_MAVERICK, 0x0e3005e0, 0x0ff00ff0, "cfsub64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
611 {ARM_CEXT_MAVERICK, 0x0e100500, 0x0ff00ff0, "cfmul32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
612 {ARM_CEXT_MAVERICK, 0x0e100520, 0x0ff00ff0, "cfmul64%c\tmvdx%12-15d, mvdx%16-19d, mvdx%0-3d"},
613 {ARM_CEXT_MAVERICK, 0x0e100540, 0x0ff00ff0, "cfmac32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
614 {ARM_CEXT_MAVERICK, 0x0e100560, 0x0ff00ff0, "cfmsc32%c\tmvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
615 {ARM_CEXT_MAVERICK, 0x0e000600, 0x0ff00f00, "cfmadd32%c\tmvax%5-7d, mvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
616 {ARM_CEXT_MAVERICK, 0x0e100600, 0x0ff00f00, "cfmsub32%c\tmvax%5-7d, mvfx%12-15d, mvfx%16-19d, mvfx%0-3d"},
617 {ARM_CEXT_MAVERICK, 0x0e200600, 0x0ff00f00, "cfmadda32%c\tmvax%5-7d, mvax%12-15d, mvfx%16-19d, mvfx%0-3d"},
618 {ARM_CEXT_MAVERICK, 0x0e300600, 0x0ff00f00, "cfmsuba32%c\tmvax%5-7d, mvax%12-15d, mvfx%16-19d, mvfx%0-3d"},
619
620 /* Generic coprocessor instructions */
621 {ARM_EXT_V2, 0x0c400000, 0x0ff00000, "mcrr%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
622 {ARM_EXT_V2, 0x0c500000, 0x0ff00000, "mrrc%c\t%8-11d, %4-7d, %12-15r, %16-19r, cr%0-3d"},
623 {ARM_EXT_V2, 0x0e000000, 0x0f000010, "cdp%c\t%8-11d, %20-23d, cr%12-15d, cr%16-19d, cr%0-3d, {%5-7d}"},
624 {ARM_EXT_V2, 0x0e100010, 0x0f100010, "mrc%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
625 {ARM_EXT_V2, 0x0e000010, 0x0f100010, "mcr%c\t%8-11d, %21-23d, %12-15r, cr%16-19d, cr%0-3d, {%5-7d}"},
626 {ARM_EXT_V2, 0x0c000000, 0x0e100000, "stc%c%22'l\t%8-11d, cr%12-15d, %A"},
627 {ARM_EXT_V2, 0x0c100000, 0x0e100000, "ldc%c%22'l\t%8-11d, cr%12-15d, %A"},
628
629 /* The rest. */
630 {ARM_EXT_V1, 0x00000000, 0x00000000, "undefined instruction %0-31x"},
631 {0, 0x00000000, 0x00000000, 0}
632};
633
634static const struct thumb_opcode thumb_opcodes[] =
635{
636 /* Thumb instructions. */
637
638 /* ARM V6. */
639 {ARM_EXT_V6, 0xb660, 0xfff8, "cpsie\t%2'a%1'i%0'f"},
640 {ARM_EXT_V6, 0xb670, 0xfff8, "cpsid\t%2'a%1'i%0'f"},
641 {ARM_EXT_V6, 0x4600, 0xffc0, "cpy\t%0-2r, %3-5r"},
642 {ARM_EXT_V6, 0xba00, 0xffc0, "rev\t%0-2r, %3-5r"},
643 {ARM_EXT_V6, 0xba40, 0xffc0, "rev16\t%0-2r, %3-5r"},
644 {ARM_EXT_V6, 0xbac0, 0xffc0, "revsh\t%0-2r, %3-5r"},
645 {ARM_EXT_V6, 0xb650, 0xfff7, "setend\t%3?ble"},
646 {ARM_EXT_V6, 0xb200, 0xffc0, "sxth\t%0-2r, %3-5r"},
647 {ARM_EXT_V6, 0xb240, 0xffc0, "sxtb\t%0-2r, %3-5r"},
648 {ARM_EXT_V6, 0xb280, 0xffc0, "uxth\t%0-2r, %3-5r"},
649 {ARM_EXT_V6, 0xb2c0, 0xffc0, "uxtb\t%0-2r, %3-5r"},
650
651 /* ARM V5 ISA extends Thumb. */
652 {ARM_EXT_V5T, 0xbe00, 0xff00, "bkpt\t%0-7x"},
653 /* Note: this is BLX(2). BLX(1) is done in arm-dis.c/print_insn_thumb()
654 as an extension of the special processing there for Thumb BL.
655 BL and BLX(1) involve 2 successive 16-bit instructions, which must
656 always appear together in the correct order. So, the empty
657 string is put in this table, and the string interpreter takes <empty>
658 to mean it has a pair of BL-ish instructions. */
659 {ARM_EXT_V5T, 0x4780, 0xff87, "blx\t%3-6r"}, /* note: 4 bit register number. */
660 /* ARM V4T ISA (Thumb v1). */
661 {ARM_EXT_V4T, 0x46C0, 0xFFFF, "nop\t\t\t(mov r8, r8)"},
662 /* Format 5 instructions do not update the PSR. */
663 {ARM_EXT_V4T, 0x1C00, 0xFFC0, "mov\t%0-2r, %3-5r\t\t(add %0-2r, %3-5r, #%6-8d)"},
664 /* Format 4. */
665 {ARM_EXT_V4T, 0x4000, 0xFFC0, "and\t%0-2r, %3-5r"},
666 {ARM_EXT_V4T, 0x4040, 0xFFC0, "eor\t%0-2r, %3-5r"},
667 {ARM_EXT_V4T, 0x4080, 0xFFC0, "lsl\t%0-2r, %3-5r"},
668 {ARM_EXT_V4T, 0x40C0, 0xFFC0, "lsr\t%0-2r, %3-5r"},
669 {ARM_EXT_V4T, 0x4100, 0xFFC0, "asr\t%0-2r, %3-5r"},
670 {ARM_EXT_V4T, 0x4140, 0xFFC0, "adc\t%0-2r, %3-5r"},
671 {ARM_EXT_V4T, 0x4180, 0xFFC0, "sbc\t%0-2r, %3-5r"},
672 {ARM_EXT_V4T, 0x41C0, 0xFFC0, "ror\t%0-2r, %3-5r"},
673 {ARM_EXT_V4T, 0x4200, 0xFFC0, "tst\t%0-2r, %3-5r"},
674 {ARM_EXT_V4T, 0x4240, 0xFFC0, "neg\t%0-2r, %3-5r"},
675 {ARM_EXT_V4T, 0x4280, 0xFFC0, "cmp\t%0-2r, %3-5r"},
676 {ARM_EXT_V4T, 0x42C0, 0xFFC0, "cmn\t%0-2r, %3-5r"},
677 {ARM_EXT_V4T, 0x4300, 0xFFC0, "orr\t%0-2r, %3-5r"},
678 {ARM_EXT_V4T, 0x4340, 0xFFC0, "mul\t%0-2r, %3-5r"},
679 {ARM_EXT_V4T, 0x4380, 0xFFC0, "bic\t%0-2r, %3-5r"},
680 {ARM_EXT_V4T, 0x43C0, 0xFFC0, "mvn\t%0-2r, %3-5r"},
681 /* format 13 */
682 {ARM_EXT_V4T, 0xB000, 0xFF80, "add\tsp, #%0-6W"},
683 {ARM_EXT_V4T, 0xB080, 0xFF80, "sub\tsp, #%0-6W"},
684 /* format 5 */
685 {ARM_EXT_V4T, 0x4700, 0xFF80, "bx\t%S"},
686 {ARM_EXT_V4T, 0x4400, 0xFF00, "add\t%D, %S"},
687 {ARM_EXT_V4T, 0x4500, 0xFF00, "cmp\t%D, %S"},
688 {ARM_EXT_V4T, 0x4600, 0xFF00, "mov\t%D, %S"},
689 /* format 14 */
690 {ARM_EXT_V4T, 0xB400, 0xFE00, "push\t%N"},
691 {ARM_EXT_V4T, 0xBC00, 0xFE00, "pop\t%O"},
692 /* format 2 */
693 {ARM_EXT_V4T, 0x1800, 0xFE00, "add\t%0-2r, %3-5r, %6-8r"},
694 {ARM_EXT_V4T, 0x1A00, 0xFE00, "sub\t%0-2r, %3-5r, %6-8r"},
695 {ARM_EXT_V4T, 0x1C00, 0xFE00, "add\t%0-2r, %3-5r, #%6-8d"},
696 {ARM_EXT_V4T, 0x1E00, 0xFE00, "sub\t%0-2r, %3-5r, #%6-8d"},
697 /* format 8 */
698 {ARM_EXT_V4T, 0x5200, 0xFE00, "strh\t%0-2r, [%3-5r, %6-8r]"},
699 {ARM_EXT_V4T, 0x5A00, 0xFE00, "ldrh\t%0-2r, [%3-5r, %6-8r]"},
700 {ARM_EXT_V4T, 0x5600, 0xF600, "ldrs%11?hb\t%0-2r, [%3-5r, %6-8r]"},
701 /* format 7 */
702 {ARM_EXT_V4T, 0x5000, 0xFA00, "str%10'b\t%0-2r, [%3-5r, %6-8r]"},
703 {ARM_EXT_V4T, 0x5800, 0xFA00, "ldr%10'b\t%0-2r, [%3-5r, %6-8r]"},
704 /* format 1 */
705 {ARM_EXT_V4T, 0x0000, 0xF800, "lsl\t%0-2r, %3-5r, #%6-10d"},
706 {ARM_EXT_V4T, 0x0800, 0xF800, "lsr\t%0-2r, %3-5r, #%6-10d"},
707 {ARM_EXT_V4T, 0x1000, 0xF800, "asr\t%0-2r, %3-5r, #%6-10d"},
708 /* format 3 */
709 {ARM_EXT_V4T, 0x2000, 0xF800, "mov\t%8-10r, #%0-7d"},
710 {ARM_EXT_V4T, 0x2800, 0xF800, "cmp\t%8-10r, #%0-7d"},
711 {ARM_EXT_V4T, 0x3000, 0xF800, "add\t%8-10r, #%0-7d"},
712 {ARM_EXT_V4T, 0x3800, 0xF800, "sub\t%8-10r, #%0-7d"},
713 /* format 6 */
714 {ARM_EXT_V4T, 0x4800, 0xF800, "ldr\t%8-10r, [pc, #%0-7W]\t(%0-7a)"}, /* TODO: Disassemble PC relative "LDR rD,=<symbolic>" */
715 /* format 9 */
716 {ARM_EXT_V4T, 0x6000, 0xF800, "str\t%0-2r, [%3-5r, #%6-10W]"},
717 {ARM_EXT_V4T, 0x6800, 0xF800, "ldr\t%0-2r, [%3-5r, #%6-10W]"},
718 {ARM_EXT_V4T, 0x7000, 0xF800, "strb\t%0-2r, [%3-5r, #%6-10d]"},
719 {ARM_EXT_V4T, 0x7800, 0xF800, "ldrb\t%0-2r, [%3-5r, #%6-10d]"},
720 /* format 10 */
721 {ARM_EXT_V4T, 0x8000, 0xF800, "strh\t%0-2r, [%3-5r, #%6-10H]"},
722 {ARM_EXT_V4T, 0x8800, 0xF800, "ldrh\t%0-2r, [%3-5r, #%6-10H]"},
723 /* format 11 */
724 {ARM_EXT_V4T, 0x9000, 0xF800, "str\t%8-10r, [sp, #%0-7W]"},
725 {ARM_EXT_V4T, 0x9800, 0xF800, "ldr\t%8-10r, [sp, #%0-7W]"},
726 /* format 12 */
727 {ARM_EXT_V4T, 0xA000, 0xF800, "add\t%8-10r, pc, #%0-7W\t(adr %8-10r,%0-7a)"},
728 {ARM_EXT_V4T, 0xA800, 0xF800, "add\t%8-10r, sp, #%0-7W"},
729 /* format 15 */
730 {ARM_EXT_V4T, 0xC000, 0xF800, "stmia\t%8-10r!,%M"},
731 {ARM_EXT_V4T, 0xC800, 0xF800, "ldmia\t%8-10r!,%M"},
732 /* format 18 */
733 {ARM_EXT_V4T, 0xE000, 0xF800, "b\t%0-10B"},
734 {ARM_EXT_V4T, 0xE800, 0xF800, "undefined"},
735 /* format 19 */
736 {ARM_EXT_V4T, 0xF000, 0xF800, ""}, /* special processing required in disassembler */
737 {ARM_EXT_V4T, 0xF800, 0xF800, "second half of BL instruction %0-15x"},
738 /* format 16 */
739 {ARM_EXT_V4T, 0xD000, 0xFF00, "beq\t%0-7B"},
740 {ARM_EXT_V4T, 0xD100, 0xFF00, "bne\t%0-7B"},
741 {ARM_EXT_V4T, 0xD200, 0xFF00, "bcs\t%0-7B"},
742 {ARM_EXT_V4T, 0xD300, 0xFF00, "bcc\t%0-7B"},
743 {ARM_EXT_V4T, 0xD400, 0xFF00, "bmi\t%0-7B"},
744 {ARM_EXT_V4T, 0xD500, 0xFF00, "bpl\t%0-7B"},
745 {ARM_EXT_V4T, 0xD600, 0xFF00, "bvs\t%0-7B"},
746 {ARM_EXT_V4T, 0xD700, 0xFF00, "bvc\t%0-7B"},
747 {ARM_EXT_V4T, 0xD800, 0xFF00, "bhi\t%0-7B"},
748 {ARM_EXT_V4T, 0xD900, 0xFF00, "bls\t%0-7B"},
749 {ARM_EXT_V4T, 0xDA00, 0xFF00, "bge\t%0-7B"},
750 {ARM_EXT_V4T, 0xDB00, 0xFF00, "blt\t%0-7B"},
751 {ARM_EXT_V4T, 0xDC00, 0xFF00, "bgt\t%0-7B"},
752 {ARM_EXT_V4T, 0xDD00, 0xFF00, "ble\t%0-7B"},
753 /* format 17 */
754 {ARM_EXT_V4T, 0xDE00, 0xFF00, "bal\t%0-7B"},
755 {ARM_EXT_V4T, 0xDF00, 0xFF00, "swi\t%0-7d"},
756 /* format 9 */
757 {ARM_EXT_V4T, 0x6000, 0xF800, "str\t%0-2r, [%3-5r, #%6-10W]"},
758 {ARM_EXT_V4T, 0x6800, 0xF800, "ldr\t%0-2r, [%3-5r, #%6-10W]"},
759 {ARM_EXT_V4T, 0x7000, 0xF800, "strb\t%0-2r, [%3-5r, #%6-10d]"},
760 {ARM_EXT_V4T, 0x7800, 0xF800, "ldrb\t%0-2r, [%3-5r, #%6-10d]"},
761 /* the rest */
762 {ARM_EXT_V1, 0x0000, 0x0000, "undefined instruction %0-15x"},
763 {0, 0x0000, 0x0000, 0}
764};
765
5876e06d 766static char * arm_conditional[] =
252b5132
RH
767{"eq", "ne", "cs", "cc", "mi", "pl", "vs", "vc",
768 "hi", "ls", "ge", "lt", "gt", "le", "", "nv"};
769
58efb6c0
NC
770typedef struct
771{
772 const char * name;
773 const char * description;
774 const char * reg_names[16];
775}
776arm_regname;
dd92f639 777
58efb6c0
NC
778static arm_regname regnames[] =
779{
780 { "raw" , "Select raw register names",
781 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"}},
7c03c75e
SB
782 { "gcc", "Select register names used by GCC",
783 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "sl", "fp", "ip", "sp", "lr", "pc" }},
58efb6c0
NC
784 { "std", "Select register names used in ARM's ISA documentation",
785 { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "sp", "lr", "pc" }},
786 { "apcs", "Select register names used in the APCS",
787 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "sl", "fp", "ip", "sp", "lr", "pc" }},
788 { "atpcs", "Select register names used in the ATPCS",
789 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8", "IP", "SP", "LR", "PC" }},
a7f8487e 790 { "special-atpcs", "Select special register names used in the ATPCS",
e16bb312 791 { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "WR", "v5", "SB", "SL", "FP", "IP", "SP", "LR", "PC" }},
5a6c6817 792 { "iwmmxt_regnames", "Select register names used on the Intel Wireless MMX technology coprocessor",
e16bb312 793 { "wr0", "wr1", "wr2", "wr3", "wr4", "wr5", "wr6", "wr7", "wr8", "wr9", "wr10", "wr11", "wr12", "wr13", "wr14", "wr15"}},
5a6c6817 794 { "iwmmxt_Cregnames", "Select control register names used on the Intel Wireless MMX technology coprocessor",
e16bb312
NC
795 {"wcid", "wcon", "wcssf", "wcasf", "reserved", "reserved", "reserved", "reserved", "wcgr0", "wcgr1", "wcgr2", "wcgr3", "reserved", "reserved", "reserved", "reserved"}}
796};
797
798static char * iwmmxt_wwnames[] =
799{"b", "h", "w", "d"};
800
801static char * iwmmxt_wwssnames[] =
802{"b", "bus", "b", "bss",
803 "h", "hus", "h", "hss",
804 "w", "wus", "w", "wss",
805 "d", "dus", "d", "dss"
58efb6c0
NC
806};
807
7c03c75e 808/* Default to GCC register name set. */
58efb6c0
NC
809static unsigned int regname_selected = 1;
810
811#define NUM_ARM_REGNAMES NUM_ELEM (regnames)
812#define arm_regnames regnames[regname_selected].reg_names
252b5132 813
b34976b6 814static bfd_boolean force_thumb = FALSE;
01c7f630 815
5876e06d 816static char * arm_fp_const[] =
252b5132
RH
817{"0.0", "1.0", "2.0", "3.0", "4.0", "5.0", "0.5", "10.0"};
818
b34976b6 819static char * arm_shift[] =
252b5132 820{"lsl", "lsr", "asr", "ror"};
01c7f630
NC
821\f
822/* Forward declarations. */
b34976b6
AM
823static void arm_decode_shift
824 PARAMS ((long, fprintf_ftype, void *));
825static int print_insn_arm
826 PARAMS ((bfd_vma, struct disassemble_info *, long));
827static int print_insn_thumb
828 PARAMS ((bfd_vma, struct disassemble_info *, long));
829static void parse_disassembler_options
830 PARAMS ((char *));
831static int print_insn
832 PARAMS ((bfd_vma, struct disassemble_info *, bfd_boolean));
e16bb312
NC
833static int set_iwmmxt_regnames
834 PARAMS ((void));
835
836int get_arm_regname_num_options
837 PARAMS ((void));
838int set_arm_regname_option
839 PARAMS ((int));
840int get_arm_regnames
841 PARAMS ((int, const char **, const char **, const char ***));
01c7f630 842\f
baf0cc5e 843/* Functions. */
a7f8487e 844int
baf0cc5e 845get_arm_regname_num_options ()
a7f8487e
FN
846{
847 return NUM_ARM_REGNAMES;
848}
849
850int
baf0cc5e
NC
851set_arm_regname_option (option)
852 int option;
a7f8487e
FN
853{
854 int old = regname_selected;
855 regname_selected = option;
856 return old;
857}
858
859int
baf0cc5e
NC
860get_arm_regnames (option, setname, setdescription, register_names)
861 int option;
862 const char **setname;
863 const char **setdescription;
864 const char ***register_names;
a7f8487e
FN
865{
866 *setname = regnames[option].name;
867 *setdescription = regnames[option].description;
868 *register_names = regnames[option].reg_names;
869 return 16;
870}
871
252b5132
RH
872static void
873arm_decode_shift (given, func, stream)
874 long given;
875 fprintf_ftype func;
5876e06d 876 void * stream;
252b5132
RH
877{
878 func (stream, "%s", arm_regnames[given & 0xf]);
b34976b6 879
252b5132
RH
880 if ((given & 0xff0) != 0)
881 {
882 if ((given & 0x10) == 0)
883 {
884 int amount = (given & 0xf80) >> 7;
885 int shift = (given & 0x60) >> 5;
b34976b6 886
252b5132
RH
887 if (amount == 0)
888 {
889 if (shift == 3)
890 {
891 func (stream, ", rrx");
892 return;
893 }
b34976b6 894
252b5132
RH
895 amount = 32;
896 }
b34976b6 897
252b5132
RH
898 func (stream, ", %s #%d", arm_shift[shift], amount);
899 }
900 else
901 func (stream, ", %s %s", arm_shift[(given & 0x60) >> 5],
902 arm_regnames[(given & 0xf00) >> 8]);
903 }
904}
905
e16bb312
NC
906static int
907set_iwmmxt_regnames ()
908{
909 const char * setname;
910 const char * setdesc;
911 const char ** regnames;
912 int iwmmxt_regnames = 0;
913 int num_regnames = get_arm_regname_num_options ();
914
915 get_arm_regnames (iwmmxt_regnames, &setname,
916 &setdesc, &regnames);
917 while ((strcmp ("iwmmxt_regnames", setname))
918 && (iwmmxt_regnames < num_regnames))
919 get_arm_regnames (++iwmmxt_regnames, &setname, &setdesc, &regnames);
920
921 return iwmmxt_regnames;
922}
923
252b5132
RH
924/* Print one instruction from PC on INFO->STREAM.
925 Return the size of the instruction (always 4 on ARM). */
baf0cc5e 926
252b5132
RH
927static int
928print_insn_arm (pc, info, given)
6a51a8a8
AM
929 bfd_vma pc;
930 struct disassemble_info *info;
931 long given;
252b5132 932{
6a51a8a8
AM
933 const struct arm_opcode *insn;
934 void *stream = info->stream;
935 fprintf_ftype func = info->fprintf_func;
e16bb312 936 static int iwmmxt_regnames = 0;
252b5132
RH
937
938 for (insn = arm_opcodes; insn->assembler; insn++)
939 {
e16bb312
NC
940 if (insn->value == FIRST_IWMMXT_INSN
941 && info->mach != bfd_mach_arm_XScale
942 && info->mach != bfd_mach_arm_iWMMXt)
943 insn = insn + IWMMXT_INSN_COUNT;
944
0a003adc
ZW
945 if ((given & insn->mask) == insn->value
946 /* Special case: an instruction with all bits set in the condition field
947 (0xFnnn_nnnn) is only matched if all those bits are set in insn->mask,
948 or by the catchall at the end of the table. */
949 && ((given & 0xF0000000) != 0xF0000000
950 || (insn->mask & 0xF0000000) == 0xF0000000
951 || (insn->mask == 0 && insn->value == 0)))
252b5132
RH
952 {
953 char * c;
b34976b6 954
252b5132
RH
955 for (c = insn->assembler; *c; c++)
956 {
957 if (*c == '%')
958 {
959 switch (*++c)
960 {
961 case '%':
962 func (stream, "%%");
963 break;
964
965 case 'a':
966 if (((given & 0x000f0000) == 0x000f0000)
967 && ((given & 0x02000000) == 0))
968 {
969 int offset = given & 0xfff;
b34976b6 970
252b5132 971 func (stream, "[pc");
b34976b6 972
252b5132
RH
973 if (given & 0x01000000)
974 {
975 if ((given & 0x00800000) == 0)
976 offset = - offset;
b34976b6 977
baf0cc5e 978 /* Pre-indexed. */
40536497 979 func (stream, ", #%d]", offset);
252b5132
RH
980
981 offset += pc + 8;
982
58efb6c0
NC
983 /* Cope with the possibility of write-back
984 being used. Probably a very dangerous thing
985 for the programmer to do, but who are we to
986 argue ? */
252b5132
RH
987 if (given & 0x00200000)
988 func (stream, "!");
989 }
990 else
991 {
58efb6c0 992 /* Post indexed. */
40536497 993 func (stream, "], #%d", offset);
252b5132 994
baf0cc5e
NC
995 /* ie ignore the offset. */
996 offset = pc + 8;
252b5132 997 }
b34976b6 998
252b5132
RH
999 func (stream, "\t; ");
1000 info->print_address_func (offset, info);
1001 }
1002 else
1003 {
b34976b6 1004 func (stream, "[%s",
252b5132
RH
1005 arm_regnames[(given >> 16) & 0xf]);
1006 if ((given & 0x01000000) != 0)
1007 {
1008 if ((given & 0x02000000) == 0)
1009 {
1010 int offset = given & 0xfff;
1011 if (offset)
8e6446ff 1012 func (stream, ", #%s%d",
252b5132
RH
1013 (((given & 0x00800000) == 0)
1014 ? "-" : ""), offset);
1015 }
1016 else
1017 {
1018 func (stream, ", %s",
1019 (((given & 0x00800000) == 0)
1020 ? "-" : ""));
1021 arm_decode_shift (given, func, stream);
1022 }
1023
b34976b6 1024 func (stream, "]%s",
252b5132
RH
1025 ((given & 0x00200000) != 0) ? "!" : "");
1026 }
1027 else
1028 {
1029 if ((given & 0x02000000) == 0)
1030 {
1031 int offset = given & 0xfff;
1032 if (offset)
8e6446ff 1033 func (stream, "], #%s%d",
252b5132
RH
1034 (((given & 0x00800000) == 0)
1035 ? "-" : ""), offset);
b34976b6 1036 else
252b5132
RH
1037 func (stream, "]");
1038 }
1039 else
1040 {
1041 func (stream, "], %s",
b34976b6 1042 (((given & 0x00800000) == 0)
252b5132
RH
1043 ? "-" : ""));
1044 arm_decode_shift (given, func, stream);
1045 }
1046 }
1047 }
1048 break;
1049
1050 case 's':
1051 if ((given & 0x004f0000) == 0x004f0000)
1052 {
58efb6c0 1053 /* PC relative with immediate offset. */
252b5132 1054 int offset = ((given & 0xf00) >> 4) | (given & 0xf);
b34976b6 1055
252b5132
RH
1056 if ((given & 0x00800000) == 0)
1057 offset = -offset;
b34976b6 1058
40536497 1059 func (stream, "[pc, #%d]\t; ", offset);
b34976b6 1060
252b5132
RH
1061 (*info->print_address_func)
1062 (offset + pc + 8, info);
1063 }
1064 else
1065 {
b34976b6 1066 func (stream, "[%s",
252b5132
RH
1067 arm_regnames[(given >> 16) & 0xf]);
1068 if ((given & 0x01000000) != 0)
1069 {
58efb6c0 1070 /* Pre-indexed. */
252b5132
RH
1071 if ((given & 0x00400000) == 0x00400000)
1072 {
58efb6c0 1073 /* Immediate. */
252b5132
RH
1074 int offset = ((given & 0xf00) >> 4) | (given & 0xf);
1075 if (offset)
8e6446ff 1076 func (stream, ", #%s%d",
252b5132
RH
1077 (((given & 0x00800000) == 0)
1078 ? "-" : ""), offset);
1079 }
1080 else
1081 {
58efb6c0 1082 /* Register. */
252b5132
RH
1083 func (stream, ", %s%s",
1084 (((given & 0x00800000) == 0)
1085 ? "-" : ""),
1086 arm_regnames[given & 0xf]);
1087 }
1088
b34976b6 1089 func (stream, "]%s",
252b5132
RH
1090 ((given & 0x00200000) != 0) ? "!" : "");
1091 }
1092 else
1093 {
58efb6c0 1094 /* Post-indexed. */
252b5132
RH
1095 if ((given & 0x00400000) == 0x00400000)
1096 {
58efb6c0 1097 /* Immediate. */
252b5132
RH
1098 int offset = ((given & 0xf00) >> 4) | (given & 0xf);
1099 if (offset)
8e6446ff 1100 func (stream, "], #%s%d",
252b5132
RH
1101 (((given & 0x00800000) == 0)
1102 ? "-" : ""), offset);
b34976b6 1103 else
252b5132
RH
1104 func (stream, "]");
1105 }
1106 else
1107 {
58efb6c0 1108 /* Register. */
252b5132
RH
1109 func (stream, "], %s%s",
1110 (((given & 0x00800000) == 0)
1111 ? "-" : ""),
1112 arm_regnames[given & 0xf]);
1113 }
1114 }
1115 }
1116 break;
b34976b6 1117
252b5132
RH
1118 case 'b':
1119 (*info->print_address_func)
1120 (BDISP (given) * 4 + pc + 8, info);
1121 break;
1122
1123 case 'c':
1124 func (stream, "%s",
1125 arm_conditional [(given >> 28) & 0xf]);
1126 break;
1127
1128 case 'm':
1129 {
1130 int started = 0;
1131 int reg;
1132
1133 func (stream, "{");
1134 for (reg = 0; reg < 16; reg++)
1135 if ((given & (1 << reg)) != 0)
1136 {
1137 if (started)
1138 func (stream, ", ");
1139 started = 1;
1140 func (stream, "%s", arm_regnames[reg]);
1141 }
1142 func (stream, "}");
1143 }
1144 break;
1145
1146 case 'o':
1147 if ((given & 0x02000000) != 0)
1148 {
1149 int rotate = (given & 0xf00) >> 7;
1150 int immed = (given & 0xff);
9f20bbfd
NC
1151 immed = (((immed << (32 - rotate))
1152 | (immed >> rotate)) & 0xffffffff);
1153 func (stream, "#%d\t; 0x%x", immed, immed);
252b5132
RH
1154 }
1155 else
1156 arm_decode_shift (given, func, stream);
1157 break;
1158
1159 case 'p':
1160 if ((given & 0x0000f000) == 0x0000f000)
1161 func (stream, "p");
1162 break;
1163
1164 case 't':
1165 if ((given & 0x01200000) == 0x00200000)
1166 func (stream, "t");
1167 break;
1168
252b5132
RH
1169 case 'A':
1170 func (stream, "[%s", arm_regnames [(given >> 16) & 0xf]);
f02232aa
NC
1171
1172 if ((given & (1 << 24)) != 0)
252b5132
RH
1173 {
1174 int offset = given & 0xff;
f02232aa 1175
252b5132 1176 if (offset)
8e6446ff 1177 func (stream, ", #%s%d]%s",
252b5132
RH
1178 ((given & 0x00800000) == 0 ? "-" : ""),
1179 offset * 4,
1180 ((given & 0x00200000) != 0 ? "!" : ""));
1181 else
1182 func (stream, "]");
1183 }
1184 else
1185 {
1186 int offset = given & 0xff;
f02232aa
NC
1187
1188 func (stream, "]");
1189
1190 if (given & (1 << 21))
1191 {
1192 if (offset)
8e6446ff 1193 func (stream, ", #%s%d",
f02232aa
NC
1194 ((given & 0x00800000) == 0 ? "-" : ""),
1195 offset * 4);
1196 }
252b5132 1197 else
f02232aa 1198 func (stream, ", {%d}", offset);
252b5132
RH
1199 }
1200 break;
1201
077b8428
NC
1202 case 'B':
1203 /* Print ARM V5 BLX(1) address: pc+25 bits. */
1204 {
1205 bfd_vma address;
1206 bfd_vma offset = 0;
b34976b6 1207
077b8428
NC
1208 if (given & 0x00800000)
1209 /* Is signed, hi bits should be ones. */
1210 offset = (-1) ^ 0x00ffffff;
1211
1212 /* Offset is (SignExtend(offset field)<<2). */
1213 offset += given & 0x00ffffff;
1214 offset <<= 2;
1215 address = offset + pc + 8;
b34976b6 1216
077b8428
NC
1217 if (given & 0x01000000)
1218 /* H bit allows addressing to 2-byte boundaries. */
1219 address += 2;
1220
1221 info->print_address_func (address, info);
1222 }
1223 break;
1224
b1ee46c5
AH
1225 case 'I':
1226 /* Print a Cirrus/DSP shift immediate. */
1227 /* Immediates are 7bit signed ints with bits 0..3 in
1228 bits 0..3 of opcode and bits 4..6 in bits 5..7
1229 of opcode. */
1230 {
1231 int imm;
1232
1233 imm = (given & 0xf) | ((given & 0xe0) >> 1);
1234
1235 /* Is ``imm'' a negative number? */
1236 if (imm & 0x40)
1237 imm |= (-1 << 7);
1238
1239 func (stream, "%d", imm);
1240 }
1241
1242 break;
1243
252b5132 1244 case 'C':
6eeeb4b4
AO
1245 func (stream, "_");
1246 if (given & 0x80000)
1247 func (stream, "f");
1248 if (given & 0x40000)
1249 func (stream, "s");
1250 if (given & 0x20000)
1251 func (stream, "x");
1252 if (given & 0x10000)
1253 func (stream, "c");
252b5132
RH
1254 break;
1255
1256 case 'F':
1257 switch (given & 0x00408000)
1258 {
1259 case 0:
1260 func (stream, "4");
1261 break;
1262 case 0x8000:
1263 func (stream, "1");
1264 break;
1265 case 0x00400000:
1266 func (stream, "2");
1267 break;
1268 default:
1269 func (stream, "3");
1270 }
1271 break;
b34976b6 1272
252b5132
RH
1273 case 'P':
1274 switch (given & 0x00080080)
1275 {
1276 case 0:
1277 func (stream, "s");
1278 break;
1279 case 0x80:
1280 func (stream, "d");
1281 break;
1282 case 0x00080000:
1283 func (stream, "e");
1284 break;
1285 default:
1286 func (stream, _("<illegal precision>"));
1287 break;
1288 }
1289 break;
1290 case 'Q':
1291 switch (given & 0x00408000)
1292 {
1293 case 0:
1294 func (stream, "s");
1295 break;
1296 case 0x8000:
1297 func (stream, "d");
1298 break;
1299 case 0x00400000:
1300 func (stream, "e");
1301 break;
1302 default:
1303 func (stream, "p");
1304 break;
1305 }
1306 break;
1307 case 'R':
1308 switch (given & 0x60)
1309 {
1310 case 0:
1311 break;
1312 case 0x20:
1313 func (stream, "p");
1314 break;
1315 case 0x40:
1316 func (stream, "m");
1317 break;
1318 default:
1319 func (stream, "z");
1320 break;
1321 }
1322 break;
1323
b34976b6 1324 case '0': case '1': case '2': case '3': case '4':
252b5132
RH
1325 case '5': case '6': case '7': case '8': case '9':
1326 {
1327 int bitstart = *c++ - '0';
1328 int bitend = 0;
1329 while (*c >= '0' && *c <= '9')
1330 bitstart = (bitstart * 10) + *c++ - '0';
1331
1332 switch (*c)
1333 {
1334 case '-':
1335 c++;
b34976b6 1336
252b5132
RH
1337 while (*c >= '0' && *c <= '9')
1338 bitend = (bitend * 10) + *c++ - '0';
b34976b6 1339
252b5132
RH
1340 if (!bitend)
1341 abort ();
b34976b6 1342
252b5132
RH
1343 switch (*c)
1344 {
1345 case 'r':
1346 {
1347 long reg;
b34976b6 1348
252b5132
RH
1349 reg = given >> bitstart;
1350 reg &= (2 << (bitend - bitstart)) - 1;
b34976b6 1351
252b5132
RH
1352 func (stream, "%s", arm_regnames[reg]);
1353 }
1354 break;
1355 case 'd':
1356 {
1357 long reg;
b34976b6 1358
252b5132
RH
1359 reg = given >> bitstart;
1360 reg &= (2 << (bitend - bitstart)) - 1;
b34976b6 1361
252b5132
RH
1362 func (stream, "%d", reg);
1363 }
1364 break;
09d92015
MM
1365 case 'W':
1366 {
1367 long reg;
1368
1369 reg = given >> bitstart;
1370 reg &= (2 << (bitend - bitstart)) - 1;
1371
1372 func (stream, "%d", reg + 1);
1373 }
1374 break;
252b5132
RH
1375 case 'x':
1376 {
1377 long reg;
b34976b6 1378
252b5132
RH
1379 reg = given >> bitstart;
1380 reg &= (2 << (bitend - bitstart)) - 1;
b34976b6 1381
252b5132 1382 func (stream, "0x%08x", reg);
b34976b6 1383
58efb6c0
NC
1384 /* Some SWI instructions have special
1385 meanings. */
5876e06d
NC
1386 if ((given & 0x0fffffff) == 0x0FF00000)
1387 func (stream, "\t; IMB");
1388 else if ((given & 0x0fffffff) == 0x0FF00001)
1389 func (stream, "\t; IMBRange");
252b5132
RH
1390 }
1391 break;
cfbd315c
DL
1392 case 'X':
1393 {
1394 long reg;
b34976b6 1395
cfbd315c
DL
1396 reg = given >> bitstart;
1397 reg &= (2 << (bitend - bitstart)) - 1;
b34976b6 1398
cfbd315c
DL
1399 func (stream, "%01x", reg & 0xf);
1400 }
1401 break;
252b5132
RH
1402 case 'f':
1403 {
1404 long reg;
b34976b6 1405
252b5132
RH
1406 reg = given >> bitstart;
1407 reg &= (2 << (bitend - bitstart)) - 1;
b34976b6 1408
252b5132
RH
1409 if (reg > 7)
1410 func (stream, "#%s",
1411 arm_fp_const[reg & 7]);
1412 else
1413 func (stream, "f%d", reg);
1414 }
1415 break;
e16bb312
NC
1416
1417 case 'w':
1418 {
1419 long reg;
1420
1421 if (bitstart != bitend)
1422 {
1423 reg = given >> bitstart;
1424 reg &= (2 << (bitend - bitstart)) - 1;
1425 if (bitend - bitstart == 1)
1426 func (stream, "%s", iwmmxt_wwnames[reg]);
1427 else
1428 func (stream, "%s", iwmmxt_wwssnames[reg]);
1429 }
1430 else
1431 {
1432 reg = (((given >> 8) & 0x1) |
1433 ((given >> 22) & 0x1));
1434 func (stream, "%s", iwmmxt_wwnames[reg]);
1435 }
1436 }
1437 break;
1438
1439 case 'g':
1440 {
1441 long reg;
1442 int current_regnames;
1443
1444 if (! iwmmxt_regnames)
1445 iwmmxt_regnames = set_iwmmxt_regnames ();
1446 current_regnames = set_arm_regname_option
1447 (iwmmxt_regnames);
1448
1449 reg = given >> bitstart;
1450 reg &= (2 << (bitend - bitstart)) - 1;
1451 func (stream, "%s", arm_regnames[reg]);
1452 set_arm_regname_option (current_regnames);
1453 }
1454 break;
1455
1456 case 'G':
1457 {
1458 long reg;
1459 int current_regnames;
1460
1461 if (! iwmmxt_regnames)
1462 iwmmxt_regnames = set_iwmmxt_regnames ();
1463 current_regnames = set_arm_regname_option
1464 (iwmmxt_regnames + 1);
1465
1466 reg = given >> bitstart;
1467 reg &= (2 << (bitend - bitstart)) - 1;
1468 func (stream, "%s", arm_regnames[reg]);
1469 set_arm_regname_option (current_regnames);
1470 }
1471 break;
1472
252b5132
RH
1473 default:
1474 abort ();
1475 }
1476 break;
a660f11e
RE
1477
1478 case 'y':
1479 case 'z':
1480 {
1481 int single = *c == 'y';
1482 int regno;
1483
1484 switch (bitstart)
1485 {
1486 case 4: /* Sm pair */
1487 func (stream, "{");
1488 /* Fall through. */
1489 case 0: /* Sm, Dm */
1490 regno = given & 0x0000000f;
1491 if (single)
1492 {
1493 regno <<= 1;
1494 regno += (given >> 5) & 1;
1495 }
1496 break;
1497
1498 case 1: /* Sd, Dd */
1499 regno = (given >> 12) & 0x0000000f;
1500 if (single)
1501 {
1502 regno <<= 1;
1503 regno += (given >> 22) & 1;
1504 }
1505 break;
1506
1507 case 2: /* Sn, Dn */
1508 regno = (given >> 16) & 0x0000000f;
1509 if (single)
1510 {
1511 regno <<= 1;
1512 regno += (given >> 7) & 1;
1513 }
1514 break;
1515
1516 case 3: /* List */
1517 func (stream, "{");
1518 regno = (given >> 12) & 0x0000000f;
1519 if (single)
1520 {
1521 regno <<= 1;
1522 regno += (given >> 22) & 1;
1523 }
1524 break;
1525
b34976b6 1526
a660f11e
RE
1527 default:
1528 abort ();
1529 }
1530
1531 func (stream, "%c%d", single ? 's' : 'd', regno);
1532
1533 if (bitstart == 3)
1534 {
1535 int count = given & 0xff;
1536
1537 if (single == 0)
1538 count >>= 1;
1539
1540 if (--count)
1541 {
1542 func (stream, "-%c%d",
1543 single ? 's' : 'd',
1544 regno + count);
1545 }
1546
1547 func (stream, "}");
1548 }
1549 else if (bitstart == 4)
1550 func (stream, ", %c%d}", single ? 's' : 'd',
1551 regno + 1);
1552
1553 break;
1554 }
1555
252b5132
RH
1556 case '`':
1557 c++;
1558 if ((given & (1 << bitstart)) == 0)
1559 func (stream, "%c", *c);
1560 break;
1561 case '\'':
1562 c++;
1563 if ((given & (1 << bitstart)) != 0)
1564 func (stream, "%c", *c);
1565 break;
1566 case '?':
1567 ++c;
1568 if ((given & (1 << bitstart)) != 0)
1569 func (stream, "%c", *c++);
1570 else
1571 func (stream, "%c", *++c);
1572 break;
1573 default:
1574 abort ();
1575 }
1576 break;
1577
e16bb312
NC
1578 case 'L':
1579 switch (given & 0x00400100)
1580 {
1581 case 0x00000000: func (stream, "b"); break;
1582 case 0x00400000: func (stream, "h"); break;
1583 case 0x00000100: func (stream, "w"); break;
1584 case 0x00400100: func (stream, "d"); break;
1585 default:
1586 break;
1587 }
1588 break;
1589
1590 case 'Z':
1591 {
1592 int value;
1593 /* given (20, 23) | given (0, 3) */
1594 value = ((given >> 16) & 0xf0) | (given & 0xf);
1595 func (stream, "%d", value);
1596 }
1597 break;
1598
1599 case 'l':
1600 /* This is like the 'A' operator, except that if
1601 the width field "M" is zero, then the offset is
1602 *not* multiplied by four. */
1603 {
1604 int offset = given & 0xff;
1605 int multiplier = (given & 0x00000100) ? 4 : 1;
1606
1607 func (stream, "[%s", arm_regnames [(given >> 16) & 0xf]);
1608
1609 if (offset)
1610 {
1611 if ((given & 0x01000000) != 0)
8e6446ff 1612 func (stream, ", #%s%d]%s",
e16bb312
NC
1613 ((given & 0x00800000) == 0 ? "-" : ""),
1614 offset * multiplier,
1615 ((given & 0x00200000) != 0 ? "!" : ""));
1616 else
8e6446ff 1617 func (stream, "], #%s%d",
e16bb312
NC
1618 ((given & 0x00800000) == 0 ? "-" : ""),
1619 offset * multiplier);
1620 }
1621 else
1622 func (stream, "]");
1623 }
1624 break;
1625
0dd132b6
NC
1626 case 'e':
1627 {
1628 int imm;
1629
1630 imm = (given & 0xf) | ((given & 0xfff00) >> 4);
1631 func (stream, "%d", imm);
1632 }
1633 break;
1634
0a003adc
ZW
1635 case 'E':
1636 /* LSB and WIDTH fields of BFI or BFC. The machine-
1637 language instruction encodes LSB and MSB. */
1638 {
1639 long msb = (given & 0x001f0000) >> 16;
1640 long lsb = (given & 0x00000f80) >> 7;
1641
1642 long width = msb - lsb + 1;
1643 if (width > 0)
1644 func (stream, "#%lu, #%lu", lsb, width);
1645 else
1646 func (stream, "(invalid: %lu:%lu)", lsb, msb);
1647 }
1648 break;
1649
1650 case 'V':
1651 /* 16-bit unsigned immediate from a MOVT or MOVW
1652 instruction, encoded in bits 0:11 and 15:19. */
1653 {
1654 long hi = (given & 0x000f0000) >> 4;
1655 long lo = (given & 0x00000fff);
1656 long imm16 = hi | lo;
1657 func (stream, "#%lu\t; 0x%lx", imm16, imm16);
1658 }
1659 break;
1660
252b5132
RH
1661 default:
1662 abort ();
1663 }
1664 }
1665 }
1666 else
1667 func (stream, "%c", *c);
1668 }
1669 return 4;
1670 }
1671 }
1672 abort ();
1673}
1674
1675/* Print one instruction from PC on INFO->STREAM.
1676 Return the size of the instruction. */
baf0cc5e 1677
252b5132
RH
1678static int
1679print_insn_thumb (pc, info, given)
6a51a8a8
AM
1680 bfd_vma pc;
1681 struct disassemble_info *info;
1682 long given;
252b5132 1683{
6a51a8a8
AM
1684 const struct thumb_opcode *insn;
1685 void *stream = info->stream;
1686 fprintf_ftype func = info->fprintf_func;
252b5132
RH
1687
1688 for (insn = thumb_opcodes; insn->assembler; insn++)
1689 {
1690 if ((given & insn->mask) == insn->value)
1691 {
5876e06d 1692 char * c = insn->assembler;
252b5132 1693
58efb6c0
NC
1694 /* Special processing for Thumb 2 instruction BL sequence: */
1695 if (!*c) /* Check for empty (not NULL) assembler string. */
252b5132 1696 {
4f3c3dbb 1697 long offset;
b34976b6 1698
252b5132
RH
1699 info->bytes_per_chunk = 4;
1700 info->bytes_per_line = 4;
4f3c3dbb
NC
1701
1702 offset = BDISP23 (given);
baf0cc5e
NC
1703 offset = offset * 2 + pc + 4;
1704
077b8428 1705 if ((given & 0x10000000) == 0)
4f3c3dbb
NC
1706 {
1707 func (stream, "blx\t");
baf0cc5e 1708 offset &= 0xfffffffc;
4f3c3dbb 1709 }
077b8428 1710 else
4f3c3dbb
NC
1711 func (stream, "bl\t");
1712
baf0cc5e 1713 info->print_address_func (offset, info);
252b5132
RH
1714 return 4;
1715 }
1716 else
1717 {
1718 info->bytes_per_chunk = 2;
1719 info->bytes_per_line = 4;
b34976b6 1720
252b5132 1721 given &= 0xffff;
b34976b6 1722
252b5132
RH
1723 for (; *c; c++)
1724 {
1725 if (*c == '%')
1726 {
1727 int domaskpc = 0;
1728 int domasklr = 0;
b34976b6 1729
252b5132
RH
1730 switch (*++c)
1731 {
1732 case '%':
1733 func (stream, "%%");
1734 break;
1735
1736 case 'S':
1737 {
1738 long reg;
b34976b6 1739
252b5132
RH
1740 reg = (given >> 3) & 0x7;
1741 if (given & (1 << 6))
1742 reg += 8;
b34976b6 1743
252b5132
RH
1744 func (stream, "%s", arm_regnames[reg]);
1745 }
1746 break;
1747
1748 case 'D':
1749 {
1750 long reg;
b34976b6 1751
252b5132
RH
1752 reg = given & 0x7;
1753 if (given & (1 << 7))
1754 reg += 8;
b34976b6 1755
252b5132
RH
1756 func (stream, "%s", arm_regnames[reg]);
1757 }
1758 break;
1759
1760 case 'T':
1761 func (stream, "%s",
1762 arm_conditional [(given >> 8) & 0xf]);
1763 break;
1764
1765 case 'N':
1766 if (given & (1 << 8))
1767 domasklr = 1;
58efb6c0 1768 /* Fall through. */
252b5132
RH
1769 case 'O':
1770 if (*c == 'O' && (given & (1 << 8)))
1771 domaskpc = 1;
58efb6c0 1772 /* Fall through. */
252b5132
RH
1773 case 'M':
1774 {
1775 int started = 0;
1776 int reg;
b34976b6 1777
252b5132 1778 func (stream, "{");
b34976b6 1779
252b5132
RH
1780 /* It would be nice if we could spot
1781 ranges, and generate the rS-rE format: */
1782 for (reg = 0; (reg < 8); reg++)
1783 if ((given & (1 << reg)) != 0)
1784 {
1785 if (started)
1786 func (stream, ", ");
1787 started = 1;
1788 func (stream, "%s", arm_regnames[reg]);
1789 }
1790
1791 if (domasklr)
1792 {
1793 if (started)
1794 func (stream, ", ");
1795 started = 1;
a7f8487e 1796 func (stream, arm_regnames[14] /* "lr" */);
252b5132
RH
1797 }
1798
1799 if (domaskpc)
1800 {
1801 if (started)
1802 func (stream, ", ");
a7f8487e 1803 func (stream, arm_regnames[15] /* "pc" */);
252b5132
RH
1804 }
1805
1806 func (stream, "}");
1807 }
1808 break;
1809
1810
b34976b6 1811 case '0': case '1': case '2': case '3': case '4':
252b5132
RH
1812 case '5': case '6': case '7': case '8': case '9':
1813 {
1814 int bitstart = *c++ - '0';
1815 int bitend = 0;
b34976b6 1816
252b5132
RH
1817 while (*c >= '0' && *c <= '9')
1818 bitstart = (bitstart * 10) + *c++ - '0';
1819
1820 switch (*c)
1821 {
1822 case '-':
1823 {
1824 long reg;
b34976b6 1825
252b5132
RH
1826 c++;
1827 while (*c >= '0' && *c <= '9')
1828 bitend = (bitend * 10) + *c++ - '0';
1829 if (!bitend)
1830 abort ();
1831 reg = given >> bitstart;
1832 reg &= (2 << (bitend - bitstart)) - 1;
1833 switch (*c)
1834 {
1835 case 'r':
1836 func (stream, "%s", arm_regnames[reg]);
1837 break;
1838
1839 case 'd':
1840 func (stream, "%d", reg);
1841 break;
1842
1843 case 'H':
1844 func (stream, "%d", reg << 1);
1845 break;
1846
1847 case 'W':
1848 func (stream, "%d", reg << 2);
1849 break;
1850
1851 case 'a':
1852 /* PC-relative address -- the bottom two
58efb6c0
NC
1853 bits of the address are dropped
1854 before the calculation. */
252b5132
RH
1855 info->print_address_func
1856 (((pc + 4) & ~3) + (reg << 2), info);
1857 break;
1858
1859 case 'x':
1860 func (stream, "0x%04x", reg);
1861 break;
1862
1863 case 'I':
1864 reg = ((reg ^ (1 << bitend)) - (1 << bitend));
1865 func (stream, "%d", reg);
1866 break;
1867
1868 case 'B':
1869 reg = ((reg ^ (1 << bitend)) - (1 << bitend));
1870 (*info->print_address_func)
1871 (reg * 2 + pc + 4, info);
1872 break;
1873
1874 default:
5876e06d 1875 abort ();
252b5132
RH
1876 }
1877 }
1878 break;
1879
1880 case '\'':
1881 c++;
1882 if ((given & (1 << bitstart)) != 0)
1883 func (stream, "%c", *c);
1884 break;
1885
1886 case '?':
1887 ++c;
1888 if ((given & (1 << bitstart)) != 0)
1889 func (stream, "%c", *c++);
1890 else
1891 func (stream, "%c", *++c);
1892 break;
1893
1894 default:
5876e06d 1895 abort ();
252b5132
RH
1896 }
1897 }
1898 break;
1899
1900 default:
1901 abort ();
1902 }
1903 }
1904 else
1905 func (stream, "%c", *c);
1906 }
1907 }
1908 return 2;
1909 }
1910 }
1911
58efb6c0 1912 /* No match. */
252b5132
RH
1913 abort ();
1914}
1915
22a398e1
NC
1916/* Disallow mapping symbols ($a, $b, $d, $t etc) from
1917 being displayed in symbol relative addresses. */
1918
1919bfd_boolean
1920arm_symbol_is_valid (asymbol * sym,
1921 struct disassemble_info * info ATTRIBUTE_UNUSED)
1922{
1923 const char * name;
1924
1925 if (sym == NULL)
1926 return FALSE;
1927
1928 name = bfd_asymbol_name (sym);
1929
1930 return (name && *name != '$');
1931}
1932
58efb6c0 1933/* Parse an individual disassembler option. */
baf0cc5e 1934
a3d9c82d
NC
1935void
1936parse_arm_disassembler_option (option)
01c7f630 1937 char * option;
dd92f639 1938{
01c7f630 1939 if (option == NULL)
dd92f639 1940 return;
b34976b6 1941
01c7f630 1942 if (strneq (option, "reg-names-", 10))
dd92f639 1943 {
58efb6c0 1944 int i;
b34976b6 1945
01c7f630 1946 option += 10;
58efb6c0
NC
1947
1948 for (i = NUM_ARM_REGNAMES; i--;)
31e0f3cd 1949 if (strneq (option, regnames[i].name, strlen (regnames[i].name)))
58efb6c0
NC
1950 {
1951 regname_selected = i;
1952 break;
1953 }
b34976b6 1954
58efb6c0 1955 if (i < 0)
31e0f3cd 1956 /* XXX - should break 'option' at following delimiter. */
58efb6c0 1957 fprintf (stderr, _("Unrecognised register name set: %s\n"), option);
dd92f639 1958 }
31e0f3cd 1959 else if (strneq (option, "force-thumb", 11))
01c7f630 1960 force_thumb = 1;
31e0f3cd 1961 else if (strneq (option, "no-force-thumb", 14))
01c7f630 1962 force_thumb = 0;
dd92f639 1963 else
31e0f3cd 1964 /* XXX - should break 'option' at following delimiter. */
58efb6c0 1965 fprintf (stderr, _("Unrecognised disassembler option: %s\n"), option);
b34976b6 1966
dd92f639
NC
1967 return;
1968}
1969
31e0f3cd
NC
1970/* Parse the string of disassembler options, spliting it at whitespaces
1971 or commas. (Whitespace separators supported for backwards compatibility). */
baf0cc5e 1972
01c7f630
NC
1973static void
1974parse_disassembler_options (options)
1975 char * options;
1976{
01c7f630
NC
1977 if (options == NULL)
1978 return;
1979
31e0f3cd 1980 while (*options)
01c7f630 1981 {
31e0f3cd
NC
1982 parse_arm_disassembler_option (options);
1983
1984 /* Skip forward to next seperator. */
1985 while ((*options) && (! ISSPACE (*options)) && (*options != ','))
1986 ++ options;
1987 /* Skip forward past seperators. */
1988 while (ISSPACE (*options) || (*options == ','))
1989 ++ options;
01c7f630 1990 }
01c7f630
NC
1991}
1992
58efb6c0
NC
1993/* NOTE: There are no checks in these routines that
1994 the relevant number of data bytes exist. */
baf0cc5e 1995
58efb6c0
NC
1996static int
1997print_insn (pc, info, little)
252b5132 1998 bfd_vma pc;
5876e06d 1999 struct disassemble_info * info;
b34976b6 2000 bfd_boolean little;
252b5132
RH
2001{
2002 unsigned char b[4];
2003 long given;
2004 int status;
b7693d02 2005 int is_thumb, second_half_valid = 1;
58efb6c0 2006
dd92f639
NC
2007 if (info->disassembler_options)
2008 {
2009 parse_disassembler_options (info->disassembler_options);
b34976b6 2010
58efb6c0 2011 /* To avoid repeated parsing of these options, we remove them here. */
dd92f639
NC
2012 info->disassembler_options = NULL;
2013 }
b34976b6 2014
01c7f630 2015 is_thumb = force_thumb;
b34976b6 2016
01c7f630 2017 if (!is_thumb && info->symbols != NULL)
252b5132 2018 {
5876e06d
NC
2019 if (bfd_asymbol_flavour (*info->symbols) == bfd_target_coff_flavour)
2020 {
2f0ca46a 2021 coff_symbol_type * cs;
b34976b6 2022
5876e06d
NC
2023 cs = coffsymbol (*info->symbols);
2024 is_thumb = ( cs->native->u.syment.n_sclass == C_THUMBEXT
2025 || cs->native->u.syment.n_sclass == C_THUMBSTAT
2026 || cs->native->u.syment.n_sclass == C_THUMBLABEL
2027 || cs->native->u.syment.n_sclass == C_THUMBEXTFUNC
2028 || cs->native->u.syment.n_sclass == C_THUMBSTATFUNC);
2029 }
2030 else if (bfd_asymbol_flavour (*info->symbols) == bfd_target_elf_flavour)
2031 {
2f0ca46a 2032 elf_symbol_type * es;
58efb6c0 2033 unsigned int type;
b34976b6 2034
5876e06d 2035 es = *(elf_symbol_type **)(info->symbols);
58efb6c0 2036 type = ELF_ST_TYPE (es->internal_elf_sym.st_info);
b34976b6 2037
58efb6c0 2038 is_thumb = (type == STT_ARM_TFUNC) || (type == STT_ARM_16BIT);
5876e06d
NC
2039 }
2040 }
b34976b6 2041
252b5132 2042 info->bytes_per_chunk = 4;
58efb6c0 2043 info->display_endian = little ? BFD_ENDIAN_LITTLE : BFD_ENDIAN_BIG;
252b5132 2044
58efb6c0 2045 if (little)
252b5132 2046 {
58efb6c0
NC
2047 status = info->read_memory_func (pc, (bfd_byte *) &b[0], 4, info);
2048 if (status != 0 && is_thumb)
2049 {
2050 info->bytes_per_chunk = 2;
b7693d02 2051 second_half_valid = 0;
b34976b6 2052
58efb6c0
NC
2053 status = info->read_memory_func (pc, (bfd_byte *) b, 2, info);
2054 b[3] = b[2] = 0;
2055 }
b34976b6 2056
58efb6c0
NC
2057 if (status != 0)
2058 {
2059 info->memory_error_func (status, pc, info);
2060 return -1;
2061 }
b34976b6 2062
58efb6c0 2063 given = (b[0]) | (b[1] << 8) | (b[2] << 16) | (b[3] << 24);
252b5132 2064 }
58efb6c0 2065 else
252b5132 2066 {
58efb6c0 2067 status = info->read_memory_func
b7693d02 2068 (WORD_ADDRESS (pc), (bfd_byte *) &b[0], 4, info);
58efb6c0 2069 if (status != 0)
252b5132 2070 {
b7693d02 2071 info->memory_error_func (status, WORD_ADDRESS (pc), info);
58efb6c0
NC
2072 return -1;
2073 }
b34976b6 2074
58efb6c0
NC
2075 if (is_thumb)
2076 {
2077 if (pc & 0x2)
252b5132 2078 {
58efb6c0 2079 given = (b[2] << 8) | b[3];
b34976b6 2080
58efb6c0 2081 status = info->read_memory_func
b7693d02 2082 (WORD_ADDRESS (pc + 4), (bfd_byte *) b, 4, info);
58efb6c0 2083 if (status != 0)
b7693d02
DJ
2084 second_half_valid = 0;
2085 else
2086 given |= (b[0] << 24) | (b[1] << 16);
252b5132 2087 }
58efb6c0
NC
2088 else
2089 given = (b[0] << 8) | b[1] | (b[2] << 24) | (b[3] << 16);
252b5132
RH
2090 }
2091 else
58efb6c0 2092 given = (b[0] << 24) | (b[1] << 16) | (b[2] << 8) | (b[3]);
252b5132 2093 }
b34976b6 2094
6a56ec7e
NC
2095 if (info->flags & INSN_HAS_RELOC)
2096 /* If the instruction has a reloc associated with it, then
2097 the offset field in the instruction will actually be the
2098 addend for the reloc. (We are using REL type relocs).
2099 In such cases, we can ignore the pc when computing
2100 addresses, since the addend is not currently pc-relative. */
2101 pc = 0;
b34976b6 2102
252b5132 2103 if (is_thumb)
5876e06d 2104 status = print_insn_thumb (pc, info, given);
252b5132 2105 else
5876e06d 2106 status = print_insn_arm (pc, info, given);
252b5132 2107
b7693d02
DJ
2108 if (is_thumb && status == 4 && second_half_valid == 0)
2109 {
2110 info->memory_error_func (status, WORD_ADDRESS (pc + 4), info);
2111 return -1;
2112 }
2113
252b5132
RH
2114 return status;
2115}
2116
2117int
58efb6c0 2118print_insn_big_arm (pc, info)
252b5132
RH
2119 bfd_vma pc;
2120 struct disassemble_info * info;
2121{
b34976b6 2122 return print_insn (pc, info, FALSE);
58efb6c0 2123}
01c7f630 2124
58efb6c0
NC
2125int
2126print_insn_little_arm (pc, info)
2127 bfd_vma pc;
2128 struct disassemble_info * info;
2129{
b34976b6 2130 return print_insn (pc, info, TRUE);
58efb6c0 2131}
252b5132 2132
58efb6c0
NC
2133void
2134print_arm_disassembler_options (FILE * stream)
2135{
2136 int i;
252b5132 2137
58efb6c0
NC
2138 fprintf (stream, _("\n\
2139The following ARM specific disassembler options are supported for use with\n\
2140the -M switch:\n"));
b34976b6 2141
58efb6c0
NC
2142 for (i = NUM_ARM_REGNAMES; i--;)
2143 fprintf (stream, " reg-names-%s %*c%s\n",
2144 regnames[i].name,
d5b2f4d6 2145 (int)(14 - strlen (regnames[i].name)), ' ',
58efb6c0
NC
2146 regnames[i].description);
2147
2148 fprintf (stream, " force-thumb Assume all insns are Thumb insns\n");
2149 fprintf (stream, " no-force-thumb Examine preceeding label to determine an insn's type\n\n");
252b5132 2150}
This page took 0.657877 seconds and 4 git commands to generate.