aurel32 | f54b3f9 | 2008-04-12 20:14:54 +0000 | [diff] [blame] | 1 | /* Disassembler for the PA-RISC. Somewhat derived from sparc-pinsn.c. |
| 2 | Copyright 1989, 1990, 1992, 1993, 1994, 1995, 1998, 1999, 2000, 2001, 2003, |
| 3 | 2005 Free Software Foundation, Inc. |
| 4 | |
| 5 | Contributed by the Center for Software Science at the |
| 6 | University of Utah (pa-gdb-bugs@cs.utah.edu). |
| 7 | |
| 8 | This program is free software; you can redistribute it and/or modify |
| 9 | it under the terms of the GNU General Public License as published by |
| 10 | the Free Software Foundation; either version 2 of the License, or |
| 11 | (at your option) any later version. |
| 12 | |
| 13 | This program is distributed in the hope that it will be useful, |
| 14 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 15 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 16 | GNU General Public License for more details. |
| 17 | |
| 18 | You should have received a copy of the GNU General Public License |
| 19 | along with this program; if not, write to the Free Software |
| 20 | Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, |
| 21 | MA 02110-1301, USA. */ |
| 22 | |
| 23 | #include "dis-asm.h" |
| 24 | |
| 25 | /* HP PA-RISC SOM object file format: definitions internal to BFD. |
| 26 | Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, |
| 27 | 2003 Free Software Foundation, Inc. |
| 28 | |
| 29 | Contributed by the Center for Software Science at the |
| 30 | University of Utah (pa-gdb-bugs@cs.utah.edu). |
| 31 | |
| 32 | This file is part of BFD, the Binary File Descriptor library. |
| 33 | |
| 34 | This program is free software; you can redistribute it and/or modify |
| 35 | it under the terms of the GNU General Public License as published by |
| 36 | the Free Software Foundation; either version 2 of the License, or |
| 37 | (at your option) any later version. |
| 38 | |
| 39 | This program is distributed in the hope that it will be useful, |
| 40 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 41 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 42 | GNU General Public License for more details. |
| 43 | |
| 44 | You should have received a copy of the GNU General Public License |
| 45 | along with this program; if not, write to the Free Software |
| 46 | Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */ |
| 47 | |
| 48 | #ifndef _LIBHPPA_H |
| 49 | #define _LIBHPPA_H |
| 50 | |
| 51 | #define BYTES_IN_WORD 4 |
| 52 | #define PA_PAGESIZE 0x1000 |
| 53 | |
| 54 | /* The PA instruction set variants. */ |
| 55 | enum pa_arch {pa10 = 10, pa11 = 11, pa20 = 20, pa20w = 25}; |
| 56 | |
| 57 | /* HP PA-RISC relocation types */ |
| 58 | |
| 59 | enum hppa_reloc_field_selector_type |
| 60 | { |
| 61 | R_HPPA_FSEL = 0x0, |
| 62 | R_HPPA_LSSEL = 0x1, |
| 63 | R_HPPA_RSSEL = 0x2, |
| 64 | R_HPPA_LSEL = 0x3, |
| 65 | R_HPPA_RSEL = 0x4, |
| 66 | R_HPPA_LDSEL = 0x5, |
| 67 | R_HPPA_RDSEL = 0x6, |
| 68 | R_HPPA_LRSEL = 0x7, |
| 69 | R_HPPA_RRSEL = 0x8, |
| 70 | R_HPPA_NSEL = 0x9, |
| 71 | R_HPPA_NLSEL = 0xa, |
| 72 | R_HPPA_NLRSEL = 0xb, |
| 73 | R_HPPA_PSEL = 0xc, |
| 74 | R_HPPA_LPSEL = 0xd, |
| 75 | R_HPPA_RPSEL = 0xe, |
| 76 | R_HPPA_TSEL = 0xf, |
| 77 | R_HPPA_LTSEL = 0x10, |
| 78 | R_HPPA_RTSEL = 0x11, |
| 79 | R_HPPA_LTPSEL = 0x12, |
| 80 | R_HPPA_RTPSEL = 0x13 |
| 81 | }; |
| 82 | |
| 83 | /* /usr/include/reloc.h defines these to constants. We want to use |
| 84 | them in enums, so #undef them before we start using them. We might |
| 85 | be able to fix this another way by simply managing not to include |
| 86 | /usr/include/reloc.h, but currently GDB picks up these defines |
| 87 | somewhere. */ |
| 88 | #undef e_fsel |
| 89 | #undef e_lssel |
| 90 | #undef e_rssel |
| 91 | #undef e_lsel |
| 92 | #undef e_rsel |
| 93 | #undef e_ldsel |
| 94 | #undef e_rdsel |
| 95 | #undef e_lrsel |
| 96 | #undef e_rrsel |
| 97 | #undef e_nsel |
| 98 | #undef e_nlsel |
| 99 | #undef e_nlrsel |
| 100 | #undef e_psel |
| 101 | #undef e_lpsel |
| 102 | #undef e_rpsel |
| 103 | #undef e_tsel |
| 104 | #undef e_ltsel |
| 105 | #undef e_rtsel |
| 106 | #undef e_one |
| 107 | #undef e_two |
| 108 | #undef e_pcrel |
| 109 | #undef e_con |
| 110 | #undef e_plabel |
| 111 | #undef e_abs |
| 112 | |
| 113 | /* for compatibility */ |
| 114 | enum hppa_reloc_field_selector_type_alt |
| 115 | { |
| 116 | e_fsel = R_HPPA_FSEL, |
| 117 | e_lssel = R_HPPA_LSSEL, |
| 118 | e_rssel = R_HPPA_RSSEL, |
| 119 | e_lsel = R_HPPA_LSEL, |
| 120 | e_rsel = R_HPPA_RSEL, |
| 121 | e_ldsel = R_HPPA_LDSEL, |
| 122 | e_rdsel = R_HPPA_RDSEL, |
| 123 | e_lrsel = R_HPPA_LRSEL, |
| 124 | e_rrsel = R_HPPA_RRSEL, |
| 125 | e_nsel = R_HPPA_NSEL, |
| 126 | e_nlsel = R_HPPA_NLSEL, |
| 127 | e_nlrsel = R_HPPA_NLRSEL, |
| 128 | e_psel = R_HPPA_PSEL, |
| 129 | e_lpsel = R_HPPA_LPSEL, |
| 130 | e_rpsel = R_HPPA_RPSEL, |
| 131 | e_tsel = R_HPPA_TSEL, |
| 132 | e_ltsel = R_HPPA_LTSEL, |
| 133 | e_rtsel = R_HPPA_RTSEL, |
| 134 | e_ltpsel = R_HPPA_LTPSEL, |
| 135 | e_rtpsel = R_HPPA_RTPSEL |
| 136 | }; |
| 137 | |
| 138 | enum hppa_reloc_expr_type |
| 139 | { |
| 140 | R_HPPA_E_ONE = 0, |
| 141 | R_HPPA_E_TWO = 1, |
| 142 | R_HPPA_E_PCREL = 2, |
| 143 | R_HPPA_E_CON = 3, |
| 144 | R_HPPA_E_PLABEL = 7, |
| 145 | R_HPPA_E_ABS = 18 |
| 146 | }; |
| 147 | |
| 148 | /* for compatibility */ |
| 149 | enum hppa_reloc_expr_type_alt |
| 150 | { |
| 151 | e_one = R_HPPA_E_ONE, |
| 152 | e_two = R_HPPA_E_TWO, |
| 153 | e_pcrel = R_HPPA_E_PCREL, |
| 154 | e_con = R_HPPA_E_CON, |
| 155 | e_plabel = R_HPPA_E_PLABEL, |
| 156 | e_abs = R_HPPA_E_ABS |
| 157 | }; |
| 158 | |
| 159 | |
| 160 | /* Relocations for function calls must be accompanied by parameter |
| 161 | relocation bits. These bits describe exactly where the caller has |
| 162 | placed the function's arguments and where it expects to find a return |
| 163 | value. |
| 164 | |
| 165 | Both ELF and SOM encode this information within the addend field |
| 166 | of the call relocation. (Note this could break very badly if one |
| 167 | was to make a call like bl foo + 0x12345678). |
| 168 | |
| 169 | The high order 10 bits contain parameter relocation information, |
| 170 | the low order 22 bits contain the constant offset. */ |
| 171 | |
| 172 | #define HPPA_R_ARG_RELOC(a) \ |
| 173 | (((a) >> 22) & 0x3ff) |
| 174 | #define HPPA_R_CONSTANT(a) \ |
| 175 | ((((bfd_signed_vma)(a)) << (BFD_ARCH_SIZE-22)) >> (BFD_ARCH_SIZE-22)) |
| 176 | #define HPPA_R_ADDEND(r, c) \ |
| 177 | (((r) << 22) + ((c) & 0x3fffff)) |
| 178 | |
| 179 | |
| 180 | /* Some functions to manipulate PA instructions. */ |
| 181 | |
| 182 | /* Declare the functions with the unused attribute to avoid warnings. */ |
| 183 | static inline int sign_extend (int, int) ATTRIBUTE_UNUSED; |
| 184 | static inline int low_sign_extend (int, int) ATTRIBUTE_UNUSED; |
| 185 | static inline int sign_unext (int, int) ATTRIBUTE_UNUSED; |
| 186 | static inline int low_sign_unext (int, int) ATTRIBUTE_UNUSED; |
| 187 | static inline int re_assemble_3 (int) ATTRIBUTE_UNUSED; |
| 188 | static inline int re_assemble_12 (int) ATTRIBUTE_UNUSED; |
| 189 | static inline int re_assemble_14 (int) ATTRIBUTE_UNUSED; |
| 190 | static inline int re_assemble_16 (int) ATTRIBUTE_UNUSED; |
| 191 | static inline int re_assemble_17 (int) ATTRIBUTE_UNUSED; |
| 192 | static inline int re_assemble_21 (int) ATTRIBUTE_UNUSED; |
| 193 | static inline int re_assemble_22 (int) ATTRIBUTE_UNUSED; |
| 194 | static inline bfd_signed_vma hppa_field_adjust |
| 195 | (bfd_vma, bfd_signed_vma, enum hppa_reloc_field_selector_type_alt) |
| 196 | ATTRIBUTE_UNUSED; |
| 197 | static inline int hppa_rebuild_insn (int, int, int) ATTRIBUTE_UNUSED; |
| 198 | |
| 199 | |
| 200 | /* The *sign_extend functions are used to assemble various bitfields |
| 201 | taken from an instruction and return the resulting immediate |
| 202 | value. */ |
| 203 | |
| 204 | static inline int |
| 205 | sign_extend (int x, int len) |
| 206 | { |
| 207 | int signbit = (1 << (len - 1)); |
| 208 | int mask = (signbit << 1) - 1; |
| 209 | return ((x & mask) ^ signbit) - signbit; |
| 210 | } |
| 211 | |
| 212 | static inline int |
| 213 | low_sign_extend (int x, int len) |
| 214 | { |
| 215 | return (x >> 1) - ((x & 1) << (len - 1)); |
| 216 | } |
| 217 | |
| 218 | |
| 219 | /* The re_assemble_* functions prepare an immediate value for |
| 220 | insertion into an opcode. pa-risc uses all sorts of weird bitfields |
| 221 | in the instruction to hold the value. */ |
| 222 | |
| 223 | static inline int |
| 224 | sign_unext (int x, int len) |
| 225 | { |
| 226 | int len_ones; |
| 227 | |
| 228 | len_ones = (1 << len) - 1; |
| 229 | |
| 230 | return x & len_ones; |
| 231 | } |
| 232 | |
| 233 | static inline int |
| 234 | low_sign_unext (int x, int len) |
| 235 | { |
| 236 | int temp; |
| 237 | int sign; |
| 238 | |
| 239 | sign = (x >> (len-1)) & 1; |
| 240 | |
| 241 | temp = sign_unext (x, len-1); |
| 242 | |
| 243 | return (temp << 1) | sign; |
| 244 | } |
| 245 | |
| 246 | static inline int |
| 247 | re_assemble_3 (int as3) |
| 248 | { |
| 249 | return (( (as3 & 4) << (13-2)) |
| 250 | | ((as3 & 3) << (13+1))); |
| 251 | } |
| 252 | |
| 253 | static inline int |
| 254 | re_assemble_12 (int as12) |
| 255 | { |
| 256 | return (( (as12 & 0x800) >> 11) |
| 257 | | ((as12 & 0x400) >> (10 - 2)) |
| 258 | | ((as12 & 0x3ff) << (1 + 2))); |
| 259 | } |
| 260 | |
| 261 | static inline int |
| 262 | re_assemble_14 (int as14) |
| 263 | { |
| 264 | return (( (as14 & 0x1fff) << 1) |
| 265 | | ((as14 & 0x2000) >> 13)); |
| 266 | } |
| 267 | |
| 268 | static inline int |
| 269 | re_assemble_16 (int as16) |
| 270 | { |
| 271 | int s, t; |
| 272 | |
| 273 | /* Unusual 16-bit encoding, for wide mode only. */ |
| 274 | t = (as16 << 1) & 0xffff; |
| 275 | s = (as16 & 0x8000); |
| 276 | return (t ^ s ^ (s >> 1)) | (s >> 15); |
| 277 | } |
| 278 | |
| 279 | static inline int |
| 280 | re_assemble_17 (int as17) |
| 281 | { |
| 282 | return (( (as17 & 0x10000) >> 16) |
| 283 | | ((as17 & 0x0f800) << (16 - 11)) |
| 284 | | ((as17 & 0x00400) >> (10 - 2)) |
| 285 | | ((as17 & 0x003ff) << (1 + 2))); |
| 286 | } |
| 287 | |
| 288 | static inline int |
| 289 | re_assemble_21 (int as21) |
| 290 | { |
| 291 | return (( (as21 & 0x100000) >> 20) |
| 292 | | ((as21 & 0x0ffe00) >> 8) |
| 293 | | ((as21 & 0x000180) << 7) |
| 294 | | ((as21 & 0x00007c) << 14) |
| 295 | | ((as21 & 0x000003) << 12)); |
| 296 | } |
| 297 | |
| 298 | static inline int |
| 299 | re_assemble_22 (int as22) |
| 300 | { |
| 301 | return (( (as22 & 0x200000) >> 21) |
| 302 | | ((as22 & 0x1f0000) << (21 - 16)) |
| 303 | | ((as22 & 0x00f800) << (16 - 11)) |
| 304 | | ((as22 & 0x000400) >> (10 - 2)) |
| 305 | | ((as22 & 0x0003ff) << (1 + 2))); |
| 306 | } |
| 307 | |
| 308 | |
| 309 | /* Handle field selectors for PA instructions. |
| 310 | The L and R (and LS, RS etc.) selectors are used in pairs to form a |
| 311 | full 32 bit address. eg. |
| 312 | |
| 313 | LDIL L'start,%r1 ; put left part into r1 |
| 314 | LDW R'start(%r1),%r2 ; add r1 and right part to form address |
| 315 | |
| 316 | This function returns sign extended values in all cases. |
| 317 | */ |
| 318 | |
| 319 | static inline bfd_signed_vma |
| 320 | hppa_field_adjust (bfd_vma sym_val, |
| 321 | bfd_signed_vma addend, |
| 322 | enum hppa_reloc_field_selector_type_alt r_field) |
| 323 | { |
| 324 | bfd_signed_vma value; |
| 325 | |
| 326 | value = sym_val + addend; |
| 327 | switch (r_field) |
| 328 | { |
| 329 | case e_fsel: |
| 330 | /* F: No change. */ |
| 331 | break; |
| 332 | |
| 333 | case e_nsel: |
| 334 | /* N: null selector. I don't really understand what this is all |
| 335 | about, but HP's documentation says "this indicates that zero |
| 336 | bits are to be used for the displacement on the instruction. |
| 337 | This fixup is used to identify three-instruction sequences to |
| 338 | access data (for importing shared library data)." */ |
| 339 | value = 0; |
| 340 | break; |
| 341 | |
| 342 | case e_lsel: |
| 343 | case e_nlsel: |
| 344 | /* L: Select top 21 bits. */ |
| 345 | value = value >> 11; |
| 346 | break; |
| 347 | |
| 348 | case e_rsel: |
| 349 | /* R: Select bottom 11 bits. */ |
| 350 | value = value & 0x7ff; |
| 351 | break; |
| 352 | |
| 353 | case e_lssel: |
| 354 | /* LS: Round to nearest multiple of 2048 then select top 21 bits. */ |
| 355 | value = value + 0x400; |
| 356 | value = value >> 11; |
| 357 | break; |
| 358 | |
| 359 | case e_rssel: |
| 360 | /* RS: Select bottom 11 bits for LS. |
| 361 | We need to return a value such that 2048 * LS'x + RS'x == x. |
| 362 | ie. RS'x = x - ((x + 0x400) & -0x800) |
| 363 | this is just a sign extension from bit 21. */ |
| 364 | value = ((value & 0x7ff) ^ 0x400) - 0x400; |
| 365 | break; |
| 366 | |
| 367 | case e_ldsel: |
| 368 | /* LD: Round to next multiple of 2048 then select top 21 bits. |
| 369 | Yes, if we are already on a multiple of 2048, we go up to the |
| 370 | next one. RD in this case will be -2048. */ |
| 371 | value = value + 0x800; |
| 372 | value = value >> 11; |
| 373 | break; |
| 374 | |
| 375 | case e_rdsel: |
| 376 | /* RD: Set bits 0-20 to one. */ |
| 377 | value = value | -0x800; |
| 378 | break; |
| 379 | |
| 380 | case e_lrsel: |
| 381 | case e_nlrsel: |
| 382 | /* LR: L with rounding of the addend to nearest 8k. */ |
| 383 | value = sym_val + ((addend + 0x1000) & -0x2000); |
| 384 | value = value >> 11; |
| 385 | break; |
| 386 | |
| 387 | case e_rrsel: |
| 388 | /* RR: R with rounding of the addend to nearest 8k. |
| 389 | We need to return a value such that 2048 * LR'x + RR'x == x |
| 390 | ie. RR'x = s+a - (s + (((a + 0x1000) & -0x2000) & -0x800)) |
| 391 | . = s+a - ((s & -0x800) + ((a + 0x1000) & -0x2000)) |
| 392 | . = (s & 0x7ff) + a - ((a + 0x1000) & -0x2000) */ |
| 393 | value = (sym_val & 0x7ff) + (((addend & 0x1fff) ^ 0x1000) - 0x1000); |
| 394 | break; |
| 395 | |
| 396 | default: |
| 397 | abort (); |
| 398 | } |
| 399 | return value; |
| 400 | } |
| 401 | |
| 402 | /* PA-RISC OPCODES */ |
| 403 | #define get_opcode(insn) (((insn) >> 26) & 0x3f) |
| 404 | |
| 405 | enum hppa_opcode_type |
| 406 | { |
| 407 | /* None of the opcodes in the first group generate relocs, so we |
| 408 | aren't too concerned about them. */ |
| 409 | OP_SYSOP = 0x00, |
| 410 | OP_MEMMNG = 0x01, |
| 411 | OP_ALU = 0x02, |
| 412 | OP_NDXMEM = 0x03, |
| 413 | OP_SPOP = 0x04, |
| 414 | OP_DIAG = 0x05, |
| 415 | OP_FMPYADD = 0x06, |
| 416 | OP_UNDEF07 = 0x07, |
| 417 | OP_COPRW = 0x09, |
| 418 | OP_COPRDW = 0x0b, |
| 419 | OP_COPR = 0x0c, |
| 420 | OP_FLOAT = 0x0e, |
| 421 | OP_PRDSPEC = 0x0f, |
| 422 | OP_UNDEF15 = 0x15, |
| 423 | OP_UNDEF1d = 0x1d, |
| 424 | OP_FMPYSUB = 0x26, |
| 425 | OP_FPFUSED = 0x2e, |
| 426 | OP_SHEXDP0 = 0x34, |
| 427 | OP_SHEXDP1 = 0x35, |
| 428 | OP_SHEXDP2 = 0x36, |
| 429 | OP_UNDEF37 = 0x37, |
| 430 | OP_SHEXDP3 = 0x3c, |
| 431 | OP_SHEXDP4 = 0x3d, |
| 432 | OP_MULTMED = 0x3e, |
| 433 | OP_UNDEF3f = 0x3f, |
| 434 | |
| 435 | OP_LDIL = 0x08, |
| 436 | OP_ADDIL = 0x0a, |
| 437 | |
| 438 | OP_LDO = 0x0d, |
| 439 | OP_LDB = 0x10, |
| 440 | OP_LDH = 0x11, |
| 441 | OP_LDW = 0x12, |
| 442 | OP_LDWM = 0x13, |
| 443 | OP_STB = 0x18, |
| 444 | OP_STH = 0x19, |
| 445 | OP_STW = 0x1a, |
| 446 | OP_STWM = 0x1b, |
| 447 | |
| 448 | OP_LDD = 0x14, |
| 449 | OP_STD = 0x1c, |
| 450 | |
| 451 | OP_FLDW = 0x16, |
| 452 | OP_LDWL = 0x17, |
| 453 | OP_FSTW = 0x1e, |
| 454 | OP_STWL = 0x1f, |
| 455 | |
| 456 | OP_COMBT = 0x20, |
| 457 | OP_COMIBT = 0x21, |
| 458 | OP_COMBF = 0x22, |
| 459 | OP_COMIBF = 0x23, |
| 460 | OP_CMPBDT = 0x27, |
| 461 | OP_ADDBT = 0x28, |
| 462 | OP_ADDIBT = 0x29, |
| 463 | OP_ADDBF = 0x2a, |
| 464 | OP_ADDIBF = 0x2b, |
| 465 | OP_CMPBDF = 0x2f, |
| 466 | OP_BVB = 0x30, |
| 467 | OP_BB = 0x31, |
| 468 | OP_MOVB = 0x32, |
| 469 | OP_MOVIB = 0x33, |
| 470 | OP_CMPIBD = 0x3b, |
| 471 | |
| 472 | OP_COMICLR = 0x24, |
| 473 | OP_SUBI = 0x25, |
| 474 | OP_ADDIT = 0x2c, |
| 475 | OP_ADDI = 0x2d, |
| 476 | |
| 477 | OP_BE = 0x38, |
| 478 | OP_BLE = 0x39, |
| 479 | OP_BL = 0x3a |
| 480 | }; |
| 481 | |
| 482 | |
| 483 | /* Insert VALUE into INSN using R_FORMAT to determine exactly what |
| 484 | bits to change. */ |
| 485 | |
| 486 | static inline int |
| 487 | hppa_rebuild_insn (int insn, int value, int r_format) |
| 488 | { |
| 489 | switch (r_format) |
| 490 | { |
| 491 | case 11: |
| 492 | return (insn & ~ 0x7ff) | low_sign_unext (value, 11); |
| 493 | |
| 494 | case 12: |
| 495 | return (insn & ~ 0x1ffd) | re_assemble_12 (value); |
| 496 | |
| 497 | |
| 498 | case 10: |
| 499 | return (insn & ~ 0x3ff1) | re_assemble_14 (value & -8); |
| 500 | |
| 501 | case -11: |
| 502 | return (insn & ~ 0x3ff9) | re_assemble_14 (value & -4); |
| 503 | |
| 504 | case 14: |
| 505 | return (insn & ~ 0x3fff) | re_assemble_14 (value); |
| 506 | |
| 507 | |
| 508 | case -10: |
| 509 | return (insn & ~ 0xfff1) | re_assemble_16 (value & -8); |
| 510 | |
| 511 | case -16: |
| 512 | return (insn & ~ 0xfff9) | re_assemble_16 (value & -4); |
| 513 | |
| 514 | case 16: |
| 515 | return (insn & ~ 0xffff) | re_assemble_16 (value); |
| 516 | |
| 517 | |
| 518 | case 17: |
| 519 | return (insn & ~ 0x1f1ffd) | re_assemble_17 (value); |
| 520 | |
| 521 | case 21: |
| 522 | return (insn & ~ 0x1fffff) | re_assemble_21 (value); |
| 523 | |
| 524 | case 22: |
| 525 | return (insn & ~ 0x3ff1ffd) | re_assemble_22 (value); |
| 526 | |
| 527 | case 32: |
| 528 | return value; |
| 529 | |
| 530 | default: |
| 531 | abort (); |
| 532 | } |
| 533 | return insn; |
| 534 | } |
| 535 | |
| 536 | #endif /* _LIBHPPA_H */ |
| 537 | /* Table of opcodes for the PA-RISC. |
| 538 | Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, |
| 539 | 2001, 2002, 2003, 2004, 2005 |
| 540 | Free Software Foundation, Inc. |
| 541 | |
| 542 | Contributed by the Center for Software Science at the |
| 543 | University of Utah (pa-gdb-bugs@cs.utah.edu). |
| 544 | |
| 545 | This file is part of GAS, the GNU Assembler, and GDB, the GNU disassembler. |
| 546 | |
| 547 | GAS/GDB is free software; you can redistribute it and/or modify |
| 548 | it under the terms of the GNU General Public License as published by |
| 549 | the Free Software Foundation; either version 1, or (at your option) |
| 550 | any later version. |
| 551 | |
| 552 | GAS/GDB is distributed in the hope that it will be useful, |
| 553 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 554 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 555 | GNU General Public License for more details. |
| 556 | |
| 557 | You should have received a copy of the GNU General Public License |
| 558 | along with GAS or GDB; see the file COPYING. If not, write to |
| 559 | the Free Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */ |
| 560 | |
| 561 | #if !defined(__STDC__) && !defined(const) |
| 562 | #define const |
| 563 | #endif |
| 564 | |
| 565 | /* |
| 566 | * Structure of an opcode table entry. |
| 567 | */ |
| 568 | |
| 569 | /* There are two kinds of delay slot nullification: normal which is |
| 570 | * controled by the nullification bit, and conditional, which depends |
| 571 | * on the direction of the branch and its success or failure. |
| 572 | * |
| 573 | * NONE is unfortunately #defined in the hiux system include files. |
| 574 | * #undef it away. |
| 575 | */ |
| 576 | #undef NONE |
| 577 | struct pa_opcode |
| 578 | { |
| 579 | const char *name; |
| 580 | unsigned long int match; /* Bits that must be set... */ |
| 581 | unsigned long int mask; /* ... in these bits. */ |
| 582 | char *args; |
| 583 | enum pa_arch arch; |
| 584 | char flags; |
| 585 | }; |
| 586 | |
| 587 | /* Enables strict matching. Opcodes with match errors are skipped |
| 588 | when this bit is set. */ |
| 589 | #define FLAG_STRICT 0x1 |
| 590 | |
| 591 | /* |
| 592 | All hppa opcodes are 32 bits. |
| 593 | |
| 594 | The match component is a mask saying which bits must match a |
| 595 | particular opcode in order for an instruction to be an instance |
| 596 | of that opcode. |
| 597 | |
| 598 | The args component is a string containing one character for each operand of |
| 599 | the instruction. Characters used as a prefix allow any second character to |
| 600 | be used without conflicting with the main operand characters. |
| 601 | |
| 602 | Bit positions in this description follow HP usage of lsb = 31, |
| 603 | "at" is lsb of field. |
| 604 | |
| 605 | In the args field, the following characters must match exactly: |
| 606 | |
| 607 | '+,() ' |
| 608 | |
| 609 | In the args field, the following characters are unused: |
| 610 | |
| 611 | ' " - / 34 6789:; ' |
| 612 | '@ C M [\] ' |
| 613 | '` e g } ' |
| 614 | |
| 615 | Here are all the characters: |
| 616 | |
| 617 | ' !"#$%&'()*+-,./0123456789:;<=>?' |
| 618 | '@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_' |
| 619 | '`abcdefghijklmnopqrstuvwxyz{|}~ ' |
| 620 | |
| 621 | Kinds of operands: |
| 622 | x integer register field at 15. |
| 623 | b integer register field at 10. |
| 624 | t integer register field at 31. |
| 625 | a integer register field at 10 and 15 (for PERMH) |
| 626 | 5 5 bit immediate at 15. |
| 627 | s 2 bit space specifier at 17. |
| 628 | S 3 bit space specifier at 18. |
| 629 | V 5 bit immediate value at 31 |
| 630 | i 11 bit immediate value at 31 |
| 631 | j 14 bit immediate value at 31 |
| 632 | k 21 bit immediate value at 31 |
| 633 | l 16 bit immediate value at 31 (wide mode only, unusual encoding). |
| 634 | n nullification for branch instructions |
| 635 | N nullification for spop and copr instructions |
| 636 | w 12 bit branch displacement |
| 637 | W 17 bit branch displacement (PC relative) |
| 638 | X 22 bit branch displacement (PC relative) |
| 639 | z 17 bit branch displacement (just a number, not an address) |
| 640 | |
| 641 | Also these: |
| 642 | |
| 643 | . 2 bit shift amount at 25 |
| 644 | * 4 bit shift amount at 25 |
| 645 | p 5 bit shift count at 26 (to support the SHD instruction) encoded as |
| 646 | 31-p |
| 647 | ~ 6 bit shift count at 20,22:26 encoded as 63-~. |
| 648 | P 5 bit bit position at 26 |
| 649 | q 6 bit bit position at 20,22:26 |
| 650 | T 5 bit field length at 31 (encoded as 32-T) |
| 651 | % 6 bit field length at 23,27:31 (variable extract/deposit) |
| 652 | | 6 bit field length at 19,27:31 (fixed extract/deposit) |
| 653 | A 13 bit immediate at 18 (to support the BREAK instruction) |
| 654 | ^ like b, but describes a control register |
| 655 | ! sar (cr11) register |
| 656 | D 26 bit immediate at 31 (to support the DIAG instruction) |
| 657 | $ 9 bit immediate at 28 (to support POPBTS) |
| 658 | |
| 659 | v 3 bit Special Function Unit identifier at 25 |
| 660 | O 20 bit Special Function Unit operation split between 15 bits at 20 |
| 661 | and 5 bits at 31 |
| 662 | o 15 bit Special Function Unit operation at 20 |
| 663 | 2 22 bit Special Function Unit operation split between 17 bits at 20 |
| 664 | and 5 bits at 31 |
| 665 | 1 15 bit Special Function Unit operation split between 10 bits at 20 |
| 666 | and 5 bits at 31 |
| 667 | 0 10 bit Special Function Unit operation split between 5 bits at 20 |
| 668 | and 5 bits at 31 |
| 669 | u 3 bit coprocessor unit identifier at 25 |
| 670 | F Source Floating Point Operand Format Completer encoded 2 bits at 20 |
| 671 | I Source Floating Point Operand Format Completer encoded 1 bits at 20 |
| 672 | (for 0xe format FP instructions) |
| 673 | G Destination Floating Point Operand Format Completer encoded 2 bits at 18 |
| 674 | H Floating Point Operand Format at 26 for 'fmpyadd' and 'fmpysub' |
| 675 | (very similar to 'F') |
| 676 | |
| 677 | r 5 bit immediate value at 31 (for the break instruction) |
| 678 | (very similar to V above, except the value is unsigned instead of |
| 679 | low_sign_ext) |
| 680 | R 5 bit immediate value at 15 (for the ssm, rsm, probei instructions) |
| 681 | (same as r above, except the value is in a different location) |
| 682 | U 10 bit immediate value at 15 (for SSM, RSM on pa2.0) |
| 683 | Q 5 bit immediate value at 10 (a bit position specified in |
| 684 | the bb instruction. It's the same as r above, except the |
| 685 | value is in a different location) |
| 686 | B 5 bit immediate value at 10 (a bit position specified in |
| 687 | the bb instruction. Similar to Q, but 64 bit handling is |
| 688 | different. |
| 689 | Z %r1 -- implicit target of addil instruction. |
| 690 | L ,%r2 completer for new syntax branch |
| 691 | { Source format completer for fcnv |
| 692 | _ Destination format completer for fcnv |
| 693 | h cbit for fcmp |
| 694 | = gfx tests for ftest |
| 695 | d 14 bit offset for single precision FP long load/store. |
| 696 | # 14 bit offset for double precision FP load long/store. |
| 697 | J Yet another 14 bit offset for load/store with ma,mb completers. |
| 698 | K Yet another 14 bit offset for load/store with ma,mb completers. |
| 699 | y 16 bit offset for word aligned load/store (PA2.0 wide). |
| 700 | & 16 bit offset for dword aligned load/store (PA2.0 wide). |
| 701 | < 16 bit offset for load/store with ma,mb completers (PA2.0 wide). |
| 702 | > 16 bit offset for load/store with ma,mb completers (PA2.0 wide). |
| 703 | Y %sr0,%r31 -- implicit target of be,l instruction. |
| 704 | @ implicit immediate value of 0 |
| 705 | |
| 706 | Completer operands all have 'c' as the prefix: |
| 707 | |
| 708 | cx indexed load and store completer. |
| 709 | cX indexed load and store completer. Like cx, but emits a space |
| 710 | after in disassembler. |
| 711 | cm short load and store completer. |
| 712 | cM short load and store completer. Like cm, but emits a space |
| 713 | after in disassembler. |
| 714 | cq long load and store completer (like cm, but inserted into a |
| 715 | different location in the target instruction). |
| 716 | cs store bytes short completer. |
| 717 | cA store bytes short completer. Like cs, but emits a space |
| 718 | after in disassembler. |
| 719 | ce long load/store completer for LDW/STW with a different encoding |
| 720 | than the others |
| 721 | cc load cache control hint |
| 722 | cd load and clear cache control hint |
| 723 | cC store cache control hint |
| 724 | co ordered access |
| 725 | |
| 726 | cp branch link and push completer |
| 727 | cP branch pop completer |
| 728 | cl branch link completer |
| 729 | cg branch gate completer |
| 730 | |
| 731 | cw read/write completer for PROBE |
| 732 | cW wide completer for MFCTL |
| 733 | cL local processor completer for cache control |
| 734 | cZ System Control Completer (to support LPA, LHA, etc.) |
| 735 | |
| 736 | ci correction completer for DCOR |
| 737 | ca add completer |
| 738 | cy 32 bit add carry completer |
| 739 | cY 64 bit add carry completer |
| 740 | cv signed overflow trap completer |
| 741 | ct trap on condition completer for ADDI, SUB |
| 742 | cT trap on condition completer for UADDCM |
| 743 | cb 32 bit borrow completer for SUB |
| 744 | cB 64 bit borrow completer for SUB |
| 745 | |
| 746 | ch left/right half completer |
| 747 | cH signed/unsigned saturation completer |
| 748 | cS signed/unsigned completer at 21 |
| 749 | cz zero/sign extension completer. |
| 750 | c* permutation completer |
| 751 | |
| 752 | Condition operands all have '?' as the prefix: |
| 753 | |
| 754 | ?f Floating point compare conditions (encoded as 5 bits at 31) |
| 755 | |
| 756 | ?a add conditions |
| 757 | ?A 64 bit add conditions |
| 758 | ?@ add branch conditions followed by nullify |
| 759 | ?d non-negated add branch conditions |
| 760 | ?D negated add branch conditions |
| 761 | ?w wide mode non-negated add branch conditions |
| 762 | ?W wide mode negated add branch conditions |
| 763 | |
| 764 | ?s compare/subtract conditions |
| 765 | ?S 64 bit compare/subtract conditions |
| 766 | ?t non-negated compare and branch conditions |
| 767 | ?n 32 bit compare and branch conditions followed by nullify |
| 768 | ?N 64 bit compare and branch conditions followed by nullify |
| 769 | ?Q 64 bit compare and branch conditions for CMPIB instruction |
| 770 | |
| 771 | ?l logical conditions |
| 772 | ?L 64 bit logical conditions |
| 773 | |
| 774 | ?b branch on bit conditions |
| 775 | ?B 64 bit branch on bit conditions |
| 776 | |
| 777 | ?x shift/extract/deposit conditions |
| 778 | ?X 64 bit shift/extract/deposit conditions |
| 779 | ?y shift/extract/deposit conditions followed by nullify for conditional |
| 780 | branches |
| 781 | |
| 782 | ?u unit conditions |
| 783 | ?U 64 bit unit conditions |
| 784 | |
| 785 | Floating point registers all have 'f' as a prefix: |
| 786 | |
| 787 | ft target register at 31 |
| 788 | fT target register with L/R halves at 31 |
| 789 | fa operand 1 register at 10 |
| 790 | fA operand 1 register with L/R halves at 10 |
| 791 | fX Same as fA, except prints a space before register during disasm |
| 792 | fb operand 2 register at 15 |
| 793 | fB operand 2 register with L/R halves at 15 |
| 794 | fC operand 3 register with L/R halves at 16:18,21:23 |
| 795 | fe Like fT, but encoding is different. |
| 796 | fE Same as fe, except prints a space before register during disasm. |
| 797 | fx target register at 15 (only for PA 2.0 long format FLDD/FSTD). |
| 798 | |
| 799 | Float registers for fmpyadd and fmpysub: |
| 800 | |
| 801 | fi mult operand 1 register at 10 |
| 802 | fj mult operand 2 register at 15 |
| 803 | fk mult target register at 20 |
| 804 | fl add/sub operand register at 25 |
| 805 | fm add/sub target register at 31 |
| 806 | |
| 807 | */ |
| 808 | |
| 809 | |
| 810 | #if 0 |
| 811 | /* List of characters not to put a space after. Note that |
| 812 | "," is included, as the "spopN" operations use literal |
| 813 | commas in their completer sections. */ |
| 814 | static const char *const completer_chars = ",CcY<>?!@+&U~FfGHINnOoZMadu|/=0123%e$m}"; |
| 815 | #endif |
| 816 | |
| 817 | /* The order of the opcodes in this table is significant: |
| 818 | |
| 819 | * The assembler requires that all instances of the same mnemonic be |
| 820 | consecutive. If they aren't, the assembler will bomb at runtime. |
| 821 | |
| 822 | * Immediate fields use pa_get_absolute_expression to parse the |
| 823 | string. It will generate a "bad expression" error if passed |
| 824 | a register name. Thus, register index variants of an opcode |
| 825 | need to precede immediate variants. |
| 826 | |
| 827 | * The disassembler does not care about the order of the opcodes |
| 828 | except in cases where implicit addressing is used. |
| 829 | |
| 830 | Here are the rules for ordering the opcodes of a mnemonic: |
| 831 | |
| 832 | 1) Opcodes with FLAG_STRICT should precede opcodes without |
| 833 | FLAG_STRICT. |
| 834 | |
| 835 | 2) Opcodes with FLAG_STRICT should be ordered as follows: |
| 836 | register index opcodes, short immediate opcodes, and finally |
| 837 | long immediate opcodes. When both pa10 and pa11 variants |
| 838 | of the same opcode are available, the pa10 opcode should |
| 839 | come first for correct architectural promotion. |
| 840 | |
| 841 | 3) When implicit addressing is available for an opcode, the |
| 842 | implicit opcode should precede the explicit opcode. |
| 843 | |
| 844 | 4) Opcodes without FLAG_STRICT should be ordered as follows: |
| 845 | register index opcodes, long immediate opcodes, and finally |
| 846 | short immediate opcodes. */ |
| 847 | |
| 848 | static const struct pa_opcode pa_opcodes[] = |
| 849 | { |
| 850 | |
| 851 | /* Pseudo-instructions. */ |
| 852 | |
| 853 | { "ldi", 0x34000000, 0xffe00000, "l,x", pa20w, 0},/* ldo val(r0),r */ |
| 854 | { "ldi", 0x34000000, 0xffe0c000, "j,x", pa10, 0},/* ldo val(r0),r */ |
| 855 | |
| 856 | { "cmpib", 0xec000000, 0xfc000000, "?Qn5,b,w", pa20, FLAG_STRICT}, |
| 857 | { "cmpib", 0x84000000, 0xf4000000, "?nn5,b,w", pa10, FLAG_STRICT}, |
| 858 | { "comib", 0x84000000, 0xfc000000, "?nn5,b,w", pa10, 0}, /* comib{tf}*/ |
| 859 | /* This entry is for the disassembler only. It will never be used by |
| 860 | assembler. */ |
| 861 | { "comib", 0x8c000000, 0xfc000000, "?nn5,b,w", pa10, 0}, /* comib{tf}*/ |
| 862 | { "cmpb", 0x9c000000, 0xdc000000, "?Nnx,b,w", pa20, FLAG_STRICT}, |
| 863 | { "cmpb", 0x80000000, 0xf4000000, "?nnx,b,w", pa10, FLAG_STRICT}, |
| 864 | { "comb", 0x80000000, 0xfc000000, "?nnx,b,w", pa10, 0}, /* comb{tf} */ |
| 865 | /* This entry is for the disassembler only. It will never be used by |
| 866 | assembler. */ |
| 867 | { "comb", 0x88000000, 0xfc000000, "?nnx,b,w", pa10, 0}, /* comb{tf} */ |
| 868 | { "addb", 0xa0000000, 0xf4000000, "?Wnx,b,w", pa20w, FLAG_STRICT}, |
| 869 | { "addb", 0xa0000000, 0xfc000000, "?@nx,b,w", pa10, 0}, /* addb{tf} */ |
| 870 | /* This entry is for the disassembler only. It will never be used by |
| 871 | assembler. */ |
| 872 | { "addb", 0xa8000000, 0xfc000000, "?@nx,b,w", pa10, 0}, |
| 873 | { "addib", 0xa4000000, 0xf4000000, "?Wn5,b,w", pa20w, FLAG_STRICT}, |
| 874 | { "addib", 0xa4000000, 0xfc000000, "?@n5,b,w", pa10, 0}, /* addib{tf}*/ |
| 875 | /* This entry is for the disassembler only. It will never be used by |
| 876 | assembler. */ |
| 877 | { "addib", 0xac000000, 0xfc000000, "?@n5,b,w", pa10, 0}, /* addib{tf}*/ |
| 878 | { "nop", 0x08000240, 0xffffffff, "", pa10, 0}, /* or 0,0,0 */ |
| 879 | { "copy", 0x08000240, 0xffe0ffe0, "x,t", pa10, 0}, /* or r,0,t */ |
| 880 | { "mtsar", 0x01601840, 0xffe0ffff, "x", pa10, 0}, /* mtctl r,cr11 */ |
| 881 | |
| 882 | /* Loads and Stores for integer registers. */ |
| 883 | |
| 884 | { "ldd", 0x0c0000c0, 0xfc00d3c0, "cxccx(b),t", pa20, FLAG_STRICT}, |
| 885 | { "ldd", 0x0c0000c0, 0xfc0013c0, "cxccx(s,b),t", pa20, FLAG_STRICT}, |
| 886 | { "ldd", 0x0c0010e0, 0xfc1ff3e0, "cocc@(b),t", pa20, FLAG_STRICT}, |
| 887 | { "ldd", 0x0c0010e0, 0xfc1f33e0, "cocc@(s,b),t", pa20, FLAG_STRICT}, |
| 888 | { "ldd", 0x0c0010c0, 0xfc00d3c0, "cmcc5(b),t", pa20, FLAG_STRICT}, |
| 889 | { "ldd", 0x0c0010c0, 0xfc0013c0, "cmcc5(s,b),t", pa20, FLAG_STRICT}, |
| 890 | { "ldd", 0x50000000, 0xfc000002, "cq&(b),x", pa20w, FLAG_STRICT}, |
| 891 | { "ldd", 0x50000000, 0xfc00c002, "cq#(b),x", pa20, FLAG_STRICT}, |
| 892 | { "ldd", 0x50000000, 0xfc000002, "cq#(s,b),x", pa20, FLAG_STRICT}, |
| 893 | { "ldw", 0x0c000080, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 894 | { "ldw", 0x0c000080, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 895 | { "ldw", 0x0c000080, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 896 | { "ldw", 0x0c000080, 0xfc0013c0, "cxccx(s,b),t", pa11, FLAG_STRICT}, |
| 897 | { "ldw", 0x0c0010a0, 0xfc1ff3e0, "cocc@(b),t", pa20, FLAG_STRICT}, |
| 898 | { "ldw", 0x0c0010a0, 0xfc1f33e0, "cocc@(s,b),t", pa20, FLAG_STRICT}, |
| 899 | { "ldw", 0x0c001080, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 900 | { "ldw", 0x0c001080, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 901 | { "ldw", 0x0c001080, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 902 | { "ldw", 0x0c001080, 0xfc0013c0, "cmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 903 | { "ldw", 0x4c000000, 0xfc000000, "ce<(b),x", pa20w, FLAG_STRICT}, |
| 904 | { "ldw", 0x5c000004, 0xfc000006, "ce>(b),x", pa20w, FLAG_STRICT}, |
| 905 | { "ldw", 0x48000000, 0xfc000000, "l(b),x", pa20w, FLAG_STRICT}, |
| 906 | { "ldw", 0x5c000004, 0xfc00c006, "ceK(b),x", pa20, FLAG_STRICT}, |
| 907 | { "ldw", 0x5c000004, 0xfc000006, "ceK(s,b),x", pa20, FLAG_STRICT}, |
| 908 | { "ldw", 0x4c000000, 0xfc00c000, "ceJ(b),x", pa10, FLAG_STRICT}, |
| 909 | { "ldw", 0x4c000000, 0xfc000000, "ceJ(s,b),x", pa10, FLAG_STRICT}, |
| 910 | { "ldw", 0x48000000, 0xfc00c000, "j(b),x", pa10, 0}, |
| 911 | { "ldw", 0x48000000, 0xfc000000, "j(s,b),x", pa10, 0}, |
| 912 | { "ldh", 0x0c000040, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 913 | { "ldh", 0x0c000040, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 914 | { "ldh", 0x0c000040, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 915 | { "ldh", 0x0c000040, 0xfc0013c0, "cxccx(s,b),t", pa11, FLAG_STRICT}, |
| 916 | { "ldh", 0x0c001060, 0xfc1ff3e0, "cocc@(b),t", pa20, FLAG_STRICT}, |
| 917 | { "ldh", 0x0c001060, 0xfc1f33e0, "cocc@(s,b),t", pa20, FLAG_STRICT}, |
| 918 | { "ldh", 0x0c001040, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 919 | { "ldh", 0x0c001040, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 920 | { "ldh", 0x0c001040, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 921 | { "ldh", 0x0c001040, 0xfc0013c0, "cmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 922 | { "ldh", 0x44000000, 0xfc000000, "l(b),x", pa20w, FLAG_STRICT}, |
| 923 | { "ldh", 0x44000000, 0xfc00c000, "j(b),x", pa10, 0}, |
| 924 | { "ldh", 0x44000000, 0xfc000000, "j(s,b),x", pa10, 0}, |
| 925 | { "ldb", 0x0c000000, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 926 | { "ldb", 0x0c000000, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 927 | { "ldb", 0x0c000000, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 928 | { "ldb", 0x0c000000, 0xfc0013c0, "cxccx(s,b),t", pa11, FLAG_STRICT}, |
| 929 | { "ldb", 0x0c001020, 0xfc1ff3e0, "cocc@(b),t", pa20, FLAG_STRICT}, |
| 930 | { "ldb", 0x0c001020, 0xfc1f33e0, "cocc@(s,b),t", pa20, FLAG_STRICT}, |
| 931 | { "ldb", 0x0c001000, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 932 | { "ldb", 0x0c001000, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 933 | { "ldb", 0x0c001000, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 934 | { "ldb", 0x0c001000, 0xfc0013c0, "cmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 935 | { "ldb", 0x40000000, 0xfc000000, "l(b),x", pa20w, FLAG_STRICT}, |
| 936 | { "ldb", 0x40000000, 0xfc00c000, "j(b),x", pa10, 0}, |
| 937 | { "ldb", 0x40000000, 0xfc000000, "j(s,b),x", pa10, 0}, |
| 938 | { "std", 0x0c0012e0, 0xfc00f3ff, "cocCx,@(b)", pa20, FLAG_STRICT}, |
| 939 | { "std", 0x0c0012e0, 0xfc0033ff, "cocCx,@(s,b)", pa20, FLAG_STRICT}, |
| 940 | { "std", 0x0c0012c0, 0xfc00d3c0, "cmcCx,V(b)", pa20, FLAG_STRICT}, |
| 941 | { "std", 0x0c0012c0, 0xfc0013c0, "cmcCx,V(s,b)", pa20, FLAG_STRICT}, |
| 942 | { "std", 0x70000000, 0xfc000002, "cqx,&(b)", pa20w, FLAG_STRICT}, |
| 943 | { "std", 0x70000000, 0xfc00c002, "cqx,#(b)", pa20, FLAG_STRICT}, |
| 944 | { "std", 0x70000000, 0xfc000002, "cqx,#(s,b)", pa20, FLAG_STRICT}, |
| 945 | { "stw", 0x0c0012a0, 0xfc00f3ff, "cocCx,@(b)", pa20, FLAG_STRICT}, |
| 946 | { "stw", 0x0c0012a0, 0xfc0033ff, "cocCx,@(s,b)", pa20, FLAG_STRICT}, |
| 947 | { "stw", 0x0c001280, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 948 | { "stw", 0x0c001280, 0xfc001fc0, "cMx,V(s,b)", pa10, FLAG_STRICT}, |
| 949 | { "stw", 0x0c001280, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 950 | { "stw", 0x0c001280, 0xfc0013c0, "cmcCx,V(s,b)", pa11, FLAG_STRICT}, |
| 951 | { "stw", 0x6c000000, 0xfc000000, "cex,<(b)", pa20w, FLAG_STRICT}, |
| 952 | { "stw", 0x7c000004, 0xfc000006, "cex,>(b)", pa20w, FLAG_STRICT}, |
| 953 | { "stw", 0x68000000, 0xfc000000, "x,l(b)", pa20w, FLAG_STRICT}, |
| 954 | { "stw", 0x7c000004, 0xfc00c006, "cex,K(b)", pa20, FLAG_STRICT}, |
| 955 | { "stw", 0x7c000004, 0xfc000006, "cex,K(s,b)", pa20, FLAG_STRICT}, |
| 956 | { "stw", 0x6c000000, 0xfc00c000, "cex,J(b)", pa10, FLAG_STRICT}, |
| 957 | { "stw", 0x6c000000, 0xfc000000, "cex,J(s,b)", pa10, FLAG_STRICT}, |
| 958 | { "stw", 0x68000000, 0xfc00c000, "x,j(b)", pa10, 0}, |
| 959 | { "stw", 0x68000000, 0xfc000000, "x,j(s,b)", pa10, 0}, |
| 960 | { "sth", 0x0c001260, 0xfc00f3ff, "cocCx,@(b)", pa20, FLAG_STRICT}, |
| 961 | { "sth", 0x0c001260, 0xfc0033ff, "cocCx,@(s,b)", pa20, FLAG_STRICT}, |
| 962 | { "sth", 0x0c001240, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 963 | { "sth", 0x0c001240, 0xfc001fc0, "cMx,V(s,b)", pa10, FLAG_STRICT}, |
| 964 | { "sth", 0x0c001240, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 965 | { "sth", 0x0c001240, 0xfc0013c0, "cmcCx,V(s,b)", pa11, FLAG_STRICT}, |
| 966 | { "sth", 0x64000000, 0xfc000000, "x,l(b)", pa20w, FLAG_STRICT}, |
| 967 | { "sth", 0x64000000, 0xfc00c000, "x,j(b)", pa10, 0}, |
| 968 | { "sth", 0x64000000, 0xfc000000, "x,j(s,b)", pa10, 0}, |
| 969 | { "stb", 0x0c001220, 0xfc00f3ff, "cocCx,@(b)", pa20, FLAG_STRICT}, |
| 970 | { "stb", 0x0c001220, 0xfc0033ff, "cocCx,@(s,b)", pa20, FLAG_STRICT}, |
| 971 | { "stb", 0x0c001200, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 972 | { "stb", 0x0c001200, 0xfc001fc0, "cMx,V(s,b)", pa10, FLAG_STRICT}, |
| 973 | { "stb", 0x0c001200, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 974 | { "stb", 0x0c001200, 0xfc0013c0, "cmcCx,V(s,b)", pa11, FLAG_STRICT}, |
| 975 | { "stb", 0x60000000, 0xfc000000, "x,l(b)", pa20w, FLAG_STRICT}, |
| 976 | { "stb", 0x60000000, 0xfc00c000, "x,j(b)", pa10, 0}, |
| 977 | { "stb", 0x60000000, 0xfc000000, "x,j(s,b)", pa10, 0}, |
| 978 | { "ldwm", 0x4c000000, 0xfc00c000, "j(b),x", pa10, 0}, |
| 979 | { "ldwm", 0x4c000000, 0xfc000000, "j(s,b),x", pa10, 0}, |
| 980 | { "stwm", 0x6c000000, 0xfc00c000, "x,j(b)", pa10, 0}, |
| 981 | { "stwm", 0x6c000000, 0xfc000000, "x,j(s,b)", pa10, 0}, |
| 982 | { "ldwx", 0x0c000080, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 983 | { "ldwx", 0x0c000080, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 984 | { "ldwx", 0x0c000080, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 985 | { "ldwx", 0x0c000080, 0xfc0013c0, "cxccx(s,b),t", pa11, FLAG_STRICT}, |
| 986 | { "ldwx", 0x0c000080, 0xfc00dfc0, "cXx(b),t", pa10, 0}, |
| 987 | { "ldwx", 0x0c000080, 0xfc001fc0, "cXx(s,b),t", pa10, 0}, |
| 988 | { "ldhx", 0x0c000040, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 989 | { "ldhx", 0x0c000040, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 990 | { "ldhx", 0x0c000040, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 991 | { "ldhx", 0x0c000040, 0xfc0013c0, "cxccx(s,b),t", pa11, FLAG_STRICT}, |
| 992 | { "ldhx", 0x0c000040, 0xfc00dfc0, "cXx(b),t", pa10, 0}, |
| 993 | { "ldhx", 0x0c000040, 0xfc001fc0, "cXx(s,b),t", pa10, 0}, |
| 994 | { "ldbx", 0x0c000000, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 995 | { "ldbx", 0x0c000000, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 996 | { "ldbx", 0x0c000000, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 997 | { "ldbx", 0x0c000000, 0xfc0013c0, "cxccx(s,b),t", pa11, FLAG_STRICT}, |
| 998 | { "ldbx", 0x0c000000, 0xfc00dfc0, "cXx(b),t", pa10, 0}, |
| 999 | { "ldbx", 0x0c000000, 0xfc001fc0, "cXx(s,b),t", pa10, 0}, |
| 1000 | { "ldwa", 0x0c000180, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 1001 | { "ldwa", 0x0c000180, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 1002 | { "ldwa", 0x0c0011a0, 0xfc1ff3e0, "cocc@(b),t", pa20, FLAG_STRICT}, |
| 1003 | { "ldwa", 0x0c001180, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 1004 | { "ldwa", 0x0c001180, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 1005 | { "ldcw", 0x0c0001c0, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 1006 | { "ldcw", 0x0c0001c0, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 1007 | { "ldcw", 0x0c0001c0, 0xfc00d3c0, "cxcdx(b),t", pa11, FLAG_STRICT}, |
| 1008 | { "ldcw", 0x0c0001c0, 0xfc0013c0, "cxcdx(s,b),t", pa11, FLAG_STRICT}, |
| 1009 | { "ldcw", 0x0c0011c0, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 1010 | { "ldcw", 0x0c0011c0, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 1011 | { "ldcw", 0x0c0011c0, 0xfc00d3c0, "cmcd5(b),t", pa11, FLAG_STRICT}, |
| 1012 | { "ldcw", 0x0c0011c0, 0xfc0013c0, "cmcd5(s,b),t", pa11, FLAG_STRICT}, |
| 1013 | { "stwa", 0x0c0013a0, 0xfc00d3ff, "cocCx,@(b)", pa20, FLAG_STRICT}, |
| 1014 | { "stwa", 0x0c001380, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 1015 | { "stwa", 0x0c001380, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 1016 | { "stby", 0x0c001300, 0xfc00dfc0, "cAx,V(b)", pa10, FLAG_STRICT}, |
| 1017 | { "stby", 0x0c001300, 0xfc001fc0, "cAx,V(s,b)", pa10, FLAG_STRICT}, |
| 1018 | { "stby", 0x0c001300, 0xfc00d3c0, "cscCx,V(b)", pa11, FLAG_STRICT}, |
| 1019 | { "stby", 0x0c001300, 0xfc0013c0, "cscCx,V(s,b)", pa11, FLAG_STRICT}, |
| 1020 | { "ldda", 0x0c000100, 0xfc00d3c0, "cxccx(b),t", pa20, FLAG_STRICT}, |
| 1021 | { "ldda", 0x0c001120, 0xfc1ff3e0, "cocc@(b),t", pa20, FLAG_STRICT}, |
| 1022 | { "ldda", 0x0c001100, 0xfc00d3c0, "cmcc5(b),t", pa20, FLAG_STRICT}, |
| 1023 | { "ldcd", 0x0c000140, 0xfc00d3c0, "cxcdx(b),t", pa20, FLAG_STRICT}, |
| 1024 | { "ldcd", 0x0c000140, 0xfc0013c0, "cxcdx(s,b),t", pa20, FLAG_STRICT}, |
| 1025 | { "ldcd", 0x0c001140, 0xfc00d3c0, "cmcd5(b),t", pa20, FLAG_STRICT}, |
| 1026 | { "ldcd", 0x0c001140, 0xfc0013c0, "cmcd5(s,b),t", pa20, FLAG_STRICT}, |
| 1027 | { "stda", 0x0c0013e0, 0xfc00f3ff, "cocCx,@(b)", pa20, FLAG_STRICT}, |
| 1028 | { "stda", 0x0c0013c0, 0xfc00d3c0, "cmcCx,V(b)", pa20, FLAG_STRICT}, |
| 1029 | { "ldwax", 0x0c000180, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 1030 | { "ldwax", 0x0c000180, 0xfc00d3c0, "cxccx(b),t", pa11, FLAG_STRICT}, |
| 1031 | { "ldwax", 0x0c000180, 0xfc00dfc0, "cXx(b),t", pa10, 0}, |
| 1032 | { "ldcwx", 0x0c0001c0, 0xfc00dfc0, "cXx(b),t", pa10, FLAG_STRICT}, |
| 1033 | { "ldcwx", 0x0c0001c0, 0xfc001fc0, "cXx(s,b),t", pa10, FLAG_STRICT}, |
| 1034 | { "ldcwx", 0x0c0001c0, 0xfc00d3c0, "cxcdx(b),t", pa11, FLAG_STRICT}, |
| 1035 | { "ldcwx", 0x0c0001c0, 0xfc0013c0, "cxcdx(s,b),t", pa11, FLAG_STRICT}, |
| 1036 | { "ldcwx", 0x0c0001c0, 0xfc00dfc0, "cXx(b),t", pa10, 0}, |
| 1037 | { "ldcwx", 0x0c0001c0, 0xfc001fc0, "cXx(s,b),t", pa10, 0}, |
| 1038 | { "ldws", 0x0c001080, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 1039 | { "ldws", 0x0c001080, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 1040 | { "ldws", 0x0c001080, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 1041 | { "ldws", 0x0c001080, 0xfc0013c0, "cmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 1042 | { "ldws", 0x0c001080, 0xfc00dfc0, "cM5(b),t", pa10, 0}, |
| 1043 | { "ldws", 0x0c001080, 0xfc001fc0, "cM5(s,b),t", pa10, 0}, |
| 1044 | { "ldhs", 0x0c001040, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 1045 | { "ldhs", 0x0c001040, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 1046 | { "ldhs", 0x0c001040, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 1047 | { "ldhs", 0x0c001040, 0xfc0013c0, "cmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 1048 | { "ldhs", 0x0c001040, 0xfc00dfc0, "cM5(b),t", pa10, 0}, |
| 1049 | { "ldhs", 0x0c001040, 0xfc001fc0, "cM5(s,b),t", pa10, 0}, |
| 1050 | { "ldbs", 0x0c001000, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 1051 | { "ldbs", 0x0c001000, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 1052 | { "ldbs", 0x0c001000, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 1053 | { "ldbs", 0x0c001000, 0xfc0013c0, "cmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 1054 | { "ldbs", 0x0c001000, 0xfc00dfc0, "cM5(b),t", pa10, 0}, |
| 1055 | { "ldbs", 0x0c001000, 0xfc001fc0, "cM5(s,b),t", pa10, 0}, |
| 1056 | { "ldwas", 0x0c001180, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 1057 | { "ldwas", 0x0c001180, 0xfc00d3c0, "cmcc5(b),t", pa11, FLAG_STRICT}, |
| 1058 | { "ldwas", 0x0c001180, 0xfc00dfc0, "cM5(b),t", pa10, 0}, |
| 1059 | { "ldcws", 0x0c0011c0, 0xfc00dfc0, "cM5(b),t", pa10, FLAG_STRICT}, |
| 1060 | { "ldcws", 0x0c0011c0, 0xfc001fc0, "cM5(s,b),t", pa10, FLAG_STRICT}, |
| 1061 | { "ldcws", 0x0c0011c0, 0xfc00d3c0, "cmcd5(b),t", pa11, FLAG_STRICT}, |
| 1062 | { "ldcws", 0x0c0011c0, 0xfc0013c0, "cmcd5(s,b),t", pa11, FLAG_STRICT}, |
| 1063 | { "ldcws", 0x0c0011c0, 0xfc00dfc0, "cM5(b),t", pa10, 0}, |
| 1064 | { "ldcws", 0x0c0011c0, 0xfc001fc0, "cM5(s,b),t", pa10, 0}, |
| 1065 | { "stws", 0x0c001280, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 1066 | { "stws", 0x0c001280, 0xfc001fc0, "cMx,V(s,b)", pa10, FLAG_STRICT}, |
| 1067 | { "stws", 0x0c001280, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 1068 | { "stws", 0x0c001280, 0xfc0013c0, "cmcCx,V(s,b)", pa11, FLAG_STRICT}, |
| 1069 | { "stws", 0x0c001280, 0xfc00dfc0, "cMx,V(b)", pa10, 0}, |
| 1070 | { "stws", 0x0c001280, 0xfc001fc0, "cMx,V(s,b)", pa10, 0}, |
| 1071 | { "sths", 0x0c001240, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 1072 | { "sths", 0x0c001240, 0xfc001fc0, "cMx,V(s,b)", pa10, FLAG_STRICT}, |
| 1073 | { "sths", 0x0c001240, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 1074 | { "sths", 0x0c001240, 0xfc0013c0, "cmcCx,V(s,b)", pa11, FLAG_STRICT}, |
| 1075 | { "sths", 0x0c001240, 0xfc00dfc0, "cMx,V(b)", pa10, 0}, |
| 1076 | { "sths", 0x0c001240, 0xfc001fc0, "cMx,V(s,b)", pa10, 0}, |
| 1077 | { "stbs", 0x0c001200, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 1078 | { "stbs", 0x0c001200, 0xfc001fc0, "cMx,V(s,b)", pa10, FLAG_STRICT}, |
| 1079 | { "stbs", 0x0c001200, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 1080 | { "stbs", 0x0c001200, 0xfc0013c0, "cmcCx,V(s,b)", pa11, FLAG_STRICT}, |
| 1081 | { "stbs", 0x0c001200, 0xfc00dfc0, "cMx,V(b)", pa10, 0}, |
| 1082 | { "stbs", 0x0c001200, 0xfc001fc0, "cMx,V(s,b)", pa10, 0}, |
| 1083 | { "stwas", 0x0c001380, 0xfc00dfc0, "cMx,V(b)", pa10, FLAG_STRICT}, |
| 1084 | { "stwas", 0x0c001380, 0xfc00d3c0, "cmcCx,V(b)", pa11, FLAG_STRICT}, |
| 1085 | { "stwas", 0x0c001380, 0xfc00dfc0, "cMx,V(b)", pa10, 0}, |
| 1086 | { "stdby", 0x0c001340, 0xfc00d3c0, "cscCx,V(b)", pa20, FLAG_STRICT}, |
| 1087 | { "stdby", 0x0c001340, 0xfc0013c0, "cscCx,V(s,b)", pa20, FLAG_STRICT}, |
| 1088 | { "stbys", 0x0c001300, 0xfc00dfc0, "cAx,V(b)", pa10, FLAG_STRICT}, |
| 1089 | { "stbys", 0x0c001300, 0xfc001fc0, "cAx,V(s,b)", pa10, FLAG_STRICT}, |
| 1090 | { "stbys", 0x0c001300, 0xfc00d3c0, "cscCx,V(b)", pa11, FLAG_STRICT}, |
| 1091 | { "stbys", 0x0c001300, 0xfc0013c0, "cscCx,V(s,b)", pa11, FLAG_STRICT}, |
| 1092 | { "stbys", 0x0c001300, 0xfc00dfc0, "cAx,V(b)", pa10, 0}, |
| 1093 | { "stbys", 0x0c001300, 0xfc001fc0, "cAx,V(s,b)", pa10, 0}, |
| 1094 | |
| 1095 | /* Immediate instructions. */ |
| 1096 | { "ldo", 0x34000000, 0xfc000000, "l(b),x", pa20w, 0}, |
| 1097 | { "ldo", 0x34000000, 0xfc00c000, "j(b),x", pa10, 0}, |
| 1098 | { "ldil", 0x20000000, 0xfc000000, "k,b", pa10, 0}, |
| 1099 | { "addil", 0x28000000, 0xfc000000, "k,b,Z", pa10, 0}, |
| 1100 | { "addil", 0x28000000, 0xfc000000, "k,b", pa10, 0}, |
| 1101 | |
| 1102 | /* Branching instructions. */ |
| 1103 | { "b", 0xe8008000, 0xfc00e000, "cpnXL", pa20, FLAG_STRICT}, |
| 1104 | { "b", 0xe800a000, 0xfc00e000, "clnXL", pa20, FLAG_STRICT}, |
| 1105 | { "b", 0xe8000000, 0xfc00e000, "clnW,b", pa10, FLAG_STRICT}, |
| 1106 | { "b", 0xe8002000, 0xfc00e000, "cgnW,b", pa10, FLAG_STRICT}, |
| 1107 | { "b", 0xe8000000, 0xffe0e000, "nW", pa10, 0}, /* b,l foo,r0 */ |
| 1108 | { "bl", 0xe8000000, 0xfc00e000, "nW,b", pa10, 0}, |
| 1109 | { "gate", 0xe8002000, 0xfc00e000, "nW,b", pa10, 0}, |
| 1110 | { "blr", 0xe8004000, 0xfc00e001, "nx,b", pa10, 0}, |
| 1111 | { "bv", 0xe800c000, 0xfc00fffd, "nx(b)", pa10, 0}, |
| 1112 | { "bv", 0xe800c000, 0xfc00fffd, "n(b)", pa10, 0}, |
| 1113 | { "bve", 0xe800f001, 0xfc1ffffd, "cpn(b)L", pa20, FLAG_STRICT}, |
| 1114 | { "bve", 0xe800f000, 0xfc1ffffd, "cln(b)L", pa20, FLAG_STRICT}, |
| 1115 | { "bve", 0xe800d001, 0xfc1ffffd, "cPn(b)", pa20, FLAG_STRICT}, |
| 1116 | { "bve", 0xe800d000, 0xfc1ffffd, "n(b)", pa20, FLAG_STRICT}, |
| 1117 | { "be", 0xe4000000, 0xfc000000, "clnz(S,b),Y", pa10, FLAG_STRICT}, |
| 1118 | { "be", 0xe4000000, 0xfc000000, "clnz(b),Y", pa10, FLAG_STRICT}, |
| 1119 | { "be", 0xe0000000, 0xfc000000, "nz(S,b)", pa10, 0}, |
| 1120 | { "be", 0xe0000000, 0xfc000000, "nz(b)", pa10, 0}, |
| 1121 | { "ble", 0xe4000000, 0xfc000000, "nz(S,b)", pa10, 0}, |
| 1122 | { "movb", 0xc8000000, 0xfc000000, "?ynx,b,w", pa10, 0}, |
| 1123 | { "movib", 0xcc000000, 0xfc000000, "?yn5,b,w", pa10, 0}, |
| 1124 | { "combt", 0x80000000, 0xfc000000, "?tnx,b,w", pa10, 0}, |
| 1125 | { "combf", 0x88000000, 0xfc000000, "?tnx,b,w", pa10, 0}, |
| 1126 | { "comibt", 0x84000000, 0xfc000000, "?tn5,b,w", pa10, 0}, |
| 1127 | { "comibf", 0x8c000000, 0xfc000000, "?tn5,b,w", pa10, 0}, |
| 1128 | { "addbt", 0xa0000000, 0xfc000000, "?dnx,b,w", pa10, 0}, |
| 1129 | { "addbf", 0xa8000000, 0xfc000000, "?dnx,b,w", pa10, 0}, |
| 1130 | { "addibt", 0xa4000000, 0xfc000000, "?dn5,b,w", pa10, 0}, |
| 1131 | { "addibf", 0xac000000, 0xfc000000, "?dn5,b,w", pa10, 0}, |
| 1132 | { "bb", 0xc0004000, 0xffe06000, "?bnx,!,w", pa10, FLAG_STRICT}, |
| 1133 | { "bb", 0xc0006000, 0xffe06000, "?Bnx,!,w", pa20, FLAG_STRICT}, |
| 1134 | { "bb", 0xc4004000, 0xfc006000, "?bnx,Q,w", pa10, FLAG_STRICT}, |
| 1135 | { "bb", 0xc4004000, 0xfc004000, "?Bnx,B,w", pa20, FLAG_STRICT}, |
| 1136 | { "bvb", 0xc0004000, 0xffe04000, "?bnx,w", pa10, 0}, |
| 1137 | { "clrbts", 0xe8004005, 0xffffffff, "", pa20, FLAG_STRICT}, |
| 1138 | { "popbts", 0xe8004005, 0xfffff007, "$", pa20, FLAG_STRICT}, |
| 1139 | { "pushnom", 0xe8004001, 0xffffffff, "", pa20, FLAG_STRICT}, |
| 1140 | { "pushbts", 0xe8004001, 0xffe0ffff, "x", pa20, FLAG_STRICT}, |
| 1141 | |
| 1142 | /* Computation Instructions. */ |
| 1143 | |
| 1144 | { "cmpclr", 0x080008a0, 0xfc000fe0, "?Sx,b,t", pa20, FLAG_STRICT}, |
| 1145 | { "cmpclr", 0x08000880, 0xfc000fe0, "?sx,b,t", pa10, FLAG_STRICT}, |
| 1146 | { "comclr", 0x08000880, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1147 | { "or", 0x08000260, 0xfc000fe0, "?Lx,b,t", pa20, FLAG_STRICT}, |
| 1148 | { "or", 0x08000240, 0xfc000fe0, "?lx,b,t", pa10, 0}, |
| 1149 | { "xor", 0x080002a0, 0xfc000fe0, "?Lx,b,t", pa20, FLAG_STRICT}, |
| 1150 | { "xor", 0x08000280, 0xfc000fe0, "?lx,b,t", pa10, 0}, |
| 1151 | { "and", 0x08000220, 0xfc000fe0, "?Lx,b,t", pa20, FLAG_STRICT}, |
| 1152 | { "and", 0x08000200, 0xfc000fe0, "?lx,b,t", pa10, 0}, |
| 1153 | { "andcm", 0x08000020, 0xfc000fe0, "?Lx,b,t", pa20, FLAG_STRICT}, |
| 1154 | { "andcm", 0x08000000, 0xfc000fe0, "?lx,b,t", pa10, 0}, |
| 1155 | { "uxor", 0x080003a0, 0xfc000fe0, "?Ux,b,t", pa20, FLAG_STRICT}, |
| 1156 | { "uxor", 0x08000380, 0xfc000fe0, "?ux,b,t", pa10, 0}, |
| 1157 | { "uaddcm", 0x080009a0, 0xfc000fa0, "cT?Ux,b,t", pa20, FLAG_STRICT}, |
| 1158 | { "uaddcm", 0x08000980, 0xfc000fa0, "cT?ux,b,t", pa10, FLAG_STRICT}, |
| 1159 | { "uaddcm", 0x08000980, 0xfc000fe0, "?ux,b,t", pa10, 0}, |
| 1160 | { "uaddcmt", 0x080009c0, 0xfc000fe0, "?ux,b,t", pa10, 0}, |
| 1161 | { "dcor", 0x08000ba0, 0xfc1f0fa0, "ci?Ub,t", pa20, FLAG_STRICT}, |
| 1162 | { "dcor", 0x08000b80, 0xfc1f0fa0, "ci?ub,t", pa10, FLAG_STRICT}, |
| 1163 | { "dcor", 0x08000b80, 0xfc1f0fe0, "?ub,t", pa10, 0}, |
| 1164 | { "idcor", 0x08000bc0, 0xfc1f0fe0, "?ub,t", pa10, 0}, |
| 1165 | { "addi", 0xb0000000, 0xfc000000, "ct?ai,b,x", pa10, FLAG_STRICT}, |
| 1166 | { "addi", 0xb4000000, 0xfc000000, "cv?ai,b,x", pa10, FLAG_STRICT}, |
| 1167 | { "addi", 0xb4000000, 0xfc000800, "?ai,b,x", pa10, 0}, |
| 1168 | { "addio", 0xb4000800, 0xfc000800, "?ai,b,x", pa10, 0}, |
| 1169 | { "addit", 0xb0000000, 0xfc000800, "?ai,b,x", pa10, 0}, |
| 1170 | { "addito", 0xb0000800, 0xfc000800, "?ai,b,x", pa10, 0}, |
| 1171 | { "add", 0x08000720, 0xfc0007e0, "cY?Ax,b,t", pa20, FLAG_STRICT}, |
| 1172 | { "add", 0x08000700, 0xfc0007e0, "cy?ax,b,t", pa10, FLAG_STRICT}, |
| 1173 | { "add", 0x08000220, 0xfc0003e0, "ca?Ax,b,t", pa20, FLAG_STRICT}, |
| 1174 | { "add", 0x08000200, 0xfc0003e0, "ca?ax,b,t", pa10, FLAG_STRICT}, |
| 1175 | { "add", 0x08000600, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1176 | { "addl", 0x08000a00, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1177 | { "addo", 0x08000e00, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1178 | { "addc", 0x08000700, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1179 | { "addco", 0x08000f00, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1180 | { "sub", 0x080004e0, 0xfc0007e0, "ct?Sx,b,t", pa20, FLAG_STRICT}, |
| 1181 | { "sub", 0x080004c0, 0xfc0007e0, "ct?sx,b,t", pa10, FLAG_STRICT}, |
| 1182 | { "sub", 0x08000520, 0xfc0007e0, "cB?Sx,b,t", pa20, FLAG_STRICT}, |
| 1183 | { "sub", 0x08000500, 0xfc0007e0, "cb?sx,b,t", pa10, FLAG_STRICT}, |
| 1184 | { "sub", 0x08000420, 0xfc0007e0, "cv?Sx,b,t", pa20, FLAG_STRICT}, |
| 1185 | { "sub", 0x08000400, 0xfc0007e0, "cv?sx,b,t", pa10, FLAG_STRICT}, |
| 1186 | { "sub", 0x08000400, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1187 | { "subo", 0x08000c00, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1188 | { "subb", 0x08000500, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1189 | { "subbo", 0x08000d00, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1190 | { "subt", 0x080004c0, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1191 | { "subto", 0x08000cc0, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1192 | { "ds", 0x08000440, 0xfc000fe0, "?sx,b,t", pa10, 0}, |
| 1193 | { "subi", 0x94000000, 0xfc000000, "cv?si,b,x", pa10, FLAG_STRICT}, |
| 1194 | { "subi", 0x94000000, 0xfc000800, "?si,b,x", pa10, 0}, |
| 1195 | { "subio", 0x94000800, 0xfc000800, "?si,b,x", pa10, 0}, |
| 1196 | { "cmpiclr", 0x90000800, 0xfc000800, "?Si,b,x", pa20, FLAG_STRICT}, |
| 1197 | { "cmpiclr", 0x90000000, 0xfc000800, "?si,b,x", pa10, FLAG_STRICT}, |
| 1198 | { "comiclr", 0x90000000, 0xfc000800, "?si,b,x", pa10, 0}, |
| 1199 | { "shladd", 0x08000220, 0xfc000320, "ca?Ax,.,b,t", pa20, FLAG_STRICT}, |
| 1200 | { "shladd", 0x08000200, 0xfc000320, "ca?ax,.,b,t", pa10, FLAG_STRICT}, |
| 1201 | { "sh1add", 0x08000640, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1202 | { "sh1addl", 0x08000a40, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1203 | { "sh1addo", 0x08000e40, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1204 | { "sh2add", 0x08000680, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1205 | { "sh2addl", 0x08000a80, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1206 | { "sh2addo", 0x08000e80, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1207 | { "sh3add", 0x080006c0, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1208 | { "sh3addl", 0x08000ac0, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1209 | { "sh3addo", 0x08000ec0, 0xfc000fe0, "?ax,b,t", pa10, 0}, |
| 1210 | |
| 1211 | /* Subword Operation Instructions. */ |
| 1212 | |
| 1213 | { "hadd", 0x08000300, 0xfc00ff20, "cHx,b,t", pa20, FLAG_STRICT}, |
| 1214 | { "havg", 0x080002c0, 0xfc00ffe0, "x,b,t", pa20, FLAG_STRICT}, |
| 1215 | { "hshl", 0xf8008800, 0xffe0fc20, "x,*,t", pa20, FLAG_STRICT}, |
| 1216 | { "hshladd", 0x08000700, 0xfc00ff20, "x,.,b,t", pa20, FLAG_STRICT}, |
| 1217 | { "hshr", 0xf800c800, 0xfc1ff820, "cSb,*,t", pa20, FLAG_STRICT}, |
| 1218 | { "hshradd", 0x08000500, 0xfc00ff20, "x,.,b,t", pa20, FLAG_STRICT}, |
| 1219 | { "hsub", 0x08000100, 0xfc00ff20, "cHx,b,t", pa20, FLAG_STRICT}, |
| 1220 | { "mixh", 0xf8008400, 0xfc009fe0, "chx,b,t", pa20, FLAG_STRICT}, |
| 1221 | { "mixw", 0xf8008000, 0xfc009fe0, "chx,b,t", pa20, FLAG_STRICT}, |
| 1222 | { "permh", 0xf8000000, 0xfc009020, "c*a,t", pa20, FLAG_STRICT}, |
| 1223 | |
| 1224 | |
| 1225 | /* Extract and Deposit Instructions. */ |
| 1226 | |
| 1227 | { "shrpd", 0xd0000200, 0xfc001fe0, "?Xx,b,!,t", pa20, FLAG_STRICT}, |
| 1228 | { "shrpd", 0xd0000400, 0xfc001400, "?Xx,b,~,t", pa20, FLAG_STRICT}, |
| 1229 | { "shrpw", 0xd0000000, 0xfc001fe0, "?xx,b,!,t", pa10, FLAG_STRICT}, |
| 1230 | { "shrpw", 0xd0000800, 0xfc001c00, "?xx,b,p,t", pa10, FLAG_STRICT}, |
| 1231 | { "vshd", 0xd0000000, 0xfc001fe0, "?xx,b,t", pa10, 0}, |
| 1232 | { "shd", 0xd0000800, 0xfc001c00, "?xx,b,p,t", pa10, 0}, |
| 1233 | { "extrd", 0xd0001200, 0xfc001ae0, "cS?Xb,!,%,x", pa20, FLAG_STRICT}, |
| 1234 | { "extrd", 0xd8000000, 0xfc000000, "cS?Xb,q,|,x", pa20, FLAG_STRICT}, |
| 1235 | { "extrw", 0xd0001000, 0xfc001be0, "cS?xb,!,T,x", pa10, FLAG_STRICT}, |
| 1236 | { "extrw", 0xd0001800, 0xfc001800, "cS?xb,P,T,x", pa10, FLAG_STRICT}, |
| 1237 | { "vextru", 0xd0001000, 0xfc001fe0, "?xb,T,x", pa10, 0}, |
| 1238 | { "vextrs", 0xd0001400, 0xfc001fe0, "?xb,T,x", pa10, 0}, |
| 1239 | { "extru", 0xd0001800, 0xfc001c00, "?xb,P,T,x", pa10, 0}, |
| 1240 | { "extrs", 0xd0001c00, 0xfc001c00, "?xb,P,T,x", pa10, 0}, |
| 1241 | { "depd", 0xd4000200, 0xfc001ae0, "cz?Xx,!,%,b", pa20, FLAG_STRICT}, |
| 1242 | { "depd", 0xf0000000, 0xfc000000, "cz?Xx,~,|,b", pa20, FLAG_STRICT}, |
| 1243 | { "depdi", 0xd4001200, 0xfc001ae0, "cz?X5,!,%,b", pa20, FLAG_STRICT}, |
| 1244 | { "depdi", 0xf4000000, 0xfc000000, "cz?X5,~,|,b", pa20, FLAG_STRICT}, |
| 1245 | { "depw", 0xd4000000, 0xfc001be0, "cz?xx,!,T,b", pa10, FLAG_STRICT}, |
| 1246 | { "depw", 0xd4000800, 0xfc001800, "cz?xx,p,T,b", pa10, FLAG_STRICT}, |
| 1247 | { "depwi", 0xd4001000, 0xfc001be0, "cz?x5,!,T,b", pa10, FLAG_STRICT}, |
| 1248 | { "depwi", 0xd4001800, 0xfc001800, "cz?x5,p,T,b", pa10, FLAG_STRICT}, |
| 1249 | { "zvdep", 0xd4000000, 0xfc001fe0, "?xx,T,b", pa10, 0}, |
| 1250 | { "vdep", 0xd4000400, 0xfc001fe0, "?xx,T,b", pa10, 0}, |
| 1251 | { "zdep", 0xd4000800, 0xfc001c00, "?xx,p,T,b", pa10, 0}, |
| 1252 | { "dep", 0xd4000c00, 0xfc001c00, "?xx,p,T,b", pa10, 0}, |
| 1253 | { "zvdepi", 0xd4001000, 0xfc001fe0, "?x5,T,b", pa10, 0}, |
| 1254 | { "vdepi", 0xd4001400, 0xfc001fe0, "?x5,T,b", pa10, 0}, |
| 1255 | { "zdepi", 0xd4001800, 0xfc001c00, "?x5,p,T,b", pa10, 0}, |
| 1256 | { "depi", 0xd4001c00, 0xfc001c00, "?x5,p,T,b", pa10, 0}, |
| 1257 | |
| 1258 | /* System Control Instructions. */ |
| 1259 | |
| 1260 | { "break", 0x00000000, 0xfc001fe0, "r,A", pa10, 0}, |
| 1261 | { "rfi", 0x00000c00, 0xffffff1f, "cr", pa10, FLAG_STRICT}, |
| 1262 | { "rfi", 0x00000c00, 0xffffffff, "", pa10, 0}, |
| 1263 | { "rfir", 0x00000ca0, 0xffffffff, "", pa11, 0}, |
| 1264 | { "ssm", 0x00000d60, 0xfc00ffe0, "U,t", pa20, FLAG_STRICT}, |
| 1265 | { "ssm", 0x00000d60, 0xffe0ffe0, "R,t", pa10, 0}, |
| 1266 | { "rsm", 0x00000e60, 0xfc00ffe0, "U,t", pa20, FLAG_STRICT}, |
| 1267 | { "rsm", 0x00000e60, 0xffe0ffe0, "R,t", pa10, 0}, |
| 1268 | { "mtsm", 0x00001860, 0xffe0ffff, "x", pa10, 0}, |
| 1269 | { "ldsid", 0x000010a0, 0xfc1fffe0, "(b),t", pa10, 0}, |
| 1270 | { "ldsid", 0x000010a0, 0xfc1f3fe0, "(s,b),t", pa10, 0}, |
| 1271 | { "mtsp", 0x00001820, 0xffe01fff, "x,S", pa10, 0}, |
| 1272 | { "mtctl", 0x00001840, 0xfc00ffff, "x,^", pa10, 0}, |
| 1273 | { "mtsarcm", 0x016018C0, 0xffe0ffff, "x", pa20, FLAG_STRICT}, |
| 1274 | { "mfia", 0x000014A0, 0xffffffe0, "t", pa20, FLAG_STRICT}, |
| 1275 | { "mfsp", 0x000004a0, 0xffff1fe0, "S,t", pa10, 0}, |
| 1276 | { "mfctl", 0x016048a0, 0xffffffe0, "cW!,t", pa20, FLAG_STRICT}, |
| 1277 | { "mfctl", 0x000008a0, 0xfc1fffe0, "^,t", pa10, 0}, |
| 1278 | { "sync", 0x00000400, 0xffffffff, "", pa10, 0}, |
| 1279 | { "syncdma", 0x00100400, 0xffffffff, "", pa10, 0}, |
| 1280 | { "probe", 0x04001180, 0xfc00ffa0, "cw(b),x,t", pa10, FLAG_STRICT}, |
| 1281 | { "probe", 0x04001180, 0xfc003fa0, "cw(s,b),x,t", pa10, FLAG_STRICT}, |
| 1282 | { "probei", 0x04003180, 0xfc00ffa0, "cw(b),R,t", pa10, FLAG_STRICT}, |
| 1283 | { "probei", 0x04003180, 0xfc003fa0, "cw(s,b),R,t", pa10, FLAG_STRICT}, |
| 1284 | { "prober", 0x04001180, 0xfc00ffe0, "(b),x,t", pa10, 0}, |
| 1285 | { "prober", 0x04001180, 0xfc003fe0, "(s,b),x,t", pa10, 0}, |
| 1286 | { "proberi", 0x04003180, 0xfc00ffe0, "(b),R,t", pa10, 0}, |
| 1287 | { "proberi", 0x04003180, 0xfc003fe0, "(s,b),R,t", pa10, 0}, |
| 1288 | { "probew", 0x040011c0, 0xfc00ffe0, "(b),x,t", pa10, 0}, |
| 1289 | { "probew", 0x040011c0, 0xfc003fe0, "(s,b),x,t", pa10, 0}, |
| 1290 | { "probewi", 0x040031c0, 0xfc00ffe0, "(b),R,t", pa10, 0}, |
| 1291 | { "probewi", 0x040031c0, 0xfc003fe0, "(s,b),R,t", pa10, 0}, |
| 1292 | { "lpa", 0x04001340, 0xfc00ffc0, "cZx(b),t", pa10, 0}, |
| 1293 | { "lpa", 0x04001340, 0xfc003fc0, "cZx(s,b),t", pa10, 0}, |
| 1294 | { "lci", 0x04001300, 0xfc00ffe0, "x(b),t", pa11, 0}, |
| 1295 | { "lci", 0x04001300, 0xfc003fe0, "x(s,b),t", pa11, 0}, |
| 1296 | { "pdtlb", 0x04001600, 0xfc00ffdf, "cLcZx(b)", pa20, FLAG_STRICT}, |
| 1297 | { "pdtlb", 0x04001600, 0xfc003fdf, "cLcZx(s,b)", pa20, FLAG_STRICT}, |
| 1298 | { "pdtlb", 0x04001600, 0xfc1fffdf, "cLcZ@(b)", pa20, FLAG_STRICT}, |
| 1299 | { "pdtlb", 0x04001600, 0xfc1f3fdf, "cLcZ@(s,b)", pa20, FLAG_STRICT}, |
| 1300 | { "pdtlb", 0x04001200, 0xfc00ffdf, "cZx(b)", pa10, 0}, |
| 1301 | { "pdtlb", 0x04001200, 0xfc003fdf, "cZx(s,b)", pa10, 0}, |
| 1302 | { "pitlb", 0x04000600, 0xfc001fdf, "cLcZx(S,b)", pa20, FLAG_STRICT}, |
| 1303 | { "pitlb", 0x04000600, 0xfc1f1fdf, "cLcZ@(S,b)", pa20, FLAG_STRICT}, |
| 1304 | { "pitlb", 0x04000200, 0xfc001fdf, "cZx(S,b)", pa10, 0}, |
| 1305 | { "pdtlbe", 0x04001240, 0xfc00ffdf, "cZx(b)", pa10, 0}, |
| 1306 | { "pdtlbe", 0x04001240, 0xfc003fdf, "cZx(s,b)", pa10, 0}, |
| 1307 | { "pitlbe", 0x04000240, 0xfc001fdf, "cZx(S,b)", pa10, 0}, |
| 1308 | { "idtlba", 0x04001040, 0xfc00ffff, "x,(b)", pa10, 0}, |
| 1309 | { "idtlba", 0x04001040, 0xfc003fff, "x,(s,b)", pa10, 0}, |
| 1310 | { "iitlba", 0x04000040, 0xfc001fff, "x,(S,b)", pa10, 0}, |
| 1311 | { "idtlbp", 0x04001000, 0xfc00ffff, "x,(b)", pa10, 0}, |
| 1312 | { "idtlbp", 0x04001000, 0xfc003fff, "x,(s,b)", pa10, 0}, |
| 1313 | { "iitlbp", 0x04000000, 0xfc001fff, "x,(S,b)", pa10, 0}, |
| 1314 | { "pdc", 0x04001380, 0xfc00ffdf, "cZx(b)", pa10, 0}, |
| 1315 | { "pdc", 0x04001380, 0xfc003fdf, "cZx(s,b)", pa10, 0}, |
| 1316 | { "fdc", 0x04001280, 0xfc00ffdf, "cZx(b)", pa10, FLAG_STRICT}, |
| 1317 | { "fdc", 0x04001280, 0xfc003fdf, "cZx(s,b)", pa10, FLAG_STRICT}, |
| 1318 | { "fdc", 0x04003280, 0xfc00ffff, "5(b)", pa20, FLAG_STRICT}, |
| 1319 | { "fdc", 0x04003280, 0xfc003fff, "5(s,b)", pa20, FLAG_STRICT}, |
| 1320 | { "fdc", 0x04001280, 0xfc00ffdf, "cZx(b)", pa10, 0}, |
| 1321 | { "fdc", 0x04001280, 0xfc003fdf, "cZx(s,b)", pa10, 0}, |
| 1322 | { "fic", 0x040013c0, 0xfc00dfdf, "cZx(b)", pa20, FLAG_STRICT}, |
| 1323 | { "fic", 0x04000280, 0xfc001fdf, "cZx(S,b)", pa10, 0}, |
| 1324 | { "fdce", 0x040012c0, 0xfc00ffdf, "cZx(b)", pa10, 0}, |
| 1325 | { "fdce", 0x040012c0, 0xfc003fdf, "cZx(s,b)", pa10, 0}, |
| 1326 | { "fice", 0x040002c0, 0xfc001fdf, "cZx(S,b)", pa10, 0}, |
| 1327 | { "diag", 0x14000000, 0xfc000000, "D", pa10, 0}, |
| 1328 | { "idtlbt", 0x04001800, 0xfc00ffff, "x,b", pa20, FLAG_STRICT}, |
| 1329 | { "iitlbt", 0x04000800, 0xfc00ffff, "x,b", pa20, FLAG_STRICT}, |
| 1330 | |
| 1331 | /* These may be specific to certain versions of the PA. Joel claimed |
| 1332 | they were 72000 (7200?) specific. However, I'm almost certain the |
| 1333 | mtcpu/mfcpu were undocumented, but available in the older 700 machines. */ |
| 1334 | { "mtcpu", 0x14001600, 0xfc00ffff, "x,^", pa10, 0}, |
| 1335 | { "mfcpu", 0x14001A00, 0xfc00ffff, "^,x", pa10, 0}, |
| 1336 | { "tocen", 0x14403600, 0xffffffff, "", pa10, 0}, |
| 1337 | { "tocdis", 0x14401620, 0xffffffff, "", pa10, 0}, |
| 1338 | { "shdwgr", 0x14402600, 0xffffffff, "", pa10, 0}, |
| 1339 | { "grshdw", 0x14400620, 0xffffffff, "", pa10, 0}, |
| 1340 | |
| 1341 | /* gfw and gfr are not in the HP PA 1.1 manual, but they are in either |
| 1342 | the Timex FPU or the Mustang ERS (not sure which) manual. */ |
| 1343 | { "gfw", 0x04001680, 0xfc00ffdf, "cZx(b)", pa11, 0}, |
| 1344 | { "gfw", 0x04001680, 0xfc003fdf, "cZx(s,b)", pa11, 0}, |
| 1345 | { "gfr", 0x04001a80, 0xfc00ffdf, "cZx(b)", pa11, 0}, |
| 1346 | { "gfr", 0x04001a80, 0xfc003fdf, "cZx(s,b)", pa11, 0}, |
| 1347 | |
| 1348 | /* Floating Point Coprocessor Instructions. */ |
| 1349 | |
| 1350 | { "fldw", 0x24000000, 0xfc00df80, "cXx(b),fT", pa10, FLAG_STRICT}, |
| 1351 | { "fldw", 0x24000000, 0xfc001f80, "cXx(s,b),fT", pa10, FLAG_STRICT}, |
| 1352 | { "fldw", 0x24000000, 0xfc00d380, "cxccx(b),fT", pa11, FLAG_STRICT}, |
| 1353 | { "fldw", 0x24000000, 0xfc001380, "cxccx(s,b),fT", pa11, FLAG_STRICT}, |
| 1354 | { "fldw", 0x24001020, 0xfc1ff3a0, "cocc@(b),fT", pa20, FLAG_STRICT}, |
| 1355 | { "fldw", 0x24001020, 0xfc1f33a0, "cocc@(s,b),fT", pa20, FLAG_STRICT}, |
| 1356 | { "fldw", 0x24001000, 0xfc00df80, "cM5(b),fT", pa10, FLAG_STRICT}, |
| 1357 | { "fldw", 0x24001000, 0xfc001f80, "cM5(s,b),fT", pa10, FLAG_STRICT}, |
| 1358 | { "fldw", 0x24001000, 0xfc00d380, "cmcc5(b),fT", pa11, FLAG_STRICT}, |
| 1359 | { "fldw", 0x24001000, 0xfc001380, "cmcc5(s,b),fT", pa11, FLAG_STRICT}, |
| 1360 | { "fldw", 0x5c000000, 0xfc000004, "y(b),fe", pa20w, FLAG_STRICT}, |
| 1361 | { "fldw", 0x58000000, 0xfc000000, "cJy(b),fe", pa20w, FLAG_STRICT}, |
| 1362 | { "fldw", 0x5c000000, 0xfc00c004, "d(b),fe", pa20, FLAG_STRICT}, |
| 1363 | { "fldw", 0x5c000000, 0xfc000004, "d(s,b),fe", pa20, FLAG_STRICT}, |
| 1364 | { "fldw", 0x58000000, 0xfc00c000, "cJd(b),fe", pa20, FLAG_STRICT}, |
| 1365 | { "fldw", 0x58000000, 0xfc000000, "cJd(s,b),fe", pa20, FLAG_STRICT}, |
| 1366 | { "fldd", 0x2c000000, 0xfc00dfc0, "cXx(b),ft", pa10, FLAG_STRICT}, |
| 1367 | { "fldd", 0x2c000000, 0xfc001fc0, "cXx(s,b),ft", pa10, FLAG_STRICT}, |
| 1368 | { "fldd", 0x2c000000, 0xfc00d3c0, "cxccx(b),ft", pa11, FLAG_STRICT}, |
| 1369 | { "fldd", 0x2c000000, 0xfc0013c0, "cxccx(s,b),ft", pa11, FLAG_STRICT}, |
| 1370 | { "fldd", 0x2c001020, 0xfc1ff3e0, "cocc@(b),ft", pa20, FLAG_STRICT}, |
| 1371 | { "fldd", 0x2c001020, 0xfc1f33e0, "cocc@(s,b),ft", pa20, FLAG_STRICT}, |
| 1372 | { "fldd", 0x2c001000, 0xfc00dfc0, "cM5(b),ft", pa10, FLAG_STRICT}, |
| 1373 | { "fldd", 0x2c001000, 0xfc001fc0, "cM5(s,b),ft", pa10, FLAG_STRICT}, |
| 1374 | { "fldd", 0x2c001000, 0xfc00d3c0, "cmcc5(b),ft", pa11, FLAG_STRICT}, |
| 1375 | { "fldd", 0x2c001000, 0xfc0013c0, "cmcc5(s,b),ft", pa11, FLAG_STRICT}, |
| 1376 | { "fldd", 0x50000002, 0xfc000002, "cq&(b),fx", pa20w, FLAG_STRICT}, |
| 1377 | { "fldd", 0x50000002, 0xfc00c002, "cq#(b),fx", pa20, FLAG_STRICT}, |
| 1378 | { "fldd", 0x50000002, 0xfc000002, "cq#(s,b),fx", pa20, FLAG_STRICT}, |
| 1379 | { "fstw", 0x24000200, 0xfc00df80, "cXfT,x(b)", pa10, FLAG_STRICT}, |
| 1380 | { "fstw", 0x24000200, 0xfc001f80, "cXfT,x(s,b)", pa10, FLAG_STRICT}, |
| 1381 | { "fstw", 0x24000200, 0xfc00d380, "cxcCfT,x(b)", pa11, FLAG_STRICT}, |
| 1382 | { "fstw", 0x24000200, 0xfc001380, "cxcCfT,x(s,b)", pa11, FLAG_STRICT}, |
| 1383 | { "fstw", 0x24001220, 0xfc1ff3a0, "cocCfT,@(b)", pa20, FLAG_STRICT}, |
| 1384 | { "fstw", 0x24001220, 0xfc1f33a0, "cocCfT,@(s,b)", pa20, FLAG_STRICT}, |
| 1385 | { "fstw", 0x24001200, 0xfc00df80, "cMfT,5(b)", pa10, FLAG_STRICT}, |
| 1386 | { "fstw", 0x24001200, 0xfc001f80, "cMfT,5(s,b)", pa10, FLAG_STRICT}, |
| 1387 | { "fstw", 0x24001200, 0xfc00df80, "cMfT,5(b)", pa10, FLAG_STRICT}, |
| 1388 | { "fstw", 0x24001200, 0xfc001f80, "cMfT,5(s,b)", pa10, FLAG_STRICT}, |
| 1389 | { "fstw", 0x7c000000, 0xfc000004, "fE,y(b)", pa20w, FLAG_STRICT}, |
| 1390 | { "fstw", 0x78000000, 0xfc000000, "cJfE,y(b)", pa20w, FLAG_STRICT}, |
| 1391 | { "fstw", 0x7c000000, 0xfc00c004, "fE,d(b)", pa20, FLAG_STRICT}, |
| 1392 | { "fstw", 0x7c000000, 0xfc000004, "fE,d(s,b)", pa20, FLAG_STRICT}, |
| 1393 | { "fstw", 0x78000000, 0xfc00c000, "cJfE,d(b)", pa20, FLAG_STRICT}, |
| 1394 | { "fstw", 0x78000000, 0xfc000000, "cJfE,d(s,b)", pa20, FLAG_STRICT}, |
| 1395 | { "fstd", 0x2c000200, 0xfc00dfc0, "cXft,x(b)", pa10, FLAG_STRICT}, |
| 1396 | { "fstd", 0x2c000200, 0xfc001fc0, "cXft,x(s,b)", pa10, FLAG_STRICT}, |
| 1397 | { "fstd", 0x2c000200, 0xfc00d3c0, "cxcCft,x(b)", pa11, FLAG_STRICT}, |
| 1398 | { "fstd", 0x2c000200, 0xfc0013c0, "cxcCft,x(s,b)", pa11, FLAG_STRICT}, |
| 1399 | { "fstd", 0x2c001220, 0xfc1ff3e0, "cocCft,@(b)", pa20, FLAG_STRICT}, |
| 1400 | { "fstd", 0x2c001220, 0xfc1f33e0, "cocCft,@(s,b)", pa20, FLAG_STRICT}, |
| 1401 | { "fstd", 0x2c001200, 0xfc00dfc0, "cMft,5(b)", pa10, FLAG_STRICT}, |
| 1402 | { "fstd", 0x2c001200, 0xfc001fc0, "cMft,5(s,b)", pa10, FLAG_STRICT}, |
| 1403 | { "fstd", 0x2c001200, 0xfc00d3c0, "cmcCft,5(b)", pa11, FLAG_STRICT}, |
| 1404 | { "fstd", 0x2c001200, 0xfc0013c0, "cmcCft,5(s,b)", pa11, FLAG_STRICT}, |
| 1405 | { "fstd", 0x70000002, 0xfc000002, "cqfx,&(b)", pa20w, FLAG_STRICT}, |
| 1406 | { "fstd", 0x70000002, 0xfc00c002, "cqfx,#(b)", pa20, FLAG_STRICT}, |
| 1407 | { "fstd", 0x70000002, 0xfc000002, "cqfx,#(s,b)", pa20, FLAG_STRICT}, |
| 1408 | { "fldwx", 0x24000000, 0xfc00df80, "cXx(b),fT", pa10, FLAG_STRICT}, |
| 1409 | { "fldwx", 0x24000000, 0xfc001f80, "cXx(s,b),fT", pa10, FLAG_STRICT}, |
| 1410 | { "fldwx", 0x24000000, 0xfc00d380, "cxccx(b),fT", pa11, FLAG_STRICT}, |
| 1411 | { "fldwx", 0x24000000, 0xfc001380, "cxccx(s,b),fT", pa11, FLAG_STRICT}, |
| 1412 | { "fldwx", 0x24000000, 0xfc00df80, "cXx(b),fT", pa10, 0}, |
| 1413 | { "fldwx", 0x24000000, 0xfc001f80, "cXx(s,b),fT", pa10, 0}, |
| 1414 | { "flddx", 0x2c000000, 0xfc00dfc0, "cXx(b),ft", pa10, FLAG_STRICT}, |
| 1415 | { "flddx", 0x2c000000, 0xfc001fc0, "cXx(s,b),ft", pa10, FLAG_STRICT}, |
| 1416 | { "flddx", 0x2c000000, 0xfc00d3c0, "cxccx(b),ft", pa11, FLAG_STRICT}, |
| 1417 | { "flddx", 0x2c000000, 0xfc0013c0, "cxccx(s,b),ft", pa11, FLAG_STRICT}, |
| 1418 | { "flddx", 0x2c000000, 0xfc00dfc0, "cXx(b),ft", pa10, 0}, |
| 1419 | { "flddx", 0x2c000000, 0xfc001fc0, "cXx(s,b),ft", pa10, 0}, |
| 1420 | { "fstwx", 0x24000200, 0xfc00df80, "cxfT,x(b)", pa10, FLAG_STRICT}, |
| 1421 | { "fstwx", 0x24000200, 0xfc001f80, "cxfT,x(s,b)", pa10, FLAG_STRICT}, |
| 1422 | { "fstwx", 0x24000200, 0xfc00d380, "cxcCfT,x(b)", pa11, FLAG_STRICT}, |
| 1423 | { "fstwx", 0x24000200, 0xfc001380, "cxcCfT,x(s,b)", pa11, FLAG_STRICT}, |
| 1424 | { "fstwx", 0x24000200, 0xfc00df80, "cxfT,x(b)", pa10, 0}, |
| 1425 | { "fstwx", 0x24000200, 0xfc001f80, "cxfT,x(s,b)", pa10, 0}, |
| 1426 | { "fstdx", 0x2c000200, 0xfc00dfc0, "cxft,x(b)", pa10, FLAG_STRICT}, |
| 1427 | { "fstdx", 0x2c000200, 0xfc001fc0, "cxft,x(s,b)", pa10, FLAG_STRICT}, |
| 1428 | { "fstdx", 0x2c000200, 0xfc00d3c0, "cxcCft,x(b)", pa11, FLAG_STRICT}, |
| 1429 | { "fstdx", 0x2c000200, 0xfc0013c0, "cxcCft,x(s,b)", pa11, FLAG_STRICT}, |
| 1430 | { "fstdx", 0x2c000200, 0xfc00dfc0, "cxft,x(b)", pa10, 0}, |
| 1431 | { "fstdx", 0x2c000200, 0xfc001fc0, "cxft,x(s,b)", pa10, 0}, |
| 1432 | { "fstqx", 0x3c000200, 0xfc00dfc0, "cxft,x(b)", pa10, 0}, |
| 1433 | { "fstqx", 0x3c000200, 0xfc001fc0, "cxft,x(s,b)", pa10, 0}, |
| 1434 | { "fldws", 0x24001000, 0xfc00df80, "cm5(b),fT", pa10, FLAG_STRICT}, |
| 1435 | { "fldws", 0x24001000, 0xfc001f80, "cm5(s,b),fT", pa10, FLAG_STRICT}, |
| 1436 | { "fldws", 0x24001000, 0xfc00d380, "cmcc5(b),fT", pa11, FLAG_STRICT}, |
| 1437 | { "fldws", 0x24001000, 0xfc001380, "cmcc5(s,b),fT", pa11, FLAG_STRICT}, |
| 1438 | { "fldws", 0x24001000, 0xfc00df80, "cm5(b),fT", pa10, 0}, |
| 1439 | { "fldws", 0x24001000, 0xfc001f80, "cm5(s,b),fT", pa10, 0}, |
| 1440 | { "fldds", 0x2c001000, 0xfc00dfc0, "cm5(b),ft", pa10, FLAG_STRICT}, |
| 1441 | { "fldds", 0x2c001000, 0xfc001fc0, "cm5(s,b),ft", pa10, FLAG_STRICT}, |
| 1442 | { "fldds", 0x2c001000, 0xfc00d3c0, "cmcc5(b),ft", pa11, FLAG_STRICT}, |
| 1443 | { "fldds", 0x2c001000, 0xfc0013c0, "cmcc5(s,b),ft", pa11, FLAG_STRICT}, |
| 1444 | { "fldds", 0x2c001000, 0xfc00dfc0, "cm5(b),ft", pa10, 0}, |
| 1445 | { "fldds", 0x2c001000, 0xfc001fc0, "cm5(s,b),ft", pa10, 0}, |
| 1446 | { "fstws", 0x24001200, 0xfc00df80, "cmfT,5(b)", pa10, FLAG_STRICT}, |
| 1447 | { "fstws", 0x24001200, 0xfc001f80, "cmfT,5(s,b)", pa10, FLAG_STRICT}, |
| 1448 | { "fstws", 0x24001200, 0xfc00d380, "cmcCfT,5(b)", pa11, FLAG_STRICT}, |
| 1449 | { "fstws", 0x24001200, 0xfc001380, "cmcCfT,5(s,b)", pa11, FLAG_STRICT}, |
| 1450 | { "fstws", 0x24001200, 0xfc00df80, "cmfT,5(b)", pa10, 0}, |
| 1451 | { "fstws", 0x24001200, 0xfc001f80, "cmfT,5(s,b)", pa10, 0}, |
| 1452 | { "fstds", 0x2c001200, 0xfc00dfc0, "cmft,5(b)", pa10, FLAG_STRICT}, |
| 1453 | { "fstds", 0x2c001200, 0xfc001fc0, "cmft,5(s,b)", pa10, FLAG_STRICT}, |
| 1454 | { "fstds", 0x2c001200, 0xfc00d3c0, "cmcCft,5(b)", pa11, FLAG_STRICT}, |
| 1455 | { "fstds", 0x2c001200, 0xfc0013c0, "cmcCft,5(s,b)", pa11, FLAG_STRICT}, |
| 1456 | { "fstds", 0x2c001200, 0xfc00dfc0, "cmft,5(b)", pa10, 0}, |
| 1457 | { "fstds", 0x2c001200, 0xfc001fc0, "cmft,5(s,b)", pa10, 0}, |
| 1458 | { "fstqs", 0x3c001200, 0xfc00dfc0, "cmft,5(b)", pa10, 0}, |
| 1459 | { "fstqs", 0x3c001200, 0xfc001fc0, "cmft,5(s,b)", pa10, 0}, |
| 1460 | { "fadd", 0x30000600, 0xfc00e7e0, "Ffa,fb,fT", pa10, 0}, |
| 1461 | { "fadd", 0x38000600, 0xfc00e720, "IfA,fB,fT", pa10, 0}, |
| 1462 | { "fsub", 0x30002600, 0xfc00e7e0, "Ffa,fb,fT", pa10, 0}, |
| 1463 | { "fsub", 0x38002600, 0xfc00e720, "IfA,fB,fT", pa10, 0}, |
| 1464 | { "fmpy", 0x30004600, 0xfc00e7e0, "Ffa,fb,fT", pa10, 0}, |
| 1465 | { "fmpy", 0x38004600, 0xfc00e720, "IfA,fB,fT", pa10, 0}, |
| 1466 | { "fdiv", 0x30006600, 0xfc00e7e0, "Ffa,fb,fT", pa10, 0}, |
| 1467 | { "fdiv", 0x38006600, 0xfc00e720, "IfA,fB,fT", pa10, 0}, |
| 1468 | { "fsqrt", 0x30008000, 0xfc1fe7e0, "Ffa,fT", pa10, 0}, |
| 1469 | { "fsqrt", 0x38008000, 0xfc1fe720, "FfA,fT", pa10, 0}, |
| 1470 | { "fabs", 0x30006000, 0xfc1fe7e0, "Ffa,fT", pa10, 0}, |
| 1471 | { "fabs", 0x38006000, 0xfc1fe720, "FfA,fT", pa10, 0}, |
| 1472 | { "frem", 0x30008600, 0xfc00e7e0, "Ffa,fb,fT", pa10, 0}, |
| 1473 | { "frem", 0x38008600, 0xfc00e720, "FfA,fB,fT", pa10, 0}, |
| 1474 | { "frnd", 0x3000a000, 0xfc1fe7e0, "Ffa,fT", pa10, 0}, |
| 1475 | { "frnd", 0x3800a000, 0xfc1fe720, "FfA,fT", pa10, 0}, |
| 1476 | { "fcpy", 0x30004000, 0xfc1fe7e0, "Ffa,fT", pa10, 0}, |
| 1477 | { "fcpy", 0x38004000, 0xfc1fe720, "FfA,fT", pa10, 0}, |
| 1478 | { "fcnvff", 0x30000200, 0xfc1f87e0, "FGfa,fT", pa10, 0}, |
| 1479 | { "fcnvff", 0x38000200, 0xfc1f8720, "FGfA,fT", pa10, 0}, |
| 1480 | { "fcnvxf", 0x30008200, 0xfc1f87e0, "FGfa,fT", pa10, 0}, |
| 1481 | { "fcnvxf", 0x38008200, 0xfc1f8720, "FGfA,fT", pa10, 0}, |
| 1482 | { "fcnvfx", 0x30010200, 0xfc1f87e0, "FGfa,fT", pa10, 0}, |
| 1483 | { "fcnvfx", 0x38010200, 0xfc1f8720, "FGfA,fT", pa10, 0}, |
| 1484 | { "fcnvfxt", 0x30018200, 0xfc1f87e0, "FGfa,fT", pa10, 0}, |
| 1485 | { "fcnvfxt", 0x38018200, 0xfc1f8720, "FGfA,fT", pa10, 0}, |
| 1486 | { "fmpyfadd", 0xb8000000, 0xfc000020, "IfA,fB,fC,fT", pa20, FLAG_STRICT}, |
| 1487 | { "fmpynfadd", 0xb8000020, 0xfc000020, "IfA,fB,fC,fT", pa20, FLAG_STRICT}, |
| 1488 | { "fneg", 0x3000c000, 0xfc1fe7e0, "Ffa,fT", pa20, FLAG_STRICT}, |
| 1489 | { "fneg", 0x3800c000, 0xfc1fe720, "IfA,fT", pa20, FLAG_STRICT}, |
| 1490 | { "fnegabs", 0x3000e000, 0xfc1fe7e0, "Ffa,fT", pa20, FLAG_STRICT}, |
| 1491 | { "fnegabs", 0x3800e000, 0xfc1fe720, "IfA,fT", pa20, FLAG_STRICT}, |
| 1492 | { "fcnv", 0x30000200, 0xfc1c0720, "{_fa,fT", pa20, FLAG_STRICT}, |
| 1493 | { "fcnv", 0x38000200, 0xfc1c0720, "FGfA,fT", pa20, FLAG_STRICT}, |
| 1494 | { "fcmp", 0x30000400, 0xfc00e7e0, "F?ffa,fb", pa10, FLAG_STRICT}, |
| 1495 | { "fcmp", 0x38000400, 0xfc00e720, "I?ffA,fB", pa10, FLAG_STRICT}, |
| 1496 | { "fcmp", 0x30000400, 0xfc0007e0, "F?ffa,fb,h", pa20, FLAG_STRICT}, |
| 1497 | { "fcmp", 0x38000400, 0xfc000720, "I?ffA,fB,h", pa20, FLAG_STRICT}, |
| 1498 | { "fcmp", 0x30000400, 0xfc00e7e0, "F?ffa,fb", pa10, 0}, |
| 1499 | { "fcmp", 0x38000400, 0xfc00e720, "I?ffA,fB", pa10, 0}, |
| 1500 | { "xmpyu", 0x38004700, 0xfc00e720, "fX,fB,fT", pa11, 0}, |
| 1501 | { "fmpyadd", 0x18000000, 0xfc000000, "Hfi,fj,fk,fl,fm", pa11, 0}, |
| 1502 | { "fmpysub", 0x98000000, 0xfc000000, "Hfi,fj,fk,fl,fm", pa11, 0}, |
| 1503 | { "ftest", 0x30002420, 0xffffffff, "", pa10, FLAG_STRICT}, |
| 1504 | { "ftest", 0x30002420, 0xffffffe0, ",=", pa20, FLAG_STRICT}, |
| 1505 | { "ftest", 0x30000420, 0xffff1fff, "m", pa20, FLAG_STRICT}, |
| 1506 | { "fid", 0x30000000, 0xffffffff, "", pa11, 0}, |
| 1507 | |
| 1508 | /* Performance Monitor Instructions. */ |
| 1509 | |
| 1510 | { "pmdis", 0x30000280, 0xffffffdf, "N", pa20, FLAG_STRICT}, |
| 1511 | { "pmenb", 0x30000680, 0xffffffff, "", pa20, FLAG_STRICT}, |
| 1512 | |
| 1513 | /* Assist Instructions. */ |
| 1514 | |
| 1515 | { "spop0", 0x10000000, 0xfc000600, "v,ON", pa10, 0}, |
| 1516 | { "spop1", 0x10000200, 0xfc000600, "v,oNt", pa10, 0}, |
| 1517 | { "spop2", 0x10000400, 0xfc000600, "v,1Nb", pa10, 0}, |
| 1518 | { "spop3", 0x10000600, 0xfc000600, "v,0Nx,b", pa10, 0}, |
| 1519 | { "copr", 0x30000000, 0xfc000000, "u,2N", pa10, 0}, |
| 1520 | { "cldw", 0x24000000, 0xfc00de00, "ucXx(b),t", pa10, FLAG_STRICT}, |
| 1521 | { "cldw", 0x24000000, 0xfc001e00, "ucXx(s,b),t", pa10, FLAG_STRICT}, |
| 1522 | { "cldw", 0x24000000, 0xfc00d200, "ucxccx(b),t", pa11, FLAG_STRICT}, |
| 1523 | { "cldw", 0x24000000, 0xfc001200, "ucxccx(s,b),t", pa11, FLAG_STRICT}, |
| 1524 | { "cldw", 0x24001000, 0xfc00d200, "ucocc@(b),t", pa20, FLAG_STRICT}, |
| 1525 | { "cldw", 0x24001000, 0xfc001200, "ucocc@(s,b),t", pa20, FLAG_STRICT}, |
| 1526 | { "cldw", 0x24001000, 0xfc00de00, "ucM5(b),t", pa10, FLAG_STRICT}, |
| 1527 | { "cldw", 0x24001000, 0xfc001e00, "ucM5(s,b),t", pa10, FLAG_STRICT}, |
| 1528 | { "cldw", 0x24001000, 0xfc00d200, "ucmcc5(b),t", pa11, FLAG_STRICT}, |
| 1529 | { "cldw", 0x24001000, 0xfc001200, "ucmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 1530 | { "cldd", 0x2c000000, 0xfc00de00, "ucXx(b),t", pa10, FLAG_STRICT}, |
| 1531 | { "cldd", 0x2c000000, 0xfc001e00, "ucXx(s,b),t", pa10, FLAG_STRICT}, |
| 1532 | { "cldd", 0x2c000000, 0xfc00d200, "ucxccx(b),t", pa11, FLAG_STRICT}, |
| 1533 | { "cldd", 0x2c000000, 0xfc001200, "ucxccx(s,b),t", pa11, FLAG_STRICT}, |
| 1534 | { "cldd", 0x2c001000, 0xfc00d200, "ucocc@(b),t", pa20, FLAG_STRICT}, |
| 1535 | { "cldd", 0x2c001000, 0xfc001200, "ucocc@(s,b),t", pa20, FLAG_STRICT}, |
| 1536 | { "cldd", 0x2c001000, 0xfc00de00, "ucM5(b),t", pa10, FLAG_STRICT}, |
| 1537 | { "cldd", 0x2c001000, 0xfc001e00, "ucM5(s,b),t", pa10, FLAG_STRICT}, |
| 1538 | { "cldd", 0x2c001000, 0xfc00d200, "ucmcc5(b),t", pa11, FLAG_STRICT}, |
| 1539 | { "cldd", 0x2c001000, 0xfc001200, "ucmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 1540 | { "cstw", 0x24000200, 0xfc00de00, "ucXt,x(b)", pa10, FLAG_STRICT}, |
| 1541 | { "cstw", 0x24000200, 0xfc001e00, "ucXt,x(s,b)", pa10, FLAG_STRICT}, |
| 1542 | { "cstw", 0x24000200, 0xfc00d200, "ucxcCt,x(b)", pa11, FLAG_STRICT}, |
| 1543 | { "cstw", 0x24000200, 0xfc001200, "ucxcCt,x(s,b)", pa11, FLAG_STRICT}, |
| 1544 | { "cstw", 0x24001200, 0xfc00d200, "ucocCt,@(b)", pa20, FLAG_STRICT}, |
| 1545 | { "cstw", 0x24001200, 0xfc001200, "ucocCt,@(s,b)", pa20, FLAG_STRICT}, |
| 1546 | { "cstw", 0x24001200, 0xfc00de00, "ucMt,5(b)", pa10, FLAG_STRICT}, |
| 1547 | { "cstw", 0x24001200, 0xfc001e00, "ucMt,5(s,b)", pa10, FLAG_STRICT}, |
| 1548 | { "cstw", 0x24001200, 0xfc00d200, "ucmcCt,5(b)", pa11, FLAG_STRICT}, |
| 1549 | { "cstw", 0x24001200, 0xfc001200, "ucmcCt,5(s,b)", pa11, FLAG_STRICT}, |
| 1550 | { "cstd", 0x2c000200, 0xfc00de00, "ucXt,x(b)", pa10, FLAG_STRICT}, |
| 1551 | { "cstd", 0x2c000200, 0xfc001e00, "ucXt,x(s,b)", pa10, FLAG_STRICT}, |
| 1552 | { "cstd", 0x2c000200, 0xfc00d200, "ucxcCt,x(b)", pa11, FLAG_STRICT}, |
| 1553 | { "cstd", 0x2c000200, 0xfc001200, "ucxcCt,x(s,b)", pa11, FLAG_STRICT}, |
| 1554 | { "cstd", 0x2c001200, 0xfc00d200, "ucocCt,@(b)", pa20, FLAG_STRICT}, |
| 1555 | { "cstd", 0x2c001200, 0xfc001200, "ucocCt,@(s,b)", pa20, FLAG_STRICT}, |
| 1556 | { "cstd", 0x2c001200, 0xfc00de00, "ucMt,5(b)", pa10, FLAG_STRICT}, |
| 1557 | { "cstd", 0x2c001200, 0xfc001e00, "ucMt,5(s,b)", pa10, FLAG_STRICT}, |
| 1558 | { "cstd", 0x2c001200, 0xfc00d200, "ucmcCt,5(b)", pa11, FLAG_STRICT}, |
| 1559 | { "cstd", 0x2c001200, 0xfc001200, "ucmcCt,5(s,b)", pa11, FLAG_STRICT}, |
| 1560 | { "cldwx", 0x24000000, 0xfc00de00, "ucXx(b),t", pa10, FLAG_STRICT}, |
| 1561 | { "cldwx", 0x24000000, 0xfc001e00, "ucXx(s,b),t", pa10, FLAG_STRICT}, |
| 1562 | { "cldwx", 0x24000000, 0xfc00d200, "ucxccx(b),t", pa11, FLAG_STRICT}, |
| 1563 | { "cldwx", 0x24000000, 0xfc001200, "ucxccx(s,b),t", pa11, FLAG_STRICT}, |
| 1564 | { "cldwx", 0x24000000, 0xfc00de00, "ucXx(b),t", pa10, 0}, |
| 1565 | { "cldwx", 0x24000000, 0xfc001e00, "ucXx(s,b),t", pa10, 0}, |
| 1566 | { "clddx", 0x2c000000, 0xfc00de00, "ucXx(b),t", pa10, FLAG_STRICT}, |
| 1567 | { "clddx", 0x2c000000, 0xfc001e00, "ucXx(s,b),t", pa10, FLAG_STRICT}, |
| 1568 | { "clddx", 0x2c000000, 0xfc00d200, "ucxccx(b),t", pa11, FLAG_STRICT}, |
| 1569 | { "clddx", 0x2c000000, 0xfc001200, "ucxccx(s,b),t", pa11, FLAG_STRICT}, |
| 1570 | { "clddx", 0x2c000000, 0xfc00de00, "ucXx(b),t", pa10, 0}, |
| 1571 | { "clddx", 0x2c000000, 0xfc001e00, "ucXx(s,b),t", pa10, 0}, |
| 1572 | { "cstwx", 0x24000200, 0xfc00de00, "ucXt,x(b)", pa10, FLAG_STRICT}, |
| 1573 | { "cstwx", 0x24000200, 0xfc001e00, "ucXt,x(s,b)", pa10, FLAG_STRICT}, |
| 1574 | { "cstwx", 0x24000200, 0xfc00d200, "ucxcCt,x(b)", pa11, FLAG_STRICT}, |
| 1575 | { "cstwx", 0x24000200, 0xfc001200, "ucxcCt,x(s,b)", pa11, FLAG_STRICT}, |
| 1576 | { "cstwx", 0x24000200, 0xfc00de00, "ucXt,x(b)", pa10, 0}, |
| 1577 | { "cstwx", 0x24000200, 0xfc001e00, "ucXt,x(s,b)", pa10, 0}, |
| 1578 | { "cstdx", 0x2c000200, 0xfc00de00, "ucXt,x(b)", pa10, FLAG_STRICT}, |
| 1579 | { "cstdx", 0x2c000200, 0xfc001e00, "ucXt,x(s,b)", pa10, FLAG_STRICT}, |
| 1580 | { "cstdx", 0x2c000200, 0xfc00d200, "ucxcCt,x(b)", pa11, FLAG_STRICT}, |
| 1581 | { "cstdx", 0x2c000200, 0xfc001200, "ucxcCt,x(s,b)", pa11, FLAG_STRICT}, |
| 1582 | { "cstdx", 0x2c000200, 0xfc00de00, "ucXt,x(b)", pa10, 0}, |
| 1583 | { "cstdx", 0x2c000200, 0xfc001e00, "ucXt,x(s,b)", pa10, 0}, |
| 1584 | { "cldws", 0x24001000, 0xfc00de00, "ucM5(b),t", pa10, FLAG_STRICT}, |
| 1585 | { "cldws", 0x24001000, 0xfc001e00, "ucM5(s,b),t", pa10, FLAG_STRICT}, |
| 1586 | { "cldws", 0x24001000, 0xfc00d200, "ucmcc5(b),t", pa11, FLAG_STRICT}, |
| 1587 | { "cldws", 0x24001000, 0xfc001200, "ucmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 1588 | { "cldws", 0x24001000, 0xfc00de00, "ucM5(b),t", pa10, 0}, |
| 1589 | { "cldws", 0x24001000, 0xfc001e00, "ucM5(s,b),t", pa10, 0}, |
| 1590 | { "cldds", 0x2c001000, 0xfc00de00, "ucM5(b),t", pa10, FLAG_STRICT}, |
| 1591 | { "cldds", 0x2c001000, 0xfc001e00, "ucM5(s,b),t", pa10, FLAG_STRICT}, |
| 1592 | { "cldds", 0x2c001000, 0xfc00d200, "ucmcc5(b),t", pa11, FLAG_STRICT}, |
| 1593 | { "cldds", 0x2c001000, 0xfc001200, "ucmcc5(s,b),t", pa11, FLAG_STRICT}, |
| 1594 | { "cldds", 0x2c001000, 0xfc00de00, "ucM5(b),t", pa10, 0}, |
| 1595 | { "cldds", 0x2c001000, 0xfc001e00, "ucM5(s,b),t", pa10, 0}, |
| 1596 | { "cstws", 0x24001200, 0xfc00de00, "ucMt,5(b)", pa10, FLAG_STRICT}, |
| 1597 | { "cstws", 0x24001200, 0xfc001e00, "ucMt,5(s,b)", pa10, FLAG_STRICT}, |
| 1598 | { "cstws", 0x24001200, 0xfc00d200, "ucmcCt,5(b)", pa11, FLAG_STRICT}, |
| 1599 | { "cstws", 0x24001200, 0xfc001200, "ucmcCt,5(s,b)", pa11, FLAG_STRICT}, |
| 1600 | { "cstws", 0x24001200, 0xfc00de00, "ucMt,5(b)", pa10, 0}, |
| 1601 | { "cstws", 0x24001200, 0xfc001e00, "ucMt,5(s,b)", pa10, 0}, |
| 1602 | { "cstds", 0x2c001200, 0xfc00de00, "ucMt,5(b)", pa10, FLAG_STRICT}, |
| 1603 | { "cstds", 0x2c001200, 0xfc001e00, "ucMt,5(s,b)", pa10, FLAG_STRICT}, |
| 1604 | { "cstds", 0x2c001200, 0xfc00d200, "ucmcCt,5(b)", pa11, FLAG_STRICT}, |
| 1605 | { "cstds", 0x2c001200, 0xfc001200, "ucmcCt,5(s,b)", pa11, FLAG_STRICT}, |
| 1606 | { "cstds", 0x2c001200, 0xfc00de00, "ucMt,5(b)", pa10, 0}, |
| 1607 | { "cstds", 0x2c001200, 0xfc001e00, "ucMt,5(s,b)", pa10, 0}, |
| 1608 | |
| 1609 | /* More pseudo instructions which must follow the main table. */ |
| 1610 | { "call", 0xe800f000, 0xfc1ffffd, "n(b)", pa20, FLAG_STRICT}, |
| 1611 | { "call", 0xe800a000, 0xffe0e000, "nW", pa10, FLAG_STRICT}, |
| 1612 | { "ret", 0xe840d000, 0xfffffffd, "n", pa20, FLAG_STRICT}, |
| 1613 | |
| 1614 | }; |
| 1615 | |
| 1616 | #define NUMOPCODES ((sizeof pa_opcodes)/(sizeof pa_opcodes[0])) |
| 1617 | |
| 1618 | /* SKV 12/18/92. Added some denotations for various operands. */ |
| 1619 | |
| 1620 | #define PA_IMM11_AT_31 'i' |
| 1621 | #define PA_IMM14_AT_31 'j' |
| 1622 | #define PA_IMM21_AT_31 'k' |
| 1623 | #define PA_DISP12 'w' |
| 1624 | #define PA_DISP17 'W' |
| 1625 | |
| 1626 | #define N_HPPA_OPERAND_FORMATS 5 |
| 1627 | |
| 1628 | /* Integer register names, indexed by the numbers which appear in the |
| 1629 | opcodes. */ |
| 1630 | static const char *const reg_names[] = |
| 1631 | { |
| 1632 | "flags", "r1", "rp", "r3", "r4", "r5", "r6", "r7", "r8", "r9", |
| 1633 | "r10", "r11", "r12", "r13", "r14", "r15", "r16", "r17", "r18", "r19", |
| 1634 | "r20", "r21", "r22", "r23", "r24", "r25", "r26", "dp", "ret0", "ret1", |
| 1635 | "sp", "r31" |
| 1636 | }; |
| 1637 | |
| 1638 | /* Floating point register names, indexed by the numbers which appear in the |
| 1639 | opcodes. */ |
| 1640 | static const char *const fp_reg_names[] = |
| 1641 | { |
| 1642 | "fpsr", "fpe2", "fpe4", "fpe6", |
| 1643 | "fr4", "fr5", "fr6", "fr7", "fr8", |
| 1644 | "fr9", "fr10", "fr11", "fr12", "fr13", "fr14", "fr15", |
| 1645 | "fr16", "fr17", "fr18", "fr19", "fr20", "fr21", "fr22", "fr23", |
| 1646 | "fr24", "fr25", "fr26", "fr27", "fr28", "fr29", "fr30", "fr31" |
| 1647 | }; |
| 1648 | |
| 1649 | typedef unsigned int CORE_ADDR; |
| 1650 | |
| 1651 | /* Get at various relevent fields of an instruction word. */ |
| 1652 | |
| 1653 | #define MASK_5 0x1f |
| 1654 | #define MASK_10 0x3ff |
| 1655 | #define MASK_11 0x7ff |
| 1656 | #define MASK_14 0x3fff |
| 1657 | #define MASK_16 0xffff |
| 1658 | #define MASK_21 0x1fffff |
| 1659 | |
| 1660 | /* These macros get bit fields using HP's numbering (MSB = 0). */ |
| 1661 | |
| 1662 | #define GET_FIELD(X, FROM, TO) \ |
| 1663 | ((X) >> (31 - (TO)) & ((1 << ((TO) - (FROM) + 1)) - 1)) |
| 1664 | |
| 1665 | #define GET_BIT(X, WHICH) \ |
| 1666 | GET_FIELD (X, WHICH, WHICH) |
| 1667 | |
| 1668 | /* Some of these have been converted to 2-d arrays because they |
| 1669 | consume less storage this way. If the maintenance becomes a |
| 1670 | problem, convert them back to const 1-d pointer arrays. */ |
| 1671 | static const char *const control_reg[] = |
| 1672 | { |
| 1673 | "rctr", "cr1", "cr2", "cr3", "cr4", "cr5", "cr6", "cr7", |
| 1674 | "pidr1", "pidr2", "ccr", "sar", "pidr3", "pidr4", |
| 1675 | "iva", "eiem", "itmr", "pcsq", "pcoq", "iir", "isr", |
| 1676 | "ior", "ipsw", "eirr", "tr0", "tr1", "tr2", "tr3", |
| 1677 | "tr4", "tr5", "tr6", "tr7" |
| 1678 | }; |
| 1679 | |
| 1680 | static const char *const compare_cond_names[] = |
| 1681 | { |
| 1682 | "", ",=", ",<", ",<=", ",<<", ",<<=", ",sv", ",od", |
| 1683 | ",tr", ",<>", ",>=", ",>", ",>>=", ",>>", ",nsv", ",ev" |
| 1684 | }; |
| 1685 | static const char *const compare_cond_64_names[] = |
| 1686 | { |
| 1687 | "", ",*=", ",*<", ",*<=", ",*<<", ",*<<=", ",*sv", ",*od", |
| 1688 | ",*tr", ",*<>", ",*>=", ",*>", ",*>>=", ",*>>", ",*nsv", ",*ev" |
| 1689 | }; |
| 1690 | static const char *const cmpib_cond_64_names[] = |
| 1691 | { |
| 1692 | ",*<<", ",*=", ",*<", ",*<=", ",*>>=", ",*<>", ",*>=", ",*>" |
| 1693 | }; |
| 1694 | static const char *const add_cond_names[] = |
| 1695 | { |
| 1696 | "", ",=", ",<", ",<=", ",nuv", ",znv", ",sv", ",od", |
| 1697 | ",tr", ",<>", ",>=", ",>", ",uv", ",vnz", ",nsv", ",ev" |
| 1698 | }; |
| 1699 | static const char *const add_cond_64_names[] = |
| 1700 | { |
| 1701 | "", ",*=", ",*<", ",*<=", ",*nuv", ",*znv", ",*sv", ",*od", |
| 1702 | ",*tr", ",*<>", ",*>=", ",*>", ",*uv", ",*vnz", ",*nsv", ",*ev" |
| 1703 | }; |
| 1704 | static const char *const wide_add_cond_names[] = |
| 1705 | { |
| 1706 | "", ",=", ",<", ",<=", ",nuv", ",*=", ",*<", ",*<=", |
| 1707 | ",tr", ",<>", ",>=", ",>", ",uv", ",*<>", ",*>=", ",*>" |
| 1708 | }; |
| 1709 | static const char *const logical_cond_names[] = |
| 1710 | { |
| 1711 | "", ",=", ",<", ",<=", 0, 0, 0, ",od", |
| 1712 | ",tr", ",<>", ",>=", ",>", 0, 0, 0, ",ev"}; |
| 1713 | static const char *const logical_cond_64_names[] = |
| 1714 | { |
| 1715 | "", ",*=", ",*<", ",*<=", 0, 0, 0, ",*od", |
| 1716 | ",*tr", ",*<>", ",*>=", ",*>", 0, 0, 0, ",*ev"}; |
| 1717 | static const char *const unit_cond_names[] = |
| 1718 | { |
| 1719 | "", ",swz", ",sbz", ",shz", ",sdc", ",swc", ",sbc", ",shc", |
| 1720 | ",tr", ",nwz", ",nbz", ",nhz", ",ndc", ",nwc", ",nbc", ",nhc" |
| 1721 | }; |
| 1722 | static const char *const unit_cond_64_names[] = |
| 1723 | { |
| 1724 | "", ",*swz", ",*sbz", ",*shz", ",*sdc", ",*swc", ",*sbc", ",*shc", |
| 1725 | ",*tr", ",*nwz", ",*nbz", ",*nhz", ",*ndc", ",*nwc", ",*nbc", ",*nhc" |
| 1726 | }; |
| 1727 | static const char *const shift_cond_names[] = |
| 1728 | { |
| 1729 | "", ",=", ",<", ",od", ",tr", ",<>", ",>=", ",ev" |
| 1730 | }; |
| 1731 | static const char *const shift_cond_64_names[] = |
| 1732 | { |
| 1733 | "", ",*=", ",*<", ",*od", ",*tr", ",*<>", ",*>=", ",*ev" |
| 1734 | }; |
| 1735 | static const char *const bb_cond_64_names[] = |
| 1736 | { |
| 1737 | ",*<", ",*>=" |
| 1738 | }; |
| 1739 | static const char *const index_compl_names[] = {"", ",m", ",s", ",sm"}; |
| 1740 | static const char *const short_ldst_compl_names[] = {"", ",ma", "", ",mb"}; |
| 1741 | static const char *const short_bytes_compl_names[] = |
| 1742 | { |
| 1743 | "", ",b,m", ",e", ",e,m" |
| 1744 | }; |
| 1745 | static const char *const float_format_names[] = {",sgl", ",dbl", "", ",quad"}; |
| 1746 | static const char *const fcnv_fixed_names[] = {",w", ",dw", "", ",qw"}; |
| 1747 | static const char *const fcnv_ufixed_names[] = {",uw", ",udw", "", ",uqw"}; |
| 1748 | static const char *const float_comp_names[] = |
| 1749 | { |
| 1750 | ",false?", ",false", ",?", ",!<=>", ",=", ",=t", ",?=", ",!<>", |
| 1751 | ",!?>=", ",<", ",?<", ",!>=", ",!?>", ",<=", ",?<=", ",!>", |
| 1752 | ",!?<=", ",>", ",?>", ",!<=", ",!?<", ",>=", ",?>=", ",!<", |
| 1753 | ",!?=", ",<>", ",!=", ",!=t", ",!?", ",<=>", ",true?", ",true" |
| 1754 | }; |
| 1755 | static const char *const signed_unsigned_names[] = {",u", ",s"}; |
| 1756 | static const char *const mix_half_names[] = {",l", ",r"}; |
| 1757 | static const char *const saturation_names[] = {",us", ",ss", 0, ""}; |
| 1758 | static const char *const read_write_names[] = {",r", ",w"}; |
| 1759 | static const char *const add_compl_names[] = { 0, "", ",l", ",tsv" }; |
| 1760 | |
| 1761 | /* For a bunch of different instructions form an index into a |
| 1762 | completer name table. */ |
| 1763 | #define GET_COMPL(insn) (GET_FIELD (insn, 26, 26) | \ |
| 1764 | GET_FIELD (insn, 18, 18) << 1) |
| 1765 | |
| 1766 | #define GET_COND(insn) (GET_FIELD ((insn), 16, 18) + \ |
| 1767 | (GET_FIELD ((insn), 19, 19) ? 8 : 0)) |
| 1768 | |
| 1769 | /* Utility function to print registers. Put these first, so gcc's function |
| 1770 | inlining can do its stuff. */ |
| 1771 | |
| 1772 | #define fputs_filtered(STR,F) (*info->fprintf_func) (info->stream, "%s", STR) |
| 1773 | |
| 1774 | static void |
| 1775 | fput_reg (unsigned reg, disassemble_info *info) |
| 1776 | { |
| 1777 | (*info->fprintf_func) (info->stream, reg ? reg_names[reg] : "r0"); |
| 1778 | } |
| 1779 | |
| 1780 | static void |
| 1781 | fput_fp_reg (unsigned reg, disassemble_info *info) |
| 1782 | { |
| 1783 | (*info->fprintf_func) (info->stream, reg ? fp_reg_names[reg] : "fr0"); |
| 1784 | } |
| 1785 | |
| 1786 | static void |
| 1787 | fput_fp_reg_r (unsigned reg, disassemble_info *info) |
| 1788 | { |
| 1789 | /* Special case floating point exception registers. */ |
| 1790 | if (reg < 4) |
| 1791 | (*info->fprintf_func) (info->stream, "fpe%d", reg * 2 + 1); |
| 1792 | else |
| 1793 | (*info->fprintf_func) (info->stream, "%sR", |
| 1794 | reg ? fp_reg_names[reg] : "fr0"); |
| 1795 | } |
| 1796 | |
| 1797 | static void |
| 1798 | fput_creg (unsigned reg, disassemble_info *info) |
| 1799 | { |
| 1800 | (*info->fprintf_func) (info->stream, control_reg[reg]); |
| 1801 | } |
| 1802 | |
| 1803 | /* Print constants with sign. */ |
| 1804 | |
| 1805 | static void |
| 1806 | fput_const (unsigned num, disassemble_info *info) |
| 1807 | { |
| 1808 | if ((int) num < 0) |
| 1809 | (*info->fprintf_func) (info->stream, "-%x", - (int) num); |
| 1810 | else |
| 1811 | (*info->fprintf_func) (info->stream, "%x", num); |
| 1812 | } |
| 1813 | |
| 1814 | /* Routines to extract various sized constants out of hppa |
| 1815 | instructions. */ |
| 1816 | |
| 1817 | /* Extract a 3-bit space register number from a be, ble, mtsp or mfsp. */ |
| 1818 | static int |
| 1819 | extract_3 (unsigned word) |
| 1820 | { |
| 1821 | return GET_FIELD (word, 18, 18) << 2 | GET_FIELD (word, 16, 17); |
| 1822 | } |
| 1823 | |
| 1824 | static int |
| 1825 | extract_5_load (unsigned word) |
| 1826 | { |
| 1827 | return low_sign_extend (word >> 16 & MASK_5, 5); |
| 1828 | } |
| 1829 | |
| 1830 | /* Extract the immediate field from a st{bhw}s instruction. */ |
| 1831 | |
| 1832 | static int |
| 1833 | extract_5_store (unsigned word) |
| 1834 | { |
| 1835 | return low_sign_extend (word & MASK_5, 5); |
| 1836 | } |
| 1837 | |
| 1838 | /* Extract the immediate field from a break instruction. */ |
| 1839 | |
| 1840 | static unsigned |
| 1841 | extract_5r_store (unsigned word) |
| 1842 | { |
| 1843 | return (word & MASK_5); |
| 1844 | } |
| 1845 | |
| 1846 | /* Extract the immediate field from a {sr}sm instruction. */ |
| 1847 | |
| 1848 | static unsigned |
| 1849 | extract_5R_store (unsigned word) |
| 1850 | { |
| 1851 | return (word >> 16 & MASK_5); |
| 1852 | } |
| 1853 | |
| 1854 | /* Extract the 10 bit immediate field from a {sr}sm instruction. */ |
| 1855 | |
| 1856 | static unsigned |
| 1857 | extract_10U_store (unsigned word) |
| 1858 | { |
| 1859 | return (word >> 16 & MASK_10); |
| 1860 | } |
| 1861 | |
| 1862 | /* Extract the immediate field from a bb instruction. */ |
| 1863 | |
| 1864 | static unsigned |
| 1865 | extract_5Q_store (unsigned word) |
| 1866 | { |
| 1867 | return (word >> 21 & MASK_5); |
| 1868 | } |
| 1869 | |
| 1870 | /* Extract an 11 bit immediate field. */ |
| 1871 | |
| 1872 | static int |
| 1873 | extract_11 (unsigned word) |
| 1874 | { |
| 1875 | return low_sign_extend (word & MASK_11, 11); |
| 1876 | } |
| 1877 | |
| 1878 | /* Extract a 14 bit immediate field. */ |
| 1879 | |
| 1880 | static int |
| 1881 | extract_14 (unsigned word) |
| 1882 | { |
| 1883 | return low_sign_extend (word & MASK_14, 14); |
| 1884 | } |
| 1885 | |
| 1886 | /* Extract a 16 bit immediate field (PA2.0 wide only). */ |
| 1887 | |
| 1888 | static int |
| 1889 | extract_16 (unsigned word) |
| 1890 | { |
| 1891 | int m15, m0, m1; |
| 1892 | |
| 1893 | m0 = GET_BIT (word, 16); |
| 1894 | m1 = GET_BIT (word, 17); |
| 1895 | m15 = GET_BIT (word, 31); |
| 1896 | word = (word >> 1) & 0x1fff; |
| 1897 | word = word | (m15 << 15) | ((m15 ^ m0) << 14) | ((m15 ^ m1) << 13); |
| 1898 | return sign_extend (word, 16); |
| 1899 | } |
| 1900 | |
| 1901 | /* Extract a 21 bit constant. */ |
| 1902 | |
| 1903 | static int |
| 1904 | extract_21 (unsigned word) |
| 1905 | { |
| 1906 | int val; |
| 1907 | |
| 1908 | word &= MASK_21; |
| 1909 | word <<= 11; |
| 1910 | val = GET_FIELD (word, 20, 20); |
| 1911 | val <<= 11; |
| 1912 | val |= GET_FIELD (word, 9, 19); |
| 1913 | val <<= 2; |
| 1914 | val |= GET_FIELD (word, 5, 6); |
| 1915 | val <<= 5; |
| 1916 | val |= GET_FIELD (word, 0, 4); |
| 1917 | val <<= 2; |
| 1918 | val |= GET_FIELD (word, 7, 8); |
| 1919 | return sign_extend (val, 21) << 11; |
| 1920 | } |
| 1921 | |
| 1922 | /* Extract a 12 bit constant from branch instructions. */ |
| 1923 | |
| 1924 | static int |
| 1925 | extract_12 (unsigned word) |
| 1926 | { |
| 1927 | return sign_extend (GET_FIELD (word, 19, 28) |
| 1928 | | GET_FIELD (word, 29, 29) << 10 |
| 1929 | | (word & 0x1) << 11, 12) << 2; |
| 1930 | } |
| 1931 | |
| 1932 | /* Extract a 17 bit constant from branch instructions, returning the |
| 1933 | 19 bit signed value. */ |
| 1934 | |
| 1935 | static int |
| 1936 | extract_17 (unsigned word) |
| 1937 | { |
| 1938 | return sign_extend (GET_FIELD (word, 19, 28) |
| 1939 | | GET_FIELD (word, 29, 29) << 10 |
| 1940 | | GET_FIELD (word, 11, 15) << 11 |
| 1941 | | (word & 0x1) << 16, 17) << 2; |
| 1942 | } |
| 1943 | |
| 1944 | static int |
| 1945 | extract_22 (unsigned word) |
| 1946 | { |
| 1947 | return sign_extend (GET_FIELD (word, 19, 28) |
| 1948 | | GET_FIELD (word, 29, 29) << 10 |
| 1949 | | GET_FIELD (word, 11, 15) << 11 |
| 1950 | | GET_FIELD (word, 6, 10) << 16 |
| 1951 | | (word & 0x1) << 21, 22) << 2; |
| 1952 | } |
| 1953 | |
| 1954 | /* Print one instruction. */ |
| 1955 | |
| 1956 | int |
| 1957 | print_insn_hppa (bfd_vma memaddr, disassemble_info *info) |
| 1958 | { |
| 1959 | bfd_byte buffer[4]; |
| 1960 | unsigned int insn, i; |
| 1961 | |
| 1962 | { |
| 1963 | int status = |
| 1964 | (*info->read_memory_func) (memaddr, buffer, sizeof (buffer), info); |
| 1965 | if (status != 0) |
| 1966 | { |
| 1967 | (*info->memory_error_func) (status, memaddr, info); |
| 1968 | return -1; |
| 1969 | } |
| 1970 | } |
| 1971 | |
| 1972 | insn = bfd_getb32 (buffer); |
| 1973 | |
| 1974 | for (i = 0; i < NUMOPCODES; ++i) |
| 1975 | { |
| 1976 | const struct pa_opcode *opcode = &pa_opcodes[i]; |
| 1977 | |
| 1978 | if ((insn & opcode->mask) == opcode->match) |
| 1979 | { |
| 1980 | const char *s; |
| 1981 | #ifndef BFD64 |
| 1982 | if (opcode->arch == pa20w) |
| 1983 | continue; |
| 1984 | #endif |
| 1985 | (*info->fprintf_func) (info->stream, "%s", opcode->name); |
| 1986 | |
| 1987 | if (!strchr ("cfCY?-+nHNZFIuv{", opcode->args[0])) |
| 1988 | (*info->fprintf_func) (info->stream, " "); |
| 1989 | for (s = opcode->args; *s != '\0'; ++s) |
| 1990 | { |
| 1991 | switch (*s) |
| 1992 | { |
| 1993 | case 'x': |
| 1994 | fput_reg (GET_FIELD (insn, 11, 15), info); |
| 1995 | break; |
| 1996 | case 'a': |
| 1997 | case 'b': |
| 1998 | fput_reg (GET_FIELD (insn, 6, 10), info); |
| 1999 | break; |
| 2000 | case '^': |
| 2001 | fput_creg (GET_FIELD (insn, 6, 10), info); |
| 2002 | break; |
| 2003 | case 't': |
| 2004 | fput_reg (GET_FIELD (insn, 27, 31), info); |
| 2005 | break; |
| 2006 | |
| 2007 | /* Handle floating point registers. */ |
| 2008 | case 'f': |
| 2009 | switch (*++s) |
| 2010 | { |
| 2011 | case 't': |
| 2012 | fput_fp_reg (GET_FIELD (insn, 27, 31), info); |
| 2013 | break; |
| 2014 | case 'T': |
| 2015 | if (GET_FIELD (insn, 25, 25)) |
| 2016 | fput_fp_reg_r (GET_FIELD (insn, 27, 31), info); |
| 2017 | else |
| 2018 | fput_fp_reg (GET_FIELD (insn, 27, 31), info); |
| 2019 | break; |
| 2020 | case 'a': |
| 2021 | if (GET_FIELD (insn, 25, 25)) |
| 2022 | fput_fp_reg_r (GET_FIELD (insn, 6, 10), info); |
| 2023 | else |
| 2024 | fput_fp_reg (GET_FIELD (insn, 6, 10), info); |
| 2025 | break; |
| 2026 | |
| 2027 | /* 'fA' will not generate a space before the regsiter |
| 2028 | name. Normally that is fine. Except that it |
| 2029 | causes problems with xmpyu which has no FP format |
| 2030 | completer. */ |
| 2031 | case 'X': |
| 2032 | fputs_filtered (" ", info); |
| 2033 | /* FALLTHRU */ |
| 2034 | |
| 2035 | case 'A': |
| 2036 | if (GET_FIELD (insn, 24, 24)) |
| 2037 | fput_fp_reg_r (GET_FIELD (insn, 6, 10), info); |
| 2038 | else |
| 2039 | fput_fp_reg (GET_FIELD (insn, 6, 10), info); |
| 2040 | break; |
| 2041 | case 'b': |
| 2042 | if (GET_FIELD (insn, 25, 25)) |
| 2043 | fput_fp_reg_r (GET_FIELD (insn, 11, 15), info); |
| 2044 | else |
| 2045 | fput_fp_reg (GET_FIELD (insn, 11, 15), info); |
| 2046 | break; |
| 2047 | case 'B': |
| 2048 | if (GET_FIELD (insn, 19, 19)) |
| 2049 | fput_fp_reg_r (GET_FIELD (insn, 11, 15), info); |
| 2050 | else |
| 2051 | fput_fp_reg (GET_FIELD (insn, 11, 15), info); |
| 2052 | break; |
| 2053 | case 'C': |
| 2054 | { |
| 2055 | int reg = GET_FIELD (insn, 21, 22); |
| 2056 | reg |= GET_FIELD (insn, 16, 18) << 2; |
| 2057 | if (GET_FIELD (insn, 23, 23) != 0) |
| 2058 | fput_fp_reg_r (reg, info); |
| 2059 | else |
| 2060 | fput_fp_reg (reg, info); |
| 2061 | break; |
| 2062 | } |
| 2063 | case 'i': |
| 2064 | { |
| 2065 | int reg = GET_FIELD (insn, 6, 10); |
| 2066 | |
| 2067 | reg |= (GET_FIELD (insn, 26, 26) << 4); |
| 2068 | fput_fp_reg (reg, info); |
| 2069 | break; |
| 2070 | } |
| 2071 | case 'j': |
| 2072 | { |
| 2073 | int reg = GET_FIELD (insn, 11, 15); |
| 2074 | |
| 2075 | reg |= (GET_FIELD (insn, 26, 26) << 4); |
| 2076 | fput_fp_reg (reg, info); |
| 2077 | break; |
| 2078 | } |
| 2079 | case 'k': |
| 2080 | { |
| 2081 | int reg = GET_FIELD (insn, 27, 31); |
| 2082 | |
| 2083 | reg |= (GET_FIELD (insn, 26, 26) << 4); |
| 2084 | fput_fp_reg (reg, info); |
| 2085 | break; |
| 2086 | } |
| 2087 | case 'l': |
| 2088 | { |
| 2089 | int reg = GET_FIELD (insn, 21, 25); |
| 2090 | |
| 2091 | reg |= (GET_FIELD (insn, 26, 26) << 4); |
| 2092 | fput_fp_reg (reg, info); |
| 2093 | break; |
| 2094 | } |
| 2095 | case 'm': |
| 2096 | { |
| 2097 | int reg = GET_FIELD (insn, 16, 20); |
| 2098 | |
| 2099 | reg |= (GET_FIELD (insn, 26, 26) << 4); |
| 2100 | fput_fp_reg (reg, info); |
| 2101 | break; |
| 2102 | } |
| 2103 | |
| 2104 | /* 'fe' will not generate a space before the register |
| 2105 | name. Normally that is fine. Except that it |
| 2106 | causes problems with fstw fe,y(b) which has no FP |
| 2107 | format completer. */ |
| 2108 | case 'E': |
| 2109 | fputs_filtered (" ", info); |
| 2110 | /* FALLTHRU */ |
| 2111 | |
| 2112 | case 'e': |
| 2113 | if (GET_FIELD (insn, 30, 30)) |
| 2114 | fput_fp_reg_r (GET_FIELD (insn, 11, 15), info); |
| 2115 | else |
| 2116 | fput_fp_reg (GET_FIELD (insn, 11, 15), info); |
| 2117 | break; |
| 2118 | case 'x': |
| 2119 | fput_fp_reg (GET_FIELD (insn, 11, 15), info); |
| 2120 | break; |
| 2121 | } |
| 2122 | break; |
| 2123 | |
| 2124 | case '5': |
| 2125 | fput_const (extract_5_load (insn), info); |
| 2126 | break; |
| 2127 | case 's': |
| 2128 | { |
| 2129 | int space = GET_FIELD (insn, 16, 17); |
| 2130 | /* Zero means implicit addressing, not use of sr0. */ |
| 2131 | if (space != 0) |
| 2132 | (*info->fprintf_func) (info->stream, "sr%d", space); |
| 2133 | } |
| 2134 | break; |
| 2135 | |
| 2136 | case 'S': |
| 2137 | (*info->fprintf_func) (info->stream, "sr%d", |
| 2138 | extract_3 (insn)); |
| 2139 | break; |
| 2140 | |
| 2141 | /* Handle completers. */ |
| 2142 | case 'c': |
| 2143 | switch (*++s) |
| 2144 | { |
| 2145 | case 'x': |
| 2146 | (*info->fprintf_func) |
| 2147 | (info->stream, "%s", |
| 2148 | index_compl_names[GET_COMPL (insn)]); |
| 2149 | break; |
| 2150 | case 'X': |
| 2151 | (*info->fprintf_func) |
| 2152 | (info->stream, "%s ", |
| 2153 | index_compl_names[GET_COMPL (insn)]); |
| 2154 | break; |
| 2155 | case 'm': |
| 2156 | (*info->fprintf_func) |
| 2157 | (info->stream, "%s", |
| 2158 | short_ldst_compl_names[GET_COMPL (insn)]); |
| 2159 | break; |
| 2160 | case 'M': |
| 2161 | (*info->fprintf_func) |
| 2162 | (info->stream, "%s ", |
| 2163 | short_ldst_compl_names[GET_COMPL (insn)]); |
| 2164 | break; |
| 2165 | case 'A': |
| 2166 | (*info->fprintf_func) |
| 2167 | (info->stream, "%s ", |
| 2168 | short_bytes_compl_names[GET_COMPL (insn)]); |
| 2169 | break; |
| 2170 | case 's': |
| 2171 | (*info->fprintf_func) |
| 2172 | (info->stream, "%s", |
| 2173 | short_bytes_compl_names[GET_COMPL (insn)]); |
| 2174 | break; |
| 2175 | case 'c': |
| 2176 | case 'C': |
| 2177 | switch (GET_FIELD (insn, 20, 21)) |
| 2178 | { |
| 2179 | case 1: |
| 2180 | (*info->fprintf_func) (info->stream, ",bc "); |
| 2181 | break; |
| 2182 | case 2: |
| 2183 | (*info->fprintf_func) (info->stream, ",sl "); |
| 2184 | break; |
| 2185 | default: |
| 2186 | (*info->fprintf_func) (info->stream, " "); |
| 2187 | } |
| 2188 | break; |
| 2189 | case 'd': |
| 2190 | switch (GET_FIELD (insn, 20, 21)) |
| 2191 | { |
| 2192 | case 1: |
| 2193 | (*info->fprintf_func) (info->stream, ",co "); |
| 2194 | break; |
| 2195 | default: |
| 2196 | (*info->fprintf_func) (info->stream, " "); |
| 2197 | } |
| 2198 | break; |
| 2199 | case 'o': |
| 2200 | (*info->fprintf_func) (info->stream, ",o"); |
| 2201 | break; |
| 2202 | case 'g': |
| 2203 | (*info->fprintf_func) (info->stream, ",gate"); |
| 2204 | break; |
| 2205 | case 'p': |
| 2206 | (*info->fprintf_func) (info->stream, ",l,push"); |
| 2207 | break; |
| 2208 | case 'P': |
| 2209 | (*info->fprintf_func) (info->stream, ",pop"); |
| 2210 | break; |
| 2211 | case 'l': |
| 2212 | case 'L': |
| 2213 | (*info->fprintf_func) (info->stream, ",l"); |
| 2214 | break; |
| 2215 | case 'w': |
| 2216 | (*info->fprintf_func) |
| 2217 | (info->stream, "%s ", |
| 2218 | read_write_names[GET_FIELD (insn, 25, 25)]); |
| 2219 | break; |
| 2220 | case 'W': |
| 2221 | (*info->fprintf_func) (info->stream, ",w "); |
| 2222 | break; |
| 2223 | case 'r': |
| 2224 | if (GET_FIELD (insn, 23, 26) == 5) |
| 2225 | (*info->fprintf_func) (info->stream, ",r"); |
| 2226 | break; |
| 2227 | case 'Z': |
| 2228 | if (GET_FIELD (insn, 26, 26)) |
| 2229 | (*info->fprintf_func) (info->stream, ",m "); |
| 2230 | else |
| 2231 | (*info->fprintf_func) (info->stream, " "); |
| 2232 | break; |
| 2233 | case 'i': |
| 2234 | if (GET_FIELD (insn, 25, 25)) |
| 2235 | (*info->fprintf_func) (info->stream, ",i"); |
| 2236 | break; |
| 2237 | case 'z': |
| 2238 | if (!GET_FIELD (insn, 21, 21)) |
| 2239 | (*info->fprintf_func) (info->stream, ",z"); |
| 2240 | break; |
| 2241 | case 'a': |
| 2242 | (*info->fprintf_func) |
| 2243 | (info->stream, "%s", |
| 2244 | add_compl_names[GET_FIELD (insn, 20, 21)]); |
| 2245 | break; |
| 2246 | case 'Y': |
| 2247 | (*info->fprintf_func) |
| 2248 | (info->stream, ",dc%s", |
| 2249 | add_compl_names[GET_FIELD (insn, 20, 21)]); |
| 2250 | break; |
| 2251 | case 'y': |
| 2252 | (*info->fprintf_func) |
| 2253 | (info->stream, ",c%s", |
| 2254 | add_compl_names[GET_FIELD (insn, 20, 21)]); |
| 2255 | break; |
| 2256 | case 'v': |
| 2257 | if (GET_FIELD (insn, 20, 20)) |
| 2258 | (*info->fprintf_func) (info->stream, ",tsv"); |
| 2259 | break; |
| 2260 | case 't': |
| 2261 | (*info->fprintf_func) (info->stream, ",tc"); |
| 2262 | if (GET_FIELD (insn, 20, 20)) |
| 2263 | (*info->fprintf_func) (info->stream, ",tsv"); |
| 2264 | break; |
| 2265 | case 'B': |
| 2266 | (*info->fprintf_func) (info->stream, ",db"); |
| 2267 | if (GET_FIELD (insn, 20, 20)) |
| 2268 | (*info->fprintf_func) (info->stream, ",tsv"); |
| 2269 | break; |
| 2270 | case 'b': |
| 2271 | (*info->fprintf_func) (info->stream, ",b"); |
| 2272 | if (GET_FIELD (insn, 20, 20)) |
| 2273 | (*info->fprintf_func) (info->stream, ",tsv"); |
| 2274 | break; |
| 2275 | case 'T': |
| 2276 | if (GET_FIELD (insn, 25, 25)) |
| 2277 | (*info->fprintf_func) (info->stream, ",tc"); |
| 2278 | break; |
| 2279 | case 'S': |
| 2280 | /* EXTRD/W has a following condition. */ |
| 2281 | if (*(s + 1) == '?') |
| 2282 | (*info->fprintf_func) |
| 2283 | (info->stream, "%s", |
| 2284 | signed_unsigned_names[GET_FIELD (insn, 21, 21)]); |
| 2285 | else |
| 2286 | (*info->fprintf_func) |
| 2287 | (info->stream, "%s ", |
| 2288 | signed_unsigned_names[GET_FIELD (insn, 21, 21)]); |
| 2289 | break; |
| 2290 | case 'h': |
| 2291 | (*info->fprintf_func) |
| 2292 | (info->stream, "%s", |
| 2293 | mix_half_names[GET_FIELD (insn, 17, 17)]); |
| 2294 | break; |
| 2295 | case 'H': |
| 2296 | (*info->fprintf_func) |
| 2297 | (info->stream, "%s ", |
| 2298 | saturation_names[GET_FIELD (insn, 24, 25)]); |
| 2299 | break; |
| 2300 | case '*': |
| 2301 | (*info->fprintf_func) |
| 2302 | (info->stream, ",%d%d%d%d ", |
| 2303 | GET_FIELD (insn, 17, 18), GET_FIELD (insn, 20, 21), |
| 2304 | GET_FIELD (insn, 22, 23), GET_FIELD (insn, 24, 25)); |
| 2305 | break; |
| 2306 | |
| 2307 | case 'q': |
| 2308 | { |
| 2309 | int m, a; |
| 2310 | |
| 2311 | m = GET_FIELD (insn, 28, 28); |
| 2312 | a = GET_FIELD (insn, 29, 29); |
| 2313 | |
| 2314 | if (m && !a) |
| 2315 | fputs_filtered (",ma ", info); |
| 2316 | else if (m && a) |
| 2317 | fputs_filtered (",mb ", info); |
| 2318 | else |
| 2319 | fputs_filtered (" ", info); |
| 2320 | break; |
| 2321 | } |
| 2322 | |
| 2323 | case 'J': |
| 2324 | { |
| 2325 | int opc = GET_FIELD (insn, 0, 5); |
| 2326 | |
| 2327 | if (opc == 0x16 || opc == 0x1e) |
| 2328 | { |
| 2329 | if (GET_FIELD (insn, 29, 29) == 0) |
| 2330 | fputs_filtered (",ma ", info); |
| 2331 | else |
| 2332 | fputs_filtered (",mb ", info); |
| 2333 | } |
| 2334 | else |
| 2335 | fputs_filtered (" ", info); |
| 2336 | break; |
| 2337 | } |
| 2338 | |
| 2339 | case 'e': |
| 2340 | { |
| 2341 | int opc = GET_FIELD (insn, 0, 5); |
| 2342 | |
| 2343 | if (opc == 0x13 || opc == 0x1b) |
| 2344 | { |
| 2345 | if (GET_FIELD (insn, 18, 18) == 1) |
| 2346 | fputs_filtered (",mb ", info); |
| 2347 | else |
| 2348 | fputs_filtered (",ma ", info); |
| 2349 | } |
| 2350 | else if (opc == 0x17 || opc == 0x1f) |
| 2351 | { |
| 2352 | if (GET_FIELD (insn, 31, 31) == 1) |
| 2353 | fputs_filtered (",ma ", info); |
| 2354 | else |
| 2355 | fputs_filtered (",mb ", info); |
| 2356 | } |
| 2357 | else |
| 2358 | fputs_filtered (" ", info); |
| 2359 | |
| 2360 | break; |
| 2361 | } |
| 2362 | } |
| 2363 | break; |
| 2364 | |
| 2365 | /* Handle conditions. */ |
| 2366 | case '?': |
| 2367 | { |
| 2368 | s++; |
| 2369 | switch (*s) |
| 2370 | { |
| 2371 | case 'f': |
| 2372 | (*info->fprintf_func) |
| 2373 | (info->stream, "%s ", |
| 2374 | float_comp_names[GET_FIELD (insn, 27, 31)]); |
| 2375 | break; |
| 2376 | |
| 2377 | /* These four conditions are for the set of instructions |
| 2378 | which distinguish true/false conditions by opcode |
| 2379 | rather than by the 'f' bit (sigh): comb, comib, |
| 2380 | addb, addib. */ |
| 2381 | case 't': |
| 2382 | fputs_filtered |
| 2383 | (compare_cond_names[GET_FIELD (insn, 16, 18)], info); |
| 2384 | break; |
| 2385 | case 'n': |
| 2386 | fputs_filtered |
| 2387 | (compare_cond_names[GET_FIELD (insn, 16, 18) |
| 2388 | + GET_FIELD (insn, 4, 4) * 8], |
| 2389 | info); |
| 2390 | break; |
| 2391 | case 'N': |
| 2392 | fputs_filtered |
| 2393 | (compare_cond_64_names[GET_FIELD (insn, 16, 18) |
| 2394 | + GET_FIELD (insn, 2, 2) * 8], |
| 2395 | info); |
| 2396 | break; |
| 2397 | case 'Q': |
| 2398 | fputs_filtered |
| 2399 | (cmpib_cond_64_names[GET_FIELD (insn, 16, 18)], |
| 2400 | info); |
| 2401 | break; |
| 2402 | case '@': |
| 2403 | fputs_filtered |
| 2404 | (add_cond_names[GET_FIELD (insn, 16, 18) |
| 2405 | + GET_FIELD (insn, 4, 4) * 8], |
| 2406 | info); |
| 2407 | break; |
| 2408 | case 's': |
| 2409 | (*info->fprintf_func) |
| 2410 | (info->stream, "%s ", |
| 2411 | compare_cond_names[GET_COND (insn)]); |
| 2412 | break; |
| 2413 | case 'S': |
| 2414 | (*info->fprintf_func) |
| 2415 | (info->stream, "%s ", |
| 2416 | compare_cond_64_names[GET_COND (insn)]); |
| 2417 | break; |
| 2418 | case 'a': |
| 2419 | (*info->fprintf_func) |
| 2420 | (info->stream, "%s ", |
| 2421 | add_cond_names[GET_COND (insn)]); |
| 2422 | break; |
| 2423 | case 'A': |
| 2424 | (*info->fprintf_func) |
| 2425 | (info->stream, "%s ", |
| 2426 | add_cond_64_names[GET_COND (insn)]); |
| 2427 | break; |
| 2428 | case 'd': |
| 2429 | (*info->fprintf_func) |
| 2430 | (info->stream, "%s", |
| 2431 | add_cond_names[GET_FIELD (insn, 16, 18)]); |
| 2432 | break; |
| 2433 | |
| 2434 | case 'W': |
| 2435 | (*info->fprintf_func) |
| 2436 | (info->stream, "%s", |
| 2437 | wide_add_cond_names[GET_FIELD (insn, 16, 18) + |
| 2438 | GET_FIELD (insn, 4, 4) * 8]); |
| 2439 | break; |
| 2440 | |
| 2441 | case 'l': |
| 2442 | (*info->fprintf_func) |
| 2443 | (info->stream, "%s ", |
| 2444 | logical_cond_names[GET_COND (insn)]); |
| 2445 | break; |
| 2446 | case 'L': |
| 2447 | (*info->fprintf_func) |
| 2448 | (info->stream, "%s ", |
| 2449 | logical_cond_64_names[GET_COND (insn)]); |
| 2450 | break; |
| 2451 | case 'u': |
| 2452 | (*info->fprintf_func) |
| 2453 | (info->stream, "%s ", |
| 2454 | unit_cond_names[GET_COND (insn)]); |
| 2455 | break; |
| 2456 | case 'U': |
| 2457 | (*info->fprintf_func) |
| 2458 | (info->stream, "%s ", |
| 2459 | unit_cond_64_names[GET_COND (insn)]); |
| 2460 | break; |
| 2461 | case 'y': |
| 2462 | case 'x': |
| 2463 | case 'b': |
| 2464 | (*info->fprintf_func) |
| 2465 | (info->stream, "%s", |
| 2466 | shift_cond_names[GET_FIELD (insn, 16, 18)]); |
| 2467 | |
| 2468 | /* If the next character in args is 'n', it will handle |
| 2469 | putting out the space. */ |
| 2470 | if (s[1] != 'n') |
| 2471 | (*info->fprintf_func) (info->stream, " "); |
| 2472 | break; |
| 2473 | case 'X': |
| 2474 | (*info->fprintf_func) |
| 2475 | (info->stream, "%s ", |
| 2476 | shift_cond_64_names[GET_FIELD (insn, 16, 18)]); |
| 2477 | break; |
| 2478 | case 'B': |
| 2479 | (*info->fprintf_func) |
| 2480 | (info->stream, "%s", |
| 2481 | bb_cond_64_names[GET_FIELD (insn, 16, 16)]); |
| 2482 | |
| 2483 | /* If the next character in args is 'n', it will handle |
| 2484 | putting out the space. */ |
| 2485 | if (s[1] != 'n') |
| 2486 | (*info->fprintf_func) (info->stream, " "); |
| 2487 | break; |
| 2488 | } |
| 2489 | break; |
| 2490 | } |
| 2491 | |
| 2492 | case 'V': |
| 2493 | fput_const (extract_5_store (insn), info); |
| 2494 | break; |
| 2495 | case 'r': |
| 2496 | fput_const (extract_5r_store (insn), info); |
| 2497 | break; |
| 2498 | case 'R': |
| 2499 | fput_const (extract_5R_store (insn), info); |
| 2500 | break; |
| 2501 | case 'U': |
| 2502 | fput_const (extract_10U_store (insn), info); |
| 2503 | break; |
| 2504 | case 'B': |
| 2505 | case 'Q': |
| 2506 | fput_const (extract_5Q_store (insn), info); |
| 2507 | break; |
| 2508 | case 'i': |
| 2509 | fput_const (extract_11 (insn), info); |
| 2510 | break; |
| 2511 | case 'j': |
| 2512 | fput_const (extract_14 (insn), info); |
| 2513 | break; |
| 2514 | case 'k': |
| 2515 | fputs_filtered ("L%", info); |
| 2516 | fput_const (extract_21 (insn), info); |
| 2517 | break; |
| 2518 | case '<': |
| 2519 | case 'l': |
| 2520 | /* 16-bit long disp., PA2.0 wide only. */ |
| 2521 | fput_const (extract_16 (insn), info); |
| 2522 | break; |
| 2523 | case 'n': |
| 2524 | if (insn & 0x2) |
| 2525 | (*info->fprintf_func) (info->stream, ",n "); |
| 2526 | else |
| 2527 | (*info->fprintf_func) (info->stream, " "); |
| 2528 | break; |
| 2529 | case 'N': |
| 2530 | if ((insn & 0x20) && s[1]) |
| 2531 | (*info->fprintf_func) (info->stream, ",n "); |
| 2532 | else if (insn & 0x20) |
| 2533 | (*info->fprintf_func) (info->stream, ",n"); |
| 2534 | else if (s[1]) |
| 2535 | (*info->fprintf_func) (info->stream, " "); |
| 2536 | break; |
| 2537 | case 'w': |
| 2538 | (*info->print_address_func) |
| 2539 | (memaddr + 8 + extract_12 (insn), info); |
| 2540 | break; |
| 2541 | case 'W': |
| 2542 | /* 17 bit PC-relative branch. */ |
| 2543 | (*info->print_address_func) |
| 2544 | ((memaddr + 8 + extract_17 (insn)), info); |
| 2545 | break; |
| 2546 | case 'z': |
| 2547 | /* 17 bit displacement. This is an offset from a register |
| 2548 | so it gets disasssembled as just a number, not any sort |
| 2549 | of address. */ |
| 2550 | fput_const (extract_17 (insn), info); |
| 2551 | break; |
| 2552 | |
| 2553 | case 'Z': |
| 2554 | /* addil %r1 implicit output. */ |
| 2555 | fputs_filtered ("r1", info); |
| 2556 | break; |
| 2557 | |
| 2558 | case 'Y': |
| 2559 | /* be,l %sr0,%r31 implicit output. */ |
| 2560 | fputs_filtered ("sr0,r31", info); |
| 2561 | break; |
| 2562 | |
| 2563 | case '@': |
| 2564 | (*info->fprintf_func) (info->stream, "0"); |
| 2565 | break; |
| 2566 | |
| 2567 | case '.': |
| 2568 | (*info->fprintf_func) (info->stream, "%d", |
| 2569 | GET_FIELD (insn, 24, 25)); |
| 2570 | break; |
| 2571 | case '*': |
| 2572 | (*info->fprintf_func) (info->stream, "%d", |
| 2573 | GET_FIELD (insn, 22, 25)); |
| 2574 | break; |
| 2575 | case '!': |
| 2576 | fputs_filtered ("sar", info); |
| 2577 | break; |
| 2578 | case 'p': |
| 2579 | (*info->fprintf_func) (info->stream, "%d", |
| 2580 | 31 - GET_FIELD (insn, 22, 26)); |
| 2581 | break; |
| 2582 | case '~': |
| 2583 | { |
| 2584 | int num; |
| 2585 | num = GET_FIELD (insn, 20, 20) << 5; |
| 2586 | num |= GET_FIELD (insn, 22, 26); |
| 2587 | (*info->fprintf_func) (info->stream, "%d", 63 - num); |
| 2588 | break; |
| 2589 | } |
| 2590 | case 'P': |
| 2591 | (*info->fprintf_func) (info->stream, "%d", |
| 2592 | GET_FIELD (insn, 22, 26)); |
| 2593 | break; |
| 2594 | case 'q': |
| 2595 | { |
| 2596 | int num; |
| 2597 | num = GET_FIELD (insn, 20, 20) << 5; |
| 2598 | num |= GET_FIELD (insn, 22, 26); |
| 2599 | (*info->fprintf_func) (info->stream, "%d", num); |
| 2600 | break; |
| 2601 | } |
| 2602 | case 'T': |
| 2603 | (*info->fprintf_func) (info->stream, "%d", |
| 2604 | 32 - GET_FIELD (insn, 27, 31)); |
| 2605 | break; |
| 2606 | case '%': |
| 2607 | { |
| 2608 | int num; |
| 2609 | num = (GET_FIELD (insn, 23, 23) + 1) * 32; |
| 2610 | num -= GET_FIELD (insn, 27, 31); |
| 2611 | (*info->fprintf_func) (info->stream, "%d", num); |
| 2612 | break; |
| 2613 | } |
| 2614 | case '|': |
| 2615 | { |
| 2616 | int num; |
| 2617 | num = (GET_FIELD (insn, 19, 19) + 1) * 32; |
| 2618 | num -= GET_FIELD (insn, 27, 31); |
| 2619 | (*info->fprintf_func) (info->stream, "%d", num); |
| 2620 | break; |
| 2621 | } |
| 2622 | case '$': |
| 2623 | fput_const (GET_FIELD (insn, 20, 28), info); |
| 2624 | break; |
| 2625 | case 'A': |
| 2626 | fput_const (GET_FIELD (insn, 6, 18), info); |
| 2627 | break; |
| 2628 | case 'D': |
| 2629 | fput_const (GET_FIELD (insn, 6, 31), info); |
| 2630 | break; |
| 2631 | case 'v': |
| 2632 | (*info->fprintf_func) (info->stream, ",%d", |
| 2633 | GET_FIELD (insn, 23, 25)); |
| 2634 | break; |
| 2635 | case 'O': |
| 2636 | fput_const ((GET_FIELD (insn, 6,20) << 5 | |
| 2637 | GET_FIELD (insn, 27, 31)), info); |
| 2638 | break; |
| 2639 | case 'o': |
| 2640 | fput_const (GET_FIELD (insn, 6, 20), info); |
| 2641 | break; |
| 2642 | case '2': |
| 2643 | fput_const ((GET_FIELD (insn, 6, 22) << 5 | |
| 2644 | GET_FIELD (insn, 27, 31)), info); |
| 2645 | break; |
| 2646 | case '1': |
| 2647 | fput_const ((GET_FIELD (insn, 11, 20) << 5 | |
| 2648 | GET_FIELD (insn, 27, 31)), info); |
| 2649 | break; |
| 2650 | case '0': |
| 2651 | fput_const ((GET_FIELD (insn, 16, 20) << 5 | |
| 2652 | GET_FIELD (insn, 27, 31)), info); |
| 2653 | break; |
| 2654 | case 'u': |
| 2655 | (*info->fprintf_func) (info->stream, ",%d", |
| 2656 | GET_FIELD (insn, 23, 25)); |
| 2657 | break; |
| 2658 | case 'F': |
| 2659 | /* If no destination completer and not before a completer |
| 2660 | for fcmp, need a space here. */ |
| 2661 | if (s[1] == 'G' || s[1] == '?') |
| 2662 | fputs_filtered |
| 2663 | (float_format_names[GET_FIELD (insn, 19, 20)], info); |
| 2664 | else |
| 2665 | (*info->fprintf_func) |
| 2666 | (info->stream, "%s ", |
| 2667 | float_format_names[GET_FIELD (insn, 19, 20)]); |
| 2668 | break; |
| 2669 | case 'G': |
| 2670 | (*info->fprintf_func) |
| 2671 | (info->stream, "%s ", |
| 2672 | float_format_names[GET_FIELD (insn, 17, 18)]); |
| 2673 | break; |
| 2674 | case 'H': |
| 2675 | if (GET_FIELD (insn, 26, 26) == 1) |
| 2676 | (*info->fprintf_func) (info->stream, "%s ", |
| 2677 | float_format_names[0]); |
| 2678 | else |
| 2679 | (*info->fprintf_func) (info->stream, "%s ", |
| 2680 | float_format_names[1]); |
| 2681 | break; |
| 2682 | case 'I': |
| 2683 | /* If no destination completer and not before a completer |
| 2684 | for fcmp, need a space here. */ |
| 2685 | if (s[1] == '?') |
| 2686 | fputs_filtered |
| 2687 | (float_format_names[GET_FIELD (insn, 20, 20)], info); |
| 2688 | else |
| 2689 | (*info->fprintf_func) |
| 2690 | (info->stream, "%s ", |
| 2691 | float_format_names[GET_FIELD (insn, 20, 20)]); |
| 2692 | break; |
| 2693 | |
| 2694 | case 'J': |
| 2695 | fput_const (extract_14 (insn), info); |
| 2696 | break; |
| 2697 | |
| 2698 | case '#': |
| 2699 | { |
| 2700 | int sign = GET_FIELD (insn, 31, 31); |
| 2701 | int imm10 = GET_FIELD (insn, 18, 27); |
| 2702 | int disp; |
| 2703 | |
| 2704 | if (sign) |
| 2705 | disp = (-1 << 10) | imm10; |
| 2706 | else |
| 2707 | disp = imm10; |
| 2708 | |
| 2709 | disp <<= 3; |
| 2710 | fput_const (disp, info); |
| 2711 | break; |
| 2712 | } |
| 2713 | case 'K': |
| 2714 | case 'd': |
| 2715 | { |
| 2716 | int sign = GET_FIELD (insn, 31, 31); |
| 2717 | int imm11 = GET_FIELD (insn, 18, 28); |
| 2718 | int disp; |
| 2719 | |
| 2720 | if (sign) |
| 2721 | disp = (-1 << 11) | imm11; |
| 2722 | else |
| 2723 | disp = imm11; |
| 2724 | |
| 2725 | disp <<= 2; |
| 2726 | fput_const (disp, info); |
| 2727 | break; |
| 2728 | } |
| 2729 | |
| 2730 | case '>': |
| 2731 | case 'y': |
| 2732 | { |
| 2733 | /* 16-bit long disp., PA2.0 wide only. */ |
| 2734 | int disp = extract_16 (insn); |
| 2735 | disp &= ~3; |
| 2736 | fput_const (disp, info); |
| 2737 | break; |
| 2738 | } |
| 2739 | |
| 2740 | case '&': |
| 2741 | { |
| 2742 | /* 16-bit long disp., PA2.0 wide only. */ |
| 2743 | int disp = extract_16 (insn); |
| 2744 | disp &= ~7; |
| 2745 | fput_const (disp, info); |
| 2746 | break; |
| 2747 | } |
| 2748 | |
| 2749 | case '_': |
| 2750 | break; /* Dealt with by '{' */ |
| 2751 | |
| 2752 | case '{': |
| 2753 | { |
| 2754 | int sub = GET_FIELD (insn, 14, 16); |
| 2755 | int df = GET_FIELD (insn, 17, 18); |
| 2756 | int sf = GET_FIELD (insn, 19, 20); |
| 2757 | const char * const * source = float_format_names; |
| 2758 | const char * const * dest = float_format_names; |
| 2759 | char *t = ""; |
| 2760 | |
| 2761 | if (sub == 4) |
| 2762 | { |
| 2763 | fputs_filtered (",UND ", info); |
| 2764 | break; |
| 2765 | } |
| 2766 | if ((sub & 3) == 3) |
| 2767 | t = ",t"; |
| 2768 | if ((sub & 3) == 1) |
| 2769 | source = sub & 4 ? fcnv_ufixed_names : fcnv_fixed_names; |
| 2770 | if (sub & 2) |
| 2771 | dest = sub & 4 ? fcnv_ufixed_names : fcnv_fixed_names; |
| 2772 | |
| 2773 | (*info->fprintf_func) (info->stream, "%s%s%s ", |
| 2774 | t, source[sf], dest[df]); |
| 2775 | break; |
| 2776 | } |
| 2777 | |
| 2778 | case 'm': |
| 2779 | { |
| 2780 | int y = GET_FIELD (insn, 16, 18); |
| 2781 | |
| 2782 | if (y != 1) |
| 2783 | fput_const ((y ^ 1) - 1, info); |
| 2784 | } |
| 2785 | break; |
| 2786 | |
| 2787 | case 'h': |
| 2788 | { |
| 2789 | int cbit; |
| 2790 | |
| 2791 | cbit = GET_FIELD (insn, 16, 18); |
| 2792 | |
| 2793 | if (cbit > 0) |
| 2794 | (*info->fprintf_func) (info->stream, ",%d", cbit - 1); |
| 2795 | break; |
| 2796 | } |
| 2797 | |
| 2798 | case '=': |
| 2799 | { |
| 2800 | int cond = GET_FIELD (insn, 27, 31); |
| 2801 | |
| 2802 | switch (cond) |
| 2803 | { |
| 2804 | case 0: fputs_filtered (" ", info); break; |
| 2805 | case 1: fputs_filtered ("acc ", info); break; |
| 2806 | case 2: fputs_filtered ("rej ", info); break; |
| 2807 | case 5: fputs_filtered ("acc8 ", info); break; |
| 2808 | case 6: fputs_filtered ("rej8 ", info); break; |
| 2809 | case 9: fputs_filtered ("acc6 ", info); break; |
| 2810 | case 13: fputs_filtered ("acc4 ", info); break; |
| 2811 | case 17: fputs_filtered ("acc2 ", info); break; |
| 2812 | default: break; |
| 2813 | } |
| 2814 | break; |
| 2815 | } |
| 2816 | |
| 2817 | case 'X': |
| 2818 | (*info->print_address_func) |
| 2819 | (memaddr + 8 + extract_22 (insn), info); |
| 2820 | break; |
| 2821 | case 'L': |
| 2822 | fputs_filtered (",rp", info); |
| 2823 | break; |
| 2824 | default: |
| 2825 | (*info->fprintf_func) (info->stream, "%c", *s); |
| 2826 | break; |
| 2827 | } |
| 2828 | } |
| 2829 | return sizeof (insn); |
| 2830 | } |
| 2831 | } |
| 2832 | (*info->fprintf_func) (info->stream, "#%8x", insn); |
| 2833 | return sizeof (insn); |
| 2834 | } |