Add support for MIPS R6.
[deliverable/binutils-gdb.git] / opcodes / mips-dis.c
1 /* Print mips instructions for GDB, the GNU debugger, or for objdump.
2 Copyright (C) 1989-2014 Free Software Foundation, Inc.
3 Contributed by Nobuyuki Hikichi(hikichi@sra.co.jp).
4
5 This file is part of the GNU opcodes library.
6
7 This library is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3, or (at your option)
10 any later version.
11
12 It is distributed in the hope that it will be useful, but WITHOUT
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
15 License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20 MA 02110-1301, USA. */
21
22 #include "sysdep.h"
23 #include "dis-asm.h"
24 #include "libiberty.h"
25 #include "opcode/mips.h"
26 #include "opintl.h"
27
28 /* FIXME: These are needed to figure out if the code is mips16 or
29 not. The low bit of the address is often a good indicator. No
30 symbol table is available when this code runs out in an embedded
31 system as when it is used for disassembler support in a monitor. */
32
33 #if !defined(EMBEDDED_ENV)
34 #define SYMTAB_AVAILABLE 1
35 #include "elf-bfd.h"
36 #include "elf/mips.h"
37 #endif
38
39 /* Mips instructions are at maximum this many bytes long. */
40 #define INSNLEN 4
41
42 \f
43 /* FIXME: These should be shared with gdb somehow. */
44
45 struct mips_cp0sel_name
46 {
47 unsigned int cp0reg;
48 unsigned int sel;
49 const char * const name;
50 };
51
52 static const char * const mips_gpr_names_numeric[32] =
53 {
54 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
55 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
56 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
57 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
58 };
59
60 static const char * const mips_gpr_names_oldabi[32] =
61 {
62 "zero", "at", "v0", "v1", "a0", "a1", "a2", "a3",
63 "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7",
64 "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
65 "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra"
66 };
67
68 static const char * const mips_gpr_names_newabi[32] =
69 {
70 "zero", "at", "v0", "v1", "a0", "a1", "a2", "a3",
71 "a4", "a5", "a6", "a7", "t0", "t1", "t2", "t3",
72 "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
73 "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra"
74 };
75
76 static const char * const mips_fpr_names_numeric[32] =
77 {
78 "$f0", "$f1", "$f2", "$f3", "$f4", "$f5", "$f6", "$f7",
79 "$f8", "$f9", "$f10", "$f11", "$f12", "$f13", "$f14", "$f15",
80 "$f16", "$f17", "$f18", "$f19", "$f20", "$f21", "$f22", "$f23",
81 "$f24", "$f25", "$f26", "$f27", "$f28", "$f29", "$f30", "$f31"
82 };
83
84 static const char * const mips_fpr_names_32[32] =
85 {
86 "fv0", "fv0f", "fv1", "fv1f", "ft0", "ft0f", "ft1", "ft1f",
87 "ft2", "ft2f", "ft3", "ft3f", "fa0", "fa0f", "fa1", "fa1f",
88 "ft4", "ft4f", "ft5", "ft5f", "fs0", "fs0f", "fs1", "fs1f",
89 "fs2", "fs2f", "fs3", "fs3f", "fs4", "fs4f", "fs5", "fs5f"
90 };
91
92 static const char * const mips_fpr_names_n32[32] =
93 {
94 "fv0", "ft14", "fv1", "ft15", "ft0", "ft1", "ft2", "ft3",
95 "ft4", "ft5", "ft6", "ft7", "fa0", "fa1", "fa2", "fa3",
96 "fa4", "fa5", "fa6", "fa7", "fs0", "ft8", "fs1", "ft9",
97 "fs2", "ft10", "fs3", "ft11", "fs4", "ft12", "fs5", "ft13"
98 };
99
100 static const char * const mips_fpr_names_64[32] =
101 {
102 "fv0", "ft12", "fv1", "ft13", "ft0", "ft1", "ft2", "ft3",
103 "ft4", "ft5", "ft6", "ft7", "fa0", "fa1", "fa2", "fa3",
104 "fa4", "fa5", "fa6", "fa7", "ft8", "ft9", "ft10", "ft11",
105 "fs0", "fs1", "fs2", "fs3", "fs4", "fs5", "fs6", "fs7"
106 };
107
108 static const char * const mips_cp0_names_numeric[32] =
109 {
110 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
111 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
112 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
113 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
114 };
115
116 static const char * const mips_cp1_names_numeric[32] =
117 {
118 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
119 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
120 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
121 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
122 };
123
124 static const char * const mips_cp0_names_r3000[32] =
125 {
126 "c0_index", "c0_random", "c0_entrylo", "$3",
127 "c0_context", "$5", "$6", "$7",
128 "c0_badvaddr", "$9", "c0_entryhi", "$11",
129 "c0_sr", "c0_cause", "c0_epc", "c0_prid",
130 "$16", "$17", "$18", "$19",
131 "$20", "$21", "$22", "$23",
132 "$24", "$25", "$26", "$27",
133 "$28", "$29", "$30", "$31",
134 };
135
136 static const char * const mips_cp0_names_r4000[32] =
137 {
138 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
139 "c0_context", "c0_pagemask", "c0_wired", "$7",
140 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
141 "c0_sr", "c0_cause", "c0_epc", "c0_prid",
142 "c0_config", "c0_lladdr", "c0_watchlo", "c0_watchhi",
143 "c0_xcontext", "$21", "$22", "$23",
144 "$24", "$25", "c0_ecc", "c0_cacheerr",
145 "c0_taglo", "c0_taghi", "c0_errorepc", "$31",
146 };
147
148 static const char * const mips_cp0_names_r5900[32] =
149 {
150 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
151 "c0_context", "c0_pagemask", "c0_wired", "$7",
152 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
153 "c0_sr", "c0_cause", "c0_epc", "c0_prid",
154 "c0_config", "$17", "$18", "$19",
155 "$20", "$21", "$22", "c0_badpaddr",
156 "c0_depc", "c0_perfcnt", "$26", "$27",
157 "c0_taglo", "c0_taghi", "c0_errorepc", "$31"
158 };
159
160 static const struct mips_cp0sel_name mips_cp0sel_names_mipsr5900[] =
161 {
162 { 24, 2, "c0_iab" },
163 { 24, 3, "c0_iabm" },
164 { 24, 4, "c0_dab" },
165 { 24, 5, "c0_dabm" },
166 { 24, 6, "c0_dvb" },
167 { 24, 7, "c0_dvbm" },
168 { 25, 1, "c0_perfcnt,1" },
169 { 25, 2, "c0_perfcnt,2" }
170 };
171
172 static const char * const mips_cp0_names_mips3264[32] =
173 {
174 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
175 "c0_context", "c0_pagemask", "c0_wired", "$7",
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
184 static const char * const mips_cp1_names_mips3264[32] =
185 {
186 "c1_fir", "c1_ufr", "$2", "$3",
187 "c1_unfr", "$5", "$6", "$7",
188 "$8", "$9", "$10", "$11",
189 "$12", "$13", "$14", "$15",
190 "$16", "$17", "$18", "$19",
191 "$20", "$21", "$22", "$23",
192 "$24", "c1_fccr", "c1_fexr", "$27",
193 "c1_fenr", "$29", "$30", "c1_fcsr"
194 };
195
196 static const struct mips_cp0sel_name mips_cp0sel_names_mips3264[] =
197 {
198 { 16, 1, "c0_config1" },
199 { 16, 2, "c0_config2" },
200 { 16, 3, "c0_config3" },
201 { 18, 1, "c0_watchlo,1" },
202 { 18, 2, "c0_watchlo,2" },
203 { 18, 3, "c0_watchlo,3" },
204 { 18, 4, "c0_watchlo,4" },
205 { 18, 5, "c0_watchlo,5" },
206 { 18, 6, "c0_watchlo,6" },
207 { 18, 7, "c0_watchlo,7" },
208 { 19, 1, "c0_watchhi,1" },
209 { 19, 2, "c0_watchhi,2" },
210 { 19, 3, "c0_watchhi,3" },
211 { 19, 4, "c0_watchhi,4" },
212 { 19, 5, "c0_watchhi,5" },
213 { 19, 6, "c0_watchhi,6" },
214 { 19, 7, "c0_watchhi,7" },
215 { 25, 1, "c0_perfcnt,1" },
216 { 25, 2, "c0_perfcnt,2" },
217 { 25, 3, "c0_perfcnt,3" },
218 { 25, 4, "c0_perfcnt,4" },
219 { 25, 5, "c0_perfcnt,5" },
220 { 25, 6, "c0_perfcnt,6" },
221 { 25, 7, "c0_perfcnt,7" },
222 { 27, 1, "c0_cacheerr,1" },
223 { 27, 2, "c0_cacheerr,2" },
224 { 27, 3, "c0_cacheerr,3" },
225 { 28, 1, "c0_datalo" },
226 { 29, 1, "c0_datahi" }
227 };
228
229 static const char * const mips_cp0_names_mips3264r2[32] =
230 {
231 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
232 "c0_context", "c0_pagemask", "c0_wired", "c0_hwrena",
233 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
234 "c0_status", "c0_cause", "c0_epc", "c0_prid",
235 "c0_config", "c0_lladdr", "c0_watchlo", "c0_watchhi",
236 "c0_xcontext", "$21", "$22", "c0_debug",
237 "c0_depc", "c0_perfcnt", "c0_errctl", "c0_cacheerr",
238 "c0_taglo", "c0_taghi", "c0_errorepc", "c0_desave",
239 };
240
241 static const struct mips_cp0sel_name mips_cp0sel_names_mips3264r2[] =
242 {
243 { 4, 1, "c0_contextconfig" },
244 { 0, 1, "c0_mvpcontrol" },
245 { 0, 2, "c0_mvpconf0" },
246 { 0, 3, "c0_mvpconf1" },
247 { 1, 1, "c0_vpecontrol" },
248 { 1, 2, "c0_vpeconf0" },
249 { 1, 3, "c0_vpeconf1" },
250 { 1, 4, "c0_yqmask" },
251 { 1, 5, "c0_vpeschedule" },
252 { 1, 6, "c0_vpeschefback" },
253 { 2, 1, "c0_tcstatus" },
254 { 2, 2, "c0_tcbind" },
255 { 2, 3, "c0_tcrestart" },
256 { 2, 4, "c0_tchalt" },
257 { 2, 5, "c0_tccontext" },
258 { 2, 6, "c0_tcschedule" },
259 { 2, 7, "c0_tcschefback" },
260 { 5, 1, "c0_pagegrain" },
261 { 6, 1, "c0_srsconf0" },
262 { 6, 2, "c0_srsconf1" },
263 { 6, 3, "c0_srsconf2" },
264 { 6, 4, "c0_srsconf3" },
265 { 6, 5, "c0_srsconf4" },
266 { 12, 1, "c0_intctl" },
267 { 12, 2, "c0_srsctl" },
268 { 12, 3, "c0_srsmap" },
269 { 15, 1, "c0_ebase" },
270 { 16, 1, "c0_config1" },
271 { 16, 2, "c0_config2" },
272 { 16, 3, "c0_config3" },
273 { 18, 1, "c0_watchlo,1" },
274 { 18, 2, "c0_watchlo,2" },
275 { 18, 3, "c0_watchlo,3" },
276 { 18, 4, "c0_watchlo,4" },
277 { 18, 5, "c0_watchlo,5" },
278 { 18, 6, "c0_watchlo,6" },
279 { 18, 7, "c0_watchlo,7" },
280 { 19, 1, "c0_watchhi,1" },
281 { 19, 2, "c0_watchhi,2" },
282 { 19, 3, "c0_watchhi,3" },
283 { 19, 4, "c0_watchhi,4" },
284 { 19, 5, "c0_watchhi,5" },
285 { 19, 6, "c0_watchhi,6" },
286 { 19, 7, "c0_watchhi,7" },
287 { 23, 1, "c0_tracecontrol" },
288 { 23, 2, "c0_tracecontrol2" },
289 { 23, 3, "c0_usertracedata" },
290 { 23, 4, "c0_tracebpc" },
291 { 25, 1, "c0_perfcnt,1" },
292 { 25, 2, "c0_perfcnt,2" },
293 { 25, 3, "c0_perfcnt,3" },
294 { 25, 4, "c0_perfcnt,4" },
295 { 25, 5, "c0_perfcnt,5" },
296 { 25, 6, "c0_perfcnt,6" },
297 { 25, 7, "c0_perfcnt,7" },
298 { 27, 1, "c0_cacheerr,1" },
299 { 27, 2, "c0_cacheerr,2" },
300 { 27, 3, "c0_cacheerr,3" },
301 { 28, 1, "c0_datalo" },
302 { 28, 2, "c0_taglo1" },
303 { 28, 3, "c0_datalo1" },
304 { 28, 4, "c0_taglo2" },
305 { 28, 5, "c0_datalo2" },
306 { 28, 6, "c0_taglo3" },
307 { 28, 7, "c0_datalo3" },
308 { 29, 1, "c0_datahi" },
309 { 29, 2, "c0_taghi1" },
310 { 29, 3, "c0_datahi1" },
311 { 29, 4, "c0_taghi2" },
312 { 29, 5, "c0_datahi2" },
313 { 29, 6, "c0_taghi3" },
314 { 29, 7, "c0_datahi3" },
315 };
316
317 /* SB-1: MIPS64 (mips_cp0_names_mips3264) with minor mods. */
318 static const char * const mips_cp0_names_sb1[32] =
319 {
320 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
321 "c0_context", "c0_pagemask", "c0_wired", "$7",
322 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
323 "c0_status", "c0_cause", "c0_epc", "c0_prid",
324 "c0_config", "c0_lladdr", "c0_watchlo", "c0_watchhi",
325 "c0_xcontext", "$21", "$22", "c0_debug",
326 "c0_depc", "c0_perfcnt", "c0_errctl", "c0_cacheerr_i",
327 "c0_taglo_i", "c0_taghi_i", "c0_errorepc", "c0_desave",
328 };
329
330 static const struct mips_cp0sel_name mips_cp0sel_names_sb1[] =
331 {
332 { 16, 1, "c0_config1" },
333 { 18, 1, "c0_watchlo,1" },
334 { 19, 1, "c0_watchhi,1" },
335 { 22, 0, "c0_perftrace" },
336 { 23, 3, "c0_edebug" },
337 { 25, 1, "c0_perfcnt,1" },
338 { 25, 2, "c0_perfcnt,2" },
339 { 25, 3, "c0_perfcnt,3" },
340 { 25, 4, "c0_perfcnt,4" },
341 { 25, 5, "c0_perfcnt,5" },
342 { 25, 6, "c0_perfcnt,6" },
343 { 25, 7, "c0_perfcnt,7" },
344 { 26, 1, "c0_buserr_pa" },
345 { 27, 1, "c0_cacheerr_d" },
346 { 27, 3, "c0_cacheerr_d_pa" },
347 { 28, 1, "c0_datalo_i" },
348 { 28, 2, "c0_taglo_d" },
349 { 28, 3, "c0_datalo_d" },
350 { 29, 1, "c0_datahi_i" },
351 { 29, 2, "c0_taghi_d" },
352 { 29, 3, "c0_datahi_d" },
353 };
354
355 /* Xlr cop0 register names. */
356 static const char * const mips_cp0_names_xlr[32] = {
357 "c0_index", "c0_random", "c0_entrylo0", "c0_entrylo1",
358 "c0_context", "c0_pagemask", "c0_wired", "$7",
359 "c0_badvaddr", "c0_count", "c0_entryhi", "c0_compare",
360 "c0_status", "c0_cause", "c0_epc", "c0_prid",
361 "c0_config", "c0_lladdr", "c0_watchlo", "c0_watchhi",
362 "c0_xcontext", "$21", "$22", "c0_debug",
363 "c0_depc", "c0_perfcnt", "c0_errctl", "c0_cacheerr_i",
364 "c0_taglo_i", "c0_taghi_i", "c0_errorepc", "c0_desave",
365 };
366
367 /* XLR's CP0 Select Registers. */
368
369 static const struct mips_cp0sel_name mips_cp0sel_names_xlr[] = {
370 { 9, 6, "c0_extintreq" },
371 { 9, 7, "c0_extintmask" },
372 { 15, 1, "c0_ebase" },
373 { 16, 1, "c0_config1" },
374 { 16, 2, "c0_config2" },
375 { 16, 3, "c0_config3" },
376 { 16, 7, "c0_procid2" },
377 { 18, 1, "c0_watchlo,1" },
378 { 18, 2, "c0_watchlo,2" },
379 { 18, 3, "c0_watchlo,3" },
380 { 18, 4, "c0_watchlo,4" },
381 { 18, 5, "c0_watchlo,5" },
382 { 18, 6, "c0_watchlo,6" },
383 { 18, 7, "c0_watchlo,7" },
384 { 19, 1, "c0_watchhi,1" },
385 { 19, 2, "c0_watchhi,2" },
386 { 19, 3, "c0_watchhi,3" },
387 { 19, 4, "c0_watchhi,4" },
388 { 19, 5, "c0_watchhi,5" },
389 { 19, 6, "c0_watchhi,6" },
390 { 19, 7, "c0_watchhi,7" },
391 { 25, 1, "c0_perfcnt,1" },
392 { 25, 2, "c0_perfcnt,2" },
393 { 25, 3, "c0_perfcnt,3" },
394 { 25, 4, "c0_perfcnt,4" },
395 { 25, 5, "c0_perfcnt,5" },
396 { 25, 6, "c0_perfcnt,6" },
397 { 25, 7, "c0_perfcnt,7" },
398 { 27, 1, "c0_cacheerr,1" },
399 { 27, 2, "c0_cacheerr,2" },
400 { 27, 3, "c0_cacheerr,3" },
401 { 28, 1, "c0_datalo" },
402 { 29, 1, "c0_datahi" }
403 };
404
405 static const char * const mips_hwr_names_numeric[32] =
406 {
407 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
408 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
409 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
410 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
411 };
412
413 static const char * const mips_hwr_names_mips3264r2[32] =
414 {
415 "hwr_cpunum", "hwr_synci_step", "hwr_cc", "hwr_ccres",
416 "$4", "$5", "$6", "$7",
417 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
418 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
419 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
420 };
421
422 static const char * const msa_control_names[32] =
423 {
424 "msa_ir", "msa_csr", "msa_access", "msa_save",
425 "msa_modify", "msa_request", "msa_map", "msa_unmap",
426 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
427 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
428 "$24", "$25", "$26", "$27", "$28", "$29", "$30", "$31"
429 };
430
431 struct mips_abi_choice
432 {
433 const char * name;
434 const char * const *gpr_names;
435 const char * const *fpr_names;
436 };
437
438 struct mips_abi_choice mips_abi_choices[] =
439 {
440 { "numeric", mips_gpr_names_numeric, mips_fpr_names_numeric },
441 { "32", mips_gpr_names_oldabi, mips_fpr_names_32 },
442 { "n32", mips_gpr_names_newabi, mips_fpr_names_n32 },
443 { "64", mips_gpr_names_newabi, mips_fpr_names_64 },
444 };
445
446 struct mips_arch_choice
447 {
448 const char *name;
449 int bfd_mach_valid;
450 unsigned long bfd_mach;
451 int processor;
452 int isa;
453 int ase;
454 const char * const *cp0_names;
455 const struct mips_cp0sel_name *cp0sel_names;
456 unsigned int cp0sel_names_len;
457 const char * const *cp1_names;
458 const char * const *hwr_names;
459 };
460
461 const struct mips_arch_choice mips_arch_choices[] =
462 {
463 { "numeric", 0, 0, 0, 0, 0,
464 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
465 mips_hwr_names_numeric },
466
467 { "r3000", 1, bfd_mach_mips3000, CPU_R3000, ISA_MIPS1, 0,
468 mips_cp0_names_r3000, NULL, 0, mips_cp1_names_numeric,
469 mips_hwr_names_numeric },
470 { "r3900", 1, bfd_mach_mips3900, CPU_R3900, ISA_MIPS1, 0,
471 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
472 mips_hwr_names_numeric },
473 { "r4000", 1, bfd_mach_mips4000, CPU_R4000, ISA_MIPS3, 0,
474 mips_cp0_names_r4000, NULL, 0, mips_cp1_names_numeric,
475 mips_hwr_names_numeric },
476 { "r4010", 1, bfd_mach_mips4010, CPU_R4010, ISA_MIPS2, 0,
477 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
478 mips_hwr_names_numeric },
479 { "vr4100", 1, bfd_mach_mips4100, CPU_VR4100, ISA_MIPS3, 0,
480 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
481 mips_hwr_names_numeric },
482 { "vr4111", 1, bfd_mach_mips4111, CPU_R4111, ISA_MIPS3, 0,
483 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
484 mips_hwr_names_numeric },
485 { "vr4120", 1, bfd_mach_mips4120, CPU_VR4120, ISA_MIPS3, 0,
486 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
487 mips_hwr_names_numeric },
488 { "r4300", 1, bfd_mach_mips4300, CPU_R4300, ISA_MIPS3, 0,
489 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
490 mips_hwr_names_numeric },
491 { "r4400", 1, bfd_mach_mips4400, CPU_R4400, ISA_MIPS3, 0,
492 mips_cp0_names_r4000, NULL, 0, mips_cp1_names_numeric,
493 mips_hwr_names_numeric },
494 { "r4600", 1, bfd_mach_mips4600, CPU_R4600, ISA_MIPS3, 0,
495 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
496 mips_hwr_names_numeric },
497 { "r4650", 1, bfd_mach_mips4650, CPU_R4650, ISA_MIPS3, 0,
498 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
499 mips_hwr_names_numeric },
500 { "r5000", 1, bfd_mach_mips5000, CPU_R5000, ISA_MIPS4, 0,
501 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
502 mips_hwr_names_numeric },
503 { "vr5400", 1, bfd_mach_mips5400, CPU_VR5400, ISA_MIPS4, 0,
504 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
505 mips_hwr_names_numeric },
506 { "vr5500", 1, bfd_mach_mips5500, CPU_VR5500, ISA_MIPS4, 0,
507 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
508 mips_hwr_names_numeric },
509 { "r5900", 1, bfd_mach_mips5900, CPU_R5900, ISA_MIPS3, 0,
510 mips_cp0_names_r5900, NULL, 0, mips_cp1_names_numeric,
511 mips_hwr_names_numeric },
512 { "r6000", 1, bfd_mach_mips6000, CPU_R6000, ISA_MIPS2, 0,
513 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
514 mips_hwr_names_numeric },
515 { "rm7000", 1, bfd_mach_mips7000, CPU_RM7000, ISA_MIPS4, 0,
516 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
517 mips_hwr_names_numeric },
518 { "rm9000", 1, bfd_mach_mips7000, CPU_RM7000, ISA_MIPS4, 0,
519 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
520 mips_hwr_names_numeric },
521 { "r8000", 1, bfd_mach_mips8000, CPU_R8000, ISA_MIPS4, 0,
522 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
523 mips_hwr_names_numeric },
524 { "r10000", 1, bfd_mach_mips10000, CPU_R10000, ISA_MIPS4, 0,
525 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
526 mips_hwr_names_numeric },
527 { "r12000", 1, bfd_mach_mips12000, CPU_R12000, ISA_MIPS4, 0,
528 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
529 mips_hwr_names_numeric },
530 { "r14000", 1, bfd_mach_mips14000, CPU_R14000, ISA_MIPS4, 0,
531 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
532 mips_hwr_names_numeric },
533 { "r16000", 1, bfd_mach_mips16000, CPU_R16000, ISA_MIPS4, 0,
534 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
535 mips_hwr_names_numeric },
536 { "mips5", 1, bfd_mach_mips5, CPU_MIPS5, ISA_MIPS5, 0,
537 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
538 mips_hwr_names_numeric },
539
540 /* For stock MIPS32, disassemble all applicable MIPS-specified ASEs.
541 Note that MIPS-3D and MDMX are not applicable to MIPS32. (See
542 _MIPS32 Architecture For Programmers Volume I: Introduction to the
543 MIPS32 Architecture_ (MIPS Document Number MD00082, Revision 0.95),
544 page 1. */
545 { "mips32", 1, bfd_mach_mipsisa32, CPU_MIPS32,
546 ISA_MIPS32, ASE_SMARTMIPS,
547 mips_cp0_names_mips3264,
548 mips_cp0sel_names_mips3264, ARRAY_SIZE (mips_cp0sel_names_mips3264),
549 mips_cp1_names_mips3264, mips_hwr_names_numeric },
550
551 { "mips32r2", 1, bfd_mach_mipsisa32r2, CPU_MIPS32R2,
552 ISA_MIPS32R2,
553 (ASE_SMARTMIPS | ASE_DSP | ASE_DSPR2 | ASE_EVA | ASE_MIPS3D
554 | ASE_MT | ASE_MCU | ASE_VIRT | ASE_MSA | ASE_XPA),
555 mips_cp0_names_mips3264r2,
556 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
557 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
558
559 { "mips32r3", 1, bfd_mach_mipsisa32r3, CPU_MIPS32R3,
560 ISA_MIPS32R3,
561 (ASE_SMARTMIPS | ASE_DSP | ASE_DSPR2 | ASE_EVA | ASE_MIPS3D
562 | ASE_MT | ASE_MCU | ASE_VIRT | ASE_MSA | ASE_XPA),
563 mips_cp0_names_mips3264r2,
564 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
565 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
566
567 { "mips32r5", 1, bfd_mach_mipsisa32r5, CPU_MIPS32R5,
568 ISA_MIPS32R5,
569 (ASE_SMARTMIPS | ASE_DSP | ASE_DSPR2 | ASE_EVA | ASE_MIPS3D
570 | ASE_MT | ASE_MCU | ASE_VIRT | ASE_MSA | ASE_XPA),
571 mips_cp0_names_mips3264r2,
572 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
573 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
574
575 { "mips32r6", 1, bfd_mach_mipsisa32r6, CPU_MIPS32R6,
576 ISA_MIPS32R6,
577 (ASE_EVA | ASE_MSA | ASE_VIRT | ASE_XPA | ASE_MCU | ASE_MT | ASE_DSP
578 | ASE_DSPR2),
579 mips_cp0_names_mips3264r2,
580 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
581 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
582
583 /* For stock MIPS64, disassemble all applicable MIPS-specified ASEs. */
584 { "mips64", 1, bfd_mach_mipsisa64, CPU_MIPS64,
585 ISA_MIPS64, ASE_MIPS3D | ASE_MDMX,
586 mips_cp0_names_mips3264,
587 mips_cp0sel_names_mips3264, ARRAY_SIZE (mips_cp0sel_names_mips3264),
588 mips_cp1_names_mips3264, mips_hwr_names_numeric },
589
590 { "mips64r2", 1, bfd_mach_mipsisa64r2, CPU_MIPS64R2,
591 ISA_MIPS64R2,
592 (ASE_MIPS3D | ASE_DSP | ASE_DSPR2 | ASE_DSP64 | ASE_EVA | ASE_MT
593 | ASE_MCU | ASE_VIRT | ASE_VIRT64 | ASE_MSA | ASE_MSA64 | ASE_XPA),
594 mips_cp0_names_mips3264r2,
595 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
596 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
597
598 { "mips64r3", 1, bfd_mach_mipsisa64r3, CPU_MIPS64R3,
599 ISA_MIPS64R3,
600 (ASE_MIPS3D | ASE_DSP | ASE_DSPR2 | ASE_DSP64 | ASE_EVA | ASE_MT
601 | ASE_MCU | ASE_VIRT | ASE_VIRT64 | ASE_MSA | ASE_MSA64 | ASE_XPA),
602 mips_cp0_names_mips3264r2,
603 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
604 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
605
606 { "mips64r5", 1, bfd_mach_mipsisa64r5, CPU_MIPS64R5,
607 ISA_MIPS64R5,
608 (ASE_MIPS3D | ASE_DSP | ASE_DSPR2 | ASE_DSP64 | ASE_EVA | ASE_MT
609 | ASE_MCU | ASE_VIRT | ASE_VIRT64 | ASE_MSA | ASE_MSA64 | ASE_XPA),
610 mips_cp0_names_mips3264r2,
611 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
612 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
613
614 { "mips64r6", 1, bfd_mach_mipsisa64r6, CPU_MIPS64R6,
615 ISA_MIPS64R6,
616 (ASE_EVA | ASE_MSA | ASE_MSA64 | ASE_XPA | ASE_VIRT | ASE_VIRT64
617 | ASE_MCU | ASE_MT | ASE_DSP | ASE_DSPR2),
618 mips_cp0_names_mips3264r2,
619 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
620 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
621
622 { "sb1", 1, bfd_mach_mips_sb1, CPU_SB1,
623 ISA_MIPS64 | INSN_SB1, ASE_MIPS3D,
624 mips_cp0_names_sb1,
625 mips_cp0sel_names_sb1, ARRAY_SIZE (mips_cp0sel_names_sb1),
626 mips_cp1_names_mips3264, mips_hwr_names_numeric },
627
628 { "loongson2e", 1, bfd_mach_mips_loongson_2e, CPU_LOONGSON_2E,
629 ISA_MIPS3 | INSN_LOONGSON_2E, 0, mips_cp0_names_numeric,
630 NULL, 0, mips_cp1_names_numeric, mips_hwr_names_numeric },
631
632 { "loongson2f", 1, bfd_mach_mips_loongson_2f, CPU_LOONGSON_2F,
633 ISA_MIPS3 | INSN_LOONGSON_2F, 0, mips_cp0_names_numeric,
634 NULL, 0, mips_cp1_names_numeric, mips_hwr_names_numeric },
635
636 { "loongson3a", 1, bfd_mach_mips_loongson_3a, CPU_LOONGSON_3A,
637 ISA_MIPS64R2 | INSN_LOONGSON_3A, 0, mips_cp0_names_numeric,
638 NULL, 0, mips_cp1_names_mips3264, mips_hwr_names_numeric },
639
640 { "octeon", 1, bfd_mach_mips_octeon, CPU_OCTEON,
641 ISA_MIPS64R2 | INSN_OCTEON, 0, mips_cp0_names_numeric, NULL, 0,
642 mips_cp1_names_mips3264, mips_hwr_names_numeric },
643
644 { "octeon+", 1, bfd_mach_mips_octeonp, CPU_OCTEONP,
645 ISA_MIPS64R2 | INSN_OCTEONP, 0, mips_cp0_names_numeric,
646 NULL, 0, mips_cp1_names_mips3264, mips_hwr_names_numeric },
647
648 { "octeon2", 1, bfd_mach_mips_octeon2, CPU_OCTEON2,
649 ISA_MIPS64R2 | INSN_OCTEON2, 0, mips_cp0_names_numeric,
650 NULL, 0, mips_cp1_names_mips3264, mips_hwr_names_numeric },
651
652 { "xlr", 1, bfd_mach_mips_xlr, CPU_XLR,
653 ISA_MIPS64 | INSN_XLR, 0,
654 mips_cp0_names_xlr,
655 mips_cp0sel_names_xlr, ARRAY_SIZE (mips_cp0sel_names_xlr),
656 mips_cp1_names_mips3264, mips_hwr_names_numeric },
657
658 /* XLP is mostly like XLR, with the prominent exception it is being
659 MIPS64R2. */
660 { "xlp", 1, bfd_mach_mips_xlr, CPU_XLR,
661 ISA_MIPS64R2 | INSN_XLR, 0,
662 mips_cp0_names_xlr,
663 mips_cp0sel_names_xlr, ARRAY_SIZE (mips_cp0sel_names_xlr),
664 mips_cp1_names_mips3264, mips_hwr_names_numeric },
665
666 /* This entry, mips16, is here only for ISA/processor selection; do
667 not print its name. */
668 { "", 1, bfd_mach_mips16, CPU_MIPS16, ISA_MIPS3, 0,
669 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
670 mips_hwr_names_numeric },
671 };
672
673 /* ISA and processor type to disassemble for, and register names to use.
674 set_default_mips_dis_options and parse_mips_dis_options fill in these
675 values. */
676 static int mips_processor;
677 static int mips_isa;
678 static int mips_ase;
679 static int micromips_ase;
680 static const char * const *mips_gpr_names;
681 static const char * const *mips_fpr_names;
682 static const char * const *mips_cp0_names;
683 static const struct mips_cp0sel_name *mips_cp0sel_names;
684 static int mips_cp0sel_names_len;
685 static const char * const *mips_cp1_names;
686 static const char * const *mips_hwr_names;
687
688 /* Other options */
689 static int no_aliases; /* If set disassemble as most general inst. */
690 \f
691 static const struct mips_abi_choice *
692 choose_abi_by_name (const char *name, unsigned int namelen)
693 {
694 const struct mips_abi_choice *c;
695 unsigned int i;
696
697 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_abi_choices) && c == NULL; i++)
698 if (strncmp (mips_abi_choices[i].name, name, namelen) == 0
699 && strlen (mips_abi_choices[i].name) == namelen)
700 c = &mips_abi_choices[i];
701
702 return c;
703 }
704
705 static const struct mips_arch_choice *
706 choose_arch_by_name (const char *name, unsigned int namelen)
707 {
708 const struct mips_arch_choice *c = NULL;
709 unsigned int i;
710
711 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_arch_choices) && c == NULL; i++)
712 if (strncmp (mips_arch_choices[i].name, name, namelen) == 0
713 && strlen (mips_arch_choices[i].name) == namelen)
714 c = &mips_arch_choices[i];
715
716 return c;
717 }
718
719 static const struct mips_arch_choice *
720 choose_arch_by_number (unsigned long mach)
721 {
722 static unsigned long hint_bfd_mach;
723 static const struct mips_arch_choice *hint_arch_choice;
724 const struct mips_arch_choice *c;
725 unsigned int i;
726
727 /* We optimize this because even if the user specifies no
728 flags, this will be done for every instruction! */
729 if (hint_bfd_mach == mach
730 && hint_arch_choice != NULL
731 && hint_arch_choice->bfd_mach == hint_bfd_mach)
732 return hint_arch_choice;
733
734 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_arch_choices) && c == NULL; i++)
735 {
736 if (mips_arch_choices[i].bfd_mach_valid
737 && mips_arch_choices[i].bfd_mach == mach)
738 {
739 c = &mips_arch_choices[i];
740 hint_bfd_mach = mach;
741 hint_arch_choice = c;
742 }
743 }
744 return c;
745 }
746
747 /* Check if the object uses NewABI conventions. */
748
749 static int
750 is_newabi (Elf_Internal_Ehdr *header)
751 {
752 /* There are no old-style ABIs which use 64-bit ELF. */
753 if (header->e_ident[EI_CLASS] == ELFCLASS64)
754 return 1;
755
756 /* If a 32-bit ELF file, n32 is a new-style ABI. */
757 if ((header->e_flags & EF_MIPS_ABI2) != 0)
758 return 1;
759
760 return 0;
761 }
762
763 /* Check if the object has microMIPS ASE code. */
764
765 static int
766 is_micromips (Elf_Internal_Ehdr *header)
767 {
768 if ((header->e_flags & EF_MIPS_ARCH_ASE_MICROMIPS) != 0)
769 return 1;
770
771 return 0;
772 }
773
774 static void
775 set_default_mips_dis_options (struct disassemble_info *info)
776 {
777 const struct mips_arch_choice *chosen_arch;
778
779 /* Defaults: mipsIII/r3000 (?!), no microMIPS ASE (any compressed code
780 is MIPS16 ASE) (o)32-style ("oldabi") GPR names, and numeric FPR,
781 CP0 register, and HWR names. */
782 mips_isa = ISA_MIPS3;
783 mips_processor = CPU_R3000;
784 micromips_ase = 0;
785 mips_ase = 0;
786 mips_gpr_names = mips_gpr_names_oldabi;
787 mips_fpr_names = mips_fpr_names_numeric;
788 mips_cp0_names = mips_cp0_names_numeric;
789 mips_cp0sel_names = NULL;
790 mips_cp0sel_names_len = 0;
791 mips_cp1_names = mips_cp1_names_numeric;
792 mips_hwr_names = mips_hwr_names_numeric;
793 no_aliases = 0;
794
795 /* Update settings according to the ELF file header flags. */
796 if (info->flavour == bfd_target_elf_flavour && info->section != NULL)
797 {
798 Elf_Internal_Ehdr *header;
799
800 header = elf_elfheader (info->section->owner);
801 /* If an ELF "newabi" binary, use the n32/(n)64 GPR names. */
802 if (is_newabi (header))
803 mips_gpr_names = mips_gpr_names_newabi;
804 /* If a microMIPS binary, then don't use MIPS16 bindings. */
805 micromips_ase = is_micromips (header);
806 }
807
808 /* Set ISA, architecture, and cp0 register names as best we can. */
809 #if ! SYMTAB_AVAILABLE
810 /* This is running out on a target machine, not in a host tool.
811 FIXME: Where does mips_target_info come from? */
812 target_processor = mips_target_info.processor;
813 mips_isa = mips_target_info.isa;
814 mips_ase = mips_target_info.ase;
815 #else
816 chosen_arch = choose_arch_by_number (info->mach);
817 if (chosen_arch != NULL)
818 {
819 mips_processor = chosen_arch->processor;
820 mips_isa = chosen_arch->isa;
821 mips_ase = chosen_arch->ase;
822 mips_cp0_names = chosen_arch->cp0_names;
823 mips_cp0sel_names = chosen_arch->cp0sel_names;
824 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
825 mips_cp1_names = chosen_arch->cp1_names;
826 mips_hwr_names = chosen_arch->hwr_names;
827 }
828 #endif
829 }
830
831 static void
832 parse_mips_dis_option (const char *option, unsigned int len)
833 {
834 unsigned int i, optionlen, vallen;
835 const char *val;
836 const struct mips_abi_choice *chosen_abi;
837 const struct mips_arch_choice *chosen_arch;
838
839 /* Try to match options that are simple flags */
840 if (CONST_STRNEQ (option, "no-aliases"))
841 {
842 no_aliases = 1;
843 return;
844 }
845
846 if (CONST_STRNEQ (option, "msa"))
847 {
848 mips_ase |= ASE_MSA;
849 if ((mips_isa & INSN_ISA_MASK) == ISA_MIPS64R2
850 || (mips_isa & INSN_ISA_MASK) == ISA_MIPS64R3
851 || (mips_isa & INSN_ISA_MASK) == ISA_MIPS64R5
852 || (mips_isa & INSN_ISA_MASK) == ISA_MIPS64R6)
853 mips_ase |= ASE_MSA64;
854 return;
855 }
856
857 if (CONST_STRNEQ (option, "virt"))
858 {
859 mips_ase |= ASE_VIRT;
860 if (mips_isa & ISA_MIPS64R2
861 || mips_isa & ISA_MIPS64R3
862 || mips_isa & ISA_MIPS64R5
863 || mips_isa & ISA_MIPS64R6)
864 mips_ase |= ASE_VIRT64;
865 return;
866 }
867
868 if (CONST_STRNEQ (option, "xpa"))
869 {
870 mips_ase |= ASE_XPA;
871 return;
872 }
873
874
875 /* Look for the = that delimits the end of the option name. */
876 for (i = 0; i < len; i++)
877 if (option[i] == '=')
878 break;
879
880 if (i == 0) /* Invalid option: no name before '='. */
881 return;
882 if (i == len) /* Invalid option: no '='. */
883 return;
884 if (i == (len - 1)) /* Invalid option: no value after '='. */
885 return;
886
887 optionlen = i;
888 val = option + (optionlen + 1);
889 vallen = len - (optionlen + 1);
890
891 if (strncmp ("gpr-names", option, optionlen) == 0
892 && strlen ("gpr-names") == optionlen)
893 {
894 chosen_abi = choose_abi_by_name (val, vallen);
895 if (chosen_abi != NULL)
896 mips_gpr_names = chosen_abi->gpr_names;
897 return;
898 }
899
900 if (strncmp ("fpr-names", option, optionlen) == 0
901 && strlen ("fpr-names") == optionlen)
902 {
903 chosen_abi = choose_abi_by_name (val, vallen);
904 if (chosen_abi != NULL)
905 mips_fpr_names = chosen_abi->fpr_names;
906 return;
907 }
908
909 if (strncmp ("cp0-names", option, optionlen) == 0
910 && strlen ("cp0-names") == optionlen)
911 {
912 chosen_arch = choose_arch_by_name (val, vallen);
913 if (chosen_arch != NULL)
914 {
915 mips_cp0_names = chosen_arch->cp0_names;
916 mips_cp0sel_names = chosen_arch->cp0sel_names;
917 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
918 }
919 return;
920 }
921
922 if (strncmp ("cp1-names", option, optionlen) == 0
923 && strlen ("cp1-names") == optionlen)
924 {
925 chosen_arch = choose_arch_by_name (val, vallen);
926 if (chosen_arch != NULL)
927 mips_cp1_names = chosen_arch->cp1_names;
928 return;
929 }
930
931 if (strncmp ("hwr-names", option, optionlen) == 0
932 && strlen ("hwr-names") == optionlen)
933 {
934 chosen_arch = choose_arch_by_name (val, vallen);
935 if (chosen_arch != NULL)
936 mips_hwr_names = chosen_arch->hwr_names;
937 return;
938 }
939
940 if (strncmp ("reg-names", option, optionlen) == 0
941 && strlen ("reg-names") == optionlen)
942 {
943 /* We check both ABI and ARCH here unconditionally, so
944 that "numeric" will do the desirable thing: select
945 numeric register names for all registers. Other than
946 that, a given name probably won't match both. */
947 chosen_abi = choose_abi_by_name (val, vallen);
948 if (chosen_abi != NULL)
949 {
950 mips_gpr_names = chosen_abi->gpr_names;
951 mips_fpr_names = chosen_abi->fpr_names;
952 }
953 chosen_arch = choose_arch_by_name (val, vallen);
954 if (chosen_arch != NULL)
955 {
956 mips_cp0_names = chosen_arch->cp0_names;
957 mips_cp0sel_names = chosen_arch->cp0sel_names;
958 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
959 mips_cp1_names = chosen_arch->cp1_names;
960 mips_hwr_names = chosen_arch->hwr_names;
961 }
962 return;
963 }
964
965 /* Invalid option. */
966 }
967
968 static void
969 parse_mips_dis_options (const char *options)
970 {
971 const char *option_end;
972
973 if (options == NULL)
974 return;
975
976 while (*options != '\0')
977 {
978 /* Skip empty options. */
979 if (*options == ',')
980 {
981 options++;
982 continue;
983 }
984
985 /* We know that *options is neither NUL or a comma. */
986 option_end = options + 1;
987 while (*option_end != ',' && *option_end != '\0')
988 option_end++;
989
990 parse_mips_dis_option (options, option_end - options);
991
992 /* Go on to the next one. If option_end points to a comma, it
993 will be skipped above. */
994 options = option_end;
995 }
996 }
997
998 static const struct mips_cp0sel_name *
999 lookup_mips_cp0sel_name (const struct mips_cp0sel_name *names,
1000 unsigned int len,
1001 unsigned int cp0reg,
1002 unsigned int sel)
1003 {
1004 unsigned int i;
1005
1006 for (i = 0; i < len; i++)
1007 if (names[i].cp0reg == cp0reg && names[i].sel == sel)
1008 return &names[i];
1009 return NULL;
1010 }
1011
1012 /* Print register REGNO, of type TYPE, for instruction OPCODE. */
1013
1014 static void
1015 print_reg (struct disassemble_info *info, const struct mips_opcode *opcode,
1016 enum mips_reg_operand_type type, int regno)
1017 {
1018 switch (type)
1019 {
1020 case OP_REG_GP:
1021 info->fprintf_func (info->stream, "%s", mips_gpr_names[regno]);
1022 break;
1023
1024 case OP_REG_FP:
1025 info->fprintf_func (info->stream, "%s", mips_fpr_names[regno]);
1026 break;
1027
1028 case OP_REG_CCC:
1029 if (opcode->pinfo & (FP_D | FP_S))
1030 info->fprintf_func (info->stream, "$fcc%d", regno);
1031 else
1032 info->fprintf_func (info->stream, "$cc%d", regno);
1033 break;
1034
1035 case OP_REG_VEC:
1036 if (opcode->membership & INSN_5400)
1037 info->fprintf_func (info->stream, "$f%d", regno);
1038 else
1039 info->fprintf_func (info->stream, "$v%d", regno);
1040 break;
1041
1042 case OP_REG_ACC:
1043 info->fprintf_func (info->stream, "$ac%d", regno);
1044 break;
1045
1046 case OP_REG_COPRO:
1047 if (opcode->name[strlen (opcode->name) - 1] == '0')
1048 info->fprintf_func (info->stream, "%s", mips_cp0_names[regno]);
1049 else if (opcode->name[strlen (opcode->name) - 1] == '1')
1050 info->fprintf_func (info->stream, "%s", mips_cp1_names[regno]);
1051 else
1052 info->fprintf_func (info->stream, "$%d", regno);
1053 break;
1054
1055 case OP_REG_HW:
1056 info->fprintf_func (info->stream, "%s", mips_hwr_names[regno]);
1057 break;
1058
1059 case OP_REG_VF:
1060 info->fprintf_func (info->stream, "$vf%d", regno);
1061 break;
1062
1063 case OP_REG_VI:
1064 info->fprintf_func (info->stream, "$vi%d", regno);
1065 break;
1066
1067 case OP_REG_R5900_I:
1068 info->fprintf_func (info->stream, "$I");
1069 break;
1070
1071 case OP_REG_R5900_Q:
1072 info->fprintf_func (info->stream, "$Q");
1073 break;
1074
1075 case OP_REG_R5900_R:
1076 info->fprintf_func (info->stream, "$R");
1077 break;
1078
1079 case OP_REG_R5900_ACC:
1080 info->fprintf_func (info->stream, "$ACC");
1081 break;
1082
1083 case OP_REG_MSA:
1084 info->fprintf_func (info->stream, "$w%d", regno);
1085 break;
1086
1087 case OP_REG_MSA_CTRL:
1088 info->fprintf_func (info->stream, "%s", msa_control_names[regno]);
1089 break;
1090
1091 }
1092 }
1093 \f
1094 /* Used to track the state carried over from previous operands in
1095 an instruction. */
1096 struct mips_print_arg_state {
1097 /* The value of the last OP_INT seen. We only use this for OP_MSB,
1098 where the value is known to be unsigned and small. */
1099 unsigned int last_int;
1100
1101 /* The type and number of the last OP_REG seen. We only use this for
1102 OP_REPEAT_DEST_REG and OP_REPEAT_PREV_REG. */
1103 enum mips_reg_operand_type last_reg_type;
1104 unsigned int last_regno;
1105 unsigned int dest_regno;
1106 unsigned int seen_dest;
1107 };
1108
1109 /* Initialize STATE for the start of an instruction. */
1110
1111 static inline void
1112 init_print_arg_state (struct mips_print_arg_state *state)
1113 {
1114 memset (state, 0, sizeof (*state));
1115 }
1116
1117 /* Print OP_VU0_SUFFIX or OP_VU0_MATCH_SUFFIX operand OPERAND,
1118 whose value is given by UVAL. */
1119
1120 static void
1121 print_vu0_channel (struct disassemble_info *info,
1122 const struct mips_operand *operand, unsigned int uval)
1123 {
1124 if (operand->size == 4)
1125 info->fprintf_func (info->stream, "%s%s%s%s",
1126 uval & 8 ? "x" : "",
1127 uval & 4 ? "y" : "",
1128 uval & 2 ? "z" : "",
1129 uval & 1 ? "w" : "");
1130 else if (operand->size == 2)
1131 info->fprintf_func (info->stream, "%c", "xyzw"[uval]);
1132 else
1133 abort ();
1134 }
1135
1136 /* Record information about a register operand. */
1137
1138 static void
1139 mips_seen_register (struct mips_print_arg_state *state,
1140 unsigned int regno,
1141 enum mips_reg_operand_type reg_type)
1142 {
1143 state->last_reg_type = reg_type;
1144 state->last_regno = regno;
1145
1146 if (!state->seen_dest)
1147 {
1148 state->seen_dest = 1;
1149 state->dest_regno = regno;
1150 }
1151 }
1152
1153 /* Print operand OPERAND of OPCODE, using STATE to track inter-operand state.
1154 UVAL is the encoding of the operand (shifted into bit 0) and BASE_PC is
1155 the base address for OP_PCREL operands. */
1156
1157 static void
1158 print_insn_arg (struct disassemble_info *info,
1159 struct mips_print_arg_state *state,
1160 const struct mips_opcode *opcode,
1161 const struct mips_operand *operand,
1162 bfd_vma base_pc,
1163 unsigned int uval)
1164 {
1165 const fprintf_ftype infprintf = info->fprintf_func;
1166 void *is = info->stream;
1167
1168 switch (operand->type)
1169 {
1170 case OP_INT:
1171 {
1172 const struct mips_int_operand *int_op;
1173
1174 int_op = (const struct mips_int_operand *) operand;
1175 uval = mips_decode_int_operand (int_op, uval);
1176 state->last_int = uval;
1177 if (int_op->print_hex)
1178 infprintf (is, "0x%x", uval);
1179 else
1180 infprintf (is, "%d", uval);
1181 }
1182 break;
1183
1184 case OP_MAPPED_INT:
1185 {
1186 const struct mips_mapped_int_operand *mint_op;
1187
1188 mint_op = (const struct mips_mapped_int_operand *) operand;
1189 uval = mint_op->int_map[uval];
1190 state->last_int = uval;
1191 if (mint_op->print_hex)
1192 infprintf (is, "0x%x", uval);
1193 else
1194 infprintf (is, "%d", uval);
1195 }
1196 break;
1197
1198 case OP_MSB:
1199 {
1200 const struct mips_msb_operand *msb_op;
1201
1202 msb_op = (const struct mips_msb_operand *) operand;
1203 uval += msb_op->bias;
1204 if (msb_op->add_lsb)
1205 uval -= state->last_int;
1206 infprintf (is, "0x%x", uval);
1207 }
1208 break;
1209
1210 case OP_REG:
1211 case OP_OPTIONAL_REG:
1212 {
1213 const struct mips_reg_operand *reg_op;
1214
1215 reg_op = (const struct mips_reg_operand *) operand;
1216 uval = mips_decode_reg_operand (reg_op, uval);
1217 print_reg (info, opcode, reg_op->reg_type, uval);
1218
1219 mips_seen_register (state, uval, reg_op->reg_type);
1220 }
1221 break;
1222
1223 case OP_REG_PAIR:
1224 {
1225 const struct mips_reg_pair_operand *pair_op;
1226
1227 pair_op = (const struct mips_reg_pair_operand *) operand;
1228 print_reg (info, opcode, pair_op->reg_type,
1229 pair_op->reg1_map[uval]);
1230 infprintf (is, ",");
1231 print_reg (info, opcode, pair_op->reg_type,
1232 pair_op->reg2_map[uval]);
1233 }
1234 break;
1235
1236 case OP_PCREL:
1237 {
1238 const struct mips_pcrel_operand *pcrel_op;
1239
1240 pcrel_op = (const struct mips_pcrel_operand *) operand;
1241 info->target = mips_decode_pcrel_operand (pcrel_op, base_pc, uval);
1242
1243 /* Preserve the ISA bit for the GDB disassembler,
1244 otherwise clear it. */
1245 if (info->flavour != bfd_target_unknown_flavour)
1246 info->target &= -2;
1247
1248 (*info->print_address_func) (info->target, info);
1249 }
1250 break;
1251
1252 case OP_PERF_REG:
1253 infprintf (is, "%d", uval);
1254 break;
1255
1256 case OP_ADDIUSP_INT:
1257 {
1258 int sval;
1259
1260 sval = mips_signed_operand (operand, uval) * 4;
1261 if (sval >= -8 && sval < 8)
1262 sval ^= 0x400;
1263 infprintf (is, "%d", sval);
1264 break;
1265 }
1266
1267 case OP_CLO_CLZ_DEST:
1268 {
1269 unsigned int reg1, reg2;
1270
1271 reg1 = uval & 31;
1272 reg2 = uval >> 5;
1273 /* If one is zero use the other. */
1274 if (reg1 == reg2 || reg2 == 0)
1275 infprintf (is, "%s", mips_gpr_names[reg1]);
1276 else if (reg1 == 0)
1277 infprintf (is, "%s", mips_gpr_names[reg2]);
1278 else
1279 /* Bogus, result depends on processor. */
1280 infprintf (is, "%s or %s", mips_gpr_names[reg1],
1281 mips_gpr_names[reg2]);
1282 }
1283 break;
1284
1285 case OP_SAME_RS_RT:
1286 case OP_CHECK_PREV:
1287 case OP_NON_ZERO_REG:
1288 {
1289 print_reg (info, opcode, OP_REG_GP, uval & 31);
1290 mips_seen_register (state, uval, OP_REG_GP);
1291 }
1292 break;
1293
1294 case OP_LWM_SWM_LIST:
1295 if (operand->size == 2)
1296 {
1297 if (uval == 0)
1298 infprintf (is, "%s,%s",
1299 mips_gpr_names[16],
1300 mips_gpr_names[31]);
1301 else
1302 infprintf (is, "%s-%s,%s",
1303 mips_gpr_names[16],
1304 mips_gpr_names[16 + uval],
1305 mips_gpr_names[31]);
1306 }
1307 else
1308 {
1309 int s_reg_encode;
1310
1311 s_reg_encode = uval & 0xf;
1312 if (s_reg_encode != 0)
1313 {
1314 if (s_reg_encode == 1)
1315 infprintf (is, "%s", mips_gpr_names[16]);
1316 else if (s_reg_encode < 9)
1317 infprintf (is, "%s-%s",
1318 mips_gpr_names[16],
1319 mips_gpr_names[15 + s_reg_encode]);
1320 else if (s_reg_encode == 9)
1321 infprintf (is, "%s-%s,%s",
1322 mips_gpr_names[16],
1323 mips_gpr_names[23],
1324 mips_gpr_names[30]);
1325 else
1326 infprintf (is, "UNKNOWN");
1327 }
1328
1329 if (uval & 0x10) /* For ra. */
1330 {
1331 if (s_reg_encode == 0)
1332 infprintf (is, "%s", mips_gpr_names[31]);
1333 else
1334 infprintf (is, ",%s", mips_gpr_names[31]);
1335 }
1336 }
1337 break;
1338
1339 case OP_ENTRY_EXIT_LIST:
1340 {
1341 const char *sep;
1342 unsigned int amask, smask;
1343
1344 sep = "";
1345 amask = (uval >> 3) & 7;
1346 if (amask > 0 && amask < 5)
1347 {
1348 infprintf (is, "%s", mips_gpr_names[4]);
1349 if (amask > 1)
1350 infprintf (is, "-%s", mips_gpr_names[amask + 3]);
1351 sep = ",";
1352 }
1353
1354 smask = (uval >> 1) & 3;
1355 if (smask == 3)
1356 {
1357 infprintf (is, "%s??", sep);
1358 sep = ",";
1359 }
1360 else if (smask > 0)
1361 {
1362 infprintf (is, "%s%s", sep, mips_gpr_names[16]);
1363 if (smask > 1)
1364 infprintf (is, "-%s", mips_gpr_names[smask + 15]);
1365 sep = ",";
1366 }
1367
1368 if (uval & 1)
1369 {
1370 infprintf (is, "%s%s", sep, mips_gpr_names[31]);
1371 sep = ",";
1372 }
1373
1374 if (amask == 5 || amask == 6)
1375 {
1376 infprintf (is, "%s%s", sep, mips_fpr_names[0]);
1377 if (amask == 6)
1378 infprintf (is, "-%s", mips_fpr_names[1]);
1379 }
1380 }
1381 break;
1382
1383 case OP_SAVE_RESTORE_LIST:
1384 /* Should be handled by the caller due to extend behavior. */
1385 abort ();
1386
1387 case OP_MDMX_IMM_REG:
1388 {
1389 unsigned int vsel;
1390
1391 vsel = uval >> 5;
1392 uval &= 31;
1393 if ((vsel & 0x10) == 0)
1394 {
1395 int fmt;
1396
1397 vsel &= 0x0f;
1398 for (fmt = 0; fmt < 3; fmt++, vsel >>= 1)
1399 if ((vsel & 1) == 0)
1400 break;
1401 print_reg (info, opcode, OP_REG_VEC, uval);
1402 infprintf (is, "[%d]", vsel >> 1);
1403 }
1404 else if ((vsel & 0x08) == 0)
1405 print_reg (info, opcode, OP_REG_VEC, uval);
1406 else
1407 infprintf (is, "0x%x", uval);
1408 }
1409 break;
1410
1411 case OP_REPEAT_PREV_REG:
1412 print_reg (info, opcode, state->last_reg_type, state->last_regno);
1413 break;
1414
1415 case OP_REPEAT_DEST_REG:
1416 print_reg (info, opcode, state->last_reg_type, state->dest_regno);
1417 break;
1418
1419 case OP_PC:
1420 infprintf (is, "$pc");
1421 break;
1422
1423 case OP_VU0_SUFFIX:
1424 case OP_VU0_MATCH_SUFFIX:
1425 print_vu0_channel (info, operand, uval);
1426 break;
1427
1428 case OP_IMM_INDEX:
1429 infprintf (is, "[%d]", uval);
1430 break;
1431
1432 case OP_REG_INDEX:
1433 infprintf (is, "[");
1434 print_reg (info, opcode, OP_REG_GP, uval);
1435 infprintf (is, "]");
1436 break;
1437 }
1438 }
1439
1440 /* Validate the arguments for INSN, which is described by OPCODE.
1441 Use DECODE_OPERAND to get the encoding of each operand. */
1442
1443 static bfd_boolean
1444 validate_insn_args (const struct mips_opcode *opcode,
1445 const struct mips_operand *(*decode_operand) (const char *),
1446 unsigned int insn)
1447 {
1448 struct mips_print_arg_state state;
1449 const struct mips_operand *operand;
1450 const char *s;
1451 unsigned int uval;
1452
1453 init_print_arg_state (&state);
1454 for (s = opcode->args; *s; ++s)
1455 {
1456 switch (*s)
1457 {
1458 case ',':
1459 case '(':
1460 case ')':
1461 break;
1462
1463 case '#':
1464 ++s;
1465 break;
1466
1467 default:
1468 operand = decode_operand (s);
1469
1470 if (operand)
1471 {
1472 uval = mips_extract_operand (operand, insn);
1473 switch (operand->type)
1474 {
1475 case OP_REG:
1476 case OP_OPTIONAL_REG:
1477 {
1478 const struct mips_reg_operand *reg_op;
1479
1480 reg_op = (const struct mips_reg_operand *) operand;
1481 uval = mips_decode_reg_operand (reg_op, uval);
1482 mips_seen_register (&state, uval, reg_op->reg_type);
1483 }
1484 break;
1485
1486 case OP_SAME_RS_RT:
1487 {
1488 unsigned int reg1, reg2;
1489
1490 reg1 = uval & 31;
1491 reg2 = uval >> 5;
1492
1493 if (reg1 != reg2 || reg1 == 0)
1494 return FALSE;
1495 }
1496 break;
1497
1498 case OP_CHECK_PREV:
1499 {
1500 const struct mips_check_prev_operand *prev_op;
1501
1502 prev_op = (const struct mips_check_prev_operand *) operand;
1503
1504 if (!prev_op->zero_ok && uval == 0)
1505 return FALSE;
1506
1507 if (((prev_op->less_than_ok && uval < state.last_regno)
1508 || (prev_op->greater_than_ok && uval > state.last_regno)
1509 || (prev_op->equal_ok && uval == state.last_regno)))
1510 break;
1511
1512 return FALSE;
1513 }
1514
1515 case OP_NON_ZERO_REG:
1516 {
1517 if (uval == 0)
1518 return FALSE;
1519 }
1520 break;
1521
1522 case OP_INT:
1523 case OP_MAPPED_INT:
1524 case OP_MSB:
1525 case OP_REG_PAIR:
1526 case OP_PCREL:
1527 case OP_PERF_REG:
1528 case OP_ADDIUSP_INT:
1529 case OP_CLO_CLZ_DEST:
1530 case OP_LWM_SWM_LIST:
1531 case OP_ENTRY_EXIT_LIST:
1532 case OP_MDMX_IMM_REG:
1533 case OP_REPEAT_PREV_REG:
1534 case OP_REPEAT_DEST_REG:
1535 case OP_PC:
1536 case OP_VU0_SUFFIX:
1537 case OP_VU0_MATCH_SUFFIX:
1538 case OP_IMM_INDEX:
1539 case OP_REG_INDEX:
1540 break;
1541
1542 case OP_SAVE_RESTORE_LIST:
1543 /* Should be handled by the caller due to extend behavior. */
1544 abort ();
1545 }
1546 }
1547 if (*s == 'm' || *s == '+' || *s == '-')
1548 ++s;
1549 }
1550 }
1551 return TRUE;
1552 }
1553
1554 /* Print the arguments for INSN, which is described by OPCODE.
1555 Use DECODE_OPERAND to get the encoding of each operand. Use BASE_PC
1556 as the base of OP_PCREL operands, adjusting by LENGTH if the OP_PCREL
1557 operand is for a branch or jump. */
1558
1559 static void
1560 print_insn_args (struct disassemble_info *info,
1561 const struct mips_opcode *opcode,
1562 const struct mips_operand *(*decode_operand) (const char *),
1563 unsigned int insn, bfd_vma insn_pc, unsigned int length)
1564 {
1565 const fprintf_ftype infprintf = info->fprintf_func;
1566 void *is = info->stream;
1567 struct mips_print_arg_state state;
1568 const struct mips_operand *operand;
1569 const char *s;
1570
1571 init_print_arg_state (&state);
1572 for (s = opcode->args; *s; ++s)
1573 {
1574 switch (*s)
1575 {
1576 case ',':
1577 case '(':
1578 case ')':
1579 infprintf (is, "%c", *s);
1580 break;
1581
1582 case '#':
1583 ++s;
1584 infprintf (is, "%c%c", *s, *s);
1585 break;
1586
1587 default:
1588 operand = decode_operand (s);
1589 if (!operand)
1590 {
1591 /* xgettext:c-format */
1592 infprintf (is,
1593 _("# internal error, undefined operand in `%s %s'"),
1594 opcode->name, opcode->args);
1595 return;
1596 }
1597 if (operand->type == OP_REG
1598 && s[1] == ','
1599 && s[2] == 'H'
1600 && opcode->name[strlen (opcode->name) - 1] == '0')
1601 {
1602 /* Coprocessor register 0 with sel field (MT ASE). */
1603 const struct mips_cp0sel_name *n;
1604 unsigned int reg, sel;
1605
1606 reg = mips_extract_operand (operand, insn);
1607 s += 2;
1608 operand = decode_operand (s);
1609 sel = mips_extract_operand (operand, insn);
1610
1611 /* CP0 register including 'sel' code for mftc0, to be
1612 printed textually if known. If not known, print both
1613 CP0 register name and sel numerically since CP0 register
1614 with sel 0 may have a name unrelated to register being
1615 printed. */
1616 n = lookup_mips_cp0sel_name (mips_cp0sel_names,
1617 mips_cp0sel_names_len,
1618 reg, sel);
1619 if (n != NULL)
1620 infprintf (is, "%s", n->name);
1621 else
1622 infprintf (is, "$%d,%d", reg, sel);
1623 }
1624 else
1625 {
1626 bfd_vma base_pc = insn_pc;
1627
1628 /* Adjust the PC relative base so that branch/jump insns use
1629 the following PC as the base but genuinely PC relative
1630 operands use the current PC. */
1631 if (operand->type == OP_PCREL)
1632 {
1633 const struct mips_pcrel_operand *pcrel_op;
1634
1635 pcrel_op = (const struct mips_pcrel_operand *) operand;
1636 /* The include_isa_bit flag is sufficient to distinguish
1637 branch/jump from other PC relative operands. */
1638 if (pcrel_op->include_isa_bit)
1639 base_pc += length;
1640 }
1641
1642 print_insn_arg (info, &state, opcode, operand, base_pc,
1643 mips_extract_operand (operand, insn));
1644 }
1645 if (*s == 'm' || *s == '+' || *s == '-')
1646 ++s;
1647 break;
1648 }
1649 }
1650 }
1651 \f
1652 /* Print the mips instruction at address MEMADDR in debugged memory,
1653 on using INFO. Returns length of the instruction, in bytes, which is
1654 always INSNLEN. BIGENDIAN must be 1 if this is big-endian code, 0 if
1655 this is little-endian code. */
1656
1657 static int
1658 print_insn_mips (bfd_vma memaddr,
1659 int word,
1660 struct disassemble_info *info)
1661 {
1662 #define GET_OP(insn, field) \
1663 (((insn) >> OP_SH_##field) & OP_MASK_##field)
1664 static const struct mips_opcode *mips_hash[OP_MASK_OP + 1];
1665 const fprintf_ftype infprintf = info->fprintf_func;
1666 const struct mips_opcode *op;
1667 static bfd_boolean init = 0;
1668 void *is = info->stream;
1669
1670 /* Build a hash table to shorten the search time. */
1671 if (! init)
1672 {
1673 unsigned int i;
1674
1675 for (i = 0; i <= OP_MASK_OP; i++)
1676 {
1677 for (op = mips_opcodes; op < &mips_opcodes[NUMOPCODES]; op++)
1678 {
1679 if (op->pinfo == INSN_MACRO
1680 || (no_aliases && (op->pinfo2 & INSN2_ALIAS)))
1681 continue;
1682 if (i == GET_OP (op->match, OP))
1683 {
1684 mips_hash[i] = op;
1685 break;
1686 }
1687 }
1688 }
1689
1690 init = 1;
1691 }
1692
1693 info->bytes_per_chunk = INSNLEN;
1694 info->display_endian = info->endian;
1695 info->insn_info_valid = 1;
1696 info->branch_delay_insns = 0;
1697 info->data_size = 0;
1698 info->insn_type = dis_nonbranch;
1699 info->target = 0;
1700 info->target2 = 0;
1701
1702 op = mips_hash[GET_OP (word, OP)];
1703 if (op != NULL)
1704 {
1705 for (; op < &mips_opcodes[NUMOPCODES]; op++)
1706 {
1707 if (op->pinfo != INSN_MACRO
1708 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
1709 && (word & op->mask) == op->match)
1710 {
1711 /* We always disassemble the jalx instruction, except for MIPS r6. */
1712 if (!opcode_is_member (op, mips_isa, mips_ase, mips_processor)
1713 && (strcmp (op->name, "jalx")
1714 || (mips_isa & INSN_ISA_MASK) == ISA_MIPS32R6
1715 || (mips_isa & INSN_ISA_MASK) == ISA_MIPS64R6))
1716 continue;
1717
1718 /* Figure out instruction type and branch delay information. */
1719 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0)
1720 {
1721 if ((op->pinfo & (INSN_WRITE_GPR_31 | INSN_WRITE_1)) != 0)
1722 info->insn_type = dis_jsr;
1723 else
1724 info->insn_type = dis_branch;
1725 info->branch_delay_insns = 1;
1726 }
1727 else if ((op->pinfo & (INSN_COND_BRANCH_DELAY
1728 | INSN_COND_BRANCH_LIKELY)) != 0)
1729 {
1730 if ((op->pinfo & INSN_WRITE_GPR_31) != 0)
1731 info->insn_type = dis_condjsr;
1732 else
1733 info->insn_type = dis_condbranch;
1734 info->branch_delay_insns = 1;
1735 }
1736 else if ((op->pinfo & (INSN_STORE_MEMORY
1737 | INSN_LOAD_MEMORY)) != 0)
1738 info->insn_type = dis_dref;
1739
1740 if (!validate_insn_args (op, decode_mips_operand, word))
1741 continue;
1742
1743 infprintf (is, "%s", op->name);
1744 if (op->pinfo2 & INSN2_VU0_CHANNEL_SUFFIX)
1745 {
1746 unsigned int uval;
1747
1748 infprintf (is, ".");
1749 uval = mips_extract_operand (&mips_vu0_channel_mask, word);
1750 print_vu0_channel (info, &mips_vu0_channel_mask, uval);
1751 }
1752
1753 if (op->args[0])
1754 {
1755 infprintf (is, "\t");
1756 print_insn_args (info, op, decode_mips_operand, word,
1757 memaddr, 4);
1758 }
1759
1760 return INSNLEN;
1761 }
1762 }
1763 }
1764 #undef GET_OP
1765
1766 /* Handle undefined instructions. */
1767 info->insn_type = dis_noninsn;
1768 infprintf (is, "0x%x", word);
1769 return INSNLEN;
1770 }
1771 \f
1772 /* Disassemble an operand for a mips16 instruction. */
1773
1774 static void
1775 print_mips16_insn_arg (struct disassemble_info *info,
1776 struct mips_print_arg_state *state,
1777 const struct mips_opcode *opcode,
1778 char type, bfd_vma memaddr,
1779 unsigned insn, bfd_boolean use_extend,
1780 unsigned extend, bfd_boolean is_offset)
1781 {
1782 const fprintf_ftype infprintf = info->fprintf_func;
1783 void *is = info->stream;
1784 const struct mips_operand *operand, *ext_operand;
1785 unsigned int uval;
1786 bfd_vma baseaddr;
1787
1788 if (!use_extend)
1789 extend = 0;
1790
1791 switch (type)
1792 {
1793 case ',':
1794 case '(':
1795 case ')':
1796 infprintf (is, "%c", type);
1797 break;
1798
1799 default:
1800 operand = decode_mips16_operand (type, FALSE);
1801 if (!operand)
1802 {
1803 /* xgettext:c-format */
1804 infprintf (is, _("# internal error, undefined operand in `%s %s'"),
1805 opcode->name, opcode->args);
1806 return;
1807 }
1808
1809 if (operand->type == OP_SAVE_RESTORE_LIST)
1810 {
1811 /* Handle this case here because of the complex interation
1812 with the EXTEND opcode. */
1813 unsigned int amask, nargs, nstatics, nsreg, smask, frame_size, i, j;
1814 const char *sep;
1815
1816 amask = extend & 0xf;
1817 if (amask == MIPS16_ALL_ARGS)
1818 {
1819 nargs = 4;
1820 nstatics = 0;
1821 }
1822 else if (amask == MIPS16_ALL_STATICS)
1823 {
1824 nargs = 0;
1825 nstatics = 4;
1826 }
1827 else
1828 {
1829 nargs = amask >> 2;
1830 nstatics = amask & 3;
1831 }
1832
1833 sep = "";
1834 if (nargs > 0)
1835 {
1836 infprintf (is, "%s", mips_gpr_names[4]);
1837 if (nargs > 1)
1838 infprintf (is, "-%s", mips_gpr_names[4 + nargs - 1]);
1839 sep = ",";
1840 }
1841
1842 frame_size = ((extend & 0xf0) | (insn & 0x0f)) * 8;
1843 if (frame_size == 0 && !use_extend)
1844 frame_size = 128;
1845 infprintf (is, "%s%d", sep, frame_size);
1846
1847 if (insn & 0x40) /* $ra */
1848 infprintf (is, ",%s", mips_gpr_names[31]);
1849
1850 nsreg = (extend >> 8) & 0x7;
1851 smask = 0;
1852 if (insn & 0x20) /* $s0 */
1853 smask |= 1 << 0;
1854 if (insn & 0x10) /* $s1 */
1855 smask |= 1 << 1;
1856 if (nsreg > 0) /* $s2-$s8 */
1857 smask |= ((1 << nsreg) - 1) << 2;
1858
1859 for (i = 0; i < 9; i++)
1860 if (smask & (1 << i))
1861 {
1862 infprintf (is, ",%s", mips_gpr_names[i == 8 ? 30 : (16 + i)]);
1863 /* Skip over string of set bits. */
1864 for (j = i; smask & (2 << j); j++)
1865 continue;
1866 if (j > i)
1867 infprintf (is, "-%s", mips_gpr_names[j == 8 ? 30 : (16 + j)]);
1868 i = j + 1;
1869 }
1870 /* Statics $ax - $a3. */
1871 if (nstatics == 1)
1872 infprintf (is, ",%s", mips_gpr_names[7]);
1873 else if (nstatics > 0)
1874 infprintf (is, ",%s-%s",
1875 mips_gpr_names[7 - nstatics + 1],
1876 mips_gpr_names[7]);
1877 break;
1878 }
1879
1880 if (is_offset && operand->type == OP_INT)
1881 {
1882 const struct mips_int_operand *int_op;
1883
1884 int_op = (const struct mips_int_operand *) operand;
1885 info->insn_type = dis_dref;
1886 info->data_size = 1 << int_op->shift;
1887 }
1888
1889 if (operand->size == 26)
1890 /* In this case INSN is the first two bytes of the instruction
1891 and EXTEND is the second two bytes. */
1892 uval = ((insn & 0x1f) << 21) | ((insn & 0x3e0) << 11) | extend;
1893 else
1894 {
1895 /* Calculate the full field value. */
1896 uval = mips_extract_operand (operand, insn);
1897 if (use_extend)
1898 {
1899 ext_operand = decode_mips16_operand (type, TRUE);
1900 if (ext_operand != operand)
1901 {
1902 operand = ext_operand;
1903 if (operand->size == 16)
1904 uval |= ((extend & 0x1f) << 11) | (extend & 0x7e0);
1905 else if (operand->size == 15)
1906 uval |= ((extend & 0xf) << 11) | (extend & 0x7f0);
1907 else
1908 uval = ((extend >> 6) & 0x1f) | (extend & 0x20);
1909 }
1910 }
1911 }
1912
1913 baseaddr = memaddr + 2;
1914 if (operand->type == OP_PCREL)
1915 {
1916 const struct mips_pcrel_operand *pcrel_op;
1917
1918 pcrel_op = (const struct mips_pcrel_operand *) operand;
1919 if (!pcrel_op->include_isa_bit && use_extend)
1920 baseaddr = memaddr - 2;
1921 else if (!pcrel_op->include_isa_bit)
1922 {
1923 bfd_byte buffer[2];
1924
1925 /* If this instruction is in the delay slot of a JR
1926 instruction, the base address is the address of the
1927 JR instruction. If it is in the delay slot of a JALR
1928 instruction, the base address is the address of the
1929 JALR instruction. This test is unreliable: we have
1930 no way of knowing whether the previous word is
1931 instruction or data. */
1932 if (info->read_memory_func (memaddr - 4, buffer, 2, info) == 0
1933 && (((info->endian == BFD_ENDIAN_BIG
1934 ? bfd_getb16 (buffer)
1935 : bfd_getl16 (buffer))
1936 & 0xf800) == 0x1800))
1937 baseaddr = memaddr - 4;
1938 else if (info->read_memory_func (memaddr - 2, buffer, 2,
1939 info) == 0
1940 && (((info->endian == BFD_ENDIAN_BIG
1941 ? bfd_getb16 (buffer)
1942 : bfd_getl16 (buffer))
1943 & 0xf81f) == 0xe800))
1944 baseaddr = memaddr - 2;
1945 else
1946 baseaddr = memaddr;
1947 }
1948 }
1949
1950 print_insn_arg (info, state, opcode, operand, baseaddr + 1, uval);
1951 break;
1952 }
1953 }
1954
1955
1956 /* Check if the given address is the last word of a MIPS16 PLT entry.
1957 This word is data and depending on the value it may interfere with
1958 disassembly of further PLT entries. We make use of the fact PLT
1959 symbols are marked BSF_SYNTHETIC. */
1960 static bfd_boolean
1961 is_mips16_plt_tail (struct disassemble_info *info, bfd_vma addr)
1962 {
1963 if (info->symbols
1964 && info->symbols[0]
1965 && (info->symbols[0]->flags & BSF_SYNTHETIC)
1966 && addr == bfd_asymbol_value (info->symbols[0]) + 12)
1967 return TRUE;
1968
1969 return FALSE;
1970 }
1971
1972 /* Disassemble mips16 instructions. */
1973
1974 static int
1975 print_insn_mips16 (bfd_vma memaddr, struct disassemble_info *info)
1976 {
1977 const fprintf_ftype infprintf = info->fprintf_func;
1978 int status;
1979 bfd_byte buffer[4];
1980 int length;
1981 int insn;
1982 bfd_boolean use_extend;
1983 int extend = 0;
1984 const struct mips_opcode *op, *opend;
1985 struct mips_print_arg_state state;
1986 void *is = info->stream;
1987
1988 info->bytes_per_chunk = 2;
1989 info->display_endian = info->endian;
1990 info->insn_info_valid = 1;
1991 info->branch_delay_insns = 0;
1992 info->data_size = 0;
1993 info->target = 0;
1994 info->target2 = 0;
1995
1996 #define GET_OP(insn, field) \
1997 (((insn) >> MIPS16OP_SH_##field) & MIPS16OP_MASK_##field)
1998 /* Decode PLT entry's GOT slot address word. */
1999 if (is_mips16_plt_tail (info, memaddr))
2000 {
2001 info->insn_type = dis_noninsn;
2002 status = (*info->read_memory_func) (memaddr, buffer, 4, info);
2003 if (status == 0)
2004 {
2005 unsigned int gotslot;
2006
2007 if (info->endian == BFD_ENDIAN_BIG)
2008 gotslot = bfd_getb32 (buffer);
2009 else
2010 gotslot = bfd_getl32 (buffer);
2011 infprintf (is, ".word\t0x%x", gotslot);
2012
2013 return 4;
2014 }
2015 }
2016 else
2017 {
2018 info->insn_type = dis_nonbranch;
2019 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
2020 }
2021 if (status != 0)
2022 {
2023 (*info->memory_error_func) (status, memaddr, info);
2024 return -1;
2025 }
2026
2027 length = 2;
2028
2029 if (info->endian == BFD_ENDIAN_BIG)
2030 insn = bfd_getb16 (buffer);
2031 else
2032 insn = bfd_getl16 (buffer);
2033
2034 /* Handle the extend opcode specially. */
2035 use_extend = FALSE;
2036 if ((insn & 0xf800) == 0xf000)
2037 {
2038 use_extend = TRUE;
2039 extend = insn & 0x7ff;
2040
2041 memaddr += 2;
2042
2043 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
2044 if (status != 0)
2045 {
2046 infprintf (is, "extend 0x%x", (unsigned int) extend);
2047 (*info->memory_error_func) (status, memaddr, info);
2048 return -1;
2049 }
2050
2051 if (info->endian == BFD_ENDIAN_BIG)
2052 insn = bfd_getb16 (buffer);
2053 else
2054 insn = bfd_getl16 (buffer);
2055
2056 /* Check for an extend opcode followed by an extend opcode. */
2057 if ((insn & 0xf800) == 0xf000)
2058 {
2059 infprintf (is, "extend 0x%x", (unsigned int) extend);
2060 info->insn_type = dis_noninsn;
2061 return length;
2062 }
2063
2064 length += 2;
2065 }
2066
2067 /* FIXME: Should probably use a hash table on the major opcode here. */
2068
2069 opend = mips16_opcodes + bfd_mips16_num_opcodes;
2070 for (op = mips16_opcodes; op < opend; op++)
2071 {
2072 if (op->pinfo != INSN_MACRO
2073 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
2074 && (insn & op->mask) == op->match)
2075 {
2076 const char *s;
2077
2078 if (op->args[0] == 'a' || op->args[0] == 'i')
2079 {
2080 if (use_extend)
2081 {
2082 infprintf (is, "extend 0x%x", (unsigned int) extend);
2083 info->insn_type = dis_noninsn;
2084 return length - 2;
2085 }
2086
2087 use_extend = FALSE;
2088
2089 memaddr += 2;
2090
2091 status = (*info->read_memory_func) (memaddr, buffer, 2,
2092 info);
2093 if (status == 0)
2094 {
2095 use_extend = TRUE;
2096 if (info->endian == BFD_ENDIAN_BIG)
2097 extend = bfd_getb16 (buffer);
2098 else
2099 extend = bfd_getl16 (buffer);
2100 length += 2;
2101 }
2102 }
2103
2104 infprintf (is, "%s", op->name);
2105 if (op->args[0] != '\0')
2106 infprintf (is, "\t");
2107
2108 init_print_arg_state (&state);
2109 for (s = op->args; *s != '\0'; s++)
2110 {
2111 if (*s == ','
2112 && s[1] == 'w'
2113 && GET_OP (insn, RX) == GET_OP (insn, RY))
2114 {
2115 /* Skip the register and the comma. */
2116 ++s;
2117 continue;
2118 }
2119 if (*s == ','
2120 && s[1] == 'v'
2121 && GET_OP (insn, RZ) == GET_OP (insn, RX))
2122 {
2123 /* Skip the register and the comma. */
2124 ++s;
2125 continue;
2126 }
2127 print_mips16_insn_arg (info, &state, op, *s, memaddr, insn,
2128 use_extend, extend, s[1] == '(');
2129 }
2130
2131 /* Figure out branch instruction type and delay slot information. */
2132 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0)
2133 info->branch_delay_insns = 1;
2134 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0
2135 || (op->pinfo2 & INSN2_UNCOND_BRANCH) != 0)
2136 {
2137 if ((op->pinfo & INSN_WRITE_GPR_31) != 0)
2138 info->insn_type = dis_jsr;
2139 else
2140 info->insn_type = dis_branch;
2141 }
2142 else if ((op->pinfo2 & INSN2_COND_BRANCH) != 0)
2143 info->insn_type = dis_condbranch;
2144
2145 return length;
2146 }
2147 }
2148 #undef GET_OP
2149
2150 if (use_extend)
2151 infprintf (is, "0x%x", extend | 0xf000);
2152 infprintf (is, "0x%x", insn);
2153 info->insn_type = dis_noninsn;
2154
2155 return length;
2156 }
2157
2158 /* Disassemble microMIPS instructions. */
2159
2160 static int
2161 print_insn_micromips (bfd_vma memaddr, struct disassemble_info *info)
2162 {
2163 const fprintf_ftype infprintf = info->fprintf_func;
2164 const struct mips_opcode *op, *opend;
2165 void *is = info->stream;
2166 bfd_byte buffer[2];
2167 unsigned int higher;
2168 unsigned int length;
2169 int status;
2170 unsigned int insn;
2171
2172 info->bytes_per_chunk = 2;
2173 info->display_endian = info->endian;
2174 info->insn_info_valid = 1;
2175 info->branch_delay_insns = 0;
2176 info->data_size = 0;
2177 info->insn_type = dis_nonbranch;
2178 info->target = 0;
2179 info->target2 = 0;
2180
2181 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
2182 if (status != 0)
2183 {
2184 (*info->memory_error_func) (status, memaddr, info);
2185 return -1;
2186 }
2187
2188 length = 2;
2189
2190 if (info->endian == BFD_ENDIAN_BIG)
2191 insn = bfd_getb16 (buffer);
2192 else
2193 insn = bfd_getl16 (buffer);
2194
2195 if ((insn & 0xfc00) == 0x7c00)
2196 {
2197 /* This is a 48-bit microMIPS instruction. */
2198 higher = insn;
2199
2200 status = (*info->read_memory_func) (memaddr + 2, buffer, 2, info);
2201 if (status != 0)
2202 {
2203 infprintf (is, "micromips 0x%x", higher);
2204 (*info->memory_error_func) (status, memaddr + 2, info);
2205 return -1;
2206 }
2207 if (info->endian == BFD_ENDIAN_BIG)
2208 insn = bfd_getb16 (buffer);
2209 else
2210 insn = bfd_getl16 (buffer);
2211 higher = (higher << 16) | insn;
2212
2213 status = (*info->read_memory_func) (memaddr + 4, buffer, 2, info);
2214 if (status != 0)
2215 {
2216 infprintf (is, "micromips 0x%x", higher);
2217 (*info->memory_error_func) (status, memaddr + 4, info);
2218 return -1;
2219 }
2220 if (info->endian == BFD_ENDIAN_BIG)
2221 insn = bfd_getb16 (buffer);
2222 else
2223 insn = bfd_getl16 (buffer);
2224 infprintf (is, "0x%x%04x (48-bit insn)", higher, insn);
2225
2226 info->insn_type = dis_noninsn;
2227 return 6;
2228 }
2229 else if ((insn & 0x1c00) == 0x0000 || (insn & 0x1000) == 0x1000)
2230 {
2231 /* This is a 32-bit microMIPS instruction. */
2232 higher = insn;
2233
2234 status = (*info->read_memory_func) (memaddr + 2, buffer, 2, info);
2235 if (status != 0)
2236 {
2237 infprintf (is, "micromips 0x%x", higher);
2238 (*info->memory_error_func) (status, memaddr + 2, info);
2239 return -1;
2240 }
2241
2242 if (info->endian == BFD_ENDIAN_BIG)
2243 insn = bfd_getb16 (buffer);
2244 else
2245 insn = bfd_getl16 (buffer);
2246
2247 insn = insn | (higher << 16);
2248
2249 length += 2;
2250 }
2251
2252 /* FIXME: Should probably use a hash table on the major opcode here. */
2253
2254 opend = micromips_opcodes + bfd_micromips_num_opcodes;
2255 for (op = micromips_opcodes; op < opend; op++)
2256 {
2257 if (op->pinfo != INSN_MACRO
2258 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
2259 && (insn & op->mask) == op->match
2260 && ((length == 2 && (op->mask & 0xffff0000) == 0)
2261 || (length == 4 && (op->mask & 0xffff0000) != 0)))
2262 {
2263 if (!validate_insn_args (op, decode_micromips_operand, insn))
2264 continue;
2265
2266 infprintf (is, "%s", op->name);
2267
2268 if (op->args[0])
2269 {
2270 infprintf (is, "\t");
2271 print_insn_args (info, op, decode_micromips_operand, insn,
2272 memaddr + 1, length);
2273 }
2274
2275 /* Figure out instruction type and branch delay information. */
2276 if ((op->pinfo
2277 & (INSN_UNCOND_BRANCH_DELAY | INSN_COND_BRANCH_DELAY)) != 0)
2278 info->branch_delay_insns = 1;
2279 if (((op->pinfo & INSN_UNCOND_BRANCH_DELAY)
2280 | (op->pinfo2 & INSN2_UNCOND_BRANCH)) != 0)
2281 {
2282 if ((op->pinfo & (INSN_WRITE_GPR_31 | INSN_WRITE_1)) != 0)
2283 info->insn_type = dis_jsr;
2284 else
2285 info->insn_type = dis_branch;
2286 }
2287 else if (((op->pinfo & INSN_COND_BRANCH_DELAY)
2288 | (op->pinfo2 & INSN2_COND_BRANCH)) != 0)
2289 {
2290 if ((op->pinfo & INSN_WRITE_GPR_31) != 0)
2291 info->insn_type = dis_condjsr;
2292 else
2293 info->insn_type = dis_condbranch;
2294 }
2295 else if ((op->pinfo
2296 & (INSN_STORE_MEMORY | INSN_LOAD_MEMORY)) != 0)
2297 info->insn_type = dis_dref;
2298
2299 return length;
2300 }
2301 }
2302
2303 infprintf (is, "0x%x", insn);
2304 info->insn_type = dis_noninsn;
2305
2306 return length;
2307 }
2308
2309 /* Return 1 if a symbol associated with the location being disassembled
2310 indicates a compressed (MIPS16 or microMIPS) mode. We iterate over
2311 all the symbols at the address being considered assuming if at least
2312 one of them indicates code compression, then such code has been
2313 genuinely produced here (other symbols could have been derived from
2314 function symbols defined elsewhere or could define data). Otherwise,
2315 return 0. */
2316
2317 static bfd_boolean
2318 is_compressed_mode_p (struct disassemble_info *info)
2319 {
2320 int i;
2321 int l;
2322
2323 for (i = info->symtab_pos, l = i + info->num_symbols; i < l; i++)
2324 if (((info->symtab[i])->flags & BSF_SYNTHETIC) != 0
2325 && ((!micromips_ase
2326 && ELF_ST_IS_MIPS16 ((*info->symbols)->udata.i))
2327 || (micromips_ase
2328 && ELF_ST_IS_MICROMIPS ((*info->symbols)->udata.i))))
2329 return 1;
2330 else if (bfd_asymbol_flavour (info->symtab[i]) == bfd_target_elf_flavour
2331 && info->symtab[i]->section == info->section)
2332 {
2333 elf_symbol_type *symbol = (elf_symbol_type *) info->symtab[i];
2334 if ((!micromips_ase
2335 && ELF_ST_IS_MIPS16 (symbol->internal_elf_sym.st_other))
2336 || (micromips_ase
2337 && ELF_ST_IS_MICROMIPS (symbol->internal_elf_sym.st_other)))
2338 return 1;
2339 }
2340
2341 return 0;
2342 }
2343
2344 /* In an environment where we do not know the symbol type of the
2345 instruction we are forced to assume that the low order bit of the
2346 instructions' address may mark it as a mips16 instruction. If we
2347 are single stepping, or the pc is within the disassembled function,
2348 this works. Otherwise, we need a clue. Sometimes. */
2349
2350 static int
2351 _print_insn_mips (bfd_vma memaddr,
2352 struct disassemble_info *info,
2353 enum bfd_endian endianness)
2354 {
2355 int (*print_insn_compr) (bfd_vma, struct disassemble_info *);
2356 bfd_byte buffer[INSNLEN];
2357 int status;
2358
2359 set_default_mips_dis_options (info);
2360 parse_mips_dis_options (info->disassembler_options);
2361
2362 if (info->mach == bfd_mach_mips16)
2363 return print_insn_mips16 (memaddr, info);
2364 if (info->mach == bfd_mach_mips_micromips)
2365 return print_insn_micromips (memaddr, info);
2366
2367 print_insn_compr = !micromips_ase ? print_insn_mips16 : print_insn_micromips;
2368
2369 #if 1
2370 /* FIXME: If odd address, this is CLEARLY a compressed instruction. */
2371 /* Only a few tools will work this way. */
2372 if (memaddr & 0x01)
2373 return print_insn_compr (memaddr, info);
2374 #endif
2375
2376 #if SYMTAB_AVAILABLE
2377 if (is_compressed_mode_p (info))
2378 return print_insn_compr (memaddr, info);
2379 #endif
2380
2381 status = (*info->read_memory_func) (memaddr, buffer, INSNLEN, info);
2382 if (status == 0)
2383 {
2384 int insn;
2385
2386 if (endianness == BFD_ENDIAN_BIG)
2387 insn = bfd_getb32 (buffer);
2388 else
2389 insn = bfd_getl32 (buffer);
2390
2391 return print_insn_mips (memaddr, insn, info);
2392 }
2393 else
2394 {
2395 (*info->memory_error_func) (status, memaddr, info);
2396 return -1;
2397 }
2398 }
2399
2400 int
2401 print_insn_big_mips (bfd_vma memaddr, struct disassemble_info *info)
2402 {
2403 return _print_insn_mips (memaddr, info, BFD_ENDIAN_BIG);
2404 }
2405
2406 int
2407 print_insn_little_mips (bfd_vma memaddr, struct disassemble_info *info)
2408 {
2409 return _print_insn_mips (memaddr, info, BFD_ENDIAN_LITTLE);
2410 }
2411 \f
2412 void
2413 print_mips_disassembler_options (FILE *stream)
2414 {
2415 unsigned int i;
2416
2417 fprintf (stream, _("\n\
2418 The following MIPS specific disassembler options are supported for use\n\
2419 with the -M switch (multiple options should be separated by commas):\n"));
2420
2421 fprintf (stream, _("\n\
2422 msa Recognize MSA instructions.\n"));
2423
2424 fprintf (stream, _("\n\
2425 virt Recognize the virtualization ASE instructions.\n"));
2426
2427 fprintf (stream, _("\n\
2428 xpa Recognize the eXtended Physical Address (XPA) ASE instructions.\n"));
2429
2430 fprintf (stream, _("\n\
2431 gpr-names=ABI Print GPR names according to specified ABI.\n\
2432 Default: based on binary being disassembled.\n"));
2433
2434 fprintf (stream, _("\n\
2435 fpr-names=ABI Print FPR names according to specified ABI.\n\
2436 Default: numeric.\n"));
2437
2438 fprintf (stream, _("\n\
2439 cp0-names=ARCH Print CP0 register names according to\n\
2440 specified architecture.\n\
2441 Default: based on binary being disassembled.\n"));
2442
2443 fprintf (stream, _("\n\
2444 hwr-names=ARCH Print HWR names according to specified \n\
2445 architecture.\n\
2446 Default: based on binary being disassembled.\n"));
2447
2448 fprintf (stream, _("\n\
2449 reg-names=ABI Print GPR and FPR names according to\n\
2450 specified ABI.\n"));
2451
2452 fprintf (stream, _("\n\
2453 reg-names=ARCH Print CP0 register and HWR names according to\n\
2454 specified architecture.\n"));
2455
2456 fprintf (stream, _("\n\
2457 For the options above, the following values are supported for \"ABI\":\n\
2458 "));
2459 for (i = 0; i < ARRAY_SIZE (mips_abi_choices); i++)
2460 fprintf (stream, " %s", mips_abi_choices[i].name);
2461 fprintf (stream, _("\n"));
2462
2463 fprintf (stream, _("\n\
2464 For the options above, The following values are supported for \"ARCH\":\n\
2465 "));
2466 for (i = 0; i < ARRAY_SIZE (mips_arch_choices); i++)
2467 if (*mips_arch_choices[i].name != '\0')
2468 fprintf (stream, " %s", mips_arch_choices[i].name);
2469 fprintf (stream, _("\n"));
2470
2471 fprintf (stream, _("\n"));
2472 }
This page took 0.122432 seconds and 5 git commands to generate.