2006-04-26 H.J. Lu <hongjiu.lu@intel.com>
[deliverable/binutils-gdb.git] / opcodes / mips-dis.c
CommitLineData
252b5132 1/* Print mips instructions for GDB, the GNU debugger, or for objdump.
060d22b0 2 Copyright 1989, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
aef6203b 3 2000, 2001, 2002, 2003, 2005
73da6b6b 4 Free Software Foundation, Inc.
252b5132
RH
5 Contributed by Nobuyuki Hikichi(hikichi@sra.co.jp).
6
47b0e7ad 7 This file is part of GDB, GAS, and the GNU binutils.
252b5132 8
47b0e7ad
NC
9 This program 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 2 of the License, or
12 (at your option) any later version.
252b5132 13
47b0e7ad
NC
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
252b5132 18
47b0e7ad
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., 51 Franklin Street - Fifth Floor, Boston,
22 MA 02110-1301, USA. */
252b5132 23
252b5132
RH
24#include "sysdep.h"
25#include "dis-asm.h"
640c0ccd 26#include "libiberty.h"
252b5132
RH
27#include "opcode/mips.h"
28#include "opintl.h"
29
30/* FIXME: These are needed to figure out if the code is mips16 or
31 not. The low bit of the address is often a good indicator. No
32 symbol table is available when this code runs out in an embedded
7f6621cd 33 system as when it is used for disassembler support in a monitor. */
252b5132
RH
34
35#if !defined(EMBEDDED_ENV)
36#define SYMTAB_AVAILABLE 1
37#include "elf-bfd.h"
38#include "elf/mips.h"
39#endif
40
aa5f19f2
NC
41/* Mips instructions are at maximum this many bytes long. */
42#define INSNLEN 4
43
252b5132 44\f
aa5f19f2 45/* FIXME: These should be shared with gdb somehow. */
252b5132 46
47b0e7ad
NC
47struct mips_cp0sel_name
48{
49 unsigned int cp0reg;
50 unsigned int sel;
51 const char * const name;
bbcc0807
CD
52};
53
654c225a
TS
54/* The mips16 registers. */
55static const unsigned int mips16_to_32_reg_map[] =
47b0e7ad 56{
654c225a 57 16, 17, 2, 3, 4, 5, 6, 7
252b5132 58};
fb48caed 59
654c225a
TS
60#define mips16_reg_names(rn) mips_gpr_names[mips16_to_32_reg_map[rn]]
61
62
47b0e7ad
NC
63static const char * const mips_gpr_names_numeric[32] =
64{
640c0ccd
CD
65 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
66 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
67 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
68 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
aa5f19f2
NC
69};
70
47b0e7ad
NC
71static const char * const mips_gpr_names_oldabi[32] =
72{
640c0ccd
CD
73 "zero", "at", "v0", "v1", "a0", "a1", "a2", "a3",
74 "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7",
75 "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
76 "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra"
aa5f19f2
NC
77};
78
47b0e7ad
NC
79static const char * const mips_gpr_names_newabi[32] =
80{
640c0ccd 81 "zero", "at", "v0", "v1", "a0", "a1", "a2", "a3",
0b14f26e 82 "a4", "a5", "a6", "a7", "t0", "t1", "t2", "t3",
640c0ccd
CD
83 "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
84 "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra"
85};
86
47b0e7ad
NC
87static const char * const mips_fpr_names_numeric[32] =
88{
640c0ccd
CD
89 "$f0", "$f1", "$f2", "$f3", "$f4", "$f5", "$f6", "$f7",
90 "$f8", "$f9", "$f10", "$f11", "$f12", "$f13", "$f14", "$f15",
91 "$f16", "$f17", "$f18", "$f19", "$f20", "$f21", "$f22", "$f23",
92 "$f24", "$f25", "$f26", "$f27", "$f28", "$f29", "$f30", "$f31"
93};
94
47b0e7ad
NC
95static const char * const mips_fpr_names_32[32] =
96{
640c0ccd
CD
97 "fv0", "fv0f", "fv1", "fv1f", "ft0", "ft0f", "ft1", "ft1f",
98 "ft2", "ft2f", "ft3", "ft3f", "fa0", "fa0f", "fa1", "fa1f",
99 "ft4", "ft4f", "ft5", "ft5f", "fs0", "fs0f", "fs1", "fs1f",
100 "fs2", "fs2f", "fs3", "fs3f", "fs4", "fs4f", "fs5", "fs5f"
101};
102
47b0e7ad
NC
103static const char * const mips_fpr_names_n32[32] =
104{
640c0ccd
CD
105 "fv0", "ft14", "fv1", "ft15", "ft0", "ft1", "ft2", "ft3",
106 "ft4", "ft5", "ft6", "ft7", "fa0", "fa1", "fa2", "fa3",
107 "fa4", "fa5", "fa6", "fa7", "fs0", "ft8", "fs1", "ft9",
108 "fs2", "ft10", "fs3", "ft11", "fs4", "ft12", "fs5", "ft13"
109};
110
47b0e7ad
NC
111static const char * const mips_fpr_names_64[32] =
112{
640c0ccd
CD
113 "fv0", "ft12", "fv1", "ft13", "ft0", "ft1", "ft2", "ft3",
114 "ft4", "ft5", "ft6", "ft7", "fa0", "fa1", "fa2", "fa3",
115 "fa4", "fa5", "fa6", "fa7", "ft8", "ft9", "ft10", "ft11",
116 "fs0", "fs1", "fs2", "fs3", "fs4", "fs5", "fs6", "fs7"
117};
118
47b0e7ad
NC
119static const char * const mips_cp0_names_numeric[32] =
120{
640c0ccd
CD
121 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
122 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
123 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
124 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
125};
126
47b0e7ad
NC
127static const char * const mips_cp0_names_mips3264[32] =
128{
640c0ccd
CD
129 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
130 "c0_context", "c0_pagemask", "c0_wired", "$7",
131 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
132 "c0_status", "c0_cause", "c0_epc", "c0_prid",
133 "c0_config", "c0_lladdr", "c0_watchlo", "c0_watchhi",
134 "c0_xcontext", "$21", "$22", "c0_debug",
135 "c0_depc", "c0_perfcnt", "c0_errctl", "c0_cacheerr",
136 "c0_taglo", "c0_taghi", "c0_errorepc", "c0_desave",
137};
138
47b0e7ad
NC
139static const struct mips_cp0sel_name mips_cp0sel_names_mips3264[] =
140{
bbcc0807
CD
141 { 16, 1, "c0_config1" },
142 { 16, 2, "c0_config2" },
143 { 16, 3, "c0_config3" },
144 { 18, 1, "c0_watchlo,1" },
145 { 18, 2, "c0_watchlo,2" },
146 { 18, 3, "c0_watchlo,3" },
147 { 18, 4, "c0_watchlo,4" },
148 { 18, 5, "c0_watchlo,5" },
149 { 18, 6, "c0_watchlo,6" },
150 { 18, 7, "c0_watchlo,7" },
151 { 19, 1, "c0_watchhi,1" },
152 { 19, 2, "c0_watchhi,2" },
153 { 19, 3, "c0_watchhi,3" },
154 { 19, 4, "c0_watchhi,4" },
155 { 19, 5, "c0_watchhi,5" },
156 { 19, 6, "c0_watchhi,6" },
157 { 19, 7, "c0_watchhi,7" },
158 { 25, 1, "c0_perfcnt,1" },
159 { 25, 2, "c0_perfcnt,2" },
160 { 25, 3, "c0_perfcnt,3" },
161 { 25, 4, "c0_perfcnt,4" },
162 { 25, 5, "c0_perfcnt,5" },
163 { 25, 6, "c0_perfcnt,6" },
164 { 25, 7, "c0_perfcnt,7" },
165 { 27, 1, "c0_cacheerr,1" },
166 { 27, 2, "c0_cacheerr,2" },
167 { 27, 3, "c0_cacheerr,3" },
168 { 28, 1, "c0_datalo" },
169 { 29, 1, "c0_datahi" }
170};
171
47b0e7ad
NC
172static const char * const mips_cp0_names_mips3264r2[32] =
173{
af7ee8bf
CD
174 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
175 "c0_context", "c0_pagemask", "c0_wired", "c0_hwrena",
176 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
177 "c0_status", "c0_cause", "c0_epc", "c0_prid",
178 "c0_config", "c0_lladdr", "c0_watchlo", "c0_watchhi",
179 "c0_xcontext", "$21", "$22", "c0_debug",
180 "c0_depc", "c0_perfcnt", "c0_errctl", "c0_cacheerr",
181 "c0_taglo", "c0_taghi", "c0_errorepc", "c0_desave",
182};
183
47b0e7ad
NC
184static const struct mips_cp0sel_name mips_cp0sel_names_mips3264r2[] =
185{
bbcc0807 186 { 4, 1, "c0_contextconfig" },
59c455b3
TS
187 { 0, 1, "c0_mvpcontrol" },
188 { 0, 2, "c0_mvpconf0" },
189 { 0, 3, "c0_mvpconf1" },
190 { 1, 1, "c0_vpecontrol" },
191 { 1, 2, "c0_vpeconf0" },
192 { 1, 3, "c0_vpeconf1" },
193 { 1, 4, "c0_yqmask" },
194 { 1, 5, "c0_vpeschedule" },
195 { 1, 6, "c0_vpeschefback" },
196 { 2, 1, "c0_tcstatus" },
197 { 2, 2, "c0_tcbind" },
198 { 2, 3, "c0_tcrestart" },
199 { 2, 4, "c0_tchalt" },
200 { 2, 5, "c0_tccontext" },
201 { 2, 6, "c0_tcschedule" },
202 { 2, 7, "c0_tcschefback" },
bbcc0807 203 { 5, 1, "c0_pagegrain" },
59c455b3
TS
204 { 6, 1, "c0_srsconf0" },
205 { 6, 2, "c0_srsconf1" },
206 { 6, 3, "c0_srsconf2" },
207 { 6, 4, "c0_srsconf3" },
208 { 6, 5, "c0_srsconf4" },
bbcc0807
CD
209 { 12, 1, "c0_intctl" },
210 { 12, 2, "c0_srsctl" },
211 { 12, 3, "c0_srsmap" },
212 { 15, 1, "c0_ebase" },
213 { 16, 1, "c0_config1" },
214 { 16, 2, "c0_config2" },
215 { 16, 3, "c0_config3" },
216 { 18, 1, "c0_watchlo,1" },
217 { 18, 2, "c0_watchlo,2" },
218 { 18, 3, "c0_watchlo,3" },
219 { 18, 4, "c0_watchlo,4" },
220 { 18, 5, "c0_watchlo,5" },
221 { 18, 6, "c0_watchlo,6" },
222 { 18, 7, "c0_watchlo,7" },
223 { 19, 1, "c0_watchhi,1" },
224 { 19, 2, "c0_watchhi,2" },
225 { 19, 3, "c0_watchhi,3" },
226 { 19, 4, "c0_watchhi,4" },
227 { 19, 5, "c0_watchhi,5" },
228 { 19, 6, "c0_watchhi,6" },
229 { 19, 7, "c0_watchhi,7" },
230 { 23, 1, "c0_tracecontrol" },
231 { 23, 2, "c0_tracecontrol2" },
232 { 23, 3, "c0_usertracedata" },
233 { 23, 4, "c0_tracebpc" },
234 { 25, 1, "c0_perfcnt,1" },
235 { 25, 2, "c0_perfcnt,2" },
236 { 25, 3, "c0_perfcnt,3" },
237 { 25, 4, "c0_perfcnt,4" },
238 { 25, 5, "c0_perfcnt,5" },
239 { 25, 6, "c0_perfcnt,6" },
240 { 25, 7, "c0_perfcnt,7" },
241 { 27, 1, "c0_cacheerr,1" },
242 { 27, 2, "c0_cacheerr,2" },
243 { 27, 3, "c0_cacheerr,3" },
244 { 28, 1, "c0_datalo" },
245 { 28, 2, "c0_taglo1" },
246 { 28, 3, "c0_datalo1" },
247 { 28, 4, "c0_taglo2" },
248 { 28, 5, "c0_datalo2" },
249 { 28, 6, "c0_taglo3" },
250 { 28, 7, "c0_datalo3" },
251 { 29, 1, "c0_datahi" },
252 { 29, 2, "c0_taghi1" },
253 { 29, 3, "c0_datahi1" },
254 { 29, 4, "c0_taghi2" },
255 { 29, 5, "c0_datahi2" },
256 { 29, 6, "c0_taghi3" },
257 { 29, 7, "c0_datahi3" },
258};
259
640c0ccd 260/* SB-1: MIPS64 (mips_cp0_names_mips3264) with minor mods. */
47b0e7ad
NC
261static const char * const mips_cp0_names_sb1[32] =
262{
640c0ccd
CD
263 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
264 "c0_context", "c0_pagemask", "c0_wired", "$7",
265 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
266 "c0_status", "c0_cause", "c0_epc", "c0_prid",
267 "c0_config", "c0_lladdr", "c0_watchlo", "c0_watchhi",
268 "c0_xcontext", "$21", "$22", "c0_debug",
269 "c0_depc", "c0_perfcnt", "c0_errctl", "c0_cacheerr_i",
270 "c0_taglo_i", "c0_taghi_i", "c0_errorepc", "c0_desave",
271};
272
47b0e7ad
NC
273static const struct mips_cp0sel_name mips_cp0sel_names_sb1[] =
274{
bbcc0807
CD
275 { 16, 1, "c0_config1" },
276 { 18, 1, "c0_watchlo,1" },
277 { 19, 1, "c0_watchhi,1" },
278 { 22, 0, "c0_perftrace" },
279 { 23, 3, "c0_edebug" },
280 { 25, 1, "c0_perfcnt,1" },
281 { 25, 2, "c0_perfcnt,2" },
282 { 25, 3, "c0_perfcnt,3" },
283 { 25, 4, "c0_perfcnt,4" },
284 { 25, 5, "c0_perfcnt,5" },
285 { 25, 6, "c0_perfcnt,6" },
286 { 25, 7, "c0_perfcnt,7" },
287 { 26, 1, "c0_buserr_pa" },
288 { 27, 1, "c0_cacheerr_d" },
289 { 27, 3, "c0_cacheerr_d_pa" },
290 { 28, 1, "c0_datalo_i" },
291 { 28, 2, "c0_taglo_d" },
292 { 28, 3, "c0_datalo_d" },
293 { 29, 1, "c0_datahi_i" },
294 { 29, 2, "c0_taghi_d" },
295 { 29, 3, "c0_datahi_d" },
296};
297
47b0e7ad
NC
298static const char * const mips_hwr_names_numeric[32] =
299{
af7ee8bf
CD
300 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
301 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
302 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
303 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
304};
305
47b0e7ad
NC
306static const char * const mips_hwr_names_mips3264r2[32] =
307{
af7ee8bf
CD
308 "hwr_cpunum", "hwr_synci_step", "hwr_cc", "hwr_ccres",
309 "$4", "$5", "$6", "$7",
310 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
311 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
312 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
313};
314
47b0e7ad
NC
315struct mips_abi_choice
316{
317 const char * name;
640c0ccd
CD
318 const char * const *gpr_names;
319 const char * const *fpr_names;
320};
321
47b0e7ad
NC
322struct mips_abi_choice mips_abi_choices[] =
323{
640c0ccd
CD
324 { "numeric", mips_gpr_names_numeric, mips_fpr_names_numeric },
325 { "32", mips_gpr_names_oldabi, mips_fpr_names_32 },
326 { "n32", mips_gpr_names_newabi, mips_fpr_names_n32 },
327 { "64", mips_gpr_names_newabi, mips_fpr_names_64 },
328};
329
47b0e7ad
NC
330struct mips_arch_choice
331{
640c0ccd
CD
332 const char *name;
333 int bfd_mach_valid;
334 unsigned long bfd_mach;
335 int processor;
336 int isa;
337 const char * const *cp0_names;
bbcc0807
CD
338 const struct mips_cp0sel_name *cp0sel_names;
339 unsigned int cp0sel_names_len;
af7ee8bf 340 const char * const *hwr_names;
640c0ccd
CD
341};
342
47b0e7ad
NC
343const struct mips_arch_choice mips_arch_choices[] =
344{
640c0ccd 345 { "numeric", 0, 0, 0, 0,
bbcc0807
CD
346 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
347
640c0ccd 348 { "r3000", 1, bfd_mach_mips3000, CPU_R3000, ISA_MIPS1,
bbcc0807 349 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 350 { "r3900", 1, bfd_mach_mips3900, CPU_R3900, ISA_MIPS1,
bbcc0807 351 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 352 { "r4000", 1, bfd_mach_mips4000, CPU_R4000, ISA_MIPS3,
bbcc0807 353 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 354 { "r4010", 1, bfd_mach_mips4010, CPU_R4010, ISA_MIPS2,
bbcc0807 355 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 356 { "vr4100", 1, bfd_mach_mips4100, CPU_VR4100, ISA_MIPS3,
bbcc0807 357 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 358 { "vr4111", 1, bfd_mach_mips4111, CPU_R4111, ISA_MIPS3,
bbcc0807 359 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 360 { "vr4120", 1, bfd_mach_mips4120, CPU_VR4120, ISA_MIPS3,
bbcc0807 361 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 362 { "r4300", 1, bfd_mach_mips4300, CPU_R4300, ISA_MIPS3,
bbcc0807 363 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 364 { "r4400", 1, bfd_mach_mips4400, CPU_R4400, ISA_MIPS3,
bbcc0807 365 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 366 { "r4600", 1, bfd_mach_mips4600, CPU_R4600, ISA_MIPS3,
bbcc0807 367 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 368 { "r4650", 1, bfd_mach_mips4650, CPU_R4650, ISA_MIPS3,
bbcc0807 369 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 370 { "r5000", 1, bfd_mach_mips5000, CPU_R5000, ISA_MIPS4,
bbcc0807 371 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 372 { "vr5400", 1, bfd_mach_mips5400, CPU_VR5400, ISA_MIPS4,
bbcc0807 373 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 374 { "vr5500", 1, bfd_mach_mips5500, CPU_VR5500, ISA_MIPS4,
bbcc0807 375 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 376 { "r6000", 1, bfd_mach_mips6000, CPU_R6000, ISA_MIPS2,
bbcc0807 377 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
5a7ea749
RS
378 { "rm7000", 1, bfd_mach_mips7000, CPU_RM7000, ISA_MIPS4,
379 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
380 { "rm9000", 1, bfd_mach_mips7000, CPU_RM7000, ISA_MIPS4,
381 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 382 { "r8000", 1, bfd_mach_mips8000, CPU_R8000, ISA_MIPS4,
bbcc0807 383 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 384 { "r10000", 1, bfd_mach_mips10000, CPU_R10000, ISA_MIPS4,
bbcc0807 385 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 386 { "r12000", 1, bfd_mach_mips12000, CPU_R12000, ISA_MIPS4,
bbcc0807 387 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd 388 { "mips5", 1, bfd_mach_mips5, CPU_MIPS5, ISA_MIPS5,
bbcc0807
CD
389 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
390
640c0ccd
CD
391 /* For stock MIPS32, disassemble all applicable MIPS-specified ASEs.
392 Note that MIPS-3D and MDMX are not applicable to MIPS32. (See
393 _MIPS32 Architecture For Programmers Volume I: Introduction to the
394 MIPS32 Architecture_ (MIPS Document Number MD00082, Revision 0.95),
395 page 1. */
396 { "mips32", 1, bfd_mach_mipsisa32, CPU_MIPS32,
fd25c5a9 397 ISA_MIPS32 | INSN_MIPS16 | INSN_DSP,
bbcc0807
CD
398 mips_cp0_names_mips3264,
399 mips_cp0sel_names_mips3264, ARRAY_SIZE (mips_cp0sel_names_mips3264),
400 mips_hwr_names_numeric },
401
af7ee8bf 402 { "mips32r2", 1, bfd_mach_mipsisa32r2, CPU_MIPS32R2,
61cc0267 403 ISA_MIPS32R2 | INSN_MIPS16 | INSN_DSP | INSN_MT,
bbcc0807
CD
404 mips_cp0_names_mips3264r2,
405 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
406 mips_hwr_names_mips3264r2 },
407
640c0ccd
CD
408 /* For stock MIPS64, disassemble all applicable MIPS-specified ASEs. */
409 { "mips64", 1, bfd_mach_mipsisa64, CPU_MIPS64,
fd25c5a9 410 ISA_MIPS64 | INSN_MIPS16 | INSN_MIPS3D | INSN_MDMX | INSN_DSP,
bbcc0807
CD
411 mips_cp0_names_mips3264,
412 mips_cp0sel_names_mips3264, ARRAY_SIZE (mips_cp0sel_names_mips3264),
413 mips_hwr_names_numeric },
414
5f74bc13 415 { "mips64r2", 1, bfd_mach_mipsisa64r2, CPU_MIPS64R2,
fd25c5a9 416 ISA_MIPS64R2 | INSN_MIPS16 | INSN_MIPS3D | INSN_MDMX | INSN_DSP,
5f74bc13
CD
417 mips_cp0_names_mips3264r2,
418 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
419 mips_hwr_names_mips3264r2 },
420
640c0ccd
CD
421 { "sb1", 1, bfd_mach_mips_sb1, CPU_SB1,
422 ISA_MIPS64 | INSN_MIPS3D | INSN_SB1,
bbcc0807
CD
423 mips_cp0_names_sb1,
424 mips_cp0sel_names_sb1, ARRAY_SIZE (mips_cp0sel_names_sb1),
425 mips_hwr_names_numeric },
640c0ccd
CD
426
427 /* This entry, mips16, is here only for ISA/processor selection; do
428 not print its name. */
429 { "", 1, bfd_mach_mips16, CPU_MIPS16, ISA_MIPS3 | INSN_MIPS16,
bbcc0807 430 mips_cp0_names_numeric, NULL, 0, mips_hwr_names_numeric },
640c0ccd
CD
431};
432
433/* ISA and processor type to disassemble for, and register names to use.
434 set_default_mips_dis_options and parse_mips_dis_options fill in these
435 values. */
436static int mips_processor;
437static int mips_isa;
438static const char * const *mips_gpr_names;
439static const char * const *mips_fpr_names;
440static const char * const *mips_cp0_names;
bbcc0807
CD
441static const struct mips_cp0sel_name *mips_cp0sel_names;
442static int mips_cp0sel_names_len;
af7ee8bf 443static const char * const *mips_hwr_names;
640c0ccd 444
986e18a5 445/* Other options */
47b0e7ad 446static int no_aliases; /* If set disassemble as most general inst. */
640c0ccd
CD
447\f
448static const struct mips_abi_choice *
47b0e7ad 449choose_abi_by_name (const char *name, unsigned int namelen)
640c0ccd
CD
450{
451 const struct mips_abi_choice *c;
452 unsigned int i;
453
454 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_abi_choices) && c == NULL; i++)
47b0e7ad
NC
455 if (strncmp (mips_abi_choices[i].name, name, namelen) == 0
456 && strlen (mips_abi_choices[i].name) == namelen)
457 c = &mips_abi_choices[i];
458
640c0ccd
CD
459 return c;
460}
461
462static const struct mips_arch_choice *
47b0e7ad 463choose_arch_by_name (const char *name, unsigned int namelen)
640c0ccd
CD
464{
465 const struct mips_arch_choice *c = NULL;
466 unsigned int i;
467
468 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_arch_choices) && c == NULL; i++)
47b0e7ad
NC
469 if (strncmp (mips_arch_choices[i].name, name, namelen) == 0
470 && strlen (mips_arch_choices[i].name) == namelen)
471 c = &mips_arch_choices[i];
472
640c0ccd
CD
473 return c;
474}
475
476static const struct mips_arch_choice *
47b0e7ad 477choose_arch_by_number (unsigned long mach)
640c0ccd
CD
478{
479 static unsigned long hint_bfd_mach;
480 static const struct mips_arch_choice *hint_arch_choice;
481 const struct mips_arch_choice *c;
482 unsigned int i;
483
484 /* We optimize this because even if the user specifies no
485 flags, this will be done for every instruction! */
486 if (hint_bfd_mach == mach
487 && hint_arch_choice != NULL
488 && hint_arch_choice->bfd_mach == hint_bfd_mach)
489 return hint_arch_choice;
490
491 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_arch_choices) && c == NULL; i++)
492 {
493 if (mips_arch_choices[i].bfd_mach_valid
494 && mips_arch_choices[i].bfd_mach == mach)
495 {
496 c = &mips_arch_choices[i];
497 hint_bfd_mach = mach;
498 hint_arch_choice = c;
499 }
500 }
501 return c;
502}
503
47b0e7ad
NC
504/* Check if the object uses NewABI conventions. */
505
506static int
507is_newabi (Elf_Internal_Ehdr *header)
508{
509 /* There are no old-style ABIs which use 64-bit ELF. */
510 if (header->e_ident[EI_CLASS] == ELFCLASS64)
511 return 1;
512
513 /* If a 32-bit ELF file, n32 is a new-style ABI. */
514 if ((header->e_flags & EF_MIPS_ABI2) != 0)
515 return 1;
516
517 return 0;
518}
519
520static void
521set_default_mips_dis_options (struct disassemble_info *info)
640c0ccd
CD
522{
523 const struct mips_arch_choice *chosen_arch;
524
525 /* Defaults: mipsIII/r3000 (?!), (o)32-style ("oldabi") GPR names,
af7ee8bf 526 and numeric FPR, CP0 register, and HWR names. */
640c0ccd
CD
527 mips_isa = ISA_MIPS3;
528 mips_processor = CPU_R3000;
529 mips_gpr_names = mips_gpr_names_oldabi;
530 mips_fpr_names = mips_fpr_names_numeric;
531 mips_cp0_names = mips_cp0_names_numeric;
bbcc0807
CD
532 mips_cp0sel_names = NULL;
533 mips_cp0sel_names_len = 0;
af7ee8bf 534 mips_hwr_names = mips_hwr_names_numeric;
986e18a5 535 no_aliases = 0;
640c0ccd
CD
536
537 /* If an ELF "newabi" binary, use the n32/(n)64 GPR names. */
fec06546 538 if (info->flavour == bfd_target_elf_flavour && info->section != NULL)
640c0ccd
CD
539 {
540 Elf_Internal_Ehdr *header;
541
fec06546 542 header = elf_elfheader (info->section->owner);
640c0ccd
CD
543 if (is_newabi (header))
544 mips_gpr_names = mips_gpr_names_newabi;
545 }
546
547 /* Set ISA, architecture, and cp0 register names as best we can. */
548#if ! SYMTAB_AVAILABLE
549 /* This is running out on a target machine, not in a host tool.
550 FIXME: Where does mips_target_info come from? */
551 target_processor = mips_target_info.processor;
552 mips_isa = mips_target_info.isa;
553#else
554 chosen_arch = choose_arch_by_number (info->mach);
555 if (chosen_arch != NULL)
556 {
557 mips_processor = chosen_arch->processor;
558 mips_isa = chosen_arch->isa;
bbcc0807
CD
559 mips_cp0_names = chosen_arch->cp0_names;
560 mips_cp0sel_names = chosen_arch->cp0sel_names;
561 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
562 mips_hwr_names = chosen_arch->hwr_names;
640c0ccd
CD
563 }
564#endif
565}
566
47b0e7ad
NC
567static void
568parse_mips_dis_option (const char *option, unsigned int len)
640c0ccd
CD
569{
570 unsigned int i, optionlen, vallen;
571 const char *val;
572 const struct mips_abi_choice *chosen_abi;
573 const struct mips_arch_choice *chosen_arch;
574
986e18a5
FF
575 /* Try to match options that are simple flags */
576 if (strncmp (option, "no-aliases", 10) == 0)
577 {
578 no_aliases = 1;
579 return;
580 }
581
640c0ccd
CD
582 /* Look for the = that delimits the end of the option name. */
583 for (i = 0; i < len; i++)
47b0e7ad
NC
584 if (option[i] == '=')
585 break;
586
640c0ccd
CD
587 if (i == 0) /* Invalid option: no name before '='. */
588 return;
589 if (i == len) /* Invalid option: no '='. */
590 return;
591 if (i == (len - 1)) /* Invalid option: no value after '='. */
592 return;
593
594 optionlen = i;
595 val = option + (optionlen + 1);
596 vallen = len - (optionlen + 1);
597
47b0e7ad
NC
598 if (strncmp ("gpr-names", option, optionlen) == 0
599 && strlen ("gpr-names") == optionlen)
640c0ccd
CD
600 {
601 chosen_abi = choose_abi_by_name (val, vallen);
bbcc0807 602 if (chosen_abi != NULL)
640c0ccd
CD
603 mips_gpr_names = chosen_abi->gpr_names;
604 return;
605 }
606
47b0e7ad
NC
607 if (strncmp ("fpr-names", option, optionlen) == 0
608 && strlen ("fpr-names") == optionlen)
640c0ccd
CD
609 {
610 chosen_abi = choose_abi_by_name (val, vallen);
bbcc0807 611 if (chosen_abi != NULL)
640c0ccd
CD
612 mips_fpr_names = chosen_abi->fpr_names;
613 return;
614 }
615
47b0e7ad
NC
616 if (strncmp ("cp0-names", option, optionlen) == 0
617 && strlen ("cp0-names") == optionlen)
640c0ccd
CD
618 {
619 chosen_arch = choose_arch_by_name (val, vallen);
bbcc0807
CD
620 if (chosen_arch != NULL)
621 {
622 mips_cp0_names = chosen_arch->cp0_names;
623 mips_cp0sel_names = chosen_arch->cp0sel_names;
624 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
625 }
640c0ccd
CD
626 return;
627 }
628
47b0e7ad
NC
629 if (strncmp ("hwr-names", option, optionlen) == 0
630 && strlen ("hwr-names") == optionlen)
af7ee8bf
CD
631 {
632 chosen_arch = choose_arch_by_name (val, vallen);
bbcc0807 633 if (chosen_arch != NULL)
af7ee8bf
CD
634 mips_hwr_names = chosen_arch->hwr_names;
635 return;
636 }
637
47b0e7ad
NC
638 if (strncmp ("reg-names", option, optionlen) == 0
639 && strlen ("reg-names") == optionlen)
640c0ccd
CD
640 {
641 /* We check both ABI and ARCH here unconditionally, so
642 that "numeric" will do the desirable thing: select
643 numeric register names for all registers. Other than
644 that, a given name probably won't match both. */
645 chosen_abi = choose_abi_by_name (val, vallen);
646 if (chosen_abi != NULL)
647 {
bbcc0807
CD
648 mips_gpr_names = chosen_abi->gpr_names;
649 mips_fpr_names = chosen_abi->fpr_names;
640c0ccd
CD
650 }
651 chosen_arch = choose_arch_by_name (val, vallen);
652 if (chosen_arch != NULL)
653 {
bbcc0807
CD
654 mips_cp0_names = chosen_arch->cp0_names;
655 mips_cp0sel_names = chosen_arch->cp0sel_names;
656 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
657 mips_hwr_names = chosen_arch->hwr_names;
640c0ccd
CD
658 }
659 return;
660 }
661
662 /* Invalid option. */
663}
664
47b0e7ad
NC
665static void
666parse_mips_dis_options (const char *options)
640c0ccd
CD
667{
668 const char *option_end;
669
670 if (options == NULL)
671 return;
672
673 while (*options != '\0')
674 {
675 /* Skip empty options. */
676 if (*options == ',')
677 {
678 options++;
679 continue;
680 }
681
682 /* We know that *options is neither NUL or a comma. */
683 option_end = options + 1;
684 while (*option_end != ',' && *option_end != '\0')
685 option_end++;
686
687 parse_mips_dis_option (options, option_end - options);
688
689 /* Go on to the next one. If option_end points to a comma, it
690 will be skipped above. */
691 options = option_end;
692 }
693}
694
bbcc0807 695static const struct mips_cp0sel_name *
47b0e7ad
NC
696lookup_mips_cp0sel_name (const struct mips_cp0sel_name *names,
697 unsigned int len,
698 unsigned int cp0reg,
699 unsigned int sel)
bbcc0807
CD
700{
701 unsigned int i;
702
703 for (i = 0; i < len; i++)
704 if (names[i].cp0reg == cp0reg && names[i].sel == sel)
705 return &names[i];
706 return NULL;
707}
252b5132 708\f
7f6621cd 709/* Print insn arguments for 32/64-bit code. */
aa5f19f2 710
794ac9d0 711static void
47b0e7ad
NC
712print_insn_args (const char *d,
713 register unsigned long int l,
714 bfd_vma pc,
cc0ca239
TS
715 struct disassemble_info *info,
716 const struct mips_opcode *opp)
252b5132 717{
794ac9d0 718 int op, delta;
440cc0bc
CD
719 unsigned int lsb, msb, msbd;
720
721 lsb = 0;
252b5132 722
794ac9d0 723 for (; *d != '\0'; d++)
252b5132 724 {
af7ee8bf
CD
725 switch (*d)
726 {
794ac9d0
CD
727 case ',':
728 case '(':
729 case ')':
730 case '[':
731 case ']':
732 (*info->fprintf_func) (info->stream, "%c", *d);
733 break;
734
735 case '+':
736 /* Extension character; switch for second char. */
737 d++;
738 switch (*d)
739 {
740 case '\0':
741 /* xgettext:c-format */
742 (*info->fprintf_func) (info->stream,
743 _("# internal error, incomplete extension sequence (+)"));
744 return;
745
746 case 'A':
440cc0bc
CD
747 lsb = (l >> OP_SH_SHAMT) & OP_MASK_SHAMT;
748 (*info->fprintf_func) (info->stream, "0x%x", lsb);
794ac9d0
CD
749 break;
750
751 case 'B':
440cc0bc
CD
752 msb = (l >> OP_SH_INSMSB) & OP_MASK_INSMSB;
753 (*info->fprintf_func) (info->stream, "0x%x", msb - lsb + 1);
794ac9d0
CD
754 break;
755
756 case 'C':
5f74bc13 757 case 'H':
440cc0bc
CD
758 msbd = (l >> OP_SH_EXTMSBD) & OP_MASK_EXTMSBD;
759 (*info->fprintf_func) (info->stream, "0x%x", msbd + 1);
794ac9d0
CD
760 break;
761
762 case 'D':
763 {
764 const struct mips_cp0sel_name *n;
765 unsigned int cp0reg, sel;
766
767 cp0reg = (l >> OP_SH_RD) & OP_MASK_RD;
768 sel = (l >> OP_SH_SEL) & OP_MASK_SEL;
769
770 /* CP0 register including 'sel' code for mtcN (et al.), to be
771 printed textually if known. If not known, print both
772 CP0 register name and sel numerically since CP0 register
773 with sel 0 may have a name unrelated to register being
774 printed. */
775 n = lookup_mips_cp0sel_name(mips_cp0sel_names,
776 mips_cp0sel_names_len, cp0reg, sel);
777 if (n != NULL)
778 (*info->fprintf_func) (info->stream, "%s", n->name);
779 else
780 (*info->fprintf_func) (info->stream, "$%d,%d", cp0reg, sel);
781 break;
782 }
783
5f74bc13
CD
784 case 'E':
785 lsb = ((l >> OP_SH_SHAMT) & OP_MASK_SHAMT) + 32;
786 (*info->fprintf_func) (info->stream, "0x%x", lsb);
787 break;
788
789 case 'F':
790 msb = ((l >> OP_SH_INSMSB) & OP_MASK_INSMSB) + 32;
791 (*info->fprintf_func) (info->stream, "0x%x", msb - lsb + 1);
792 break;
793
794 case 'G':
795 msbd = ((l >> OP_SH_EXTMSBD) & OP_MASK_EXTMSBD) + 32;
796 (*info->fprintf_func) (info->stream, "0x%x", msbd + 1);
797 break;
798
61cc0267
CF
799 case 't': /* Coprocessor 0 reg name */
800 (*info->fprintf_func) (info->stream, "%s",
801 mips_cp0_names[(l >> OP_SH_RT) &
802 OP_MASK_RT]);
803 break;
804
805 case 'T': /* Coprocessor 0 reg name */
806 {
807 const struct mips_cp0sel_name *n;
808 unsigned int cp0reg, sel;
809
810 cp0reg = (l >> OP_SH_RT) & OP_MASK_RT;
811 sel = (l >> OP_SH_SEL) & OP_MASK_SEL;
812
813 /* CP0 register including 'sel' code for mftc0, to be
814 printed textually if known. If not known, print both
815 CP0 register name and sel numerically since CP0 register
816 with sel 0 may have a name unrelated to register being
817 printed. */
818 n = lookup_mips_cp0sel_name(mips_cp0sel_names,
819 mips_cp0sel_names_len, cp0reg, sel);
820 if (n != NULL)
821 (*info->fprintf_func) (info->stream, "%s", n->name);
822 else
823 (*info->fprintf_func) (info->stream, "$%d,%d", cp0reg, sel);
824 break;
825 }
826
794ac9d0
CD
827 default:
828 /* xgettext:c-format */
829 (*info->fprintf_func) (info->stream,
830 _("# internal error, undefined extension sequence (+%c)"),
831 *d);
832 return;
833 }
834 break;
835
fd25c5a9
CF
836 case '3':
837 (*info->fprintf_func) (info->stream, "0x%lx",
838 (l >> OP_SH_SA3) & OP_MASK_SA3);
839 break;
840
841 case '4':
842 (*info->fprintf_func) (info->stream, "0x%lx",
843 (l >> OP_SH_SA4) & OP_MASK_SA4);
844 break;
845
846 case '5':
847 (*info->fprintf_func) (info->stream, "0x%lx",
848 (l >> OP_SH_IMM8) & OP_MASK_IMM8);
849 break;
850
851 case '6':
852 (*info->fprintf_func) (info->stream, "0x%lx",
853 (l >> OP_SH_RS) & OP_MASK_RS);
854 break;
855
856 case '7':
857 (*info->fprintf_func) (info->stream, "$ac%ld",
858 (l >> OP_SH_DSPACC) & OP_MASK_DSPACC);
859 break;
860
861 case '8':
862 (*info->fprintf_func) (info->stream, "0x%lx",
863 (l >> OP_SH_WRDSP) & OP_MASK_WRDSP);
864 break;
865
866 case '9':
867 (*info->fprintf_func) (info->stream, "$ac%ld",
868 (l >> OP_SH_DSPACC_S) & OP_MASK_DSPACC_S);
869 break;
870
871 case '0': /* dsp 6-bit signed immediate in bit 20 */
872 delta = ((l >> OP_SH_DSPSFT) & OP_MASK_DSPSFT);
873 if (delta & 0x20) /* test sign bit */
874 delta |= ~OP_MASK_DSPSFT;
875 (*info->fprintf_func) (info->stream, "%d", delta);
876 break;
877
878 case ':': /* dsp 7-bit signed immediate in bit 19 */
879 delta = ((l >> OP_SH_DSPSFT_7) & OP_MASK_DSPSFT_7);
880 if (delta & 0x40) /* test sign bit */
881 delta |= ~OP_MASK_DSPSFT_7;
882 (*info->fprintf_func) (info->stream, "%d", delta);
883 break;
884
885 case '\'':
886 (*info->fprintf_func) (info->stream, "0x%lx",
887 (l >> OP_SH_RDDSP) & OP_MASK_RDDSP);
888 break;
889
890 case '@': /* dsp 10-bit signed immediate in bit 16 */
891 delta = ((l >> OP_SH_IMM10) & OP_MASK_IMM10);
892 if (delta & 0x200) /* test sign bit */
893 delta |= ~OP_MASK_IMM10;
894 (*info->fprintf_func) (info->stream, "%d", delta);
895 break;
896
61cc0267
CF
897 case '!':
898 (*info->fprintf_func) (info->stream, "%ld",
899 (l >> OP_SH_MT_U) & OP_MASK_MT_U);
900 break;
901
902 case '$':
903 (*info->fprintf_func) (info->stream, "%ld",
904 (l >> OP_SH_MT_H) & OP_MASK_MT_H);
905 break;
906
907 case '*':
908 (*info->fprintf_func) (info->stream, "$ac%ld",
909 (l >> OP_SH_MTACC_T) & OP_MASK_MTACC_T);
910 break;
911
912 case '&':
913 (*info->fprintf_func) (info->stream, "$ac%ld",
914 (l >> OP_SH_MTACC_D) & OP_MASK_MTACC_D);
915 break;
916
917 case 'g':
918 /* Coprocessor register for CTTC1, MTTC2, MTHC2, CTTC2. */
919 (*info->fprintf_func) (info->stream, "$%ld",
920 (l >> OP_SH_RD) & OP_MASK_RD);
921 break;
922
794ac9d0
CD
923 case 's':
924 case 'b':
925 case 'r':
926 case 'v':
927 (*info->fprintf_func) (info->stream, "%s",
928 mips_gpr_names[(l >> OP_SH_RS) & OP_MASK_RS]);
929 break;
930
931 case 't':
932 case 'w':
933 (*info->fprintf_func) (info->stream, "%s",
934 mips_gpr_names[(l >> OP_SH_RT) & OP_MASK_RT]);
935 break;
936
937 case 'i':
938 case 'u':
0fd3a477 939 (*info->fprintf_func) (info->stream, "0x%lx",
794ac9d0
CD
940 (l >> OP_SH_IMMEDIATE) & OP_MASK_IMMEDIATE);
941 break;
942
943 case 'j': /* Same as i, but sign-extended. */
944 case 'o':
945 delta = (l >> OP_SH_DELTA) & OP_MASK_DELTA;
946 if (delta & 0x8000)
947 delta |= ~0xffff;
948 (*info->fprintf_func) (info->stream, "%d",
949 delta);
950 break;
951
952 case 'h':
953 (*info->fprintf_func) (info->stream, "0x%x",
954 (unsigned int) ((l >> OP_SH_PREFX)
955 & OP_MASK_PREFX));
956 break;
957
958 case 'k':
959 (*info->fprintf_func) (info->stream, "0x%x",
960 (unsigned int) ((l >> OP_SH_CACHE)
961 & OP_MASK_CACHE));
962 break;
963
964 case 'a':
965 info->target = (((pc + 4) & ~(bfd_vma) 0x0fffffff)
966 | (((l >> OP_SH_TARGET) & OP_MASK_TARGET) << 2));
967 (*info->print_address_func) (info->target, info);
968 break;
969
970 case 'p':
971 /* Sign extend the displacement. */
972 delta = (l >> OP_SH_DELTA) & OP_MASK_DELTA;
973 if (delta & 0x8000)
974 delta |= ~0xffff;
975 info->target = (delta << 2) + pc + INSNLEN;
976 (*info->print_address_func) (info->target, info);
977 break;
978
979 case 'd':
980 (*info->fprintf_func) (info->stream, "%s",
981 mips_gpr_names[(l >> OP_SH_RD) & OP_MASK_RD]);
982 break;
983
984 case 'U':
985 {
986 /* First check for both rd and rt being equal. */
987 unsigned int reg = (l >> OP_SH_RD) & OP_MASK_RD;
988 if (reg == ((l >> OP_SH_RT) & OP_MASK_RT))
989 (*info->fprintf_func) (info->stream, "%s",
990 mips_gpr_names[reg]);
991 else
992 {
993 /* If one is zero use the other. */
994 if (reg == 0)
995 (*info->fprintf_func) (info->stream, "%s",
996 mips_gpr_names[(l >> OP_SH_RT) & OP_MASK_RT]);
997 else if (((l >> OP_SH_RT) & OP_MASK_RT) == 0)
998 (*info->fprintf_func) (info->stream, "%s",
999 mips_gpr_names[reg]);
1000 else /* Bogus, result depends on processor. */
1001 (*info->fprintf_func) (info->stream, "%s or %s",
1002 mips_gpr_names[reg],
1003 mips_gpr_names[(l >> OP_SH_RT) & OP_MASK_RT]);
1004 }
1005 }
1006 break;
1007
1008 case 'z':
1009 (*info->fprintf_func) (info->stream, "%s", mips_gpr_names[0]);
1010 break;
1011
1012 case '<':
0fd3a477 1013 (*info->fprintf_func) (info->stream, "0x%lx",
af7ee8bf
CD
1014 (l >> OP_SH_SHAMT) & OP_MASK_SHAMT);
1015 break;
794ac9d0
CD
1016
1017 case 'c':
0fd3a477 1018 (*info->fprintf_func) (info->stream, "0x%lx",
794ac9d0
CD
1019 (l >> OP_SH_CODE) & OP_MASK_CODE);
1020 break;
1021
1022 case 'q':
0fd3a477 1023 (*info->fprintf_func) (info->stream, "0x%lx",
794ac9d0 1024 (l >> OP_SH_CODE2) & OP_MASK_CODE2);
af7ee8bf
CD
1025 break;
1026
1027 case 'C':
0fd3a477 1028 (*info->fprintf_func) (info->stream, "0x%lx",
794ac9d0
CD
1029 (l >> OP_SH_COPZ) & OP_MASK_COPZ);
1030 break;
1031
1032 case 'B':
0fd3a477
JW
1033 (*info->fprintf_func) (info->stream, "0x%lx",
1034
794ac9d0
CD
1035 (l >> OP_SH_CODE20) & OP_MASK_CODE20);
1036 break;
1037
1038 case 'J':
0fd3a477 1039 (*info->fprintf_func) (info->stream, "0x%lx",
794ac9d0
CD
1040 (l >> OP_SH_CODE19) & OP_MASK_CODE19);
1041 break;
1042
1043 case 'S':
1044 case 'V':
1045 (*info->fprintf_func) (info->stream, "%s",
1046 mips_fpr_names[(l >> OP_SH_FS) & OP_MASK_FS]);
1047 break;
1048
1049 case 'T':
1050 case 'W':
1051 (*info->fprintf_func) (info->stream, "%s",
1052 mips_fpr_names[(l >> OP_SH_FT) & OP_MASK_FT]);
af7ee8bf
CD
1053 break;
1054
bbcc0807 1055 case 'D':
794ac9d0
CD
1056 (*info->fprintf_func) (info->stream, "%s",
1057 mips_fpr_names[(l >> OP_SH_FD) & OP_MASK_FD]);
1058 break;
1059
1060 case 'R':
1061 (*info->fprintf_func) (info->stream, "%s",
1062 mips_fpr_names[(l >> OP_SH_FR) & OP_MASK_FR]);
1063 break;
1064
1065 case 'E':
1066 /* Coprocessor register for lwcN instructions, et al.
1067
1068 Note that there is no load/store cp0 instructions, and
1069 that FPU (cp1) instructions disassemble this field using
1070 'T' format. Therefore, until we gain understanding of
1071 cp2 register names, we can simply print the register
1072 numbers. */
0fd3a477 1073 (*info->fprintf_func) (info->stream, "$%ld",
794ac9d0
CD
1074 (l >> OP_SH_RT) & OP_MASK_RT);
1075 break;
1076
1077 case 'G':
1078 /* Coprocessor register for mtcN instructions, et al. Note
1079 that FPU (cp1) instructions disassemble this field using
1080 'S' format. Therefore, we only need to worry about cp0,
1081 cp2, and cp3. */
1082 op = (l >> OP_SH_OP) & OP_MASK_OP;
1083 if (op == OP_OP_COP0)
1084 (*info->fprintf_func) (info->stream, "%s",
1085 mips_cp0_names[(l >> OP_SH_RD) & OP_MASK_RD]);
1086 else
0fd3a477 1087 (*info->fprintf_func) (info->stream, "$%ld",
794ac9d0
CD
1088 (l >> OP_SH_RD) & OP_MASK_RD);
1089 break;
1090
1091 case 'K':
1092 (*info->fprintf_func) (info->stream, "%s",
1093 mips_hwr_names[(l >> OP_SH_RD) & OP_MASK_RD]);
1094 break;
1095
1096 case 'N':
0d09bfe6
TS
1097 (*info->fprintf_func) (info->stream,
1098 ((opp->pinfo & (FP_D | FP_S)) != 0
1099 ? "$fcc%ld" : "$cc%ld"),
794ac9d0
CD
1100 (l >> OP_SH_BCC) & OP_MASK_BCC);
1101 break;
1102
1103 case 'M':
0fd3a477 1104 (*info->fprintf_func) (info->stream, "$fcc%ld",
794ac9d0
CD
1105 (l >> OP_SH_CCC) & OP_MASK_CCC);
1106 break;
1107
1108 case 'P':
0fd3a477 1109 (*info->fprintf_func) (info->stream, "%ld",
794ac9d0
CD
1110 (l >> OP_SH_PERFREG) & OP_MASK_PERFREG);
1111 break;
1112
1113 case 'e':
0fd3a477 1114 (*info->fprintf_func) (info->stream, "%ld",
794ac9d0
CD
1115 (l >> OP_SH_VECBYTE) & OP_MASK_VECBYTE);
1116 break;
1117
1118 case '%':
0fd3a477 1119 (*info->fprintf_func) (info->stream, "%ld",
794ac9d0
CD
1120 (l >> OP_SH_VECALIGN) & OP_MASK_VECALIGN);
1121 break;
1122
1123 case 'H':
0fd3a477 1124 (*info->fprintf_func) (info->stream, "%ld",
794ac9d0
CD
1125 (l >> OP_SH_SEL) & OP_MASK_SEL);
1126 break;
1127
1128 case 'O':
0fd3a477 1129 (*info->fprintf_func) (info->stream, "%ld",
794ac9d0
CD
1130 (l >> OP_SH_ALN) & OP_MASK_ALN);
1131 break;
1132
1133 case 'Q':
bbcc0807 1134 {
794ac9d0 1135 unsigned int vsel = (l >> OP_SH_VSEL) & OP_MASK_VSEL;
47b0e7ad 1136
794ac9d0
CD
1137 if ((vsel & 0x10) == 0)
1138 {
1139 int fmt;
47b0e7ad 1140
794ac9d0
CD
1141 vsel &= 0x0f;
1142 for (fmt = 0; fmt < 3; fmt++, vsel >>= 1)
1143 if ((vsel & 1) == 0)
1144 break;
0fd3a477 1145 (*info->fprintf_func) (info->stream, "$v%ld[%d]",
794ac9d0
CD
1146 (l >> OP_SH_FT) & OP_MASK_FT,
1147 vsel >> 1);
1148 }
1149 else if ((vsel & 0x08) == 0)
1150 {
0fd3a477 1151 (*info->fprintf_func) (info->stream, "$v%ld",
794ac9d0
CD
1152 (l >> OP_SH_FT) & OP_MASK_FT);
1153 }
bbcc0807 1154 else
794ac9d0 1155 {
0fd3a477 1156 (*info->fprintf_func) (info->stream, "0x%lx",
794ac9d0
CD
1157 (l >> OP_SH_FT) & OP_MASK_FT);
1158 }
bbcc0807 1159 }
794ac9d0
CD
1160 break;
1161
1162 case 'X':
0fd3a477 1163 (*info->fprintf_func) (info->stream, "$v%ld",
794ac9d0
CD
1164 (l >> OP_SH_FD) & OP_MASK_FD);
1165 break;
1166
1167 case 'Y':
0fd3a477 1168 (*info->fprintf_func) (info->stream, "$v%ld",
794ac9d0
CD
1169 (l >> OP_SH_FS) & OP_MASK_FS);
1170 break;
1171
1172 case 'Z':
0fd3a477 1173 (*info->fprintf_func) (info->stream, "$v%ld",
794ac9d0
CD
1174 (l >> OP_SH_FT) & OP_MASK_FT);
1175 break;
bbcc0807 1176
af7ee8bf
CD
1177 default:
1178 /* xgettext:c-format */
1179 (*info->fprintf_func) (info->stream,
794ac9d0 1180 _("# internal error, undefined modifier(%c)"),
af7ee8bf 1181 *d);
794ac9d0 1182 return;
af7ee8bf 1183 }
252b5132
RH
1184 }
1185}
1186\f
252b5132
RH
1187/* Print the mips instruction at address MEMADDR in debugged memory,
1188 on using INFO. Returns length of the instruction, in bytes, which is
aa5f19f2 1189 always INSNLEN. BIGENDIAN must be 1 if this is big-endian code, 0 if
252b5132
RH
1190 this is little-endian code. */
1191
1192static int
47b0e7ad
NC
1193print_insn_mips (bfd_vma memaddr,
1194 unsigned long int word,
1195 struct disassemble_info *info)
252b5132 1196{
47b0e7ad 1197 const struct mips_opcode *op;
b34976b6 1198 static bfd_boolean init = 0;
252b5132
RH
1199 static const struct mips_opcode *mips_hash[OP_MASK_OP + 1];
1200
1201 /* Build a hash table to shorten the search time. */
1202 if (! init)
1203 {
1204 unsigned int i;
1205
1206 for (i = 0; i <= OP_MASK_OP; i++)
1207 {
1208 for (op = mips_opcodes; op < &mips_opcodes[NUMOPCODES]; op++)
1209 {
986e18a5 1210 if (op->pinfo == INSN_MACRO
9e836e3d 1211 || (no_aliases && (op->pinfo2 & INSN2_ALIAS)))
252b5132
RH
1212 continue;
1213 if (i == ((op->match >> OP_SH_OP) & OP_MASK_OP))
1214 {
1215 mips_hash[i] = op;
1216 break;
1217 }
1218 }
7f6621cd 1219 }
252b5132
RH
1220
1221 init = 1;
1222 }
1223
aa5f19f2 1224 info->bytes_per_chunk = INSNLEN;
252b5132 1225 info->display_endian = info->endian;
9bb28706
CD
1226 info->insn_info_valid = 1;
1227 info->branch_delay_insns = 0;
def7143b 1228 info->data_size = 0;
9bb28706
CD
1229 info->insn_type = dis_nonbranch;
1230 info->target = 0;
1231 info->target2 = 0;
252b5132
RH
1232
1233 op = mips_hash[(word >> OP_SH_OP) & OP_MASK_OP];
1234 if (op != NULL)
1235 {
1236 for (; op < &mips_opcodes[NUMOPCODES]; op++)
1237 {
986e18a5 1238 if (op->pinfo != INSN_MACRO
9e836e3d 1239 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
986e18a5 1240 && (word & op->mask) == op->match)
252b5132 1241 {
47b0e7ad 1242 const char *d;
2bd7f1f3 1243
3396de36 1244 /* We always allow to disassemble the jalx instruction. */
640c0ccd 1245 if (! OPCODE_IS_MEMBER (op, mips_isa, mips_processor)
3396de36 1246 && strcmp (op->name, "jalx"))
252b5132
RH
1247 continue;
1248
9bb28706
CD
1249 /* Figure out instruction type and branch delay information. */
1250 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0)
1251 {
1252 if ((info->insn_type & INSN_WRITE_GPR_31) != 0)
1253 info->insn_type = dis_jsr;
1254 else
1255 info->insn_type = dis_branch;
1256 info->branch_delay_insns = 1;
1257 }
1258 else if ((op->pinfo & (INSN_COND_BRANCH_DELAY
1259 | INSN_COND_BRANCH_LIKELY)) != 0)
1260 {
1261 if ((info->insn_type & INSN_WRITE_GPR_31) != 0)
1262 info->insn_type = dis_condjsr;
1263 else
1264 info->insn_type = dis_condbranch;
1265 info->branch_delay_insns = 1;
1266 }
1267 else if ((op->pinfo & (INSN_STORE_MEMORY
1268 | INSN_LOAD_MEMORY_DELAY)) != 0)
1269 info->insn_type = dis_dref;
1270
252b5132
RH
1271 (*info->fprintf_func) (info->stream, "%s", op->name);
1272
1273 d = op->args;
1274 if (d != NULL && *d != '\0')
1275 {
7f6621cd 1276 (*info->fprintf_func) (info->stream, "\t");
cc0ca239 1277 print_insn_args (d, word, memaddr, info, op);
252b5132
RH
1278 }
1279
aa5f19f2 1280 return INSNLEN;
252b5132
RH
1281 }
1282 }
1283 }
1284
1285 /* Handle undefined instructions. */
9bb28706 1286 info->insn_type = dis_noninsn;
0fd3a477 1287 (*info->fprintf_func) (info->stream, "0x%lx", word);
aa5f19f2 1288 return INSNLEN;
252b5132 1289}
aa5f19f2 1290\f
252b5132
RH
1291/* Disassemble an operand for a mips16 instruction. */
1292
1293static void
47b0e7ad
NC
1294print_mips16_insn_arg (char type,
1295 const struct mips_opcode *op,
1296 int l,
1297 bfd_boolean use_extend,
1298 int extend,
1299 bfd_vma memaddr,
1300 struct disassemble_info *info)
252b5132
RH
1301{
1302 switch (type)
1303 {
1304 case ',':
1305 case '(':
1306 case ')':
1307 (*info->fprintf_func) (info->stream, "%c", type);
1308 break;
1309
1310 case 'y':
1311 case 'w':
aa5f19f2 1312 (*info->fprintf_func) (info->stream, "%s",
654c225a
TS
1313 mips16_reg_names(((l >> MIPS16OP_SH_RY)
1314 & MIPS16OP_MASK_RY)));
252b5132
RH
1315 break;
1316
1317 case 'x':
1318 case 'v':
aa5f19f2 1319 (*info->fprintf_func) (info->stream, "%s",
654c225a
TS
1320 mips16_reg_names(((l >> MIPS16OP_SH_RX)
1321 & MIPS16OP_MASK_RX)));
252b5132
RH
1322 break;
1323
1324 case 'z':
aa5f19f2 1325 (*info->fprintf_func) (info->stream, "%s",
654c225a
TS
1326 mips16_reg_names(((l >> MIPS16OP_SH_RZ)
1327 & MIPS16OP_MASK_RZ)));
252b5132
RH
1328 break;
1329
1330 case 'Z':
aa5f19f2 1331 (*info->fprintf_func) (info->stream, "%s",
654c225a
TS
1332 mips16_reg_names(((l >> MIPS16OP_SH_MOVE32Z)
1333 & MIPS16OP_MASK_MOVE32Z)));
252b5132
RH
1334 break;
1335
1336 case '0':
640c0ccd 1337 (*info->fprintf_func) (info->stream, "%s", mips_gpr_names[0]);
252b5132
RH
1338 break;
1339
1340 case 'S':
640c0ccd 1341 (*info->fprintf_func) (info->stream, "%s", mips_gpr_names[29]);
252b5132
RH
1342 break;
1343
1344 case 'P':
1345 (*info->fprintf_func) (info->stream, "$pc");
1346 break;
1347
1348 case 'R':
640c0ccd 1349 (*info->fprintf_func) (info->stream, "%s", mips_gpr_names[31]);
252b5132
RH
1350 break;
1351
1352 case 'X':
aa5f19f2 1353 (*info->fprintf_func) (info->stream, "%s",
640c0ccd
CD
1354 mips_gpr_names[((l >> MIPS16OP_SH_REGR32)
1355 & MIPS16OP_MASK_REGR32)]);
252b5132
RH
1356 break;
1357
1358 case 'Y':
aa5f19f2 1359 (*info->fprintf_func) (info->stream, "%s",
640c0ccd 1360 mips_gpr_names[MIPS16OP_EXTRACT_REG32R (l)]);
252b5132
RH
1361 break;
1362
1363 case '<':
1364 case '>':
1365 case '[':
1366 case ']':
1367 case '4':
1368 case '5':
1369 case 'H':
1370 case 'W':
1371 case 'D':
1372 case 'j':
1373 case '6':
1374 case '8':
1375 case 'V':
1376 case 'C':
1377 case 'U':
1378 case 'k':
1379 case 'K':
1380 case 'p':
1381 case 'q':
1382 case 'A':
1383 case 'B':
1384 case 'E':
1385 {
1386 int immed, nbits, shift, signedp, extbits, pcrel, extu, branch;
1387
1388 shift = 0;
1389 signedp = 0;
1390 extbits = 16;
1391 pcrel = 0;
1392 extu = 0;
1393 branch = 0;
1394 switch (type)
1395 {
1396 case '<':
1397 nbits = 3;
1398 immed = (l >> MIPS16OP_SH_RZ) & MIPS16OP_MASK_RZ;
1399 extbits = 5;
1400 extu = 1;
1401 break;
1402 case '>':
1403 nbits = 3;
1404 immed = (l >> MIPS16OP_SH_RX) & MIPS16OP_MASK_RX;
1405 extbits = 5;
1406 extu = 1;
1407 break;
1408 case '[':
1409 nbits = 3;
1410 immed = (l >> MIPS16OP_SH_RZ) & MIPS16OP_MASK_RZ;
1411 extbits = 6;
1412 extu = 1;
1413 break;
1414 case ']':
1415 nbits = 3;
1416 immed = (l >> MIPS16OP_SH_RX) & MIPS16OP_MASK_RX;
1417 extbits = 6;
1418 extu = 1;
1419 break;
1420 case '4':
1421 nbits = 4;
1422 immed = (l >> MIPS16OP_SH_IMM4) & MIPS16OP_MASK_IMM4;
1423 signedp = 1;
1424 extbits = 15;
1425 break;
1426 case '5':
1427 nbits = 5;
1428 immed = (l >> MIPS16OP_SH_IMM5) & MIPS16OP_MASK_IMM5;
1429 info->insn_type = dis_dref;
1430 info->data_size = 1;
1431 break;
1432 case 'H':
1433 nbits = 5;
1434 shift = 1;
1435 immed = (l >> MIPS16OP_SH_IMM5) & MIPS16OP_MASK_IMM5;
1436 info->insn_type = dis_dref;
1437 info->data_size = 2;
1438 break;
1439 case 'W':
1440 nbits = 5;
1441 shift = 2;
1442 immed = (l >> MIPS16OP_SH_IMM5) & MIPS16OP_MASK_IMM5;
1443 if ((op->pinfo & MIPS16_INSN_READ_PC) == 0
1444 && (op->pinfo & MIPS16_INSN_READ_SP) == 0)
1445 {
1446 info->insn_type = dis_dref;
1447 info->data_size = 4;
1448 }
1449 break;
1450 case 'D':
1451 nbits = 5;
1452 shift = 3;
1453 immed = (l >> MIPS16OP_SH_IMM5) & MIPS16OP_MASK_IMM5;
1454 info->insn_type = dis_dref;
1455 info->data_size = 8;
1456 break;
1457 case 'j':
1458 nbits = 5;
1459 immed = (l >> MIPS16OP_SH_IMM5) & MIPS16OP_MASK_IMM5;
1460 signedp = 1;
1461 break;
1462 case '6':
1463 nbits = 6;
1464 immed = (l >> MIPS16OP_SH_IMM6) & MIPS16OP_MASK_IMM6;
1465 break;
1466 case '8':
1467 nbits = 8;
1468 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1469 break;
1470 case 'V':
1471 nbits = 8;
1472 shift = 2;
1473 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1474 /* FIXME: This might be lw, or it might be addiu to $sp or
1475 $pc. We assume it's load. */
1476 info->insn_type = dis_dref;
1477 info->data_size = 4;
1478 break;
1479 case 'C':
1480 nbits = 8;
1481 shift = 3;
1482 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1483 info->insn_type = dis_dref;
1484 info->data_size = 8;
1485 break;
1486 case 'U':
1487 nbits = 8;
1488 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1489 extu = 1;
1490 break;
1491 case 'k':
1492 nbits = 8;
1493 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1494 signedp = 1;
1495 break;
1496 case 'K':
1497 nbits = 8;
1498 shift = 3;
1499 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1500 signedp = 1;
1501 break;
1502 case 'p':
1503 nbits = 8;
1504 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1505 signedp = 1;
1506 pcrel = 1;
1507 branch = 1;
1508 info->insn_type = dis_condbranch;
1509 break;
1510 case 'q':
1511 nbits = 11;
1512 immed = (l >> MIPS16OP_SH_IMM11) & MIPS16OP_MASK_IMM11;
1513 signedp = 1;
1514 pcrel = 1;
1515 branch = 1;
1516 info->insn_type = dis_branch;
1517 break;
1518 case 'A':
1519 nbits = 8;
1520 shift = 2;
1521 immed = (l >> MIPS16OP_SH_IMM8) & MIPS16OP_MASK_IMM8;
1522 pcrel = 1;
1523 /* FIXME: This can be lw or la. We assume it is lw. */
1524 info->insn_type = dis_dref;
1525 info->data_size = 4;
1526 break;
1527 case 'B':
1528 nbits = 5;
1529 shift = 3;
1530 immed = (l >> MIPS16OP_SH_IMM5) & MIPS16OP_MASK_IMM5;
1531 pcrel = 1;
1532 info->insn_type = dis_dref;
1533 info->data_size = 8;
1534 break;
1535 case 'E':
1536 nbits = 5;
1537 shift = 2;
1538 immed = (l >> MIPS16OP_SH_IMM5) & MIPS16OP_MASK_IMM5;
1539 pcrel = 1;
1540 break;
1541 default:
1542 abort ();
1543 }
1544
1545 if (! use_extend)
1546 {
1547 if (signedp && immed >= (1 << (nbits - 1)))
1548 immed -= 1 << nbits;
1549 immed <<= shift;
1550 if ((type == '<' || type == '>' || type == '[' || type == ']')
1551 && immed == 0)
1552 immed = 8;
1553 }
1554 else
1555 {
1556 if (extbits == 16)
1557 immed |= ((extend & 0x1f) << 11) | (extend & 0x7e0);
1558 else if (extbits == 15)
1559 immed |= ((extend & 0xf) << 11) | (extend & 0x7f0);
1560 else
1561 immed = ((extend >> 6) & 0x1f) | (extend & 0x20);
1562 immed &= (1 << extbits) - 1;
1563 if (! extu && immed >= (1 << (extbits - 1)))
1564 immed -= 1 << extbits;
1565 }
1566
1567 if (! pcrel)
1568 (*info->fprintf_func) (info->stream, "%d", immed);
1569 else
1570 {
1571 bfd_vma baseaddr;
252b5132
RH
1572
1573 if (branch)
1574 {
1575 immed *= 2;
1576 baseaddr = memaddr + 2;
1577 }
1578 else if (use_extend)
1579 baseaddr = memaddr - 2;
1580 else
1581 {
1582 int status;
1583 bfd_byte buffer[2];
1584
1585 baseaddr = memaddr;
1586
1587 /* If this instruction is in the delay slot of a jr
1588 instruction, the base address is the address of the
1589 jr instruction. If it is in the delay slot of jalr
1590 instruction, the base address is the address of the
1591 jalr instruction. This test is unreliable: we have
1592 no way of knowing whether the previous word is
1593 instruction or data. */
1594 status = (*info->read_memory_func) (memaddr - 4, buffer, 2,
1595 info);
1596 if (status == 0
1597 && (((info->endian == BFD_ENDIAN_BIG
1598 ? bfd_getb16 (buffer)
1599 : bfd_getl16 (buffer))
1600 & 0xf800) == 0x1800))
1601 baseaddr = memaddr - 4;
1602 else
1603 {
1604 status = (*info->read_memory_func) (memaddr - 2, buffer,
1605 2, info);
1606 if (status == 0
1607 && (((info->endian == BFD_ENDIAN_BIG
1608 ? bfd_getb16 (buffer)
1609 : bfd_getl16 (buffer))
1610 & 0xf81f) == 0xe800))
1611 baseaddr = memaddr - 2;
1612 }
1613 }
9bb28706
CD
1614 info->target = (baseaddr & ~((1 << shift) - 1)) + immed;
1615 (*info->print_address_func) (info->target, info);
252b5132
RH
1616 }
1617 }
1618 break;
1619
1620 case 'a':
1621 if (! use_extend)
1622 extend = 0;
1623 l = ((l & 0x1f) << 23) | ((l & 0x3e0) << 13) | (extend << 2);
9bb28706
CD
1624 info->target = ((memaddr + 4) & ~(bfd_vma) 0x0fffffff) | l;
1625 (*info->print_address_func) (info->target, info);
252b5132 1626 info->insn_type = dis_jsr;
252b5132
RH
1627 info->branch_delay_insns = 1;
1628 break;
1629
1630 case 'l':
1631 case 'L':
1632 {
1633 int need_comma, amask, smask;
1634
1635 need_comma = 0;
1636
1637 l = (l >> MIPS16OP_SH_IMM6) & MIPS16OP_MASK_IMM6;
1638
1639 amask = (l >> 3) & 7;
1640
1641 if (amask > 0 && amask < 5)
1642 {
640c0ccd 1643 (*info->fprintf_func) (info->stream, "%s", mips_gpr_names[4]);
252b5132 1644 if (amask > 1)
aa5f19f2 1645 (*info->fprintf_func) (info->stream, "-%s",
640c0ccd 1646 mips_gpr_names[amask + 3]);
252b5132
RH
1647 need_comma = 1;
1648 }
1649
1650 smask = (l >> 1) & 3;
1651 if (smask == 3)
1652 {
1653 (*info->fprintf_func) (info->stream, "%s??",
1654 need_comma ? "," : "");
1655 need_comma = 1;
1656 }
1657 else if (smask > 0)
1658 {
aa5f19f2 1659 (*info->fprintf_func) (info->stream, "%s%s",
252b5132 1660 need_comma ? "," : "",
640c0ccd 1661 mips_gpr_names[16]);
252b5132 1662 if (smask > 1)
aa5f19f2 1663 (*info->fprintf_func) (info->stream, "-%s",
640c0ccd 1664 mips_gpr_names[smask + 15]);
252b5132
RH
1665 need_comma = 1;
1666 }
1667
1668 if (l & 1)
1669 {
aa5f19f2 1670 (*info->fprintf_func) (info->stream, "%s%s",
252b5132 1671 need_comma ? "," : "",
640c0ccd 1672 mips_gpr_names[31]);
252b5132
RH
1673 need_comma = 1;
1674 }
1675
1676 if (amask == 5 || amask == 6)
1677 {
1678 (*info->fprintf_func) (info->stream, "%s$f0",
1679 need_comma ? "," : "");
1680 if (amask == 6)
1681 (*info->fprintf_func) (info->stream, "-$f1");
1682 }
1683 }
1684 break;
1685
0499d65b
TS
1686 case 'm':
1687 case 'M':
1688 /* MIPS16e save/restore. */
1689 {
1690 int need_comma = 0;
1691 int amask, args, statics;
1692 int nsreg, smask;
1693 int framesz;
1694 int i, j;
1695
1696 l = l & 0x7f;
1697 if (use_extend)
1698 l |= extend << 16;
1699
1700 amask = (l >> 16) & 0xf;
1701 if (amask == MIPS16_ALL_ARGS)
1702 {
1703 args = 4;
1704 statics = 0;
1705 }
1706 else if (amask == MIPS16_ALL_STATICS)
1707 {
1708 args = 0;
1709 statics = 4;
1710 }
1711 else
1712 {
1713 args = amask >> 2;
1714 statics = amask & 3;
1715 }
1716
1717 if (args > 0) {
1718 (*info->fprintf_func) (info->stream, "%s", mips_gpr_names[4]);
1719 if (args > 1)
1720 (*info->fprintf_func) (info->stream, "-%s",
1721 mips_gpr_names[4 + args - 1]);
1722 need_comma = 1;
1723 }
1724
1725 framesz = (((l >> 16) & 0xf0) | (l & 0x0f)) * 8;
1726 if (framesz == 0 && !use_extend)
1727 framesz = 128;
1728
1729 (*info->fprintf_func) (info->stream, "%s%d",
1730 need_comma ? "," : "",
1731 framesz);
1732
1733 if (l & 0x40) /* $ra */
1734 (*info->fprintf_func) (info->stream, ",%s", mips_gpr_names[31]);
1735
1736 nsreg = (l >> 24) & 0x7;
1737 smask = 0;
1738 if (l & 0x20) /* $s0 */
1739 smask |= 1 << 0;
1740 if (l & 0x10) /* $s1 */
1741 smask |= 1 << 1;
1742 if (nsreg > 0) /* $s2-$s8 */
1743 smask |= ((1 << nsreg) - 1) << 2;
1744
1745 /* Find first set static reg bit. */
1746 for (i = 0; i < 9; i++)
1747 {
1748 if (smask & (1 << i))
1749 {
1750 (*info->fprintf_func) (info->stream, ",%s",
1751 mips_gpr_names[i == 8 ? 30 : (16 + i)]);
1752 /* Skip over string of set bits. */
1753 for (j = i; smask & (2 << j); j++)
1754 continue;
1755 if (j > i)
1756 (*info->fprintf_func) (info->stream, "-%s",
1757 mips_gpr_names[j == 8 ? 30 : (16 + j)]);
1758 i = j + 1;
1759 }
1760 }
1761
1762 /* Statics $ax - $a3. */
1763 if (statics == 1)
1764 (*info->fprintf_func) (info->stream, ",%s", mips_gpr_names[7]);
1765 else if (statics > 0)
1766 (*info->fprintf_func) (info->stream, ",%s-%s",
1767 mips_gpr_names[7 - statics + 1],
1768 mips_gpr_names[7]);
1769 }
1770 break;
1771
252b5132 1772 default:
aa5f19f2
NC
1773 /* xgettext:c-format */
1774 (*info->fprintf_func)
1775 (info->stream,
1776 _("# internal disassembler error, unrecognised modifier (%c)"),
1777 type);
252b5132
RH
1778 abort ();
1779 }
1780}
640c0ccd 1781
47b0e7ad
NC
1782/* Disassemble mips16 instructions. */
1783
1784static int
1785print_insn_mips16 (bfd_vma memaddr, struct disassemble_info *info)
1786{
1787 int status;
1788 bfd_byte buffer[2];
1789 int length;
1790 int insn;
1791 bfd_boolean use_extend;
1792 int extend = 0;
1793 const struct mips_opcode *op, *opend;
1794
1795 info->bytes_per_chunk = 2;
1796 info->display_endian = info->endian;
1797 info->insn_info_valid = 1;
1798 info->branch_delay_insns = 0;
1799 info->data_size = 0;
1800 info->insn_type = dis_nonbranch;
1801 info->target = 0;
1802 info->target2 = 0;
1803
1804 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
1805 if (status != 0)
1806 {
1807 (*info->memory_error_func) (status, memaddr, info);
1808 return -1;
1809 }
1810
1811 length = 2;
1812
1813 if (info->endian == BFD_ENDIAN_BIG)
1814 insn = bfd_getb16 (buffer);
1815 else
1816 insn = bfd_getl16 (buffer);
1817
1818 /* Handle the extend opcode specially. */
1819 use_extend = FALSE;
1820 if ((insn & 0xf800) == 0xf000)
1821 {
1822 use_extend = TRUE;
1823 extend = insn & 0x7ff;
1824
1825 memaddr += 2;
1826
1827 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
1828 if (status != 0)
1829 {
1830 (*info->fprintf_func) (info->stream, "extend 0x%x",
1831 (unsigned int) extend);
1832 (*info->memory_error_func) (status, memaddr, info);
1833 return -1;
1834 }
1835
1836 if (info->endian == BFD_ENDIAN_BIG)
1837 insn = bfd_getb16 (buffer);
1838 else
1839 insn = bfd_getl16 (buffer);
1840
1841 /* Check for an extend opcode followed by an extend opcode. */
1842 if ((insn & 0xf800) == 0xf000)
1843 {
1844 (*info->fprintf_func) (info->stream, "extend 0x%x",
1845 (unsigned int) extend);
1846 info->insn_type = dis_noninsn;
1847 return length;
1848 }
1849
1850 length += 2;
1851 }
1852
1853 /* FIXME: Should probably use a hash table on the major opcode here. */
1854
1855 opend = mips16_opcodes + bfd_mips16_num_opcodes;
1856 for (op = mips16_opcodes; op < opend; op++)
1857 {
1858 if (op->pinfo != INSN_MACRO
1859 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
1860 && (insn & op->mask) == op->match)
1861 {
1862 const char *s;
1863
1864 if (strchr (op->args, 'a') != NULL)
1865 {
1866 if (use_extend)
1867 {
1868 (*info->fprintf_func) (info->stream, "extend 0x%x",
1869 (unsigned int) extend);
1870 info->insn_type = dis_noninsn;
1871 return length - 2;
1872 }
1873
1874 use_extend = FALSE;
1875
1876 memaddr += 2;
1877
1878 status = (*info->read_memory_func) (memaddr, buffer, 2,
1879 info);
1880 if (status == 0)
1881 {
1882 use_extend = TRUE;
1883 if (info->endian == BFD_ENDIAN_BIG)
1884 extend = bfd_getb16 (buffer);
1885 else
1886 extend = bfd_getl16 (buffer);
1887 length += 2;
1888 }
1889 }
1890
1891 (*info->fprintf_func) (info->stream, "%s", op->name);
1892 if (op->args[0] != '\0')
1893 (*info->fprintf_func) (info->stream, "\t");
1894
1895 for (s = op->args; *s != '\0'; s++)
1896 {
1897 if (*s == ','
1898 && s[1] == 'w'
1899 && (((insn >> MIPS16OP_SH_RX) & MIPS16OP_MASK_RX)
1900 == ((insn >> MIPS16OP_SH_RY) & MIPS16OP_MASK_RY)))
1901 {
1902 /* Skip the register and the comma. */
1903 ++s;
1904 continue;
1905 }
1906 if (*s == ','
1907 && s[1] == 'v'
1908 && (((insn >> MIPS16OP_SH_RZ) & MIPS16OP_MASK_RZ)
1909 == ((insn >> MIPS16OP_SH_RX) & MIPS16OP_MASK_RX)))
1910 {
1911 /* Skip the register and the comma. */
1912 ++s;
1913 continue;
1914 }
1915 print_mips16_insn_arg (*s, op, insn, use_extend, extend, memaddr,
1916 info);
1917 }
1918
1919 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0)
1920 {
1921 info->branch_delay_insns = 1;
1922 if (info->insn_type != dis_jsr)
1923 info->insn_type = dis_branch;
1924 }
1925
1926 return length;
1927 }
1928 }
1929
1930 if (use_extend)
1931 (*info->fprintf_func) (info->stream, "0x%x", extend | 0xf000);
1932 (*info->fprintf_func) (info->stream, "0x%x", insn);
1933 info->insn_type = dis_noninsn;
1934
1935 return length;
1936}
1937
1938/* In an environment where we do not know the symbol type of the
1939 instruction we are forced to assume that the low order bit of the
1940 instructions' address may mark it as a mips16 instruction. If we
1941 are single stepping, or the pc is within the disassembled function,
1942 this works. Otherwise, we need a clue. Sometimes. */
1943
1944static int
1945_print_insn_mips (bfd_vma memaddr,
1946 struct disassemble_info *info,
1947 enum bfd_endian endianness)
1948{
1949 bfd_byte buffer[INSNLEN];
1950 int status;
1951
1952 set_default_mips_dis_options (info);
1953 parse_mips_dis_options (info->disassembler_options);
1954
1955#if 1
1956 /* FIXME: If odd address, this is CLEARLY a mips 16 instruction. */
1957 /* Only a few tools will work this way. */
1958 if (memaddr & 0x01)
1959 return print_insn_mips16 (memaddr, info);
1960#endif
1961
1962#if SYMTAB_AVAILABLE
1963 if (info->mach == bfd_mach_mips16
1964 || (info->flavour == bfd_target_elf_flavour
1965 && info->symbols != NULL
1966 && ((*(elf_symbol_type **) info->symbols)->internal_elf_sym.st_other
1967 == STO_MIPS16)))
1968 return print_insn_mips16 (memaddr, info);
1969#endif
1970
1971 status = (*info->read_memory_func) (memaddr, buffer, INSNLEN, info);
1972 if (status == 0)
1973 {
1974 unsigned long insn;
1975
1976 if (endianness == BFD_ENDIAN_BIG)
1977 insn = (unsigned long) bfd_getb32 (buffer);
1978 else
1979 insn = (unsigned long) bfd_getl32 (buffer);
1980
1981 return print_insn_mips (memaddr, insn, info);
1982 }
1983 else
1984 {
1985 (*info->memory_error_func) (status, memaddr, info);
1986 return -1;
1987 }
1988}
1989
1990int
1991print_insn_big_mips (bfd_vma memaddr, struct disassemble_info *info)
1992{
1993 return _print_insn_mips (memaddr, info, BFD_ENDIAN_BIG);
1994}
1995
1996int
1997print_insn_little_mips (bfd_vma memaddr, struct disassemble_info *info)
1998{
1999 return _print_insn_mips (memaddr, info, BFD_ENDIAN_LITTLE);
2000}
2001\f
640c0ccd 2002void
47b0e7ad 2003print_mips_disassembler_options (FILE *stream)
640c0ccd 2004{
4a9a3c54 2005 unsigned int i;
640c0ccd
CD
2006
2007 fprintf (stream, _("\n\
2008The following MIPS specific disassembler options are supported for use\n\
2009with the -M switch (multiple options should be separated by commas):\n"));
2010
2011 fprintf (stream, _("\n\
2012 gpr-names=ABI Print GPR names according to specified ABI.\n\
2013 Default: based on binary being disassembled.\n"));
2014
2015 fprintf (stream, _("\n\
2016 fpr-names=ABI Print FPR names according to specified ABI.\n\
2017 Default: numeric.\n"));
2018
2019 fprintf (stream, _("\n\
2020 cp0-names=ARCH Print CP0 register names according to\n\
2021 specified architecture.\n\
2022 Default: based on binary being disassembled.\n"));
2023
af7ee8bf
CD
2024 fprintf (stream, _("\n\
2025 hwr-names=ARCH Print HWR names according to specified \n\
2026 architecture.\n\
2027 Default: based on binary being disassembled.\n"));
2028
640c0ccd
CD
2029 fprintf (stream, _("\n\
2030 reg-names=ABI Print GPR and FPR names according to\n\
2031 specified ABI.\n"));
2032
2033 fprintf (stream, _("\n\
af7ee8bf 2034 reg-names=ARCH Print CP0 register and HWR names according to\n\
640c0ccd
CD
2035 specified architecture.\n"));
2036
2037 fprintf (stream, _("\n\
2038 For the options above, the following values are supported for \"ABI\":\n\
2039 "));
4a9a3c54 2040 for (i = 0; i < ARRAY_SIZE (mips_abi_choices); i++)
640c0ccd
CD
2041 fprintf (stream, " %s", mips_abi_choices[i].name);
2042 fprintf (stream, _("\n"));
2043
2044 fprintf (stream, _("\n\
2045 For the options above, The following values are supported for \"ARCH\":\n\
2046 "));
4a9a3c54 2047 for (i = 0; i < ARRAY_SIZE (mips_arch_choices); i++)
640c0ccd
CD
2048 if (*mips_arch_choices[i].name != '\0')
2049 fprintf (stream, " %s", mips_arch_choices[i].name);
2050 fprintf (stream, _("\n"));
2051
2052 fprintf (stream, _("\n"));
2053}
This page took 0.416592 seconds and 4 git commands to generate.