This commit is contained in:
Stanislav Shwartsman 2009-03-27 16:42:21 +00:00
parent 10e373f79f
commit a0b1fda178
6 changed files with 37 additions and 26 deletions

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: descriptor.h,v 1.28 2009-02-09 19:46:34 sshwarts Exp $
// $Id: descriptor.h,v 1.29 2009-03-27 16:42:21 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (c) 2007 Stanislav Shwartsman
@ -154,6 +154,7 @@ union {
#if BX_CPU_LEVEL >= 3
Bit32u limit_scaled; // Same notes as for 'segment' field
bx_bool g; /* granularity: 0=byte, 1=4K (page) */
bx_bool d_b; /* default size: 0=16bit, 1=32bit */
bx_bool avl; /* available for use by system */
#endif
} system; /* TSS and LDT */

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: exception.cc,v 1.138 2009-02-20 08:12:51 sshwarts Exp $
// $Id: exception.cc,v 1.139 2009-03-27 16:42:21 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -756,9 +756,15 @@ void BX_CPU_C::real_mode_int(Bit8u vector, unsigned is_INT, bx_bool push_error,
push_16(BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].selector.value);
push_16(IP);
EIP = system_read_word(BX_CPU_THIS_PTR idtr.base + 4 * vector);
Bit16u new_ip = system_read_word(BX_CPU_THIS_PTR idtr.base + 4 * vector);
// CS.LIMIT can't change when in real/v8086 mode
if (new_ip > BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].cache.u.segment.limit_scaled) {
BX_ERROR(("interrupt(real mode): instruction pointer not within code segment limits"));
exception(BX_GP_EXCEPTION, 0, 0);
}
cs_selector = system_read_word(BX_CPU_THIS_PTR idtr.base + 4 * vector + 2);
load_seg_reg(&BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS], cs_selector);
EIP = new_ip;
/* INT affects the following flags: I,T */
BX_CPU_THIS_PTR clear_IF();

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: flag_ctrl.cc,v 1.44 2009-03-10 20:01:56 sshwarts Exp $
// $Id: flag_ctrl.cc,v 1.45 2009-03-27 16:42:21 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2002 MandrakeSoft S.A.
@ -193,10 +193,12 @@ void BX_CPP_AttrRegparmN(1) BX_CPU_C::POPF_Fw(bxInstruction_c *i)
#if BX_CPU_LEVEL >= 3
changeMask |= EFlagsNTMask; // NT could be modified
#endif
Bit16u flags16;
RSP_SPECULATIVE;
Bit16u flags16 = pop_16();
if (protected_mode()) {
flags16 = pop_16();
if (CPL==0)
changeMask |= EFlagsIOPLMask;
if (CPL <= BX_CPU_THIS_PTR get_IOPL())
@ -207,16 +209,13 @@ void BX_CPP_AttrRegparmN(1) BX_CPU_C::POPF_Fw(bxInstruction_c *i)
BX_DEBUG(("POPFW: #GP(0) in v8086 (no VME) mode"));
exception(BX_GP_EXCEPTION, 0, 0);
}
RSP_SPECULATIVE;
flags16 = pop_16();
#if BX_SUPPORT_VME
if (BX_CR4_VME_ENABLED && BX_CPU_THIS_PTR get_IOPL() < 3) {
if (((flags16 & EFlagsIFMask) && BX_CPU_THIS_PTR get_VIP()) ||
(flags16 & EFlagsTFMask))
{
BX_DEBUG(("POPFW: #GP(0) in VME mode"));
BX_ERROR(("POPFW: #GP(0) in VME mode"));
exception(BX_GP_EXCEPTION, 0, 0);
}
@ -225,22 +224,21 @@ void BX_CPP_AttrRegparmN(1) BX_CPU_C::POPF_Fw(bxInstruction_c *i)
Bit32u flags32 = (Bit32u) flags16;
if (BX_CPU_THIS_PTR get_IF()) flags32 |= EFlagsVIFMask;
writeEFlags(flags32, changeMask);
RSP_COMMIT;
return;
}
#endif
changeMask |= EFlagsIFMask;
RSP_COMMIT;
}
else {
flags16 = pop_16();
// All non-reserved flags can be modified
changeMask |= (EFlagsIOPLMask | EFlagsIFMask);
}
writeEFlags((Bit32u) flags16, changeMask);
RSP_COMMIT;
}
#if BX_CPU_LEVEL >= 3
@ -265,10 +263,12 @@ void BX_CPP_AttrRegparmN(1) BX_CPU_C::POPF_Fd(bxInstruction_c *i)
#if BX_CPU_LEVEL >= 4
changeMask |= (EFlagsIDMask | EFlagsACMask); // ID/AC
#endif
Bit32u flags32;
RSP_SPECULATIVE;
Bit32u flags32 = pop_32();
if (protected_mode()) {
flags32 = pop_32();
// IOPL changed only if (CPL == 0),
// IF changed only if (CPL <= EFLAGS.IOPL),
// VIF, VIP, VM are unaffected
@ -279,20 +279,20 @@ void BX_CPP_AttrRegparmN(1) BX_CPU_C::POPF_Fd(bxInstruction_c *i)
}
else if (v8086_mode()) {
if (BX_CPU_THIS_PTR get_IOPL() < 3) {
BX_DEBUG(("POPFD: #GP(0) in v8086 mode"));
BX_ERROR(("POPFD: #GP(0) in v8086 mode"));
exception(BX_GP_EXCEPTION, 0, 0);
}
flags32 = pop_32();
// v8086-mode: VM, IOPL, VIP, VIF are unaffected
changeMask |= EFlagsIFMask;
}
else { // Real-mode
flags32 = pop_32();
// VIF, VIP, VM are unaffected
changeMask |= (EFlagsIOPLMask | EFlagsIFMask);
}
writeEFlags(flags32, changeMask);
RSP_COMMIT;
}
#if BX_SUPPORT_X86_64

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: init.cc,v 1.204 2009-03-13 18:48:08 sshwarts Exp $
// $Id: init.cc,v 1.205 2009-03-27 16:42:21 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -393,22 +393,24 @@ void BX_CPU_C::register_state(void)
BXRS_HEX_PARAM_FIELD(IDTR, base, idtr.base);
BXRS_HEX_PARAM_FIELD(IDTR, limit, idtr.limit);
bx_list_c *LDTR = new bx_list_c(cpu, "LDTR", 7);
bx_list_c *LDTR = new bx_list_c(cpu, "LDTR", 8);
BXRS_PARAM_SPECIAL16(LDTR, selector, param_save_handler, param_restore_handler);
BXRS_HEX_PARAM_FIELD(LDTR, base, ldtr.cache.u.system.base);
BXRS_HEX_PARAM_FIELD(LDTR, limit, ldtr.cache.u.system.limit);
BXRS_HEX_PARAM_FIELD(LDTR, limit_scaled, ldtr.cache.u.system.limit);
BXRS_HEX_PARAM_FIELD(LDTR, limit_scaled, ldtr.cache.u.system.limit_scaled);
BXRS_PARAM_SPECIAL8 (LDTR, ar_byte, param_save_handler, param_restore_handler);
BXRS_PARAM_BOOL(LDTR, granularity, ldtr.cache.u.system.g);
BXRS_PARAM_BOOL(LDTR, d_b, ldtr.cache.u.system.d_b);
BXRS_PARAM_BOOL(LDTR, avl, ldtr.cache.u.system.avl);
bx_list_c *TR = new bx_list_c(cpu, "TR", 7);
bx_list_c *TR = new bx_list_c(cpu, "TR", 8);
BXRS_PARAM_SPECIAL16(TR, selector, param_save_handler, param_restore_handler);
BXRS_HEX_PARAM_FIELD(TR, base, tr.cache.u.system.base);
BXRS_HEX_PARAM_FIELD(TR, limit, tr.cache.u.system.limit);
BXRS_HEX_PARAM_FIELD(TR, limit_scaled, tr.cache.u.system.limit_scaled);
BXRS_PARAM_SPECIAL8 (TR, ar_byte, param_save_handler, param_restore_handler);
BXRS_PARAM_BOOL(TR, granularity, tr.cache.u.system.g);
BXRS_PARAM_BOOL(TR, d_b, tr.cache.u.system.d_b);
BXRS_PARAM_BOOL(TR, avl, tr.cache.u.system.avl);
BXRS_HEX_PARAM_SIMPLE(cpu, smbase);

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: paging.cc,v 1.172 2009-03-08 21:23:37 sshwarts Exp $
// $Id: paging.cc,v 1.173 2009-03-27 16:42:21 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -666,7 +666,7 @@ void BX_CPU_C::page_fault(unsigned fault, bx_address laddr, unsigned user, unsig
}
/* PAE PML4: bits [51 .. physical address width], [7] - support 1G paging */
#define PAGING_PAE_PML4_RESERVED_BITS \
#define PAGING_PAE_PML4_RESERVED_BITS \
(BX_PHY_ADDRESS_RESERVED_BITS | BX_CONST64(0x80))
#if BX_SUPPORT_1G_PAGES

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: segment_ctrl_pro.cc,v 1.108 2009-03-10 20:01:56 sshwarts Exp $
// $Id: segment_ctrl_pro.cc,v 1.109 2009-03-27 16:42:21 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -414,6 +414,7 @@ BX_CPU_C::get_descriptor_h(const bx_descriptor_t *d)
(d->p << 15) |
(d->u.system.limit & 0xf0000) |
(d->u.system.avl << 20) |
(d->u.system.d_b << 22) |
(d->u.system.g << 23) |
(d->u.system.base & 0xff000000);
return(val);
@ -558,6 +559,7 @@ BX_CPU_C::parse_descriptor(Bit32u dword1, Bit32u dword2, bx_descriptor_t *temp)
((dword2 & 0xff) << 16) | (dword2 & 0xff000000);
temp->u.system.limit = (dword1 & 0x0000ffff) | (dword2 & 0x000f0000);
temp->u.system.g = (dword2 & 0x00800000) > 0;
temp->u.system.d_b = (dword2 & 0x00400000) > 0;
temp->u.system.avl = (dword2 & 0x00100000) > 0;
if (temp->u.system.g)
temp->u.system.limit_scaled = (temp->u.system.limit << 12) | 0xfff;