1 /* Disassembler code for CRIS.
2 Copyright 2000, 2001, 2002, 2004, 2005, 2006 Free Software Foundation, Inc.
3 Contributed by Axis Communications AB, Lund, Sweden.
4 Written by Hans-Peter Nilsson.
6 This file is part of the GNU binutils and GDB, the GNU debugger.
8 This program is free software; you can redistribute it and/or modify it
9 under the terms of the GNU General Public License as published by the
10 Free Software Foundation; either version 2, or (at your option) any later
13 This program is distributed in the hope that it will be useful, but WITHOUT
14 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, see <http://www.gnu.org/licenses/>. */
23 #include "target-cris/opcode-cris.h"
24 //#include "libiberty.h"
27 void *qemu_malloc(size_t len
); /* can't include qemu-common.h here */
29 #define CONST_STRNEQ(STR1,STR2) (strncmp ((STR1), (STR2), sizeof (STR2) - 1) == 0)
31 /* cris-opc.c -- Table of opcodes for the CRIS processor.
32 Copyright 2000, 2001, 2004 Free Software Foundation, Inc.
33 Contributed by Axis Communications AB, Lund, Sweden.
34 Originally written for GAS 1.38.1 by Mikael Asker.
35 Reorganized by Hans-Peter Nilsson.
37 This file is part of GAS, GDB and the GNU binutils.
39 GAS, GDB, and GNU binutils is free software; you can redistribute it
40 and/or modify it under the terms of the GNU General Public License as
41 published by the Free Software Foundation; either version 2, or (at your
42 option) any later version.
44 GAS, GDB, and GNU binutils are distributed in the hope that they will be
45 useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
46 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
47 GNU General Public License for more details.
49 You should have received a copy of the GNU General Public License
50 along with this program; if not, see <http://www.gnu.org/licenses/>. */
56 /* This table isn't used for CRISv32 and the size of immediate operands. */
57 const struct cris_spec_reg
60 {"bz", 0, 1, cris_ver_v32p
, NULL
},
61 {"p0", 0, 1, 0, NULL
},
62 {"vr", 1, 1, 0, NULL
},
63 {"p1", 1, 1, 0, NULL
},
64 {"pid", 2, 1, cris_ver_v32p
, NULL
},
65 {"p2", 2, 1, cris_ver_v32p
, NULL
},
66 {"p2", 2, 1, cris_ver_warning
, NULL
},
67 {"srs", 3, 1, cris_ver_v32p
, NULL
},
68 {"p3", 3, 1, cris_ver_v32p
, NULL
},
69 {"p3", 3, 1, cris_ver_warning
, NULL
},
70 {"wz", 4, 2, cris_ver_v32p
, NULL
},
71 {"p4", 4, 2, 0, NULL
},
72 {"ccr", 5, 2, cris_ver_v0_10
, NULL
},
73 {"exs", 5, 4, cris_ver_v32p
, NULL
},
74 {"p5", 5, 2, cris_ver_v0_10
, NULL
},
75 {"p5", 5, 4, cris_ver_v32p
, NULL
},
76 {"dcr0",6, 2, cris_ver_v0_3
, NULL
},
77 {"eda", 6, 4, cris_ver_v32p
, NULL
},
78 {"p6", 6, 2, cris_ver_v0_3
, NULL
},
79 {"p6", 6, 4, cris_ver_v32p
, NULL
},
80 {"dcr1/mof", 7, 4, cris_ver_v10p
,
81 "Register `dcr1/mof' with ambiguous size specified. Guessing 4 bytes"},
82 {"dcr1/mof", 7, 2, cris_ver_v0_3
,
83 "Register `dcr1/mof' with ambiguous size specified. Guessing 2 bytes"},
84 {"mof", 7, 4, cris_ver_v10p
, NULL
},
85 {"dcr1",7, 2, cris_ver_v0_3
, NULL
},
86 {"p7", 7, 4, cris_ver_v10p
, NULL
},
87 {"p7", 7, 2, cris_ver_v0_3
, NULL
},
88 {"dz", 8, 4, cris_ver_v32p
, NULL
},
89 {"p8", 8, 4, 0, NULL
},
90 {"ibr", 9, 4, cris_ver_v0_10
, NULL
},
91 {"ebp", 9, 4, cris_ver_v32p
, NULL
},
92 {"p9", 9, 4, 0, NULL
},
93 {"irp", 10, 4, cris_ver_v0_10
, NULL
},
94 {"erp", 10, 4, cris_ver_v32p
, NULL
},
95 {"p10", 10, 4, 0, NULL
},
96 {"srp", 11, 4, 0, NULL
},
97 {"p11", 11, 4, 0, NULL
},
98 /* For disassembly use only. Accept at assembly with a warning. */
99 {"bar/dtp0", 12, 4, cris_ver_warning
,
100 "Ambiguous register `bar/dtp0' specified"},
101 {"nrp", 12, 4, cris_ver_v32p
, NULL
},
102 {"bar", 12, 4, cris_ver_v8_10
, NULL
},
103 {"dtp0",12, 4, cris_ver_v0_3
, NULL
},
104 {"p12", 12, 4, 0, NULL
},
105 /* For disassembly use only. Accept at assembly with a warning. */
106 {"dccr/dtp1",13, 4, cris_ver_warning
,
107 "Ambiguous register `dccr/dtp1' specified"},
108 {"ccs", 13, 4, cris_ver_v32p
, NULL
},
109 {"dccr",13, 4, cris_ver_v8_10
, NULL
},
110 {"dtp1",13, 4, cris_ver_v0_3
, NULL
},
111 {"p13", 13, 4, 0, NULL
},
112 {"brp", 14, 4, cris_ver_v3_10
, NULL
},
113 {"usp", 14, 4, cris_ver_v32p
, NULL
},
114 {"p14", 14, 4, cris_ver_v3p
, NULL
},
115 {"usp", 15, 4, cris_ver_v10
, NULL
},
116 {"spc", 15, 4, cris_ver_v32p
, NULL
},
117 {"p15", 15, 4, cris_ver_v10p
, NULL
},
118 {NULL
, 0, 0, cris_ver_version_all
, NULL
}
121 /* Add version specifiers to this table when necessary.
122 The (now) regular coding of register names suggests a simpler
124 const struct cris_support_reg cris_support_regs
[] =
145 /* All CRIS opcodes are 16 bits.
147 - The match component is a mask saying which bits must match a
148 particular opcode in order for an instruction to be an instance
151 - The args component is a string containing characters symbolically
152 matching the operands of an instruction. Used for both assembly
155 Operand-matching characters:
158 A The string "ACR" (case-insensitive).
159 B Not really an operand. It causes a "BDAP -size,SP" prefix to be
160 output for the PUSH alias-instructions and recognizes a push-
161 prefix at disassembly. This letter isn't recognized for v32.
162 Must be followed by a R or P letter.
163 ! Non-match pattern, will not match if there's a prefix insn.
164 b Non-matching operand, used for branches with 16-bit
165 displacement. Only recognized by the disassembler.
166 c 5-bit unsigned immediate in bits <4:0>.
167 C 4-bit unsigned immediate in bits <3:0>.
168 d At assembly, optionally (as in put other cases before this one)
169 ".d" or ".D" at the start of the operands, followed by one space
170 character. At disassembly, nothing.
171 D General register in bits <15:12> and <3:0>.
172 f List of flags in bits <15:12> and <3:0>.
173 i 6-bit signed immediate in bits <5:0>.
174 I 6-bit unsigned immediate in bits <5:0>.
175 M Size modifier (B, W or D) for CLEAR instructions.
176 m Size modifier (B, W or D) in bits <5:4>
177 N A 32-bit dword, like in the difference between s and y.
178 This has no effect on bits in the opcode. Can also be expressed
180 n As N, but PC-relative (to the start of the instruction).
181 o [-128..127] word offset in bits <7:1> and <0>. Used by 8-bit
183 O [-128..127] offset in bits <7:0>. Also matches a comma and a
184 general register after the expression, in bits <15:12>. Used
185 only for the BDAP prefix insn (in v32 the ADDOQ insn; same opcode).
186 P Special register in bits <15:12>.
187 p Indicates that the insn is a prefix insn. Must be first
189 Q As O, but don't relax; force an 8-bit offset.
190 R General register in bits <15:12>.
191 r General register in bits <3:0>.
192 S Source operand in bit <10> and a prefix; a 3-operand prefix
194 s Source operand in bits <10> and <3:0>, optionally with a
195 side-effect prefix, except [pc] (the name, not R15 as in ACR)
196 isn't allowed for v32 and higher.
197 T Support register in bits <15:12>.
198 u 4-bit (PC-relative) unsigned immediate word offset in bits <3:0>.
199 U Relaxes to either u or n, instruction is assumed LAPCQ or LAPC.
200 Not recognized at disassembly.
201 x Register-dot-modifier, for example "r5.w" in bits <15:12> and <5:4>.
202 y Like 's' but do not allow an integer at assembly.
203 Y The difference s-y; only an integer is allowed.
204 z Size modifier (B or W) in bit <4>. */
207 /* Please note the order of the opcodes in this table is significant.
208 The assembler requires that all instances of the same mnemonic must
209 be consecutive. If they aren't, the assembler might not recognize
210 them, or may indicate an internal error.
212 The disassembler should not normally care about the order of the
213 opcodes, but will prefer an earlier alternative if the "match-score"
214 (see cris-dis.c) is computed as equal.
216 It should not be significant for proper execution that this table is
217 in alphabetical order, but please follow that convention for an easy
220 const struct cris_opcode
223 {"abs", 0x06B0, 0x0940, "r,R", 0, SIZE_NONE
, 0,
226 {"add", 0x0600, 0x09c0, "m r,R", 0, SIZE_NONE
, 0,
227 cris_reg_mode_add_sub_cmp_and_or_move_op
},
229 {"add", 0x0A00, 0x01c0, "m s,R", 0, SIZE_FIELD
, 0,
230 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
232 {"add", 0x0A00, 0x01c0, "m S,D", 0, SIZE_NONE
,
234 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
236 {"add", 0x0a00, 0x05c0, "m S,R,r", 0, SIZE_NONE
,
238 cris_three_operand_add_sub_cmp_and_or_op
},
240 {"add", 0x0A00, 0x01c0, "m s,R", 0, SIZE_FIELD
,
242 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
244 {"addc", 0x0570, 0x0A80, "r,R", 0, SIZE_FIX_32
,
246 cris_not_implemented_op
},
248 {"addc", 0x09A0, 0x0250, "s,R", 0, SIZE_FIX_32
,
250 cris_not_implemented_op
},
252 {"addi", 0x0540, 0x0A80, "x,r,A", 0, SIZE_NONE
,
256 {"addi", 0x0500, 0x0Ac0, "x,r", 0, SIZE_NONE
, 0,
259 /* This collates after "addo", but we want to disassemble as "addoq",
261 {"addoq", 0x0100, 0x0E00, "Q,A", 0, SIZE_NONE
,
263 cris_not_implemented_op
},
265 {"addo", 0x0940, 0x0280, "m s,R,A", 0, SIZE_FIELD_SIGNED
,
267 cris_not_implemented_op
},
269 /* This must be located after the insn above, lest we misinterpret
270 "addo.b -1,r0,acr" as "addo .b-1,r0,acr". FIXME: Sounds like a
272 {"addo", 0x0100, 0x0E00, "O,A", 0, SIZE_NONE
,
274 cris_not_implemented_op
},
276 {"addq", 0x0200, 0x0Dc0, "I,R", 0, SIZE_NONE
, 0,
277 cris_quick_mode_add_sub_op
},
279 {"adds", 0x0420, 0x0Bc0, "z r,R", 0, SIZE_NONE
, 0,
280 cris_reg_mode_add_sub_cmp_and_or_move_op
},
282 /* FIXME: SIZE_FIELD_SIGNED and all necessary changes. */
283 {"adds", 0x0820, 0x03c0, "z s,R", 0, SIZE_FIELD
, 0,
284 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
286 {"adds", 0x0820, 0x03c0, "z S,D", 0, SIZE_NONE
,
288 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
290 {"adds", 0x0820, 0x07c0, "z S,R,r", 0, SIZE_NONE
,
292 cris_three_operand_add_sub_cmp_and_or_op
},
294 {"addu", 0x0400, 0x0be0, "z r,R", 0, SIZE_NONE
, 0,
295 cris_reg_mode_add_sub_cmp_and_or_move_op
},
297 /* FIXME: SIZE_FIELD_UNSIGNED and all necessary changes. */
298 {"addu", 0x0800, 0x03e0, "z s,R", 0, SIZE_FIELD
, 0,
299 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
301 {"addu", 0x0800, 0x03e0, "z S,D", 0, SIZE_NONE
,
303 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
305 {"addu", 0x0800, 0x07e0, "z S,R,r", 0, SIZE_NONE
,
307 cris_three_operand_add_sub_cmp_and_or_op
},
309 {"and", 0x0700, 0x08C0, "m r,R", 0, SIZE_NONE
, 0,
310 cris_reg_mode_add_sub_cmp_and_or_move_op
},
312 {"and", 0x0B00, 0x00C0, "m s,R", 0, SIZE_FIELD
, 0,
313 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
315 {"and", 0x0B00, 0x00C0, "m S,D", 0, SIZE_NONE
,
317 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
319 {"and", 0x0B00, 0x04C0, "m S,R,r", 0, SIZE_NONE
,
321 cris_three_operand_add_sub_cmp_and_or_op
},
323 {"andq", 0x0300, 0x0CC0, "i,R", 0, SIZE_NONE
, 0,
324 cris_quick_mode_and_cmp_move_or_op
},
326 {"asr", 0x0780, 0x0840, "m r,R", 0, SIZE_NONE
, 0,
329 {"asrq", 0x03a0, 0x0c40, "c,R", 0, SIZE_NONE
, 0,
332 {"ax", 0x15B0, 0xEA4F, "", 0, SIZE_NONE
, 0,
335 /* FIXME: Should use branch #defines. */
336 {"b", 0x0dff, 0x0200, "b", 1, SIZE_NONE
, 0,
337 cris_sixteen_bit_offset_branch_op
},
341 0x0F00+(0xF-CC_A
)*0x1000, "o", 1, SIZE_NONE
, 0,
342 cris_eight_bit_offset_branch_op
},
344 /* Needs to come after the usual "ba o", which might be relaxed to
346 {"ba", BA_DWORD_OPCODE
,
347 0xffff & (~BA_DWORD_OPCODE
), "n", 0, SIZE_FIX_32
,
349 cris_none_reg_mode_jump_op
},
351 {"bas", 0x0EBF, 0x0140, "n,P", 0, SIZE_FIX_32
,
353 cris_none_reg_mode_jump_op
},
355 {"basc", 0x0EFF, 0x0100, "n,P", 0, SIZE_FIX_32
,
357 cris_none_reg_mode_jump_op
},
360 BRANCH_QUICK_OPCODE
+CC_CC
*0x1000,
361 0x0f00+(0xF-CC_CC
)*0x1000, "o", 1, SIZE_NONE
, 0,
362 cris_eight_bit_offset_branch_op
},
365 BRANCH_QUICK_OPCODE
+CC_CS
*0x1000,
366 0x0f00+(0xF-CC_CS
)*0x1000, "o", 1, SIZE_NONE
, 0,
367 cris_eight_bit_offset_branch_op
},
370 BDAP_INDIR_OPCODE
, BDAP_INDIR_Z_BITS
, "pm s,R", 0, SIZE_FIELD_SIGNED
,
375 BDAP_QUICK_OPCODE
, BDAP_QUICK_Z_BITS
, "pO", 0, SIZE_NONE
,
377 cris_quick_mode_bdap_prefix
},
380 BRANCH_QUICK_OPCODE
+CC_EQ
*0x1000,
381 0x0f00+(0xF-CC_EQ
)*0x1000, "o", 1, SIZE_NONE
, 0,
382 cris_eight_bit_offset_branch_op
},
384 /* This is deliberately put before "bext" to trump it, even though not
385 in alphabetical order, since we don't do excluding version checks
388 BRANCH_QUICK_OPCODE
+CC_EXT
*0x1000,
389 0x0f00+(0xF-CC_EXT
)*0x1000, "o", 1, SIZE_NONE
,
391 cris_eight_bit_offset_branch_op
},
394 BRANCH_QUICK_OPCODE
+CC_EXT
*0x1000,
395 0x0f00+(0xF-CC_EXT
)*0x1000, "o", 1, SIZE_NONE
,
397 cris_eight_bit_offset_branch_op
},
400 BRANCH_QUICK_OPCODE
+CC_GE
*0x1000,
401 0x0f00+(0xF-CC_GE
)*0x1000, "o", 1, SIZE_NONE
, 0,
402 cris_eight_bit_offset_branch_op
},
405 BRANCH_QUICK_OPCODE
+CC_GT
*0x1000,
406 0x0f00+(0xF-CC_GT
)*0x1000, "o", 1, SIZE_NONE
, 0,
407 cris_eight_bit_offset_branch_op
},
410 BRANCH_QUICK_OPCODE
+CC_HI
*0x1000,
411 0x0f00+(0xF-CC_HI
)*0x1000, "o", 1, SIZE_NONE
, 0,
412 cris_eight_bit_offset_branch_op
},
415 BRANCH_QUICK_OPCODE
+CC_HS
*0x1000,
416 0x0f00+(0xF-CC_HS
)*0x1000, "o", 1, SIZE_NONE
, 0,
417 cris_eight_bit_offset_branch_op
},
419 {"biap", BIAP_OPCODE
, BIAP_Z_BITS
, "pm r,R", 0, SIZE_NONE
,
424 BRANCH_QUICK_OPCODE
+CC_LE
*0x1000,
425 0x0f00+(0xF-CC_LE
)*0x1000, "o", 1, SIZE_NONE
, 0,
426 cris_eight_bit_offset_branch_op
},
429 BRANCH_QUICK_OPCODE
+CC_LO
*0x1000,
430 0x0f00+(0xF-CC_LO
)*0x1000, "o", 1, SIZE_NONE
, 0,
431 cris_eight_bit_offset_branch_op
},
434 BRANCH_QUICK_OPCODE
+CC_LS
*0x1000,
435 0x0f00+(0xF-CC_LS
)*0x1000, "o", 1, SIZE_NONE
, 0,
436 cris_eight_bit_offset_branch_op
},
439 BRANCH_QUICK_OPCODE
+CC_LT
*0x1000,
440 0x0f00+(0xF-CC_LT
)*0x1000, "o", 1, SIZE_NONE
, 0,
441 cris_eight_bit_offset_branch_op
},
444 BRANCH_QUICK_OPCODE
+CC_MI
*0x1000,
445 0x0f00+(0xF-CC_MI
)*0x1000, "o", 1, SIZE_NONE
, 0,
446 cris_eight_bit_offset_branch_op
},
448 {"bmod", 0x0ab0, 0x0140, "s,R", 0, SIZE_FIX_32
,
450 cris_not_implemented_op
},
452 {"bmod", 0x0ab0, 0x0140, "S,D", 0, SIZE_NONE
,
454 cris_not_implemented_op
},
456 {"bmod", 0x0ab0, 0x0540, "S,R,r", 0, SIZE_NONE
,
458 cris_not_implemented_op
},
461 BRANCH_QUICK_OPCODE
+CC_NE
*0x1000,
462 0x0f00+(0xF-CC_NE
)*0x1000, "o", 1, SIZE_NONE
, 0,
463 cris_eight_bit_offset_branch_op
},
465 {"bound", 0x05c0, 0x0A00, "m r,R", 0, SIZE_NONE
, 0,
466 cris_two_operand_bound_op
},
467 /* FIXME: SIZE_FIELD_UNSIGNED and all necessary changes. */
468 {"bound", 0x09c0, 0x0200, "m s,R", 0, SIZE_FIELD
,
470 cris_two_operand_bound_op
},
471 /* FIXME: SIZE_FIELD_UNSIGNED and all necessary changes. */
472 {"bound", 0x0dcf, 0x0200, "m Y,R", 0, SIZE_FIELD
, 0,
473 cris_two_operand_bound_op
},
474 {"bound", 0x09c0, 0x0200, "m S,D", 0, SIZE_NONE
,
476 cris_two_operand_bound_op
},
477 {"bound", 0x09c0, 0x0600, "m S,R,r", 0, SIZE_NONE
,
479 cris_three_operand_bound_op
},
482 BRANCH_QUICK_OPCODE
+CC_PL
*0x1000,
483 0x0f00+(0xF-CC_PL
)*0x1000, "o", 1, SIZE_NONE
, 0,
484 cris_eight_bit_offset_branch_op
},
486 {"break", 0xe930, 0x16c0, "C", 0, SIZE_NONE
,
491 BRANCH_QUICK_OPCODE
+CC_EXT
*0x1000,
492 0x0f00+(0xF-CC_EXT
)*0x1000, "o", 1, SIZE_NONE
,
494 cris_eight_bit_offset_branch_op
},
496 {"bsr", 0xBEBF, 0x4140, "n", 0, SIZE_FIX_32
,
498 cris_none_reg_mode_jump_op
},
500 {"bsrc", 0xBEFF, 0x4100, "n", 0, SIZE_FIX_32
,
502 cris_none_reg_mode_jump_op
},
504 {"bstore", 0x0af0, 0x0100, "s,R", 0, SIZE_FIX_32
,
506 cris_not_implemented_op
},
508 {"bstore", 0x0af0, 0x0100, "S,D", 0, SIZE_NONE
,
510 cris_not_implemented_op
},
512 {"bstore", 0x0af0, 0x0500, "S,R,r", 0, SIZE_NONE
,
514 cris_not_implemented_op
},
516 {"btst", 0x04F0, 0x0B00, "r,R", 0, SIZE_NONE
, 0,
518 {"btstq", 0x0380, 0x0C60, "c,R", 0, SIZE_NONE
, 0,
522 BRANCH_QUICK_OPCODE
+CC_VC
*0x1000,
523 0x0f00+(0xF-CC_VC
)*0x1000, "o", 1, SIZE_NONE
, 0,
524 cris_eight_bit_offset_branch_op
},
527 BRANCH_QUICK_OPCODE
+CC_VS
*0x1000,
528 0x0f00+(0xF-CC_VS
)*0x1000, "o", 1, SIZE_NONE
, 0,
529 cris_eight_bit_offset_branch_op
},
531 {"clear", 0x0670, 0x3980, "M r", 0, SIZE_NONE
, 0,
532 cris_reg_mode_clear_op
},
534 {"clear", 0x0A70, 0x3180, "M y", 0, SIZE_NONE
, 0,
535 cris_none_reg_mode_clear_test_op
},
537 {"clear", 0x0A70, 0x3180, "M S", 0, SIZE_NONE
,
539 cris_none_reg_mode_clear_test_op
},
541 {"clearf", 0x05F0, 0x0A00, "f", 0, SIZE_NONE
, 0,
544 {"cmp", 0x06C0, 0x0900, "m r,R", 0, SIZE_NONE
, 0,
545 cris_reg_mode_add_sub_cmp_and_or_move_op
},
547 {"cmp", 0x0Ac0, 0x0100, "m s,R", 0, SIZE_FIELD
, 0,
548 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
550 {"cmp", 0x0Ac0, 0x0100, "m S,D", 0, SIZE_NONE
,
552 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
554 {"cmpq", 0x02C0, 0x0D00, "i,R", 0, SIZE_NONE
, 0,
555 cris_quick_mode_and_cmp_move_or_op
},
557 /* FIXME: SIZE_FIELD_SIGNED and all necessary changes. */
558 {"cmps", 0x08e0, 0x0300, "z s,R", 0, SIZE_FIELD
, 0,
559 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
561 {"cmps", 0x08e0, 0x0300, "z S,D", 0, SIZE_NONE
,
563 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
565 /* FIXME: SIZE_FIELD_UNSIGNED and all necessary changes. */
566 {"cmpu", 0x08c0, 0x0320, "z s,R" , 0, SIZE_FIELD
, 0,
567 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
569 {"cmpu", 0x08c0, 0x0320, "z S,D", 0, SIZE_NONE
,
571 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
573 {"di", 0x25F0, 0xDA0F, "", 0, SIZE_NONE
, 0,
576 {"dip", DIP_OPCODE
, DIP_Z_BITS
, "ps", 0, SIZE_FIX_32
,
580 {"div", 0x0980, 0x0640, "m R,r", 0, SIZE_FIELD
, 0,
581 cris_not_implemented_op
},
583 {"dstep", 0x06f0, 0x0900, "r,R", 0, SIZE_NONE
, 0,
584 cris_dstep_logshift_mstep_neg_not_op
},
586 {"ei", 0x25B0, 0xDA4F, "", 0, SIZE_NONE
, 0,
589 {"fidxd", 0x0ab0, 0xf540, "[r]", 0, SIZE_NONE
,
591 cris_not_implemented_op
},
593 {"fidxi", 0x0d30, 0xF2C0, "[r]", 0, SIZE_NONE
,
595 cris_not_implemented_op
},
597 {"ftagd", 0x1AB0, 0xE540, "[r]", 0, SIZE_NONE
,
599 cris_not_implemented_op
},
601 {"ftagi", 0x1D30, 0xE2C0, "[r]", 0, SIZE_NONE
,
603 cris_not_implemented_op
},
605 {"halt", 0xF930, 0x06CF, "", 0, SIZE_NONE
,
607 cris_not_implemented_op
},
609 {"jas", 0x09B0, 0x0640, "r,P", 0, SIZE_NONE
,
611 cris_reg_mode_jump_op
},
613 {"jas", 0x0DBF, 0x0240, "N,P", 0, SIZE_FIX_32
,
615 cris_reg_mode_jump_op
},
617 {"jasc", 0x0B30, 0x04C0, "r,P", 0, SIZE_NONE
,
619 cris_reg_mode_jump_op
},
621 {"jasc", 0x0F3F, 0x00C0, "N,P", 0, SIZE_FIX_32
,
623 cris_reg_mode_jump_op
},
625 {"jbrc", 0x69b0, 0x9640, "r", 0, SIZE_NONE
,
627 cris_reg_mode_jump_op
},
629 {"jbrc", 0x6930, 0x92c0, "s", 0, SIZE_FIX_32
,
631 cris_none_reg_mode_jump_op
},
633 {"jbrc", 0x6930, 0x92c0, "S", 0, SIZE_NONE
,
635 cris_none_reg_mode_jump_op
},
637 {"jir", 0xA9b0, 0x5640, "r", 0, SIZE_NONE
,
639 cris_reg_mode_jump_op
},
641 {"jir", 0xA930, 0x52c0, "s", 0, SIZE_FIX_32
,
643 cris_none_reg_mode_jump_op
},
645 {"jir", 0xA930, 0x52c0, "S", 0, SIZE_NONE
,
647 cris_none_reg_mode_jump_op
},
649 {"jirc", 0x29b0, 0xd640, "r", 0, SIZE_NONE
,
651 cris_reg_mode_jump_op
},
653 {"jirc", 0x2930, 0xd2c0, "s", 0, SIZE_FIX_32
,
655 cris_none_reg_mode_jump_op
},
657 {"jirc", 0x2930, 0xd2c0, "S", 0, SIZE_NONE
,
659 cris_none_reg_mode_jump_op
},
661 {"jsr", 0xB9b0, 0x4640, "r", 0, SIZE_NONE
, 0,
662 cris_reg_mode_jump_op
},
664 {"jsr", 0xB930, 0x42c0, "s", 0, SIZE_FIX_32
,
666 cris_none_reg_mode_jump_op
},
668 {"jsr", 0xBDBF, 0x4240, "N", 0, SIZE_FIX_32
,
670 cris_none_reg_mode_jump_op
},
672 {"jsr", 0xB930, 0x42c0, "S", 0, SIZE_NONE
,
674 cris_none_reg_mode_jump_op
},
676 {"jsrc", 0x39b0, 0xc640, "r", 0, SIZE_NONE
,
678 cris_reg_mode_jump_op
},
680 {"jsrc", 0x3930, 0xc2c0, "s", 0, SIZE_FIX_32
,
682 cris_none_reg_mode_jump_op
},
684 {"jsrc", 0x3930, 0xc2c0, "S", 0, SIZE_NONE
,
686 cris_none_reg_mode_jump_op
},
688 {"jsrc", 0xBB30, 0x44C0, "r", 0, SIZE_NONE
,
690 cris_reg_mode_jump_op
},
692 {"jsrc", 0xBF3F, 0x40C0, "N", 0, SIZE_FIX_32
,
694 cris_reg_mode_jump_op
},
696 {"jump", 0x09b0, 0xF640, "r", 0, SIZE_NONE
, 0,
697 cris_reg_mode_jump_op
},
700 JUMP_INDIR_OPCODE
, JUMP_INDIR_Z_BITS
, "s", 0, SIZE_FIX_32
,
702 cris_none_reg_mode_jump_op
},
705 JUMP_INDIR_OPCODE
, JUMP_INDIR_Z_BITS
, "S", 0, SIZE_NONE
,
707 cris_none_reg_mode_jump_op
},
709 {"jump", 0x09F0, 0x060F, "P", 0, SIZE_NONE
,
711 cris_none_reg_mode_jump_op
},
714 JUMP_PC_INCR_OPCODE_V32
,
715 (0xffff & ~JUMP_PC_INCR_OPCODE_V32
), "N", 0, SIZE_FIX_32
,
717 cris_none_reg_mode_jump_op
},
719 {"jmpu", 0x8930, 0x72c0, "s", 0, SIZE_FIX_32
,
721 cris_none_reg_mode_jump_op
},
723 {"jmpu", 0x8930, 0x72c0, "S", 0, SIZE_NONE
,
725 cris_none_reg_mode_jump_op
},
727 {"lapc", 0x0970, 0x0680, "U,R", 0, SIZE_NONE
,
729 cris_not_implemented_op
},
731 {"lapc", 0x0D7F, 0x0280, "dn,R", 0, SIZE_FIX_32
,
733 cris_not_implemented_op
},
735 {"lapcq", 0x0970, 0x0680, "u,R", 0, SIZE_NONE
,
739 {"lsl", 0x04C0, 0x0B00, "m r,R", 0, SIZE_NONE
, 0,
740 cris_dstep_logshift_mstep_neg_not_op
},
742 {"lslq", 0x03c0, 0x0C20, "c,R", 0, SIZE_NONE
, 0,
743 cris_dstep_logshift_mstep_neg_not_op
},
745 {"lsr", 0x07C0, 0x0800, "m r,R", 0, SIZE_NONE
, 0,
746 cris_dstep_logshift_mstep_neg_not_op
},
748 {"lsrq", 0x03e0, 0x0C00, "c,R", 0, SIZE_NONE
, 0,
749 cris_dstep_logshift_mstep_neg_not_op
},
751 {"lz", 0x0730, 0x08C0, "r,R", 0, SIZE_NONE
,
753 cris_not_implemented_op
},
755 {"mcp", 0x07f0, 0x0800, "P,r", 0, SIZE_NONE
,
757 cris_not_implemented_op
},
759 {"move", 0x0640, 0x0980, "m r,R", 0, SIZE_NONE
, 0,
760 cris_reg_mode_add_sub_cmp_and_or_move_op
},
762 {"move", 0x0A40, 0x0180, "m s,R", 0, SIZE_FIELD
, 0,
763 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
765 {"move", 0x0A40, 0x0180, "m S,D", 0, SIZE_NONE
,
767 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
769 {"move", 0x0630, 0x09c0, "r,P", 0, SIZE_NONE
, 0,
770 cris_move_to_preg_op
},
772 {"move", 0x0670, 0x0980, "P,r", 0, SIZE_NONE
, 0,
773 cris_reg_mode_move_from_preg_op
},
775 {"move", 0x0BC0, 0x0000, "m R,y", 0, SIZE_FIELD
, 0,
776 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
778 {"move", 0x0BC0, 0x0000, "m D,S", 0, SIZE_NONE
,
780 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
783 MOVE_M_TO_PREG_OPCODE
, MOVE_M_TO_PREG_ZBITS
,
784 "s,P", 0, SIZE_SPEC_REG
, 0,
785 cris_move_to_preg_op
},
787 {"move", 0x0A30, 0x01c0, "S,P", 0, SIZE_NONE
,
789 cris_move_to_preg_op
},
791 {"move", 0x0A70, 0x0180, "P,y", 0, SIZE_SPEC_REG
, 0,
792 cris_none_reg_mode_move_from_preg_op
},
794 {"move", 0x0A70, 0x0180, "P,S", 0, SIZE_NONE
,
796 cris_none_reg_mode_move_from_preg_op
},
798 {"move", 0x0B70, 0x0480, "r,T", 0, SIZE_NONE
,
800 cris_not_implemented_op
},
802 {"move", 0x0F70, 0x0080, "T,r", 0, SIZE_NONE
,
804 cris_not_implemented_op
},
806 {"movem", 0x0BF0, 0x0000, "R,y", 0, SIZE_FIX_32
, 0,
807 cris_move_reg_to_mem_movem_op
},
809 {"movem", 0x0BF0, 0x0000, "D,S", 0, SIZE_NONE
,
811 cris_move_reg_to_mem_movem_op
},
813 {"movem", 0x0BB0, 0x0040, "s,R", 0, SIZE_FIX_32
, 0,
814 cris_move_mem_to_reg_movem_op
},
816 {"movem", 0x0BB0, 0x0040, "S,D", 0, SIZE_NONE
,
818 cris_move_mem_to_reg_movem_op
},
820 {"moveq", 0x0240, 0x0D80, "i,R", 0, SIZE_NONE
, 0,
821 cris_quick_mode_and_cmp_move_or_op
},
823 {"movs", 0x0460, 0x0B80, "z r,R", 0, SIZE_NONE
, 0,
824 cris_reg_mode_add_sub_cmp_and_or_move_op
},
826 /* FIXME: SIZE_FIELD_SIGNED and all necessary changes. */
827 {"movs", 0x0860, 0x0380, "z s,R", 0, SIZE_FIELD
, 0,
828 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
830 {"movs", 0x0860, 0x0380, "z S,D", 0, SIZE_NONE
,
832 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
834 {"movu", 0x0440, 0x0Ba0, "z r,R", 0, SIZE_NONE
, 0,
835 cris_reg_mode_add_sub_cmp_and_or_move_op
},
837 /* FIXME: SIZE_FIELD_UNSIGNED and all necessary changes. */
838 {"movu", 0x0840, 0x03a0, "z s,R", 0, SIZE_FIELD
, 0,
839 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
841 {"movu", 0x0840, 0x03a0, "z S,D", 0, SIZE_NONE
,
843 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
845 {"mstep", 0x07f0, 0x0800, "r,R", 0, SIZE_NONE
,
847 cris_dstep_logshift_mstep_neg_not_op
},
849 {"muls", 0x0d00, 0x02c0, "m r,R", 0, SIZE_NONE
,
853 {"mulu", 0x0900, 0x06c0, "m r,R", 0, SIZE_NONE
,
857 {"neg", 0x0580, 0x0A40, "m r,R", 0, SIZE_NONE
, 0,
858 cris_dstep_logshift_mstep_neg_not_op
},
860 {"nop", NOP_OPCODE
, NOP_Z_BITS
, "", 0, SIZE_NONE
,
864 {"nop", NOP_OPCODE_V32
, NOP_Z_BITS_V32
, "", 0, SIZE_NONE
,
868 {"not", 0x8770, 0x7880, "r", 0, SIZE_NONE
, 0,
869 cris_dstep_logshift_mstep_neg_not_op
},
871 {"or", 0x0740, 0x0880, "m r,R", 0, SIZE_NONE
, 0,
872 cris_reg_mode_add_sub_cmp_and_or_move_op
},
874 {"or", 0x0B40, 0x0080, "m s,R", 0, SIZE_FIELD
, 0,
875 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
877 {"or", 0x0B40, 0x0080, "m S,D", 0, SIZE_NONE
,
879 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
881 {"or", 0x0B40, 0x0480, "m S,R,r", 0, SIZE_NONE
,
883 cris_three_operand_add_sub_cmp_and_or_op
},
885 {"orq", 0x0340, 0x0C80, "i,R", 0, SIZE_NONE
, 0,
886 cris_quick_mode_and_cmp_move_or_op
},
888 {"pop", 0x0E6E, 0x0191, "!R", 0, SIZE_NONE
,
890 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
892 {"pop", 0x0e3e, 0x01c1, "!P", 0, SIZE_NONE
,
894 cris_none_reg_mode_move_from_preg_op
},
896 {"push", 0x0FEE, 0x0011, "BR", 0, SIZE_NONE
,
898 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
900 {"push", 0x0E7E, 0x0181, "BP", 0, SIZE_NONE
,
902 cris_move_to_preg_op
},
904 {"rbf", 0x3b30, 0xc0c0, "y", 0, SIZE_NONE
,
906 cris_not_implemented_op
},
908 {"rbf", 0x3b30, 0xc0c0, "S", 0, SIZE_NONE
,
910 cris_not_implemented_op
},
912 {"rfe", 0x2930, 0xD6CF, "", 0, SIZE_NONE
,
914 cris_not_implemented_op
},
916 {"rfg", 0x4930, 0xB6CF, "", 0, SIZE_NONE
,
918 cris_not_implemented_op
},
920 {"rfn", 0x5930, 0xA6CF, "", 0, SIZE_NONE
,
922 cris_not_implemented_op
},
924 {"ret", 0xB67F, 0x4980, "", 1, SIZE_NONE
,
926 cris_reg_mode_move_from_preg_op
},
928 {"ret", 0xB9F0, 0x460F, "", 1, SIZE_NONE
,
930 cris_reg_mode_move_from_preg_op
},
932 {"retb", 0xe67f, 0x1980, "", 1, SIZE_NONE
,
934 cris_reg_mode_move_from_preg_op
},
936 {"rete", 0xA9F0, 0x560F, "", 1, SIZE_NONE
,
938 cris_reg_mode_move_from_preg_op
},
940 {"reti", 0xA67F, 0x5980, "", 1, SIZE_NONE
,
942 cris_reg_mode_move_from_preg_op
},
944 {"retn", 0xC9F0, 0x360F, "", 1, SIZE_NONE
,
946 cris_reg_mode_move_from_preg_op
},
948 {"sbfs", 0x3b70, 0xc080, "y", 0, SIZE_NONE
,
950 cris_not_implemented_op
},
952 {"sbfs", 0x3b70, 0xc080, "S", 0, SIZE_NONE
,
954 cris_not_implemented_op
},
958 0x0AC0+(0xf-CC_A
)*0x1000, "r", 0, SIZE_NONE
, 0,
962 0x0530+CC_EXT
*0x1000,
963 0x0AC0+(0xf-CC_EXT
)*0x1000, "r", 0, SIZE_NONE
,
969 0x0AC0+(0xf-CC_CC
)*0x1000, "r", 0, SIZE_NONE
, 0,
974 0x0AC0+(0xf-CC_CS
)*0x1000, "r", 0, SIZE_NONE
, 0,
979 0x0AC0+(0xf-CC_EQ
)*0x1000, "r", 0, SIZE_NONE
, 0,
982 {"setf", 0x05b0, 0x0A40, "f", 0, SIZE_NONE
, 0,
985 {"sfe", 0x3930, 0xC6CF, "", 0, SIZE_NONE
,
987 cris_not_implemented_op
},
989 /* Need to have "swf" in front of "sext" so it is the one displayed in
992 0x0530+CC_EXT
*0x1000,
993 0x0AC0+(0xf-CC_EXT
)*0x1000, "r", 0, SIZE_NONE
,
998 0x0530+CC_EXT
*0x1000,
999 0x0AC0+(0xf-CC_EXT
)*0x1000, "r", 0, SIZE_NONE
,
1004 0x0530+CC_GE
*0x1000,
1005 0x0AC0+(0xf-CC_GE
)*0x1000, "r", 0, SIZE_NONE
, 0,
1009 0x0530+CC_GT
*0x1000,
1010 0x0AC0+(0xf-CC_GT
)*0x1000, "r", 0, SIZE_NONE
, 0,
1014 0x0530+CC_HI
*0x1000,
1015 0x0AC0+(0xf-CC_HI
)*0x1000, "r", 0, SIZE_NONE
, 0,
1019 0x0530+CC_HS
*0x1000,
1020 0x0AC0+(0xf-CC_HS
)*0x1000, "r", 0, SIZE_NONE
, 0,
1024 0x0530+CC_LE
*0x1000,
1025 0x0AC0+(0xf-CC_LE
)*0x1000, "r", 0, SIZE_NONE
, 0,
1029 0x0530+CC_LO
*0x1000,
1030 0x0AC0+(0xf-CC_LO
)*0x1000, "r", 0, SIZE_NONE
, 0,
1034 0x0530+CC_LS
*0x1000,
1035 0x0AC0+(0xf-CC_LS
)*0x1000, "r", 0, SIZE_NONE
, 0,
1039 0x0530+CC_LT
*0x1000,
1040 0x0AC0+(0xf-CC_LT
)*0x1000, "r", 0, SIZE_NONE
, 0,
1044 0x0530+CC_MI
*0x1000,
1045 0x0AC0+(0xf-CC_MI
)*0x1000, "r", 0, SIZE_NONE
, 0,
1049 0x0530+CC_NE
*0x1000,
1050 0x0AC0+(0xf-CC_NE
)*0x1000, "r", 0, SIZE_NONE
, 0,
1054 0x0530+CC_PL
*0x1000,
1055 0x0AC0+(0xf-CC_PL
)*0x1000, "r", 0, SIZE_NONE
, 0,
1058 {"sub", 0x0680, 0x0940, "m r,R", 0, SIZE_NONE
, 0,
1059 cris_reg_mode_add_sub_cmp_and_or_move_op
},
1061 {"sub", 0x0a80, 0x0140, "m s,R", 0, SIZE_FIELD
, 0,
1062 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
1064 {"sub", 0x0a80, 0x0140, "m S,D", 0, SIZE_NONE
,
1066 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
1068 {"sub", 0x0a80, 0x0540, "m S,R,r", 0, SIZE_NONE
,
1070 cris_three_operand_add_sub_cmp_and_or_op
},
1072 {"subq", 0x0280, 0x0d40, "I,R", 0, SIZE_NONE
, 0,
1073 cris_quick_mode_add_sub_op
},
1075 {"subs", 0x04a0, 0x0b40, "z r,R", 0, SIZE_NONE
, 0,
1076 cris_reg_mode_add_sub_cmp_and_or_move_op
},
1078 /* FIXME: SIZE_FIELD_SIGNED and all necessary changes. */
1079 {"subs", 0x08a0, 0x0340, "z s,R", 0, SIZE_FIELD
, 0,
1080 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
1082 {"subs", 0x08a0, 0x0340, "z S,D", 0, SIZE_NONE
,
1084 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
1086 {"subs", 0x08a0, 0x0740, "z S,R,r", 0, SIZE_NONE
,
1088 cris_three_operand_add_sub_cmp_and_or_op
},
1090 {"subu", 0x0480, 0x0b60, "z r,R", 0, SIZE_NONE
, 0,
1091 cris_reg_mode_add_sub_cmp_and_or_move_op
},
1093 /* FIXME: SIZE_FIELD_UNSIGNED and all necessary changes. */
1094 {"subu", 0x0880, 0x0360, "z s,R", 0, SIZE_FIELD
, 0,
1095 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
1097 {"subu", 0x0880, 0x0360, "z S,D", 0, SIZE_NONE
,
1099 cris_none_reg_mode_add_sub_cmp_and_or_move_op
},
1101 {"subu", 0x0880, 0x0760, "z S,R,r", 0, SIZE_NONE
,
1103 cris_three_operand_add_sub_cmp_and_or_op
},
1106 0x0530+CC_VC
*0x1000,
1107 0x0AC0+(0xf-CC_VC
)*0x1000, "r", 0, SIZE_NONE
, 0,
1111 0x0530+CC_VS
*0x1000,
1112 0x0AC0+(0xf-CC_VS
)*0x1000, "r", 0, SIZE_NONE
, 0,
1115 /* The insn "swapn" is the same as "not" and will be disassembled as
1116 such, but the swap* family of mnmonics are generally v8-and-higher
1117 only, so count it in. */
1118 {"swapn", 0x8770, 0x7880, "r", 0, SIZE_NONE
,
1120 cris_not_implemented_op
},
1122 {"swapw", 0x4770, 0xb880, "r", 0, SIZE_NONE
,
1124 cris_not_implemented_op
},
1126 {"swapnw", 0xc770, 0x3880, "r", 0, SIZE_NONE
,
1128 cris_not_implemented_op
},
1130 {"swapb", 0x2770, 0xd880, "r", 0, SIZE_NONE
,
1132 cris_not_implemented_op
},
1134 {"swapnb", 0xA770, 0x5880, "r", 0, SIZE_NONE
,
1136 cris_not_implemented_op
},
1138 {"swapwb", 0x6770, 0x9880, "r", 0, SIZE_NONE
,
1140 cris_not_implemented_op
},
1142 {"swapnwb", 0xE770, 0x1880, "r", 0, SIZE_NONE
,
1144 cris_not_implemented_op
},
1146 {"swapr", 0x1770, 0xe880, "r", 0, SIZE_NONE
,
1148 cris_not_implemented_op
},
1150 {"swapnr", 0x9770, 0x6880, "r", 0, SIZE_NONE
,
1152 cris_not_implemented_op
},
1154 {"swapwr", 0x5770, 0xa880, "r", 0, SIZE_NONE
,
1156 cris_not_implemented_op
},
1158 {"swapnwr", 0xd770, 0x2880, "r", 0, SIZE_NONE
,
1160 cris_not_implemented_op
},
1162 {"swapbr", 0x3770, 0xc880, "r", 0, SIZE_NONE
,
1164 cris_not_implemented_op
},
1166 {"swapnbr", 0xb770, 0x4880, "r", 0, SIZE_NONE
,
1168 cris_not_implemented_op
},
1170 {"swapwbr", 0x7770, 0x8880, "r", 0, SIZE_NONE
,
1172 cris_not_implemented_op
},
1174 {"swapnwbr", 0xf770, 0x0880, "r", 0, SIZE_NONE
,
1176 cris_not_implemented_op
},
1178 {"test", 0x0640, 0x0980, "m D", 0, SIZE_NONE
,
1180 cris_reg_mode_test_op
},
1182 {"test", 0x0b80, 0xf040, "m y", 0, SIZE_FIELD
, 0,
1183 cris_none_reg_mode_clear_test_op
},
1185 {"test", 0x0b80, 0xf040, "m S", 0, SIZE_NONE
,
1187 cris_none_reg_mode_clear_test_op
},
1189 {"xor", 0x07B0, 0x0840, "r,R", 0, SIZE_NONE
, 0,
1192 {NULL
, 0, 0, NULL
, 0, 0, 0, cris_not_implemented_op
}
1195 /* Condition-names, indexed by the CC_* numbers as found in cris.h. */
1214 /* This is a placeholder. In v0, this would be "ext". In v32, this
1215 is "sb". See cris_conds15. */
1219 /* Different names and semantics for condition 1111 (0xf). */
1220 const struct cris_cond15 cris_cond15s
[] =
1222 /* FIXME: In what version did condition "ext" disappear? */
1223 {"ext", cris_ver_v0_3
},
1224 {"wf", cris_ver_v10
},
1225 {"sb", cris_ver_v32p
},
1232 * eval: (c-set-style "gnu")
1233 * indent-tabs-mode: t
1238 /* No instruction will be disassembled longer than this. In theory, and
1239 in silicon, address prefixes can be cascaded. In practice, cascading
1240 is not used by GCC, and not supported by the assembler. */
1241 #ifndef MAX_BYTES_PER_CRIS_INSN
1242 #define MAX_BYTES_PER_CRIS_INSN 8
1245 /* Whether or not to decode prefixes, folding it into the following
1246 instruction. FIXME: Make this optional later. */
1247 #ifndef PARSE_PREFIX
1248 #define PARSE_PREFIX 1
1251 /* Sometimes we prefix all registers with this character. */
1252 #define REGISTER_PREFIX_CHAR '$'
1254 /* Whether or not to trace the following sequence:
1257 adds.w [pc+r%d.w],pc
1259 This is the assembly form of a switch-statement in C.
1260 The "sub is optional. If there is none, then X will be zero.
1261 X is the value of the first case,
1262 Y is the number of cases (including default).
1264 This results in case offsets printed on the form:
1265 case N: -> case_address
1266 where N is an estimation on the corresponding 'case' operand in C,
1267 and case_address is where execution of that case continues after the
1268 sequence presented above.
1270 The old style of output was to print the offsets as instructions,
1271 which made it hard to follow "case"-constructs in the disassembly,
1272 and caused a lot of annoying warnings about undefined instructions.
1274 FIXME: Make this optional later. */
1276 #define TRACE_CASE (disdata->trace_case)
1279 enum cris_disass_family
1280 { cris_dis_v0_v10
, cris_dis_common_v10_v32
, cris_dis_v32
};
1282 /* Stored in the disasm_info->private_data member. */
1283 struct cris_disasm_data
1285 /* Whether to print something less confusing if we find something
1286 matching a switch-construct. */
1287 bfd_boolean trace_case
;
1289 /* Whether this code is flagged as crisv32. FIXME: Should be an enum
1290 that includes "compatible". */
1291 enum cris_disass_family distype
;
1294 /* Value of first element in switch. */
1295 static long case_offset
= 0;
1297 /* How many more case-offsets to print. */
1298 static long case_offset_counter
= 0;
1300 /* Number of case offsets. */
1301 static long no_of_case_offsets
= 0;
1303 /* Candidate for next case_offset. */
1304 static long last_immediate
= 0;
1306 static int cris_constraint
1307 (const char *, unsigned, unsigned, struct cris_disasm_data
*);
1309 /* Parse disassembler options and store state in info. FIXME: For the
1310 time being, we abuse static variables. */
1313 cris_parse_disassembler_options (disassemble_info
*info
,
1314 enum cris_disass_family distype
)
1316 struct cris_disasm_data
*disdata
;
1318 info
->private_data
= calloc (1, sizeof (struct cris_disasm_data
));
1319 disdata
= (struct cris_disasm_data
*) info
->private_data
;
1320 if (disdata
== NULL
)
1325 = (info
->disassembler_options
== NULL
1326 || (strcmp (info
->disassembler_options
, "nocase") != 0));
1328 disdata
->distype
= distype
;
1332 static const struct cris_spec_reg
*
1333 spec_reg_info (unsigned int sreg
, enum cris_disass_family distype
)
1337 for (i
= 0; cris_spec_regs
[i
].name
!= NULL
; i
++)
1339 if (cris_spec_regs
[i
].number
== sreg
)
1341 if (distype
== cris_dis_v32
)
1342 switch (cris_spec_regs
[i
].applicable_version
)
1344 case cris_ver_warning
:
1345 case cris_ver_version_all
:
1350 /* No ambiguous sizes or register names with CRISv32. */
1351 if (cris_spec_regs
[i
].warning
== NULL
)
1352 return &cris_spec_regs
[i
];
1356 else if (cris_spec_regs
[i
].applicable_version
!= cris_ver_v32p
)
1357 return &cris_spec_regs
[i
];
1364 /* Return the number of bits in the argument. */
1367 number_of_bits (unsigned int val
)
1371 for (bits
= 0; val
!= 0; val
&= val
- 1)
1377 /* Get an entry in the opcode-table. */
1379 static const struct cris_opcode
*
1380 get_opcode_entry (unsigned int insn
,
1381 unsigned int prefix_insn
,
1382 struct cris_disasm_data
*disdata
)
1384 /* For non-prefixed insns, we keep a table of pointers, indexed by the
1385 insn code. Each entry is initialized when found to be NULL. */
1386 static const struct cris_opcode
**opc_table
= NULL
;
1388 const struct cris_opcode
*max_matchedp
= NULL
;
1389 const struct cris_opcode
**prefix_opc_table
= NULL
;
1391 /* We hold a table for each prefix that need to be handled differently. */
1392 static const struct cris_opcode
**dip_prefixes
= NULL
;
1393 static const struct cris_opcode
**bdapq_m1_prefixes
= NULL
;
1394 static const struct cris_opcode
**bdapq_m2_prefixes
= NULL
;
1395 static const struct cris_opcode
**bdapq_m4_prefixes
= NULL
;
1396 static const struct cris_opcode
**rest_prefixes
= NULL
;
1398 /* Allocate and clear the opcode-table. */
1399 if (opc_table
== NULL
)
1401 opc_table
= qemu_malloc (65536 * sizeof (opc_table
[0]));
1403 memset (opc_table
, 0, 65536 * sizeof (const struct cris_opcode
*));
1406 = qemu_malloc (65536 * sizeof (const struct cris_opcode
**));
1408 memset (dip_prefixes
, 0, 65536 * sizeof (dip_prefixes
[0]));
1411 = qemu_malloc (65536 * sizeof (const struct cris_opcode
**));
1413 memset (bdapq_m1_prefixes
, 0, 65536 * sizeof (bdapq_m1_prefixes
[0]));
1416 = qemu_malloc (65536 * sizeof (const struct cris_opcode
**));
1418 memset (bdapq_m2_prefixes
, 0, 65536 * sizeof (bdapq_m2_prefixes
[0]));
1421 = qemu_malloc (65536 * sizeof (const struct cris_opcode
**));
1423 memset (bdapq_m4_prefixes
, 0, 65536 * sizeof (bdapq_m4_prefixes
[0]));
1426 = qemu_malloc (65536 * sizeof (const struct cris_opcode
**));
1428 memset (rest_prefixes
, 0, 65536 * sizeof (rest_prefixes
[0]));
1431 /* Get the right table if this is a prefix.
1432 This code is connected to cris_constraints in that it knows what
1433 prefixes play a role in recognition of patterns; the necessary
1434 state is reflected by which table is used. If constraints
1435 involving match or non-match of prefix insns are changed, then this
1436 probably needs changing too. */
1437 if (prefix_insn
!= NO_CRIS_PREFIX
)
1439 const struct cris_opcode
*popcodep
1440 = (opc_table
[prefix_insn
] != NULL
1441 ? opc_table
[prefix_insn
]
1442 : get_opcode_entry (prefix_insn
, NO_CRIS_PREFIX
, disdata
));
1444 if (popcodep
== NULL
)
1447 if (popcodep
->match
== BDAP_QUICK_OPCODE
)
1449 /* Since some offsets are recognized with "push" macros, we
1450 have to have different tables for them. */
1451 int offset
= (prefix_insn
& 255);
1459 prefix_opc_table
= bdapq_m4_prefixes
;
1463 prefix_opc_table
= bdapq_m2_prefixes
;
1467 prefix_opc_table
= bdapq_m1_prefixes
;
1471 prefix_opc_table
= rest_prefixes
;
1475 else if (popcodep
->match
== DIP_OPCODE
)
1476 /* We don't allow postincrement when the prefix is DIP, so use a
1477 different table for DIP. */
1478 prefix_opc_table
= dip_prefixes
;
1480 prefix_opc_table
= rest_prefixes
;
1483 if (prefix_insn
!= NO_CRIS_PREFIX
1484 && prefix_opc_table
[insn
] != NULL
)
1485 max_matchedp
= prefix_opc_table
[insn
];
1486 else if (prefix_insn
== NO_CRIS_PREFIX
&& opc_table
[insn
] != NULL
)
1487 max_matchedp
= opc_table
[insn
];
1490 const struct cris_opcode
*opcodep
;
1491 int max_level_of_match
= -1;
1493 for (opcodep
= cris_opcodes
;
1494 opcodep
->name
!= NULL
;
1499 if (disdata
->distype
== cris_dis_v32
)
1501 switch (opcodep
->applicable_version
)
1503 case cris_ver_version_all
:
1507 case cris_ver_v0_10
:
1508 case cris_ver_v3_10
:
1509 case cris_ver_sim_v0_10
:
1510 case cris_ver_v8_10
:
1512 case cris_ver_warning
:
1529 switch (opcodep
->applicable_version
)
1531 case cris_ver_version_all
:
1534 case cris_ver_v0_10
:
1536 case cris_ver_v8_10
:
1538 case cris_ver_sim_v0_10
:
1540 case cris_ver_warning
:
1553 /* We give a double lead for bits matching the template in
1554 cris_opcodes. Not even, because then "move p8,r10" would
1555 be given 2 bits lead over "clear.d r10". When there's a
1556 tie, the first entry in the table wins. This is
1557 deliberate, to avoid a more complicated recognition
1559 if ((opcodep
->match
& insn
) == opcodep
->match
1560 && (opcodep
->lose
& insn
) == 0
1562 = cris_constraint (opcodep
->args
,
1568 += 2 * number_of_bits (opcodep
->match
1570 > max_level_of_match
))
1572 max_matchedp
= opcodep
;
1573 max_level_of_match
= level_of_match
;
1575 /* If there was a full match, never mind looking
1577 if (level_of_match
>= 2 * 16)
1581 /* Fill in the new entry.
1583 If there are changes to the opcode-table involving prefixes, and
1584 disassembly then does not work correctly, try removing the
1585 else-clause below that fills in the prefix-table. If that
1586 helps, you need to change the prefix_opc_table setting above, or
1587 something related. */
1588 if (prefix_insn
== NO_CRIS_PREFIX
)
1589 opc_table
[insn
] = max_matchedp
;
1591 prefix_opc_table
[insn
] = max_matchedp
;
1594 return max_matchedp
;
1597 /* Return -1 if the constraints of a bitwise-matched instruction say
1598 that there is no match. Otherwise return a nonnegative number
1599 indicating the confidence in the match (higher is better). */
1602 cris_constraint (const char *cs
,
1604 unsigned int prefix_insn
,
1605 struct cris_disasm_data
*disdata
)
1612 for (s
= cs
; *s
; s
++)
1616 /* Do not recognize "pop" if there's a prefix and then only for
1618 if (prefix_insn
!= NO_CRIS_PREFIX
1619 || disdata
->distype
!= cris_dis_v0_v10
)
1624 /* Not recognized at disassembly. */
1628 /* Size modifier for "clear", i.e. special register 0, 4 or 8.
1629 Check that it is one of them. Only special register 12 could
1630 be mismatched, but checking for matches is more logical than
1631 checking for mismatches when there are only a few cases. */
1632 tmp
= ((insn
>> 12) & 0xf);
1633 if (tmp
!= 0 && tmp
!= 4 && tmp
!= 8)
1638 if ((insn
& 0x30) == 0x30)
1643 /* A prefix operand without side-effect. */
1644 if (prefix_insn
!= NO_CRIS_PREFIX
&& (insn
& 0x400) == 0)
1655 /* If this is a prefixed insn with postincrement (side-effect),
1656 the prefix must not be DIP. */
1657 if (prefix_insn
!= NO_CRIS_PREFIX
)
1661 const struct cris_opcode
*prefix_opcodep
1662 = get_opcode_entry (prefix_insn
, NO_CRIS_PREFIX
, disdata
);
1664 if (prefix_opcodep
->match
== DIP_OPCODE
)
1673 /* If we don't fall through, then the prefix is ok. */
1676 /* A "push" prefix. Check for valid "push" size.
1677 In case of special register, it may be != 4. */
1678 if (prefix_insn
!= NO_CRIS_PREFIX
)
1680 /* Match the prefix insn to BDAPQ. */
1681 const struct cris_opcode
*prefix_opcodep
1682 = get_opcode_entry (prefix_insn
, NO_CRIS_PREFIX
, disdata
);
1684 if (prefix_opcodep
->match
== BDAP_QUICK_OPCODE
)
1686 int pushsize
= (prefix_insn
& 255);
1693 unsigned int spec_reg
= (insn
>> 12) & 15;
1694 const struct cris_spec_reg
*sregp
1695 = spec_reg_info (spec_reg
, disdata
->distype
);
1697 /* For a special-register, the "prefix size" must
1698 match the size of the register. */
1699 if (sregp
&& sregp
->reg_size
== (unsigned int) -pushsize
)
1702 else if (s
[1] == 'R')
1704 if ((insn
& 0x30) == 0x20 && pushsize
== -4)
1707 /* FIXME: Should abort here; next constraint letter
1708 *must* be 'P' or 'R'. */
1714 retval
= (((insn
>> 12) & 15) == (insn
& 15));
1723 const struct cris_spec_reg
*sregp
1724 = spec_reg_info ((insn
>> 12) & 15, disdata
->distype
);
1726 /* Since we match four bits, we will give a value of 4-1 = 3
1727 in a match. If there is a corresponding exact match of a
1728 special register in another pattern, it will get a value of
1729 4, which will be higher. This should be correct in that an
1730 exact pattern would match better than a general pattern.
1732 Note that there is a reason for not returning zero; the
1733 pattern for "clear" is partly matched in the bit-pattern
1734 (the two lower bits must be zero), while the bit-pattern
1735 for a move from a special register is matched in the
1736 register constraint. */
1748 if (prefix_insn
!= NO_CRIS_PREFIX
&& ! prefix_ok
)
1754 /* Format number as hex with a leading "0x" into outbuffer. */
1757 format_hex (unsigned long number
,
1759 struct cris_disasm_data
*disdata
)
1761 /* Truncate negative numbers on >32-bit hosts. */
1762 number
&= 0xffffffff;
1764 sprintf (outbuffer
, "0x%lx", number
);
1766 /* Save this value for the "case" support. */
1768 last_immediate
= number
;
1770 return outbuffer
+ strlen (outbuffer
);
1773 /* Format number as decimal into outbuffer. Parameter signedp says
1774 whether the number should be formatted as signed (!= 0) or
1778 format_dec (long number
, char *outbuffer
, int signedp
)
1780 last_immediate
= number
;
1781 sprintf (outbuffer
, signedp
? "%ld" : "%lu", number
);
1783 return outbuffer
+ strlen (outbuffer
);
1786 /* Format the name of the general register regno into outbuffer. */
1789 format_reg (struct cris_disasm_data
*disdata
,
1791 char *outbuffer_start
,
1792 bfd_boolean with_reg_prefix
)
1794 char *outbuffer
= outbuffer_start
;
1796 if (with_reg_prefix
)
1797 *outbuffer
++ = REGISTER_PREFIX_CHAR
;
1802 /* For v32, there is no context in which we output PC. */
1803 if (disdata
->distype
== cris_dis_v32
)
1804 strcpy (outbuffer
, "acr");
1806 strcpy (outbuffer
, "pc");
1810 strcpy (outbuffer
, "sp");
1814 sprintf (outbuffer
, "r%d", regno
);
1818 return outbuffer_start
+ strlen (outbuffer_start
);
1821 /* Format the name of a support register into outbuffer. */
1824 format_sup_reg (unsigned int regno
,
1825 char *outbuffer_start
,
1826 bfd_boolean with_reg_prefix
)
1828 char *outbuffer
= outbuffer_start
;
1831 if (with_reg_prefix
)
1832 *outbuffer
++ = REGISTER_PREFIX_CHAR
;
1834 for (i
= 0; cris_support_regs
[i
].name
!= NULL
; i
++)
1835 if (cris_support_regs
[i
].number
== regno
)
1837 sprintf (outbuffer
, "%s", cris_support_regs
[i
].name
);
1838 return outbuffer_start
+ strlen (outbuffer_start
);
1841 /* There's supposed to be register names covering all numbers, though
1842 some may be generic names. */
1843 sprintf (outbuffer
, "format_sup_reg-BUG");
1844 return outbuffer_start
+ strlen (outbuffer_start
);
1847 /* Return the length of an instruction. */
1850 bytes_to_skip (unsigned int insn
,
1851 const struct cris_opcode
*matchedp
,
1852 enum cris_disass_family distype
,
1853 const struct cris_opcode
*prefix_matchedp
)
1855 /* Each insn is a word plus "immediate" operands. */
1856 unsigned to_skip
= 2;
1857 const char *template = matchedp
->args
;
1860 for (s
= template; *s
; s
++)
1861 if ((*s
== 's' || *s
== 'N' || *s
== 'Y')
1862 && (insn
& 0x400) && (insn
& 15) == 15
1863 && prefix_matchedp
== NULL
)
1865 /* Immediate via [pc+], so we have to check the size of the
1867 int mode_size
= 1 << ((insn
>> 4) & (*template == 'z' ? 1 : 3));
1869 if (matchedp
->imm_oprnd_size
== SIZE_FIX_32
)
1871 else if (matchedp
->imm_oprnd_size
== SIZE_SPEC_REG
)
1873 const struct cris_spec_reg
*sregp
1874 = spec_reg_info ((insn
>> 12) & 15, distype
);
1876 /* FIXME: Improve error handling; should have been caught
1881 /* PC is incremented by two, not one, for a byte. Except on
1882 CRISv32, where constants are always DWORD-size for
1883 special registers. */
1885 distype
== cris_dis_v32
? 4 : (sregp
->reg_size
+ 1) & ~1;
1888 to_skip
+= (mode_size
+ 1) & ~1;
1898 /* Print condition code flags. */
1901 print_flags (struct cris_disasm_data
*disdata
, unsigned int insn
, char *cp
)
1903 /* Use the v8 (Etrax 100) flag definitions for disassembly.
1904 The differences with v0 (Etrax 1..4) vs. Svinto are:
1907 FIXME: Emit v0..v3 flag names somehow. */
1908 static const char v8_fnames
[] = "cvznxibm";
1909 static const char v32_fnames
[] = "cvznxiup";
1911 = disdata
->distype
== cris_dis_v32
? v32_fnames
: v8_fnames
;
1913 unsigned char flagbits
= (((insn
>> 8) & 0xf0) | (insn
& 15));
1916 for (i
= 0; i
< 8; i
++)
1917 if (flagbits
& (1 << i
))
1923 /* Print out an insn with its operands, and update the info->insn_type
1924 fields. The prefix_opcodep and the rest hold a prefix insn that is
1925 supposed to be output as an address mode. */
1928 print_with_operands (const struct cris_opcode
*opcodep
,
1930 unsigned char *buffer
,
1932 disassemble_info
*info
,
1933 /* If a prefix insn was before this insn (and is supposed
1934 to be output as an address), here is a description of
1936 const struct cris_opcode
*prefix_opcodep
,
1937 unsigned int prefix_insn
,
1938 unsigned char *prefix_buffer
,
1939 bfd_boolean with_reg_prefix
)
1941 /* Get a buffer of somewhat reasonable size where we store
1942 intermediate parts of the insn. */
1943 char temp
[sizeof (".d [$r13=$r12-2147483648],$r10") * 2];
1945 static const char mode_char
[] = "bwd?";
1948 struct cris_disasm_data
*disdata
1949 = (struct cris_disasm_data
*) info
->private_data
;
1951 /* Print out the name first thing we do. */
1952 (*info
->fprintf_func
) (info
->stream
, "%s", opcodep
->name
);
1957 /* Ignore any prefix indicator. */
1961 if (*s
== 'm' || *s
== 'M' || *s
== 'z')
1965 /* Get the size-letter. */
1967 ? (insn
& 0x8000 ? 'd'
1968 : insn
& 0x4000 ? 'w' : 'b')
1969 : mode_char
[(insn
>> 4) & (*s
== 'z' ? 1 : 3)];
1971 /* Ignore the size and the space character that follows. */
1975 /* Add a space if this isn't a long-branch, because for those will add
1976 the condition part of the name later. */
1977 if (opcodep
->match
!= (BRANCH_PC_LOW
+ BRANCH_INCR_HIGH
* 256))
1980 /* Fill in the insn-type if deducible from the name (and there's no
1982 if (opcodep
->name
[0] == 'j')
1984 if (CONST_STRNEQ (opcodep
->name
, "jsr"))
1985 /* It's "jsr" or "jsrc". */
1986 info
->insn_type
= dis_jsr
;
1988 /* Any other jump-type insn is considered a branch. */
1989 info
->insn_type
= dis_branch
;
1992 /* We might know some more fields right now. */
1993 info
->branch_delay_insns
= opcodep
->delayed
;
1995 /* Handle operands. */
2001 tp
= format_sup_reg ((insn
>> 12) & 15, tp
, with_reg_prefix
);
2005 if (with_reg_prefix
)
2006 *tp
++ = REGISTER_PREFIX_CHAR
;
2019 /* Ignore at this point; used at earlier stages to avoid
2020 recognition if there's a prefix at something that in other
2021 ways looks like a "pop". */
2025 /* Ignore. This is an optional ".d " on the large one of
2030 /* This was the prefix that made this a "push". We've already
2031 handled it by recognizing it, so signal that the prefix is
2032 handled by setting it to NULL. */
2033 prefix_opcodep
= NULL
;
2038 tp
= format_reg (disdata
, insn
& 15, tp
, with_reg_prefix
);
2042 tp
= format_reg (disdata
, (insn
>> 12) & 15, tp
, with_reg_prefix
);
2047 /* Like N but pc-relative to the start of the insn. */
2048 unsigned long number
2049 = (buffer
[2] + buffer
[3] * 256 + buffer
[4] * 65536
2050 + buffer
[5] * 0x1000000 + addr
);
2052 /* Finish off and output previous formatted bytes. */
2055 (*info
->fprintf_func
) (info
->stream
, "%s", temp
);
2058 (*info
->print_address_func
) ((bfd_vma
) number
, info
);
2064 /* Like n but the offset is bits <3:0> in the instruction. */
2065 unsigned long number
= (buffer
[0] & 0xf) * 2 + addr
;
2067 /* Finish off and output previous formatted bytes. */
2070 (*info
->fprintf_func
) (info
->stream
, "%s", temp
);
2073 (*info
->print_address_func
) ((bfd_vma
) number
, info
);
2082 /* Any "normal" memory operand. */
2083 if ((insn
& 0x400) && (insn
& 15) == 15 && prefix_opcodep
== NULL
)
2085 /* We're looking at [pc+], i.e. we need to output an immediate
2086 number, where the size can depend on different things. */
2089 = ((*cs
== 'z' && (insn
& 0x20))
2090 || opcodep
->match
== BDAP_QUICK_OPCODE
);
2093 if (opcodep
->imm_oprnd_size
== SIZE_FIX_32
)
2095 else if (opcodep
->imm_oprnd_size
== SIZE_SPEC_REG
)
2097 const struct cris_spec_reg
*sregp
2098 = spec_reg_info ((insn
>> 12) & 15, disdata
->distype
);
2100 /* A NULL return should have been as a non-match earlier,
2101 so catch it as an internal error in the error-case
2104 /* Whatever non-valid size. */
2107 /* PC is always incremented by a multiple of two.
2108 For CRISv32, immediates are always 4 bytes for
2109 special registers. */
2110 nbytes
= disdata
->distype
== cris_dis_v32
2111 ? 4 : (sregp
->reg_size
+ 1) & ~1;
2115 int mode_size
= 1 << ((insn
>> 4) & (*cs
== 'z' ? 1 : 3));
2127 if (signedp
&& number
> 127)
2132 number
= buffer
[2] + buffer
[3] * 256;
2133 if (signedp
&& number
> 32767)
2139 = buffer
[2] + buffer
[3] * 256 + buffer
[4] * 65536
2140 + buffer
[5] * 0x1000000;
2149 if ((*cs
== 'z' && (insn
& 0x20))
2150 || (opcodep
->match
== BDAP_QUICK_OPCODE
2151 && (nbytes
<= 2 || buffer
[1 + nbytes
] == 0)))
2152 tp
= format_dec (number
, tp
, signedp
);
2155 unsigned int highbyte
= (number
>> 24) & 0xff;
2157 /* Either output this as an address or as a number. If it's
2158 a dword with the same high-byte as the address of the
2159 insn, assume it's an address, and also if it's a non-zero
2160 non-0xff high-byte. If this is a jsr or a jump, then
2161 it's definitely an address. */
2163 && (highbyte
== ((addr
>> 24) & 0xff)
2164 || (highbyte
!= 0 && highbyte
!= 0xff)
2165 || info
->insn_type
== dis_branch
2166 || info
->insn_type
== dis_jsr
))
2168 /* Finish off and output previous formatted bytes. */
2172 (*info
->fprintf_func
) (info
->stream
, "%s", temp
);
2174 (*info
->print_address_func
) ((bfd_vma
) number
, info
);
2176 info
->target
= number
;
2179 tp
= format_hex (number
, tp
, disdata
);
2184 /* Not an immediate number. Then this is a (possibly
2185 prefixed) memory operand. */
2186 if (info
->insn_type
!= dis_nonbranch
)
2190 & (opcodep
->args
[0] == 'z' ? 1 : 3));
2192 info
->insn_type
= dis_dref
;
2193 info
->flags
|= CRIS_DIS_FLAG_MEMREF
;
2195 if (opcodep
->imm_oprnd_size
== SIZE_FIX_32
)
2197 else if (opcodep
->imm_oprnd_size
== SIZE_SPEC_REG
)
2199 const struct cris_spec_reg
*sregp
2200 = spec_reg_info ((insn
>> 12) & 15, disdata
->distype
);
2202 /* FIXME: Improve error handling; should have been caught
2207 size
= sregp
->reg_size
;
2212 info
->data_size
= size
;
2218 /* We don't match dip with a postincremented field
2219 as a side-effect address mode. */
2220 && ((insn
& 0x400) == 0
2221 || prefix_opcodep
->match
!= DIP_OPCODE
))
2225 tp
= format_reg (disdata
, insn
& 15, tp
, with_reg_prefix
);
2230 /* We mainly ignore the prefix format string when the
2231 address-mode syntax is output. */
2232 switch (prefix_opcodep
->match
)
2235 /* It's [r], [r+] or [pc+]. */
2236 if ((prefix_insn
& 0x400) && (prefix_insn
& 15) == 15)
2238 /* It's [pc+]. This cannot possibly be anything
2240 unsigned long number
2241 = prefix_buffer
[2] + prefix_buffer
[3] * 256
2242 + prefix_buffer
[4] * 65536
2243 + prefix_buffer
[5] * 0x1000000;
2245 info
->target
= (bfd_vma
) number
;
2247 /* Finish off and output previous formatted
2252 (*info
->fprintf_func
) (info
->stream
, "%s", temp
);
2254 (*info
->print_address_func
) ((bfd_vma
) number
, info
);
2258 /* For a memref in an address, we use target2.
2259 In this case, target is zero. */
2261 |= (CRIS_DIS_FLAG_MEM_TARGET2_IS_REG
2262 | CRIS_DIS_FLAG_MEM_TARGET2_MEM
);
2264 info
->target2
= prefix_insn
& 15;
2267 tp
= format_reg (disdata
, prefix_insn
& 15, tp
,
2269 if (prefix_insn
& 0x400)
2275 case BDAP_QUICK_OPCODE
:
2279 number
= prefix_buffer
[0];
2283 /* Output "reg+num" or, if num < 0, "reg-num". */
2284 tp
= format_reg (disdata
, (prefix_insn
>> 12) & 15, tp
,
2288 tp
= format_dec (number
, tp
, 1);
2290 info
->flags
|= CRIS_DIS_FLAG_MEM_TARGET_IS_REG
;
2291 info
->target
= (prefix_insn
>> 12) & 15;
2292 info
->target2
= (bfd_vma
) number
;
2297 /* Output "r+R.m". */
2298 tp
= format_reg (disdata
, prefix_insn
& 15, tp
,
2301 tp
= format_reg (disdata
, (prefix_insn
>> 12) & 15, tp
,
2304 *tp
++ = mode_char
[(prefix_insn
>> 4) & 3];
2307 |= (CRIS_DIS_FLAG_MEM_TARGET2_IS_REG
2308 | CRIS_DIS_FLAG_MEM_TARGET_IS_REG
2310 | ((prefix_insn
& 0x8000)
2311 ? CRIS_DIS_FLAG_MEM_TARGET2_MULT4
2312 : ((prefix_insn
& 0x8000)
2313 ? CRIS_DIS_FLAG_MEM_TARGET2_MULT2
: 0)));
2315 /* Is it the casejump? It's a "adds.w [pc+r%d.w],pc". */
2316 if (insn
== 0xf83f && (prefix_insn
& ~0xf000) == 0x55f)
2317 /* Then start interpreting data as offsets. */
2318 case_offset_counter
= no_of_case_offsets
;
2321 case BDAP_INDIR_OPCODE
:
2322 /* Output "r+s.m", or, if "s" is [pc+], "r+s" or
2324 tp
= format_reg (disdata
, (prefix_insn
>> 12) & 15, tp
,
2327 if ((prefix_insn
& 0x400) && (prefix_insn
& 15) == 15)
2330 unsigned int nbytes
;
2332 /* It's a value. Get its size. */
2333 int mode_size
= 1 << ((prefix_insn
>> 4) & 3);
2343 number
= prefix_buffer
[2];
2349 number
= prefix_buffer
[2] + prefix_buffer
[3] * 256;
2356 = prefix_buffer
[2] + prefix_buffer
[3] * 256
2357 + prefix_buffer
[4] * 65536
2358 + prefix_buffer
[5] * 0x1000000;
2367 info
->flags
|= CRIS_DIS_FLAG_MEM_TARGET_IS_REG
;
2368 info
->target2
= (bfd_vma
) number
;
2370 /* If the size is dword, then assume it's an
2374 /* Finish off and output previous formatted
2379 (*info
->fprintf_func
) (info
->stream
, "%s", temp
);
2381 (*info
->print_address_func
) ((bfd_vma
) number
, info
);
2387 tp
= format_dec (number
, tp
, 1);
2392 /* Output "r+[R].m" or "r+[R+].m". */
2395 tp
= format_reg (disdata
, prefix_insn
& 15, tp
,
2397 if (prefix_insn
& 0x400)
2401 *tp
++ = mode_char
[(prefix_insn
>> 4) & 3];
2404 |= (CRIS_DIS_FLAG_MEM_TARGET2_IS_REG
2405 | CRIS_DIS_FLAG_MEM_TARGET2_MEM
2406 | CRIS_DIS_FLAG_MEM_TARGET_IS_REG
2408 | (((prefix_insn
>> 4) == 2)
2410 : (((prefix_insn
>> 4) & 3) == 1
2411 ? CRIS_DIS_FLAG_MEM_TARGET2_MEM_WORD
2412 : CRIS_DIS_FLAG_MEM_TARGET2_MEM_BYTE
)));
2417 (*info
->fprintf_func
) (info
->stream
, "?prefix-bug");
2420 /* To mark that the prefix is used, reset it. */
2421 prefix_opcodep
= NULL
;
2425 tp
= format_reg (disdata
, insn
& 15, tp
, with_reg_prefix
);
2427 info
->flags
|= CRIS_DIS_FLAG_MEM_TARGET_IS_REG
;
2428 info
->target
= insn
& 15;
2438 tp
= format_reg (disdata
, (insn
>> 12) & 15, tp
, with_reg_prefix
);
2440 *tp
++ = mode_char
[(insn
>> 4) & 3];
2444 tp
= format_dec (insn
& 63, tp
, 0);
2449 int where
= buffer
[2] + buffer
[3] * 256;
2454 where
+= addr
+ ((disdata
->distype
== cris_dis_v32
) ? 0 : 4);
2456 if (insn
== BA_PC_INCR_OPCODE
)
2457 info
->insn_type
= dis_branch
;
2459 info
->insn_type
= dis_condbranch
;
2461 info
->target
= (bfd_vma
) where
;
2465 (*info
->fprintf_func
) (info
->stream
, "%s%s ",
2466 temp
, cris_cc_strings
[insn
>> 12]);
2468 (*info
->print_address_func
) ((bfd_vma
) where
, info
);
2473 tp
= format_dec (insn
& 31, tp
, 0);
2477 tp
= format_dec (insn
& 15, tp
, 0);
2482 long offset
= insn
& 0xfe;
2488 if (opcodep
->match
== BA_QUICK_OPCODE
)
2489 info
->insn_type
= dis_branch
;
2491 info
->insn_type
= dis_condbranch
;
2493 target
= addr
+ ((disdata
->distype
== cris_dis_v32
) ? 0 : 2) + offset
;
2494 info
->target
= target
;
2497 (*info
->fprintf_func
) (info
->stream
, "%s", temp
);
2498 (*info
->print_address_func
) (target
, info
);
2505 long number
= buffer
[0];
2508 number
= number
- 256;
2510 tp
= format_dec (number
, tp
, 1);
2512 tp
= format_reg (disdata
, (insn
>> 12) & 15, tp
, with_reg_prefix
);
2517 tp
= print_flags (disdata
, insn
, tp
);
2521 tp
= format_dec ((insn
& 32) ? (insn
& 31) | ~31L : insn
& 31, tp
, 1);
2526 const struct cris_spec_reg
*sregp
2527 = spec_reg_info ((insn
>> 12) & 15, disdata
->distype
);
2529 if (sregp
->name
== NULL
)
2530 /* Should have been caught as a non-match eariler. */
2534 if (with_reg_prefix
)
2535 *tp
++ = REGISTER_PREFIX_CHAR
;
2536 strcpy (tp
, sregp
->name
);
2551 (*info
->fprintf_func
) (info
->stream
, " (OOPS unused prefix \"%s: %s\")",
2552 prefix_opcodep
->name
, prefix_opcodep
->args
);
2554 (*info
->fprintf_func
) (info
->stream
, "%s", temp
);
2556 /* Get info for matching case-tables, if we don't have any active.
2557 We assume that the last constant seen is used; either in the insn
2558 itself or in a "move.d const,rN, sub.d rN,rM"-like sequence. */
2559 if (TRACE_CASE
&& case_offset_counter
== 0)
2561 if (CONST_STRNEQ (opcodep
->name
, "sub"))
2562 case_offset
= last_immediate
;
2564 /* It could also be an "add", if there are negative case-values. */
2565 else if (CONST_STRNEQ (opcodep
->name
, "add"))
2566 /* The first case is the negated operand to the add. */
2567 case_offset
= -last_immediate
;
2569 /* A bound insn will tell us the number of cases. */
2570 else if (CONST_STRNEQ (opcodep
->name
, "bound"))
2571 no_of_case_offsets
= last_immediate
+ 1;
2573 /* A jump or jsr or branch breaks the chain of insns for a
2574 case-table, so assume default first-case again. */
2575 else if (info
->insn_type
== dis_jsr
2576 || info
->insn_type
== dis_branch
2577 || info
->insn_type
== dis_condbranch
)
2583 /* Print the CRIS instruction at address memaddr on stream. Returns
2584 length of the instruction, in bytes. Prefix register names with `$' if
2588 print_insn_cris_generic (bfd_vma memaddr
,
2589 disassemble_info
*info
,
2590 bfd_boolean with_reg_prefix
)
2594 const struct cris_opcode
*matchedp
;
2596 struct cris_disasm_data
*disdata
2597 = (struct cris_disasm_data
*) info
->private_data
;
2599 /* No instruction will be disassembled as longer than this number of
2600 bytes; stacked prefixes will not be expanded. */
2601 unsigned char buffer
[MAX_BYTES_PER_CRIS_INSN
];
2602 unsigned char *bufp
;
2606 /* There will be an "out of range" error after the last instruction.
2607 Reading pairs of bytes in decreasing number, we hope that we will get
2608 at least the amount that we will consume.
2610 If we can't get any data, or we do not get enough data, we print
2611 the error message. */
2613 nbytes
= info
->buffer_length
;
2614 if (nbytes
> MAX_BYTES_PER_CRIS_INSN
)
2615 nbytes
= MAX_BYTES_PER_CRIS_INSN
;
2616 status
= (*info
->read_memory_func
) (memaddr
, buffer
, nbytes
, info
);
2618 /* If we did not get all we asked for, then clear the rest.
2619 Hopefully this makes a reproducible result in case of errors. */
2620 if (nbytes
!= MAX_BYTES_PER_CRIS_INSN
)
2621 memset (buffer
+ nbytes
, 0, MAX_BYTES_PER_CRIS_INSN
- nbytes
);
2626 /* Set some defaults for the insn info. */
2627 info
->insn_info_valid
= 1;
2628 info
->branch_delay_insns
= 0;
2629 info
->data_size
= 0;
2630 info
->insn_type
= dis_nonbranch
;
2635 /* If we got any data, disassemble it. */
2640 insn
= bufp
[0] + bufp
[1] * 256;
2642 /* If we're in a case-table, don't disassemble the offsets. */
2643 if (TRACE_CASE
&& case_offset_counter
!= 0)
2645 info
->insn_type
= dis_noninsn
;
2648 /* If to print data as offsets, then shortcut here. */
2649 (*info
->fprintf_func
) (info
->stream
, "case %ld%s: -> ",
2650 case_offset
+ no_of_case_offsets
2651 - case_offset_counter
,
2652 case_offset_counter
== 1 ? "/default" :
2655 (*info
->print_address_func
) ((bfd_vma
)
2658 - (no_of_case_offsets
2659 - case_offset_counter
)
2661 case_offset_counter
--;
2663 /* The default case start (without a "sub" or "add") must be
2665 if (case_offset_counter
== 0)
2670 /* We're often called to disassemble zeroes. While this is a
2671 valid "bcc .+2" insn, it is also useless enough and enough
2672 of a nuiscance that we will just output "bcc .+2" for it
2673 and signal it as a noninsn. */
2674 (*info
->fprintf_func
) (info
->stream
,
2675 disdata
->distype
== cris_dis_v32
2676 ? "bcc ." : "bcc .+2");
2677 info
->insn_type
= dis_noninsn
;
2682 const struct cris_opcode
*prefix_opcodep
= NULL
;
2683 unsigned char *prefix_buffer
= bufp
;
2684 unsigned int prefix_insn
= insn
;
2685 int prefix_size
= 0;
2687 matchedp
= get_opcode_entry (insn
, NO_CRIS_PREFIX
, disdata
);
2689 /* Check if we're supposed to write out prefixes as address
2690 modes and if this was a prefix. */
2691 if (matchedp
!= NULL
&& PARSE_PREFIX
&& matchedp
->args
[0] == 'p')
2693 /* If it's a prefix, put it into the prefix vars and get the
2695 prefix_size
= bytes_to_skip (prefix_insn
, matchedp
,
2696 disdata
->distype
, NULL
);
2697 prefix_opcodep
= matchedp
;
2699 insn
= bufp
[prefix_size
] + bufp
[prefix_size
+ 1] * 256;
2700 matchedp
= get_opcode_entry (insn
, prefix_insn
, disdata
);
2702 if (matchedp
!= NULL
)
2704 addr
+= prefix_size
;
2705 bufp
+= prefix_size
;
2706 advance
+= prefix_size
;
2710 /* The "main" insn wasn't valid, at least not when
2711 prefixed. Put back things enough to output the
2712 prefix insn only, as a normal insn. */
2713 matchedp
= prefix_opcodep
;
2715 prefix_opcodep
= NULL
;
2719 if (matchedp
== NULL
)
2721 (*info
->fprintf_func
) (info
->stream
, "??0x%x", insn
);
2724 info
->insn_type
= dis_noninsn
;
2729 += bytes_to_skip (insn
, matchedp
, disdata
->distype
,
2732 /* The info_type and assorted fields will be set according
2734 print_with_operands (matchedp
, insn
, bufp
, addr
, info
,
2735 prefix_opcodep
, prefix_insn
,
2736 prefix_buffer
, with_reg_prefix
);
2741 info
->insn_type
= dis_noninsn
;
2743 /* If we read less than MAX_BYTES_PER_CRIS_INSN, i.e. we got an error
2744 status when reading that much, and the insn decoding indicated a
2745 length exceeding what we read, there is an error. */
2746 if (status
!= 0 && (nbytes
== 0 || advance
> nbytes
))
2748 (*info
->memory_error_func
) (status
, memaddr
, info
);
2752 /* Max supported insn size with one folded prefix insn. */
2753 info
->bytes_per_line
= MAX_BYTES_PER_CRIS_INSN
;
2755 /* I would like to set this to a fixed value larger than the actual
2756 number of bytes to print in order to avoid spaces between bytes,
2757 but objdump.c (2.9.1) does not like that, so we print 16-bit
2758 chunks, which is the next choice. */
2759 info
->bytes_per_chunk
= 2;
2761 /* Printing bytes in order of increasing addresses makes sense,
2762 especially on a little-endian target.
2763 This is completely the opposite of what you think; setting this to
2764 BFD_ENDIAN_LITTLE will print bytes in order N..0 rather than the 0..N
2766 info
->display_endian
= BFD_ENDIAN_BIG
;
2771 /* Disassemble, prefixing register names with `$'. CRIS v0..v10. */
2774 print_insn_cris_with_register_prefix (bfd_vma vma
,
2775 disassemble_info
*info
)
2777 if (info
->private_data
== NULL
2778 && !cris_parse_disassembler_options (info
, cris_dis_v0_v10
))
2780 return print_insn_cris_generic (vma
, info
, true);
2783 /* Disassemble, prefixing register names with `$'. CRIS v32. */
2786 print_insn_crisv32_with_register_prefix (bfd_vma vma
,
2787 disassemble_info
*info
)
2789 if (info
->private_data
== NULL
2790 && !cris_parse_disassembler_options (info
, cris_dis_v32
))
2792 return print_insn_cris_generic (vma
, info
, true);
2796 /* Disassemble, prefixing register names with `$'.
2797 Common v10 and v32 subset. */
2800 print_insn_crisv10_v32_with_register_prefix (bfd_vma vma
,
2801 disassemble_info
*info
)
2803 if (info
->private_data
== NULL
2804 && !cris_parse_disassembler_options (info
, cris_dis_common_v10_v32
))
2806 return print_insn_cris_generic (vma
, info
, true);
2809 /* Disassemble, no prefixes on register names. CRIS v0..v10. */
2812 print_insn_cris_without_register_prefix (bfd_vma vma
,
2813 disassemble_info
*info
)
2815 if (info
->private_data
== NULL
2816 && !cris_parse_disassembler_options (info
, cris_dis_v0_v10
))
2818 return print_insn_cris_generic (vma
, info
, false);
2821 /* Disassemble, no prefixes on register names. CRIS v32. */
2824 print_insn_crisv32_without_register_prefix (bfd_vma vma
,
2825 disassemble_info
*info
)
2827 if (info
->private_data
== NULL
2828 && !cris_parse_disassembler_options (info
, cris_dis_v32
))
2830 return print_insn_cris_generic (vma
, info
, false);
2833 /* Disassemble, no prefixes on register names.
2834 Common v10 and v32 subset. */
2837 print_insn_crisv10_v32_without_register_prefix (bfd_vma vma
,
2838 disassemble_info
*info
)
2840 if (info
->private_data
== NULL
2841 && !cris_parse_disassembler_options (info
, cris_dis_common_v10_v32
))
2843 return print_insn_cris_generic (vma
, info
, false);
2848 print_insn_crisv32 (bfd_vma vma
,
2849 disassemble_info
*info
)
2851 return print_insn_crisv32_with_register_prefix(vma
, info
);
2854 /* Return a disassembler-function that prints registers with a `$' prefix,
2855 or one that prints registers without a prefix.
2856 FIXME: We should improve the solution to avoid the multitude of
2857 functions seen above. */
2860 cris_get_disassembler (bfd
*abfd
)
2862 /* If there's no bfd in sight, we return what is valid as input in all
2863 contexts if fed back to the assembler: disassembly *with* register
2864 prefix. Unfortunately this will be totally wrong for v32. */
2866 return print_insn_cris_with_register_prefix
;
2868 if (bfd_get_symbol_leading_char (abfd
) == 0)
2870 if (bfd_get_mach (abfd
) == bfd_mach_cris_v32
)
2871 return print_insn_crisv32_with_register_prefix
;
2872 if (bfd_get_mach (abfd
) == bfd_mach_cris_v10_v32
)
2873 return print_insn_crisv10_v32_with_register_prefix
;
2875 /* We default to v10. This may be specifically specified in the
2876 bfd mach, but is also the default setting. */
2877 return print_insn_cris_with_register_prefix
;
2880 if (bfd_get_mach (abfd
) == bfd_mach_cris_v32
)
2881 return print_insn_crisv32_without_register_prefix
;
2882 if (bfd_get_mach (abfd
) == bfd_mach_cris_v10_v32
)
2883 return print_insn_crisv10_v32_without_register_prefix
;
2884 return print_insn_cris_without_register_prefix
;
2888 eval: (c-set-style "gnu")