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