Back to index

cell-binutils  2.17cvs20070401
i386-dis.c
Go to the documentation of this file.
00001 /* Print i386 instructions for GDB, the GNU debugger.
00002    Copyright 1988, 1989, 1991, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
00003    2001, 2002, 2003, 2004, 2005, 2006 Free Software Foundation, Inc.
00004 
00005    This file is part of GDB.
00006 
00007    This program is free software; you can redistribute it and/or modify
00008    it under the terms of the GNU General Public License as published by
00009    the Free Software Foundation; either version 2 of the License, or
00010    (at your option) any later version.
00011 
00012    This program is distributed in the hope that it will be useful,
00013    but WITHOUT ANY WARRANTY; without even the implied warranty of
00014    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015    GNU General Public License for more details.
00016 
00017    You should have received a copy of the GNU General Public License
00018    along with this program; if not, write to the Free Software
00019    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
00020 
00021 /* 80386 instruction printer by Pace Willisson (pace@prep.ai.mit.edu)
00022    July 1988
00023     modified by John Hassey (hassey@dg-rtp.dg.com)
00024     x86-64 support added by Jan Hubicka (jh@suse.cz)
00025     VIA PadLock support by Michal Ludvig (mludvig@suse.cz).  */
00026 
00027 /* The main tables describing the instructions is essentially a copy
00028    of the "Opcode Map" chapter (Appendix A) of the Intel 80386
00029    Programmers Manual.  Usually, there is a capital letter, followed
00030    by a small letter.  The capital letter tell the addressing mode,
00031    and the small letter tells about the operand size.  Refer to
00032    the Intel manual for details.  */
00033 
00034 #include "dis-asm.h"
00035 #include "sysdep.h"
00036 #include "opintl.h"
00037 #include "opcode/i386.h"
00038 
00039 #include <setjmp.h>
00040 
00041 static int fetch_data (struct disassemble_info *, bfd_byte *);
00042 static void ckprefix (void);
00043 static const char *prefix_name (int, int);
00044 static int print_insn (bfd_vma, disassemble_info *);
00045 static void dofloat (int);
00046 static void OP_ST (int, int);
00047 static void OP_STi (int, int);
00048 static int putop (const char *, int);
00049 static void oappend (const char *);
00050 static void append_seg (void);
00051 static void OP_indirE (int, int);
00052 static void print_operand_value (char *, int, bfd_vma);
00053 static void OP_E (int, int);
00054 static void OP_G (int, int);
00055 static bfd_vma get64 (void);
00056 static bfd_signed_vma get32 (void);
00057 static bfd_signed_vma get32s (void);
00058 static int get16 (void);
00059 static void set_op (bfd_vma, int);
00060 static void OP_REG (int, int);
00061 static void OP_IMREG (int, int);
00062 static void OP_I (int, int);
00063 static void OP_I64 (int, int);
00064 static void OP_sI (int, int);
00065 static void OP_J (int, int);
00066 static void OP_SEG (int, int);
00067 static void OP_DIR (int, int);
00068 static void OP_OFF (int, int);
00069 static void OP_OFF64 (int, int);
00070 static void ptr_reg (int, int);
00071 static void OP_ESreg (int, int);
00072 static void OP_DSreg (int, int);
00073 static void OP_C (int, int);
00074 static void OP_D (int, int);
00075 static void OP_T (int, int);
00076 static void OP_R (int, int);
00077 static void OP_MMX (int, int);
00078 static void OP_XMM (int, int);
00079 static void OP_EM (int, int);
00080 static void OP_EX (int, int);
00081 static void OP_EMC (int,int);
00082 static void OP_MXC (int,int);
00083 static void OP_MS (int, int);
00084 static void OP_XS (int, int);
00085 static void OP_M (int, int);
00086 static void OP_VMX (int, int);
00087 static void OP_0fae (int, int);
00088 static void OP_0f07 (int, int);
00089 static void NOP_Fixup1 (int, int);
00090 static void NOP_Fixup2 (int, int);
00091 static void OP_3DNowSuffix (int, int);
00092 static void OP_SIMD_Suffix (int, int);
00093 static void SIMD_Fixup (int, int);
00094 static void PNI_Fixup (int, int);
00095 static void SVME_Fixup (int, int);
00096 static void INVLPG_Fixup (int, int);
00097 static void BadOp (void);
00098 static void VMX_Fixup (int, int);
00099 static void REP_Fixup (int, int);
00100 static void CMPXCHG8B_Fixup (int, int);
00101 
00102 struct dis_private {
00103   /* Points to first byte not fetched.  */
00104   bfd_byte *max_fetched;
00105   bfd_byte the_buffer[MAX_MNEM_SIZE];
00106   bfd_vma insn_start;
00107   int orig_sizeflag;
00108   jmp_buf bailout;
00109 };
00110 
00111 enum address_mode
00112 {
00113   mode_16bit,
00114   mode_32bit,
00115   mode_64bit
00116 };
00117 
00118 enum address_mode address_mode;
00119 
00120 /* Flags for the prefixes for the current instruction.  See below.  */
00121 static int prefixes;
00122 
00123 /* REX prefix the current instruction.  See below.  */
00124 static int rex;
00125 /* Bits of REX we've already used.  */
00126 static int rex_used;
00127 /* Mark parts used in the REX prefix.  When we are testing for
00128    empty prefix (for 8bit register REX extension), just mask it
00129    out.  Otherwise test for REX bit is excuse for existence of REX
00130    only in case value is nonzero.  */
00131 #define USED_REX(value)                                 \
00132   {                                              \
00133     if (value)                                          \
00134       {                                                 \
00135        if ((rex & value))                        \
00136          rex_used |= (value) | REX_OPCODE;              \
00137       }                                                 \
00138     else                                         \
00139       rex_used |= REX_OPCODE;                           \
00140   }
00141 
00142 /* Flags for prefixes which we somehow handled when printing the
00143    current instruction.  */
00144 static int used_prefixes;
00145 
00146 /* Flags stored in PREFIXES.  */
00147 #define PREFIX_REPZ 1
00148 #define PREFIX_REPNZ 2
00149 #define PREFIX_LOCK 4
00150 #define PREFIX_CS 8
00151 #define PREFIX_SS 0x10
00152 #define PREFIX_DS 0x20
00153 #define PREFIX_ES 0x40
00154 #define PREFIX_FS 0x80
00155 #define PREFIX_GS 0x100
00156 #define PREFIX_DATA 0x200
00157 #define PREFIX_ADDR 0x400
00158 #define PREFIX_FWAIT 0x800
00159 
00160 /* Make sure that bytes from INFO->PRIVATE_DATA->BUFFER (inclusive)
00161    to ADDR (exclusive) are valid.  Returns 1 for success, longjmps
00162    on error.  */
00163 #define FETCH_DATA(info, addr) \
00164   ((addr) <= ((struct dis_private *) (info->private_data))->max_fetched \
00165    ? 1 : fetch_data ((info), (addr)))
00166 
00167 static int
00168 fetch_data (struct disassemble_info *info, bfd_byte *addr)
00169 {
00170   int status;
00171   struct dis_private *priv = (struct dis_private *) info->private_data;
00172   bfd_vma start = priv->insn_start + (priv->max_fetched - priv->the_buffer);
00173 
00174   if (addr <= priv->the_buffer + MAX_MNEM_SIZE)
00175     status = (*info->read_memory_func) (start,
00176                                    priv->max_fetched,
00177                                    addr - priv->max_fetched,
00178                                    info);
00179   else
00180     status = -1;
00181   if (status != 0)
00182     {
00183       /* If we did manage to read at least one byte, then
00184         print_insn_i386 will do something sensible.  Otherwise, print
00185         an error.  We do that here because this is where we know
00186         STATUS.  */
00187       if (priv->max_fetched == priv->the_buffer)
00188        (*info->memory_error_func) (status, start, info);
00189       longjmp (priv->bailout, 1);
00190     }
00191   else
00192     priv->max_fetched = addr;
00193   return 1;
00194 }
00195 
00196 #define XX { NULL, 0 }
00197 
00198 #define Eb { OP_E, b_mode }
00199 #define Ev { OP_E, v_mode }
00200 #define Ed { OP_E, d_mode }
00201 #define Edq { OP_E, dq_mode }
00202 #define Edqw { OP_E, dqw_mode }
00203 #define indirEv { OP_indirE, stack_v_mode }
00204 #define indirEp { OP_indirE, f_mode }
00205 #define stackEv { OP_E, stack_v_mode }
00206 #define Em { OP_E, m_mode }
00207 #define Ew { OP_E, w_mode }
00208 #define M { OP_M, 0 }              /* lea, lgdt, etc. */
00209 #define Ma { OP_M, v_mode }
00210 #define Mp { OP_M, f_mode }        /* 32 or 48 bit memory operand for LDS, LES etc */
00211 #define Mq { OP_M, q_mode }
00212 #define Gb { OP_G, b_mode }
00213 #define Gv { OP_G, v_mode }
00214 #define Gd { OP_G, d_mode }
00215 #define Gdq { OP_G, dq_mode }
00216 #define Gm { OP_G, m_mode }
00217 #define Gw { OP_G, w_mode }
00218 #define Rd { OP_R, d_mode }
00219 #define Rm { OP_R, m_mode }
00220 #define Ib { OP_I, b_mode }
00221 #define sIb { OP_sI, b_mode }      /* sign extened byte */
00222 #define Iv { OP_I, v_mode }
00223 #define Iq { OP_I, q_mode }
00224 #define Iv64 { OP_I64, v_mode }
00225 #define Iw { OP_I, w_mode }
00226 #define I1 { OP_I, const_1_mode }
00227 #define Jb { OP_J, b_mode }
00228 #define Jv { OP_J, v_mode }
00229 #define Cm { OP_C, m_mode }
00230 #define Dm { OP_D, m_mode }
00231 #define Td { OP_T, d_mode }
00232 
00233 #define RMeAX { OP_REG, eAX_reg }
00234 #define RMeBX { OP_REG, eBX_reg }
00235 #define RMeCX { OP_REG, eCX_reg }
00236 #define RMeDX { OP_REG, eDX_reg }
00237 #define RMeSP { OP_REG, eSP_reg }
00238 #define RMeBP { OP_REG, eBP_reg }
00239 #define RMeSI { OP_REG, eSI_reg }
00240 #define RMeDI { OP_REG, eDI_reg }
00241 #define RMrAX { OP_REG, rAX_reg }
00242 #define RMrBX { OP_REG, rBX_reg }
00243 #define RMrCX { OP_REG, rCX_reg }
00244 #define RMrDX { OP_REG, rDX_reg }
00245 #define RMrSP { OP_REG, rSP_reg }
00246 #define RMrBP { OP_REG, rBP_reg }
00247 #define RMrSI { OP_REG, rSI_reg }
00248 #define RMrDI { OP_REG, rDI_reg }
00249 #define RMAL { OP_REG, al_reg }
00250 #define RMAL { OP_REG, al_reg }
00251 #define RMCL { OP_REG, cl_reg }
00252 #define RMDL { OP_REG, dl_reg }
00253 #define RMBL { OP_REG, bl_reg }
00254 #define RMAH { OP_REG, ah_reg }
00255 #define RMCH { OP_REG, ch_reg }
00256 #define RMDH { OP_REG, dh_reg }
00257 #define RMBH { OP_REG, bh_reg }
00258 #define RMAX { OP_REG, ax_reg }
00259 #define RMDX { OP_REG, dx_reg }
00260 
00261 #define eAX { OP_IMREG, eAX_reg }
00262 #define eBX { OP_IMREG, eBX_reg }
00263 #define eCX { OP_IMREG, eCX_reg }
00264 #define eDX { OP_IMREG, eDX_reg }
00265 #define eSP { OP_IMREG, eSP_reg }
00266 #define eBP { OP_IMREG, eBP_reg }
00267 #define eSI { OP_IMREG, eSI_reg }
00268 #define eDI { OP_IMREG, eDI_reg }
00269 #define AL { OP_IMREG, al_reg }
00270 #define CL { OP_IMREG, cl_reg }
00271 #define DL { OP_IMREG, dl_reg }
00272 #define BL { OP_IMREG, bl_reg }
00273 #define AH { OP_IMREG, ah_reg }
00274 #define CH { OP_IMREG, ch_reg }
00275 #define DH { OP_IMREG, dh_reg }
00276 #define BH { OP_IMREG, bh_reg }
00277 #define AX { OP_IMREG, ax_reg }
00278 #define DX { OP_IMREG, dx_reg }
00279 #define zAX { OP_IMREG, z_mode_ax_reg }
00280 #define indirDX { OP_IMREG, indir_dx_reg }
00281 
00282 #define Sw { OP_SEG, w_mode }
00283 #define Sv { OP_SEG, v_mode }
00284 #define Ap { OP_DIR, 0 }
00285 #define Ob { OP_OFF64, b_mode }
00286 #define Ov { OP_OFF64, v_mode }
00287 #define Xb { OP_DSreg, eSI_reg }
00288 #define Xv { OP_DSreg, eSI_reg }
00289 #define Xz { OP_DSreg, eSI_reg }
00290 #define Yb { OP_ESreg, eDI_reg }
00291 #define Yv { OP_ESreg, eDI_reg }
00292 #define DSBX { OP_DSreg, eBX_reg }
00293 
00294 #define es { OP_REG, es_reg }
00295 #define ss { OP_REG, ss_reg }
00296 #define cs { OP_REG, cs_reg }
00297 #define ds { OP_REG, ds_reg }
00298 #define fs { OP_REG, fs_reg }
00299 #define gs { OP_REG, gs_reg }
00300 
00301 #define MX { OP_MMX, 0 }
00302 #define XM { OP_XMM, 0 }
00303 #define EM { OP_EM, v_mode }
00304 #define EX { OP_EX, v_mode }
00305 #define MS { OP_MS, v_mode }
00306 #define XS { OP_XS, v_mode }
00307 #define EMC { OP_EMC, v_mode }
00308 #define MXC { OP_MXC, 0 }
00309 #define VM { OP_VMX, q_mode }
00310 #define OPSUF { OP_3DNowSuffix, 0 }
00311 #define OPSIMD { OP_SIMD_Suffix, 0 }
00312 
00313 /* Used handle "rep" prefix for string instructions.  */
00314 #define Xbr { REP_Fixup, eSI_reg }
00315 #define Xvr { REP_Fixup, eSI_reg }
00316 #define Ybr { REP_Fixup, eDI_reg }
00317 #define Yvr { REP_Fixup, eDI_reg }
00318 #define Yzr { REP_Fixup, eDI_reg }
00319 #define indirDXr { REP_Fixup, indir_dx_reg }
00320 #define ALr { REP_Fixup, al_reg }
00321 #define eAXr { REP_Fixup, eAX_reg }
00322 
00323 #define cond_jump_flag { NULL, cond_jump_mode }
00324 #define loop_jcxz_flag { NULL, loop_jcxz_mode }
00325 
00326 /* bits in sizeflag */
00327 #define SUFFIX_ALWAYS 4
00328 #define AFLAG 2
00329 #define DFLAG 1
00330 
00331 #define b_mode 1  /* byte operand */
00332 #define v_mode 2  /* operand size depends on prefixes */
00333 #define w_mode 3  /* word operand */
00334 #define d_mode 4  /* double word operand  */
00335 #define q_mode 5  /* quad word operand */
00336 #define t_mode 6  /* ten-byte operand */
00337 #define x_mode 7  /* 16-byte XMM operand */
00338 #define m_mode 8  /* d_mode in 32bit, q_mode in 64bit mode.  */
00339 #define cond_jump_mode 9
00340 #define loop_jcxz_mode 10
00341 #define dq_mode 11 /* operand size depends on REX prefixes.  */
00342 #define dqw_mode 12 /* registers like dq_mode, memory like w_mode.  */
00343 #define f_mode 13 /* 4- or 6-byte pointer operand */
00344 #define const_1_mode 14
00345 #define stack_v_mode 15 /* v_mode for stack-related opcodes.  */
00346 #define z_mode 16 /* non-quad operand size depends on prefixes */
00347 #define o_mode 17  /* 16-byte operand */
00348 
00349 #define es_reg 100
00350 #define cs_reg 101
00351 #define ss_reg 102
00352 #define ds_reg 103
00353 #define fs_reg 104
00354 #define gs_reg 105
00355 
00356 #define eAX_reg 108
00357 #define eCX_reg 109
00358 #define eDX_reg 110
00359 #define eBX_reg 111
00360 #define eSP_reg 112
00361 #define eBP_reg 113
00362 #define eSI_reg 114
00363 #define eDI_reg 115
00364 
00365 #define al_reg 116
00366 #define cl_reg 117
00367 #define dl_reg 118
00368 #define bl_reg 119
00369 #define ah_reg 120
00370 #define ch_reg 121
00371 #define dh_reg 122
00372 #define bh_reg 123
00373 
00374 #define ax_reg 124
00375 #define cx_reg 125
00376 #define dx_reg 126
00377 #define bx_reg 127
00378 #define sp_reg 128
00379 #define bp_reg 129
00380 #define si_reg 130
00381 #define di_reg 131
00382 
00383 #define rAX_reg 132
00384 #define rCX_reg 133
00385 #define rDX_reg 134
00386 #define rBX_reg 135
00387 #define rSP_reg 136
00388 #define rBP_reg 137
00389 #define rSI_reg 138
00390 #define rDI_reg 139
00391 
00392 #define z_mode_ax_reg 149
00393 #define indir_dx_reg 150
00394 
00395 #define FLOATCODE 1
00396 #define USE_GROUPS 2
00397 #define USE_PREFIX_USER_TABLE 3
00398 #define X86_64_SPECIAL 4
00399 #define IS_3BYTE_OPCODE 5
00400 
00401 #define FLOAT   NULL, { { NULL, FLOATCODE } }
00402 
00403 #define GRP1b   NULL, { { NULL, USE_GROUPS }, { NULL,  0 } }
00404 #define GRP1S   NULL, { { NULL, USE_GROUPS }, { NULL,  1 } }
00405 #define GRP1Ss         NULL, { { NULL, USE_GROUPS }, { NULL,  2 } }
00406 #define GRP2b   NULL, { { NULL, USE_GROUPS }, { NULL,  3 } }
00407 #define GRP2S   NULL, { { NULL, USE_GROUPS }, { NULL,  4 } }
00408 #define GRP2b_one NULL, { { NULL, USE_GROUPS }, { NULL,  5 } }
00409 #define GRP2S_one NULL, { { NULL, USE_GROUPS }, { NULL,  6 } }
00410 #define GRP2b_cl  NULL, { { NULL, USE_GROUPS }, { NULL,  7 } }
00411 #define GRP2S_cl  NULL, { { NULL, USE_GROUPS }, { NULL,  8 } }
00412 #define GRP3b   NULL, { { NULL, USE_GROUPS }, { NULL,  9 } }
00413 #define GRP3S   NULL, { { NULL, USE_GROUPS }, { NULL, 10 } }
00414 #define GRP4    NULL, { { NULL, USE_GROUPS }, { NULL, 11 } }
00415 #define GRP5    NULL, { { NULL, USE_GROUPS }, { NULL, 12 } }
00416 #define GRP6    NULL, { { NULL, USE_GROUPS }, { NULL, 13 } }
00417 #define GRP7    NULL, { { NULL, USE_GROUPS }, { NULL, 14 } }
00418 #define GRP8    NULL, { { NULL, USE_GROUPS }, { NULL, 15 } }
00419 #define GRP9    NULL, { { NULL, USE_GROUPS }, { NULL, 16 } }
00420 #define GRP11_C6  NULL, { { NULL, USE_GROUPS }, { NULL, 17 } }
00421 #define GRP11_C7  NULL, { { NULL, USE_GROUPS }, { NULL, 18 } }
00422 #define GRP12   NULL, { { NULL, USE_GROUPS }, { NULL, 19 } }
00423 #define GRP13   NULL, { { NULL, USE_GROUPS }, { NULL, 20 } }
00424 #define GRP14   NULL, { { NULL, USE_GROUPS }, { NULL, 21 } }
00425 #define GRP15   NULL, { { NULL, USE_GROUPS }, { NULL, 22 } }
00426 #define GRP16   NULL, { { NULL, USE_GROUPS }, { NULL, 23 } }
00427 #define GRPAMD         NULL, { { NULL, USE_GROUPS }, { NULL, 24 } }
00428 #define GRPPADLCK1 NULL, { { NULL, USE_GROUPS }, { NULL, 25 } }
00429 #define GRPPADLCK2 NULL, { { NULL, USE_GROUPS }, { NULL, 26 } }
00430 
00431 #define PREGRP0   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  0 } }
00432 #define PREGRP1   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  1 } }
00433 #define PREGRP2   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  2 } }
00434 #define PREGRP3   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  3 } }
00435 #define PREGRP4   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  4 } }
00436 #define PREGRP5   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  5 } }
00437 #define PREGRP6   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  6 } }
00438 #define PREGRP7   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  7 } }
00439 #define PREGRP8   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  8 } }
00440 #define PREGRP9   NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL,  9 } }
00441 #define PREGRP10  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 10 } }
00442 #define PREGRP11  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 11 } }
00443 #define PREGRP12  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 12 } }
00444 #define PREGRP13  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 13 } }
00445 #define PREGRP14  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 14 } }
00446 #define PREGRP15  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 15 } }
00447 #define PREGRP16  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 16 } }
00448 #define PREGRP17  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 17 } }
00449 #define PREGRP18  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 18 } }
00450 #define PREGRP19  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 19 } }
00451 #define PREGRP20  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 20 } }
00452 #define PREGRP21  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 21 } }
00453 #define PREGRP22  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 22 } }
00454 #define PREGRP23  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 23 } }
00455 #define PREGRP24  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 24 } }
00456 #define PREGRP25  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 25 } }
00457 #define PREGRP26  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 26 } }
00458 #define PREGRP27  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 27 } }
00459 #define PREGRP28  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 28 } }
00460 #define PREGRP29  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 29 } }
00461 #define PREGRP30  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 30 } }
00462 #define PREGRP31  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 31 } }
00463 #define PREGRP32  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 32 } }
00464 #define PREGRP33  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 33 } }
00465 #define PREGRP34  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 34 } }
00466 #define PREGRP35  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 35 } }
00467 #define PREGRP36  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 36 } }
00468 #define PREGRP37  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 37 } }
00469 #define PREGRP38  NULL, { { NULL, USE_PREFIX_USER_TABLE }, { NULL, 38 } }
00470 
00471 
00472 #define X86_64_0  NULL, { { NULL, X86_64_SPECIAL }, { NULL, 0 } }
00473 #define X86_64_1  NULL, { { NULL, X86_64_SPECIAL }, { NULL, 1 } }
00474 #define X86_64_2  NULL, { { NULL, X86_64_SPECIAL }, { NULL, 2 } }
00475 #define X86_64_3  NULL, { { NULL, X86_64_SPECIAL }, { NULL, 3 } }
00476 
00477 #define THREE_BYTE_0 NULL, { { NULL, IS_3BYTE_OPCODE }, { NULL, 0 } }
00478 #define THREE_BYTE_1 NULL, { { NULL, IS_3BYTE_OPCODE }, { NULL, 1 } }
00479 
00480 typedef void (*op_rtn) (int bytemode, int sizeflag);
00481 
00482 struct dis386 {
00483   const char *name;
00484   struct
00485     {
00486       op_rtn rtn;
00487       int bytemode;
00488     } op[MAX_OPERANDS];
00489 };
00490 
00491 /* Upper case letters in the instruction names here are macros.
00492    'A' => print 'b' if no register operands or suffix_always is true
00493    'B' => print 'b' if suffix_always is true
00494    'C' => print 's' or 'l' ('w' or 'd' in Intel mode) depending on operand
00495    .      size prefix
00496    'D' => print 'w' if no register operands or 'w', 'l' or 'q', if
00497    .      suffix_always is true
00498    'E' => print 'e' if 32-bit form of jcxz
00499    'F' => print 'w' or 'l' depending on address size prefix (loop insns)
00500    'G' => print 'w' or 'l' depending on operand size prefix (i/o insns)
00501    'H' => print ",pt" or ",pn" branch hint
00502    'I' => honor following macro letter even in Intel mode (implemented only
00503    .      for some of the macro letters)
00504    'J' => print 'l'
00505    'L' => print 'l' if suffix_always is true
00506    'N' => print 'n' if instruction has no wait "prefix"
00507    'O' => print 'd' or 'o' (or 'q' in Intel mode)
00508    'P' => print 'w', 'l' or 'q' if instruction has an operand size prefix,
00509    .      or suffix_always is true.  print 'q' if rex prefix is present.
00510    'Q' => print 'w', 'l' or 'q' if no register operands or suffix_always
00511    .      is true
00512    'R' => print 'w', 'l' or 'q' ('d' for 'l' and 'e' in Intel mode)
00513    'S' => print 'w', 'l' or 'q' if suffix_always is true
00514    'T' => print 'q' in 64bit mode and behave as 'P' otherwise
00515    'U' => print 'q' in 64bit mode and behave as 'Q' otherwise
00516    'V' => print 'q' in 64bit mode and behave as 'S' otherwise
00517    'W' => print 'b', 'w' or 'l' ('d' in Intel mode)
00518    'X' => print 's', 'd' depending on data16 prefix (for XMM)
00519    'Y' => 'q' if instruction has an REX 64bit overwrite prefix
00520    'Z' => print 'q' in 64bit mode and behave as 'L' otherwise
00521 
00522    Many of the above letters print nothing in Intel mode.  See "putop"
00523    for the details.
00524 
00525    Braces '{' and '}', and vertical bars '|', indicate alternative
00526    mnemonic strings for AT&T, Intel, X86_64 AT&T, and X86_64 Intel
00527    modes.  In cases where there are only two alternatives, the X86_64
00528    instruction is reserved, and "(bad)" is printed.
00529 */
00530 
00531 static const struct dis386 dis386[] = {
00532   /* 00 */
00533   { "addB",          { Eb, Gb } },
00534   { "addS",          { Ev, Gv } },
00535   { "addB",          { Gb, Eb } },
00536   { "addS",          { Gv, Ev } },
00537   { "addB",          { AL, Ib } },
00538   { "addS",          { eAX, Iv } },
00539   { "push{T|}",             { es } },
00540   { "pop{T|}",              { es } },
00541   /* 08 */
00542   { "orB",           { Eb, Gb } },
00543   { "orS",           { Ev, Gv } },
00544   { "orB",           { Gb, Eb } },
00545   { "orS",           { Gv, Ev } },
00546   { "orB",           { AL, Ib } },
00547   { "orS",           { eAX, Iv } },
00548   { "push{T|}",             { cs } },
00549   { "(bad)",         { XX } },     /* 0x0f extended opcode escape */
00550   /* 10 */
00551   { "adcB",          { Eb, Gb } },
00552   { "adcS",          { Ev, Gv } },
00553   { "adcB",          { Gb, Eb } },
00554   { "adcS",          { Gv, Ev } },
00555   { "adcB",          { AL, Ib } },
00556   { "adcS",          { eAX, Iv } },
00557   { "push{T|}",             { ss } },
00558   { "pop{T|}",              { ss } },
00559   /* 18 */
00560   { "sbbB",          { Eb, Gb } },
00561   { "sbbS",          { Ev, Gv } },
00562   { "sbbB",          { Gb, Eb } },
00563   { "sbbS",          { Gv, Ev } },
00564   { "sbbB",          { AL, Ib } },
00565   { "sbbS",          { eAX, Iv } },
00566   { "push{T|}",             { ds } },
00567   { "pop{T|}",              { ds } },
00568   /* 20 */
00569   { "andB",          { Eb, Gb } },
00570   { "andS",          { Ev, Gv } },
00571   { "andB",          { Gb, Eb } },
00572   { "andS",          { Gv, Ev } },
00573   { "andB",          { AL, Ib } },
00574   { "andS",          { eAX, Iv } },
00575   { "(bad)",         { XX } },     /* SEG ES prefix */
00576   { "daa{|}",        { XX } },
00577   /* 28 */
00578   { "subB",          { Eb, Gb } },
00579   { "subS",          { Ev, Gv } },
00580   { "subB",          { Gb, Eb } },
00581   { "subS",          { Gv, Ev } },
00582   { "subB",          { AL, Ib } },
00583   { "subS",          { eAX, Iv } },
00584   { "(bad)",         { XX } },     /* SEG CS prefix */
00585   { "das{|}",        { XX } },
00586   /* 30 */
00587   { "xorB",          { Eb, Gb } },
00588   { "xorS",          { Ev, Gv } },
00589   { "xorB",          { Gb, Eb } },
00590   { "xorS",          { Gv, Ev } },
00591   { "xorB",          { AL, Ib } },
00592   { "xorS",          { eAX, Iv } },
00593   { "(bad)",         { XX } },     /* SEG SS prefix */
00594   { "aaa{|}",        { XX } },
00595   /* 38 */
00596   { "cmpB",          { Eb, Gb } },
00597   { "cmpS",          { Ev, Gv } },
00598   { "cmpB",          { Gb, Eb } },
00599   { "cmpS",          { Gv, Ev } },
00600   { "cmpB",          { AL, Ib } },
00601   { "cmpS",          { eAX, Iv } },
00602   { "(bad)",         { XX } },     /* SEG DS prefix */
00603   { "aas{|}",        { XX } },
00604   /* 40 */
00605   { "inc{S|}",              { RMeAX } },
00606   { "inc{S|}",              { RMeCX } },
00607   { "inc{S|}",              { RMeDX } },
00608   { "inc{S|}",              { RMeBX } },
00609   { "inc{S|}",              { RMeSP } },
00610   { "inc{S|}",              { RMeBP } },
00611   { "inc{S|}",              { RMeSI } },
00612   { "inc{S|}",              { RMeDI } },
00613   /* 48 */
00614   { "dec{S|}",              { RMeAX } },
00615   { "dec{S|}",              { RMeCX } },
00616   { "dec{S|}",              { RMeDX } },
00617   { "dec{S|}",              { RMeBX } },
00618   { "dec{S|}",              { RMeSP } },
00619   { "dec{S|}",              { RMeBP } },
00620   { "dec{S|}",              { RMeSI } },
00621   { "dec{S|}",              { RMeDI } },
00622   /* 50 */
00623   { "pushV",         { RMrAX } },
00624   { "pushV",         { RMrCX } },
00625   { "pushV",         { RMrDX } },
00626   { "pushV",         { RMrBX } },
00627   { "pushV",         { RMrSP } },
00628   { "pushV",         { RMrBP } },
00629   { "pushV",         { RMrSI } },
00630   { "pushV",         { RMrDI } },
00631   /* 58 */
00632   { "popV",          { RMrAX } },
00633   { "popV",          { RMrCX } },
00634   { "popV",          { RMrDX } },
00635   { "popV",          { RMrBX } },
00636   { "popV",          { RMrSP } },
00637   { "popV",          { RMrBP } },
00638   { "popV",          { RMrSI } },
00639   { "popV",          { RMrDI } },
00640   /* 60 */
00641   { X86_64_0 },
00642   { X86_64_1 },
00643   { X86_64_2 },
00644   { X86_64_3 },
00645   { "(bad)",         { XX } },     /* seg fs */
00646   { "(bad)",         { XX } },     /* seg gs */
00647   { "(bad)",         { XX } },     /* op size prefix */
00648   { "(bad)",         { XX } },     /* adr size prefix */
00649   /* 68 */
00650   { "pushT",         { Iq } },
00651   { "imulS",         { Gv, Ev, Iv } },
00652   { "pushT",         { sIb } },
00653   { "imulS",         { Gv, Ev, sIb } },
00654   { "ins{b||b|}",    { Ybr, indirDX } },
00655   { "ins{R||G|}",    { Yzr, indirDX } },
00656   { "outs{b||b|}",   { indirDXr, Xb } },
00657   { "outs{R||G|}",   { indirDXr, Xz } },
00658   /* 70 */
00659   { "joH",           { Jb, XX, cond_jump_flag } },
00660   { "jnoH",          { Jb, XX, cond_jump_flag } },
00661   { "jbH",           { Jb, XX, cond_jump_flag } },
00662   { "jaeH",          { Jb, XX, cond_jump_flag } },
00663   { "jeH",           { Jb, XX, cond_jump_flag } },
00664   { "jneH",          { Jb, XX, cond_jump_flag } },
00665   { "jbeH",          { Jb, XX, cond_jump_flag } },
00666   { "jaH",           { Jb, XX, cond_jump_flag } },
00667   /* 78 */
00668   { "jsH",           { Jb, XX, cond_jump_flag } },
00669   { "jnsH",          { Jb, XX, cond_jump_flag } },
00670   { "jpH",           { Jb, XX, cond_jump_flag } },
00671   { "jnpH",          { Jb, XX, cond_jump_flag } },
00672   { "jlH",           { Jb, XX, cond_jump_flag } },
00673   { "jgeH",          { Jb, XX, cond_jump_flag } },
00674   { "jleH",          { Jb, XX, cond_jump_flag } },
00675   { "jgH",           { Jb, XX, cond_jump_flag } },
00676   /* 80 */
00677   { GRP1b },
00678   { GRP1S },
00679   { "(bad)",         { XX } },
00680   { GRP1Ss },
00681   { "testB",         { Eb, Gb } },
00682   { "testS",         { Ev, Gv } },
00683   { "xchgB",         { Eb, Gb } },
00684   { "xchgS",         { Ev, Gv } },
00685   /* 88 */
00686   { "movB",          { Eb, Gb } },
00687   { "movS",          { Ev, Gv } },
00688   { "movB",          { Gb, Eb } },
00689   { "movS",          { Gv, Ev } },
00690   { "movD",          { Sv, Sw } },
00691   { "leaS",          { Gv, M } },
00692   { "movD",          { Sw, Sv } },
00693   { "popU",          { stackEv } },
00694   /* 90 */
00695   { PREGRP38 },
00696   { "xchgS",         { RMeCX, eAX } },
00697   { "xchgS",         { RMeDX, eAX } },
00698   { "xchgS",         { RMeBX, eAX } },
00699   { "xchgS",         { RMeSP, eAX } },
00700   { "xchgS",         { RMeBP, eAX } },
00701   { "xchgS",         { RMeSI, eAX } },
00702   { "xchgS",         { RMeDI, eAX } },
00703   /* 98 */
00704   { "cW{t||t|}R",    { XX } },
00705   { "cR{t||t|}O",    { XX } },
00706   { "Jcall{T|}",     { Ap } },
00707   { "(bad)",         { XX } },     /* fwait */
00708   { "pushfT",        { XX } },
00709   { "popfT",         { XX } },
00710   { "sahf{|}",              { XX } },
00711   { "lahf{|}",              { XX } },
00712   /* a0 */
00713   { "movB",          { AL, Ob } },
00714   { "movS",          { eAX, Ov } },
00715   { "movB",          { Ob, AL } },
00716   { "movS",          { Ov, eAX } },
00717   { "movs{b||b|}",   { Ybr, Xb } },
00718   { "movs{R||R|}",   { Yvr, Xv } },
00719   { "cmps{b||b|}",   { Xb, Yb } },
00720   { "cmps{R||R|}",   { Xv, Yv } },
00721   /* a8 */
00722   { "testB",         { AL, Ib } },
00723   { "testS",         { eAX, Iv } },
00724   { "stosB",         { Ybr, AL } },
00725   { "stosS",         { Yvr, eAX } },
00726   { "lodsB",         { ALr, Xb } },
00727   { "lodsS",         { eAXr, Xv } },
00728   { "scasB",         { AL, Yb } },
00729   { "scasS",         { eAX, Yv } },
00730   /* b0 */
00731   { "movB",          { RMAL, Ib } },
00732   { "movB",          { RMCL, Ib } },
00733   { "movB",          { RMDL, Ib } },
00734   { "movB",          { RMBL, Ib } },
00735   { "movB",          { RMAH, Ib } },
00736   { "movB",          { RMCH, Ib } },
00737   { "movB",          { RMDH, Ib } },
00738   { "movB",          { RMBH, Ib } },
00739   /* b8 */
00740   { "movS",          { RMeAX, Iv64 } },
00741   { "movS",          { RMeCX, Iv64 } },
00742   { "movS",          { RMeDX, Iv64 } },
00743   { "movS",          { RMeBX, Iv64 } },
00744   { "movS",          { RMeSP, Iv64 } },
00745   { "movS",          { RMeBP, Iv64 } },
00746   { "movS",          { RMeSI, Iv64 } },
00747   { "movS",          { RMeDI, Iv64 } },
00748   /* c0 */
00749   { GRP2b },
00750   { GRP2S },
00751   { "retT",          { Iw } },
00752   { "retT",          { XX } },
00753   { "les{S|}",              { Gv, Mp } },
00754   { "ldsS",          { Gv, Mp } },
00755   { GRP11_C6 },
00756   { GRP11_C7 },
00757   /* c8 */
00758   { "enterT",        { Iw, Ib } },
00759   { "leaveT",        { XX } },
00760   { "lretP",         { Iw } },
00761   { "lretP",         { XX } },
00762   { "int3",          { XX } },
00763   { "int",           { Ib } },
00764   { "into{|}",              { XX } },
00765   { "iretP",         { XX } },
00766   /* d0 */
00767   { GRP2b_one },
00768   { GRP2S_one },
00769   { GRP2b_cl },
00770   { GRP2S_cl },
00771   { "aam{|}",        { sIb } },
00772   { "aad{|}",        { sIb } },
00773   { "(bad)",         { XX } },
00774   { "xlat",          { DSBX } },
00775   /* d8 */
00776   { FLOAT },
00777   { FLOAT },
00778   { FLOAT },
00779   { FLOAT },
00780   { FLOAT },
00781   { FLOAT },
00782   { FLOAT },
00783   { FLOAT },
00784   /* e0 */
00785   { "loopneFH",             { Jb, XX, loop_jcxz_flag } },
00786   { "loopeFH",              { Jb, XX, loop_jcxz_flag } },
00787   { "loopFH",        { Jb, XX, loop_jcxz_flag } },
00788   { "jEcxzH",        { Jb, XX, loop_jcxz_flag } },
00789   { "inB",           { AL, Ib } },
00790   { "inG",           { zAX, Ib } },
00791   { "outB",          { Ib, AL } },
00792   { "outG",          { Ib, zAX } },
00793   /* e8 */
00794   { "callT",         { Jv } },
00795   { "jmpT",          { Jv } },
00796   { "Jjmp{T|}",             { Ap } },
00797   { "jmp",           { Jb } },
00798   { "inB",           { AL, indirDX } },
00799   { "inG",           { zAX, indirDX } },
00800   { "outB",          { indirDX, AL } },
00801   { "outG",          { indirDX, zAX } },
00802   /* f0 */
00803   { "(bad)",         { XX } },     /* lock prefix */
00804   { "icebp",         { XX } },
00805   { "(bad)",         { XX } },     /* repne */
00806   { "(bad)",         { XX } },     /* repz */
00807   { "hlt",           { XX } },
00808   { "cmc",           { XX } },
00809   { GRP3b },
00810   { GRP3S },
00811   /* f8 */
00812   { "clc",           { XX } },
00813   { "stc",           { XX } },
00814   { "cli",           { XX } },
00815   { "sti",           { XX } },
00816   { "cld",           { XX } },
00817   { "std",           { XX } },
00818   { GRP4 },
00819   { GRP5 },
00820 };
00821 
00822 static const struct dis386 dis386_twobyte[] = {
00823   /* 00 */
00824   { GRP6 },
00825   { GRP7 },
00826   { "larS",          { Gv, Ew } },
00827   { "lslS",          { Gv, Ew } },
00828   { "(bad)",         { XX } },
00829   { "syscall",              { XX } },
00830   { "clts",          { XX } },
00831   { "sysretP",              { XX } },
00832   /* 08 */
00833   { "invd",          { XX } },
00834   { "wbinvd",        { XX } },
00835   { "(bad)",         { XX } },
00836   { "ud2a",          { XX } },
00837   { "(bad)",         { XX } },
00838   { GRPAMD },
00839   { "femms",         { XX } },
00840   { "",                     { MX, EM, OPSUF } }, /* See OP_3DNowSuffix.  */
00841   /* 10 */
00842   { PREGRP8 },
00843   { PREGRP9 },
00844   { PREGRP30 },
00845   { "movlpX",        { EX, XM, { SIMD_Fixup, 'h' } } },
00846   { "unpcklpX",             { XM, EX } },
00847   { "unpckhpX",             { XM, EX } },
00848   { PREGRP31 },
00849   { "movhpX",        { EX, XM, { SIMD_Fixup, 'l' } } },
00850   /* 18 */
00851   { GRP16 },
00852   { "(bad)",         { XX } },
00853   { "(bad)",         { XX } },
00854   { "(bad)",         { XX } },
00855   { "(bad)",         { XX } },
00856   { "(bad)",         { XX } },
00857   { "(bad)",         { XX } },
00858   { "nopQ",          { Ev } },
00859   /* 20 */
00860   { "movZ",          { Rm, Cm } },
00861   { "movZ",          { Rm, Dm } },
00862   { "movZ",          { Cm, Rm } },
00863   { "movZ",          { Dm, Rm } },
00864   { "movL",          { Rd, Td } },
00865   { "(bad)",         { XX } },
00866   { "movL",          { Td, Rd } },
00867   { "(bad)",         { XX } },
00868   /* 28 */
00869   { "movapX",        { XM, EX } },
00870   { "movapX",        { EX, XM } },
00871   { PREGRP2 },
00872   { PREGRP33 },
00873   { PREGRP4 },
00874   { PREGRP3 },
00875   { "ucomisX",              { XM,EX } },
00876   { "comisX",        { XM,EX } },
00877   /* 30 */
00878   { "wrmsr",         { XX } },
00879   { "rdtsc",         { XX } },
00880   { "rdmsr",         { XX } },
00881   { "rdpmc",         { XX } },
00882   { "sysenter",             { XX } },
00883   { "sysexit",              { XX } },
00884   { "(bad)",         { XX } },
00885   { "(bad)",         { XX } },
00886   /* 38 */
00887   { THREE_BYTE_0 },
00888   { "(bad)",         { XX } },
00889   { THREE_BYTE_1 },
00890   { "(bad)",         { XX } },
00891   { "(bad)",         { XX } },
00892   { "(bad)",         { XX } },
00893   { "(bad)",         { XX } },
00894   { "(bad)",         { XX } },
00895   /* 40 */
00896   { "cmovo",         { Gv, Ev } },
00897   { "cmovno",        { Gv, Ev } },
00898   { "cmovb",         { Gv, Ev } },
00899   { "cmovae",        { Gv, Ev } },
00900   { "cmove",         { Gv, Ev } },
00901   { "cmovne",        { Gv, Ev } },
00902   { "cmovbe",        { Gv, Ev } },
00903   { "cmova",         { Gv, Ev } },
00904   /* 48 */
00905   { "cmovs",         { Gv, Ev } },
00906   { "cmovns",        { Gv, Ev } },
00907   { "cmovp",         { Gv, Ev } },
00908   { "cmovnp",        { Gv, Ev } },
00909   { "cmovl",         { Gv, Ev } },
00910   { "cmovge",        { Gv, Ev } },
00911   { "cmovle",        { Gv, Ev } },
00912   { "cmovg",         { Gv, Ev } },
00913   /* 50 */
00914   { "movmskpX",             { Gdq, XS } },
00915   { PREGRP13 },
00916   { PREGRP12 },
00917   { PREGRP11 },
00918   { "andpX",         { XM, EX } },
00919   { "andnpX",        { XM, EX } },
00920   { "orpX",          { XM, EX } },
00921   { "xorpX",         { XM, EX } },
00922   /* 58 */
00923   { PREGRP0 },
00924   { PREGRP10 },
00925   { PREGRP17 },
00926   { PREGRP16 },
00927   { PREGRP14 },
00928   { PREGRP7 },
00929   { PREGRP5 },
00930   { PREGRP6 },
00931   /* 60 */
00932   { "punpcklbw",     { MX, EM } },
00933   { "punpcklwd",     { MX, EM } },
00934   { "punpckldq",     { MX, EM } },
00935   { "packsswb",             { MX, EM } },
00936   { "pcmpgtb",              { MX, EM } },
00937   { "pcmpgtw",              { MX, EM } },
00938   { "pcmpgtd",              { MX, EM } },
00939   { "packuswb",             { MX, EM } },
00940   /* 68 */
00941   { "punpckhbw",     { MX, EM } },
00942   { "punpckhwd",     { MX, EM } },
00943   { "punpckhdq",     { MX, EM } },
00944   { "packssdw",             { MX, EM } },
00945   { PREGRP26 },
00946   { PREGRP24 },
00947   { "movd",          { MX, Edq } },
00948   { PREGRP19 },
00949   /* 70 */
00950   { PREGRP22 },
00951   { GRP12 },
00952   { GRP13 },
00953   { GRP14 },
00954   { "pcmpeqb",              { MX, EM } },
00955   { "pcmpeqw",              { MX, EM } },
00956   { "pcmpeqd",              { MX, EM } },
00957   { "emms",          { XX } },
00958   /* 78 */
00959   { PREGRP34 },
00960   { PREGRP35 },
00961   { "(bad)",         { XX } },
00962   { "(bad)",         { XX } },
00963   { PREGRP28 },
00964   { PREGRP29 },
00965   { PREGRP23 },
00966   { PREGRP20 },
00967   /* 80 */
00968   { "joH",           { Jv, XX, cond_jump_flag } },
00969   { "jnoH",          { Jv, XX, cond_jump_flag } },
00970   { "jbH",           { Jv, XX, cond_jump_flag } },
00971   { "jaeH",          { Jv, XX, cond_jump_flag } },
00972   { "jeH",           { Jv, XX, cond_jump_flag } },
00973   { "jneH",          { Jv, XX, cond_jump_flag } },
00974   { "jbeH",          { Jv, XX, cond_jump_flag } },
00975   { "jaH",           { Jv, XX, cond_jump_flag } },
00976   /* 88 */
00977   { "jsH",           { Jv, XX, cond_jump_flag } },
00978   { "jnsH",          { Jv, XX, cond_jump_flag } },
00979   { "jpH",           { Jv, XX, cond_jump_flag } },
00980   { "jnpH",          { Jv, XX, cond_jump_flag } },
00981   { "jlH",           { Jv, XX, cond_jump_flag } },
00982   { "jgeH",          { Jv, XX, cond_jump_flag } },
00983   { "jleH",          { Jv, XX, cond_jump_flag } },
00984   { "jgH",           { Jv, XX, cond_jump_flag } },
00985   /* 90 */
00986   { "seto",          { Eb } },
00987   { "setno",         { Eb } },
00988   { "setb",          { Eb } },
00989   { "setae",         { Eb } },
00990   { "sete",          { Eb } },
00991   { "setne",         { Eb } },
00992   { "setbe",         { Eb } },
00993   { "seta",          { Eb } },
00994   /* 98 */
00995   { "sets",          { Eb } },
00996   { "setns",         { Eb } },
00997   { "setp",          { Eb } },
00998   { "setnp",         { Eb } },
00999   { "setl",          { Eb } },
01000   { "setge",         { Eb } },
01001   { "setle",         { Eb } },
01002   { "setg",          { Eb } },
01003   /* a0 */
01004   { "pushT",         { fs } },
01005   { "popT",          { fs } },
01006   { "cpuid",         { XX } },
01007   { "btS",           { Ev, Gv } },
01008   { "shldS",         { Ev, Gv, Ib } },
01009   { "shldS",         { Ev, Gv, CL } },
01010   { GRPPADLCK2 },
01011   { GRPPADLCK1 },
01012   /* a8 */
01013   { "pushT",         { gs } },
01014   { "popT",          { gs } },
01015   { "rsm",           { XX } },
01016   { "btsS",          { Ev, Gv } },
01017   { "shrdS",         { Ev, Gv, Ib } },
01018   { "shrdS",         { Ev, Gv, CL } },
01019   { GRP15 },
01020   { "imulS",         { Gv, Ev } },
01021   /* b0 */
01022   { "cmpxchgB",             { Eb, Gb } },
01023   { "cmpxchgS",             { Ev, Gv } },
01024   { "lssS",          { Gv, Mp } },
01025   { "btrS",          { Ev, Gv } },
01026   { "lfsS",          { Gv, Mp } },
01027   { "lgsS",          { Gv, Mp } },
01028   { "movz{bR|x|bR|x}",      { Gv, Eb } },
01029   { "movz{wR|x|wR|x}",      { Gv, Ew } }, /* yes, there really is movzww ! */
01030   /* b8 */
01031   { PREGRP37 },
01032   { "ud2b",          { XX } },
01033   { GRP8 },
01034   { "btcS",          { Ev, Gv } },
01035   { "bsfS",          { Gv, Ev } },
01036   { PREGRP36 },
01037   { "movs{bR|x|bR|x}",      { Gv, Eb } },
01038   { "movs{wR|x|wR|x}",      { Gv, Ew } }, /* yes, there really is movsww ! */
01039   /* c0 */
01040   { "xaddB",         { Eb, Gb } },
01041   { "xaddS",         { Ev, Gv } },
01042   { PREGRP1 },
01043   { "movntiS",              { Ev, Gv } },
01044   { "pinsrw",        { MX, Edqw, Ib } },
01045   { "pextrw",        { Gdq, MS, Ib } },
01046   { "shufpX",        { XM, EX, Ib } },
01047   { GRP9 },
01048   /* c8 */
01049   { "bswap",         { RMeAX } },
01050   { "bswap",         { RMeCX } },
01051   { "bswap",         { RMeDX } },
01052   { "bswap",         { RMeBX } },
01053   { "bswap",         { RMeSP } },
01054   { "bswap",         { RMeBP } },
01055   { "bswap",         { RMeSI } },
01056   { "bswap",         { RMeDI } },
01057   /* d0 */
01058   { PREGRP27 },
01059   { "psrlw",         { MX, EM } },
01060   { "psrld",         { MX, EM } },
01061   { "psrlq",         { MX, EM } },
01062   { "paddq",         { MX, EM } },
01063   { "pmullw",        { MX, EM } },
01064   { PREGRP21 },
01065   { "pmovmskb",             { Gdq, MS } },
01066   /* d8 */
01067   { "psubusb",              { MX, EM } },
01068   { "psubusw",              { MX, EM } },
01069   { "pminub",        { MX, EM } },
01070   { "pand",          { MX, EM } },
01071   { "paddusb",              { MX, EM } },
01072   { "paddusw",              { MX, EM } },
01073   { "pmaxub",        { MX, EM } },
01074   { "pandn",         { MX, EM } },
01075   /* e0 */
01076   { "pavgb",         { MX, EM } },
01077   { "psraw",         { MX, EM } },
01078   { "psrad",         { MX, EM } },
01079   { "pavgw",         { MX, EM } },
01080   { "pmulhuw",              { MX, EM } },
01081   { "pmulhw",        { MX, EM } },
01082   { PREGRP15 },
01083   { PREGRP25 },
01084   /* e8 */
01085   { "psubsb",        { MX, EM } },
01086   { "psubsw",        { MX, EM } },
01087   { "pminsw",        { MX, EM } },
01088   { "por",           { MX, EM } },
01089   { "paddsb",        { MX, EM } },
01090   { "paddsw",        { MX, EM } },
01091   { "pmaxsw",        { MX, EM } },
01092   { "pxor",          { MX, EM } },
01093   /* f0 */
01094   { PREGRP32 },
01095   { "psllw",         { MX, EM } },
01096   { "pslld",         { MX, EM } },
01097   { "psllq",         { MX, EM } },
01098   { "pmuludq",              { MX, EM } },
01099   { "pmaddwd",              { MX, EM } },
01100   { "psadbw",        { MX, EM } },
01101   { PREGRP18 },
01102   /* f8 */
01103   { "psubb",         { MX, EM } },
01104   { "psubw",         { MX, EM } },
01105   { "psubd",         { MX, EM } },
01106   { "psubq",         { MX, EM } },
01107   { "paddb",         { MX, EM } },
01108   { "paddw",         { MX, EM } },
01109   { "paddd",         { MX, EM } },
01110   { "(bad)",         { XX } },
01111 };
01112 
01113 static const unsigned char onebyte_has_modrm[256] = {
01114   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01115   /*       -------------------------------        */
01116   /* 00 */ 1,1,1,1,0,0,0,0,1,1,1,1,0,0,0,0, /* 00 */
01117   /* 10 */ 1,1,1,1,0,0,0,0,1,1,1,1,0,0,0,0, /* 10 */
01118   /* 20 */ 1,1,1,1,0,0,0,0,1,1,1,1,0,0,0,0, /* 20 */
01119   /* 30 */ 1,1,1,1,0,0,0,0,1,1,1,1,0,0,0,0, /* 30 */
01120   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 40 */
01121   /* 50 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 50 */
01122   /* 60 */ 0,0,1,1,0,0,0,0,0,1,0,1,0,0,0,0, /* 60 */
01123   /* 70 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 70 */
01124   /* 80 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 80 */
01125   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 90 */
01126   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* a0 */
01127   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* b0 */
01128   /* c0 */ 1,1,0,0,1,1,1,1,0,0,0,0,0,0,0,0, /* c0 */
01129   /* d0 */ 1,1,1,1,0,0,0,0,1,1,1,1,1,1,1,1, /* d0 */
01130   /* e0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* e0 */
01131   /* f0 */ 0,0,0,0,0,0,1,1,0,0,0,0,0,0,1,1  /* f0 */
01132   /*       -------------------------------        */
01133   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01134 };
01135 
01136 static const unsigned char twobyte_has_modrm[256] = {
01137   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01138   /*       -------------------------------        */
01139   /* 00 */ 1,1,1,1,0,0,0,0,0,0,0,0,0,1,0,1, /* 0f */
01140   /* 10 */ 1,1,1,1,1,1,1,1,1,0,0,0,0,0,0,1, /* 1f */
01141   /* 20 */ 1,1,1,1,1,0,1,0,1,1,1,1,1,1,1,1, /* 2f */
01142   /* 30 */ 0,0,0,0,0,0,0,0,1,0,1,0,0,0,0,0, /* 3f */
01143   /* 40 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 4f */
01144   /* 50 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 5f */
01145   /* 60 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 6f */
01146   /* 70 */ 1,1,1,1,1,1,1,0,1,1,0,0,1,1,1,1, /* 7f */
01147   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01148   /* 90 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* 9f */
01149   /* a0 */ 0,0,0,1,1,1,1,1,0,0,0,1,1,1,1,1, /* af */
01150   /* b0 */ 1,1,1,1,1,1,1,1,1,0,1,1,1,1,1,1, /* bf */
01151   /* c0 */ 1,1,1,1,1,1,1,1,0,0,0,0,0,0,0,0, /* cf */
01152   /* d0 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* df */
01153   /* e0 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, /* ef */
01154   /* f0 */ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0  /* ff */
01155   /*       -------------------------------        */
01156   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01157 };
01158 
01159 static const unsigned char twobyte_uses_DATA_prefix[256] = {
01160   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01161   /*       -------------------------------        */
01162   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */
01163   /* 10 */ 1,1,1,0,0,0,1,0,0,0,0,0,0,0,0,0, /* 1f */
01164   /* 20 */ 0,0,0,0,0,0,0,0,0,0,1,1,1,1,0,0, /* 2f */
01165   /* 30 */ 0,0,0,0,0,0,0,0,1,0,1,0,0,0,0,0, /* 3f */
01166   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01167   /* 50 */ 0,1,1,1,0,0,0,0,1,1,1,1,1,1,1,1, /* 5f */
01168   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1, /* 6f */
01169   /* 70 */ 1,0,0,0,0,0,0,0,1,1,0,0,1,1,1,1, /* 7f */
01170   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01171   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01172   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01173   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01174   /* c0 */ 0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01175   /* d0 */ 1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* df */
01176   /* e0 */ 0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* ef */
01177   /* f0 */ 1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0  /* ff */
01178   /*       -------------------------------        */
01179   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01180 };
01181 
01182 static const unsigned char twobyte_uses_REPNZ_prefix[256] = {
01183   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01184   /*       -------------------------------        */
01185   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */
01186   /* 10 */ 1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 1f */
01187   /* 20 */ 0,0,0,0,0,0,0,0,0,0,1,1,1,1,0,0, /* 2f */
01188   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01189   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01190   /* 50 */ 0,1,0,0,0,0,0,0,1,1,1,0,1,1,1,1, /* 5f */
01191   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 6f */
01192   /* 70 */ 1,0,0,0,0,0,0,0,1,1,0,0,1,1,0,0, /* 7f */
01193   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01194   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01195   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01196   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01197   /* c0 */ 0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01198   /* d0 */ 1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* df */
01199   /* e0 */ 0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* ef */
01200   /* f0 */ 1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01201   /*       -------------------------------        */
01202   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01203 };
01204 
01205 static const unsigned char twobyte_uses_REPZ_prefix[256] = {
01206   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01207   /*       -------------------------------        */
01208   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */
01209   /* 10 */ 1,1,1,0,0,0,1,0,0,0,0,0,0,0,0,0, /* 1f */
01210   /* 20 */ 0,0,0,0,0,0,0,0,0,0,1,1,1,1,0,0, /* 2f */
01211   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01212   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01213   /* 50 */ 0,1,1,1,0,0,0,0,1,1,1,1,1,1,1,1, /* 5f */
01214   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1, /* 6f */
01215   /* 70 */ 1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1, /* 7f */
01216   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01217   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01218   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01219   /* b0 */ 0,0,0,0,0,0,0,0,1,0,0,0,0,1,0,0, /* bf */
01220   /* c0 */ 0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01221   /* d0 */ 0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* df */
01222   /* e0 */ 0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0, /* ef */
01223   /* f0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01224   /*       -------------------------------        */
01225   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01226 };
01227 
01228 /* This is used to determine if opcode 0f 38 XX uses DATA prefix.  */ 
01229 static const unsigned char threebyte_0x38_uses_DATA_prefix[256] = {
01230   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01231   /*       -------------------------------        */
01232   /* 00 */ 1,1,1,1,1,1,1,1,1,1,1,1,0,0,0,0, /* 0f */
01233   /* 10 */ 0,0,0,0,0,0,0,0,0,0,0,0,1,1,1,0, /* 1f */
01234   /* 20 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 2f */
01235   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01236   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01237   /* 50 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 5f */
01238   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 6f */
01239   /* 70 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 7f */
01240   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01241   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01242   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01243   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01244   /* c0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01245   /* d0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* df */
01246   /* e0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ef */
01247   /* f0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01248   /*       -------------------------------        */
01249   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01250 };
01251 
01252 /* This is used to determine if opcode 0f 38 XX uses REPNZ prefix.  */ 
01253 static const unsigned char threebyte_0x38_uses_REPNZ_prefix[256] = {
01254   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01255   /*       -------------------------------        */
01256   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */
01257   /* 10 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 1f */
01258   /* 20 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 2f */
01259   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01260   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01261   /* 50 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 5f */
01262   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 6f */
01263   /* 70 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 7f */
01264   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01265   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01266   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01267   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01268   /* c0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01269   /* d0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* df */
01270   /* e0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ef */
01271   /* f0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01272   /*       -------------------------------        */
01273   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01274 };
01275 
01276 /* This is used to determine if opcode 0f 38 XX uses REPZ prefix.  */ 
01277 static const unsigned char threebyte_0x38_uses_REPZ_prefix[256] = {
01278   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01279   /*       -------------------------------        */
01280   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */
01281   /* 10 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 1f */
01282   /* 20 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 2f */
01283   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01284   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01285   /* 50 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 5f */
01286   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 6f */
01287   /* 70 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 7f */
01288   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01289   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01290   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01291   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01292   /* c0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01293   /* d0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* df */
01294   /* e0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ef */
01295   /* f0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01296   /*       -------------------------------        */
01297   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01298 };
01299 
01300 /* This is used to determine if opcode 0f 3a XX uses DATA prefix.  */ 
01301 static const unsigned char threebyte_0x3a_uses_DATA_prefix[256] = {
01302   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01303   /*       -------------------------------        */
01304   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1, /* 0f */
01305   /* 10 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 1f */
01306   /* 20 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 2f */
01307   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01308   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01309   /* 50 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 5f */
01310   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 6f */
01311   /* 70 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 7f */
01312   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01313   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01314   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01315   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01316   /* c0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01317   /* d0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* df */
01318   /* e0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ef */
01319   /* f0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01320   /*       -------------------------------        */
01321   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01322 };
01323 
01324 /* This is used to determine if opcode 0f 3a XX uses REPNZ prefix.  */ 
01325 static const unsigned char threebyte_0x3a_uses_REPNZ_prefix[256] = {
01326   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01327   /*       -------------------------------        */
01328   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */
01329   /* 10 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 1f */
01330   /* 20 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 2f */
01331   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01332   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01333   /* 50 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 5f */
01334   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 6f */
01335   /* 70 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 7f */
01336   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01337   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01338   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01339   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01340   /* c0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01341   /* d0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* df */
01342   /* e0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ef */
01343   /* f0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01344   /*       -------------------------------        */
01345   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01346 };
01347 
01348 /* This is used to determine if opcode 0f 3a XX uses REPZ prefix.  */ 
01349 static const unsigned char threebyte_0x3a_uses_REPZ_prefix[256] = {
01350   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01351   /*       -------------------------------        */
01352   /* 00 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 0f */
01353   /* 10 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 1f */
01354   /* 20 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 2f */
01355   /* 30 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 3f */
01356   /* 40 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 4f */
01357   /* 50 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 5f */
01358   /* 60 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 6f */
01359   /* 70 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 7f */
01360   /* 80 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 8f */
01361   /* 90 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 9f */
01362   /* a0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* af */
01363   /* b0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* bf */
01364   /* c0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* cf */
01365   /* d0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* df */
01366   /* e0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ef */
01367   /* f0 */ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* ff */
01368   /*       -------------------------------        */
01369   /*       0 1 2 3 4 5 6 7 8 9 a b c d e f        */
01370 };
01371 
01372 static char obuf[100];
01373 static char *obufp;
01374 static char scratchbuf[100];
01375 static unsigned char *start_codep;
01376 static unsigned char *insn_codep;
01377 static unsigned char *codep;
01378 static disassemble_info *the_info;
01379 static int mod;
01380 static int rm;
01381 static int reg;
01382 static unsigned char need_modrm;
01383 
01384 /* If we are accessing mod/rm/reg without need_modrm set, then the
01385    values are stale.  Hitting this abort likely indicates that you
01386    need to update onebyte_has_modrm or twobyte_has_modrm.  */
01387 #define MODRM_CHECK  if (!need_modrm) abort ()
01388 
01389 static const char **names64;
01390 static const char **names32;
01391 static const char **names16;
01392 static const char **names8;
01393 static const char **names8rex;
01394 static const char **names_seg;
01395 static const char **index16;
01396 
01397 static const char *intel_names64[] = {
01398   "rax", "rcx", "rdx", "rbx", "rsp", "rbp", "rsi", "rdi",
01399   "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"
01400 };
01401 static const char *intel_names32[] = {
01402   "eax", "ecx", "edx", "ebx", "esp", "ebp", "esi", "edi",
01403   "r8d", "r9d", "r10d", "r11d", "r12d", "r13d", "r14d", "r15d"
01404 };
01405 static const char *intel_names16[] = {
01406   "ax", "cx", "dx", "bx", "sp", "bp", "si", "di",
01407   "r8w", "r9w", "r10w", "r11w", "r12w", "r13w", "r14w", "r15w"
01408 };
01409 static const char *intel_names8[] = {
01410   "al", "cl", "dl", "bl", "ah", "ch", "dh", "bh",
01411 };
01412 static const char *intel_names8rex[] = {
01413   "al", "cl", "dl", "bl", "spl", "bpl", "sil", "dil",
01414   "r8b", "r9b", "r10b", "r11b", "r12b", "r13b", "r14b", "r15b"
01415 };
01416 static const char *intel_names_seg[] = {
01417   "es", "cs", "ss", "ds", "fs", "gs", "?", "?",
01418 };
01419 static const char *intel_index16[] = {
01420   "bx+si", "bx+di", "bp+si", "bp+di", "si", "di", "bp", "bx"
01421 };
01422 
01423 static const char *att_names64[] = {
01424   "%rax", "%rcx", "%rdx", "%rbx", "%rsp", "%rbp", "%rsi", "%rdi",
01425   "%r8", "%r9", "%r10", "%r11", "%r12", "%r13", "%r14", "%r15"
01426 };
01427 static const char *att_names32[] = {
01428   "%eax", "%ecx", "%edx", "%ebx", "%esp", "%ebp", "%esi", "%edi",
01429   "%r8d", "%r9d", "%r10d", "%r11d", "%r12d", "%r13d", "%r14d", "%r15d"
01430 };
01431 static const char *att_names16[] = {
01432   "%ax", "%cx", "%dx", "%bx", "%sp", "%bp", "%si", "%di",
01433   "%r8w", "%r9w", "%r10w", "%r11w", "%r12w", "%r13w", "%r14w", "%r15w"
01434 };
01435 static const char *att_names8[] = {
01436   "%al", "%cl", "%dl", "%bl", "%ah", "%ch", "%dh", "%bh",
01437 };
01438 static const char *att_names8rex[] = {
01439   "%al", "%cl", "%dl", "%bl", "%spl", "%bpl", "%sil", "%dil",
01440   "%r8b", "%r9b", "%r10b", "%r11b", "%r12b", "%r13b", "%r14b", "%r15b"
01441 };
01442 static const char *att_names_seg[] = {
01443   "%es", "%cs", "%ss", "%ds", "%fs", "%gs", "%?", "%?",
01444 };
01445 static const char *att_index16[] = {
01446   "%bx,%si", "%bx,%di", "%bp,%si", "%bp,%di", "%si", "%di", "%bp", "%bx"
01447 };
01448 
01449 static const struct dis386 grps[][8] = {
01450   /* GRP1b */
01451   {
01452     { "addA", { Eb, Ib } },
01453     { "orA",  { Eb, Ib } },
01454     { "adcA", { Eb, Ib } },
01455     { "sbbA", { Eb, Ib } },
01456     { "andA", { Eb, Ib } },
01457     { "subA", { Eb, Ib } },
01458     { "xorA", { Eb, Ib } },
01459     { "cmpA", { Eb, Ib } },
01460   },
01461   /* GRP1S */
01462   {
01463     { "addQ", { Ev, Iv } },
01464     { "orQ",  { Ev, Iv } },
01465     { "adcQ", { Ev, Iv } },
01466     { "sbbQ", { Ev, Iv } },
01467     { "andQ", { Ev, Iv } },
01468     { "subQ", { Ev, Iv } },
01469     { "xorQ", { Ev, Iv } },
01470     { "cmpQ", { Ev, Iv } },
01471   },
01472   /* GRP1Ss */
01473   {
01474     { "addQ", { Ev, sIb } },
01475     { "orQ",  { Ev, sIb } },
01476     { "adcQ", { Ev, sIb } },
01477     { "sbbQ", { Ev, sIb } },
01478     { "andQ", { Ev, sIb } },
01479     { "subQ", { Ev, sIb } },
01480     { "xorQ", { Ev, sIb } },
01481     { "cmpQ", { Ev, sIb } },
01482   },
01483   /* GRP2b */
01484   {
01485     { "rolA", { Eb, Ib } },
01486     { "rorA", { Eb, Ib } },
01487     { "rclA", { Eb, Ib } },
01488     { "rcrA", { Eb, Ib } },
01489     { "shlA", { Eb, Ib } },
01490     { "shrA", { Eb, Ib } },
01491     { "(bad)",       { XX } },
01492     { "sarA", { Eb, Ib } },
01493   },
01494   /* GRP2S */
01495   {
01496     { "rolQ", { Ev, Ib } },
01497     { "rorQ", { Ev, Ib } },
01498     { "rclQ", { Ev, Ib } },
01499     { "rcrQ", { Ev, Ib } },
01500     { "shlQ", { Ev, Ib } },
01501     { "shrQ", { Ev, Ib } },
01502     { "(bad)",       { XX } },
01503     { "sarQ", { Ev, Ib } },
01504   },
01505   /* GRP2b_one */
01506   {
01507     { "rolA", { Eb, I1 } },
01508     { "rorA", { Eb, I1 } },
01509     { "rclA", { Eb, I1 } },
01510     { "rcrA", { Eb, I1 } },
01511     { "shlA", { Eb, I1 } },
01512     { "shrA", { Eb, I1 } },
01513     { "(bad)",       { XX } },
01514     { "sarA", { Eb, I1 } },
01515   },
01516   /* GRP2S_one */
01517   {
01518     { "rolQ", { Ev, I1 } },
01519     { "rorQ", { Ev, I1 } },
01520     { "rclQ", { Ev, I1 } },
01521     { "rcrQ", { Ev, I1 } },
01522     { "shlQ", { Ev, I1 } },
01523     { "shrQ", { Ev, I1 } },
01524     { "(bad)",       { XX } },
01525     { "sarQ", { Ev, I1 } },
01526   },
01527   /* GRP2b_cl */
01528   {
01529     { "rolA", { Eb, CL } },
01530     { "rorA", { Eb, CL } },
01531     { "rclA", { Eb, CL } },
01532     { "rcrA", { Eb, CL } },
01533     { "shlA", { Eb, CL } },
01534     { "shrA", { Eb, CL } },
01535     { "(bad)",       { XX } },
01536     { "sarA", { Eb, CL } },
01537   },
01538   /* GRP2S_cl */
01539   {
01540     { "rolQ", { Ev, CL } },
01541     { "rorQ", { Ev, CL } },
01542     { "rclQ", { Ev, CL } },
01543     { "rcrQ", { Ev, CL } },
01544     { "shlQ", { Ev, CL } },
01545     { "shrQ", { Ev, CL } },
01546     { "(bad)",       { XX } },
01547     { "sarQ", { Ev, CL } },
01548   },
01549   /* GRP3b */
01550   {
01551     { "testA",       { Eb, Ib } },
01552     { "(bad)",       { Eb } },
01553     { "notA", { Eb } },
01554     { "negA", { Eb } },
01555     { "mulA", { Eb } },     /* Don't print the implicit %al register,  */
01556     { "imulA",       { Eb } },     /* to distinguish these opcodes from other */
01557     { "divA", { Eb } },     /* mul/imul opcodes.  Do the same for div  */
01558     { "idivA",       { Eb } },     /* and idiv for consistency.                 */
01559   },
01560   /* GRP3S */
01561   {
01562     { "testQ",       { Ev, Iv } },
01563     { "(bad)",       { XX } },
01564     { "notQ", { Ev } },
01565     { "negQ", { Ev } },
01566     { "mulQ", { Ev } },     /* Don't print the implicit register.  */
01567     { "imulQ",       { Ev } },
01568     { "divQ", { Ev } },
01569     { "idivQ",       { Ev } },
01570   },
01571   /* GRP4 */
01572   {
01573     { "incA", { Eb } },
01574     { "decA", { Eb } },
01575     { "(bad)",       { XX } },
01576     { "(bad)",       { XX } },
01577     { "(bad)",       { XX } },
01578     { "(bad)",       { XX } },
01579     { "(bad)",       { XX } },
01580     { "(bad)",       { XX } },
01581   },
01582   /* GRP5 */
01583   {
01584     { "incQ", { Ev } },
01585     { "decQ", { Ev } },
01586     { "callT",       { indirEv } },
01587     { "JcallT",      { indirEp } },
01588     { "jmpT", { indirEv } },
01589     { "JjmpT",       { indirEp } },
01590     { "pushU",       { stackEv } },
01591     { "(bad)",       { XX } },
01592   },
01593   /* GRP6 */
01594   {
01595     { "sldtD",       { Sv } },
01596     { "strD", { Sv } },
01597     { "lldt", { Ew } },
01598     { "ltr",  { Ew } },
01599     { "verr", { Ew } },
01600     { "verw", { Ew } },
01601     { "(bad)",       { XX } },
01602     { "(bad)",       { XX } },
01603   },
01604   /* GRP7 */
01605   {
01606     { "sgdt{Q|IQ||}", { { VMX_Fixup, 0 } } },
01607     { "sidt{Q|IQ||}", { { PNI_Fixup, 0 } } },
01608     { "lgdt{Q|Q||}",  { M } },
01609     { "lidt{Q|Q||}",  { { SVME_Fixup, 0 } } },
01610     { "smswD",       { Sv } },
01611     { "(bad)",       { XX } },
01612     { "lmsw", { Ew } },
01613     { "invlpg",      { { INVLPG_Fixup, w_mode } } },
01614   },
01615   /* GRP8 */
01616   {
01617     { "(bad)",       { XX } },
01618     { "(bad)",       { XX } },
01619     { "(bad)",       { XX } },
01620     { "(bad)",       { XX } },
01621     { "btQ",  { Ev, Ib } },
01622     { "btsQ", { Ev, Ib } },
01623     { "btrQ", { Ev, Ib } },
01624     { "btcQ", { Ev, Ib } },
01625   },
01626   /* GRP9 */
01627   {
01628     { "(bad)",       { XX } },
01629     { "cmpxchg8b", { { CMPXCHG8B_Fixup, q_mode } } },
01630     { "(bad)",       { XX } },
01631     { "(bad)",       { XX } },
01632     { "(bad)",       { XX } },
01633     { "(bad)",       { XX } },
01634     { "",     { VM } },            /* See OP_VMX.  */
01635     { "vmptrst", { Mq } },
01636   },
01637   /* GRP11_C6 */
01638   {
01639     { "movA", { Eb, Ib } },
01640     { "(bad)",       { XX } },
01641     { "(bad)",       { XX } },
01642     { "(bad)",       { XX } },
01643     { "(bad)",       { XX } },
01644     { "(bad)",       { XX } },
01645     { "(bad)",       { XX } },
01646     { "(bad)",       { XX } },
01647   },
01648   /* GRP11_C7 */
01649   {
01650     { "movQ", { Ev, Iv } },
01651     { "(bad)",       { XX } },
01652     { "(bad)",       { XX } },
01653     { "(bad)",       { XX } },
01654     { "(bad)",       { XX } },
01655     { "(bad)",       { XX } },
01656     { "(bad)",       { XX } },
01657     { "(bad)",  { XX } },
01658   },
01659   /* GRP12 */
01660   {
01661     { "(bad)",       { XX } },
01662     { "(bad)",       { XX } },
01663     { "psrlw",       { MS, Ib } },
01664     { "(bad)",       { XX } },
01665     { "psraw",       { MS, Ib } },
01666     { "(bad)",       { XX } },
01667     { "psllw",       { MS, Ib } },
01668     { "(bad)",       { XX } },
01669   },
01670   /* GRP13 */
01671   {
01672     { "(bad)",       { XX } },
01673     { "(bad)",       { XX } },
01674     { "psrld",       { MS, Ib } },
01675     { "(bad)",       { XX } },
01676     { "psrad",       { MS, Ib } },
01677     { "(bad)",       { XX } },
01678     { "pslld",       { MS, Ib } },
01679     { "(bad)",       { XX } },
01680   },
01681   /* GRP14 */
01682   {
01683     { "(bad)",       { XX } },
01684     { "(bad)",       { XX } },
01685     { "psrlq",       { MS, Ib } },
01686     { "psrldq",      { MS, Ib } },
01687     { "(bad)",       { XX } },
01688     { "(bad)",       { XX } },
01689     { "psllq",       { MS, Ib } },
01690     { "pslldq",      { MS, Ib } },
01691   },
01692   /* GRP15 */
01693   {
01694     { "fxsave",             { Ev } },
01695     { "fxrstor",     { Ev } },
01696     { "ldmxcsr",     { Ev } },
01697     { "stmxcsr",     { Ev } },
01698     { "(bad)",              { XX } },
01699     { "lfence",             { { OP_0fae, 0 } } },
01700     { "mfence",             { { OP_0fae, 0 } } },
01701     { "clflush",     { { OP_0fae, 0 } } },
01702   },
01703   /* GRP16 */
01704   {
01705     { "prefetchnta", { Ev } },
01706     { "prefetcht0",  { Ev } },
01707     { "prefetcht1",  { Ev } },
01708     { "prefetcht2",  { Ev } },
01709     { "(bad)",              { XX } },
01710     { "(bad)",              { XX } },
01711     { "(bad)",              { XX } },
01712     { "(bad)",              { XX } },
01713   },
01714   /* GRPAMD */
01715   {
01716     { "prefetch",    { Eb } },
01717     { "prefetchw",   { Eb } },
01718     { "(bad)",              { XX } },
01719     { "(bad)",              { XX } },
01720     { "(bad)",              { XX } },
01721     { "(bad)",              { XX } },
01722     { "(bad)",              { XX } },
01723     { "(bad)",              { XX } },
01724   },
01725   /* GRPPADLCK1 */
01726   {
01727     { "xstore-rng",  { { OP_0f07, 0 } } },
01728     { "xcrypt-ecb",  { { OP_0f07, 0 } } },
01729     { "xcrypt-cbc",  { { OP_0f07, 0 } } },
01730     { "xcrypt-ctr",  { { OP_0f07, 0 } } },
01731     { "xcrypt-cfb",  { { OP_0f07, 0 } } },
01732     { "xcrypt-ofb",  { { OP_0f07, 0 } } },
01733     { "(bad)",              { { OP_0f07, 0 } } },
01734     { "(bad)",              { { OP_0f07, 0 } } },
01735   },
01736   /* GRPPADLCK2 */
01737   {
01738     { "montmul",     { { OP_0f07, 0 } } },
01739     { "xsha1",              { { OP_0f07, 0 } } },
01740     { "xsha256",     { { OP_0f07, 0 } } },
01741     { "(bad)",              { { OP_0f07, 0 } } },
01742     { "(bad)",              { { OP_0f07, 0 } } },
01743     { "(bad)",              { { OP_0f07, 0 } } },
01744     { "(bad)",              { { OP_0f07, 0 } } },
01745     { "(bad)",              { { OP_0f07, 0 } } },
01746   }
01747 };
01748 
01749 static const struct dis386 prefix_user_table[][4] = {
01750   /* PREGRP0 */
01751   {
01752     { "addps", { XM, EX } },
01753     { "addss", { XM, EX } },
01754     { "addpd", { XM, EX } },
01755     { "addsd", { XM, EX } },
01756   },
01757   /* PREGRP1 */
01758   {
01759     { "", { XM, EX, OPSIMD } },    /* See OP_SIMD_SUFFIX.  */
01760     { "", { XM, EX, OPSIMD } },
01761     { "", { XM, EX, OPSIMD } },
01762     { "", { XM, EX, OPSIMD } },
01763   },
01764   /* PREGRP2 */
01765   {
01766     { "cvtpi2ps", { XM, EMC } },
01767     { "cvtsi2ssY", { XM, Ev } },
01768     { "cvtpi2pd", { XM, EMC } },
01769     { "cvtsi2sdY", { XM, Ev } },
01770   },
01771   /* PREGRP3 */
01772   {
01773     { "cvtps2pi", { MXC, EX } },
01774     { "cvtss2siY", { Gv, EX } },
01775     { "cvtpd2pi", { MXC, EX } },
01776     { "cvtsd2siY", { Gv, EX } },
01777   },
01778   /* PREGRP4 */
01779   {
01780     { "cvttps2pi", { MXC, EX } },
01781     { "cvttss2siY", { Gv, EX } },
01782     { "cvttpd2pi", { MXC, EX } },
01783     { "cvttsd2siY", { Gv, EX } },
01784   },
01785   /* PREGRP5 */
01786   {
01787     { "divps",       { XM, EX } },
01788     { "divss",       { XM, EX } },
01789     { "divpd",       { XM, EX } },
01790     { "divsd",       { XM, EX } },
01791   },
01792   /* PREGRP6 */
01793   {
01794     { "maxps",       { XM, EX } },
01795     { "maxss",       { XM, EX } },
01796     { "maxpd",       { XM, EX } },
01797     { "maxsd",       { XM, EX } },
01798   },
01799   /* PREGRP7 */
01800   {
01801     { "minps",       { XM, EX } },
01802     { "minss",       { XM, EX } },
01803     { "minpd",       { XM, EX } },
01804     { "minsd",       { XM, EX } },
01805   },
01806   /* PREGRP8 */
01807   {
01808     { "movups",      { XM, EX } },
01809     { "movss",       { XM, EX } },
01810     { "movupd",      { XM, EX } },
01811     { "movsd",       { XM, EX } },
01812   },
01813   /* PREGRP9 */
01814   {
01815     { "movups",      { EX, XM } },
01816     { "movss",       { EX, XM } },
01817     { "movupd",      { EX, XM } },
01818     { "movsd",       { EX, XM } },
01819   },
01820   /* PREGRP10 */
01821   {
01822     { "mulps",       { XM, EX } },
01823     { "mulss",       { XM, EX } },
01824     { "mulpd",       { XM, EX } },
01825     { "mulsd",       { XM, EX } },
01826   },
01827   /* PREGRP11 */
01828   {
01829     { "rcpps",       { XM, EX } },
01830     { "rcpss",       { XM, EX } },
01831     { "(bad)",       { XM, EX } },
01832     { "(bad)",       { XM, EX } },
01833   },
01834   /* PREGRP12 */
01835   {
01836     { "rsqrtps",{ XM, EX } },
01837     { "rsqrtss",{ XM, EX } },
01838     { "(bad)",       { XM, EX } },
01839     { "(bad)",       { XM, EX } },
01840   },
01841   /* PREGRP13 */
01842   {
01843     { "sqrtps", { XM, EX } },
01844     { "sqrtss", { XM, EX } },
01845     { "sqrtpd", { XM, EX } },
01846     { "sqrtsd",      { XM, EX } },
01847   },
01848   /* PREGRP14 */
01849   {
01850     { "subps",       { XM, EX } },
01851     { "subss",       { XM, EX } },
01852     { "subpd",       { XM, EX } },
01853     { "subsd",       { XM, EX } },
01854   },
01855   /* PREGRP15 */
01856   {
01857     { "(bad)",       { XM, EX } },
01858     { "cvtdq2pd", { XM, EX } },
01859     { "cvttpd2dq", { XM, EX } },
01860     { "cvtpd2dq", { XM, EX } },
01861   },
01862   /* PREGRP16 */
01863   {
01864     { "cvtdq2ps", { XM, EX } },
01865     { "cvttps2dq", { XM, EX } },
01866     { "cvtps2dq", { XM, EX } },
01867     { "(bad)",       { XM, EX } },
01868   },
01869   /* PREGRP17 */
01870   {
01871     { "cvtps2pd", { XM, EX } },
01872     { "cvtss2sd", { XM, EX } },
01873     { "cvtpd2ps", { XM, EX } },
01874     { "cvtsd2ss", { XM, EX } },
01875   },
01876   /* PREGRP18 */
01877   {
01878     { "maskmovq", { MX, MS } },
01879     { "(bad)",       { XM, EX } },
01880     { "maskmovdqu", { XM, XS } },
01881     { "(bad)",       { XM, EX } },
01882   },
01883   /* PREGRP19 */
01884   {
01885     { "movq", { MX, EM } },
01886     { "movdqu",      { XM, EX } },
01887     { "movdqa",      { XM, EX } },
01888     { "(bad)",       { XM, EX } },
01889   },
01890   /* PREGRP20 */
01891   {
01892     { "movq", { EM, MX } },
01893     { "movdqu",      { EX, XM } },
01894     { "movdqa",      { EX, XM } },
01895     { "(bad)",       { EX, XM } },
01896   },
01897   /* PREGRP21 */
01898   {
01899     { "(bad)",       { EX, XM } },
01900     { "movq2dq",{ XM, MS } },
01901     { "movq", { EX, XM } },
01902     { "movdq2q",{ MX, XS } },
01903   },
01904   /* PREGRP22 */
01905   {
01906     { "pshufw",      { MX, EM, Ib } },
01907     { "pshufhw",{ XM, EX, Ib } },
01908     { "pshufd",      { XM, EX, Ib } },
01909     { "pshuflw",{ XM, EX, Ib } },
01910   },
01911   /* PREGRP23 */
01912   {
01913     { "movd", { Edq, MX } },
01914     { "movq", { XM, EX } },
01915     { "movd", { Edq, XM } },
01916     { "(bad)",       { Ed, XM } },
01917   },
01918   /* PREGRP24 */
01919   {
01920     { "(bad)",       { MX, EX } },
01921     { "(bad)",       { XM, EX } },
01922     { "punpckhqdq", { XM, EX } },
01923     { "(bad)",       { XM, EX } },
01924   },
01925   /* PREGRP25 */
01926   {
01927     { "movntq",      { EM, MX } },
01928     { "(bad)",       { EM, XM } },
01929     { "movntdq",{ EM, XM } },
01930     { "(bad)",       { EM, XM } },
01931   },
01932   /* PREGRP26 */
01933   {
01934     { "(bad)",       { MX, EX } },
01935     { "(bad)",       { XM, EX } },
01936     { "punpcklqdq", { XM, EX } },
01937     { "(bad)",       { XM, EX } },
01938   },
01939   /* PREGRP27 */
01940   {
01941     { "(bad)",       { MX, EX } },
01942     { "(bad)",       { XM, EX } },
01943     { "addsubpd", { XM, EX } },
01944     { "addsubps", { XM, EX } },
01945   },
01946   /* PREGRP28 */
01947   {
01948     { "(bad)",       { MX, EX } },
01949     { "(bad)",       { XM, EX } },
01950     { "haddpd",      { XM, EX } },
01951     { "haddps",      { XM, EX } },
01952   },
01953   /* PREGRP29 */
01954   {
01955     { "(bad)",       { MX, EX } },
01956     { "(bad)",       { XM, EX } },
01957     { "hsubpd",      { XM, EX } },
01958     { "hsubps",      { XM, EX } },
01959   },
01960   /* PREGRP30 */
01961   {
01962     { "movlpX",      { XM, EX, { SIMD_Fixup, 'h' } } }, /* really only 2 operands */
01963     { "movsldup", { XM, EX } },
01964     { "movlpd",      { XM, EX } },
01965     { "movddup", { XM, EX } },
01966   },
01967   /* PREGRP31 */
01968   {
01969     { "movhpX",      { XM, EX, { SIMD_Fixup, 'l' } } },
01970     { "movshdup", { XM, EX } },
01971     { "movhpd",      { XM, EX } },
01972     { "(bad)",       { XM, EX } },
01973   },
01974   /* PREGRP32 */
01975   {
01976     { "(bad)",       { XM, EX } },
01977     { "(bad)",       { XM, EX } },
01978     { "(bad)",       { XM, EX } },
01979     { "lddqu",       { XM, M } },
01980   },
01981   /* PREGRP33 */
01982   {
01983     {"movntps", { Ev, XM } },
01984     {"movntss", { Ev, XM } },
01985     {"movntpd", { Ev, XM } },
01986     {"movntsd", { Ev, XM } },
01987   },
01988 
01989   /* PREGRP34 */
01990   {
01991     {"vmread",       { Em, Gm } },
01992     {"(bad)", { XX } },
01993     {"extrq", { XS, Ib, Ib } },
01994     {"insertq",      { XM, XS, Ib, Ib } },
01995   },
01996   
01997  /* PREGRP35 */  
01998   {
01999     {"vmwrite",      { Gm, Em } },
02000     {"(bad)", { XX } },
02001     {"extrq", { XM, XS } },
02002     {"insertq",      { XM, XS } },
02003   }, 
02004 
02005   /* PREGRP36 */
02006   {
02007     { "bsrS", { Gv, Ev } },
02008     { "lzcntS",      { Gv, Ev } },
02009     { "bsrS", { Gv, Ev } },
02010     { "(bad)",       { XX } },
02011   },
02012 
02013   /* PREGRP37 */
02014   {
02015     { "(bad)", { XX } },
02016     { "popcntS", { Gv, Ev } },
02017     { "(bad)", { XX } },
02018     { "(bad)", { XX } },    
02019   },
02020 
02021   /* PREGRP38 */
02022   {
02023     { "xchgS", { { NOP_Fixup1, eAX_reg }, { NOP_Fixup2, eAX_reg } } },
02024     { "pause", { XX } },
02025     { "xchgS", { { NOP_Fixup1, eAX_reg }, { NOP_Fixup2, eAX_reg } } },
02026     { "(bad)", { XX } },    
02027   },
02028 };
02029 
02030 static const struct dis386 x86_64_table[][2] = {
02031   {
02032     { "pusha{P|}", { XX } },
02033     { "(bad)", { XX } },
02034   },
02035   {
02036     { "popa{P|}", { XX } },
02037     { "(bad)", { XX } },
02038   },
02039   {
02040     { "bound{S|}", { Gv, Ma } },
02041     { "(bad)", { XX } },
02042   },
02043   {
02044     { "arpl", { Ew, Gw } },
02045     { "movs{||lq|xd}", { Gv, Ed } },
02046   },
02047 };
02048 
02049 static const struct dis386 three_byte_table[][256] = {
02050   /* THREE_BYTE_0 */
02051   {
02052     /* 00 */
02053     { "pshufb", { MX, EM } },
02054     { "phaddw", { MX, EM } },
02055     { "phaddd",      { MX, EM } },
02056     { "phaddsw", { MX, EM } },
02057     { "pmaddubsw", { MX, EM } },
02058     { "phsubw", { MX, EM } },
02059     { "phsubd", { MX, EM } },
02060     { "phsubsw", { MX, EM } },
02061     /* 08 */
02062     { "psignb", { MX, EM } },
02063     { "psignw", { MX, EM } },
02064     { "psignd", { MX, EM } },
02065     { "pmulhrsw", { MX, EM } },
02066     { "(bad)", { XX } },
02067     { "(bad)", { XX } },
02068     { "(bad)", { XX } },
02069     { "(bad)", { XX } },
02070     /* 10 */
02071     { "(bad)", { XX } },
02072     { "(bad)", { XX } },
02073     { "(bad)", { XX } },
02074     { "(bad)", { XX } },
02075     { "(bad)", { XX } },
02076     { "(bad)", { XX } },
02077     { "(bad)", { XX } },
02078     { "(bad)", { XX } },
02079     /* 18 */
02080     { "(bad)", { XX } },
02081     { "(bad)", { XX } },
02082     { "(bad)", { XX } },
02083     { "(bad)", { XX } },
02084     { "pabsb", { MX, EM } },
02085     { "pabsw", { MX, EM } },
02086     { "pabsd", { MX, EM } },
02087     { "(bad)", { XX } },
02088     /* 20 */
02089     { "(bad)", { XX } },
02090     { "(bad)", { XX } },
02091     { "(bad)", { XX } },
02092     { "(bad)", { XX } },
02093     { "(bad)", { XX } },
02094     { "(bad)", { XX } },
02095     { "(bad)", { XX } },
02096     { "(bad)", { XX } },
02097     /* 28 */
02098     { "(bad)", { XX } },
02099     { "(bad)", { XX } },
02100     { "(bad)", { XX } },
02101     { "(bad)", { XX } },
02102     { "(bad)", { XX } },
02103     { "(bad)", { XX } },
02104     { "(bad)", { XX } },
02105     { "(bad)", { XX } },
02106     /* 30 */
02107     { "(bad)", { XX } },
02108     { "(bad)", { XX } },
02109     { "(bad)", { XX } },
02110     { "(bad)", { XX } },
02111     { "(bad)", { XX } },
02112     { "(bad)", { XX } },
02113     { "(bad)", { XX } },
02114     { "(bad)", { XX } },
02115     /* 38 */
02116     { "(bad)", { XX } },
02117     { "(bad)", { XX } },
02118     { "(bad)", { XX } },
02119     { "(bad)", { XX } },
02120     { "(bad)", { XX } },
02121     { "(bad)", { XX } },
02122     { "(bad)", { XX } },
02123     { "(bad)", { XX } },
02124     /* 40 */
02125     { "(bad)", { XX } },
02126     { "(bad)", { XX } },
02127     { "(bad)", { XX } },
02128     { "(bad)", { XX } },
02129     { "(bad)", { XX } },
02130     { "(bad)", { XX } },
02131     { "(bad)", { XX } },
02132     { "(bad)", { XX } },
02133     /* 48 */
02134     { "(bad)", { XX } },
02135     { "(bad)", { XX } },
02136     { "(bad)", { XX } },
02137     { "(bad)", { XX } },
02138     { "(bad)", { XX } },
02139     { "(bad)", { XX } },
02140     { "(bad)", { XX } },
02141     { "(bad)", { XX } },
02142     /* 50 */
02143     { "(bad)", { XX } },
02144     { "(bad)", { XX } },
02145     { "(bad)", { XX } },
02146     { "(bad)", { XX } },
02147     { "(bad)", { XX } },
02148     { "(bad)", { XX } },
02149     { "(bad)", { XX } },
02150     { "(bad)", { XX } },
02151     /* 58 */
02152     { "(bad)", { XX } },
02153     { "(bad)", { XX } },
02154     { "(bad)", { XX } },
02155     { "(bad)", { XX } },
02156     { "(bad)", { XX } },
02157     { "(bad)", { XX } },
02158     { "(bad)", { XX } },
02159     { "(bad)", { XX } },
02160     /* 60 */
02161     { "(bad)", { XX } },
02162     { "(bad)", { XX } },
02163     { "(bad)", { XX } },
02164     { "(bad)", { XX } },
02165     { "(bad)", { XX } },
02166     { "(bad)", { XX } },
02167     { "(bad)", { XX } },
02168     { "(bad)", { XX } },
02169     /* 68 */
02170     { "(bad)", { XX } },
02171     { "(bad)", { XX } },
02172     { "(bad)", { XX } },
02173     { "(bad)", { XX } },
02174     { "(bad)", { XX } },
02175     { "(bad)", { XX } },
02176     { "(bad)", { XX } },
02177     { "(bad)", { XX } },
02178     /* 70 */
02179     { "(bad)", { XX } },
02180     { "(bad)", { XX } },
02181     { "(bad)", { XX } },
02182     { "(bad)", { XX } },
02183     { "(bad)", { XX } },
02184     { "(bad)", { XX } },
02185     { "(bad)", { XX } },
02186     { "(bad)", { XX } },
02187     /* 78 */
02188     { "(bad)", { XX } },
02189     { "(bad)", { XX } },
02190     { "(bad)", { XX } },
02191     { "(bad)", { XX } },
02192     { "(bad)", { XX } },
02193     { "(bad)", { XX } },
02194     { "(bad)", { XX } },
02195     { "(bad)", { XX } },
02196     /* 80 */
02197     { "(bad)", { XX } },
02198     { "(bad)", { XX } },
02199     { "(bad)", { XX } },
02200     { "(bad)", { XX } },
02201     { "(bad)", { XX } },
02202     { "(bad)", { XX } },
02203     { "(bad)", { XX } },
02204     { "(bad)", { XX } },
02205     /* 88 */
02206     { "(bad)", { XX } },
02207     { "(bad)", { XX } },
02208     { "(bad)", { XX } },
02209     { "(bad)", { XX } },
02210     { "(bad)", { XX } },
02211     { "(bad)", { XX } },
02212     { "(bad)", { XX } },
02213     { "(bad)", { XX } },
02214     /* 90 */
02215     { "(bad)", { XX } },
02216     { "(bad)", { XX } },
02217     { "(bad)", { XX } },
02218     { "(bad)", { XX } },
02219     { "(bad)", { XX } },
02220     { "(bad)", { XX } },
02221     { "(bad)", { XX } },
02222     { "(bad)", { XX } },
02223     /* 98 */
02224     { "(bad)", { XX } },
02225     { "(bad)", { XX } },
02226     { "(bad)", { XX } },
02227     { "(bad)", { XX } },
02228     { "(bad)", { XX } },
02229     { "(bad)", { XX } },
02230     { "(bad)", { XX } },
02231     { "(bad)", { XX } },
02232     /* a0 */
02233     { "(bad)", { XX } },
02234     { "(bad)", { XX } },
02235     { "(bad)", { XX } },
02236     { "(bad)", { XX } },
02237     { "(bad)", { XX } },
02238     { "(bad)", { XX } },
02239     { "(bad)", { XX } },
02240     { "(bad)", { XX } },
02241     /* a8 */
02242     { "(bad)", { XX } },
02243     { "(bad)", { XX } },
02244     { "(bad)", { XX } },
02245     { "(bad)", { XX } },
02246     { "(bad)", { XX } },
02247     { "(bad)", { XX } },
02248     { "(bad)", { XX } },
02249     { "(bad)", { XX } },
02250     /* b0 */
02251     { "(bad)", { XX } },
02252     { "(bad)", { XX } },
02253     { "(bad)", { XX } },
02254     { "(bad)", { XX } },
02255     { "(bad)", { XX } },
02256     { "(bad)", { XX } },
02257     { "(bad)", { XX } },
02258     { "(bad)", { XX } },
02259     /* b8 */
02260     { "(bad)", { XX } },
02261     { "(bad)", { XX } },
02262     { "(bad)", { XX } },
02263     { "(bad)", { XX } },
02264     { "(bad)", { XX } },
02265     { "(bad)", { XX } },
02266     { "(bad)", { XX } },
02267     { "(bad)", { XX } },
02268     /* c0 */
02269     { "(bad)", { XX } },
02270     { "(bad)", { XX } },
02271     { "(bad)", { XX } },
02272     { "(bad)", { XX } },
02273     { "(bad)", { XX } },
02274     { "(bad)", { XX } },
02275     { "(bad)", { XX } },
02276     { "(bad)", { XX } },
02277     /* c8 */
02278     { "(bad)", { XX } },
02279     { "(bad)", { XX } },
02280     { "(bad)", { XX } },
02281     { "(bad)", { XX } },
02282     { "(bad)", { XX } },
02283     { "(bad)", { XX } },
02284     { "(bad)", { XX } },
02285     { "(bad)", { XX } },
02286     /* d0 */
02287     { "(bad)", { XX } },
02288     { "(bad)", { XX } },
02289     { "(bad)", { XX } },
02290     { "(bad)", { XX } },
02291     { "(bad)", { XX } },
02292     { "(bad)", { XX } },
02293     { "(bad)", { XX } },
02294     { "(bad)", { XX } },
02295     /* d8 */
02296     { "(bad)", { XX } },
02297     { "(bad)", { XX } },
02298     { "(bad)", { XX } },
02299     { "(bad)", { XX } },
02300     { "(bad)", { XX } },
02301     { "(bad)", { XX } },
02302     { "(bad)", { XX } },
02303     { "(bad)", { XX } },
02304     /* e0 */
02305     { "(bad)", { XX } },
02306     { "(bad)", { XX } },
02307     { "(bad)", { XX } },
02308     { "(bad)", { XX } },
02309     { "(bad)", { XX } },
02310     { "(bad)", { XX } },
02311     { "(bad)", { XX } },
02312     { "(bad)", { XX } },
02313     /* e8 */
02314     { "(bad)", { XX } },
02315     { "(bad)", { XX } },
02316     { "(bad)", { XX } },
02317     { "(bad)", { XX } },
02318     { "(bad)", { XX } },
02319     { "(bad)", { XX } },
02320     { "(bad)", { XX } },
02321     { "(bad)", { XX } },
02322     /* f0 */
02323     { "(bad)", { XX } },
02324     { "(bad)", { XX } },
02325     { "(bad)", { XX } },
02326     { "(bad)", { XX } },
02327     { "(bad)", { XX } },
02328     { "(bad)", { XX } },
02329     { "(bad)", { XX } },
02330     { "(bad)", { XX } },
02331     /* f8 */
02332     { "(bad)", { XX } },
02333     { "(bad)", { XX } },
02334     { "(bad)", { XX } },
02335     { "(bad)", { XX } },
02336     { "(bad)", { XX } },
02337     { "(bad)", { XX } },
02338     { "(bad)", { XX } },
02339     { "(bad)", { XX } },
02340   },
02341   /* THREE_BYTE_1 */
02342   {
02343     /* 00 */
02344     { "(bad)", { XX } },
02345     { "(bad)", { XX } },
02346     { "(bad)", { XX } },
02347     { "(bad)", { XX } },
02348     { "(bad)", { XX } },
02349     { "(bad)", { XX } },
02350     { "(bad)", { XX } },
02351     { "(bad)", { XX } },
02352     /* 08 */
02353     { "(bad)", { XX } },
02354     { "(bad)", { XX } },
02355     { "(bad)", { XX } },
02356     { "(bad)", { XX } },
02357     { "(bad)", { XX } },
02358     { "(bad)", { XX } },
02359     { "(bad)", { XX } },
02360     { "palignr", { MX, EM, Ib } },
02361     /* 10 */
02362     { "(bad)", { XX } },
02363     { "(bad)", { XX } },
02364     { "(bad)", { XX } },
02365     { "(bad)", { XX } },
02366     { "(bad)", { XX } },
02367     { "(bad)", { XX } },
02368     { "(bad)", { XX } },
02369     { "(bad)", { XX } },
02370     /* 18 */
02371     { "(bad)", { XX } },
02372     { "(bad)", { XX } },
02373     { "(bad)", { XX } },
02374     { "(bad)", { XX } },
02375     { "(bad)", { XX } },
02376     { "(bad)", { XX } },
02377     { "(bad)", { XX } },
02378     { "(bad)", { XX } },
02379     /* 20 */
02380     { "(bad)", { XX } },
02381     { "(bad)", { XX } },
02382     { "(bad)", { XX } },
02383     { "(bad)", { XX } },
02384     { "(bad)", { XX } },
02385     { "(bad)", { XX } },
02386     { "(bad)", { XX } },
02387     { "(bad)", { XX } },
02388     /* 28 */
02389     { "(bad)", { XX } },
02390     { "(bad)", { XX } },
02391     { "(bad)", { XX } },
02392     { "(bad)", { XX } },
02393     { "(bad)", { XX } },
02394     { "(bad)", { XX } },
02395     { "(bad)", { XX } },
02396     { "(bad)", { XX } },
02397     /* 30 */
02398     { "(bad)", { XX } },
02399     { "(bad)", { XX } },
02400     { "(bad)", { XX } },
02401     { "(bad)", { XX } },
02402     { "(bad)", { XX } },
02403     { "(bad)", { XX } },
02404     { "(bad)", { XX } },
02405     { "(bad)", { XX } },
02406     /* 38 */
02407     { "(bad)", { XX } },
02408     { "(bad)", { XX } },
02409     { "(bad)", { XX } },
02410     { "(bad)", { XX } },
02411     { "(bad)", { XX } },
02412     { "(bad)", { XX } },
02413     { "(bad)", { XX } },
02414     { "(bad)", { XX } },
02415     /* 40 */
02416     { "(bad)", { XX } },
02417     { "(bad)", { XX } },
02418     { "(bad)", { XX } },
02419     { "(bad)", { XX } },
02420     { "(bad)", { XX } },
02421     { "(bad)", { XX } },
02422     { "(bad)", { XX } },
02423     { "(bad)", { XX } },
02424     /* 48 */
02425     { "(bad)", { XX } },
02426     { "(bad)", { XX } },
02427     { "(bad)", { XX } },
02428     { "(bad)", { XX } },
02429     { "(bad)", { XX } },
02430     { "(bad)", { XX } },
02431     { "(bad)", { XX } },
02432     { "(bad)", { XX } },
02433     /* 50 */
02434     { "(bad)", { XX } },
02435     { "(bad)", { XX } },
02436     { "(bad)", { XX } },
02437     { "(bad)", { XX } },
02438     { "(bad)", { XX } },
02439     { "(bad)", { XX } },
02440     { "(bad)", { XX } },
02441     { "(bad)", { XX } },
02442     /* 58 */
02443     { "(bad)", { XX } },
02444     { "(bad)", { XX } },
02445     { "(bad)", { XX } },
02446     { "(bad)", { XX } },
02447     { "(bad)", { XX } },
02448     { "(bad)", { XX } },
02449     { "(bad)", { XX } },
02450     { "(bad)", { XX } },
02451     /* 60 */
02452     { "(bad)", { XX } },
02453     { "(bad)", { XX } },
02454     { "(bad)", { XX } },
02455     { "(bad)", { XX } },
02456     { "(bad)", { XX } },
02457     { "(bad)", { XX } },
02458     { "(bad)", { XX } },
02459     { "(bad)", { XX } },
02460     /* 68 */
02461     { "(bad)", { XX } },
02462     { "(bad)", { XX } },
02463     { "(bad)", { XX } },
02464     { "(bad)", { XX } },
02465     { "(bad)", { XX } },
02466     { "(bad)", { XX } },
02467     { "(bad)", { XX } },
02468     { "(bad)", { XX } },
02469     /* 70 */
02470     { "(bad)", { XX } },
02471     { "(bad)", { XX } },
02472     { "(bad)", { XX } },
02473     { "(bad)", { XX } },
02474     { "(bad)", { XX } },
02475     { "(bad)", { XX } },
02476     { "(bad)", { XX } },
02477     { "(bad)", { XX } },
02478     /* 78 */
02479     { "(bad)", { XX } },
02480     { "(bad)", { XX } },
02481     { "(bad)", { XX } },
02482     { "(bad)", { XX } },
02483     { "(bad)", { XX } },
02484     { "(bad)", { XX } },
02485     { "(bad)", { XX } },
02486     { "(bad)", { XX } },
02487     /* 80 */
02488     { "(bad)", { XX } },
02489     { "(bad)", { XX } },
02490     { "(bad)", { XX } },
02491     { "(bad)", { XX } },
02492     { "(bad)", { XX } },
02493     { "(bad)", { XX } },
02494     { "(bad)", { XX } },
02495     { "(bad)", { XX } },
02496     /* 88 */
02497     { "(bad)", { XX } },
02498     { "(bad)", { XX } },
02499     { "(bad)", { XX } },
02500     { "(bad)", { XX } },
02501     { "(bad)", { XX } },
02502     { "(bad)", { XX } },
02503     { "(bad)", { XX } },
02504     { "(bad)", { XX } },
02505     /* 90 */
02506     { "(bad)", { XX } },
02507     { "(bad)", { XX } },
02508     { "(bad)", { XX } },
02509     { "(bad)", { XX } },
02510     { "(bad)", { XX } },
02511     { "(bad)", { XX } },
02512     { "(bad)", { XX } },
02513     { "(bad)", { XX } },
02514     /* 98 */
02515     { "(bad)", { XX } },
02516     { "(bad)", { XX } },
02517     { "(bad)", { XX } },
02518     { "(bad)", { XX } },
02519     { "(bad)", { XX } },
02520     { "(bad)", { XX } },
02521     { "(bad)", { XX } },
02522     { "(bad)", { XX } },
02523     /* a0 */
02524     { "(bad)", { XX } },
02525     { "(bad)", { XX } },
02526     { "(bad)", { XX } },
02527     { "(bad)", { XX } },
02528     { "(bad)", { XX } },
02529     { "(bad)", { XX } },
02530     { "(bad)", { XX } },
02531     { "(bad)", { XX } },
02532     /* a8 */
02533     { "(bad)", { XX } },
02534     { "(bad)", { XX } },
02535     { "(bad)", { XX } },
02536     { "(bad)", { XX } },
02537     { "(bad)", { XX } },
02538     { "(bad)", { XX } },
02539     { "(bad)", { XX } },
02540     { "(bad)", { XX } },
02541     /* b0 */
02542     { "(bad)", { XX } },
02543     { "(bad)", { XX } },
02544     { "(bad)", { XX } },
02545     { "(bad)", { XX } },
02546     { "(bad)", { XX } },
02547     { "(bad)", { XX } },
02548     { "(bad)", { XX } },
02549     { "(bad)", { XX } },
02550     /* b8 */
02551     { "(bad)", { XX } },
02552     { "(bad)", { XX } },
02553     { "(bad)", { XX } },
02554     { "(bad)", { XX } },
02555     { "(bad)", { XX } },
02556     { "(bad)", { XX } },
02557     { "(bad)", { XX } },
02558     { "(bad)", { XX } },
02559     /* c0 */
02560     { "(bad)", { XX } },
02561     { "(bad)", { XX } },
02562     { "(bad)", { XX } },
02563     { "(bad)", { XX } },
02564     { "(bad)", { XX } },
02565     { "(bad)", { XX } },
02566     { "(bad)", { XX } },
02567     { "(bad)", { XX } },
02568     /* c8 */
02569     { "(bad)", { XX } },
02570     { "(bad)", { XX } },
02571     { "(bad)", { XX } },
02572     { "(bad)", { XX } },
02573     { "(bad)", { XX } },
02574     { "(bad)", { XX } },
02575     { "(bad)", { XX } },
02576     { "(bad)", { XX } },
02577     /* d0 */
02578     { "(bad)", { XX } },
02579     { "(bad)", { XX } },
02580     { "(bad)", { XX } },
02581     { "(bad)", { XX } },
02582     { "(bad)", { XX } },
02583     { "(bad)", { XX } },
02584     { "(bad)", { XX } },
02585     { "(bad)", { XX } },
02586     /* d8 */
02587     { "(bad)", { XX } },
02588     { "(bad)", { XX } },
02589     { "(bad)", { XX } },
02590     { "(bad)", { XX } },
02591     { "(bad)", { XX } },
02592     { "(bad)", { XX } },
02593     { "(bad)", { XX } },
02594     { "(bad)", { XX } },
02595     /* e0 */
02596     { "(bad)", { XX } },
02597     { "(bad)", { XX } },
02598     { "(bad)", { XX } },
02599     { "(bad)", { XX } },
02600     { "(bad)", { XX } },
02601     { "(bad)", { XX } },
02602     { "(bad)", { XX } },
02603     { "(bad)", { XX } },
02604     /* e8 */
02605     { "(bad)", { XX } },
02606     { "(bad)", { XX } },
02607     { "(bad)", { XX } },
02608     { "(bad)", { XX } },
02609     { "(bad)", { XX } },
02610     { "(bad)", { XX } },
02611     { "(bad)", { XX } },
02612     { "(bad)", { XX } },
02613     /* f0 */
02614     { "(bad)", { XX } },
02615     { "(bad)", { XX } },
02616     { "(bad)", { XX } },
02617     { "(bad)", { XX } },
02618     { "(bad)", { XX } },
02619     { "(bad)", { XX } },
02620     { "(bad)", { XX } },
02621     { "(bad)", { XX } },
02622     /* f8 */
02623     { "(bad)", { XX } },
02624     { "(bad)", { XX } },
02625     { "(bad)", { XX } },
02626     { "(bad)", { XX } },
02627     { "(bad)", { XX } },
02628     { "(bad)", { XX } },
02629     { "(bad)", { XX } },
02630     { "(bad)", { XX } },
02631   }
02632 };
02633 
02634 #define INTERNAL_DISASSEMBLER_ERROR _("<internal disassembler error>")
02635 
02636 static void
02637 ckprefix (void)
02638 {
02639   int newrex;
02640   rex = 0;
02641   prefixes = 0;
02642   used_prefixes = 0;
02643   rex_used = 0;
02644   while (1)
02645     {
02646       FETCH_DATA (the_info, codep + 1);
02647       newrex = 0;
02648       switch (*codep)
02649        {
02650        /* REX prefixes family.  */
02651        case 0x40:
02652        case 0x41:
02653        case 0x42:
02654        case 0x43:
02655        case 0x44:
02656        case 0x45:
02657        case 0x46:
02658        case 0x47:
02659        case 0x48:
02660        case 0x49:
02661        case 0x4a:
02662        case 0x4b:
02663        case 0x4c:
02664        case 0x4d:
02665        case 0x4e:
02666        case 0x4f:
02667            if (address_mode == mode_64bit)
02668              newrex = *codep;
02669            else
02670              return;
02671          break;
02672        case 0xf3:
02673          prefixes |= PREFIX_REPZ;
02674          break;
02675        case 0xf2:
02676          prefixes |= PREFIX_REPNZ;
02677          break;
02678        case 0xf0:
02679          prefixes |= PREFIX_LOCK;
02680          break;
02681        case 0x2e:
02682          prefixes |= PREFIX_CS;
02683          break;
02684        case 0x36:
02685          prefixes |= PREFIX_SS;
02686          break;
02687        case 0x3e:
02688          prefixes |= PREFIX_DS;
02689          break;
02690        case 0x26:
02691          prefixes |= PREFIX_ES;
02692          break;
02693        case 0x64:
02694          prefixes |= PREFIX_FS;
02695          break;
02696        case 0x65:
02697          prefixes |= PREFIX_GS;
02698          break;
02699        case 0x66:
02700          prefixes |= PREFIX_DATA;
02701          break;
02702        case 0x67:
02703          prefixes |= PREFIX_ADDR;
02704          break;
02705        case FWAIT_OPCODE:
02706          /* fwait is really an instruction.  If there are prefixes
02707             before the fwait, they belong to the fwait, *not* to the
02708             following instruction.  */
02709          if (prefixes || rex)
02710            {
02711              prefixes |= PREFIX_FWAIT;
02712              codep++;
02713              return;
02714            }
02715          prefixes = PREFIX_FWAIT;
02716          break;
02717        default:
02718          return;
02719        }
02720       /* Rex is ignored when followed by another prefix.  */
02721       if (rex)
02722        {
02723          rex_used = rex;
02724          return;
02725        }
02726       rex = newrex;
02727       codep++;
02728     }
02729 }
02730 
02731 /* Return the name of the prefix byte PREF, or NULL if PREF is not a
02732    prefix byte.  */
02733 
02734 static const char *
02735 prefix_name (int pref, int sizeflag)
02736 {
02737   static const char *rexes [16] =
02738     {
02739       "rex",         /* 0x40 */
02740       "rex.B",              /* 0x41 */
02741       "rex.X",              /* 0x42 */
02742       "rex.XB",             /* 0x43 */
02743       "rex.R",              /* 0x44 */
02744       "rex.RB",             /* 0x45 */
02745       "rex.RX",             /* 0x46 */
02746       "rex.RXB",     /* 0x47 */
02747       "rex.W",              /* 0x48 */
02748       "rex.WB",             /* 0x49 */
02749       "rex.WX",             /* 0x4a */
02750       "rex.WXB",     /* 0x4b */
02751       "rex.WR",             /* 0x4c */
02752       "rex.WRB",     /* 0x4d */
02753       "rex.WRX",     /* 0x4e */
02754       "rex.WRXB",    /* 0x4f */
02755     };
02756 
02757   switch (pref)
02758     {
02759     /* REX prefixes family.  */
02760     case 0x40:
02761     case 0x41:
02762     case 0x42:
02763     case 0x43:
02764     case 0x44:
02765     case 0x45:
02766     case 0x46:
02767     case 0x47:
02768     case 0x48:
02769     case 0x49:
02770     case 0x4a:
02771     case 0x4b:
02772     case 0x4c:
02773     case 0x4d:
02774     case 0x4e:
02775     case 0x4f:
02776       return rexes [pref - 0x40];
02777     case 0xf3:
02778       return "repz";
02779     case 0xf2:
02780       return "repnz";
02781     case 0xf0:
02782       return "lock";
02783     case 0x2e:
02784       return "cs";
02785     case 0x36:
02786       return "ss";
02787     case 0x3e:
02788       return "ds";
02789     case 0x26:
02790       return "es";
02791     case 0x64:
02792       return "fs";
02793     case 0x65:
02794       return "gs";
02795     case 0x66:
02796       return (sizeflag & DFLAG) ? "data16" : "data32";
02797     case 0x67:
02798       if (address_mode == mode_64bit)
02799        return (sizeflag & AFLAG) ? "addr32" : "addr64";
02800       else
02801        return (sizeflag & AFLAG) ? "addr16" : "addr32";
02802     case FWAIT_OPCODE:
02803       return "fwait";
02804     default:
02805       return NULL;
02806     }
02807 }
02808 
02809 static char op_out[MAX_OPERANDS][100];
02810 static int op_ad, op_index[MAX_OPERANDS];
02811 static int two_source_ops;
02812 static bfd_vma op_address[MAX_OPERANDS];
02813 static bfd_vma op_riprel[MAX_OPERANDS];
02814 static bfd_vma start_pc;
02815 
02816 /*
02817  *   On the 386's of 1988, the maximum length of an instruction is 15 bytes.
02818  *   (see topic "Redundant prefixes" in the "Differences from 8086"
02819  *   section of the "Virtual 8086 Mode" chapter.)
02820  * 'pc' should be the address of this instruction, it will
02821  *   be used to print the target address if this is a relative jump or call
02822  * The function returns the length of this instruction in bytes.
02823  */
02824 
02825 static char intel_syntax;
02826 static char open_char;
02827 static char close_char;
02828 static char separator_char;
02829 static char scale_char;
02830 
02831 /* Here for backwards compatibility.  When gdb stops using
02832    print_insn_i386_att and print_insn_i386_intel these functions can
02833    disappear, and print_insn_i386 be merged into print_insn.  */
02834 int
02835 print_insn_i386_att (bfd_vma pc, disassemble_info *info)
02836 {
02837   intel_syntax = 0;
02838 
02839   return print_insn (pc, info);
02840 }
02841 
02842 int
02843 print_insn_i386_intel (bfd_vma pc, disassemble_info *info)
02844 {
02845   intel_syntax = 1;
02846 
02847   return print_insn (pc, info);
02848 }
02849 
02850 int
02851 print_insn_i386 (bfd_vma pc, disassemble_info *info)
02852 {
02853   intel_syntax = -1;
02854 
02855   return print_insn (pc, info);
02856 }
02857 
02858 void
02859 print_i386_disassembler_options (FILE *stream)
02860 {
02861   fprintf (stream, _("\n\
02862 The following i386/x86-64 specific disassembler options are supported for use\n\
02863 with the -M switch (multiple options should be separated by commas):\n"));
02864 
02865   fprintf (stream, _("  x86-64      Disassemble in 64bit mode\n"));
02866   fprintf (stream, _("  i386        Disassemble in 32bit mode\n"));
02867   fprintf (stream, _("  i8086       Disassemble in 16bit mode\n"));
02868   fprintf (stream, _("  att         Display instruction in AT&T syntax\n"));
02869   fprintf (stream, _("  intel       Display instruction in Intel syntax\n"));
02870   fprintf (stream, _("  addr64      Assume 64bit address size\n"));
02871   fprintf (stream, _("  addr32      Assume 32bit address size\n"));
02872   fprintf (stream, _("  addr16      Assume 16bit address size\n"));
02873   fprintf (stream, _("  data32      Assume 32bit data size\n"));
02874   fprintf (stream, _("  data16      Assume 16bit data size\n"));
02875   fprintf (stream, _("  suffix      Always display instruction suffix in AT&T syntax\n"));
02876 }
02877 
02878 static int
02879 print_insn (bfd_vma pc, disassemble_info *info)
02880 {
02881   const struct dis386 *dp;
02882   int i;
02883   char *op_txt[MAX_OPERANDS];
02884   int needcomma;
02885   unsigned char uses_DATA_prefix, uses_LOCK_prefix;
02886   unsigned char uses_REPNZ_prefix, uses_REPZ_prefix;
02887   int sizeflag;
02888   const char *p;
02889   struct dis_private priv;
02890   unsigned char op;
02891 
02892   if (info->mach == bfd_mach_x86_64_intel_syntax
02893       || info->mach == bfd_mach_x86_64)
02894     address_mode = mode_64bit;
02895   else
02896     address_mode = mode_32bit;
02897 
02898   if (intel_syntax == (char) -1)
02899     intel_syntax = (info->mach == bfd_mach_i386_i386_intel_syntax
02900                   || info->mach == bfd_mach_x86_64_intel_syntax);
02901 
02902   if (info->mach == bfd_mach_i386_i386
02903       || info->mach == bfd_mach_x86_64
02904       || info->mach == bfd_mach_i386_i386_intel_syntax
02905       || info->mach == bfd_mach_x86_64_intel_syntax)
02906     priv.orig_sizeflag = AFLAG | DFLAG;
02907   else if (info->mach == bfd_mach_i386_i8086)
02908     priv.orig_sizeflag = 0;
02909   else
02910     abort ();
02911 
02912   for (p = info->disassembler_options; p != NULL; )
02913     {
02914       if (CONST_STRNEQ (p, "x86-64"))
02915        {
02916          address_mode = mode_64bit;
02917          priv.orig_sizeflag = AFLAG | DFLAG;
02918        }
02919       else if (CONST_STRNEQ (p, "i386"))
02920        {
02921          address_mode = mode_32bit;
02922          priv.orig_sizeflag = AFLAG | DFLAG;
02923        }
02924       else if (CONST_STRNEQ (p, "i8086"))
02925        {
02926          address_mode = mode_16bit;
02927          priv.orig_sizeflag = 0;
02928        }
02929       else if (CONST_STRNEQ (p, "intel"))
02930        {
02931          intel_syntax = 1;
02932        }
02933       else if (CONST_STRNEQ (p, "att"))
02934        {
02935          intel_syntax = 0;
02936        }
02937       else if (CONST_STRNEQ (p, "addr"))
02938        {
02939          if (address_mode == mode_64bit)
02940            {
02941              if (p[4] == '3' && p[5] == '2')
02942               priv.orig_sizeflag &= ~AFLAG;
02943              else if (p[4] == '6' && p[5] == '4')
02944               priv.orig_sizeflag |= AFLAG;
02945            }
02946          else
02947            {
02948              if (p[4] == '1' && p[5] == '6')
02949               priv.orig_sizeflag &= ~AFLAG;
02950              else if (p[4] == '3' && p[5] == '2')
02951               priv.orig_sizeflag |= AFLAG;
02952            }
02953        }
02954       else if (CONST_STRNEQ (p, "data"))
02955        {
02956          if (p[4] == '1' && p[5] == '6')
02957            priv.orig_sizeflag &= ~DFLAG;
02958          else if (p[4] == '3' && p[5] == '2')
02959            priv.orig_sizeflag |= DFLAG;
02960        }
02961       else if (CONST_STRNEQ (p, "suffix"))
02962        priv.orig_sizeflag |= SUFFIX_ALWAYS;
02963 
02964       p = strchr (p, ',');
02965       if (p != NULL)
02966        p++;
02967     }
02968 
02969   if (intel_syntax)
02970     {
02971       names64 = intel_names64;
02972       names32 = intel_names32;
02973       names16 = intel_names16;
02974       names8 = intel_names8;
02975       names8rex = intel_names8rex;
02976       names_seg = intel_names_seg;
02977       index16 = intel_index16;
02978       open_char = '[';
02979       close_char = ']';
02980       separator_char = '+';
02981       scale_char = '*';
02982     }
02983   else
02984     {
02985       names64 = att_names64;
02986       names32 = att_names32;
02987       names16 = att_names16;
02988       names8 = att_names8;
02989       names8rex = att_names8rex;
02990       names_seg = att_names_seg;
02991       index16 = att_index16;
02992       open_char = '(';
02993       close_char =  ')';
02994       separator_char = ',';
02995       scale_char = ',';
02996     }
02997 
02998   /* The output looks better if we put 7 bytes on a line, since that
02999      puts most long word instructions on a single line.  */
03000   info->bytes_per_line = 7;
03001 
03002   info->private_data = &priv;
03003   priv.max_fetched = priv.the_buffer;
03004   priv.insn_start = pc;
03005 
03006   obuf[0] = 0;
03007   for (i = 0; i < MAX_OPERANDS; ++i)
03008     {
03009       op_out[i][0] = 0;
03010       op_index[i] = -1;
03011     }
03012 
03013   the_info = info;
03014   start_pc = pc;
03015   start_codep = priv.the_buffer;
03016   codep = priv.the_buffer;
03017 
03018   if (setjmp (priv.bailout) != 0)
03019     {
03020       const char *name;
03021 
03022       /* Getting here means we tried for data but didn't get it.  That
03023         means we have an incomplete instruction of some sort.  Just
03024         print the first byte as a prefix or a .byte pseudo-op.  */
03025       if (codep > priv.the_buffer)
03026        {
03027          name = prefix_name (priv.the_buffer[0], priv.orig_sizeflag);
03028          if (name != NULL)
03029            (*info->fprintf_func) (info->stream, "%s", name);
03030          else
03031            {
03032              /* Just print the first byte as a .byte instruction.  */
03033              (*info->fprintf_func) (info->stream, ".byte 0x%x",
03034                                  (unsigned int) priv.the_buffer[0]);
03035            }
03036 
03037          return 1;
03038        }
03039 
03040       return -1;
03041     }
03042 
03043   obufp = obuf;
03044   ckprefix ();
03045 
03046   insn_codep = codep;
03047   sizeflag = priv.orig_sizeflag;
03048 
03049   FETCH_DATA (info, codep + 1);
03050   two_source_ops = (*codep == 0x62) || (*codep == 0xc8);
03051 
03052   if (((prefixes & PREFIX_FWAIT)
03053        && ((*codep < 0xd8) || (*codep > 0xdf)))
03054       || (rex && rex_used))
03055     {
03056       const char *name;
03057 
03058       /* fwait not followed by floating point instruction, or rex followed
03059         by other prefixes.  Print the first prefix.  */
03060       name = prefix_name (priv.the_buffer[0], priv.orig_sizeflag);
03061       if (name == NULL)
03062        name = INTERNAL_DISASSEMBLER_ERROR;
03063       (*info->fprintf_func) (info->stream, "%s", name);
03064       return 1;
03065     }
03066 
03067   op = 0;
03068   if (*codep == 0x0f)
03069     {
03070       unsigned char threebyte;
03071       FETCH_DATA (info, codep + 2);
03072       threebyte = *++codep;
03073       dp = &dis386_twobyte[threebyte];
03074       need_modrm = twobyte_has_modrm[*codep];
03075       uses_DATA_prefix = twobyte_uses_DATA_prefix[*codep];
03076       uses_REPNZ_prefix = twobyte_uses_REPNZ_prefix[*codep];
03077       uses_REPZ_prefix = twobyte_uses_REPZ_prefix[*codep];
03078       uses_LOCK_prefix = (*codep & ~0x02) == 0x20;
03079       codep++;
03080       if (dp->name == NULL && dp->op[0].bytemode == IS_3BYTE_OPCODE)
03081        {
03082          FETCH_DATA (info, codep + 2);
03083          op = *codep++;
03084          switch (threebyte)
03085            {
03086            case 0x38:
03087              uses_DATA_prefix = threebyte_0x38_uses_DATA_prefix[op];
03088              uses_REPNZ_prefix = threebyte_0x38_uses_REPNZ_prefix[op];
03089              uses_REPZ_prefix = threebyte_0x38_uses_REPZ_prefix[op];
03090              break;
03091            case 0x3a:
03092              uses_DATA_prefix = threebyte_0x3a_uses_DATA_prefix[op];
03093              uses_REPNZ_prefix = threebyte_0x3a_uses_REPNZ_prefix[op];
03094              uses_REPZ_prefix = threebyte_0x3a_uses_REPZ_prefix[op];
03095              break;
03096            default:
03097              break;
03098            }
03099        }
03100     }
03101   else
03102     {
03103       dp = &dis386[*codep];
03104       need_modrm = onebyte_has_modrm[*codep];
03105       uses_DATA_prefix = 0;
03106       uses_REPNZ_prefix = 0;
03107       /* pause is 0xf3 0x90.  */
03108       uses_REPZ_prefix = *codep == 0x90;
03109       uses_LOCK_prefix = 0;
03110       codep++;
03111     }
03112   
03113   if (!uses_REPZ_prefix && (prefixes & PREFIX_REPZ))
03114     {
03115       oappend ("repz ");
03116       used_prefixes |= PREFIX_REPZ;
03117     }
03118   if (!uses_REPNZ_prefix && (prefixes & PREFIX_REPNZ))
03119     {
03120       oappend ("repnz ");
03121       used_prefixes |= PREFIX_REPNZ;
03122     }
03123 
03124   if (!uses_LOCK_prefix && (prefixes & PREFIX_LOCK))
03125     {
03126       oappend ("lock ");
03127       used_prefixes |= PREFIX_LOCK;
03128     }
03129 
03130   if (prefixes & PREFIX_ADDR)
03131     {
03132       sizeflag ^= AFLAG;
03133       if (dp->op[2].bytemode != loop_jcxz_mode || intel_syntax)
03134        {
03135          if ((sizeflag & AFLAG) || address_mode == mode_64bit)
03136            oappend ("addr32 ");
03137          else
03138            oappend ("addr16 ");
03139          used_prefixes |= PREFIX_ADDR;
03140        }
03141     }
03142 
03143   if (!uses_DATA_prefix && (prefixes & PREFIX_DATA))
03144     {
03145       sizeflag ^= DFLAG;
03146       if (dp->op[2].bytemode == cond_jump_mode
03147          && dp->op[0].bytemode == v_mode
03148          && !intel_syntax)
03149        {
03150          if (sizeflag & DFLAG)
03151            oappend ("data32 ");
03152          else
03153            oappend ("data16 ");
03154          used_prefixes |= PREFIX_DATA;
03155        }
03156     }
03157 
03158   if (dp->name == NULL && dp->op[0].bytemode == IS_3BYTE_OPCODE)
03159     {
03160       dp = &three_byte_table[dp->op[1].bytemode][op];
03161       mod = (*codep >> 6) & 3;
03162       reg = (*codep >> 3) & 7;
03163       rm = *codep & 7;
03164     }
03165   else if (need_modrm)
03166     {
03167       FETCH_DATA (info, codep + 1);
03168       mod = (*codep >> 6) & 3;
03169       reg = (*codep >> 3) & 7;
03170       rm = *codep & 7;
03171     }
03172 
03173   if (dp->name == NULL && dp->op[0].bytemode == FLOATCODE)
03174     {
03175       dofloat (sizeflag);
03176     }
03177   else
03178     {
03179       int index;
03180       if (dp->name == NULL)
03181        {
03182          switch (dp->op[0].bytemode)
03183            {
03184            case USE_GROUPS:
03185              dp = &grps[dp->op[1].bytemode][reg];
03186              break;
03187 
03188            case USE_PREFIX_USER_TABLE:
03189              index = 0;
03190              used_prefixes |= (prefixes & PREFIX_REPZ);
03191              if (prefixes & PREFIX_REPZ)
03192               index = 1;
03193              else
03194               {
03195                 /* We should check PREFIX_REPNZ and PREFIX_REPZ
03196                    before PREFIX_DATA.  */
03197                 used_prefixes |= (prefixes & PREFIX_REPNZ);
03198                 if (prefixes & PREFIX_REPNZ)
03199                   index = 3;
03200                 else
03201                   {
03202                     used_prefixes |= (prefixes & PREFIX_DATA);
03203                     if (prefixes & PREFIX_DATA)
03204                      index = 2;
03205                   }
03206               }
03207              dp = &prefix_user_table[dp->op[1].bytemode][index];
03208              break;
03209 
03210            case X86_64_SPECIAL:
03211              index = address_mode == mode_64bit ? 1 : 0;
03212              dp = &x86_64_table[dp->op[1].bytemode][index];
03213              break;
03214 
03215            default:
03216              oappend (INTERNAL_DISASSEMBLER_ERROR);
03217              break;
03218            }
03219        }
03220 
03221       if (putop (dp->name, sizeflag) == 0)
03222         {
03223          for (i = 0; i < MAX_OPERANDS; ++i)
03224            {
03225              obufp = op_out[i];             
03226              op_ad = MAX_OPERANDS - 1 - i;
03227              if (dp->op[i].rtn)
03228               (*dp->op[i].rtn) (dp->op[i].bytemode, sizeflag);
03229            }
03230        }
03231     }
03232 
03233   /* See if any prefixes were not used.  If so, print the first one
03234      separately.  If we don't do this, we'll wind up printing an
03235      instruction stream which does not precisely correspond to the
03236      bytes we are disassembling.  */
03237   if ((prefixes & ~used_prefixes) != 0)
03238     {
03239       const char *name;
03240 
03241       name = prefix_name (priv.the_buffer[0], priv.orig_sizeflag);
03242       if (name == NULL)
03243        name = INTERNAL_DISASSEMBLER_ERROR;
03244       (*info->fprintf_func) (info->stream, "%s", name);
03245       return 1;
03246     }
03247   if (rex & ~rex_used)
03248     {
03249       const char *name;
03250       name = prefix_name (rex | 0x40, priv.orig_sizeflag);
03251       if (name == NULL)
03252        name = INTERNAL_DISASSEMBLER_ERROR;
03253       (*info->fprintf_func) (info->stream, "%s ", name);
03254     }
03255 
03256   obufp = obuf + strlen (obuf);
03257   for (i = strlen (obuf); i < 6; i++)
03258     oappend (" ");
03259   oappend (" ");
03260   (*info->fprintf_func) (info->stream, "%s", obuf);
03261 
03262   /* The enter and bound instructions are printed with operands in the same
03263      order as the intel book; everything else is printed in reverse order.  */
03264   if (intel_syntax || two_source_ops)
03265     {
03266       for (i = 0; i < MAX_OPERANDS; ++i)
03267         op_txt[i] = op_out[i];
03268        
03269       for (i = 0; i < (MAX_OPERANDS >> 1); ++i)
03270        {
03271           op_ad = op_index[i];
03272           op_index[i] = op_index[MAX_OPERANDS - 1 - i];
03273           op_index[MAX_OPERANDS - 1 - i] = op_ad;
03274        }
03275     }
03276   else
03277     {
03278       for (i = 0; i < MAX_OPERANDS; ++i)
03279         op_txt[MAX_OPERANDS - 1 - i] = op_out[i];
03280     }
03281 
03282   needcomma = 0;
03283   for (i = 0; i < MAX_OPERANDS; ++i)
03284     if (*op_txt[i])
03285       {
03286        if (needcomma)
03287          (*info->fprintf_func) (info->stream, ",");
03288        if (op_index[i] != -1 && !op_riprel[i])
03289          (*info->print_address_func) ((bfd_vma) op_address[op_index[i]], info);
03290        else
03291          (*info->fprintf_func) (info->stream, "%s", op_txt[i]);
03292        needcomma = 1;
03293       }
03294 
03295   for (i = 0; i < MAX_OPERANDS; i++)
03296     if (op_index[i] != -1 && op_riprel[i])
03297       {
03298        (*info->fprintf_func) (info->stream, "        # ");
03299        (*info->print_address_func) ((bfd_vma) (start_pc + codep - start_codep
03300                                           + op_address[op_index[i]]), info);
03301       }
03302   return codep - priv.the_buffer;
03303 }
03304 
03305 static const char *float_mem[] = {
03306   /* d8 */
03307   "fadd{s||s|}",
03308   "fmul{s||s|}",
03309   "fcom{s||s|}",
03310   "fcomp{s||s|}",
03311   "fsub{s||s|}",
03312   "fsubr{s||s|}",
03313   "fdiv{s||s|}",
03314   "fdivr{s||s|}",
03315   /* d9 */
03316   "fld{s||s|}",
03317   "(bad)",
03318   "fst{s||s|}",
03319   "fstp{s||s|}",
03320   "fldenvIC",
03321   "fldcw",
03322   "fNstenvIC",
03323   "fNstcw",
03324   /* da */
03325   "fiadd{l||l|}",
03326   "fimul{l||l|}",
03327   "ficom{l||l|}",
03328   "ficomp{l||l|}",
03329   "fisub{l||l|}",
03330   "fisubr{l||l|}",
03331   "fidiv{l||l|}",
03332   "fidivr{l||l|}",
03333   /* db */
03334   "fild{l||l|}",
03335   "fisttp{l||l|}",
03336   "fist{l||l|}",
03337   "fistp{l||l|}",
03338   "(bad)",
03339   "fld{t||t|}",
03340   "(bad)",
03341   "fstp{t||t|}",
03342   /* dc */
03343   "fadd{l||l|}",
03344   "fmul{l||l|}",
03345   "fcom{l||l|}",
03346   "fcomp{l||l|}",
03347   "fsub{l||l|}",
03348   "fsubr{l||l|}",
03349   "fdiv{l||l|}",
03350   "fdivr{l||l|}",
03351   /* dd */
03352   "fld{l||l|}",
03353   "fisttp{ll||ll|}",
03354   "fst{l||l|}",
03355   "fstp{l||l|}",
03356   "frstorIC",
03357   "(bad)",
03358   "fNsaveIC",
03359   "fNstsw",
03360   /* de */
03361   "fiadd",
03362   "fimul",
03363   "ficom",
03364   "ficomp",
03365   "fisub",
03366   "fisubr",
03367   "fidiv",
03368   "fidivr",
03369   /* df */
03370   "fild",
03371   "fisttp",
03372   "fist",
03373   "fistp",
03374   "fbld",
03375   "fild{ll||ll|}",
03376   "fbstp",
03377   "fistp{ll||ll|}",
03378 };
03379 
03380 static const unsigned char float_mem_mode[] = {
03381   /* d8 */
03382   d_mode,
03383   d_mode,
03384   d_mode,
03385   d_mode,
03386   d_mode,
03387   d_mode,
03388   d_mode,
03389   d_mode,
03390   /* d9 */
03391   d_mode,
03392   0,
03393   d_mode,
03394   d_mode,
03395   0,
03396   w_mode,
03397   0,
03398   w_mode,
03399   /* da */
03400   d_mode,
03401   d_mode,
03402   d_mode,
03403   d_mode,
03404   d_mode,
03405   d_mode,
03406   d_mode,
03407   d_mode,
03408   /* db */
03409   d_mode,
03410   d_mode,
03411   d_mode,
03412   d_mode,
03413   0,
03414   t_mode,
03415   0,
03416   t_mode,
03417   /* dc */
03418   q_mode,
03419   q_mode,
03420   q_mode,
03421   q_mode,
03422   q_mode,
03423   q_mode,
03424   q_mode,
03425   q_mode,
03426   /* dd */
03427   q_mode,
03428   q_mode,
03429   q_mode,
03430   q_mode,
03431   0,
03432   0,
03433   0,
03434   w_mode,
03435   /* de */
03436   w_mode,
03437   w_mode,
03438   w_mode,
03439   w_mode,
03440   w_mode,
03441   w_mode,
03442   w_mode,
03443   w_mode,
03444   /* df */
03445   w_mode,
03446   w_mode,
03447   w_mode,
03448   w_mode,
03449   t_mode,
03450   q_mode,
03451   t_mode,
03452   q_mode
03453 };
03454 
03455 #define ST { OP_ST, 0 }
03456 #define STi { OP_STi, 0 }
03457 
03458 #define FGRPd9_2 NULL, { { NULL, 0 } }
03459 #define FGRPd9_4 NULL, { { NULL, 1 } }
03460 #define FGRPd9_5 NULL, { { NULL, 2 } }
03461 #define FGRPd9_6 NULL, { { NULL, 3 } }
03462 #define FGRPd9_7 NULL, { { NULL, 4 } }
03463 #define FGRPda_5 NULL, { { NULL, 5 } }
03464 #define FGRPdb_4 NULL, { { NULL, 6 } }
03465 #define FGRPde_3 NULL, { { NULL, 7 } }
03466 #define FGRPdf_4 NULL, { { NULL, 8 } }
03467 
03468 static const struct dis386 float_reg[][8] = {
03469   /* d8 */
03470   {
03471     { "fadd", { ST, STi } },
03472     { "fmul", { ST, STi } },
03473     { "fcom", { STi } },
03474     { "fcomp",       { STi } },
03475     { "fsub", { ST, STi } },
03476     { "fsubr",       { ST, STi } },
03477     { "fdiv", { ST, STi } },
03478     { "fdivr",       { ST, STi } },
03479   },
03480   /* d9 */
03481   {
03482     { "fld",  { STi } },
03483     { "fxch", { STi } },
03484     { FGRPd9_2 },
03485     { "(bad)",       { XX } },
03486     { FGRPd9_4 },
03487     { FGRPd9_5 },
03488     { FGRPd9_6 },
03489     { FGRPd9_7 },
03490   },
03491   /* da */
03492   {
03493     { "fcmovb",      { ST, STi } },
03494     { "fcmove",      { ST, STi } },
03495     { "fcmovbe",{ ST, STi } },
03496     { "fcmovu",      { ST, STi } },
03497     { "(bad)",       { XX } },
03498     { FGRPda_5 },
03499     { "(bad)",       { XX } },
03500     { "(bad)",       { XX } },
03501   },
03502   /* db */
03503   {
03504     { "fcmovnb",{ ST, STi } },
03505     { "fcmovne",{ ST, STi } },
03506     { "fcmovnbe",{ ST, STi } },
03507     { "fcmovnu",{ ST, STi } },
03508     { FGRPdb_4 },
03509     { "fucomi",      { ST, STi } },
03510     { "fcomi",       { ST, STi } },
03511     { "(bad)",       { XX } },
03512   },
03513   /* dc */
03514   {
03515     { "fadd", { STi, ST } },
03516     { "fmul", { STi, ST } },
03517     { "(bad)",       { XX } },
03518     { "(bad)",       { XX } },
03519 #if SYSV386_COMPAT
03520     { "fsub", { STi, ST } },
03521     { "fsubr",       { STi, ST } },
03522     { "fdiv", { STi, ST } },
03523     { "fdivr",       { STi, ST } },
03524 #else
03525     { "fsubr",       { STi, ST } },
03526     { "fsub", { STi, ST } },
03527     { "fdivr",       { STi, ST } },
03528     { "fdiv", { STi, ST } },
03529 #endif
03530   },
03531   /* dd */
03532   {
03533     { "ffree",       { STi } },
03534     { "(bad)",       { XX } },
03535     { "fst",  { STi } },
03536     { "fstp", { STi } },
03537     { "fucom",       { STi } },
03538     { "fucomp",      { STi } },
03539     { "(bad)",       { XX } },
03540     { "(bad)",       { XX } },
03541   },
03542   /* de */
03543   {
03544     { "faddp",       { STi, ST } },
03545     { "fmulp",       { STi, ST } },
03546     { "(bad)",       { XX } },
03547     { FGRPde_3 },
03548 #if SYSV386_COMPAT
03549     { "fsubp",       { STi, ST } },
03550     { "fsubrp",      { STi, ST } },
03551     { "fdivp",       { STi, ST } },
03552     { "fdivrp",      { STi, ST } },
03553 #else
03554     { "fsubrp",      { STi, ST } },
03555     { "fsubp",       { STi, ST } },
03556     { "fdivrp",      { STi, ST } },
03557     { "fdivp",       { STi, ST } },
03558 #endif
03559   },
03560   /* df */
03561   {
03562     { "ffreep",      { STi } },
03563     { "(bad)",       { XX } },
03564     { "(bad)",       { XX } },
03565     { "(bad)",       { XX } },
03566     { FGRPdf_4 },
03567     { "fucomip", { ST, STi } },
03568     { "fcomip", { ST, STi } },
03569     { "(bad)",       { XX } },
03570   },
03571 };
03572 
03573 static char *fgrps[][8] = {
03574   /* d9_2  0 */
03575   {
03576     "fnop","(bad)","(bad)","(bad)","(bad)","(bad)","(bad)","(bad)",
03577   },
03578 
03579   /* d9_4  1 */
03580   {
03581     "fchs","fabs","(bad)","(bad)","ftst","fxam","(bad)","(bad)",
03582   },
03583 
03584   /* d9_5  2 */
03585   {
03586     "fld1","fldl2t","fldl2e","fldpi","fldlg2","fldln2","fldz","(bad)",
03587   },
03588 
03589   /* d9_6  3 */
03590   {
03591     "f2xm1","fyl2x","fptan","fpatan","fxtract","fprem1","fdecstp","fincstp",
03592   },
03593 
03594   /* d9_7  4 */
03595   {
03596     "fprem","fyl2xp1","fsqrt","fsincos","frndint","fscale","fsin","fcos",
03597   },
03598 
03599   /* da_5  5 */
03600   {
03601     "(bad)","fucompp","(bad)","(bad)","(bad)","(bad)","(bad)","(bad)",
03602   },
03603 
03604   /* db_4  6 */
03605   {
03606     "feni(287 only)","fdisi(287 only)","fNclex","fNinit",
03607     "fNsetpm(287 only)","(bad)","(bad)","(bad)",
03608   },
03609 
03610   /* de_3  7 */
03611   {
03612     "(bad)","fcompp","(bad)","(bad)","(bad)","(bad)","(bad)","(bad)",
03613   },
03614 
03615   /* df_4  8 */
03616   {
03617     "fNstsw","(bad)","(bad)","(bad)","(bad)","(bad)","(bad)","(bad)",
03618   },
03619 };
03620 
03621 static void
03622 dofloat (int sizeflag)
03623 {
03624   const struct dis386 *dp;
03625   unsigned char floatop;
03626 
03627   floatop = codep[-1];
03628 
03629   if (mod != 3)
03630     {
03631       int fp_indx = (floatop - 0xd8) * 8 + reg;
03632 
03633       putop (float_mem[fp_indx], sizeflag);
03634       obufp = op_out[0];
03635       op_ad = 2;
03636       OP_E (float_mem_mode[fp_indx], sizeflag);
03637       return;
03638     }
03639   /* Skip mod/rm byte.  */
03640   MODRM_CHECK;
03641   codep++;
03642 
03643   dp = &float_reg[floatop - 0xd8][reg];
03644   if (dp->name == NULL)
03645     {
03646       putop (fgrps[dp->op[0].bytemode][rm], sizeflag);
03647 
03648       /* Instruction fnstsw is only one with strange arg.  */
03649       if (floatop == 0xdf && codep[-1] == 0xe0)
03650        strcpy (op_out[0], names16[0]);
03651     }
03652   else
03653     {
03654       putop (dp->name, sizeflag);
03655 
03656       obufp = op_out[0];
03657       op_ad = 2;
03658       if (dp->op[0].rtn)
03659        (*dp->op[0].rtn) (dp->op[0].bytemode, sizeflag);
03660 
03661       obufp = op_out[1];
03662       op_ad = 1;
03663       if (dp->op[1].rtn)
03664        (*dp->op[1].rtn) (dp->op[1].bytemode, sizeflag);
03665     }
03666 }
03667 
03668 static void
03669 OP_ST (int bytemode ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
03670 {
03671   oappend ("%st" + intel_syntax);
03672 }
03673 
03674 static void
03675 OP_STi (int bytemode ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
03676 {
03677   sprintf (scratchbuf, "%%st(%d)", rm);
03678   oappend (scratchbuf + intel_syntax);
03679 }
03680 
03681 /* Capital letters in template are macros.  */
03682 static int
03683 putop (const char *template, int sizeflag)
03684 {
03685   const char *p;
03686   int alt = 0;
03687 
03688   for (p = template; *p; p++)
03689     {
03690       switch (*p)
03691        {
03692        default:
03693          *obufp++ = *p;
03694          break;
03695        case '{':
03696          alt = 0;
03697          if (intel_syntax)
03698            alt += 1;
03699          if (address_mode == mode_64bit)
03700            alt += 2;
03701          while (alt != 0)
03702            {
03703              while (*++p != '|')
03704               {
03705                 if (*p == '}')
03706                   {
03707                     /* Alternative not valid.  */
03708                     strcpy (obuf, "(bad)");
03709                     obufp = obuf + 5;
03710                     return 1;
03711                   }
03712                 else if (*p == '\0')
03713                   abort ();
03714               }
03715              alt--;
03716            }
03717          /* Fall through.  */
03718        case 'I':
03719          alt = 1;
03720          continue;
03721        case '|':
03722          while (*++p != '}')
03723            {
03724              if (*p == '\0')
03725               abort ();
03726            }
03727          break;
03728        case '}':
03729          break;
03730        case 'A':
03731          if (intel_syntax)
03732            break;
03733          if (mod != 3 || (sizeflag & SUFFIX_ALWAYS))
03734            *obufp++ = 'b';
03735          break;
03736        case 'B':
03737          if (intel_syntax)
03738            break;
03739          if (sizeflag & SUFFIX_ALWAYS)
03740            *obufp++ = 'b';
03741          break;
03742        case 'C':
03743          if (intel_syntax && !alt)
03744            break;
03745          if ((prefixes & PREFIX_DATA) || (sizeflag & SUFFIX_ALWAYS))
03746            {
03747              if (sizeflag & DFLAG)
03748               *obufp++ = intel_syntax ? 'd' : 'l';
03749              else
03750               *obufp++ = intel_syntax ? 'w' : 's';
03751              used_prefixes |= (prefixes & PREFIX_DATA);
03752            }
03753          break;
03754        case 'D':
03755          if (intel_syntax || !(sizeflag & SUFFIX_ALWAYS))
03756            break;
03757          USED_REX (REX_W);
03758          if (mod == 3)
03759            {
03760              if (rex & REX_W)
03761               *obufp++ = 'q';
03762              else if (sizeflag & DFLAG)
03763               *obufp++ = intel_syntax ? 'd' : 'l';
03764              else
03765               *obufp++ = 'w';
03766              used_prefixes |= (prefixes & PREFIX_DATA);
03767            }
03768          else
03769            *obufp++ = 'w';
03770          break;
03771        case 'E':            /* For jcxz/jecxz */
03772          if (address_mode == mode_64bit)
03773            {
03774              if (sizeflag & AFLAG)
03775               *obufp++ = 'r';
03776              else
03777               *obufp++ = 'e';
03778            }
03779          else
03780            if (sizeflag & AFLAG)
03781              *obufp++ = 'e';
03782          used_prefixes |= (prefixes & PREFIX_ADDR);
03783          break;
03784        case 'F':
03785          if (intel_syntax)
03786            break;
03787          if ((prefixes & PREFIX_ADDR) || (sizeflag & SUFFIX_ALWAYS))
03788            {
03789              if (sizeflag & AFLAG)
03790               *obufp++ = address_mode == mode_64bit ? 'q' : 'l';
03791              else
03792               *obufp++ = address_mode == mode_64bit ? 'l' : 'w';
03793              used_prefixes |= (prefixes & PREFIX_ADDR);
03794            }
03795          break;
03796        case 'G':
03797          if (intel_syntax || (obufp[-1] != 's' && !(sizeflag & SUFFIX_ALWAYS)))
03798            break;
03799          if ((rex & REX_W) || (sizeflag & DFLAG))
03800            *obufp++ = 'l';
03801          else
03802            *obufp++ = 'w';
03803          if (!(rex & REX_W))
03804            used_prefixes |= (prefixes & PREFIX_DATA);
03805          break;
03806        case 'H':
03807          if (intel_syntax)
03808            break;
03809          if ((prefixes & (PREFIX_CS | PREFIX_DS)) == PREFIX_CS
03810              || (prefixes & (PREFIX_CS | PREFIX_DS)) == PREFIX_DS)
03811            {
03812              used_prefixes |= prefixes & (PREFIX_CS | PREFIX_DS);
03813              *obufp++ = ',';
03814              *obufp++ = 'p';
03815              if (prefixes & PREFIX_DS)
03816               *obufp++ = 't';
03817              else
03818               *obufp++ = 'n';
03819            }
03820          break;
03821        case 'J':
03822          if (intel_syntax)
03823            break;
03824          *obufp++ = 'l';
03825          break;
03826        case 'Z':
03827          if (intel_syntax)
03828            break;
03829          if (address_mode == mode_64bit && (sizeflag & SUFFIX_ALWAYS))
03830            {
03831              *obufp++ = 'q';
03832              break;
03833            }
03834          /* Fall through.  */
03835        case 'L':
03836          if (intel_syntax)
03837            break;
03838          if (sizeflag & SUFFIX_ALWAYS)
03839            *obufp++ = 'l';
03840          break;
03841        case 'N':
03842          if ((prefixes & PREFIX_FWAIT) == 0)
03843            *obufp++ = 'n';
03844          else
03845            used_prefixes |= PREFIX_FWAIT;
03846          break;
03847        case 'O':
03848          USED_REX (REX_W);
03849          if (rex & REX_W)
03850            *obufp++ = 'o';
03851          else if (intel_syntax && (sizeflag & DFLAG))
03852            *obufp++ = 'q';
03853          else
03854            *obufp++ = 'd';
03855          if (!(rex & REX_W))
03856            used_prefixes |= (prefixes & PREFIX_DATA);
03857          break;
03858        case 'T':
03859          if (intel_syntax)
03860            break;
03861          if (address_mode == mode_64bit && (sizeflag & DFLAG))
03862            {
03863              *obufp++ = 'q';
03864              break;
03865            }
03866          /* Fall through.  */
03867        case 'P':
03868          if (intel_syntax)
03869            break;
03870          if ((prefixes & PREFIX_DATA)
03871              || (rex & REX_W)
03872              || (sizeflag & SUFFIX_ALWAYS))
03873            {
03874              USED_REX (REX_W);
03875              if (rex & REX_W)
03876               *obufp++ = 'q';
03877              else
03878               {
03879                  if (sizeflag & DFLAG)
03880                     *obufp++ = 'l';
03881                  else
03882                    *obufp++ = 'w';
03883               }
03884              used_prefixes |= (prefixes & PREFIX_DATA);
03885            }
03886          break;
03887        case 'U':
03888          if (intel_syntax)
03889            break;
03890          if (address_mode == mode_64bit && (sizeflag & DFLAG))
03891            {
03892              if (mod != 3 || (sizeflag & SUFFIX_ALWAYS))
03893               *obufp++ = 'q';
03894              break;
03895            }
03896          /* Fall through.  */
03897        case 'Q':
03898          if (intel_syntax && !alt)
03899            break;
03900          USED_REX (REX_W);
03901          if (mod != 3 || (sizeflag & SUFFIX_ALWAYS))
03902            {
03903              if (rex & REX_W)
03904               *obufp++ = 'q';
03905              else
03906               {
03907                 if (sizeflag & DFLAG)
03908                   *obufp++ = intel_syntax ? 'd' : 'l';
03909                 else
03910                   *obufp++ = 'w';
03911               }
03912              used_prefixes |= (prefixes & PREFIX_DATA);
03913            }
03914          break;
03915        case 'R':
03916          USED_REX (REX_W);
03917          if (rex & REX_W)
03918            *obufp++ = 'q';
03919          else if (sizeflag & DFLAG)
03920            {
03921              if (intel_syntax)
03922                 *obufp++ = 'd';
03923              else
03924                 *obufp++ = 'l';
03925            }
03926          else
03927            *obufp++ = 'w';
03928          if (intel_syntax && !p[1]
03929              && ((rex & REX_W) || (sizeflag & DFLAG)))
03930            *obufp++ = 'e';
03931          if (!(rex & REX_W))
03932            used_prefixes |= (prefixes & PREFIX_DATA);
03933          break;
03934        case 'V':
03935          if (intel_syntax)
03936            break;
03937          if (address_mode == mode_64bit && (sizeflag & DFLAG))
03938            {
03939              if (sizeflag & SUFFIX_ALWAYS)
03940               *obufp++ = 'q';
03941              break;
03942            }
03943          /* Fall through.  */
03944        case 'S':
03945          if (intel_syntax)
03946            break;
03947          if (sizeflag & SUFFIX_ALWAYS)
03948            {
03949              if (rex & REX_W)
03950               *obufp++ = 'q';
03951              else
03952               {
03953                 if (sizeflag & DFLAG)
03954                   *obufp++ = 'l';
03955                 else
03956                   *obufp++ = 'w';
03957                 used_prefixes |= (prefixes & PREFIX_DATA);
03958               }
03959            }
03960          break;
03961        case 'X':
03962          if (prefixes & PREFIX_DATA)
03963            *obufp++ = 'd';
03964          else
03965            *obufp++ = 's';
03966          used_prefixes |= (prefixes & PREFIX_DATA);
03967          break;
03968        case 'Y':
03969          if (intel_syntax)
03970            break;
03971          if (rex & REX_W)
03972            {
03973              USED_REX (REX_W);
03974              *obufp++ = 'q';
03975            }
03976          break;
03977          /* implicit operand size 'l' for i386 or 'q' for x86-64 */
03978        case 'W':
03979          /* operand size flag for cwtl, cbtw */
03980          USED_REX (REX_W);
03981          if (rex & REX_W)
03982            {
03983              if (intel_syntax)
03984               *obufp++ = 'd';
03985              else
03986               *obufp++ = 'l';
03987            }
03988          else if (sizeflag & DFLAG)
03989            *obufp++ = 'w';
03990          else
03991            *obufp++ = 'b';
03992          if (!(rex & REX_W))
03993            used_prefixes |= (prefixes & PREFIX_DATA);
03994          break;
03995        }
03996       alt = 0;
03997     }
03998   *obufp = 0;
03999   return 0;
04000 }
04001 
04002 static void
04003 oappend (const char *s)
04004 {
04005   strcpy (obufp, s);
04006   obufp += strlen (s);
04007 }
04008 
04009 static void
04010 append_seg (void)
04011 {
04012   if (prefixes & PREFIX_CS)
04013     {
04014       used_prefixes |= PREFIX_CS;
04015       oappend ("%cs:" + intel_syntax);
04016     }
04017   if (prefixes & PREFIX_DS)
04018     {
04019       used_prefixes |= PREFIX_DS;
04020       oappend ("%ds:" + intel_syntax);
04021     }
04022   if (prefixes & PREFIX_SS)
04023     {
04024       used_prefixes |= PREFIX_SS;
04025       oappend ("%ss:" + intel_syntax);
04026     }
04027   if (prefixes & PREFIX_ES)
04028     {
04029       used_prefixes |= PREFIX_ES;
04030       oappend ("%es:" + intel_syntax);
04031     }
04032   if (prefixes & PREFIX_FS)
04033     {
04034       used_prefixes |= PREFIX_FS;
04035       oappend ("%fs:" + intel_syntax);
04036     }
04037   if (prefixes & PREFIX_GS)
04038     {
04039       used_prefixes |= PREFIX_GS;
04040       oappend ("%gs:" + intel_syntax);
04041     }
04042 }
04043 
04044 static void
04045 OP_indirE (int bytemode, int sizeflag)
04046 {
04047   if (!intel_syntax)
04048     oappend ("*");
04049   OP_E (bytemode, sizeflag);
04050 }
04051 
04052 static void
04053 print_operand_value (char *buf, int hex, bfd_vma disp)
04054 {
04055   if (address_mode == mode_64bit)
04056     {
04057       if (hex)
04058        {
04059          char tmp[30];
04060          int i;
04061          buf[0] = '0';
04062          buf[1] = 'x';
04063          sprintf_vma (tmp, disp);
04064          for (i = 0; tmp[i] == '0' && tmp[i + 1]; i++);
04065          strcpy (buf + 2, tmp + i);
04066        }
04067       else
04068        {
04069          bfd_signed_vma v = disp;
04070          char tmp[30];
04071          int i;
04072          if (v < 0)
04073            {
04074              *(buf++) = '-';
04075              v = -disp;
04076              /* Check for possible overflow on 0x8000000000000000.  */
04077              if (v < 0)
04078               {
04079                 strcpy (buf, "9223372036854775808");
04080                 return;
04081               }
04082            }
04083          if (!v)
04084            {
04085              strcpy (buf, "0");
04086              return;
04087            }
04088 
04089          i = 0;
04090          tmp[29] = 0;
04091          while (v)
04092            {
04093              tmp[28 - i] = (v % 10) + '0';
04094              v /= 10;
04095              i++;
04096            }
04097          strcpy (buf, tmp + 29 - i);
04098        }
04099     }
04100   else
04101     {
04102       if (hex)
04103        sprintf (buf, "0x%x", (unsigned int) disp);
04104       else
04105        sprintf (buf, "%d", (int) disp);
04106     }
04107 }
04108 
04109 static void
04110 intel_operand_size (int bytemode, int sizeflag)
04111 {
04112   switch (bytemode)
04113     {
04114     case b_mode:
04115       oappend ("BYTE PTR ");
04116       break;
04117     case w_mode:
04118     case dqw_mode:
04119       oappend ("WORD PTR ");
04120       break;
04121     case stack_v_mode:
04122       if (address_mode == mode_64bit && (sizeflag & DFLAG))
04123        {
04124          oappend ("QWORD PTR ");
04125          used_prefixes |= (prefixes & PREFIX_DATA);
04126          break;
04127        }
04128       /* FALLTHRU */
04129     case v_mode:
04130     case dq_mode:
04131       USED_REX (REX_W);
04132       if (rex & REX_W)
04133        oappend ("QWORD PTR ");
04134       else if ((sizeflag & DFLAG) || bytemode == dq_mode)
04135        oappend ("DWORD PTR ");
04136       else
04137        oappend ("WORD PTR ");
04138       used_prefixes |= (prefixes & PREFIX_DATA);
04139       break;
04140     case z_mode:
04141       if ((rex & REX_W) || (sizeflag & DFLAG))
04142        *obufp++ = 'D';
04143       oappend ("WORD PTR ");
04144       if (!(rex & REX_W))
04145        used_prefixes |= (prefixes & PREFIX_DATA);
04146       break;
04147     case d_mode:
04148       oappend ("DWORD PTR ");
04149       break;
04150     case q_mode:
04151       oappend ("QWORD PTR ");
04152       break;
04153     case m_mode:
04154       if (address_mode == mode_64bit)
04155        oappend ("QWORD PTR ");
04156       else
04157        oappend ("DWORD PTR ");
04158       break;
04159     case f_mode:
04160       if (sizeflag & DFLAG)
04161        oappend ("FWORD PTR ");
04162       else
04163        oappend ("DWORD PTR ");
04164       used_prefixes |= (prefixes & PREFIX_DATA);
04165       break;
04166     case t_mode:
04167       oappend ("TBYTE PTR ");
04168       break;
04169     case x_mode:
04170       oappend ("XMMWORD PTR ");
04171       break;
04172     case o_mode:
04173       oappend ("OWORD PTR ");
04174       break;
04175     default:
04176       break;
04177     }
04178 }
04179 
04180 static void
04181 OP_E (int bytemode, int sizeflag)
04182 {
04183   bfd_vma disp;
04184   int add = 0;
04185   int riprel = 0;
04186   USED_REX (REX_B);
04187   if (rex & REX_B)
04188     add += 8;
04189 
04190   /* Skip mod/rm byte.  */
04191   MODRM_CHECK;
04192   codep++;
04193 
04194   if (mod == 3)
04195     {
04196       switch (bytemode)
04197        {
04198        case b_mode:
04199          USED_REX (0);
04200          if (rex)
04201            oappend (names8rex[rm + add]);
04202          else
04203            oappend (names8[rm + add]);
04204          break;
04205        case w_mode:
04206          oappend (names16[rm + add]);
04207          break;
04208        case d_mode:
04209          oappend (names32[rm + add]);
04210          break;
04211        case q_mode:
04212          oappend (names64[rm + add]);
04213          break;
04214        case m_mode:
04215          if (address_mode == mode_64bit)
04216            oappend (names64[rm + add]);
04217          else
04218            oappend (names32[rm + add]);
04219          break;
04220        case stack_v_mode:
04221          if (address_mode == mode_64bit && (sizeflag & DFLAG))
04222            {
04223              oappend (names64[rm + add]);
04224              used_prefixes |= (prefixes & PREFIX_DATA);
04225              break;
04226            }
04227          bytemode = v_mode;
04228          /* FALLTHRU */
04229        case v_mode:
04230        case dq_mode:
04231        case dqw_mode:
04232          USED_REX (REX_W);
04233          if (rex & REX_W)
04234            oappend (names64[rm + add]);
04235          else if ((sizeflag & DFLAG) || bytemode != v_mode)
04236            oappend (names32[rm + add]);
04237          else
04238            oappend (names16[rm + add]);
04239          used_prefixes |= (prefixes & PREFIX_DATA);
04240          break;
04241        case 0:
04242          break;
04243        default:
04244          oappend (INTERNAL_DISASSEMBLER_ERROR);
04245          break;
04246        }
04247       return;
04248     }
04249 
04250   disp = 0;
04251   if (intel_syntax)
04252     intel_operand_size (bytemode, sizeflag);
04253   append_seg ();
04254 
04255   if ((sizeflag & AFLAG) || address_mode == mode_64bit) /* 32 bit address mode */
04256     {
04257       int havesib;
04258       int havebase;
04259       int base;
04260       int index = 0;
04261       int scale = 0;
04262 
04263       havesib = 0;
04264       havebase = 1;
04265       base = rm;
04266 
04267       if (base == 4)
04268        {
04269          havesib = 1;
04270          FETCH_DATA (the_info, codep + 1);
04271          index = (*codep >> 3) & 7;
04272          if (address_mode == mode_64bit || index != 0x4)
04273            /* When INDEX == 0x4 in 32 bit mode, SCALE is ignored.  */
04274            scale = (*codep >> 6) & 3;
04275          base = *codep & 7;
04276          USED_REX (REX_X);
04277          if (rex & REX_X)
04278            index += 8;
04279          codep++;
04280        }
04281       base += add;
04282 
04283       switch (mod)
04284        {
04285        case 0:
04286          if ((base & 7) == 5)
04287            {
04288              havebase = 0;
04289              if (address_mode == mode_64bit && !havesib)
04290               riprel = 1;
04291              disp = get32s ();
04292            }
04293          break;
04294        case 1:
04295          FETCH_DATA (the_info, codep + 1);
04296          disp = *codep++;
04297          if ((disp & 0x80) != 0)
04298            disp -= 0x100;
04299          break;
04300        case 2:
04301          disp = get32s ();
04302          break;
04303        }
04304 
04305       if (!intel_syntax)
04306        if (mod != 0 || (base & 7) == 5)
04307          {
04308            print_operand_value (scratchbuf, !riprel, disp);
04309            oappend (scratchbuf);
04310            if (riprel)
04311              {
04312               set_op (disp, 1);
04313               oappend ("(%rip)");
04314              }
04315          }
04316 
04317       if (havebase || (havesib && (index != 4 || scale != 0)))
04318        {
04319          *obufp++ = open_char;
04320          if (intel_syntax && riprel)
04321            oappend ("rip + ");
04322          *obufp = '\0';
04323          if (havebase)
04324            oappend (address_mode == mode_64bit && (sizeflag & AFLAG)
04325                    ? names64[base] : names32[base]);
04326          if (havesib)
04327            {
04328              if (index != 4)
04329               {
04330                 if (!intel_syntax || havebase)
04331                   {
04332                     *obufp++ = separator_char;
04333                     *obufp = '\0';
04334                   }
04335                 oappend (address_mode == mode_64bit && (sizeflag & AFLAG)
04336                         ? names64[index] : names32[index]);
04337               }
04338              if (scale != 0 || (!intel_syntax && index != 4))
04339               {
04340                 *obufp++ = scale_char;
04341                 *obufp = '\0';
04342                 sprintf (scratchbuf, "%d", 1 << scale);
04343                 oappend (scratchbuf);
04344               }
04345            }
04346          if (intel_syntax && disp)
04347            {
04348              if ((bfd_signed_vma) disp > 0)
04349               {
04350                 *obufp++ = '+';
04351                 *obufp = '\0';
04352               }
04353              else if (mod != 1)
04354               {
04355                 *obufp++ = '-';
04356                 *obufp = '\0';
04357                 disp = - (bfd_signed_vma) disp;
04358               }
04359 
04360              print_operand_value (scratchbuf, mod != 1, disp);
04361              oappend (scratchbuf);
04362            }
04363 
04364          *obufp++ = close_char;
04365          *obufp = '\0';
04366        }
04367       else if (intel_syntax)
04368        {
04369          if (mod != 0 || (base & 7) == 5)
04370            {
04371              if (prefixes & (PREFIX_CS | PREFIX_SS | PREFIX_DS
04372                            | PREFIX_ES | PREFIX_FS | PREFIX_GS))
04373               ;
04374              else
04375               {
04376                 oappend (names_seg[ds_reg - es_reg]);
04377                 oappend (":");
04378               }
04379              print_operand_value (scratchbuf, 1, disp);
04380              oappend (scratchbuf);
04381            }
04382        }
04383     }
04384   else
04385     { /* 16 bit address mode */
04386       switch (mod)
04387        {
04388        case 0:
04389          if (rm == 6)
04390            {
04391              disp = get16 ();
04392              if ((disp & 0x8000) != 0)
04393               disp -= 0x10000;
04394            }
04395          break;
04396        case 1:
04397          FETCH_DATA (the_info, codep + 1);
04398          disp = *codep++;
04399          if ((disp & 0x80) != 0)
04400            disp -= 0x100;
04401          break;
04402        case 2:
04403          disp = get16 ();
04404          if ((disp & 0x8000) != 0)
04405            disp -= 0x10000;
04406          break;
04407        }
04408 
04409       if (!intel_syntax)
04410        if (mod != 0 || rm == 6)
04411          {
04412            print_operand_value (scratchbuf, 0, disp);
04413            oappend (scratchbuf);
04414          }
04415 
04416       if (mod != 0 || rm != 6)
04417        {
04418          *obufp++ = open_char;
04419          *obufp = '\0';
04420          oappend (index16[rm]);
04421          if (intel_syntax && disp)
04422            {
04423              if ((bfd_signed_vma) disp > 0)
04424               {
04425                 *obufp++ = '+';
04426                 *obufp = '\0';
04427               }
04428              else if (mod != 1)
04429               {
04430                 *obufp++ = '-';
04431                 *obufp = '\0';
04432                 disp = - (bfd_signed_vma) disp;
04433               }
04434 
04435              print_operand_value (scratchbuf, mod != 1, disp);
04436              oappend (scratchbuf);
04437            }
04438 
04439          *obufp++ = close_char;
04440          *obufp = '\0';
04441        }
04442       else if (intel_syntax)
04443        {
04444          if (prefixes & (PREFIX_CS | PREFIX_SS | PREFIX_DS
04445                        | PREFIX_ES | PREFIX_FS | PREFIX_GS))
04446            ;
04447          else
04448            {
04449              oappend (names_seg[ds_reg - es_reg]);
04450              oappend (":");
04451            }
04452          print_operand_value (scratchbuf, 1, disp & 0xffff);
04453          oappend (scratchbuf);
04454        }
04455     }
04456 }
04457 
04458 static void
04459 OP_G (int bytemode, int sizeflag)
04460 {
04461   int add = 0;
04462   USED_REX (REX_R);
04463   if (rex & REX_R)
04464     add += 8;
04465   switch (bytemode)
04466     {
04467     case b_mode:
04468       USED_REX (0);
04469       if (rex)
04470        oappend (names8rex[reg + add]);
04471       else
04472        oappend (names8[reg + add]);
04473       break;
04474     case w_mode:
04475       oappend (names16[reg + add]);
04476       break;
04477     case d_mode:
04478       oappend (names32[reg + add]);
04479       break;
04480     case q_mode:
04481       oappend (names64[reg + add]);
04482       break;
04483     case v_mode:
04484     case dq_mode:
04485     case dqw_mode:
04486       USED_REX (REX_W);
04487       if (rex & REX_W)
04488        oappend (names64[reg + add]);
04489       else if ((sizeflag & DFLAG) || bytemode != v_mode)
04490        oappend (names32[reg + add]);
04491       else
04492        oappend (names16[reg + add]);
04493       used_prefixes |= (prefixes & PREFIX_DATA);
04494       break;
04495     case m_mode:
04496       if (address_mode == mode_64bit)
04497        oappend (names64[reg + add]);
04498       else
04499        oappend (names32[reg + add]);
04500       break;
04501     default:
04502       oappend (INTERNAL_DISASSEMBLER_ERROR);
04503       break;
04504     }
04505 }
04506 
04507 static bfd_vma
04508 get64 (void)
04509 {
04510   bfd_vma x;
04511 #ifdef BFD64
04512   unsigned int a;
04513   unsigned int b;
04514 
04515   FETCH_DATA (the_info, codep + 8);
04516   a = *codep++ & 0xff;
04517   a |= (*codep++ & 0xff) << 8;
04518   a |= (*codep++ & 0xff) << 16;
04519   a |= (*codep++ & 0xff) << 24;
04520   b = *codep++ & 0xff;
04521   b |= (*codep++ & 0xff) << 8;
04522   b |= (*codep++ & 0xff) << 16;
04523   b |= (*codep++ & 0xff) << 24;
04524   x = a + ((bfd_vma) b << 32);
04525 #else
04526   abort ();
04527   x = 0;
04528 #endif
04529   return x;
04530 }
04531 
04532 static bfd_signed_vma
04533 get32 (void)
04534 {
04535   bfd_signed_vma x = 0;
04536 
04537   FETCH_DATA (the_info, codep + 4);
04538   x = *codep++ & (bfd_signed_vma) 0xff;
04539   x |= (*codep++ & (bfd_signed_vma) 0xff) << 8;
04540   x |= (*codep++ & (bfd_signed_vma) 0xff) << 16;
04541   x |= (*codep++ & (bfd_signed_vma) 0xff) << 24;
04542   return x;
04543 }
04544 
04545 static bfd_signed_vma
04546 get32s (void)
04547 {
04548   bfd_signed_vma x = 0;
04549 
04550   FETCH_DATA (the_info, codep + 4);
04551   x = *codep++ & (bfd_signed_vma) 0xff;
04552   x |= (*codep++ & (bfd_signed_vma) 0xff) << 8;
04553   x |= (*codep++ & (bfd_signed_vma) 0xff) << 16;
04554   x |= (*codep++ & (bfd_signed_vma) 0xff) << 24;
04555 
04556   x = (x ^ ((bfd_signed_vma) 1 << 31)) - ((bfd_signed_vma) 1 << 31);
04557 
04558   return x;
04559 }
04560 
04561 static int
04562 get16 (void)
04563 {
04564   int x = 0;
04565 
04566   FETCH_DATA (the_info, codep + 2);
04567   x = *codep++ & 0xff;
04568   x |= (*codep++ & 0xff) << 8;
04569   return x;
04570 }
04571 
04572 static void
04573 set_op (bfd_vma op, int riprel)
04574 {
04575   op_index[op_ad] = op_ad;
04576   if (address_mode == mode_64bit)
04577     {
04578       op_address[op_ad] = op;
04579       op_riprel[op_ad] = riprel;
04580     }
04581   else
04582     {
04583       /* Mask to get a 32-bit address.  */
04584       op_address[op_ad] = op & 0xffffffff;
04585       op_riprel[op_ad] = riprel & 0xffffffff;
04586     }
04587 }
04588 
04589 static void
04590 OP_REG (int code, int sizeflag)
04591 {
04592   const char *s;
04593   int add = 0;
04594   USED_REX (REX_B);
04595   if (rex & REX_B)
04596     add = 8;
04597 
04598   switch (code)
04599     {
04600     case ax_reg: case cx_reg: case dx_reg: case bx_reg:
04601     case sp_reg: case bp_reg: case si_reg: case di_reg:
04602       s = names16[code - ax_reg + add];
04603       break;
04604     case es_reg: case ss_reg: case cs_reg:
04605     case ds_reg: case fs_reg: case gs_reg:
04606       s = names_seg[code - es_reg + add];
04607       break;
04608     case al_reg: case ah_reg: case cl_reg: case ch_reg:
04609     case dl_reg: case dh_reg: case bl_reg: case bh_reg:
04610       USED_REX (0);
04611       if (rex)
04612        s = names8rex[code - al_reg + add];
04613       else
04614        s = names8[code - al_reg];
04615       break;
04616     case rAX_reg: case rCX_reg: case rDX_reg: case rBX_reg:
04617     case rSP_reg: case rBP_reg: case rSI_reg: case rDI_reg:
04618       if (address_mode == mode_64bit && (sizeflag & DFLAG))
04619        {
04620          s = names64[code - rAX_reg + add];
04621          break;
04622        }
04623       code += eAX_reg - rAX_reg;
04624       /* Fall through.  */
04625     case eAX_reg: case eCX_reg: case eDX_reg: case eBX_reg:
04626     case eSP_reg: case eBP_reg: case eSI_reg: case eDI_reg:
04627       USED_REX (REX_W);
04628       if (rex & REX_W)
04629        s = names64[code - eAX_reg + add];
04630       else if (sizeflag & DFLAG)
04631        s = names32[code - eAX_reg + add];
04632       else
04633        s = names16[code - eAX_reg + add];
04634       used_prefixes |= (prefixes & PREFIX_DATA);
04635       break;
04636     default:
04637       s = INTERNAL_DISASSEMBLER_ERROR;
04638       break;
04639     }
04640   oappend (s);
04641 }
04642 
04643 static void
04644 OP_IMREG (int code, int sizeflag)
04645 {
04646   const char *s;
04647 
04648   switch (code)
04649     {
04650     case indir_dx_reg:
04651       if (intel_syntax)
04652        s = "dx";
04653       else
04654        s = "(%dx)";
04655       break;
04656     case ax_reg: case cx_reg: case dx_reg: case bx_reg:
04657     case sp_reg: case bp_reg: case si_reg: case di_reg:
04658       s = names16[code - ax_reg];
04659       break;
04660     case es_reg: case ss_reg: case cs_reg:
04661     case ds_reg: case fs_reg: case gs_reg:
04662       s = names_seg[code - es_reg];
04663       break;
04664     case al_reg: case ah_reg: case cl_reg: case ch_reg:
04665     case dl_reg: case dh_reg: case bl_reg: case bh_reg:
04666       USED_REX (0);
04667       if (rex)
04668        s = names8rex[code - al_reg];
04669       else
04670        s = names8[code - al_reg];
04671       break;
04672     case eAX_reg: case eCX_reg: case eDX_reg: case eBX_reg:
04673     case eSP_reg: case eBP_reg: case eSI_reg: case eDI_reg:
04674       USED_REX (REX_W);
04675       if (rex & REX_W)
04676        s = names64[code - eAX_reg];
04677       else if (sizeflag & DFLAG)
04678        s = names32[code - eAX_reg];
04679       else
04680        s = names16[code - eAX_reg];
04681       used_prefixes |= (prefixes & PREFIX_DATA);
04682       break;
04683     case z_mode_ax_reg:
04684       if ((rex & REX_W) || (sizeflag & DFLAG))
04685        s = *names32;
04686       else
04687        s = *names16;
04688       if (!(rex & REX_W))
04689        used_prefixes |= (prefixes & PREFIX_DATA);
04690       break;
04691     default:
04692       s = INTERNAL_DISASSEMBLER_ERROR;
04693       break;
04694     }
04695   oappend (s);
04696 }
04697 
04698 static void
04699 OP_I (int bytemode, int sizeflag)
04700 {
04701   bfd_signed_vma op;
04702   bfd_signed_vma mask = -1;
04703 
04704   switch (bytemode)
04705     {
04706     case b_mode:
04707       FETCH_DATA (the_info, codep + 1);
04708       op = *codep++;
04709       mask = 0xff;
04710       break;
04711     case q_mode:
04712       if (address_mode == mode_64bit)
04713        {
04714          op = get32s ();
04715          break;
04716        }
04717       /* Fall through.  */
04718     case v_mode:
04719       USED_REX (REX_W);
04720       if (rex & REX_W)
04721        op = get32s ();
04722       else if (sizeflag & DFLAG)
04723        {
04724          op = get32 ();
04725          mask = 0xffffffff;
04726        }
04727       else
04728        {
04729          op = get16 ();
04730          mask = 0xfffff;
04731        }
04732       used_prefixes |= (prefixes & PREFIX_DATA);
04733       break;
04734     case w_mode:
04735       mask = 0xfffff;
04736       op = get16 ();
04737       break;
04738     case const_1_mode:
04739       if (intel_syntax)
04740         oappend ("1");
04741       return;
04742     default:
04743       oappend (INTERNAL_DISASSEMBLER_ERROR);
04744       return;
04745     }
04746 
04747   op &= mask;
04748   scratchbuf[0] = '$';
04749   print_operand_value (scratchbuf + 1, 1, op);
04750   oappend (scratchbuf + intel_syntax);
04751   scratchbuf[0] = '\0';
04752 }
04753 
04754 static void
04755 OP_I64 (int bytemode, int sizeflag)
04756 {
04757   bfd_signed_vma op;
04758   bfd_signed_vma mask = -1;
04759 
04760   if (address_mode != mode_64bit)
04761     {
04762       OP_I (bytemode, sizeflag);
04763       return;
04764     }
04765 
04766   switch (bytemode)
04767     {
04768     case b_mode:
04769       FETCH_DATA (the_info, codep + 1);
04770       op = *codep++;
04771       mask = 0xff;
04772       break;
04773     case v_mode:
04774       USED_REX (REX_W);
04775       if (rex & REX_W)
04776        op = get64 ();
04777       else if (sizeflag & DFLAG)
04778        {
04779          op = get32 ();
04780          mask = 0xffffffff;
04781        }
04782       else
04783        {
04784          op = get16 ();
04785          mask = 0xfffff;
04786        }
04787       used_prefixes |= (prefixes & PREFIX_DATA);
04788       break;
04789     case w_mode:
04790       mask = 0xfffff;
04791       op = get16 ();
04792       break;
04793     default:
04794       oappend (INTERNAL_DISASSEMBLER_ERROR);
04795       return;
04796     }
04797 
04798   op &= mask;
04799   scratchbuf[0] = '$';
04800   print_operand_value (scratchbuf + 1, 1, op);
04801   oappend (scratchbuf + intel_syntax);
04802   scratchbuf[0] = '\0';
04803 }
04804 
04805 static void
04806 OP_sI (int bytemode, int sizeflag)
04807 {
04808   bfd_signed_vma op;
04809   bfd_signed_vma mask = -1;
04810 
04811   switch (bytemode)
04812     {
04813     case b_mode:
04814       FETCH_DATA (the_info, codep + 1);
04815       op = *codep++;
04816       if ((op & 0x80) != 0)
04817        op -= 0x100;
04818       mask = 0xffffffff;
04819       break;
04820     case v_mode:
04821       USED_REX (REX_W);
04822       if (rex & REX_W)
04823        op = get32s ();
04824       else if (sizeflag & DFLAG)
04825        {
04826          op = get32s ();
04827          mask = 0xffffffff;
04828        }
04829       else
04830        {
04831          mask = 0xffffffff;
04832          op = get16 ();
04833          if ((op & 0x8000) != 0)
04834            op -= 0x10000;
04835        }
04836       used_prefixes |= (prefixes & PREFIX_DATA);
04837       break;
04838     case w_mode:
04839       op = get16 ();
04840       mask = 0xffffffff;
04841       if ((op & 0x8000) != 0)
04842        op -= 0x10000;
04843       break;
04844     default:
04845       oappend (INTERNAL_DISASSEMBLER_ERROR);
04846       return;
04847     }
04848 
04849   scratchbuf[0] = '$';
04850   print_operand_value (scratchbuf + 1, 1, op);
04851   oappend (scratchbuf + intel_syntax);
04852 }
04853 
04854 static void
04855 OP_J (int bytemode, int sizeflag)
04856 {
04857   bfd_vma disp;
04858   bfd_vma mask = -1;
04859   bfd_vma segment = 0;
04860 
04861   switch (bytemode)
04862     {
04863     case b_mode:
04864       FETCH_DATA (the_info, codep + 1);
04865       disp = *codep++;
04866       if ((disp & 0x80) != 0)
04867        disp -= 0x100;
04868       break;
04869     case v_mode:
04870       if ((sizeflag & DFLAG) || (rex & REX_W))
04871        disp = get32s ();
04872       else
04873        {
04874          disp = get16 ();
04875          if ((disp & 0x8000) != 0)
04876            disp -= 0x10000;
04877          /* In 16bit mode, address is wrapped around at 64k within
04878             the same segment.  Otherwise, a data16 prefix on a jump
04879             instruction means that the pc is masked to 16 bits after
04880             the displacement is added!  */
04881          mask = 0xffff;
04882          if ((prefixes & PREFIX_DATA) == 0)
04883            segment = ((start_pc + codep - start_codep)
04884                      & ~((bfd_vma) 0xffff));
04885        }
04886       used_prefixes |= (prefixes & PREFIX_DATA);
04887       break;
04888     default:
04889       oappend (INTERNAL_DISASSEMBLER_ERROR);
04890       return;
04891     }
04892   disp = ((start_pc + codep - start_codep + disp) & mask) | segment;
04893   set_op (disp, 0);
04894   print_operand_value (scratchbuf, 1, disp);
04895   oappend (scratchbuf);
04896 }
04897 
04898 static void
04899 OP_SEG (int bytemode, int sizeflag)
04900 {
04901   if (bytemode == w_mode)
04902     oappend (names_seg[reg]);
04903   else
04904     OP_E (mod == 3 ? bytemode : w_mode, sizeflag);
04905 }
04906 
04907 static void
04908 OP_DIR (int dummy ATTRIBUTE_UNUSED, int sizeflag)
04909 {
04910   int seg, offset;
04911 
04912   if (sizeflag & DFLAG)
04913     {
04914       offset = get32 ();
04915       seg = get16 ();
04916     }
04917   else
04918     {
04919       offset = get16 ();
04920       seg = get16 ();
04921     }
04922   used_prefixes |= (prefixes & PREFIX_DATA);
04923   if (intel_syntax)
04924     sprintf (scratchbuf, "0x%x:0x%x", seg, offset);
04925   else
04926     sprintf (scratchbuf, "$0x%x,$0x%x", seg, offset);
04927   oappend (scratchbuf);
04928 }
04929 
04930 static void
04931 OP_OFF (int bytemode, int sizeflag)
04932 {
04933   bfd_vma off;
04934 
04935   if (intel_syntax && (sizeflag & SUFFIX_ALWAYS))
04936     intel_operand_size (bytemode, sizeflag);
04937   append_seg ();
04938 
04939   if ((sizeflag & AFLAG) || address_mode == mode_64bit)
04940     off = get32 ();
04941   else
04942     off = get16 ();
04943 
04944   if (intel_syntax)
04945     {
04946       if (!(prefixes & (PREFIX_CS | PREFIX_SS | PREFIX_DS
04947                      | PREFIX_ES | PREFIX_FS | PREFIX_GS)))
04948        {
04949          oappend (names_seg[ds_reg - es_reg]);
04950          oappend (":");
04951        }
04952     }
04953   print_operand_value (scratchbuf, 1, off);
04954   oappend (scratchbuf);
04955 }
04956 
04957 static void
04958 OP_OFF64 (int bytemode, int sizeflag)
04959 {
04960   bfd_vma off;
04961 
04962   if (address_mode != mode_64bit
04963       || (prefixes & PREFIX_ADDR))
04964     {
04965       OP_OFF (bytemode, sizeflag);
04966       return;
04967     }
04968 
04969   if (intel_syntax && (sizeflag & SUFFIX_ALWAYS))
04970     intel_operand_size (bytemode, sizeflag);
04971   append_seg ();
04972 
04973   off = get64 ();
04974 
04975   if (intel_syntax)
04976     {
04977       if (!(prefixes & (PREFIX_CS | PREFIX_SS | PREFIX_DS
04978                      | PREFIX_ES | PREFIX_FS | PREFIX_GS)))
04979        {
04980          oappend (names_seg[ds_reg - es_reg]);
04981          oappend (":");
04982        }
04983     }
04984   print_operand_value (scratchbuf, 1, off);
04985   oappend (scratchbuf);
04986 }
04987 
04988 static void
04989 ptr_reg (int code, int sizeflag)
04990 {
04991   const char *s;
04992 
04993   *obufp++ = open_char;
04994   used_prefixes |= (prefixes & PREFIX_ADDR);
04995   if (address_mode == mode_64bit)
04996     {
04997       if (!(sizeflag & AFLAG))
04998        s = names32[code - eAX_reg];
04999       else
05000        s = names64[code - eAX_reg];
05001     }
05002   else if (sizeflag & AFLAG)
05003     s = names32[code - eAX_reg];
05004   else
05005     s = names16[code - eAX_reg];
05006   oappend (s);
05007   *obufp++ = close_char;
05008   *obufp = 0;
05009 }
05010 
05011 static void
05012 OP_ESreg (int code, int sizeflag)
05013 {
05014   if (intel_syntax)
05015     {
05016       switch (codep[-1])
05017        {
05018        case 0x6d:    /* insw/insl */
05019          intel_operand_size (z_mode, sizeflag);
05020          break;
05021        case 0xa5:    /* movsw/movsl/movsq */
05022        case 0xa7:    /* cmpsw/cmpsl/cmpsq */
05023        case 0xab:    /* stosw/stosl */
05024        case 0xaf:    /* scasw/scasl */
05025          intel_operand_size (v_mode, sizeflag);
05026          break;
05027        default:
05028          intel_operand_size (b_mode, sizeflag);
05029        }
05030     }
05031   oappend ("%es:" + intel_syntax);
05032   ptr_reg (code, sizeflag);
05033 }
05034 
05035 static void
05036 OP_DSreg (int code, int sizeflag)
05037 {
05038   if (intel_syntax)
05039     {
05040       switch (codep[-1])
05041        {
05042        case 0x6f:    /* outsw/outsl */
05043          intel_operand_size (z_mode, sizeflag);
05044          break;
05045        case 0xa5:    /* movsw/movsl/movsq */
05046        case 0xa7:    /* cmpsw/cmpsl/cmpsq */
05047        case 0xad:    /* lodsw/lodsl/lodsq */
05048          intel_operand_size (v_mode, sizeflag);
05049          break;
05050        default:
05051          intel_operand_size (b_mode, sizeflag);
05052        }
05053     }
05054   if ((prefixes
05055        & (PREFIX_CS
05056          | PREFIX_DS
05057          | PREFIX_SS
05058          | PREFIX_ES
05059          | PREFIX_FS
05060          | PREFIX_GS)) == 0)
05061     prefixes |= PREFIX_DS;
05062   append_seg ();
05063   ptr_reg (code, sizeflag);
05064 }
05065 
05066 static void
05067 OP_C (int dummy ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05068 {
05069   int add = 0;
05070   if (rex & REX_R)
05071     {
05072       USED_REX (REX_R);
05073       add = 8;
05074     }
05075   else if (address_mode != mode_64bit && (prefixes & PREFIX_LOCK))
05076     {
05077       used_prefixes |= PREFIX_LOCK;
05078       add = 8;
05079     }
05080   sprintf (scratchbuf, "%%cr%d", reg + add);
05081   oappend (scratchbuf + intel_syntax);
05082 }
05083 
05084 static void
05085 OP_D (int dummy ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05086 {
05087   int add = 0;
05088   USED_REX (REX_R);
05089   if (rex & REX_R)
05090     add = 8;
05091   if (intel_syntax)
05092     sprintf (scratchbuf, "db%d", reg + add);
05093   else
05094     sprintf (scratchbuf, "%%db%d", reg + add);
05095   oappend (scratchbuf);
05096 }
05097 
05098 static void
05099 OP_T (int dummy ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05100 {
05101   sprintf (scratchbuf, "%%tr%d", reg);
05102   oappend (scratchbuf + intel_syntax);
05103 }
05104 
05105 static void
05106 OP_R (int bytemode, int sizeflag)
05107 {
05108   if (mod == 3)
05109     OP_E (bytemode, sizeflag);
05110   else
05111     BadOp ();
05112 }
05113 
05114 static void
05115 OP_MMX (int bytemode ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05116 {
05117   used_prefixes |= (prefixes & PREFIX_DATA);
05118   if (prefixes & PREFIX_DATA)
05119     {
05120       int add = 0;
05121       USED_REX (REX_R);
05122       if (rex & REX_R)
05123        add = 8;
05124       sprintf (scratchbuf, "%%xmm%d", reg + add);
05125     }
05126   else
05127     sprintf (scratchbuf, "%%mm%d", reg);
05128   oappend (scratchbuf + intel_syntax);
05129 }
05130 
05131 static void
05132 OP_XMM (int bytemode ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05133 {
05134   int add = 0;
05135   USED_REX (REX_R);
05136   if (rex & REX_R)
05137     add = 8;
05138   sprintf (scratchbuf, "%%xmm%d", reg + add);
05139   oappend (scratchbuf + intel_syntax);
05140 }
05141 
05142 static void
05143 OP_EM (int bytemode, int sizeflag)
05144 {
05145   if (mod != 3)
05146     {
05147       if (intel_syntax && bytemode == v_mode)
05148        {
05149          bytemode = (prefixes & PREFIX_DATA) ? x_mode : q_mode;
05150          used_prefixes |= (prefixes & PREFIX_DATA);
05151        }
05152       OP_E (bytemode, sizeflag);
05153       return;
05154     }
05155 
05156   /* Skip mod/rm byte.  */
05157   MODRM_CHECK;
05158   codep++;
05159   used_prefixes |= (prefixes & PREFIX_DATA);
05160   if (prefixes & PREFIX_DATA)
05161     {
05162       int add = 0;
05163 
05164       USED_REX (REX_B);
05165       if (rex & REX_B)
05166        add = 8;
05167       sprintf (scratchbuf, "%%xmm%d", rm + add);
05168     }
05169   else
05170     sprintf (scratchbuf, "%%mm%d", rm);
05171   oappend (scratchbuf + intel_syntax);
05172 }
05173 
05174 /* cvt* are the only instructions in sse2 which have 
05175    both SSE and MMX operands and also have 0x66 prefix 
05176    in their opcode. 0x66 was originally used to differentiate 
05177    between SSE and MMX instruction(operands). So we have to handle the 
05178    cvt* separately using OP_EMC and OP_MXC */
05179 static void
05180 OP_EMC (int bytemode, int sizeflag)
05181 {
05182   if (mod != 3)
05183     {
05184       if (intel_syntax && bytemode == v_mode)
05185        {
05186          bytemode = (prefixes & PREFIX_DATA) ? x_mode : q_mode;
05187          used_prefixes |= (prefixes & PREFIX_DATA);
05188        }
05189       OP_E (bytemode, sizeflag);
05190       return;
05191     }
05192   
05193   /* Skip mod/rm byte.  */
05194   MODRM_CHECK;
05195   codep++;
05196   used_prefixes |= (prefixes & PREFIX_DATA);
05197   sprintf (scratchbuf, "%%mm%d", rm);
05198   oappend (scratchbuf + intel_syntax);
05199 }
05200 
05201 static void
05202 OP_MXC (int bytemode ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05203 {
05204   used_prefixes |= (prefixes & PREFIX_DATA);
05205   sprintf (scratchbuf, "%%mm%d", reg);
05206   oappend (scratchbuf + intel_syntax);
05207 }
05208 
05209 static void
05210 OP_EX (int bytemode, int sizeflag)
05211 {
05212   int add = 0;
05213   if (mod != 3)
05214     {
05215       if (intel_syntax && bytemode == v_mode)
05216        {
05217          switch (prefixes & (PREFIX_DATA|PREFIX_REPZ|PREFIX_REPNZ))
05218            {
05219            case 0:            bytemode = x_mode; break;
05220            case PREFIX_REPZ:  bytemode = d_mode; used_prefixes |= PREFIX_REPZ;  break;
05221            case PREFIX_DATA:  bytemode = x_mode; used_prefixes |= PREFIX_DATA;  break;
05222            case PREFIX_REPNZ: bytemode = q_mode; used_prefixes |= PREFIX_REPNZ; break;
05223            default:           bytemode = 0; break;
05224            }
05225        }
05226       OP_E (bytemode, sizeflag);
05227       return;
05228     }
05229   USED_REX (REX_B);
05230   if (rex & REX_B)
05231     add = 8;
05232 
05233   /* Skip mod/rm byte.  */
05234   MODRM_CHECK;
05235   codep++;
05236   sprintf (scratchbuf, "%%xmm%d", rm + add);
05237   oappend (scratchbuf + intel_syntax);
05238 }
05239 
05240 static void
05241 OP_MS (int bytemode, int sizeflag)
05242 {
05243   if (mod == 3)
05244     OP_EM (bytemode, sizeflag);
05245   else
05246     BadOp ();
05247 }
05248 
05249 static void
05250 OP_XS (int bytemode, int sizeflag)
05251 {
05252   if (mod == 3)
05253     OP_EX (bytemode, sizeflag);
05254   else
05255     BadOp ();
05256 }
05257 
05258 static void
05259 OP_M (int bytemode, int sizeflag)
05260 {
05261   if (mod == 3)
05262     /* bad bound,lea,lds,les,lfs,lgs,lss,cmpxchg8b,vmptrst modrm */
05263     BadOp ();
05264   else
05265     OP_E (bytemode, sizeflag);
05266 }
05267 
05268 static void
05269 OP_0f07 (int bytemode, int sizeflag)
05270 {
05271   if (mod != 3 || rm != 0)
05272     BadOp ();
05273   else
05274     OP_E (bytemode, sizeflag);
05275 }
05276 
05277 static void
05278 OP_0fae (int bytemode, int sizeflag)
05279 {
05280   if (mod == 3)
05281     {
05282       if (reg == 7)
05283        strcpy (obuf + strlen (obuf) - sizeof ("clflush") + 1, "sfence");
05284 
05285       if (reg < 5 || rm != 0)
05286        {
05287          BadOp ();   /* bad sfence, mfence, or lfence */
05288          return;
05289        }
05290     }
05291   else if (reg != 7)
05292     {
05293       BadOp ();             /* bad clflush */
05294       return;
05295     }
05296 
05297   OP_E (bytemode, sizeflag);
05298 }
05299 
05300 /* NOP is an alias of "xchg %ax,%ax" in 16bit mode, "xchg %eax,%eax" in
05301    32bit mode and "xchg %rax,%rax" in 64bit mode.  */  
05302 
05303 static void
05304 NOP_Fixup1 (int bytemode, int sizeflag)
05305 {
05306   if ((prefixes & PREFIX_DATA) != 0
05307       || (rex != 0
05308          && rex != 0x48
05309          && address_mode == mode_64bit))
05310     OP_REG (bytemode, sizeflag);
05311   else
05312     strcpy (obuf, "nop");
05313 }
05314 
05315 static void
05316 NOP_Fixup2 (int bytemode, int sizeflag)
05317 {
05318   if ((prefixes & PREFIX_DATA) != 0
05319       || (rex != 0
05320          && rex != 0x48
05321          && address_mode == mode_64bit))
05322     OP_IMREG (bytemode, sizeflag);
05323 }
05324 
05325 static const char *const Suffix3DNow[] = {
05326 /* 00 */      NULL,         NULL,         NULL,         NULL,
05327 /* 04 */      NULL,         NULL,         NULL,         NULL,
05328 /* 08 */      NULL,         NULL,         NULL,         NULL,
05329 /* 0C */      "pi2fw",      "pi2fd",      NULL,         NULL,
05330 /* 10 */      NULL,         NULL,         NULL,         NULL,
05331 /* 14 */      NULL,         NULL,         NULL,         NULL,
05332 /* 18 */      NULL,         NULL,         NULL,         NULL,
05333 /* 1C */      "pf2iw",      "pf2id",      NULL,         NULL,
05334 /* 20 */      NULL,         NULL,         NULL,         NULL,
05335 /* 24 */      NULL,         NULL,         NULL,         NULL,
05336 /* 28 */      NULL,         NULL,         NULL,         NULL,
05337 /* 2C */      NULL,         NULL,         NULL,         NULL,
05338 /* 30 */      NULL,         NULL,         NULL,         NULL,
05339 /* 34 */      NULL,         NULL,         NULL,         NULL,
05340 /* 38 */      NULL,         NULL,         NULL,         NULL,
05341 /* 3C */      NULL,         NULL,         NULL,         NULL,
05342 /* 40 */      NULL,         NULL,         NULL,         NULL,
05343 /* 44 */      NULL,         NULL,         NULL,         NULL,
05344 /* 48 */      NULL,         NULL,         NULL,         NULL,
05345 /* 4C */      NULL,         NULL,         NULL,         NULL,
05346 /* 50 */      NULL,         NULL,         NULL,         NULL,
05347 /* 54 */      NULL,         NULL,         NULL,         NULL,
05348 /* 58 */      NULL,         NULL,         NULL,         NULL,
05349 /* 5C */      NULL,         NULL,         NULL,         NULL,
05350 /* 60 */      NULL,         NULL,         NULL,         NULL,
05351 /* 64 */      NULL,         NULL,         NULL,         NULL,
05352 /* 68 */      NULL,         NULL,         NULL,         NULL,
05353 /* 6C */      NULL,         NULL,         NULL,         NULL,
05354 /* 70 */      NULL,         NULL,         NULL,         NULL,
05355 /* 74 */      NULL,         NULL,         NULL,         NULL,
05356 /* 78 */      NULL,         NULL,         NULL,         NULL,
05357 /* 7C */      NULL,         NULL,         NULL,         NULL,
05358 /* 80 */      NULL,         NULL,         NULL,         NULL,
05359 /* 84 */      NULL,         NULL,         NULL,         NULL,
05360 /* 88 */      NULL,         NULL,         "pfnacc",     NULL,
05361 /* 8C */      NULL,         NULL,         "pfpnacc",    NULL,
05362 /* 90 */      "pfcmpge",    NULL,         NULL,         NULL,
05363 /* 94 */      "pfmin",      NULL,         "pfrcp",      "pfrsqrt",
05364 /* 98 */      NULL,         NULL,         "pfsub",      NULL,
05365 /* 9C */      NULL,         NULL,         "pfadd",      NULL,
05366 /* A0 */      "pfcmpgt",    NULL,         NULL,         NULL,
05367 /* A4 */      "pfmax",      NULL,         "pfrcpit1",   "pfrsqit1",
05368 /* A8 */      NULL,         NULL,         "pfsubr",     NULL,
05369 /* AC */      NULL,         NULL,         "pfacc",      NULL,
05370 /* B0 */      "pfcmpeq",    NULL,         NULL,         NULL,
05371 /* B4 */      "pfmul",      NULL,         "pfrcpit2",   "pfmulhrw",
05372 /* B8 */      NULL,         NULL,         NULL,         "pswapd",
05373 /* BC */      NULL,         NULL,         NULL,         "pavgusb",
05374 /* C0 */      NULL,         NULL,         NULL,         NULL,
05375 /* C4 */      NULL,         NULL,         NULL,         NULL,
05376 /* C8 */      NULL,         NULL,         NULL,         NULL,
05377 /* CC */      NULL,         NULL,         NULL,         NULL,
05378 /* D0 */      NULL,         NULL,         NULL,         NULL,
05379 /* D4 */      NULL,         NULL,         NULL,         NULL,
05380 /* D8 */      NULL,         NULL,         NULL,         NULL,
05381 /* DC */      NULL,         NULL,         NULL,         NULL,
05382 /* E0 */      NULL,         NULL,         NULL,         NULL,
05383 /* E4 */      NULL,         NULL,         NULL,         NULL,
05384 /* E8 */      NULL,         NULL,         NULL,         NULL,
05385 /* EC */      NULL,         NULL,         NULL,         NULL,
05386 /* F0 */      NULL,         NULL,         NULL,         NULL,
05387 /* F4 */      NULL,         NULL,         NULL,         NULL,
05388 /* F8 */      NULL,         NULL,         NULL,         NULL,
05389 /* FC */      NULL,         NULL,         NULL,         NULL,
05390 };
05391 
05392 static void
05393 OP_3DNowSuffix (int bytemode ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05394 {
05395   const char *mnemonic;
05396 
05397   FETCH_DATA (the_info, codep + 1);
05398   /* AMD 3DNow! instructions are specified by an opcode suffix in the
05399      place where an 8-bit immediate would normally go.  ie. the last
05400      byte of the instruction.  */
05401   obufp = obuf + strlen (obuf);
05402   mnemonic = Suffix3DNow[*codep++ & 0xff];
05403   if (mnemonic)
05404     oappend (mnemonic);
05405   else
05406     {
05407       /* Since a variable sized modrm/sib chunk is between the start
05408         of the opcode (0x0f0f) and the opcode suffix, we need to do
05409         all the modrm processing first, and don't know until now that
05410         we have a bad opcode.  This necessitates some cleaning up.  */
05411       op_out[0][0] = '\0';
05412       op_out[1][0] = '\0';
05413       BadOp ();
05414     }
05415 }
05416 
05417 static const char *simd_cmp_op[] = {
05418   "eq",
05419   "lt",
05420   "le",
05421   "unord",
05422   "neq",
05423   "nlt",
05424   "nle",
05425   "ord"
05426 };
05427 
05428 static void
05429 OP_SIMD_Suffix (int bytemode ATTRIBUTE_UNUSED, int sizeflag ATTRIBUTE_UNUSED)
05430 {
05431   unsigned int cmp_type;
05432 
05433   FETCH_DATA (the_info, codep + 1);
05434   obufp = obuf + strlen (obuf);
05435   cmp_type = *codep++ & 0xff;
05436   if (cmp_type < 8)
05437     {
05438       char suffix1 = 'p', suffix2 = 's';
05439       used_prefixes |= (prefixes & PREFIX_REPZ);
05440       if (prefixes & PREFIX_REPZ)
05441        suffix1 = 's';
05442       else
05443        {
05444          used_prefixes |= (prefixes & PREFIX_DATA);
05445          if (prefixes & PREFIX_DATA)
05446            suffix2 = 'd';
05447          else
05448            {
05449              used_prefixes |= (prefixes & PREFIX_REPNZ);
05450              if (prefixes & PREFIX_REPNZ)
05451               suffix1 = 's', suffix2 = 'd';
05452            }
05453        }
05454       sprintf (scratchbuf, "cmp%s%c%c",
05455               simd_cmp_op[cmp_type], suffix1, suffix2);
05456       used_prefixes |= (prefixes & PREFIX_REPZ);
05457       oappend (scratchbuf);
05458     }
05459   else
05460     {
05461       /* We have a bad extension byte.  Clean up.  */
05462       op_out[0][0] = '\0';
05463       op_out[1][0] = '\0';
05464       BadOp ();
05465     }
05466 }
05467 
05468 static void
05469 SIMD_Fixup (int extrachar, int sizeflag ATTRIBUTE_UNUSED)
05470 {
05471   /* Change movlps/movhps to movhlps/movlhps for 2 register operand
05472      forms of these instructions.  */
05473   if (mod == 3)
05474     {
05475       char *p = obuf + strlen (obuf);
05476       *(p + 1) = '\0';
05477       *p       = *(p - 1);
05478       *(p - 1) = *(p - 2);
05479       *(p - 2) = *(p - 3);
05480       *(p - 3) = extrachar;
05481     }
05482 }
05483 
05484 static void
05485 PNI_Fixup (int extrachar ATTRIBUTE_UNUSED, int sizeflag)
05486 {
05487   if (mod == 3 && reg == 1 && rm <= 1)
05488     {
05489       /* Override "sidt".  */
05490       size_t olen = strlen (obuf);
05491       char *p = obuf + olen - 4;
05492       const char **names = (address_mode == mode_64bit
05493                          ? names64 : names32);
05494 
05495       /* We might have a suffix when disassembling with -Msuffix.  */
05496       if (*p == 'i')
05497        --p;
05498 
05499       /* Remove "addr16/addr32" if we aren't in Intel mode.  */
05500       if (!intel_syntax
05501          && (prefixes & PREFIX_ADDR)
05502          && olen >= (4 + 7)
05503          && *(p - 1) == ' '
05504          && CONST_STRNEQ (p - 7, "addr")
05505          && (CONST_STRNEQ (p - 3, "16")
05506              || CONST_STRNEQ (p - 3, "32")))
05507        p -= 7;
05508 
05509       if (rm)
05510        {
05511          /* mwait %eax,%ecx  */
05512          strcpy (p, "mwait");
05513          if (!intel_syntax)
05514            strcpy (op_out[0], names[0]);
05515        }
05516       else
05517        {
05518          /* monitor %eax,%ecx,%edx"  */
05519          strcpy (p, "monitor");
05520          if (!intel_syntax)
05521            {
05522              const char **op1_names;
05523              if (!(prefixes & PREFIX_ADDR))
05524               op1_names = (address_mode == mode_16bit
05525                           ? names16 : names);
05526              else
05527               {
05528                 op1_names = (address_mode != mode_32bit
05529                             ? names32 : names16);
05530                 used_prefixes |= PREFIX_ADDR;
05531               }
05532              strcpy (op_out[0], op1_names[0]);
05533              strcpy (op_out[2], names[2]);
05534            }
05535        }
05536       if (!intel_syntax)
05537        {
05538          strcpy (op_out[1], names[1]);
05539          two_source_ops = 1;
05540        }
05541 
05542       codep++;
05543     }
05544   else
05545     OP_M (0, sizeflag);
05546 }
05547 
05548 static void
05549 SVME_Fixup (int bytemode, int sizeflag)
05550 {
05551   const char *alt;
05552   char *p;
05553 
05554   switch (*codep)
05555     {
05556     case 0xd8:
05557       alt = "vmrun";
05558       break;
05559     case 0xd9:
05560       alt = "vmmcall";
05561       break;
05562     case 0xda:
05563       alt = "vmload";
05564       break;
05565     case 0xdb:
05566       alt = "vmsave";
05567       break;
05568     case 0xdc:
05569       alt = "stgi";
05570       break;
05571     case 0xdd:
05572       alt = "clgi";
05573       break;
05574     case 0xde:
05575       alt = "skinit";
05576       break;
05577     case 0xdf:
05578       alt = "invlpga";
05579       break;
05580     default:
05581       OP_M (bytemode, sizeflag);
05582       return;
05583     }
05584   /* Override "lidt".  */
05585   p = obuf + strlen (obuf) - 4;
05586   /* We might have a suffix.  */
05587   if (*p == 'i')
05588     --p;
05589   strcpy (p, alt);
05590   if (!(prefixes & PREFIX_ADDR))
05591     {
05592       ++codep;
05593       return;
05594     }
05595   used_prefixes |= PREFIX_ADDR;
05596   switch (*codep++)
05597     {
05598     case 0xdf:
05599       strcpy (op_out[1], names32[1]);
05600       two_source_ops = 1;
05601          /* Fall through.  */
05602     case 0xd8:
05603     case 0xda:
05604     case 0xdb:
05605       *obufp++ = open_char;
05606       if (address_mode == mode_64bit || (sizeflag & AFLAG))
05607         alt = names32[0];
05608       else
05609         alt = names16[0];
05610       strcpy (obufp, alt);
05611       obufp += strlen (alt);
05612       *obufp++ = close_char;
05613       *obufp = '\0';
05614       break;
05615     }
05616 }
05617 
05618 static void
05619 INVLPG_Fixup (int bytemode, int sizeflag)
05620 {
05621   const char *alt;
05622 
05623   switch (*codep)
05624     {
05625     case 0xf8:
05626       alt = "swapgs";
05627       break;
05628     case 0xf9:
05629       alt = "rdtscp";
05630       break;
05631     default:
05632       OP_M (bytemode, sizeflag);
05633       return;
05634     }
05635   /* Override "invlpg".  */
05636   strcpy (obuf + strlen (obuf) - 6, alt);
05637   codep++;
05638 }
05639 
05640 static void
05641 BadOp (void)
05642 {
05643   /* Throw away prefixes and 1st. opcode byte.  */
05644   codep = insn_codep + 1;
05645   oappend ("(bad)");
05646 }
05647 
05648 static void
05649 VMX_Fixup (int extrachar ATTRIBUTE_UNUSED, int sizeflag)
05650 {
05651   if (mod == 3 && reg == 0 && rm >=1 && rm <= 4)
05652     {
05653       /* Override "sgdt".  */
05654       char *p = obuf + strlen (obuf) - 4;
05655 
05656       /* We might have a suffix when disassembling with -Msuffix.  */
05657       if (*p == 'g')
05658        --p;
05659 
05660       switch (rm)
05661        {
05662        case 1:
05663          strcpy (p, "vmcall");
05664          break;
05665        case 2:
05666          strcpy (p, "vmlaunch");
05667          break;
05668        case 3:
05669          strcpy (p, "vmresume");
05670          break;
05671        case 4:
05672          strcpy (p, "vmxoff");
05673          break;
05674        }
05675 
05676       codep++;
05677     }
05678   else
05679     OP_E (0, sizeflag);
05680 }
05681 
05682 static void
05683 OP_VMX (int bytemode, int sizeflag)
05684 {
05685   used_prefixes |= (prefixes & (PREFIX_DATA | PREFIX_REPZ));
05686   if (prefixes & PREFIX_DATA)
05687     strcpy (obuf, "vmclear");
05688   else if (prefixes & PREFIX_REPZ)
05689     strcpy (obuf, "vmxon");
05690   else
05691     strcpy (obuf, "vmptrld");
05692   OP_E (bytemode, sizeflag);
05693 }
05694 
05695 static void
05696 REP_Fixup (int bytemode, int sizeflag)
05697 {
05698   /* The 0xf3 prefix should be displayed as "rep" for ins, outs, movs,
05699      lods and stos.  */
05700   size_t ilen = 0;
05701 
05702   if (prefixes & PREFIX_REPZ)
05703     switch (*insn_codep) 
05704       {
05705       case 0x6e:     /* outsb */
05706       case 0x6f:     /* outsw/outsl */
05707       case 0xa4:     /* movsb */
05708       case 0xa5:     /* movsw/movsl/movsq */
05709        if (!intel_syntax)
05710          ilen = 5;
05711        else
05712          ilen = 4;
05713        break;
05714       case 0xaa:     /* stosb */
05715       case 0xab:     /* stosw/stosl/stosq */
05716       case 0xac:     /* lodsb */
05717       case 0xad:     /* lodsw/lodsl/lodsq */
05718        if (!intel_syntax && (sizeflag & SUFFIX_ALWAYS))
05719          ilen = 5;
05720        else
05721          ilen = 4;
05722        break;
05723       case 0x6c:     /* insb */
05724       case 0x6d:     /* insl/insw */
05725        if (!intel_syntax)
05726          ilen = 4;
05727        else
05728          ilen = 3;
05729        break;
05730       default:
05731        abort ();
05732        break;
05733       }
05734 
05735   if (ilen != 0)
05736     {
05737       size_t olen;
05738       char *p;
05739 
05740       olen = strlen (obuf);
05741       p = obuf + olen - ilen - 1 - 4;
05742       /* Handle "repz [addr16|addr32]".  */
05743       if ((prefixes & PREFIX_ADDR))
05744        p -= 1 + 6;
05745 
05746       memmove (p + 3, p + 4, olen - (p + 3 - obuf));
05747     }
05748 
05749   switch (bytemode)
05750     {
05751     case al_reg:
05752     case eAX_reg:
05753     case indir_dx_reg:
05754       OP_IMREG (bytemode, sizeflag);
05755       break;
05756     case eDI_reg:
05757       OP_ESreg (bytemode, sizeflag);
05758       break;
05759     case eSI_reg:
05760       OP_DSreg (bytemode, sizeflag);
05761       break;
05762     default:
05763       abort ();
05764       break;
05765     }
05766 }
05767 
05768 static void
05769 CMPXCHG8B_Fixup (int bytemode, int sizeflag)
05770 {
05771   USED_REX (REX_W);
05772   if (rex & REX_W)
05773     {
05774       /* Change cmpxchg8b to cmpxchg16b.  */
05775       char *p = obuf + strlen (obuf) - 2;
05776       strcpy (p, "16b");
05777       bytemode = o_mode;
05778     }
05779   OP_M (bytemode, sizeflag);
05780 }