Home | History | Annotate | Line # | Download | only in opcodes
sparc-dis.c revision 1.1.1.4
      1      1.1  christos /* Print SPARC instructions.
      2  1.1.1.4  christos    Copyright (C) 1989-2015 Free Software Foundation, Inc.
      3      1.1  christos 
      4      1.1  christos    This file is part of the GNU opcodes library.
      5      1.1  christos 
      6      1.1  christos    This library is free software; you can redistribute it and/or modify
      7      1.1  christos    it under the terms of the GNU General Public License as published by
      8      1.1  christos    the Free Software Foundation; either version 3, or (at your option)
      9      1.1  christos    any later version.
     10      1.1  christos 
     11      1.1  christos    It is distributed in the hope that it will be useful, but WITHOUT
     12      1.1  christos    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
     13      1.1  christos    or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
     14      1.1  christos    License for more details.
     15      1.1  christos 
     16      1.1  christos    You should have received a copy of the GNU General Public License
     17      1.1  christos    along with this program; if not, write to the Free Software
     18      1.1  christos    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
     19      1.1  christos    MA 02110-1301, USA.  */
     20      1.1  christos 
     21      1.1  christos #include "sysdep.h"
     22  1.1.1.2  christos #include <stdio.h>
     23      1.1  christos #include "opcode/sparc.h"
     24      1.1  christos #include "dis-asm.h"
     25      1.1  christos #include "libiberty.h"
     26      1.1  christos #include "opintl.h"
     27      1.1  christos 
     28      1.1  christos /* Bitmask of v9 architectures.  */
     29      1.1  christos #define MASK_V9 ((1 << SPARC_OPCODE_ARCH_V9) \
     30      1.1  christos 		 | (1 << SPARC_OPCODE_ARCH_V9A) \
     31      1.1  christos 		 | (1 << SPARC_OPCODE_ARCH_V9B))
     32      1.1  christos /* 1 if INSN is for v9 only.  */
     33      1.1  christos #define V9_ONLY_P(insn) (! ((insn)->architecture & ~MASK_V9))
     34      1.1  christos /* 1 if INSN is for v9.  */
     35      1.1  christos #define V9_P(insn) (((insn)->architecture & MASK_V9) != 0)
     36      1.1  christos 
     37      1.1  christos /* The sorted opcode table.  */
     38      1.1  christos static const sparc_opcode **sorted_opcodes;
     39      1.1  christos 
     40      1.1  christos /* For faster lookup, after insns are sorted they are hashed.  */
     41      1.1  christos /* ??? I think there is room for even more improvement.  */
     42      1.1  christos 
     43      1.1  christos #define HASH_SIZE 256
     44      1.1  christos /* It is important that we only look at insn code bits as that is how the
     45      1.1  christos    opcode table is hashed.  OPCODE_BITS is a table of valid bits for each
     46      1.1  christos    of the main types (0,1,2,3).  */
     47      1.1  christos static int opcode_bits[4] = { 0x01c00000, 0x0, 0x01f80000, 0x01f80000 };
     48      1.1  christos #define HASH_INSN(INSN) \
     49      1.1  christos   ((((INSN) >> 24) & 0xc0) | (((INSN) & opcode_bits[((INSN) >> 30) & 3]) >> 19))
     50      1.1  christos typedef struct sparc_opcode_hash
     51      1.1  christos {
     52      1.1  christos   struct sparc_opcode_hash *next;
     53      1.1  christos   const sparc_opcode *opcode;
     54      1.1  christos } sparc_opcode_hash;
     55      1.1  christos 
     56      1.1  christos static sparc_opcode_hash *opcode_hash_table[HASH_SIZE];
     57      1.1  christos 
     58      1.1  christos /* Sign-extend a value which is N bits long.  */
     59      1.1  christos #define	SEX(value, bits) \
     60      1.1  christos 	((((int)(value)) << ((8 * sizeof (int)) - bits))	\
     61      1.1  christos 			 >> ((8 * sizeof (int)) - bits) )
     62      1.1  christos 
     63      1.1  christos static  char *reg_names[] =
     64      1.1  christos { "g0", "g1", "g2", "g3", "g4", "g5", "g6", "g7",
     65      1.1  christos   "o0", "o1", "o2", "o3", "o4", "o5", "sp", "o7",
     66      1.1  christos   "l0", "l1", "l2", "l3", "l4", "l5", "l6", "l7",
     67      1.1  christos   "i0", "i1", "i2", "i3", "i4", "i5", "fp", "i7",
     68      1.1  christos   "f0", "f1", "f2", "f3", "f4", "f5", "f6", "f7",
     69      1.1  christos   "f8", "f9", "f10", "f11", "f12", "f13", "f14", "f15",
     70      1.1  christos   "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23",
     71      1.1  christos   "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31",
     72      1.1  christos   "f32", "f33", "f34", "f35", "f36", "f37", "f38", "f39",
     73      1.1  christos   "f40", "f41", "f42", "f43", "f44", "f45", "f46", "f47",
     74      1.1  christos   "f48", "f49", "f50", "f51", "f52", "f53", "f54", "f55",
     75      1.1  christos   "f56", "f57", "f58", "f59", "f60", "f61", "f62", "f63",
     76      1.1  christos /* psr, wim, tbr, fpsr, cpsr are v8 only.  */
     77      1.1  christos   "y", "psr", "wim", "tbr", "pc", "npc", "fpsr", "cpsr"
     78      1.1  christos };
     79      1.1  christos 
     80      1.1  christos #define	freg_names	(&reg_names[4 * 8])
     81      1.1  christos 
     82      1.1  christos /* These are ordered according to there register number in
     83      1.1  christos    rdpr and wrpr insns.  */
     84      1.1  christos static char *v9_priv_reg_names[] =
     85      1.1  christos {
     86      1.1  christos   "tpc", "tnpc", "tstate", "tt", "tick", "tba", "pstate", "tl",
     87      1.1  christos   "pil", "cwp", "cansave", "canrestore", "cleanwin", "otherwin",
     88      1.1  christos   "wstate", "fq", "gl"
     89      1.1  christos   /* "ver" - special cased */
     90      1.1  christos };
     91      1.1  christos 
     92      1.1  christos /* These are ordered according to there register number in
     93      1.1  christos    rdhpr and wrhpr insns.  */
     94      1.1  christos static char *v9_hpriv_reg_names[] =
     95      1.1  christos {
     96      1.1  christos   "hpstate", "htstate", "resv2", "hintp", "resv4", "htba", "hver",
     97      1.1  christos   "resv7", "resv8", "resv9", "resv10", "resv11", "resv12", "resv13",
     98      1.1  christos   "resv14", "resv15", "resv16", "resv17", "resv18", "resv19", "resv20",
     99      1.1  christos   "resv21", "resv22", "resv23", "resv24", "resv25", "resv26", "resv27",
    100  1.1.1.4  christos   "hstick_offset", "hstick_enable", "resv30", "hstick_cmpr"
    101      1.1  christos };
    102      1.1  christos 
    103      1.1  christos /* These are ordered according to there register number in
    104      1.1  christos    rd and wr insns (-16).  */
    105      1.1  christos static char *v9a_asr_reg_names[] =
    106      1.1  christos {
    107      1.1  christos   "pcr", "pic", "dcr", "gsr", "set_softint", "clear_softint",
    108  1.1.1.2  christos   "softint", "tick_cmpr", "stick", "stick_cmpr", "cfr",
    109  1.1.1.4  christos   "pause", "mwait"
    110      1.1  christos };
    111      1.1  christos 
    112      1.1  christos /* Macros used to extract instruction fields.  Not all fields have
    113      1.1  christos    macros defined here, only those which are actually used.  */
    114      1.1  christos 
    115      1.1  christos #define X_RD(i)      (((i) >> 25) & 0x1f)
    116      1.1  christos #define X_RS1(i)     (((i) >> 14) & 0x1f)
    117      1.1  christos #define X_LDST_I(i)  (((i) >> 13) & 1)
    118      1.1  christos #define X_ASI(i)     (((i) >> 5) & 0xff)
    119      1.1  christos #define X_RS2(i)     (((i) >> 0) & 0x1f)
    120  1.1.1.2  christos #define X_RS3(i)     (((i) >> 9) & 0x1f)
    121      1.1  christos #define X_IMM(i,n)   (((i) >> 0) & ((1 << (n)) - 1))
    122      1.1  christos #define X_SIMM(i,n)  SEX (X_IMM ((i), (n)), (n))
    123      1.1  christos #define X_DISP22(i)  (((i) >> 0) & 0x3fffff)
    124      1.1  christos #define X_IMM22(i)   X_DISP22 (i)
    125      1.1  christos #define X_DISP30(i)  (((i) >> 0) & 0x3fffffff)
    126      1.1  christos 
    127      1.1  christos /* These are for v9.  */
    128      1.1  christos #define X_DISP16(i)  (((((i) >> 20) & 3) << 14) | (((i) >> 0) & 0x3fff))
    129  1.1.1.2  christos #define X_DISP10(i)  (((((i) >> 19) & 3) << 8) | (((i) >> 5) & 0xff))
    130      1.1  christos #define X_DISP19(i)  (((i) >> 0) & 0x7ffff)
    131      1.1  christos #define X_MEMBAR(i)  ((i) & 0x7f)
    132      1.1  christos 
    133      1.1  christos /* Here is the union which was used to extract instruction fields
    134      1.1  christos    before the shift and mask macros were written.
    135      1.1  christos 
    136      1.1  christos    union sparc_insn
    137      1.1  christos      {
    138      1.1  christos        unsigned long int code;
    139      1.1  christos        struct
    140      1.1  christos 	 {
    141      1.1  christos 	   unsigned int anop:2;
    142      1.1  christos 	   #define	op	ldst.anop
    143      1.1  christos 	   unsigned int anrd:5;
    144      1.1  christos 	   #define	rd	ldst.anrd
    145      1.1  christos 	   unsigned int op3:6;
    146      1.1  christos 	   unsigned int anrs1:5;
    147      1.1  christos 	   #define	rs1	ldst.anrs1
    148      1.1  christos 	   unsigned int i:1;
    149      1.1  christos 	   unsigned int anasi:8;
    150      1.1  christos 	   #define	asi	ldst.anasi
    151      1.1  christos 	   unsigned int anrs2:5;
    152      1.1  christos 	   #define	rs2	ldst.anrs2
    153      1.1  christos 	   #define	shcnt	rs2
    154      1.1  christos 	 } ldst;
    155      1.1  christos        struct
    156      1.1  christos 	 {
    157      1.1  christos 	   unsigned int anop:2, anrd:5, op3:6, anrs1:5, i:1;
    158      1.1  christos 	   unsigned int IMM13:13;
    159      1.1  christos 	   #define	imm13	IMM13.IMM13
    160      1.1  christos 	 } IMM13;
    161      1.1  christos        struct
    162      1.1  christos 	 {
    163      1.1  christos 	   unsigned int anop:2;
    164      1.1  christos 	   unsigned int a:1;
    165      1.1  christos 	   unsigned int cond:4;
    166      1.1  christos 	   unsigned int op2:3;
    167      1.1  christos 	   unsigned int DISP22:22;
    168      1.1  christos 	   #define	disp22	branch.DISP22
    169      1.1  christos 	   #define	imm22	disp22
    170      1.1  christos 	 } branch;
    171      1.1  christos        struct
    172      1.1  christos 	 {
    173      1.1  christos 	   unsigned int anop:2;
    174      1.1  christos 	   unsigned int a:1;
    175      1.1  christos 	   unsigned int z:1;
    176      1.1  christos 	   unsigned int rcond:3;
    177      1.1  christos 	   unsigned int op2:3;
    178      1.1  christos 	   unsigned int DISP16HI:2;
    179      1.1  christos 	   unsigned int p:1;
    180      1.1  christos 	   unsigned int _rs1:5;
    181      1.1  christos 	   unsigned int DISP16LO:14;
    182      1.1  christos 	 } branch16;
    183      1.1  christos        struct
    184      1.1  christos 	 {
    185      1.1  christos 	   unsigned int anop:2;
    186      1.1  christos 	   unsigned int adisp30:30;
    187      1.1  christos 	   #define	disp30	call.adisp30
    188      1.1  christos 	 } call;
    189      1.1  christos      };  */
    190      1.1  christos 
    191      1.1  christos /* Nonzero if INSN is the opcode for a delayed branch.  */
    192      1.1  christos 
    193      1.1  christos static int
    194      1.1  christos is_delayed_branch (unsigned long insn)
    195      1.1  christos {
    196      1.1  christos   sparc_opcode_hash *op;
    197      1.1  christos 
    198      1.1  christos   for (op = opcode_hash_table[HASH_INSN (insn)]; op; op = op->next)
    199      1.1  christos     {
    200      1.1  christos       const sparc_opcode *opcode = op->opcode;
    201      1.1  christos 
    202      1.1  christos       if ((opcode->match & insn) == opcode->match
    203      1.1  christos 	  && (opcode->lose & insn) == 0)
    204      1.1  christos 	return opcode->flags & F_DELAYED;
    205      1.1  christos     }
    206      1.1  christos   return 0;
    207      1.1  christos }
    208      1.1  christos 
    209      1.1  christos /* extern void qsort (); */
    210      1.1  christos 
    211      1.1  christos /* Records current mask of SPARC_OPCODE_ARCH_FOO values, used to pass value
    212      1.1  christos    to compare_opcodes.  */
    213      1.1  christos static unsigned int current_arch_mask;
    214      1.1  christos 
    215      1.1  christos /* Given BFD mach number, return a mask of SPARC_OPCODE_ARCH_FOO values.  */
    216      1.1  christos 
    217      1.1  christos static int
    218      1.1  christos compute_arch_mask (unsigned long mach)
    219      1.1  christos {
    220      1.1  christos   switch (mach)
    221      1.1  christos     {
    222      1.1  christos     case 0 :
    223      1.1  christos     case bfd_mach_sparc :
    224  1.1.1.3  christos       return (SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_V8)
    225  1.1.1.3  christos               | SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_LEON));
    226      1.1  christos     case bfd_mach_sparc_sparclet :
    227      1.1  christos       return SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_SPARCLET);
    228      1.1  christos     case bfd_mach_sparc_sparclite :
    229      1.1  christos     case bfd_mach_sparc_sparclite_le :
    230      1.1  christos       /* sparclites insns are recognized by default (because that's how
    231      1.1  christos 	 they've always been treated, for better or worse).  Kludge this by
    232      1.1  christos 	 indicating generic v8 is also selected.  */
    233      1.1  christos       return (SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_SPARCLITE)
    234      1.1  christos 	      | SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_V8));
    235      1.1  christos     case bfd_mach_sparc_v8plus :
    236      1.1  christos     case bfd_mach_sparc_v9 :
    237      1.1  christos       return SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_V9);
    238      1.1  christos     case bfd_mach_sparc_v8plusa :
    239      1.1  christos     case bfd_mach_sparc_v9a :
    240      1.1  christos       return SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_V9A);
    241      1.1  christos     case bfd_mach_sparc_v8plusb :
    242      1.1  christos     case bfd_mach_sparc_v9b :
    243      1.1  christos       return SPARC_OPCODE_ARCH_MASK (SPARC_OPCODE_ARCH_V9B);
    244      1.1  christos     }
    245      1.1  christos   abort ();
    246      1.1  christos }
    247      1.1  christos 
    248      1.1  christos /* Compare opcodes A and B.  */
    249      1.1  christos 
    250      1.1  christos static int
    251      1.1  christos compare_opcodes (const void * a, const void * b)
    252      1.1  christos {
    253      1.1  christos   sparc_opcode *op0 = * (sparc_opcode **) a;
    254      1.1  christos   sparc_opcode *op1 = * (sparc_opcode **) b;
    255      1.1  christos   unsigned long int match0 = op0->match, match1 = op1->match;
    256      1.1  christos   unsigned long int lose0 = op0->lose, lose1 = op1->lose;
    257      1.1  christos   register unsigned int i;
    258      1.1  christos 
    259      1.1  christos   /* If one (and only one) insn isn't supported by the current architecture,
    260      1.1  christos      prefer the one that is.  If neither are supported, but they're both for
    261      1.1  christos      the same architecture, continue processing.  Otherwise (both unsupported
    262      1.1  christos      and for different architectures), prefer lower numbered arch's (fudged
    263      1.1  christos      by comparing the bitmasks).  */
    264      1.1  christos   if (op0->architecture & current_arch_mask)
    265      1.1  christos     {
    266      1.1  christos       if (! (op1->architecture & current_arch_mask))
    267      1.1  christos 	return -1;
    268      1.1  christos     }
    269      1.1  christos   else
    270      1.1  christos     {
    271      1.1  christos       if (op1->architecture & current_arch_mask)
    272      1.1  christos 	return 1;
    273      1.1  christos       else if (op0->architecture != op1->architecture)
    274      1.1  christos 	return op0->architecture - op1->architecture;
    275      1.1  christos     }
    276      1.1  christos 
    277      1.1  christos   /* If a bit is set in both match and lose, there is something
    278      1.1  christos      wrong with the opcode table.  */
    279      1.1  christos   if (match0 & lose0)
    280      1.1  christos     {
    281      1.1  christos       fprintf
    282      1.1  christos 	(stderr,
    283      1.1  christos 	 /* xgettext:c-format */
    284      1.1  christos 	 _("Internal error:  bad sparc-opcode.h: \"%s\", %#.8lx, %#.8lx\n"),
    285      1.1  christos 	 op0->name, match0, lose0);
    286      1.1  christos       op0->lose &= ~op0->match;
    287      1.1  christos       lose0 = op0->lose;
    288      1.1  christos     }
    289      1.1  christos 
    290      1.1  christos   if (match1 & lose1)
    291      1.1  christos     {
    292      1.1  christos       fprintf
    293      1.1  christos 	(stderr,
    294      1.1  christos 	 /* xgettext:c-format */
    295      1.1  christos 	 _("Internal error: bad sparc-opcode.h: \"%s\", %#.8lx, %#.8lx\n"),
    296      1.1  christos 	 op1->name, match1, lose1);
    297      1.1  christos       op1->lose &= ~op1->match;
    298      1.1  christos       lose1 = op1->lose;
    299      1.1  christos     }
    300      1.1  christos 
    301      1.1  christos   /* Because the bits that are variable in one opcode are constant in
    302      1.1  christos      another, it is important to order the opcodes in the right order.  */
    303      1.1  christos   for (i = 0; i < 32; ++i)
    304      1.1  christos     {
    305      1.1  christos       unsigned long int x = 1 << i;
    306      1.1  christos       int x0 = (match0 & x) != 0;
    307      1.1  christos       int x1 = (match1 & x) != 0;
    308      1.1  christos 
    309      1.1  christos       if (x0 != x1)
    310      1.1  christos 	return x1 - x0;
    311      1.1  christos     }
    312      1.1  christos 
    313      1.1  christos   for (i = 0; i < 32; ++i)
    314      1.1  christos     {
    315      1.1  christos       unsigned long int x = 1 << i;
    316      1.1  christos       int x0 = (lose0 & x) != 0;
    317      1.1  christos       int x1 = (lose1 & x) != 0;
    318      1.1  christos 
    319      1.1  christos       if (x0 != x1)
    320      1.1  christos 	return x1 - x0;
    321      1.1  christos     }
    322      1.1  christos 
    323      1.1  christos   /* They are functionally equal.  So as long as the opcode table is
    324      1.1  christos      valid, we can put whichever one first we want, on aesthetic grounds.  */
    325      1.1  christos 
    326      1.1  christos   /* Our first aesthetic ground is that aliases defer to real insns.  */
    327      1.1  christos   {
    328      1.1  christos     int alias_diff = (op0->flags & F_ALIAS) - (op1->flags & F_ALIAS);
    329      1.1  christos 
    330      1.1  christos     if (alias_diff != 0)
    331      1.1  christos       /* Put the one that isn't an alias first.  */
    332      1.1  christos       return alias_diff;
    333      1.1  christos   }
    334      1.1  christos 
    335      1.1  christos   /* Except for aliases, two "identical" instructions had
    336      1.1  christos      better have the same opcode.  This is a sanity check on the table.  */
    337      1.1  christos   i = strcmp (op0->name, op1->name);
    338      1.1  christos   if (i)
    339      1.1  christos     {
    340  1.1.1.3  christos       if (op0->flags & F_ALIAS)
    341  1.1.1.3  christos 	{
    342  1.1.1.3  christos 	  if (op0->flags & F_PREFERRED)
    343  1.1.1.3  christos 	    return -1;
    344  1.1.1.3  christos 	  if (op1->flags & F_PREFERRED)
    345  1.1.1.3  christos 	    return 1;
    346  1.1.1.3  christos 
    347  1.1.1.3  christos 	  /* If they're both aliases, and neither is marked as preferred,
    348  1.1.1.3  christos 	     be arbitrary.  */
    349  1.1.1.3  christos 	  return i;
    350  1.1.1.3  christos 	}
    351      1.1  christos       else
    352      1.1  christos 	fprintf (stderr,
    353      1.1  christos 		 /* xgettext:c-format */
    354      1.1  christos 		 _("Internal error: bad sparc-opcode.h: \"%s\" == \"%s\"\n"),
    355      1.1  christos 		 op0->name, op1->name);
    356      1.1  christos     }
    357      1.1  christos 
    358      1.1  christos   /* Fewer arguments are preferred.  */
    359      1.1  christos   {
    360      1.1  christos     int length_diff = strlen (op0->args) - strlen (op1->args);
    361      1.1  christos 
    362      1.1  christos     if (length_diff != 0)
    363      1.1  christos       /* Put the one with fewer arguments first.  */
    364      1.1  christos       return length_diff;
    365      1.1  christos   }
    366      1.1  christos 
    367      1.1  christos   /* Put 1+i before i+1.  */
    368      1.1  christos   {
    369      1.1  christos     char *p0 = (char *) strchr (op0->args, '+');
    370      1.1  christos     char *p1 = (char *) strchr (op1->args, '+');
    371      1.1  christos 
    372      1.1  christos     if (p0 && p1)
    373      1.1  christos       {
    374      1.1  christos 	/* There is a plus in both operands.  Note that a plus
    375      1.1  christos 	   sign cannot be the first character in args,
    376      1.1  christos 	   so the following [-1]'s are valid.  */
    377      1.1  christos 	if (p0[-1] == 'i' && p1[1] == 'i')
    378      1.1  christos 	  /* op0 is i+1 and op1 is 1+i, so op1 goes first.  */
    379      1.1  christos 	  return 1;
    380      1.1  christos 	if (p0[1] == 'i' && p1[-1] == 'i')
    381      1.1  christos 	  /* op0 is 1+i and op1 is i+1, so op0 goes first.  */
    382      1.1  christos 	  return -1;
    383      1.1  christos       }
    384      1.1  christos   }
    385      1.1  christos 
    386      1.1  christos   /* Put 1,i before i,1.  */
    387      1.1  christos   {
    388      1.1  christos     int i0 = strncmp (op0->args, "i,1", 3) == 0;
    389      1.1  christos     int i1 = strncmp (op1->args, "i,1", 3) == 0;
    390      1.1  christos 
    391      1.1  christos     if (i0 ^ i1)
    392      1.1  christos       return i0 - i1;
    393      1.1  christos   }
    394      1.1  christos 
    395      1.1  christos   /* They are, as far as we can tell, identical.
    396      1.1  christos      Since qsort may have rearranged the table partially, there is
    397      1.1  christos      no way to tell which one was first in the opcode table as
    398      1.1  christos      written, so just say there are equal.  */
    399      1.1  christos   /* ??? This is no longer true now that we sort a vector of pointers,
    400      1.1  christos      not the table itself.  */
    401      1.1  christos   return 0;
    402      1.1  christos }
    403      1.1  christos 
    404      1.1  christos /* Build a hash table from the opcode table.
    405      1.1  christos    OPCODE_TABLE is a sorted list of pointers into the opcode table.  */
    406      1.1  christos 
    407      1.1  christos static void
    408      1.1  christos build_hash_table (const sparc_opcode **opcode_table,
    409      1.1  christos 		  sparc_opcode_hash **hash_table,
    410      1.1  christos 		  int num_opcodes)
    411      1.1  christos {
    412      1.1  christos   int i;
    413      1.1  christos   int hash_count[HASH_SIZE];
    414      1.1  christos   static sparc_opcode_hash *hash_buf = NULL;
    415      1.1  christos 
    416      1.1  christos   /* Start at the end of the table and work backwards so that each
    417      1.1  christos      chain is sorted.  */
    418      1.1  christos 
    419      1.1  christos   memset (hash_table, 0, HASH_SIZE * sizeof (hash_table[0]));
    420      1.1  christos   memset (hash_count, 0, HASH_SIZE * sizeof (hash_count[0]));
    421      1.1  christos   if (hash_buf != NULL)
    422      1.1  christos     free (hash_buf);
    423      1.1  christos   hash_buf = xmalloc (sizeof (* hash_buf) * num_opcodes);
    424      1.1  christos   for (i = num_opcodes - 1; i >= 0; --i)
    425      1.1  christos     {
    426      1.1  christos       int hash = HASH_INSN (opcode_table[i]->match);
    427      1.1  christos       sparc_opcode_hash *h = &hash_buf[i];
    428      1.1  christos 
    429      1.1  christos       h->next = hash_table[hash];
    430      1.1  christos       h->opcode = opcode_table[i];
    431      1.1  christos       hash_table[hash] = h;
    432      1.1  christos       ++hash_count[hash];
    433      1.1  christos     }
    434      1.1  christos 
    435      1.1  christos #if 0 /* for debugging */
    436      1.1  christos   {
    437      1.1  christos     int min_count = num_opcodes, max_count = 0;
    438      1.1  christos     int total;
    439      1.1  christos 
    440      1.1  christos     for (i = 0; i < HASH_SIZE; ++i)
    441      1.1  christos       {
    442      1.1  christos         if (hash_count[i] < min_count)
    443      1.1  christos 	  min_count = hash_count[i];
    444      1.1  christos 	if (hash_count[i] > max_count)
    445      1.1  christos 	  max_count = hash_count[i];
    446      1.1  christos 	total += hash_count[i];
    447      1.1  christos       }
    448      1.1  christos 
    449      1.1  christos     printf ("Opcode hash table stats: min %d, max %d, ave %f\n",
    450      1.1  christos 	    min_count, max_count, (double) total / HASH_SIZE);
    451      1.1  christos   }
    452      1.1  christos #endif
    453      1.1  christos }
    454      1.1  christos 
    455      1.1  christos /* Print one instruction from MEMADDR on INFO->STREAM.
    456      1.1  christos 
    457      1.1  christos    We suffix the instruction with a comment that gives the absolute
    458      1.1  christos    address involved, as well as its symbolic form, if the instruction
    459      1.1  christos    is preceded by a findable `sethi' and it either adds an immediate
    460      1.1  christos    displacement to that register, or it is an `add' or `or' instruction
    461      1.1  christos    on that register.  */
    462      1.1  christos 
    463      1.1  christos int
    464      1.1  christos print_insn_sparc (bfd_vma memaddr, disassemble_info *info)
    465      1.1  christos {
    466      1.1  christos   FILE *stream = info->stream;
    467      1.1  christos   bfd_byte buffer[4];
    468      1.1  christos   unsigned long insn;
    469      1.1  christos   sparc_opcode_hash *op;
    470      1.1  christos   /* Nonzero of opcode table has been initialized.  */
    471      1.1  christos   static int opcodes_initialized = 0;
    472      1.1  christos   /* bfd mach number of last call.  */
    473      1.1  christos   static unsigned long current_mach = 0;
    474      1.1  christos   bfd_vma (*getword) (const void *);
    475      1.1  christos 
    476      1.1  christos   if (!opcodes_initialized
    477      1.1  christos       || info->mach != current_mach)
    478      1.1  christos     {
    479      1.1  christos       int i;
    480      1.1  christos 
    481      1.1  christos       current_arch_mask = compute_arch_mask (info->mach);
    482      1.1  christos 
    483      1.1  christos       if (!opcodes_initialized)
    484      1.1  christos 	sorted_opcodes =
    485      1.1  christos 	  xmalloc (sparc_num_opcodes * sizeof (sparc_opcode *));
    486      1.1  christos       /* Reset the sorted table so we can resort it.  */
    487      1.1  christos       for (i = 0; i < sparc_num_opcodes; ++i)
    488      1.1  christos 	sorted_opcodes[i] = &sparc_opcodes[i];
    489      1.1  christos       qsort ((char *) sorted_opcodes, sparc_num_opcodes,
    490      1.1  christos 	     sizeof (sorted_opcodes[0]), compare_opcodes);
    491      1.1  christos 
    492      1.1  christos       build_hash_table (sorted_opcodes, opcode_hash_table, sparc_num_opcodes);
    493      1.1  christos       current_mach = info->mach;
    494      1.1  christos       opcodes_initialized = 1;
    495      1.1  christos     }
    496      1.1  christos 
    497      1.1  christos   {
    498      1.1  christos     int status =
    499      1.1  christos       (*info->read_memory_func) (memaddr, buffer, sizeof (buffer), info);
    500      1.1  christos 
    501      1.1  christos     if (status != 0)
    502      1.1  christos       {
    503      1.1  christos 	(*info->memory_error_func) (status, memaddr, info);
    504      1.1  christos 	return -1;
    505      1.1  christos       }
    506      1.1  christos   }
    507      1.1  christos 
    508      1.1  christos   /* On SPARClite variants such as DANlite (sparc86x), instructions
    509      1.1  christos      are always big-endian even when the machine is in little-endian mode.  */
    510      1.1  christos   if (info->endian == BFD_ENDIAN_BIG || info->mach == bfd_mach_sparc_sparclite)
    511      1.1  christos     getword = bfd_getb32;
    512      1.1  christos   else
    513      1.1  christos     getword = bfd_getl32;
    514      1.1  christos 
    515      1.1  christos   insn = getword (buffer);
    516      1.1  christos 
    517      1.1  christos   info->insn_info_valid = 1;			/* We do return this info.  */
    518      1.1  christos   info->insn_type = dis_nonbranch;		/* Assume non branch insn.  */
    519      1.1  christos   info->branch_delay_insns = 0;			/* Assume no delay.  */
    520      1.1  christos   info->target = 0;				/* Assume no target known.  */
    521      1.1  christos 
    522      1.1  christos   for (op = opcode_hash_table[HASH_INSN (insn)]; op; op = op->next)
    523      1.1  christos     {
    524      1.1  christos       const sparc_opcode *opcode = op->opcode;
    525      1.1  christos 
    526      1.1  christos       /* If the insn isn't supported by the current architecture, skip it.  */
    527      1.1  christos       if (! (opcode->architecture & current_arch_mask))
    528      1.1  christos 	continue;
    529      1.1  christos 
    530      1.1  christos       if ((opcode->match & insn) == opcode->match
    531      1.1  christos 	  && (opcode->lose & insn) == 0)
    532      1.1  christos 	{
    533      1.1  christos 	  /* Nonzero means that we have found an instruction which has
    534      1.1  christos 	     the effect of adding or or'ing the imm13 field to rs1.  */
    535      1.1  christos 	  int imm_added_to_rs1 = 0;
    536      1.1  christos 	  int imm_ored_to_rs1 = 0;
    537      1.1  christos 
    538      1.1  christos 	  /* Nonzero means that we have found a plus sign in the args
    539      1.1  christos 	     field of the opcode table.  */
    540      1.1  christos 	  int found_plus = 0;
    541      1.1  christos 
    542      1.1  christos 	  /* Nonzero means we have an annulled branch.  */
    543      1.1  christos 	  int is_annulled = 0;
    544      1.1  christos 
    545      1.1  christos 	  /* Do we have an `add' or `or' instruction combining an
    546      1.1  christos              immediate with rs1?  */
    547      1.1  christos 	  if (opcode->match == 0x80102000) /* or */
    548      1.1  christos 	    imm_ored_to_rs1 = 1;
    549      1.1  christos 	  if (opcode->match == 0x80002000) /* add */
    550      1.1  christos 	    imm_added_to_rs1 = 1;
    551      1.1  christos 
    552      1.1  christos 	  if (X_RS1 (insn) != X_RD (insn)
    553      1.1  christos 	      && strchr (opcode->args, 'r') != 0)
    554      1.1  christos 	      /* Can't do simple format if source and dest are different.  */
    555      1.1  christos 	      continue;
    556      1.1  christos 	  if (X_RS2 (insn) != X_RD (insn)
    557      1.1  christos 	      && strchr (opcode->args, 'O') != 0)
    558      1.1  christos 	      /* Can't do simple format if source and dest are different.  */
    559      1.1  christos 	      continue;
    560      1.1  christos 
    561  1.1.1.2  christos 	  (*info->fprintf_func) (stream, "%s", opcode->name);
    562      1.1  christos 
    563      1.1  christos 	  {
    564      1.1  christos 	    const char *s;
    565      1.1  christos 
    566      1.1  christos 	    if (opcode->args[0] != ',')
    567      1.1  christos 	      (*info->fprintf_func) (stream, " ");
    568      1.1  christos 
    569      1.1  christos 	    for (s = opcode->args; *s != '\0'; ++s)
    570      1.1  christos 	      {
    571      1.1  christos 		while (*s == ',')
    572      1.1  christos 		  {
    573      1.1  christos 		    (*info->fprintf_func) (stream, ",");
    574      1.1  christos 		    ++s;
    575      1.1  christos 		    switch (*s)
    576      1.1  christos 		      {
    577      1.1  christos 		      case 'a':
    578      1.1  christos 			(*info->fprintf_func) (stream, "a");
    579      1.1  christos 			is_annulled = 1;
    580      1.1  christos 			++s;
    581      1.1  christos 			continue;
    582      1.1  christos 		      case 'N':
    583      1.1  christos 			(*info->fprintf_func) (stream, "pn");
    584      1.1  christos 			++s;
    585      1.1  christos 			continue;
    586      1.1  christos 
    587      1.1  christos 		      case 'T':
    588      1.1  christos 			(*info->fprintf_func) (stream, "pt");
    589      1.1  christos 			++s;
    590      1.1  christos 			continue;
    591      1.1  christos 
    592      1.1  christos 		      default:
    593      1.1  christos 			break;
    594      1.1  christos 		      }
    595      1.1  christos 		  }
    596      1.1  christos 
    597      1.1  christos 		(*info->fprintf_func) (stream, " ");
    598      1.1  christos 
    599      1.1  christos 		switch (*s)
    600      1.1  christos 		  {
    601      1.1  christos 		  case '+':
    602      1.1  christos 		    found_plus = 1;
    603      1.1  christos 		    /* Fall through.  */
    604      1.1  christos 
    605      1.1  christos 		  default:
    606      1.1  christos 		    (*info->fprintf_func) (stream, "%c", *s);
    607      1.1  christos 		    break;
    608      1.1  christos 
    609      1.1  christos 		  case '#':
    610      1.1  christos 		    (*info->fprintf_func) (stream, "0");
    611      1.1  christos 		    break;
    612      1.1  christos 
    613      1.1  christos #define	reg(n)	(*info->fprintf_func) (stream, "%%%s", reg_names[n])
    614      1.1  christos 		  case '1':
    615      1.1  christos 		  case 'r':
    616      1.1  christos 		    reg (X_RS1 (insn));
    617      1.1  christos 		    break;
    618      1.1  christos 
    619      1.1  christos 		  case '2':
    620      1.1  christos 		  case 'O':
    621      1.1  christos 		    reg (X_RS2 (insn));
    622      1.1  christos 		    break;
    623      1.1  christos 
    624      1.1  christos 		  case 'd':
    625      1.1  christos 		    reg (X_RD (insn));
    626      1.1  christos 		    break;
    627      1.1  christos #undef	reg
    628      1.1  christos 
    629      1.1  christos #define	freg(n)		(*info->fprintf_func) (stream, "%%%s", freg_names[n])
    630      1.1  christos #define	fregx(n)	(*info->fprintf_func) (stream, "%%%s", freg_names[((n) & ~1) | (((n) & 1) << 5)])
    631      1.1  christos 		  case 'e':
    632      1.1  christos 		    freg (X_RS1 (insn));
    633      1.1  christos 		    break;
    634      1.1  christos 		  case 'v':	/* Double/even.  */
    635      1.1  christos 		  case 'V':	/* Quad/multiple of 4.  */
    636      1.1  christos 		    fregx (X_RS1 (insn));
    637      1.1  christos 		    break;
    638      1.1  christos 
    639      1.1  christos 		  case 'f':
    640      1.1  christos 		    freg (X_RS2 (insn));
    641      1.1  christos 		    break;
    642      1.1  christos 		  case 'B':	/* Double/even.  */
    643      1.1  christos 		  case 'R':	/* Quad/multiple of 4.  */
    644      1.1  christos 		    fregx (X_RS2 (insn));
    645      1.1  christos 		    break;
    646      1.1  christos 
    647  1.1.1.2  christos 		  case '4':
    648  1.1.1.2  christos 		    freg (X_RS3 (insn));
    649  1.1.1.2  christos 		    break;
    650  1.1.1.2  christos 		  case '5':	/* Double/even.  */
    651  1.1.1.2  christos 		    fregx (X_RS3 (insn));
    652  1.1.1.2  christos 		    break;
    653  1.1.1.2  christos 
    654      1.1  christos 		  case 'g':
    655      1.1  christos 		    freg (X_RD (insn));
    656      1.1  christos 		    break;
    657      1.1  christos 		  case 'H':	/* Double/even.  */
    658      1.1  christos 		  case 'J':	/* Quad/multiple of 4.  */
    659  1.1.1.4  christos 		  case '}':     /* Double/even.  */
    660      1.1  christos 		    fregx (X_RD (insn));
    661      1.1  christos 		    break;
    662      1.1  christos #undef	freg
    663      1.1  christos #undef	fregx
    664      1.1  christos 
    665      1.1  christos #define	creg(n)	(*info->fprintf_func) (stream, "%%c%u", (unsigned int) (n))
    666      1.1  christos 		  case 'b':
    667      1.1  christos 		    creg (X_RS1 (insn));
    668      1.1  christos 		    break;
    669      1.1  christos 
    670      1.1  christos 		  case 'c':
    671      1.1  christos 		    creg (X_RS2 (insn));
    672      1.1  christos 		    break;
    673      1.1  christos 
    674      1.1  christos 		  case 'D':
    675      1.1  christos 		    creg (X_RD (insn));
    676      1.1  christos 		    break;
    677      1.1  christos #undef	creg
    678      1.1  christos 
    679      1.1  christos 		  case 'h':
    680      1.1  christos 		    (*info->fprintf_func) (stream, "%%hi(%#x)",
    681      1.1  christos 					   ((unsigned) 0xFFFFFFFF
    682      1.1  christos 					    & ((int) X_IMM22 (insn) << 10)));
    683      1.1  christos 		    break;
    684      1.1  christos 
    685      1.1  christos 		  case 'i':	/* 13 bit immediate.  */
    686      1.1  christos 		  case 'I':	/* 11 bit immediate.  */
    687      1.1  christos 		  case 'j':	/* 10 bit immediate.  */
    688      1.1  christos 		    {
    689      1.1  christos 		      int imm;
    690      1.1  christos 
    691      1.1  christos 		      if (*s == 'i')
    692      1.1  christos 		        imm = X_SIMM (insn, 13);
    693      1.1  christos 		      else if (*s == 'I')
    694      1.1  christos 			imm = X_SIMM (insn, 11);
    695      1.1  christos 		      else
    696      1.1  christos 			imm = X_SIMM (insn, 10);
    697      1.1  christos 
    698      1.1  christos 		      /* Check to see whether we have a 1+i, and take
    699      1.1  christos 			 note of that fact.
    700      1.1  christos 
    701      1.1  christos 			 Note: because of the way we sort the table,
    702      1.1  christos 			 we will be matching 1+i rather than i+1,
    703      1.1  christos 			 so it is OK to assume that i is after +,
    704      1.1  christos 			 not before it.  */
    705      1.1  christos 		      if (found_plus)
    706      1.1  christos 			imm_added_to_rs1 = 1;
    707      1.1  christos 
    708      1.1  christos 		      if (imm <= 9)
    709      1.1  christos 			(*info->fprintf_func) (stream, "%d", imm);
    710      1.1  christos 		      else
    711      1.1  christos 			(*info->fprintf_func) (stream, "%#x", imm);
    712      1.1  christos 		    }
    713      1.1  christos 		    break;
    714      1.1  christos 
    715  1.1.1.2  christos 		  case ')':	/* 5 bit unsigned immediate from RS3.  */
    716  1.1.1.2  christos 		    (info->fprintf_func) (stream, "%#x", (unsigned int) X_RS3 (insn));
    717  1.1.1.2  christos 		    break;
    718  1.1.1.2  christos 
    719      1.1  christos 		  case 'X':	/* 5 bit unsigned immediate.  */
    720      1.1  christos 		  case 'Y':	/* 6 bit unsigned immediate.  */
    721      1.1  christos 		    {
    722      1.1  christos 		      int imm = X_IMM (insn, *s == 'X' ? 5 : 6);
    723      1.1  christos 
    724      1.1  christos 		      if (imm <= 9)
    725      1.1  christos 			(info->fprintf_func) (stream, "%d", imm);
    726      1.1  christos 		      else
    727      1.1  christos 			(info->fprintf_func) (stream, "%#x", (unsigned) imm);
    728      1.1  christos 		    }
    729      1.1  christos 		    break;
    730      1.1  christos 
    731      1.1  christos 		  case '3':
    732      1.1  christos 		    (info->fprintf_func) (stream, "%ld", X_IMM (insn, 3));
    733      1.1  christos 		    break;
    734      1.1  christos 
    735      1.1  christos 		  case 'K':
    736      1.1  christos 		    {
    737      1.1  christos 		      int mask = X_MEMBAR (insn);
    738      1.1  christos 		      int bit = 0x40, printed_one = 0;
    739      1.1  christos 		      const char *name;
    740      1.1  christos 
    741      1.1  christos 		      if (mask == 0)
    742      1.1  christos 			(info->fprintf_func) (stream, "0");
    743      1.1  christos 		      else
    744      1.1  christos 			while (bit)
    745      1.1  christos 			  {
    746      1.1  christos 			    if (mask & bit)
    747      1.1  christos 			      {
    748      1.1  christos 				if (printed_one)
    749      1.1  christos 				  (info->fprintf_func) (stream, "|");
    750      1.1  christos 				name = sparc_decode_membar (bit);
    751      1.1  christos 				(info->fprintf_func) (stream, "%s", name);
    752      1.1  christos 				printed_one = 1;
    753      1.1  christos 			      }
    754      1.1  christos 			    bit >>= 1;
    755      1.1  christos 			  }
    756      1.1  christos 		      break;
    757      1.1  christos 		    }
    758      1.1  christos 
    759  1.1.1.2  christos 		  case '=':
    760  1.1.1.2  christos 		    info->target = memaddr + SEX (X_DISP10 (insn), 10) * 4;
    761  1.1.1.2  christos 		    (*info->print_address_func) (info->target, info);
    762  1.1.1.2  christos 		    break;
    763  1.1.1.2  christos 
    764      1.1  christos 		  case 'k':
    765      1.1  christos 		    info->target = memaddr + SEX (X_DISP16 (insn), 16) * 4;
    766      1.1  christos 		    (*info->print_address_func) (info->target, info);
    767      1.1  christos 		    break;
    768      1.1  christos 
    769      1.1  christos 		  case 'G':
    770      1.1  christos 		    info->target = memaddr + SEX (X_DISP19 (insn), 19) * 4;
    771      1.1  christos 		    (*info->print_address_func) (info->target, info);
    772      1.1  christos 		    break;
    773      1.1  christos 
    774      1.1  christos 		  case '6':
    775      1.1  christos 		  case '7':
    776      1.1  christos 		  case '8':
    777      1.1  christos 		  case '9':
    778      1.1  christos 		    (*info->fprintf_func) (stream, "%%fcc%c", *s - '6' + '0');
    779      1.1  christos 		    break;
    780      1.1  christos 
    781      1.1  christos 		  case 'z':
    782      1.1  christos 		    (*info->fprintf_func) (stream, "%%icc");
    783      1.1  christos 		    break;
    784      1.1  christos 
    785      1.1  christos 		  case 'Z':
    786      1.1  christos 		    (*info->fprintf_func) (stream, "%%xcc");
    787      1.1  christos 		    break;
    788      1.1  christos 
    789      1.1  christos 		  case 'E':
    790      1.1  christos 		    (*info->fprintf_func) (stream, "%%ccr");
    791      1.1  christos 		    break;
    792      1.1  christos 
    793      1.1  christos 		  case 's':
    794      1.1  christos 		    (*info->fprintf_func) (stream, "%%fprs");
    795      1.1  christos 		    break;
    796      1.1  christos 
    797  1.1.1.4  christos 		  case '{':
    798  1.1.1.4  christos 		    (*info->fprintf_func) (stream, "%%mcdper");
    799  1.1.1.4  christos 		    break;
    800  1.1.1.4  christos 
    801      1.1  christos 		  case 'o':
    802      1.1  christos 		    (*info->fprintf_func) (stream, "%%asi");
    803      1.1  christos 		    break;
    804      1.1  christos 
    805      1.1  christos 		  case 'W':
    806      1.1  christos 		    (*info->fprintf_func) (stream, "%%tick");
    807      1.1  christos 		    break;
    808      1.1  christos 
    809      1.1  christos 		  case 'P':
    810      1.1  christos 		    (*info->fprintf_func) (stream, "%%pc");
    811      1.1  christos 		    break;
    812      1.1  christos 
    813      1.1  christos 		  case '?':
    814      1.1  christos 		    if (X_RS1 (insn) == 31)
    815      1.1  christos 		      (*info->fprintf_func) (stream, "%%ver");
    816      1.1  christos 		    else if ((unsigned) X_RS1 (insn) < 17)
    817      1.1  christos 		      (*info->fprintf_func) (stream, "%%%s",
    818      1.1  christos 					     v9_priv_reg_names[X_RS1 (insn)]);
    819      1.1  christos 		    else
    820      1.1  christos 		      (*info->fprintf_func) (stream, "%%reserved");
    821      1.1  christos 		    break;
    822      1.1  christos 
    823      1.1  christos 		  case '!':
    824      1.1  christos 		    if ((unsigned) X_RD (insn) < 17)
    825      1.1  christos 		      (*info->fprintf_func) (stream, "%%%s",
    826      1.1  christos 					     v9_priv_reg_names[X_RD (insn)]);
    827      1.1  christos 		    else
    828      1.1  christos 		      (*info->fprintf_func) (stream, "%%reserved");
    829      1.1  christos 		    break;
    830      1.1  christos 
    831      1.1  christos 		  case '$':
    832      1.1  christos 		    if ((unsigned) X_RS1 (insn) < 32)
    833      1.1  christos 		      (*info->fprintf_func) (stream, "%%%s",
    834      1.1  christos 					     v9_hpriv_reg_names[X_RS1 (insn)]);
    835      1.1  christos 		    else
    836      1.1  christos 		      (*info->fprintf_func) (stream, "%%reserved");
    837      1.1  christos 		    break;
    838      1.1  christos 
    839      1.1  christos 		  case '%':
    840      1.1  christos 		    if ((unsigned) X_RD (insn) < 32)
    841      1.1  christos 		      (*info->fprintf_func) (stream, "%%%s",
    842      1.1  christos 					     v9_hpriv_reg_names[X_RD (insn)]);
    843      1.1  christos 		    else
    844      1.1  christos 		      (*info->fprintf_func) (stream, "%%reserved");
    845      1.1  christos 		    break;
    846      1.1  christos 
    847      1.1  christos 		  case '/':
    848  1.1.1.2  christos 		    if (X_RS1 (insn) < 16 || X_RS1 (insn) > 28)
    849      1.1  christos 		      (*info->fprintf_func) (stream, "%%reserved");
    850      1.1  christos 		    else
    851      1.1  christos 		      (*info->fprintf_func) (stream, "%%%s",
    852      1.1  christos 					     v9a_asr_reg_names[X_RS1 (insn)-16]);
    853      1.1  christos 		    break;
    854      1.1  christos 
    855      1.1  christos 		  case '_':
    856  1.1.1.2  christos 		    if (X_RD (insn) < 16 || X_RD (insn) > 28)
    857      1.1  christos 		      (*info->fprintf_func) (stream, "%%reserved");
    858      1.1  christos 		    else
    859      1.1  christos 		      (*info->fprintf_func) (stream, "%%%s",
    860      1.1  christos 					     v9a_asr_reg_names[X_RD (insn)-16]);
    861      1.1  christos 		    break;
    862      1.1  christos 
    863      1.1  christos 		  case '*':
    864      1.1  christos 		    {
    865      1.1  christos 		      const char *name = sparc_decode_prefetch (X_RD (insn));
    866      1.1  christos 
    867      1.1  christos 		      if (name)
    868      1.1  christos 			(*info->fprintf_func) (stream, "%s", name);
    869      1.1  christos 		      else
    870      1.1  christos 			(*info->fprintf_func) (stream, "%ld", X_RD (insn));
    871      1.1  christos 		      break;
    872      1.1  christos 		    }
    873      1.1  christos 
    874      1.1  christos 		  case 'M':
    875      1.1  christos 		    (*info->fprintf_func) (stream, "%%asr%ld", X_RS1 (insn));
    876      1.1  christos 		    break;
    877      1.1  christos 
    878      1.1  christos 		  case 'm':
    879      1.1  christos 		    (*info->fprintf_func) (stream, "%%asr%ld", X_RD (insn));
    880      1.1  christos 		    break;
    881      1.1  christos 
    882      1.1  christos 		  case 'L':
    883      1.1  christos 		    info->target = memaddr + SEX (X_DISP30 (insn), 30) * 4;
    884      1.1  christos 		    (*info->print_address_func) (info->target, info);
    885      1.1  christos 		    break;
    886      1.1  christos 
    887      1.1  christos 		  case 'n':
    888      1.1  christos 		    (*info->fprintf_func)
    889      1.1  christos 		      (stream, "%#x", SEX (X_DISP22 (insn), 22));
    890      1.1  christos 		    break;
    891      1.1  christos 
    892      1.1  christos 		  case 'l':
    893      1.1  christos 		    info->target = memaddr + SEX (X_DISP22 (insn), 22) * 4;
    894      1.1  christos 		    (*info->print_address_func) (info->target, info);
    895      1.1  christos 		    break;
    896      1.1  christos 
    897      1.1  christos 		  case 'A':
    898      1.1  christos 		    {
    899      1.1  christos 		      const char *name = sparc_decode_asi (X_ASI (insn));
    900      1.1  christos 
    901      1.1  christos 		      if (name)
    902      1.1  christos 			(*info->fprintf_func) (stream, "%s", name);
    903      1.1  christos 		      else
    904      1.1  christos 			(*info->fprintf_func) (stream, "(%ld)", X_ASI (insn));
    905      1.1  christos 		      break;
    906      1.1  christos 		    }
    907      1.1  christos 
    908      1.1  christos 		  case 'C':
    909      1.1  christos 		    (*info->fprintf_func) (stream, "%%csr");
    910      1.1  christos 		    break;
    911      1.1  christos 
    912      1.1  christos 		  case 'F':
    913      1.1  christos 		    (*info->fprintf_func) (stream, "%%fsr");
    914      1.1  christos 		    break;
    915      1.1  christos 
    916  1.1.1.2  christos 		  case '(':
    917  1.1.1.2  christos 		    (*info->fprintf_func) (stream, "%%efsr");
    918  1.1.1.2  christos 		    break;
    919  1.1.1.2  christos 
    920      1.1  christos 		  case 'p':
    921      1.1  christos 		    (*info->fprintf_func) (stream, "%%psr");
    922      1.1  christos 		    break;
    923      1.1  christos 
    924      1.1  christos 		  case 'q':
    925      1.1  christos 		    (*info->fprintf_func) (stream, "%%fq");
    926      1.1  christos 		    break;
    927      1.1  christos 
    928      1.1  christos 		  case 'Q':
    929      1.1  christos 		    (*info->fprintf_func) (stream, "%%cq");
    930      1.1  christos 		    break;
    931      1.1  christos 
    932      1.1  christos 		  case 't':
    933      1.1  christos 		    (*info->fprintf_func) (stream, "%%tbr");
    934      1.1  christos 		    break;
    935      1.1  christos 
    936      1.1  christos 		  case 'w':
    937      1.1  christos 		    (*info->fprintf_func) (stream, "%%wim");
    938      1.1  christos 		    break;
    939      1.1  christos 
    940      1.1  christos 		  case 'x':
    941      1.1  christos 		    (*info->fprintf_func) (stream, "%ld",
    942      1.1  christos 					   ((X_LDST_I (insn) << 8)
    943      1.1  christos 					    + X_ASI (insn)));
    944      1.1  christos 		    break;
    945      1.1  christos 
    946      1.1  christos 		  case 'y':
    947      1.1  christos 		    (*info->fprintf_func) (stream, "%%y");
    948      1.1  christos 		    break;
    949      1.1  christos 
    950      1.1  christos 		  case 'u':
    951      1.1  christos 		  case 'U':
    952      1.1  christos 		    {
    953      1.1  christos 		      int val = *s == 'U' ? X_RS1 (insn) : X_RD (insn);
    954      1.1  christos 		      const char *name = sparc_decode_sparclet_cpreg (val);
    955      1.1  christos 
    956      1.1  christos 		      if (name)
    957      1.1  christos 			(*info->fprintf_func) (stream, "%s", name);
    958      1.1  christos 		      else
    959      1.1  christos 			(*info->fprintf_func) (stream, "%%cpreg(%d)", val);
    960      1.1  christos 		      break;
    961      1.1  christos 		    }
    962      1.1  christos 		  }
    963      1.1  christos 	      }
    964      1.1  christos 	  }
    965      1.1  christos 
    966      1.1  christos 	  /* If we are adding or or'ing something to rs1, then
    967      1.1  christos 	     check to see whether the previous instruction was
    968      1.1  christos 	     a sethi to the same register as in the sethi.
    969      1.1  christos 	     If so, attempt to print the result of the add or
    970      1.1  christos 	     or (in this context add and or do the same thing)
    971      1.1  christos 	     and its symbolic value.  */
    972      1.1  christos 	  if (imm_ored_to_rs1 || imm_added_to_rs1)
    973      1.1  christos 	    {
    974      1.1  christos 	      unsigned long prev_insn;
    975      1.1  christos 	      int errcode;
    976      1.1  christos 
    977      1.1  christos 	      if (memaddr >= 4)
    978      1.1  christos 		errcode =
    979      1.1  christos 		  (*info->read_memory_func)
    980      1.1  christos 		  (memaddr - 4, buffer, sizeof (buffer), info);
    981      1.1  christos 	      else
    982      1.1  christos 		errcode = 1;
    983      1.1  christos 
    984      1.1  christos 	      prev_insn = getword (buffer);
    985      1.1  christos 
    986      1.1  christos 	      if (errcode == 0)
    987      1.1  christos 		{
    988      1.1  christos 		  /* If it is a delayed branch, we need to look at the
    989      1.1  christos 		     instruction before the delayed branch.  This handles
    990      1.1  christos 		     sequences such as:
    991      1.1  christos 
    992      1.1  christos 		     sethi %o1, %hi(_foo), %o1
    993      1.1  christos 		     call _printf
    994      1.1  christos 		     or %o1, %lo(_foo), %o1  */
    995      1.1  christos 
    996      1.1  christos 		  if (is_delayed_branch (prev_insn))
    997      1.1  christos 		    {
    998      1.1  christos 		      if (memaddr >= 8)
    999      1.1  christos 			errcode = (*info->read_memory_func)
   1000      1.1  christos 			  (memaddr - 8, buffer, sizeof (buffer), info);
   1001      1.1  christos 		      else
   1002      1.1  christos 			errcode = 1;
   1003      1.1  christos 
   1004      1.1  christos 		      prev_insn = getword (buffer);
   1005      1.1  christos 		    }
   1006      1.1  christos 		}
   1007      1.1  christos 
   1008      1.1  christos 	      /* If there was a problem reading memory, then assume
   1009      1.1  christos 		 the previous instruction was not sethi.  */
   1010      1.1  christos 	      if (errcode == 0)
   1011      1.1  christos 		{
   1012      1.1  christos 		  /* Is it sethi to the same register?  */
   1013      1.1  christos 		  if ((prev_insn & 0xc1c00000) == 0x01000000
   1014      1.1  christos 		      && X_RD (prev_insn) == X_RS1 (insn))
   1015      1.1  christos 		    {
   1016      1.1  christos 		      (*info->fprintf_func) (stream, "\t! ");
   1017      1.1  christos 		      info->target =
   1018      1.1  christos 			((unsigned) 0xFFFFFFFF
   1019      1.1  christos 			 & ((int) X_IMM22 (prev_insn) << 10));
   1020      1.1  christos 		      if (imm_added_to_rs1)
   1021      1.1  christos 			info->target += X_SIMM (insn, 13);
   1022      1.1  christos 		      else
   1023      1.1  christos 			info->target |= X_SIMM (insn, 13);
   1024      1.1  christos 		      (*info->print_address_func) (info->target, info);
   1025      1.1  christos 		      info->insn_type = dis_dref;
   1026      1.1  christos 		      info->data_size = 4;  /* FIXME!!! */
   1027      1.1  christos 		    }
   1028      1.1  christos 		}
   1029      1.1  christos 	    }
   1030      1.1  christos 
   1031      1.1  christos 	  if (opcode->flags & (F_UNBR|F_CONDBR|F_JSR))
   1032      1.1  christos 	    {
   1033      1.1  christos 	      /* FIXME -- check is_annulled flag.  */
   1034      1.1  christos 	      (void) is_annulled;
   1035      1.1  christos 	      if (opcode->flags & F_UNBR)
   1036      1.1  christos 		info->insn_type = dis_branch;
   1037      1.1  christos 	      if (opcode->flags & F_CONDBR)
   1038      1.1  christos 		info->insn_type = dis_condbranch;
   1039      1.1  christos 	      if (opcode->flags & F_JSR)
   1040      1.1  christos 		info->insn_type = dis_jsr;
   1041      1.1  christos 	      if (opcode->flags & F_DELAYED)
   1042      1.1  christos 		info->branch_delay_insns = 1;
   1043      1.1  christos 	    }
   1044      1.1  christos 
   1045      1.1  christos 	  return sizeof (buffer);
   1046      1.1  christos 	}
   1047      1.1  christos     }
   1048      1.1  christos 
   1049      1.1  christos   info->insn_type = dis_noninsn;	/* Mark as non-valid instruction.  */
   1050      1.1  christos   (*info->fprintf_func) (stream, _("unknown"));
   1051      1.1  christos   return sizeof (buffer);
   1052      1.1  christos }
   1053