- Fixed bug with missed ES segment override prefix

- Correctly disassemble x86-64 opcodes

	Ia_cvttsd2si_Gq_Wsd
	Ia_cvttss2si_Gq_Wss
	Ia_cvtsd2si_Gq_Wsd
	Ia_cvtss2si_Gq_Wss
	Ia_movq_Pq_Eq
	Ia_movq_Vdq_Eq
	Ia_movq_Eq_Pq
	Ia_movq_Eq_Vq

- Correctly disassemble Intel SSE3 opcodes (not supported by Bochs)
	Ia_monitor
	Ia_mwait
This commit is contained in:
Stanislav Shwartsman 2006-01-31 17:42:31 +00:00
parent 24c27deae8
commit 24d4de03a1
4 changed files with 72 additions and 21 deletions

View File

@ -366,7 +366,7 @@ void disassembler::OP_O(const x86_insn *insn, unsigned size)
{
const char *seg;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = segment_name[DS_REG];
@ -427,7 +427,7 @@ void disassembler::OP_X(const x86_insn *insn, unsigned size)
rsi = general_16bit_regname[rSI_REG];
}
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = segment_name[DS_REG];

View File

@ -99,6 +99,13 @@ static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f2c[4] = {
/* F3 */ { 0, &Ia_cvttss2si_Gd_Wss }
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f2cQ[4] = {
/* -- */ { 0, &Ia_cvttps2pi_Pq_Wps },
/* 66 */ { 0, &Ia_cvttpd2pi_Pq_Wpd },
/* F2 */ { 0, &Ia_cvttsd2si_Gq_Wsd },
/* F3 */ { 0, &Ia_cvttss2si_Gq_Wss }
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f2d[4] = {
/* -- */ { 0, &Ia_cvtps2pi_Pq_Wps },
/* 66 */ { 0, &Ia_cvtpd2pi_Pq_Wpd },
@ -106,6 +113,13 @@ static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f2d[4] = {
/* F3 */ { 0, &Ia_cvtss2si_Gd_Wss }
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f2dQ[4] = {
/* -- */ { 0, &Ia_cvtps2pi_Pq_Wps },
/* 66 */ { 0, &Ia_cvtpd2pi_Pq_Wpd },
/* F2 */ { 0, &Ia_cvtsd2si_Gq_Wsd },
/* F3 */ { 0, &Ia_cvtss2si_Gq_Wss }
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f2e[4] = {
/* -- */ { 0, &Ia_ucomiss_Vss_Wss },
/* 66 */ { 0, &Ia_ucomisd_Vsd_Wss },
@ -337,6 +351,13 @@ static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f6e[4] = {
/* F3 */ { 0, &Ia_Invalid }
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f6eQ[4] = {
/* -- */ { 0, &Ia_movq_Pq_Eq },
/* 66 */ { 0, &Ia_movq_Vdq_Eq },
/* F2 */ { 0, &Ia_Invalid },
/* F3 */ { 0, &Ia_Invalid }
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f6f[4] = {
/* -- */ { 0, &Ia_movq_Pq_Qq },
/* 66 */ { 0, &Ia_movdqa_Vdq_Wdq },
@ -393,6 +414,13 @@ static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f7e[4] = {
/* F3 */ { 0, &Ia_movq_Vq_Wq },
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f7eQ[4] = {
/* -- */ { 0, &Ia_movq_Eq_Pq },
/* 66 */ { 0, &Ia_movq_Eq_Vq },
/* F2 */ { 0, &Ia_Invalid },
/* F3 */ { 0, &Ia_movq_Vq_Wq },
};
static BxDisasmOpcodeTable_t BxDisasmGroupSSE_0f7f[4] = {
/* -- */ { 0, &Ia_movq_Qq_Pq },
/* 66 */ { 0, &Ia_movdqa_Wdq_Vdq },
@ -1180,11 +1208,27 @@ static BxDisasmOpcodeTable_t BxDisasmGroupModINVLPG[2] = {
/* M */ { 0, &Ia_invlpg }
};
static BxDisasmOpcodeTable_t BxDisasmGroupRmSIDT[8] = {
/* 0 */ { 0, &Ia_monitor },
/* 1 */ { 0, &Ia_mwait },
/* 2 */ { 0, &Ia_Invalid },
/* 3 */ { 0, &Ia_Invalid },
/* 4 */ { 0, &Ia_Invalid },
/* 5 */ { 0, &Ia_Invalid },
/* 6 */ { 0, &Ia_Invalid },
/* 7 */ { 0, &Ia_Invalid },
};
static BxDisasmOpcodeTable_t BxDisasmGroupModSIDT[2] = {
/* R */ { GRPRM(SIDT) },
/* M */ { 0, &Ia_sidt }
};
static BxDisasmOpcodeTable_t BxDisasmGroupG7[8] = {
/* 0 */ { 0, &Ia_sgdt },
/* 1 */ { 0, &Ia_sidt },
/* 2 */ { 0, &Ia_lgdt },
/* 3 */ { 0, &Ia_lidt },
/* 0 */ { 0, &Ia_sgdt },
/* 1 */ { GRPMOD(SIDT) },
/* 2 */ { 0, &Ia_lgdt },
/* 3 */ { 0, &Ia_lidt },
/* 4 */ { 0, &Ia_smsw_Ew },
/* 5 */ { 0, &Ia_Invalid },
/* 6 */ { 0, &Ia_lmsw_Ew },
@ -4589,8 +4633,8 @@ static BxDisasmOpcodeTable_t BxDisasmOpcodes64q[256*2] = {
/* 0F 29 */ { GRPSSE(0f29) },
/* 0F 2A */ { GRPSSE(640f2a) },
/* 0F 2B */ { GRPSSE(0f2b) },
/* 0F 2C */ { GRPSSE(0f2c) },
/* 0F 2D */ { GRPSSE(0f2d) },
/* 0F 2C */ { GRPSSE(0f2cQ) },
/* 0F 2D */ { GRPSSE(0f2dQ) },
/* 0F 2E */ { GRPSSE(0f2e) },
/* 0F 2F */ { GRPSSE(0f2f) },
/* 0F 30 */ { 0, &Ia_wrmsr },
@ -4655,7 +4699,7 @@ static BxDisasmOpcodeTable_t BxDisasmOpcodes64q[256*2] = {
/* 0F 6B */ { GRPSSE(0f6b) },
/* 0F 6C */ { GRPSSE(0f6c) },
/* 0F 6D */ { GRPSSE(0f6d) },
/* 0F 6E */ { GRPSSE(0f6e) },
/* 0F 6E */ { GRPSSE(0f6eQ) },
/* 0F 6F */ { GRPSSE(0f6f) },
/* 0F 70 */ { GRPSSE(0f70) },
/* 0F 71 */ { GRPN(G12) },
@ -4671,7 +4715,7 @@ static BxDisasmOpcodeTable_t BxDisasmOpcodes64q[256*2] = {
/* 0F 7B */ { 0, &Ia_Invalid },
/* 0F 7C */ { GRPSSE(0f7c) },
/* 0F 7D */ { GRPSSE(0f7d) },
/* 0F 7E */ { GRPSSE(0f7e) },
/* 0F 7E */ { GRPSSE(0f7eQ) },
/* 0F 7F */ { GRPSSE(0f7f) },
/* 0F 80 */ { 0, &Ia_jo_Jd },
/* 0F 81 */ { 0, &Ia_jno_Jd },

View File

@ -86,6 +86,9 @@ struct BxDisasmOpcodeTable_t
const void *OpcodeInfo;
};
// segment override not used
#define NO_SEG_OVERRIDE 0xFF
// datasize attributes
#define X_SIZE 0x0000
#define B_SIZE 0x0100
@ -106,6 +109,10 @@ struct x86_insn
public:
x86_insn(bx_bool is32, bx_bool is64);
bx_bool is_seg_override() const {
return (seg_override != NO_SEG_OVERRIDE);
}
public:
bx_bool is_32, is_64;
bx_bool as_32, as_64;
@ -144,7 +151,7 @@ BX_CPP_INLINE x86_insn::x86_insn(bx_bool is32, bx_bool is64)
extend8b = 0;
rex_r = rex_b = rex_x = 0;
seg_override = 0;
seg_override = NO_SEG_OVERRIDE;
b1 = 0;
modrm = mod = nnn = rm = 0;

View File

@ -131,7 +131,7 @@ void disassembler::resolve16_mod0(const x86_insn *insn, unsigned mode)
{
const char *seg;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod00_rm16[insn->rm];
@ -146,7 +146,7 @@ void disassembler::resolve16_mod1or2(const x86_insn *insn, unsigned mode)
{
const char *seg;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod01or10_rm16[insn->rm];
@ -158,7 +158,7 @@ void disassembler::resolve32_mod0(const x86_insn *insn, unsigned mode)
{
const char *seg;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = segment_name[DS_REG];
@ -173,7 +173,7 @@ void disassembler::resolve32_mod1or2(const x86_insn *insn, unsigned mode)
{
const char *seg;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod01or10_rm32[insn->rm];
@ -187,7 +187,7 @@ void disassembler::resolve32_mod0_rm4(const x86_insn *insn, unsigned mode)
const char *seg, *base = NULL, *index = NULL;
Bit32u disp32 = 0;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod00_base32[insn->base];
@ -209,7 +209,7 @@ void disassembler::resolve32_mod1or2_rm4(const x86_insn *insn, unsigned mode)
{
const char *seg, *index = NULL;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod01or10_base32[insn->base];
@ -227,7 +227,7 @@ void disassembler::resolve64_mod0(const x86_insn *insn, unsigned mode)
{
const char *seg, *rip_regname;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = segment_name[DS_REG];
@ -245,7 +245,7 @@ void disassembler::resolve64_mod1or2(const x86_insn *insn, unsigned mode)
{
const char *seg;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod01or10_rm32[insn->rm];
@ -259,7 +259,7 @@ void disassembler::resolve64_mod0_rm4(const x86_insn *insn, unsigned mode)
const char *seg, *base = NULL, *index = NULL;
Bit32u disp32 = 0;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod00_base32[insn->base];
@ -281,7 +281,7 @@ void disassembler::resolve64_mod1or2_rm4(const x86_insn *insn, unsigned mode)
{
const char *seg, *index = NULL;
if (insn->seg_override)
if (insn->is_seg_override())
seg = segment_name[insn->seg_override];
else
seg = sreg_mod01or10_base32[insn->base];