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