Fixed cpu_mode corruption in x86-64 mode

Removed all potentially unsafe and duplicated code in setFLAGS methods to avoid such kind of problems in future
This commit is contained in:
Stanislav Shwartsman 2005-09-29 17:32:32 +00:00
parent 9e0089fb9e
commit 8c783bc329
9 changed files with 159 additions and 192 deletions

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: bit.cc,v 1.24 2005-07-25 04:18:10 sshwarts Exp $
// $Id: bit.cc,v 1.25 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -346,7 +346,7 @@ void BX_CPU_C::BSF_GwEw(bxInstruction_c *i)
}
if (op2_16 == 0) {
set_ZF(1); /* op1_16 undefined */
assert_ZF(); /* op1_16 undefined */
return;
}
@ -377,7 +377,7 @@ void BX_CPU_C::BSF_GdEd(bxInstruction_c *i)
}
if (op2_32 == 0) {
set_ZF(1); /* op1_32 undefined */
assert_ZF(); /* op1_32 undefined */
return;
}
@ -409,7 +409,7 @@ void BX_CPU_C::BSF_GqEq(bxInstruction_c *i)
}
if (op2_64 == 0) {
set_ZF(1); /* op1_64 undefined */
assert_ZF(); /* op1_64 undefined */
return;
}
@ -440,7 +440,7 @@ void BX_CPU_C::BSR_GwEw(bxInstruction_c *i)
}
if (op2_16 == 0) {
set_ZF(1); /* op1_16 undefined */
assert_ZF(); /* op1_16 undefined */
return;
}
@ -471,7 +471,7 @@ void BX_CPU_C::BSR_GdEd(bxInstruction_c *i)
}
if (op2_32 == 0) {
set_ZF(1); /* op1_32 undefined */
assert_ZF(); /* op1_32 undefined */
return;
}
@ -503,7 +503,7 @@ void BX_CPU_C::BSR_GqEq(bxInstruction_c *i)
}
if (op2_64 == 0) {
set_ZF(1); /* op1_64 undefined */
assert_ZF(); /* op1_64 undefined */
return;
}

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: cpu.h,v 1.242 2005-09-23 16:45:40 sshwarts Exp $
// $Id: cpu.h,v 1.243 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -408,101 +408,79 @@ typedef struct {
// some eflags which are not cached in separate fields.
Bit32u VM_cached;
#define DECLARE_EFLAGS_ACCESSORS() \
BX_CPP_INLINE void setEFlags(Bit32u val);
#define IMPLEMENT_EFLAGS_ACCESSORS() \
BX_CPP_INLINE void BX_CPU_C::setEFlags(Bit32u val) { \
BX_CPU_THIS_PTR eflags.val32 = val; \
BX_CPU_THIS_PTR eflags.VM_cached = val & (1<<17); \
if (BX_CPU_THIS_PTR cr0.pe) { \
if (BX_CPU_THIS_PTR eflags.VM_cached) \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_V8086; \
else \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_PROTECTED; \
} \
}
// accessors for all eflags in bx_flags_reg_t
// The macro is used once for each flag bit.
#define DECLARE_EFLAG_ACCESSOR(name,bitnum) \
BX_CPP_INLINE void assert_##name (); \
BX_CPP_INLINE void clear_##name (); \
BX_CPP_INLINE Bit32u get_##name (); \
BX_CPP_INLINE bx_bool getB_##name (); \
#define DECLARE_EFLAG_ACCESSOR(name,bitnum) \
BX_CPP_INLINE void assert_##name (); \
BX_CPP_INLINE void clear_##name (); \
BX_CPP_INLINE Bit32u get_##name (); \
BX_CPP_INLINE bx_bool getB_##name (); \
BX_CPP_INLINE void set_##name (Bit8u val);
#define IMPLEMENT_EFLAG_ACCESSOR(name,bitnum) \
BX_CPP_INLINE void BX_CPU_C::assert_##name () { \
BX_CPU_THIS_PTR eflags.val32 |= (1<<bitnum); \
} \
BX_CPP_INLINE void BX_CPU_C::clear_##name () { \
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<bitnum); \
} \
BX_CPP_INLINE bx_bool BX_CPU_C::getB_##name () { \
return 1 & (BX_CPU_THIS_PTR eflags.val32 >> bitnum); \
} \
BX_CPP_INLINE Bit32u BX_CPU_C::get_##name () { \
return BX_CPU_THIS_PTR eflags.val32 & (1 << bitnum); \
} \
BX_CPP_INLINE void BX_CPU_C::set_##name (Bit8u val) { \
BX_CPU_THIS_PTR eflags.val32 = \
(BX_CPU_THIS_PTR eflags.val32&~(1<<bitnum)) | ((!!val)<<bitnum); \
#define IMPLEMENT_EFLAG_ACCESSOR(name,bitnum) \
BX_CPP_INLINE void BX_CPU_C::assert_##name () { \
BX_CPU_THIS_PTR eflags.val32 |= (1<<bitnum); \
} \
BX_CPP_INLINE void BX_CPU_C::clear_##name () { \
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<bitnum); \
} \
BX_CPP_INLINE bx_bool BX_CPU_C::getB_##name () { \
return 1 & (BX_CPU_THIS_PTR eflags.val32 >> bitnum); \
} \
BX_CPP_INLINE Bit32u BX_CPU_C::get_##name () { \
return BX_CPU_THIS_PTR eflags.val32 & (1 << bitnum); \
} \
BX_CPP_INLINE void BX_CPU_C::set_##name (Bit8u val) { \
BX_CPU_THIS_PTR eflags.val32 = \
(BX_CPU_THIS_PTR eflags.val32&~(1<<bitnum))|((!!val)<<bitnum); \
}
#define DECLARE_EFLAG_ACCESSOR_VM(bitnum) \
BX_CPP_INLINE void assert_VM(); \
BX_CPP_INLINE void clear_VM(); \
BX_CPP_INLINE Bit32u get_VM(); \
BX_CPP_INLINE bx_bool getB_VM(); \
#define DECLARE_EFLAG_ACCESSOR_VM(bitnum) \
BX_CPP_INLINE void assert_VM(); \
BX_CPP_INLINE void clear_VM(); \
BX_CPP_INLINE Bit32u get_VM(); \
BX_CPP_INLINE bx_bool getB_VM(); \
BX_CPP_INLINE void set_VM(Bit32u val);
#define IMPLEMENT_EFLAG_ACCESSOR_VM(bitnum) \
BX_CPP_INLINE void BX_CPU_C::assert_VM() { \
BX_CPU_THIS_PTR eflags.val32 |= (1<<bitnum); \
BX_CPU_THIS_PTR eflags.VM_cached = 1; \
if (BX_CPU_THIS_PTR cr0.pe) { \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_V8086; \
} \
} \
BX_CPP_INLINE void BX_CPU_C::clear_VM() { \
if (BX_CPU_THIS_PTR eflags.VM_cached) { \
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<bitnum); \
BX_CPU_THIS_PTR eflags.VM_cached = 0; \
if (BX_CPU_THIS_PTR cr0.pe) { \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_PROTECTED; \
} \
} \
} \
BX_CPP_INLINE Bit32u BX_CPU_C::get_VM() { \
return BX_CPU_THIS_PTR eflags.VM_cached; \
} \
BX_CPP_INLINE bx_bool BX_CPU_C::getB_VM() { \
return (BX_CPU_THIS_PTR eflags.VM_cached>0); \
} \
BX_CPP_INLINE void BX_CPU_C::set_VM(Bit32u val) { \
BX_CPU_THIS_PTR eflags.val32 = \
(BX_CPU_THIS_PTR eflags.val32&~(1<<bitnum)) | (val ? (1<<bitnum) : 0); \
BX_CPU_THIS_PTR eflags.VM_cached = val; \
if (BX_CPU_THIS_PTR cr0.pe) { \
if (BX_CPU_THIS_PTR eflags.VM_cached) \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_V8086; \
else \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_PROTECTED; \
} \
#define IMPLEMENT_EFLAG_ACCESSOR_VM(bitnum) \
BX_CPP_INLINE Bit32u BX_CPU_C::get_VM() { \
return BX_CPU_THIS_PTR eflags.VM_cached; \
} \
BX_CPP_INLINE Bit32u BX_CPU_C::getB_VM() { \
return BX_CPU_THIS_PTR eflags.VM_cached > 0; \
} \
BX_CPP_INLINE void BX_CPU_C::assert_VM() { \
set_VM(1); \
} \
BX_CPP_INLINE void BX_CPU_C::clear_VM() { \
set_VM(0); \
} \
BX_CPP_INLINE void BX_CPU_C::set_VM(Bit32u val) { \
if (IsLongMode()) return; \
if (val) { \
BX_CPU_THIS_PTR eflags.val32 |= (1<<bitnum); \
BX_CPU_THIS_PTR eflags.VM_cached = 1; \
if (BX_CPU_THIS_PTR cr0.pe) \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_V8086; \
} else { \
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<bitnum); \
BX_CPU_THIS_PTR eflags.VM_cached = 0; \
if (BX_CPU_THIS_PTR cr0.pe) \
BX_CPU_THIS_PTR cpu_mode = BX_MODE_IA32_PROTECTED; \
} \
}
#define DECLARE_EFLAG_ACCESSOR_IOPL(bitnum) \
BX_CPP_INLINE void set_IOPL(Bit32u val); \
#define DECLARE_EFLAG_ACCESSOR_IOPL(bitnum) \
BX_CPP_INLINE void set_IOPL(Bit32u val); \
BX_CPP_INLINE Bit32u get_IOPL(void);
#define IMPLEMENT_EFLAG_ACCESSOR_IOPL(bitnum) \
BX_CPP_INLINE void BX_CPU_C::set_IOPL(Bit32u val) { \
BX_CPU_THIS_PTR eflags.val32 &= ~(3<<12); \
BX_CPU_THIS_PTR eflags.val32 |= ((3&val) << 12); \
} \
BX_CPP_INLINE Bit32u BX_CPU_C::get_IOPL() { \
return 3 & (BX_CPU_THIS_PTR eflags.val32 >> 12); \
#define IMPLEMENT_EFLAG_ACCESSOR_IOPL(bitnum) \
BX_CPP_INLINE void BX_CPU_C::set_IOPL(Bit32u val) { \
BX_CPU_THIS_PTR eflags.val32 &= ~(3<<12); \
BX_CPU_THIS_PTR eflags.val32 |= ((3&val) << 12); \
} \
BX_CPP_INLINE Bit32u BX_CPU_C::get_IOPL() { \
return 3 & (BX_CPU_THIS_PTR eflags.val32 >> 12); \
}
#define EFlagsCFMask (1 << 0)
@ -1248,10 +1226,6 @@ public: // for now...
Bit8u ispanic;
#endif
#if BX_SUPPORT_X86_64
#define TLB_GENERATION_MAX (BX_TLB_SIZE-1)
#endif
// SYSENTER/SYSEXIT instruction msr's
#if BX_SUPPORT_SEP
Bit32u sysenter_cs_msr;
@ -1302,27 +1276,51 @@ public: // for now...
virtual void ask (int level, const char *prefix, const char *fmt, va_list ap);
#endif
#define ArithmeticalFlag(flag, lfMaskShift, eflagsBitShift) \
void setEFlags(Bit32u val) BX_CPP_AttrRegparmN(1);
#define lfMaskCF 0x0000000f
#define lfMaskPF 0x000000f0
#define lfMaskAF 0x00000f00
#define lfMaskZF 0x0000f000
#define lfMaskSF 0x000f0000
#define lfMaskOF 0x00f00000
#define ArithmeticalFlag(flag, lfMask, eflagsBitShift) \
BX_SMF bx_bool get_##flag##Lazy(void); \
BX_SMF bx_bool getB_##flag(void) { \
if ( (BX_CPU_THIS_PTR lf_flags_status & (0xf<<lfMaskShift)) == 0) \
if ( (BX_CPU_THIS_PTR lf_flags_status & (lfMask)) == 0) \
return (BX_CPU_THIS_PTR eflags.val32 >> eflagsBitShift) & 1; \
else \
return get_##flag##Lazy(); \
} \
BX_SMF bx_bool get_##flag(void) { \
if ( (BX_CPU_THIS_PTR lf_flags_status & (0xf<<lfMaskShift)) == 0) \
if ( (BX_CPU_THIS_PTR lf_flags_status & (lfMask)) == 0) \
return BX_CPU_THIS_PTR eflags.val32 & (1<<eflagsBitShift); \
else \
return get_##flag##Lazy(); \
}
} \
BX_SMF void set_##flag(bx_bool val) { \
BX_CPU_THIS_PTR lf_flags_status &= ~(lfMask); \
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<eflagsBitShift); \
BX_CPU_THIS_PTR eflags.val32 |= ((!!val)<<eflagsBitShift); \
} \
BX_SMF void clear_##flag(void) { \
BX_CPU_THIS_PTR lf_flags_status &= ~(lfMask); \
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<eflagsBitShift); \
} \
BX_SMF void assert_##flag(void) { \
BX_CPU_THIS_PTR lf_flags_status &= ~(lfMask); \
BX_CPU_THIS_PTR eflags.val32 |= (1<<eflagsBitShift); \
}
ArithmeticalFlag(OF, 20, 11);
ArithmeticalFlag(SF, 16, 7);
ArithmeticalFlag(ZF, 12, 6);
ArithmeticalFlag(AF, 8, 4);
ArithmeticalFlag(PF, 4, 2);
ArithmeticalFlag(CF, 0, 0);
ArithmeticalFlag(OF, lfMaskOF, 11);
ArithmeticalFlag(SF, lfMaskSF, 7);
ArithmeticalFlag(ZF, lfMaskZF, 6);
ArithmeticalFlag(AF, lfMaskAF, 4);
ArithmeticalFlag(PF, lfMaskPF, 2);
ArithmeticalFlag(CF, lfMaskCF, 0);
BX_SMF BX_CPP_INLINE void set_PF_base(Bit8u val);
void set_cpu_id(unsigned id);
@ -2876,7 +2874,6 @@ public: // for now...
BX_CPP_INLINE unsigned which_cpu(void) { return bx_cpuid; }
BX_CPP_INLINE const bx_gen_reg_t *get_gen_reg() { return gen_reg; }
DECLARE_EFLAGS_ACCESSORS()
DECLARE_EFLAG_ACCESSOR (DF, 10)
DECLARE_EFLAG_ACCESSOR (ID, 21)
DECLARE_EFLAG_ACCESSOR (VIP, 20)
@ -2889,14 +2886,6 @@ public: // for now...
DECLARE_EFLAG_ACCESSOR (IF, 9)
DECLARE_EFLAG_ACCESSOR (TF, 8)
BX_SMF BX_CPP_INLINE void set_CF(bx_bool val);
BX_SMF BX_CPP_INLINE void set_AF(bx_bool val);
BX_SMF BX_CPP_INLINE void set_ZF(bx_bool val);
BX_SMF BX_CPP_INLINE void set_SF(bx_bool val);
BX_SMF BX_CPP_INLINE void set_OF(bx_bool val);
BX_SMF BX_CPP_INLINE void set_PF(bx_bool val);
BX_SMF BX_CPP_INLINE void set_PF_base(Bit8u val);
DECLARE_8BIT_REGISTER_ACCESSORS(AL);
DECLARE_8BIT_REGISTER_ACCESSORS(AH);
DECLARE_8BIT_REGISTER_ACCESSORS(BL);
@ -2927,6 +2916,10 @@ public: // for now...
BX_CPP_INLINE Bit8u get_CPL(void);
BX_CPP_INLINE Bit32u get_EIP(void);
#if BX_SUPPORT_X86_64
BX_SMF BX_CPP_INLINE Bit32u get_EFER(void);
#endif
BX_SMF BX_CPP_INLINE bx_address get_segment_base(unsigned seg);
BX_SMF BX_CPP_INLINE bx_bool real_mode(void);
@ -3032,7 +3025,18 @@ BX_SMF BX_CPP_INLINE Bit8u BX_CPU_C_PREFIX get_CPL(void)
BX_CPP_INLINE Bit32u BX_CPU_C::get_EIP(void)
{
return (BX_CPU_THIS_PTR dword.eip);
}
}
#if BX_SUPPORT_X86_64
BX_CPP_INLINE Bit32u BX_CPU_C::get_EFER(void)
{
return (BX_CPU_THIS_PTR msr.sce << 0) |
(BX_CPU_THIS_PTR msr.lme << 8) |
(BX_CPU_THIS_PTR msr.lma << 10) |
(BX_CPU_THIS_PTR msr.nxe << 11) |
(BX_CPU_THIS_PTR msr.ffxsr << 14);
}
#endif
BX_CPP_INLINE bx_address BX_CPU_C::get_segment_base(unsigned seg)
{
@ -3061,52 +3065,10 @@ BX_CPP_INLINE bx_bool BX_CPU_C::protected_mode(void)
return (BX_CPU_THIS_PTR cpu_mode >= BX_MODE_IA32_PROTECTED);
}
BX_CPP_INLINE void
BX_CPU_C::set_CF(bx_bool val) {
BX_CPU_THIS_PTR lf_flags_status &= 0xfffff0;
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<0);
BX_CPU_THIS_PTR eflags.val32 |= (!!val);
}
BX_CPP_INLINE void
BX_CPU_C::set_AF(bx_bool val) {
BX_CPU_THIS_PTR lf_flags_status &= 0xfff0ff;
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<4);
BX_CPU_THIS_PTR eflags.val32 |= (!!val)<<4;
}
BX_CPP_INLINE void
BX_CPU_C::set_ZF(bx_bool val) {
BX_CPU_THIS_PTR lf_flags_status &= 0xff0fff;
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<6);
BX_CPU_THIS_PTR eflags.val32 |= (!!val)<<6;
}
BX_CPP_INLINE void
BX_CPU_C::set_SF(bx_bool val) {
BX_CPU_THIS_PTR lf_flags_status &= 0xf0ffff;
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<7);
BX_CPU_THIS_PTR eflags.val32 |= (!!val)<<7;
}
BX_CPP_INLINE void
BX_CPU_C::set_OF(bx_bool val) {
BX_CPU_THIS_PTR lf_flags_status &= 0x0fffff;
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<11);
BX_CPU_THIS_PTR eflags.val32 |= (!!val)<<11;
}
BX_CPP_INLINE void
BX_CPU_C::set_PF(bx_bool val) {
BX_CPU_THIS_PTR lf_flags_status &= 0xffff0f;
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<2);
BX_CPU_THIS_PTR eflags.val32 |= (!!val)<<2;
}
BOCHSAPI extern const bx_bool bx_parity_lookup[256];
BX_CPP_INLINE void
BX_CPU_C::set_PF_base(Bit8u val) {
BX_CPP_INLINE void BX_CPU_C::set_PF_base(Bit8u val)
{
BX_CPU_THIS_PTR lf_flags_status &= 0xffff0f;
val = bx_parity_lookup[val]; // Always returns 0 or 1.
BX_CPU_THIS_PTR eflags.val32 &= ~(1<<2);
@ -3254,7 +3216,6 @@ BX_CPU_C::set_PF_base(Bit8u val) {
SET_FLAGS_OSZAP_RESULT_SIZE(_64, result, ins)
#endif
IMPLEMENT_EFLAGS_ACCESSORS()
IMPLEMENT_EFLAG_ACCESSOR (DF, 10)
IMPLEMENT_EFLAG_ACCESSOR (ID, 21)
IMPLEMENT_EFLAG_ACCESSOR (VIP, 20)
@ -3267,6 +3228,7 @@ IMPLEMENT_EFLAG_ACCESSOR_IOPL( 12)
IMPLEMENT_EFLAG_ACCESSOR (IF, 9)
IMPLEMENT_EFLAG_ACCESSOR (TF, 8)
// <TAG-DEFINES-DECODE-START>
//
// For decoding...

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: debugstuff.cc,v 1.39 2005-05-20 20:06:50 sshwarts Exp $
// $Id: debugstuff.cc,v 1.40 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -48,8 +48,9 @@ void BX_CPU_C::debug(bx_address offset)
BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].cache.u.segment.d_b ? 32 : 16));
BX_INFO(("SS.d_b = %u bit",
BX_CPU_THIS_PTR sregs[BX_SEG_REG_SS].cache.u.segment.d_b ? 32 : 16));
#if BX_SUPPORT_X86_64
BX_INFO(("EFER = 0x%08x", get_EFER()));
BX_INFO(("| RAX=%08x%08x RBX=%08x%08x",
(unsigned) (RAX >> 32), (unsigned) EAX,
(unsigned) (RBX >> 32), (unsigned) EBX));

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: flag_ctrl.cc,v 1.21 2005-08-08 19:56:11 sshwarts Exp $
// $Id: flag_ctrl.cc,v 1.22 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2002 MandrakeSoft S.A.
@ -52,12 +52,12 @@ void BX_CPU_C::LAHF(bxInstruction_c *i)
void BX_CPU_C::CLC(bxInstruction_c *i)
{
set_CF(0);
clear_CF ();
}
void BX_CPU_C::STC(bxInstruction_c *i)
{
set_CF(1);
assert_CF();
}
void BX_CPU_C::CLI(bxInstruction_c *i)
@ -127,15 +127,12 @@ void BX_CPU_C::STI(bxInstruction_c *i)
}
exception(BX_GP_EXCEPTION, 0, 0);
return;
}
}
}
#endif
if (cpl > IOPL) {
if (cpl > IOPL)
exception(BX_GP_EXCEPTION, 0, 0);
return;
}
}
#if BX_CPU_LEVEL >= 3
else if (v8086_mode())
@ -149,7 +146,6 @@ void BX_CPU_C::STI(bxInstruction_c *i)
}
#endif
exception(BX_GP_EXCEPTION, 0, 0);
return;
}
}
#endif

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: flag_ctrl_pro.cc,v 1.18 2005-07-01 14:05:56 sshwarts Exp $
// $Id: flag_ctrl_pro.cc,v 1.19 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -30,6 +30,18 @@
#define LOG_THIS BX_CPU_THIS_PTR
void BX_CPP_AttrRegparmN(1) BX_CPU_C::setEFlags(Bit32u val)
{
// VM flag could not be set from long mode
if (IsLongMode()) {
if (get_VM()) BX_PANIC(("VM is set in long mode !"));
val &= ~EFlagsVMMask;
}
BX_CPU_THIS_PTR eflags.val32 = val;
BX_CPU_THIS_PTR lf_flags_status = 0; // OSZAPC flags are known.
set_VM(val & EFlagsVMMask);
}
void BX_CPP_AttrRegparmN(2)
BX_CPU_C::writeEFlags(Bit32u flags, Bit32u changeMask)
{
@ -47,12 +59,12 @@ BX_CPU_C::writeEFlags(Bit32u flags, Bit32u changeMask)
newEFlags = (BX_CPU_THIS_PTR eflags.val32 & ~changeMask) |
(flags & changeMask);
BX_CPU_THIS_PTR setEFlags( newEFlags );
BX_CPU_THIS_PTR lf_flags_status = 0; // OSZAPC flags are known.
BX_CPU_THIS_PTR setEFlags(newEFlags);
// OSZAPC flags are known - done in setEFlags(newEFlags)
if (newEFlags & (1 << 8)) {
BX_CPU_THIS_PTR async_event = 1; // TF = 1
}
}
}
void BX_CPP_AttrRegparmN(3)

