]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blob - opcodes/mips-dis.c
Add support for the MIPS eXtended Physical Address (XPA) ASE.
[thirdparty/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 /* For stock MIPS64, disassemble all applicable MIPS-specified ASEs. */
560 { "mips64", 1, bfd_mach_mipsisa64, CPU_MIPS64,
561 ISA_MIPS64, ASE_MIPS3D | ASE_MDMX,
562 mips_cp0_names_mips3264,
563 mips_cp0sel_names_mips3264, ARRAY_SIZE (mips_cp0sel_names_mips3264),
564 mips_cp1_names_mips3264, mips_hwr_names_numeric },
565
566 { "mips64r2", 1, bfd_mach_mipsisa64r2, CPU_MIPS64R2,
567 ISA_MIPS64R2,
568 (ASE_MIPS3D | ASE_DSP | ASE_DSPR2 | ASE_DSP64 | ASE_EVA | ASE_MT
569 | ASE_MCU | ASE_VIRT | ASE_VIRT64 | ASE_MSA | ASE_MSA64 | ASE_XPA),
570 mips_cp0_names_mips3264r2,
571 mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
572 mips_cp1_names_mips3264, mips_hwr_names_mips3264r2 },
573
574 { "sb1", 1, bfd_mach_mips_sb1, CPU_SB1,
575 ISA_MIPS64 | INSN_SB1, ASE_MIPS3D,
576 mips_cp0_names_sb1,
577 mips_cp0sel_names_sb1, ARRAY_SIZE (mips_cp0sel_names_sb1),
578 mips_cp1_names_mips3264, mips_hwr_names_numeric },
579
580 { "loongson2e", 1, bfd_mach_mips_loongson_2e, CPU_LOONGSON_2E,
581 ISA_MIPS3 | INSN_LOONGSON_2E, 0, mips_cp0_names_numeric,
582 NULL, 0, mips_cp1_names_numeric, mips_hwr_names_numeric },
583
584 { "loongson2f", 1, bfd_mach_mips_loongson_2f, CPU_LOONGSON_2F,
585 ISA_MIPS3 | INSN_LOONGSON_2F, 0, mips_cp0_names_numeric,
586 NULL, 0, mips_cp1_names_numeric, mips_hwr_names_numeric },
587
588 { "loongson3a", 1, bfd_mach_mips_loongson_3a, CPU_LOONGSON_3A,
589 ISA_MIPS64R2 | INSN_LOONGSON_3A, 0, mips_cp0_names_numeric,
590 NULL, 0, mips_cp1_names_mips3264, mips_hwr_names_numeric },
591
592 { "octeon", 1, bfd_mach_mips_octeon, CPU_OCTEON,
593 ISA_MIPS64R2 | INSN_OCTEON, 0, mips_cp0_names_numeric, NULL, 0,
594 mips_cp1_names_mips3264, mips_hwr_names_numeric },
595
596 { "octeon+", 1, bfd_mach_mips_octeonp, CPU_OCTEONP,
597 ISA_MIPS64R2 | INSN_OCTEONP, 0, mips_cp0_names_numeric,
598 NULL, 0, mips_cp1_names_mips3264, mips_hwr_names_numeric },
599
600 { "octeon2", 1, bfd_mach_mips_octeon2, CPU_OCTEON2,
601 ISA_MIPS64R2 | INSN_OCTEON2, 0, mips_cp0_names_numeric,
602 NULL, 0, mips_cp1_names_mips3264, mips_hwr_names_numeric },
603
604 { "xlr", 1, bfd_mach_mips_xlr, CPU_XLR,
605 ISA_MIPS64 | INSN_XLR, 0,
606 mips_cp0_names_xlr,
607 mips_cp0sel_names_xlr, ARRAY_SIZE (mips_cp0sel_names_xlr),
608 mips_cp1_names_mips3264, mips_hwr_names_numeric },
609
610 /* XLP is mostly like XLR, with the prominent exception it is being
611 MIPS64R2. */
612 { "xlp", 1, bfd_mach_mips_xlr, CPU_XLR,
613 ISA_MIPS64R2 | INSN_XLR, 0,
614 mips_cp0_names_xlr,
615 mips_cp0sel_names_xlr, ARRAY_SIZE (mips_cp0sel_names_xlr),
616 mips_cp1_names_mips3264, mips_hwr_names_numeric },
617
618 /* This entry, mips16, is here only for ISA/processor selection; do
619 not print its name. */
620 { "", 1, bfd_mach_mips16, CPU_MIPS16, ISA_MIPS3, 0,
621 mips_cp0_names_numeric, NULL, 0, mips_cp1_names_numeric,
622 mips_hwr_names_numeric },
623 };
624
625 /* ISA and processor type to disassemble for, and register names to use.
626 set_default_mips_dis_options and parse_mips_dis_options fill in these
627 values. */
628 static int mips_processor;
629 static int mips_isa;
630 static int mips_ase;
631 static int micromips_ase;
632 static const char * const *mips_gpr_names;
633 static const char * const *mips_fpr_names;
634 static const char * const *mips_cp0_names;
635 static const struct mips_cp0sel_name *mips_cp0sel_names;
636 static int mips_cp0sel_names_len;
637 static const char * const *mips_cp1_names;
638 static const char * const *mips_hwr_names;
639
640 /* Other options */
641 static int no_aliases; /* If set disassemble as most general inst. */
642 \f
643 static const struct mips_abi_choice *
644 choose_abi_by_name (const char *name, unsigned int namelen)
645 {
646 const struct mips_abi_choice *c;
647 unsigned int i;
648
649 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_abi_choices) && c == NULL; i++)
650 if (strncmp (mips_abi_choices[i].name, name, namelen) == 0
651 && strlen (mips_abi_choices[i].name) == namelen)
652 c = &mips_abi_choices[i];
653
654 return c;
655 }
656
657 static const struct mips_arch_choice *
658 choose_arch_by_name (const char *name, unsigned int namelen)
659 {
660 const struct mips_arch_choice *c = NULL;
661 unsigned int i;
662
663 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_arch_choices) && c == NULL; i++)
664 if (strncmp (mips_arch_choices[i].name, name, namelen) == 0
665 && strlen (mips_arch_choices[i].name) == namelen)
666 c = &mips_arch_choices[i];
667
668 return c;
669 }
670
671 static const struct mips_arch_choice *
672 choose_arch_by_number (unsigned long mach)
673 {
674 static unsigned long hint_bfd_mach;
675 static const struct mips_arch_choice *hint_arch_choice;
676 const struct mips_arch_choice *c;
677 unsigned int i;
678
679 /* We optimize this because even if the user specifies no
680 flags, this will be done for every instruction! */
681 if (hint_bfd_mach == mach
682 && hint_arch_choice != NULL
683 && hint_arch_choice->bfd_mach == hint_bfd_mach)
684 return hint_arch_choice;
685
686 for (i = 0, c = NULL; i < ARRAY_SIZE (mips_arch_choices) && c == NULL; i++)
687 {
688 if (mips_arch_choices[i].bfd_mach_valid
689 && mips_arch_choices[i].bfd_mach == mach)
690 {
691 c = &mips_arch_choices[i];
692 hint_bfd_mach = mach;
693 hint_arch_choice = c;
694 }
695 }
696 return c;
697 }
698
699 /* Check if the object uses NewABI conventions. */
700
701 static int
702 is_newabi (Elf_Internal_Ehdr *header)
703 {
704 /* There are no old-style ABIs which use 64-bit ELF. */
705 if (header->e_ident[EI_CLASS] == ELFCLASS64)
706 return 1;
707
708 /* If a 32-bit ELF file, n32 is a new-style ABI. */
709 if ((header->e_flags & EF_MIPS_ABI2) != 0)
710 return 1;
711
712 return 0;
713 }
714
715 /* Check if the object has microMIPS ASE code. */
716
717 static int
718 is_micromips (Elf_Internal_Ehdr *header)
719 {
720 if ((header->e_flags & EF_MIPS_ARCH_ASE_MICROMIPS) != 0)
721 return 1;
722
723 return 0;
724 }
725
726 static void
727 set_default_mips_dis_options (struct disassemble_info *info)
728 {
729 const struct mips_arch_choice *chosen_arch;
730
731 /* Defaults: mipsIII/r3000 (?!), no microMIPS ASE (any compressed code
732 is MIPS16 ASE) (o)32-style ("oldabi") GPR names, and numeric FPR,
733 CP0 register, and HWR names. */
734 mips_isa = ISA_MIPS3;
735 mips_processor = CPU_R3000;
736 micromips_ase = 0;
737 mips_ase = 0;
738 mips_gpr_names = mips_gpr_names_oldabi;
739 mips_fpr_names = mips_fpr_names_numeric;
740 mips_cp0_names = mips_cp0_names_numeric;
741 mips_cp0sel_names = NULL;
742 mips_cp0sel_names_len = 0;
743 mips_cp1_names = mips_cp1_names_numeric;
744 mips_hwr_names = mips_hwr_names_numeric;
745 no_aliases = 0;
746
747 /* Update settings according to the ELF file header flags. */
748 if (info->flavour == bfd_target_elf_flavour && info->section != NULL)
749 {
750 Elf_Internal_Ehdr *header;
751
752 header = elf_elfheader (info->section->owner);
753 /* If an ELF "newabi" binary, use the n32/(n)64 GPR names. */
754 if (is_newabi (header))
755 mips_gpr_names = mips_gpr_names_newabi;
756 /* If a microMIPS binary, then don't use MIPS16 bindings. */
757 micromips_ase = is_micromips (header);
758 }
759
760 /* Set ISA, architecture, and cp0 register names as best we can. */
761 #if ! SYMTAB_AVAILABLE
762 /* This is running out on a target machine, not in a host tool.
763 FIXME: Where does mips_target_info come from? */
764 target_processor = mips_target_info.processor;
765 mips_isa = mips_target_info.isa;
766 mips_ase = mips_target_info.ase;
767 #else
768 chosen_arch = choose_arch_by_number (info->mach);
769 if (chosen_arch != NULL)
770 {
771 mips_processor = chosen_arch->processor;
772 mips_isa = chosen_arch->isa;
773 mips_ase = chosen_arch->ase;
774 mips_cp0_names = chosen_arch->cp0_names;
775 mips_cp0sel_names = chosen_arch->cp0sel_names;
776 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
777 mips_cp1_names = chosen_arch->cp1_names;
778 mips_hwr_names = chosen_arch->hwr_names;
779 }
780 #endif
781 }
782
783 static void
784 parse_mips_dis_option (const char *option, unsigned int len)
785 {
786 unsigned int i, optionlen, vallen;
787 const char *val;
788 const struct mips_abi_choice *chosen_abi;
789 const struct mips_arch_choice *chosen_arch;
790
791 /* Try to match options that are simple flags */
792 if (CONST_STRNEQ (option, "no-aliases"))
793 {
794 no_aliases = 1;
795 return;
796 }
797
798 if (CONST_STRNEQ (option, "msa"))
799 {
800 mips_ase |= ASE_MSA;
801 if ((mips_isa & INSN_ISA_MASK) == ISA_MIPS64R2)
802 mips_ase |= ASE_MSA64;
803 return;
804 }
805
806 if (CONST_STRNEQ (option, "virt"))
807 {
808 mips_ase |= ASE_VIRT;
809 if (mips_isa & ISA_MIPS64R2)
810 mips_ase |= ASE_VIRT64;
811 return;
812 }
813
814 if (CONST_STRNEQ (option, "xpa"))
815 {
816 mips_ase |= ASE_XPA;
817 return;
818 }
819
820
821 /* Look for the = that delimits the end of the option name. */
822 for (i = 0; i < len; i++)
823 if (option[i] == '=')
824 break;
825
826 if (i == 0) /* Invalid option: no name before '='. */
827 return;
828 if (i == len) /* Invalid option: no '='. */
829 return;
830 if (i == (len - 1)) /* Invalid option: no value after '='. */
831 return;
832
833 optionlen = i;
834 val = option + (optionlen + 1);
835 vallen = len - (optionlen + 1);
836
837 if (strncmp ("gpr-names", option, optionlen) == 0
838 && strlen ("gpr-names") == optionlen)
839 {
840 chosen_abi = choose_abi_by_name (val, vallen);
841 if (chosen_abi != NULL)
842 mips_gpr_names = chosen_abi->gpr_names;
843 return;
844 }
845
846 if (strncmp ("fpr-names", option, optionlen) == 0
847 && strlen ("fpr-names") == optionlen)
848 {
849 chosen_abi = choose_abi_by_name (val, vallen);
850 if (chosen_abi != NULL)
851 mips_fpr_names = chosen_abi->fpr_names;
852 return;
853 }
854
855 if (strncmp ("cp0-names", option, optionlen) == 0
856 && strlen ("cp0-names") == optionlen)
857 {
858 chosen_arch = choose_arch_by_name (val, vallen);
859 if (chosen_arch != NULL)
860 {
861 mips_cp0_names = chosen_arch->cp0_names;
862 mips_cp0sel_names = chosen_arch->cp0sel_names;
863 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
864 }
865 return;
866 }
867
868 if (strncmp ("cp1-names", option, optionlen) == 0
869 && strlen ("cp1-names") == optionlen)
870 {
871 chosen_arch = choose_arch_by_name (val, vallen);
872 if (chosen_arch != NULL)
873 mips_cp1_names = chosen_arch->cp1_names;
874 return;
875 }
876
877 if (strncmp ("hwr-names", option, optionlen) == 0
878 && strlen ("hwr-names") == optionlen)
879 {
880 chosen_arch = choose_arch_by_name (val, vallen);
881 if (chosen_arch != NULL)
882 mips_hwr_names = chosen_arch->hwr_names;
883 return;
884 }
885
886 if (strncmp ("reg-names", option, optionlen) == 0
887 && strlen ("reg-names") == optionlen)
888 {
889 /* We check both ABI and ARCH here unconditionally, so
890 that "numeric" will do the desirable thing: select
891 numeric register names for all registers. Other than
892 that, a given name probably won't match both. */
893 chosen_abi = choose_abi_by_name (val, vallen);
894 if (chosen_abi != NULL)
895 {
896 mips_gpr_names = chosen_abi->gpr_names;
897 mips_fpr_names = chosen_abi->fpr_names;
898 }
899 chosen_arch = choose_arch_by_name (val, vallen);
900 if (chosen_arch != NULL)
901 {
902 mips_cp0_names = chosen_arch->cp0_names;
903 mips_cp0sel_names = chosen_arch->cp0sel_names;
904 mips_cp0sel_names_len = chosen_arch->cp0sel_names_len;
905 mips_cp1_names = chosen_arch->cp1_names;
906 mips_hwr_names = chosen_arch->hwr_names;
907 }
908 return;
909 }
910
911 /* Invalid option. */
912 }
913
914 static void
915 parse_mips_dis_options (const char *options)
916 {
917 const char *option_end;
918
919 if (options == NULL)
920 return;
921
922 while (*options != '\0')
923 {
924 /* Skip empty options. */
925 if (*options == ',')
926 {
927 options++;
928 continue;
929 }
930
931 /* We know that *options is neither NUL or a comma. */
932 option_end = options + 1;
933 while (*option_end != ',' && *option_end != '\0')
934 option_end++;
935
936 parse_mips_dis_option (options, option_end - options);
937
938 /* Go on to the next one. If option_end points to a comma, it
939 will be skipped above. */
940 options = option_end;
941 }
942 }
943
944 static const struct mips_cp0sel_name *
945 lookup_mips_cp0sel_name (const struct mips_cp0sel_name *names,
946 unsigned int len,
947 unsigned int cp0reg,
948 unsigned int sel)
949 {
950 unsigned int i;
951
952 for (i = 0; i < len; i++)
953 if (names[i].cp0reg == cp0reg && names[i].sel == sel)
954 return &names[i];
955 return NULL;
956 }
957
958 /* Print register REGNO, of type TYPE, for instruction OPCODE. */
959
960 static void
961 print_reg (struct disassemble_info *info, const struct mips_opcode *opcode,
962 enum mips_reg_operand_type type, int regno)
963 {
964 switch (type)
965 {
966 case OP_REG_GP:
967 info->fprintf_func (info->stream, "%s", mips_gpr_names[regno]);
968 break;
969
970 case OP_REG_FP:
971 info->fprintf_func (info->stream, "%s", mips_fpr_names[regno]);
972 break;
973
974 case OP_REG_CCC:
975 if (opcode->pinfo & (FP_D | FP_S))
976 info->fprintf_func (info->stream, "$fcc%d", regno);
977 else
978 info->fprintf_func (info->stream, "$cc%d", regno);
979 break;
980
981 case OP_REG_VEC:
982 if (opcode->membership & INSN_5400)
983 info->fprintf_func (info->stream, "$f%d", regno);
984 else
985 info->fprintf_func (info->stream, "$v%d", regno);
986 break;
987
988 case OP_REG_ACC:
989 info->fprintf_func (info->stream, "$ac%d", regno);
990 break;
991
992 case OP_REG_COPRO:
993 if (opcode->name[strlen (opcode->name) - 1] == '0')
994 info->fprintf_func (info->stream, "%s", mips_cp0_names[regno]);
995 else if (opcode->name[strlen (opcode->name) - 1] == '1')
996 info->fprintf_func (info->stream, "%s", mips_cp1_names[regno]);
997 else
998 info->fprintf_func (info->stream, "$%d", regno);
999 break;
1000
1001 case OP_REG_HW:
1002 info->fprintf_func (info->stream, "%s", mips_hwr_names[regno]);
1003 break;
1004
1005 case OP_REG_VF:
1006 info->fprintf_func (info->stream, "$vf%d", regno);
1007 break;
1008
1009 case OP_REG_VI:
1010 info->fprintf_func (info->stream, "$vi%d", regno);
1011 break;
1012
1013 case OP_REG_R5900_I:
1014 info->fprintf_func (info->stream, "$I");
1015 break;
1016
1017 case OP_REG_R5900_Q:
1018 info->fprintf_func (info->stream, "$Q");
1019 break;
1020
1021 case OP_REG_R5900_R:
1022 info->fprintf_func (info->stream, "$R");
1023 break;
1024
1025 case OP_REG_R5900_ACC:
1026 info->fprintf_func (info->stream, "$ACC");
1027 break;
1028
1029 case OP_REG_MSA:
1030 info->fprintf_func (info->stream, "$w%d", regno);
1031 break;
1032
1033 case OP_REG_MSA_CTRL:
1034 info->fprintf_func (info->stream, "%s", msa_control_names[regno]);
1035 break;
1036
1037 }
1038 }
1039 \f
1040 /* Used to track the state carried over from previous operands in
1041 an instruction. */
1042 struct mips_print_arg_state {
1043 /* The value of the last OP_INT seen. We only use this for OP_MSB,
1044 where the value is known to be unsigned and small. */
1045 unsigned int last_int;
1046
1047 /* The type and number of the last OP_REG seen. We only use this for
1048 OP_REPEAT_DEST_REG and OP_REPEAT_PREV_REG. */
1049 enum mips_reg_operand_type last_reg_type;
1050 unsigned int last_regno;
1051 };
1052
1053 /* Initialize STATE for the start of an instruction. */
1054
1055 static inline void
1056 init_print_arg_state (struct mips_print_arg_state *state)
1057 {
1058 memset (state, 0, sizeof (*state));
1059 }
1060
1061 /* Print OP_VU0_SUFFIX or OP_VU0_MATCH_SUFFIX operand OPERAND,
1062 whose value is given by UVAL. */
1063
1064 static void
1065 print_vu0_channel (struct disassemble_info *info,
1066 const struct mips_operand *operand, unsigned int uval)
1067 {
1068 if (operand->size == 4)
1069 info->fprintf_func (info->stream, "%s%s%s%s",
1070 uval & 8 ? "x" : "",
1071 uval & 4 ? "y" : "",
1072 uval & 2 ? "z" : "",
1073 uval & 1 ? "w" : "");
1074 else if (operand->size == 2)
1075 info->fprintf_func (info->stream, "%c", "xyzw"[uval]);
1076 else
1077 abort ();
1078 }
1079
1080 /* Print operand OPERAND of OPCODE, using STATE to track inter-operand state.
1081 UVAL is the encoding of the operand (shifted into bit 0) and BASE_PC is
1082 the base address for OP_PCREL operands. */
1083
1084 static void
1085 print_insn_arg (struct disassemble_info *info,
1086 struct mips_print_arg_state *state,
1087 const struct mips_opcode *opcode,
1088 const struct mips_operand *operand,
1089 bfd_vma base_pc,
1090 unsigned int uval)
1091 {
1092 const fprintf_ftype infprintf = info->fprintf_func;
1093 void *is = info->stream;
1094
1095 switch (operand->type)
1096 {
1097 case OP_INT:
1098 {
1099 const struct mips_int_operand *int_op;
1100
1101 int_op = (const struct mips_int_operand *) operand;
1102 uval = mips_decode_int_operand (int_op, uval);
1103 state->last_int = uval;
1104 if (int_op->print_hex)
1105 infprintf (is, "0x%x", uval);
1106 else
1107 infprintf (is, "%d", uval);
1108 }
1109 break;
1110
1111 case OP_MAPPED_INT:
1112 {
1113 const struct mips_mapped_int_operand *mint_op;
1114
1115 mint_op = (const struct mips_mapped_int_operand *) operand;
1116 uval = mint_op->int_map[uval];
1117 state->last_int = uval;
1118 if (mint_op->print_hex)
1119 infprintf (is, "0x%x", uval);
1120 else
1121 infprintf (is, "%d", uval);
1122 }
1123 break;
1124
1125 case OP_MSB:
1126 {
1127 const struct mips_msb_operand *msb_op;
1128
1129 msb_op = (const struct mips_msb_operand *) operand;
1130 uval += msb_op->bias;
1131 if (msb_op->add_lsb)
1132 uval -= state->last_int;
1133 infprintf (is, "0x%x", uval);
1134 }
1135 break;
1136
1137 case OP_REG:
1138 case OP_OPTIONAL_REG:
1139 {
1140 const struct mips_reg_operand *reg_op;
1141
1142 reg_op = (const struct mips_reg_operand *) operand;
1143 uval = mips_decode_reg_operand (reg_op, uval);
1144 print_reg (info, opcode, reg_op->reg_type, uval);
1145
1146 state->last_reg_type = reg_op->reg_type;
1147 state->last_regno = uval;
1148 }
1149 break;
1150
1151 case OP_REG_PAIR:
1152 {
1153 const struct mips_reg_pair_operand *pair_op;
1154
1155 pair_op = (const struct mips_reg_pair_operand *) operand;
1156 print_reg (info, opcode, pair_op->reg_type,
1157 pair_op->reg1_map[uval]);
1158 infprintf (is, ",");
1159 print_reg (info, opcode, pair_op->reg_type,
1160 pair_op->reg2_map[uval]);
1161 }
1162 break;
1163
1164 case OP_PCREL:
1165 {
1166 const struct mips_pcrel_operand *pcrel_op;
1167
1168 pcrel_op = (const struct mips_pcrel_operand *) operand;
1169 info->target = mips_decode_pcrel_operand (pcrel_op, base_pc, uval);
1170
1171 /* Preserve the ISA bit for the GDB disassembler,
1172 otherwise clear it. */
1173 if (info->flavour != bfd_target_unknown_flavour)
1174 info->target &= -2;
1175
1176 (*info->print_address_func) (info->target, info);
1177 }
1178 break;
1179
1180 case OP_PERF_REG:
1181 infprintf (is, "%d", uval);
1182 break;
1183
1184 case OP_ADDIUSP_INT:
1185 {
1186 int sval;
1187
1188 sval = mips_signed_operand (operand, uval) * 4;
1189 if (sval >= -8 && sval < 8)
1190 sval ^= 0x400;
1191 infprintf (is, "%d", sval);
1192 break;
1193 }
1194
1195 case OP_CLO_CLZ_DEST:
1196 {
1197 unsigned int reg1, reg2;
1198
1199 reg1 = uval & 31;
1200 reg2 = uval >> 5;
1201 /* If one is zero use the other. */
1202 if (reg1 == reg2 || reg2 == 0)
1203 infprintf (is, "%s", mips_gpr_names[reg1]);
1204 else if (reg1 == 0)
1205 infprintf (is, "%s", mips_gpr_names[reg2]);
1206 else
1207 /* Bogus, result depends on processor. */
1208 infprintf (is, "%s or %s", mips_gpr_names[reg1],
1209 mips_gpr_names[reg2]);
1210 }
1211 break;
1212
1213 case OP_LWM_SWM_LIST:
1214 if (operand->size == 2)
1215 {
1216 if (uval == 0)
1217 infprintf (is, "%s,%s",
1218 mips_gpr_names[16],
1219 mips_gpr_names[31]);
1220 else
1221 infprintf (is, "%s-%s,%s",
1222 mips_gpr_names[16],
1223 mips_gpr_names[16 + uval],
1224 mips_gpr_names[31]);
1225 }
1226 else
1227 {
1228 int s_reg_encode;
1229
1230 s_reg_encode = uval & 0xf;
1231 if (s_reg_encode != 0)
1232 {
1233 if (s_reg_encode == 1)
1234 infprintf (is, "%s", mips_gpr_names[16]);
1235 else if (s_reg_encode < 9)
1236 infprintf (is, "%s-%s",
1237 mips_gpr_names[16],
1238 mips_gpr_names[15 + s_reg_encode]);
1239 else if (s_reg_encode == 9)
1240 infprintf (is, "%s-%s,%s",
1241 mips_gpr_names[16],
1242 mips_gpr_names[23],
1243 mips_gpr_names[30]);
1244 else
1245 infprintf (is, "UNKNOWN");
1246 }
1247
1248 if (uval & 0x10) /* For ra. */
1249 {
1250 if (s_reg_encode == 0)
1251 infprintf (is, "%s", mips_gpr_names[31]);
1252 else
1253 infprintf (is, ",%s", mips_gpr_names[31]);
1254 }
1255 }
1256 break;
1257
1258 case OP_ENTRY_EXIT_LIST:
1259 {
1260 const char *sep;
1261 unsigned int amask, smask;
1262
1263 sep = "";
1264 amask = (uval >> 3) & 7;
1265 if (amask > 0 && amask < 5)
1266 {
1267 infprintf (is, "%s", mips_gpr_names[4]);
1268 if (amask > 1)
1269 infprintf (is, "-%s", mips_gpr_names[amask + 3]);
1270 sep = ",";
1271 }
1272
1273 smask = (uval >> 1) & 3;
1274 if (smask == 3)
1275 {
1276 infprintf (is, "%s??", sep);
1277 sep = ",";
1278 }
1279 else if (smask > 0)
1280 {
1281 infprintf (is, "%s%s", sep, mips_gpr_names[16]);
1282 if (smask > 1)
1283 infprintf (is, "-%s", mips_gpr_names[smask + 15]);
1284 sep = ",";
1285 }
1286
1287 if (uval & 1)
1288 {
1289 infprintf (is, "%s%s", sep, mips_gpr_names[31]);
1290 sep = ",";
1291 }
1292
1293 if (amask == 5 || amask == 6)
1294 {
1295 infprintf (is, "%s%s", sep, mips_fpr_names[0]);
1296 if (amask == 6)
1297 infprintf (is, "-%s", mips_fpr_names[1]);
1298 }
1299 }
1300 break;
1301
1302 case OP_SAVE_RESTORE_LIST:
1303 /* Should be handled by the caller due to extend behavior. */
1304 abort ();
1305
1306 case OP_MDMX_IMM_REG:
1307 {
1308 unsigned int vsel;
1309
1310 vsel = uval >> 5;
1311 uval &= 31;
1312 if ((vsel & 0x10) == 0)
1313 {
1314 int fmt;
1315
1316 vsel &= 0x0f;
1317 for (fmt = 0; fmt < 3; fmt++, vsel >>= 1)
1318 if ((vsel & 1) == 0)
1319 break;
1320 print_reg (info, opcode, OP_REG_VEC, uval);
1321 infprintf (is, "[%d]", vsel >> 1);
1322 }
1323 else if ((vsel & 0x08) == 0)
1324 print_reg (info, opcode, OP_REG_VEC, uval);
1325 else
1326 infprintf (is, "0x%x", uval);
1327 }
1328 break;
1329
1330 case OP_REPEAT_PREV_REG:
1331 print_reg (info, opcode, state->last_reg_type, state->last_regno);
1332 break;
1333
1334 case OP_REPEAT_DEST_REG:
1335 /* Should always match OP_REPEAT_PREV_REG first. */
1336 abort ();
1337
1338 case OP_PC:
1339 infprintf (is, "$pc");
1340 break;
1341
1342 case OP_VU0_SUFFIX:
1343 case OP_VU0_MATCH_SUFFIX:
1344 print_vu0_channel (info, operand, uval);
1345 break;
1346
1347 case OP_IMM_INDEX:
1348 infprintf (is, "[%d]", uval);
1349 break;
1350
1351 case OP_REG_INDEX:
1352 infprintf (is, "[");
1353 print_reg (info, opcode, OP_REG_GP, uval);
1354 infprintf (is, "]");
1355 break;
1356 }
1357 }
1358
1359 /* Print the arguments for INSN, which is described by OPCODE.
1360 Use DECODE_OPERAND to get the encoding of each operand. Use BASE_PC
1361 as the base of OP_PCREL operands. */
1362
1363 static void
1364 print_insn_args (struct disassemble_info *info,
1365 const struct mips_opcode *opcode,
1366 const struct mips_operand *(*decode_operand) (const char *),
1367 unsigned int insn, bfd_vma base_pc)
1368 {
1369 const fprintf_ftype infprintf = info->fprintf_func;
1370 void *is = info->stream;
1371 struct mips_print_arg_state state;
1372 const struct mips_operand *operand;
1373 const char *s;
1374
1375 init_print_arg_state (&state);
1376 for (s = opcode->args; *s; ++s)
1377 {
1378 switch (*s)
1379 {
1380 case ',':
1381 case '(':
1382 case ')':
1383 infprintf (is, "%c", *s);
1384 break;
1385
1386 case '#':
1387 ++s;
1388 infprintf (is, "%c%c", *s, *s);
1389 break;
1390
1391 default:
1392 operand = decode_operand (s);
1393 if (!operand)
1394 {
1395 /* xgettext:c-format */
1396 infprintf (is,
1397 _("# internal error, undefined operand in `%s %s'"),
1398 opcode->name, opcode->args);
1399 return;
1400 }
1401 if (operand->type == OP_REG
1402 && s[1] == ','
1403 && s[2] == 'H'
1404 && opcode->name[strlen (opcode->name) - 1] == '0')
1405 {
1406 /* Coprocessor register 0 with sel field (MT ASE). */
1407 const struct mips_cp0sel_name *n;
1408 unsigned int reg, sel;
1409
1410 reg = mips_extract_operand (operand, insn);
1411 s += 2;
1412 operand = decode_operand (s);
1413 sel = mips_extract_operand (operand, insn);
1414
1415 /* CP0 register including 'sel' code for mftc0, to be
1416 printed textually if known. If not known, print both
1417 CP0 register name and sel numerically since CP0 register
1418 with sel 0 may have a name unrelated to register being
1419 printed. */
1420 n = lookup_mips_cp0sel_name (mips_cp0sel_names,
1421 mips_cp0sel_names_len,
1422 reg, sel);
1423 if (n != NULL)
1424 infprintf (is, "%s", n->name);
1425 else
1426 infprintf (is, "$%d,%d", reg, sel);
1427 }
1428 else
1429 print_insn_arg (info, &state, opcode, operand, base_pc,
1430 mips_extract_operand (operand, insn));
1431 if (*s == 'm' || *s == '+')
1432 ++s;
1433 break;
1434 }
1435 }
1436 }
1437 \f
1438 /* Print the mips instruction at address MEMADDR in debugged memory,
1439 on using INFO. Returns length of the instruction, in bytes, which is
1440 always INSNLEN. BIGENDIAN must be 1 if this is big-endian code, 0 if
1441 this is little-endian code. */
1442
1443 static int
1444 print_insn_mips (bfd_vma memaddr,
1445 int word,
1446 struct disassemble_info *info)
1447 {
1448 #define GET_OP(insn, field) \
1449 (((insn) >> OP_SH_##field) & OP_MASK_##field)
1450 static const struct mips_opcode *mips_hash[OP_MASK_OP + 1];
1451 const fprintf_ftype infprintf = info->fprintf_func;
1452 const struct mips_opcode *op;
1453 static bfd_boolean init = 0;
1454 void *is = info->stream;
1455
1456 /* Build a hash table to shorten the search time. */
1457 if (! init)
1458 {
1459 unsigned int i;
1460
1461 for (i = 0; i <= OP_MASK_OP; i++)
1462 {
1463 for (op = mips_opcodes; op < &mips_opcodes[NUMOPCODES]; op++)
1464 {
1465 if (op->pinfo == INSN_MACRO
1466 || (no_aliases && (op->pinfo2 & INSN2_ALIAS)))
1467 continue;
1468 if (i == GET_OP (op->match, OP))
1469 {
1470 mips_hash[i] = op;
1471 break;
1472 }
1473 }
1474 }
1475
1476 init = 1;
1477 }
1478
1479 info->bytes_per_chunk = INSNLEN;
1480 info->display_endian = info->endian;
1481 info->insn_info_valid = 1;
1482 info->branch_delay_insns = 0;
1483 info->data_size = 0;
1484 info->insn_type = dis_nonbranch;
1485 info->target = 0;
1486 info->target2 = 0;
1487
1488 op = mips_hash[GET_OP (word, OP)];
1489 if (op != NULL)
1490 {
1491 for (; op < &mips_opcodes[NUMOPCODES]; op++)
1492 {
1493 if (op->pinfo != INSN_MACRO
1494 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
1495 && (word & op->mask) == op->match)
1496 {
1497 /* We always allow to disassemble the jalx instruction. */
1498 if (!opcode_is_member (op, mips_isa, mips_ase, mips_processor)
1499 && strcmp (op->name, "jalx"))
1500 continue;
1501
1502 /* Figure out instruction type and branch delay information. */
1503 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0)
1504 {
1505 if ((op->pinfo & (INSN_WRITE_GPR_31 | INSN_WRITE_1)) != 0)
1506 info->insn_type = dis_jsr;
1507 else
1508 info->insn_type = dis_branch;
1509 info->branch_delay_insns = 1;
1510 }
1511 else if ((op->pinfo & (INSN_COND_BRANCH_DELAY
1512 | INSN_COND_BRANCH_LIKELY)) != 0)
1513 {
1514 if ((op->pinfo & INSN_WRITE_GPR_31) != 0)
1515 info->insn_type = dis_condjsr;
1516 else
1517 info->insn_type = dis_condbranch;
1518 info->branch_delay_insns = 1;
1519 }
1520 else if ((op->pinfo & (INSN_STORE_MEMORY
1521 | INSN_LOAD_MEMORY)) != 0)
1522 info->insn_type = dis_dref;
1523
1524 infprintf (is, "%s", op->name);
1525 if (op->pinfo2 & INSN2_VU0_CHANNEL_SUFFIX)
1526 {
1527 unsigned int uval;
1528
1529 infprintf (is, ".");
1530 uval = mips_extract_operand (&mips_vu0_channel_mask, word);
1531 print_vu0_channel (info, &mips_vu0_channel_mask, uval);
1532 }
1533
1534 if (op->args[0])
1535 {
1536 infprintf (is, "\t");
1537 print_insn_args (info, op, decode_mips_operand, word,
1538 memaddr + 4);
1539 }
1540
1541 return INSNLEN;
1542 }
1543 }
1544 }
1545 #undef GET_OP
1546
1547 /* Handle undefined instructions. */
1548 info->insn_type = dis_noninsn;
1549 infprintf (is, "0x%x", word);
1550 return INSNLEN;
1551 }
1552 \f
1553 /* Disassemble an operand for a mips16 instruction. */
1554
1555 static void
1556 print_mips16_insn_arg (struct disassemble_info *info,
1557 struct mips_print_arg_state *state,
1558 const struct mips_opcode *opcode,
1559 char type, bfd_vma memaddr,
1560 unsigned insn, bfd_boolean use_extend,
1561 unsigned extend, bfd_boolean is_offset)
1562 {
1563 const fprintf_ftype infprintf = info->fprintf_func;
1564 void *is = info->stream;
1565 const struct mips_operand *operand, *ext_operand;
1566 unsigned int uval;
1567 bfd_vma baseaddr;
1568
1569 if (!use_extend)
1570 extend = 0;
1571
1572 switch (type)
1573 {
1574 case ',':
1575 case '(':
1576 case ')':
1577 infprintf (is, "%c", type);
1578 break;
1579
1580 default:
1581 operand = decode_mips16_operand (type, FALSE);
1582 if (!operand)
1583 {
1584 /* xgettext:c-format */
1585 infprintf (is, _("# internal error, undefined operand in `%s %s'"),
1586 opcode->name, opcode->args);
1587 return;
1588 }
1589
1590 if (operand->type == OP_SAVE_RESTORE_LIST)
1591 {
1592 /* Handle this case here because of the complex interation
1593 with the EXTEND opcode. */
1594 unsigned int amask, nargs, nstatics, nsreg, smask, frame_size, i, j;
1595 const char *sep;
1596
1597 amask = extend & 0xf;
1598 if (amask == MIPS16_ALL_ARGS)
1599 {
1600 nargs = 4;
1601 nstatics = 0;
1602 }
1603 else if (amask == MIPS16_ALL_STATICS)
1604 {
1605 nargs = 0;
1606 nstatics = 4;
1607 }
1608 else
1609 {
1610 nargs = amask >> 2;
1611 nstatics = amask & 3;
1612 }
1613
1614 sep = "";
1615 if (nargs > 0)
1616 {
1617 infprintf (is, "%s", mips_gpr_names[4]);
1618 if (nargs > 1)
1619 infprintf (is, "-%s", mips_gpr_names[4 + nargs - 1]);
1620 sep = ",";
1621 }
1622
1623 frame_size = ((extend & 0xf0) | (insn & 0x0f)) * 8;
1624 if (frame_size == 0 && !use_extend)
1625 frame_size = 128;
1626 infprintf (is, "%s%d", sep, frame_size);
1627
1628 if (insn & 0x40) /* $ra */
1629 infprintf (is, ",%s", mips_gpr_names[31]);
1630
1631 nsreg = (extend >> 8) & 0x7;
1632 smask = 0;
1633 if (insn & 0x20) /* $s0 */
1634 smask |= 1 << 0;
1635 if (insn & 0x10) /* $s1 */
1636 smask |= 1 << 1;
1637 if (nsreg > 0) /* $s2-$s8 */
1638 smask |= ((1 << nsreg) - 1) << 2;
1639
1640 for (i = 0; i < 9; i++)
1641 if (smask & (1 << i))
1642 {
1643 infprintf (is, ",%s", mips_gpr_names[i == 8 ? 30 : (16 + i)]);
1644 /* Skip over string of set bits. */
1645 for (j = i; smask & (2 << j); j++)
1646 continue;
1647 if (j > i)
1648 infprintf (is, "-%s", mips_gpr_names[j == 8 ? 30 : (16 + j)]);
1649 i = j + 1;
1650 }
1651 /* Statics $ax - $a3. */
1652 if (nstatics == 1)
1653 infprintf (is, ",%s", mips_gpr_names[7]);
1654 else if (nstatics > 0)
1655 infprintf (is, ",%s-%s",
1656 mips_gpr_names[7 - nstatics + 1],
1657 mips_gpr_names[7]);
1658 break;
1659 }
1660
1661 if (is_offset && operand->type == OP_INT)
1662 {
1663 const struct mips_int_operand *int_op;
1664
1665 int_op = (const struct mips_int_operand *) operand;
1666 info->insn_type = dis_dref;
1667 info->data_size = 1 << int_op->shift;
1668 }
1669
1670 if (operand->size == 26)
1671 /* In this case INSN is the first two bytes of the instruction
1672 and EXTEND is the second two bytes. */
1673 uval = ((insn & 0x1f) << 21) | ((insn & 0x3e0) << 11) | extend;
1674 else
1675 {
1676 /* Calculate the full field value. */
1677 uval = mips_extract_operand (operand, insn);
1678 if (use_extend)
1679 {
1680 ext_operand = decode_mips16_operand (type, TRUE);
1681 if (ext_operand != operand)
1682 {
1683 operand = ext_operand;
1684 if (operand->size == 16)
1685 uval |= ((extend & 0x1f) << 11) | (extend & 0x7e0);
1686 else if (operand->size == 15)
1687 uval |= ((extend & 0xf) << 11) | (extend & 0x7f0);
1688 else
1689 uval = ((extend >> 6) & 0x1f) | (extend & 0x20);
1690 }
1691 }
1692 }
1693
1694 baseaddr = memaddr + 2;
1695 if (operand->type == OP_PCREL)
1696 {
1697 const struct mips_pcrel_operand *pcrel_op;
1698
1699 pcrel_op = (const struct mips_pcrel_operand *) operand;
1700 if (!pcrel_op->include_isa_bit && use_extend)
1701 baseaddr = memaddr - 2;
1702 else if (!pcrel_op->include_isa_bit)
1703 {
1704 bfd_byte buffer[2];
1705
1706 /* If this instruction is in the delay slot of a JR
1707 instruction, the base address is the address of the
1708 JR instruction. If it is in the delay slot of a JALR
1709 instruction, the base address is the address of the
1710 JALR instruction. This test is unreliable: we have
1711 no way of knowing whether the previous word is
1712 instruction or data. */
1713 if (info->read_memory_func (memaddr - 4, buffer, 2, info) == 0
1714 && (((info->endian == BFD_ENDIAN_BIG
1715 ? bfd_getb16 (buffer)
1716 : bfd_getl16 (buffer))
1717 & 0xf800) == 0x1800))
1718 baseaddr = memaddr - 4;
1719 else if (info->read_memory_func (memaddr - 2, buffer, 2,
1720 info) == 0
1721 && (((info->endian == BFD_ENDIAN_BIG
1722 ? bfd_getb16 (buffer)
1723 : bfd_getl16 (buffer))
1724 & 0xf81f) == 0xe800))
1725 baseaddr = memaddr - 2;
1726 else
1727 baseaddr = memaddr;
1728 }
1729 }
1730
1731 print_insn_arg (info, state, opcode, operand, baseaddr + 1, uval);
1732 break;
1733 }
1734 }
1735
1736
1737 /* Check if the given address is the last word of a MIPS16 PLT entry.
1738 This word is data and depending on the value it may interfere with
1739 disassembly of further PLT entries. We make use of the fact PLT
1740 symbols are marked BSF_SYNTHETIC. */
1741 static bfd_boolean
1742 is_mips16_plt_tail (struct disassemble_info *info, bfd_vma addr)
1743 {
1744 if (info->symbols
1745 && info->symbols[0]
1746 && (info->symbols[0]->flags & BSF_SYNTHETIC)
1747 && addr == bfd_asymbol_value (info->symbols[0]) + 12)
1748 return TRUE;
1749
1750 return FALSE;
1751 }
1752
1753 /* Disassemble mips16 instructions. */
1754
1755 static int
1756 print_insn_mips16 (bfd_vma memaddr, struct disassemble_info *info)
1757 {
1758 const fprintf_ftype infprintf = info->fprintf_func;
1759 int status;
1760 bfd_byte buffer[4];
1761 int length;
1762 int insn;
1763 bfd_boolean use_extend;
1764 int extend = 0;
1765 const struct mips_opcode *op, *opend;
1766 struct mips_print_arg_state state;
1767 void *is = info->stream;
1768
1769 info->bytes_per_chunk = 2;
1770 info->display_endian = info->endian;
1771 info->insn_info_valid = 1;
1772 info->branch_delay_insns = 0;
1773 info->data_size = 0;
1774 info->target = 0;
1775 info->target2 = 0;
1776
1777 #define GET_OP(insn, field) \
1778 (((insn) >> MIPS16OP_SH_##field) & MIPS16OP_MASK_##field)
1779 /* Decode PLT entry's GOT slot address word. */
1780 if (is_mips16_plt_tail (info, memaddr))
1781 {
1782 info->insn_type = dis_noninsn;
1783 status = (*info->read_memory_func) (memaddr, buffer, 4, info);
1784 if (status == 0)
1785 {
1786 unsigned int gotslot;
1787
1788 if (info->endian == BFD_ENDIAN_BIG)
1789 gotslot = bfd_getb32 (buffer);
1790 else
1791 gotslot = bfd_getl32 (buffer);
1792 infprintf (is, ".word\t0x%x", gotslot);
1793
1794 return 4;
1795 }
1796 }
1797 else
1798 {
1799 info->insn_type = dis_nonbranch;
1800 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
1801 }
1802 if (status != 0)
1803 {
1804 (*info->memory_error_func) (status, memaddr, info);
1805 return -1;
1806 }
1807
1808 length = 2;
1809
1810 if (info->endian == BFD_ENDIAN_BIG)
1811 insn = bfd_getb16 (buffer);
1812 else
1813 insn = bfd_getl16 (buffer);
1814
1815 /* Handle the extend opcode specially. */
1816 use_extend = FALSE;
1817 if ((insn & 0xf800) == 0xf000)
1818 {
1819 use_extend = TRUE;
1820 extend = insn & 0x7ff;
1821
1822 memaddr += 2;
1823
1824 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
1825 if (status != 0)
1826 {
1827 infprintf (is, "extend 0x%x", (unsigned int) extend);
1828 (*info->memory_error_func) (status, memaddr, info);
1829 return -1;
1830 }
1831
1832 if (info->endian == BFD_ENDIAN_BIG)
1833 insn = bfd_getb16 (buffer);
1834 else
1835 insn = bfd_getl16 (buffer);
1836
1837 /* Check for an extend opcode followed by an extend opcode. */
1838 if ((insn & 0xf800) == 0xf000)
1839 {
1840 infprintf (is, "extend 0x%x", (unsigned int) extend);
1841 info->insn_type = dis_noninsn;
1842 return length;
1843 }
1844
1845 length += 2;
1846 }
1847
1848 /* FIXME: Should probably use a hash table on the major opcode here. */
1849
1850 opend = mips16_opcodes + bfd_mips16_num_opcodes;
1851 for (op = mips16_opcodes; op < opend; op++)
1852 {
1853 if (op->pinfo != INSN_MACRO
1854 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
1855 && (insn & op->mask) == op->match)
1856 {
1857 const char *s;
1858
1859 if (op->args[0] == 'a' || op->args[0] == 'i')
1860 {
1861 if (use_extend)
1862 {
1863 infprintf (is, "extend 0x%x", (unsigned int) extend);
1864 info->insn_type = dis_noninsn;
1865 return length - 2;
1866 }
1867
1868 use_extend = FALSE;
1869
1870 memaddr += 2;
1871
1872 status = (*info->read_memory_func) (memaddr, buffer, 2,
1873 info);
1874 if (status == 0)
1875 {
1876 use_extend = TRUE;
1877 if (info->endian == BFD_ENDIAN_BIG)
1878 extend = bfd_getb16 (buffer);
1879 else
1880 extend = bfd_getl16 (buffer);
1881 length += 2;
1882 }
1883 }
1884
1885 infprintf (is, "%s", op->name);
1886 if (op->args[0] != '\0')
1887 infprintf (is, "\t");
1888
1889 init_print_arg_state (&state);
1890 for (s = op->args; *s != '\0'; s++)
1891 {
1892 if (*s == ','
1893 && s[1] == 'w'
1894 && GET_OP (insn, RX) == GET_OP (insn, RY))
1895 {
1896 /* Skip the register and the comma. */
1897 ++s;
1898 continue;
1899 }
1900 if (*s == ','
1901 && s[1] == 'v'
1902 && GET_OP (insn, RZ) == GET_OP (insn, RX))
1903 {
1904 /* Skip the register and the comma. */
1905 ++s;
1906 continue;
1907 }
1908 print_mips16_insn_arg (info, &state, op, *s, memaddr, insn,
1909 use_extend, extend, s[1] == '(');
1910 }
1911
1912 /* Figure out branch instruction type and delay slot information. */
1913 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0)
1914 info->branch_delay_insns = 1;
1915 if ((op->pinfo & INSN_UNCOND_BRANCH_DELAY) != 0
1916 || (op->pinfo2 & INSN2_UNCOND_BRANCH) != 0)
1917 {
1918 if ((op->pinfo & INSN_WRITE_GPR_31) != 0)
1919 info->insn_type = dis_jsr;
1920 else
1921 info->insn_type = dis_branch;
1922 }
1923 else if ((op->pinfo2 & INSN2_COND_BRANCH) != 0)
1924 info->insn_type = dis_condbranch;
1925
1926 return length;
1927 }
1928 }
1929 #undef GET_OP
1930
1931 if (use_extend)
1932 infprintf (is, "0x%x", extend | 0xf000);
1933 infprintf (is, "0x%x", insn);
1934 info->insn_type = dis_noninsn;
1935
1936 return length;
1937 }
1938
1939 /* Disassemble microMIPS instructions. */
1940
1941 static int
1942 print_insn_micromips (bfd_vma memaddr, struct disassemble_info *info)
1943 {
1944 const fprintf_ftype infprintf = info->fprintf_func;
1945 const struct mips_opcode *op, *opend;
1946 void *is = info->stream;
1947 bfd_byte buffer[2];
1948 unsigned int higher;
1949 unsigned int length;
1950 int status;
1951 unsigned int insn;
1952
1953 info->bytes_per_chunk = 2;
1954 info->display_endian = info->endian;
1955 info->insn_info_valid = 1;
1956 info->branch_delay_insns = 0;
1957 info->data_size = 0;
1958 info->insn_type = dis_nonbranch;
1959 info->target = 0;
1960 info->target2 = 0;
1961
1962 status = (*info->read_memory_func) (memaddr, buffer, 2, info);
1963 if (status != 0)
1964 {
1965 (*info->memory_error_func) (status, memaddr, info);
1966 return -1;
1967 }
1968
1969 length = 2;
1970
1971 if (info->endian == BFD_ENDIAN_BIG)
1972 insn = bfd_getb16 (buffer);
1973 else
1974 insn = bfd_getl16 (buffer);
1975
1976 if ((insn & 0xfc00) == 0x7c00)
1977 {
1978 /* This is a 48-bit microMIPS instruction. */
1979 higher = insn;
1980
1981 status = (*info->read_memory_func) (memaddr + 2, buffer, 2, info);
1982 if (status != 0)
1983 {
1984 infprintf (is, "micromips 0x%x", higher);
1985 (*info->memory_error_func) (status, memaddr + 2, info);
1986 return -1;
1987 }
1988 if (info->endian == BFD_ENDIAN_BIG)
1989 insn = bfd_getb16 (buffer);
1990 else
1991 insn = bfd_getl16 (buffer);
1992 higher = (higher << 16) | insn;
1993
1994 status = (*info->read_memory_func) (memaddr + 4, buffer, 2, info);
1995 if (status != 0)
1996 {
1997 infprintf (is, "micromips 0x%x", higher);
1998 (*info->memory_error_func) (status, memaddr + 4, info);
1999 return -1;
2000 }
2001 if (info->endian == BFD_ENDIAN_BIG)
2002 insn = bfd_getb16 (buffer);
2003 else
2004 insn = bfd_getl16 (buffer);
2005 infprintf (is, "0x%x%04x (48-bit insn)", higher, insn);
2006
2007 info->insn_type = dis_noninsn;
2008 return 6;
2009 }
2010 else if ((insn & 0x1c00) == 0x0000 || (insn & 0x1000) == 0x1000)
2011 {
2012 /* This is a 32-bit microMIPS instruction. */
2013 higher = insn;
2014
2015 status = (*info->read_memory_func) (memaddr + 2, buffer, 2, info);
2016 if (status != 0)
2017 {
2018 infprintf (is, "micromips 0x%x", higher);
2019 (*info->memory_error_func) (status, memaddr + 2, info);
2020 return -1;
2021 }
2022
2023 if (info->endian == BFD_ENDIAN_BIG)
2024 insn = bfd_getb16 (buffer);
2025 else
2026 insn = bfd_getl16 (buffer);
2027
2028 insn = insn | (higher << 16);
2029
2030 length += 2;
2031 }
2032
2033 /* FIXME: Should probably use a hash table on the major opcode here. */
2034
2035 opend = micromips_opcodes + bfd_micromips_num_opcodes;
2036 for (op = micromips_opcodes; op < opend; op++)
2037 {
2038 if (op->pinfo != INSN_MACRO
2039 && !(no_aliases && (op->pinfo2 & INSN2_ALIAS))
2040 && (insn & op->mask) == op->match
2041 && ((length == 2 && (op->mask & 0xffff0000) == 0)
2042 || (length == 4 && (op->mask & 0xffff0000) != 0)))
2043 {
2044 infprintf (is, "%s", op->name);
2045
2046 if (op->args[0])
2047 {
2048 infprintf (is, "\t");
2049 print_insn_args (info, op, decode_micromips_operand, insn,
2050 memaddr + length + 1);
2051 }
2052
2053 /* Figure out instruction type and branch delay information. */
2054 if ((op->pinfo
2055 & (INSN_UNCOND_BRANCH_DELAY | INSN_COND_BRANCH_DELAY)) != 0)
2056 info->branch_delay_insns = 1;
2057 if (((op->pinfo & INSN_UNCOND_BRANCH_DELAY)
2058 | (op->pinfo2 & INSN2_UNCOND_BRANCH)) != 0)
2059 {
2060 if ((op->pinfo & (INSN_WRITE_GPR_31 | INSN_WRITE_1)) != 0)
2061 info->insn_type = dis_jsr;
2062 else
2063 info->insn_type = dis_branch;
2064 }
2065 else if (((op->pinfo & INSN_COND_BRANCH_DELAY)
2066 | (op->pinfo2 & INSN2_COND_BRANCH)) != 0)
2067 {
2068 if ((op->pinfo & INSN_WRITE_GPR_31) != 0)
2069 info->insn_type = dis_condjsr;
2070 else
2071 info->insn_type = dis_condbranch;
2072 }
2073 else if ((op->pinfo
2074 & (INSN_STORE_MEMORY | INSN_LOAD_MEMORY)) != 0)
2075 info->insn_type = dis_dref;
2076
2077 return length;
2078 }
2079 }
2080
2081 infprintf (is, "0x%x", insn);
2082 info->insn_type = dis_noninsn;
2083
2084 return length;
2085 }
2086
2087 /* Return 1 if a symbol associated with the location being disassembled
2088 indicates a compressed (MIPS16 or microMIPS) mode. We iterate over
2089 all the symbols at the address being considered assuming if at least
2090 one of them indicates code compression, then such code has been
2091 genuinely produced here (other symbols could have been derived from
2092 function symbols defined elsewhere or could define data). Otherwise,
2093 return 0. */
2094
2095 static bfd_boolean
2096 is_compressed_mode_p (struct disassemble_info *info)
2097 {
2098 int i;
2099 int l;
2100
2101 for (i = info->symtab_pos, l = i + info->num_symbols; i < l; i++)
2102 if (((info->symtab[i])->flags & BSF_SYNTHETIC) != 0
2103 && ((!micromips_ase
2104 && ELF_ST_IS_MIPS16 ((*info->symbols)->udata.i))
2105 || (micromips_ase
2106 && ELF_ST_IS_MICROMIPS ((*info->symbols)->udata.i))))
2107 return 1;
2108 else if (bfd_asymbol_flavour (info->symtab[i]) == bfd_target_elf_flavour
2109 && info->symtab[i]->section == info->section)
2110 {
2111 elf_symbol_type *symbol = (elf_symbol_type *) info->symtab[i];
2112 if ((!micromips_ase
2113 && ELF_ST_IS_MIPS16 (symbol->internal_elf_sym.st_other))
2114 || (micromips_ase
2115 && ELF_ST_IS_MICROMIPS (symbol->internal_elf_sym.st_other)))
2116 return 1;
2117 }
2118
2119 return 0;
2120 }
2121
2122 /* In an environment where we do not know the symbol type of the
2123 instruction we are forced to assume that the low order bit of the
2124 instructions' address may mark it as a mips16 instruction. If we
2125 are single stepping, or the pc is within the disassembled function,
2126 this works. Otherwise, we need a clue. Sometimes. */
2127
2128 static int
2129 _print_insn_mips (bfd_vma memaddr,
2130 struct disassemble_info *info,
2131 enum bfd_endian endianness)
2132 {
2133 int (*print_insn_compr) (bfd_vma, struct disassemble_info *);
2134 bfd_byte buffer[INSNLEN];
2135 int status;
2136
2137 set_default_mips_dis_options (info);
2138 parse_mips_dis_options (info->disassembler_options);
2139
2140 if (info->mach == bfd_mach_mips16)
2141 return print_insn_mips16 (memaddr, info);
2142 if (info->mach == bfd_mach_mips_micromips)
2143 return print_insn_micromips (memaddr, info);
2144
2145 print_insn_compr = !micromips_ase ? print_insn_mips16 : print_insn_micromips;
2146
2147 #if 1
2148 /* FIXME: If odd address, this is CLEARLY a compressed instruction. */
2149 /* Only a few tools will work this way. */
2150 if (memaddr & 0x01)
2151 return print_insn_compr (memaddr, info);
2152 #endif
2153
2154 #if SYMTAB_AVAILABLE
2155 if (is_compressed_mode_p (info))
2156 return print_insn_compr (memaddr, info);
2157 #endif
2158
2159 status = (*info->read_memory_func) (memaddr, buffer, INSNLEN, info);
2160 if (status == 0)
2161 {
2162 int insn;
2163
2164 if (endianness == BFD_ENDIAN_BIG)
2165 insn = bfd_getb32 (buffer);
2166 else
2167 insn = bfd_getl32 (buffer);
2168
2169 return print_insn_mips (memaddr, insn, info);
2170 }
2171 else
2172 {
2173 (*info->memory_error_func) (status, memaddr, info);
2174 return -1;
2175 }
2176 }
2177
2178 int
2179 print_insn_big_mips (bfd_vma memaddr, struct disassemble_info *info)
2180 {
2181 return _print_insn_mips (memaddr, info, BFD_ENDIAN_BIG);
2182 }
2183
2184 int
2185 print_insn_little_mips (bfd_vma memaddr, struct disassemble_info *info)
2186 {
2187 return _print_insn_mips (memaddr, info, BFD_ENDIAN_LITTLE);
2188 }
2189 \f
2190 void
2191 print_mips_disassembler_options (FILE *stream)
2192 {
2193 unsigned int i;
2194
2195 fprintf (stream, _("\n\
2196 The following MIPS specific disassembler options are supported for use\n\
2197 with the -M switch (multiple options should be separated by commas):\n"));
2198
2199 fprintf (stream, _("\n\
2200 msa Recognize MSA instructions.\n"));
2201
2202 fprintf (stream, _("\n\
2203 virt Recognize the virtualization ASE instructions.\n"));
2204
2205 fprintf (stream, _("\n\
2206 xpa Recognize the eXtended Physical Address (XPA) ASE instructions.\n"));
2207
2208 fprintf (stream, _("\n\
2209 gpr-names=ABI Print GPR names according to specified ABI.\n\
2210 Default: based on binary being disassembled.\n"));
2211
2212 fprintf (stream, _("\n\
2213 fpr-names=ABI Print FPR names according to specified ABI.\n\
2214 Default: numeric.\n"));
2215
2216 fprintf (stream, _("\n\
2217 cp0-names=ARCH Print CP0 register names according to\n\
2218 specified architecture.\n\
2219 Default: based on binary being disassembled.\n"));
2220
2221 fprintf (stream, _("\n\
2222 hwr-names=ARCH Print HWR names according to specified \n\
2223 architecture.\n\
2224 Default: based on binary being disassembled.\n"));
2225
2226 fprintf (stream, _("\n\
2227 reg-names=ABI Print GPR and FPR names according to\n\
2228 specified ABI.\n"));
2229
2230 fprintf (stream, _("\n\
2231 reg-names=ARCH Print CP0 register and HWR names according to\n\
2232 specified architecture.\n"));
2233
2234 fprintf (stream, _("\n\
2235 For the options above, the following values are supported for \"ABI\":\n\
2236 "));
2237 for (i = 0; i < ARRAY_SIZE (mips_abi_choices); i++)
2238 fprintf (stream, " %s", mips_abi_choices[i].name);
2239 fprintf (stream, _("\n"));
2240
2241 fprintf (stream, _("\n\
2242 For the options above, The following values are supported for \"ARCH\":\n\
2243 "));
2244 for (i = 0; i < ARRAY_SIZE (mips_arch_choices); i++)
2245 if (*mips_arch_choices[i].name != '\0')
2246 fprintf (stream, " %s", mips_arch_choices[i].name);
2247 fprintf (stream, _("\n"));
2248
2249 fprintf (stream, _("\n"));
2250 }