View File

@ -1,5 +1,5 @@
////////////////////////////////////////////////////////////////////////
// $Id: iret.cc,v 1.6 2005-08-14 18:01:04 sshwarts Exp $
// $Id: iret.cc,v 1.7 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -436,9 +436,9 @@ BX_CPU_C::long_iret(bxInstruction_c *i)
}
// if VM=1 in flags image on stack then STACK_RETURN_TO_V86
if (new_eflags & 0x00020000) {
if (new_eflags & EFlagsVMMask) {
BX_PANIC(("iret64: no V86 mode in x86-64 LONG mode"));
return;
new_eflags &= ~EFlagsVMMask;
}
parse_selector(raw_cs_selector, &cs_selector);

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: mult16.cc,v 1.19 2005-05-20 20:06:50 sshwarts Exp $
// $Id: mult16.cc,v 1.20 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -118,7 +118,7 @@ void BX_CPU_C::DIV_AXEw(bxInstruction_c *i)
*/
#if INTEL_DIV_FLAG_BUG == 1
set_CF(1);
assert_CF();
#endif
/* now write quotient back to destination */
@ -161,7 +161,7 @@ void BX_CPU_C::IDIV_AXEw(bxInstruction_c *i)
*/
#if INTEL_DIV_FLAG_BUG == 1
set_CF(1);
assert_CF();
#endif
/* now write quotient back to destination */

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: mult8.cc,v 1.19 2005-05-20 20:06:50 sshwarts Exp $
// $Id: mult8.cc,v 1.20 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -121,7 +121,7 @@ void BX_CPU_C::DIV_ALEb(bxInstruction_c *i)
*/
#if INTEL_DIV_FLAG_BUG == 1
set_CF(1);
assert_CF();
#endif
/* now write quotient back to destination */
@ -164,7 +164,7 @@ void BX_CPU_C::IDIV_ALEb(bxInstruction_c *i)
*/
#if INTEL_DIV_FLAG_BUG == 1
set_CF(1);
assert_CF();
#endif
/* now write quotient back to destination */

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: proc_ctrl.cc,v 1.113 2005-09-14 20:01:42 sshwarts Exp $
// $Id: proc_ctrl.cc,v 1.114 2005-09-29 17:32:32 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -1603,11 +1603,7 @@ void BX_CPU_C::RDMSR(bxInstruction_c *i)
#if BX_SUPPORT_X86_64
case BX_MSR_EFER:
RAX = (BX_CPU_THIS_PTR msr.sce << 0)
| (BX_CPU_THIS_PTR msr.lme << 8)
| (BX_CPU_THIS_PTR msr.lma << 10)
| (BX_CPU_THIS_PTR msr.nxe << 11)
| (BX_CPU_THIS_PTR msr.ffxsr << 14);
RAX = (Bit64u) get_EFER();
RDX = 0;
return;
@ -1834,9 +1830,9 @@ void BX_CPU_C::SYSENTER (bxInstruction_c *i)
invalidate_prefetch_q();
BX_CPU_THIS_PTR set_VM(0); // do this just like the book says to do
BX_CPU_THIS_PTR set_IF(0);
BX_CPU_THIS_PTR set_RF(0);
BX_CPU_THIS_PTR clear_VM(); // do this just like the book says to do
BX_CPU_THIS_PTR clear_IF();
BX_CPU_THIS_PTR clear_RF();
BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].selector.value = BX_CPU_THIS_PTR sysenter_cs_msr & BX_SELECTOR_RPL_MASK;
BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].selector.index = BX_CPU_THIS_PTR sysenter_cs_msr >> 3;