Make efer control MSR separate register
This commit is contained in:
parent
471e89dc84
commit
70f513b07b
@ -1,5 +1,5 @@
|
|||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: cpu.h,v 1.324 2007-09-10 16:00:14 sshwarts Exp $
|
// $Id: cpu.h,v 1.325 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||||
@ -537,13 +537,6 @@ typedef struct
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
// x86-64 EFER bits
|
|
||||||
bx_bool sce; // system call extensions
|
|
||||||
bx_bool lme; // long mode enable
|
|
||||||
bx_bool lma; // long mode active
|
|
||||||
bx_bool nxe; // no-execute enable
|
|
||||||
bx_bool ffxsr; // fast FXSAVE/FXRSTOR
|
|
||||||
|
|
||||||
Bit64u star;
|
Bit64u star;
|
||||||
Bit64u lstar;
|
Bit64u lstar;
|
||||||
Bit64u cstar;
|
Bit64u cstar;
|
||||||
@ -571,6 +564,17 @@ typedef struct
|
|||||||
} bx_regs_msr_t;
|
} bx_regs_msr_t;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if BX_SUPPORT_X86_64
|
||||||
|
typedef struct bx_efer_t {
|
||||||
|
// x86-64 EFER bits
|
||||||
|
bx_bool sce; // system call extensions
|
||||||
|
bx_bool lme; // long mode enable
|
||||||
|
bx_bool lma; // long mode active
|
||||||
|
bx_bool nxe; // no-execute enable
|
||||||
|
bx_bool ffxsr; // fast FXSAVE/FXRSTOR
|
||||||
|
} bx_efer_t;
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "crregs.h"
|
#include "crregs.h"
|
||||||
#include "descriptor.h"
|
#include "descriptor.h"
|
||||||
|
|
||||||
@ -1037,6 +1041,10 @@ public: // for now...
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if BX_SUPPORT_X86_64
|
||||||
|
bx_efer_t efer;
|
||||||
|
#endif
|
||||||
|
|
||||||
/* SMM base register */
|
/* SMM base register */
|
||||||
Bit32u smbase;
|
Bit32u smbase;
|
||||||
|
|
||||||
@ -3145,11 +3153,11 @@ BX_CPP_INLINE void BX_CPU_C::set_reg64(unsigned reg, Bit64u val)
|
|||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
BX_CPP_INLINE Bit32u BX_CPU_C::get_EFER(void)
|
BX_CPP_INLINE Bit32u BX_CPU_C::get_EFER(void)
|
||||||
{
|
{
|
||||||
return (BX_CPU_THIS_PTR msr.sce << 0) |
|
return (BX_CPU_THIS_PTR efer.sce << 0) |
|
||||||
(BX_CPU_THIS_PTR msr.lme << 8) |
|
(BX_CPU_THIS_PTR efer.lme << 8) |
|
||||||
(BX_CPU_THIS_PTR msr.lma << 10) |
|
(BX_CPU_THIS_PTR efer.lma << 10) |
|
||||||
(BX_CPU_THIS_PTR msr.nxe << 11) |
|
(BX_CPU_THIS_PTR efer.nxe << 11) |
|
||||||
(BX_CPU_THIS_PTR msr.ffxsr << 14);
|
(BX_CPU_THIS_PTR efer.ffxsr << 14);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -3176,7 +3184,7 @@ BX_CPP_INLINE bx_bool BX_CPU_C::protected_mode(void)
|
|||||||
BX_CPP_INLINE unsigned BX_CPU_C::long_mode(void)
|
BX_CPP_INLINE unsigned BX_CPU_C::long_mode(void)
|
||||||
{
|
{
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
return BX_CPU_THIS_PTR msr.lma;
|
return BX_CPU_THIS_PTR efer.lma;
|
||||||
#else
|
#else
|
||||||
return 0;
|
return 0;
|
||||||
#endif
|
#endif
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: ctrl_xfer_pro.cc,v 1.56 2007-03-14 21:15:15 sshwarts Exp $
|
// $Id: ctrl_xfer_pro.cc,v 1.57 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||||
@ -51,7 +51,7 @@ void BX_CPU_C::check_cs(bx_descriptor_t *descriptor, Bit16u cs_raw, Bit8u check_
|
|||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (descriptor->u.segment.l)
|
if (descriptor->u.segment.l)
|
||||||
{
|
{
|
||||||
if (! BX_CPU_THIS_PTR msr.lma) {
|
if (! BX_CPU_THIS_PTR efer.lma) {
|
||||||
BX_PANIC(("check_cs: attempt to jump to long mode without enabling EFER.LMA !"));
|
BX_PANIC(("check_cs: attempt to jump to long mode without enabling EFER.LMA !"));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -104,7 +104,7 @@ BX_CPU_C::load_cs(bx_selector_t *selector, bx_descriptor_t *descriptor, Bit8u cp
|
|||||||
(0xfffc & BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].selector.value) | cpl;
|
(0xfffc & BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].selector.value) | cpl;
|
||||||
|
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (BX_CPU_THIS_PTR msr.lma) {
|
if (BX_CPU_THIS_PTR efer.lma) {
|
||||||
if (descriptor->u.segment.l) {
|
if (descriptor->u.segment.l) {
|
||||||
BX_CPU_THIS_PTR cpu_mode = BX_MODE_LONG_64;
|
BX_CPU_THIS_PTR cpu_mode = BX_MODE_LONG_64;
|
||||||
BX_DEBUG(("Long Mode Activated"));
|
BX_DEBUG(("Long Mode Activated"));
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: init.cc,v 1.130 2007-07-31 20:25:52 sshwarts Exp $
|
// $Id: init.cc,v 1.131 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||||
@ -647,11 +647,11 @@ Bit64s BX_CPU_C::param_restore(bx_param_c *param, Bit64s val)
|
|||||||
BX_CPU_THIS_PTR setEFlags((Bit32u)val);
|
BX_CPU_THIS_PTR setEFlags((Bit32u)val);
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
} else if (!strcmp(pname, "EFER")) {
|
} else if (!strcmp(pname, "EFER")) {
|
||||||
BX_CPU_THIS_PTR msr.sce = (val >> 0) & 1;
|
BX_CPU_THIS_PTR efer.sce = (val >> 0) & 1;
|
||||||
BX_CPU_THIS_PTR msr.lme = (val >> 8) & 1;
|
BX_CPU_THIS_PTR efer.lme = (val >> 8) & 1;
|
||||||
BX_CPU_THIS_PTR msr.lma = (val >> 10) & 1;
|
BX_CPU_THIS_PTR efer.lma = (val >> 10) & 1;
|
||||||
BX_CPU_THIS_PTR msr.nxe = (val >> 11) & 1;
|
BX_CPU_THIS_PTR efer.nxe = (val >> 11) & 1;
|
||||||
BX_CPU_THIS_PTR msr.ffxsr = (val >> 14) & 1;
|
BX_CPU_THIS_PTR efer.ffxsr = (val >> 14) & 1;
|
||||||
#endif
|
#endif
|
||||||
} else if (!strcmp(pname, "ar_byte") || !strcmp(pname, "selector")) {
|
} else if (!strcmp(pname, "ar_byte") || !strcmp(pname, "selector")) {
|
||||||
segname = param->get_parent()->get_name();
|
segname = param->get_parent()->get_name();
|
||||||
@ -946,9 +946,10 @@ void BX_CPU_C::reset(unsigned source)
|
|||||||
BX_CPU_THIS_PTR msr.apicbase |= 0x900;
|
BX_CPU_THIS_PTR msr.apicbase |= 0x900;
|
||||||
#endif
|
#endif
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
BX_CPU_THIS_PTR msr.lme = BX_CPU_THIS_PTR msr.lma = 0;
|
BX_CPU_THIS_PTR efer.lme = BX_CPU_THIS_PTR efer.lma = 0;
|
||||||
BX_CPU_THIS_PTR msr.sce = BX_CPU_THIS_PTR msr.nxe = 0;
|
BX_CPU_THIS_PTR efer.sce = BX_CPU_THIS_PTR efer.nxe = 0;
|
||||||
BX_CPU_THIS_PTR msr.ffxsr = 0;
|
BX_CPU_THIS_PTR efer.ffxsr = 0;
|
||||||
|
|
||||||
BX_CPU_THIS_PTR msr.star = 0;
|
BX_CPU_THIS_PTR msr.star = 0;
|
||||||
BX_CPU_THIS_PTR msr.lstar = 0;
|
BX_CPU_THIS_PTR msr.lstar = 0;
|
||||||
BX_CPU_THIS_PTR msr.cstar = 0;
|
BX_CPU_THIS_PTR msr.cstar = 0;
|
||||||
@ -1105,7 +1106,7 @@ void BX_CPU_C::assert_checks(void)
|
|||||||
{
|
{
|
||||||
// check CPU mode consistency
|
// check CPU mode consistency
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (BX_CPU_THIS_PTR msr.lma) {
|
if (BX_CPU_THIS_PTR efer.lma) {
|
||||||
if (! BX_CPU_THIS_PTR cr0.get_PE()) {
|
if (! BX_CPU_THIS_PTR cr0.get_PE()) {
|
||||||
BX_PANIC(("assert_checks: EFER.LMA is set when CR0.PE=0 !"));
|
BX_PANIC(("assert_checks: EFER.LMA is set when CR0.PE=0 !"));
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: iret.cc,v 1.18 2007-03-14 21:15:15 sshwarts Exp $
|
// $Id: iret.cc,v 1.19 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||||
@ -46,8 +46,7 @@ BX_CPU_C::iret_protected(bxInstruction_c *i)
|
|||||||
bx_descriptor_t cs_descriptor, ss_descriptor;
|
bx_descriptor_t cs_descriptor, ss_descriptor;
|
||||||
|
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (BX_CPU_THIS_PTR msr.lma)
|
if (long_mode()) {
|
||||||
{
|
|
||||||
long_iret(i);
|
long_iret(i);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: paging.cc,v 1.84 2007-08-30 16:48:10 sshwarts Exp $
|
// $Id: paging.cc,v 1.85 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||||
@ -584,7 +584,7 @@ void BX_CPU_C::page_fault(unsigned fault, bx_address laddr, unsigned pl, unsigne
|
|||||||
|
|
||||||
error_code |= (pl << 2) | (rw << 1);
|
error_code |= (pl << 2) | (rw << 1);
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (BX_CPU_THIS_PTR msr.nxe && (access_type == CODE_ACCESS))
|
if (BX_CPU_THIS_PTR efer.nxe && (access_type == CODE_ACCESS))
|
||||||
error_code |= ERROR_CODE_ACCESS; // I/D = 1
|
error_code |= ERROR_CODE_ACCESS; // I/D = 1
|
||||||
#endif
|
#endif
|
||||||
BX_CPU_THIS_PTR cr2 = laddr;
|
BX_CPU_THIS_PTR cr2 = laddr;
|
||||||
@ -669,7 +669,7 @@ bx_phy_address BX_CPU_C::translate_linear(bx_address laddr, unsigned pl, unsigne
|
|||||||
page_fault(ERROR_NOT_PRESENT, laddr, pl, isWrite, access_type); // PML4 Entry NOT present
|
page_fault(ERROR_NOT_PRESENT, laddr, pl, isWrite, access_type); // PML4 Entry NOT present
|
||||||
}
|
}
|
||||||
if (pml4 & PAGE_DIRECTORY_NX_BIT) {
|
if (pml4 & PAGE_DIRECTORY_NX_BIT) {
|
||||||
if (! BX_CPU_THIS_PTR msr.nxe) {
|
if (! BX_CPU_THIS_PTR efer.nxe) {
|
||||||
BX_DEBUG(("PML4: NX bit set when EFER.NXE is disabled"));
|
BX_DEBUG(("PML4: NX bit set when EFER.NXE is disabled"));
|
||||||
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
||||||
}
|
}
|
||||||
@ -704,10 +704,10 @@ bx_phy_address BX_CPU_C::translate_linear(bx_address laddr, unsigned pl, unsigne
|
|||||||
page_fault(ERROR_NOT_PRESENT, laddr, pl, isWrite, access_type); // PDP Entry NOT present
|
page_fault(ERROR_NOT_PRESENT, laddr, pl, isWrite, access_type); // PDP Entry NOT present
|
||||||
}
|
}
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (BX_CPU_THIS_PTR msr.lma)
|
if (BX_CPU_THIS_PTR efer.lma)
|
||||||
{
|
{
|
||||||
if (pdp & PAGE_DIRECTORY_NX_BIT) {
|
if (pdp & PAGE_DIRECTORY_NX_BIT) {
|
||||||
if (! BX_CPU_THIS_PTR msr.nxe) {
|
if (! BX_CPU_THIS_PTR efer.nxe) {
|
||||||
BX_DEBUG(("PAE PDP: NX bit set when EFER.NXE is disabled"));
|
BX_DEBUG(("PAE PDP: NX bit set when EFER.NXE is disabled"));
|
||||||
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
||||||
}
|
}
|
||||||
@ -738,7 +738,7 @@ bx_phy_address BX_CPU_C::translate_linear(bx_address laddr, unsigned pl, unsigne
|
|||||||
|
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (pde & PAGE_DIRECTORY_NX_BIT) {
|
if (pde & PAGE_DIRECTORY_NX_BIT) {
|
||||||
if (! BX_CPU_THIS_PTR msr.nxe) {
|
if (! BX_CPU_THIS_PTR efer.nxe) {
|
||||||
BX_DEBUG(("PAE PDE: NX bit set when EFER.NXE is disabled"));
|
BX_DEBUG(("PAE PDE: NX bit set when EFER.NXE is disabled"));
|
||||||
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
||||||
}
|
}
|
||||||
@ -800,7 +800,7 @@ bx_phy_address BX_CPU_C::translate_linear(bx_address laddr, unsigned pl, unsigne
|
|||||||
|
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (pte & PAGE_DIRECTORY_NX_BIT) {
|
if (pte & PAGE_DIRECTORY_NX_BIT) {
|
||||||
if (! BX_CPU_THIS_PTR msr.nxe) {
|
if (! BX_CPU_THIS_PTR efer.nxe) {
|
||||||
BX_DEBUG(("PAE PTE: NX bit set when EFER.NXE is disabled"));
|
BX_DEBUG(("PAE PTE: NX bit set when EFER.NXE is disabled"));
|
||||||
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
page_fault(ERROR_RESERVED | ERROR_PROTECTION, laddr, pl, isWrite, access_type);
|
||||||
}
|
}
|
||||||
@ -854,7 +854,7 @@ bx_phy_address BX_CPU_C::translate_linear(bx_address laddr, unsigned pl, unsigne
|
|||||||
else
|
else
|
||||||
#endif // #if BX_SUPPORT_PAE
|
#endif // #if BX_SUPPORT_PAE
|
||||||
{
|
{
|
||||||
// CR4.PAE==0 (and MSR.LMA==0)
|
// CR4.PAE==0 (and EFER.LMA==0)
|
||||||
Bit32u pde, pte;
|
Bit32u pde, pte;
|
||||||
bx_phy_address pde_addr;
|
bx_phy_address pde_addr;
|
||||||
|
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: proc_ctrl.cc,v 1.167 2007-07-31 20:25:52 sshwarts Exp $
|
// $Id: proc_ctrl.cc,v 1.168 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||||
@ -1210,7 +1210,7 @@ void BX_CPU_C::LOADALL(bxInstruction_c *i)
|
|||||||
void BX_CPU_C::handleCpuModeChange(void)
|
void BX_CPU_C::handleCpuModeChange(void)
|
||||||
{
|
{
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (BX_CPU_THIS_PTR msr.lma) {
|
if (BX_CPU_THIS_PTR efer.lma) {
|
||||||
if (! BX_CPU_THIS_PTR cr0.get_PE()) {
|
if (! BX_CPU_THIS_PTR cr0.get_PE()) {
|
||||||
BX_PANIC(("change_cpu_mode: EFER.LMA is set when CR0.PE=0 !"));
|
BX_PANIC(("change_cpu_mode: EFER.LMA is set when CR0.PE=0 !"));
|
||||||
}
|
}
|
||||||
@ -1293,20 +1293,24 @@ void BX_CPU_C::SetCR0(Bit32u val_32)
|
|||||||
|
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
if (prev_pg==0 && BX_CPU_THIS_PTR cr0.get_PG()) {
|
if (prev_pg==0 && BX_CPU_THIS_PTR cr0.get_PG()) {
|
||||||
if (BX_CPU_THIS_PTR msr.lme) {
|
if (BX_CPU_THIS_PTR efer.lme) {
|
||||||
if (!BX_CPU_THIS_PTR cr4.get_PAE()) {
|
if (!BX_CPU_THIS_PTR cr4.get_PAE()) {
|
||||||
BX_ERROR(("SetCR0: attempt to enter x86-64 LONG mode without enabling CR4.PAE !"));
|
BX_ERROR(("SetCR0: attempt to enter x86-64 long mode without enabling CR4.PAE !"));
|
||||||
exception(BX_GP_EXCEPTION, 0, 0);
|
exception(BX_GP_EXCEPTION, 0, 0);
|
||||||
}
|
}
|
||||||
BX_CPU_THIS_PTR msr.lma = 1;
|
if (BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].cache.u.segment.l) {
|
||||||
|
BX_ERROR(("SetCR0: attempt to enter x86-64 long mode with CS.L !"));
|
||||||
|
exception(BX_GP_EXCEPTION, 0, 0);
|
||||||
|
}
|
||||||
|
BX_CPU_THIS_PTR efer.lma = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (prev_pg==1 && ! BX_CPU_THIS_PTR cr0.get_PG()) {
|
else if (prev_pg==1 && ! BX_CPU_THIS_PTR cr0.get_PG()) {
|
||||||
if (BX_CPU_THIS_PTR msr.lma) {
|
if (BX_CPU_THIS_PTR efer.lma) {
|
||||||
if (BX_CPU_THIS_PTR dword.rip_upper != 0) {
|
if (BX_CPU_THIS_PTR dword.rip_upper != 0) {
|
||||||
BX_PANIC(("SetCR0: attempt to leave x86-64 LONG mode with RIP upper != 0 !!!"));
|
BX_PANIC(("SetCR0: attempt to leave x86-64 LONG mode with RIP upper != 0 !!!"));
|
||||||
}
|
}
|
||||||
BX_CPU_THIS_PTR msr.lma = 0;
|
BX_CPU_THIS_PTR efer.lma = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif // #if BX_SUPPORT_X86_64
|
#endif // #if BX_SUPPORT_X86_64
|
||||||
@ -1376,11 +1380,11 @@ bx_bool BX_CPU_C::SetCR4(Bit32u val_32)
|
|||||||
|
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
// need to GP(0) if LMA=1 and PAE=1->0
|
// need to GP(0) if LMA=1 and PAE=1->0
|
||||||
if ((BX_CPU_THIS_PTR msr.lma)
|
if ((BX_CPU_THIS_PTR efer.lma)
|
||||||
&& (!(val_32 >> 5) & 1)
|
&& (!(val_32 >> 5) & 1)
|
||||||
&& (BX_CPU_THIS_PTR cr4.get_PAE()))
|
&& (BX_CPU_THIS_PTR cr4.get_PAE()))
|
||||||
{
|
{
|
||||||
BX_ERROR(("SetCR4: attempt to change PAE when LMA=1"));
|
BX_ERROR(("SetCR4: attempt to change PAE when EFER.LMA=1"));
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
@ -1711,16 +1715,16 @@ void BX_CPU_C::WRMSR(bxInstruction_c *i)
|
|||||||
case BX_MSR_EFER:
|
case BX_MSR_EFER:
|
||||||
// GPF #0 if lme 0->1 and cr0.pg = 1
|
// GPF #0 if lme 0->1 and cr0.pg = 1
|
||||||
// GPF #0 if lme 1->0 and cr0.pg = 1
|
// GPF #0 if lme 1->0 and cr0.pg = 1
|
||||||
if ((BX_CPU_THIS_PTR msr.lme != ((EAX >> 8) & 1)) &&
|
if ((BX_CPU_THIS_PTR efer.lme != ((EAX >> 8) & 1)) &&
|
||||||
BX_CPU_THIS_PTR cr0.get_PG())
|
BX_CPU_THIS_PTR cr0.get_PG())
|
||||||
{
|
{
|
||||||
BX_ERROR(("WRMSR: attempt to change LME when CR0.PG=1"));
|
BX_ERROR(("WRMSR: attempt to change LME when CR0.PG=1"));
|
||||||
exception(BX_GP_EXCEPTION, 0, 0);
|
exception(BX_GP_EXCEPTION, 0, 0);
|
||||||
}
|
}
|
||||||
BX_CPU_THIS_PTR msr.sce = (EAX >> 0) & 1;
|
BX_CPU_THIS_PTR efer.sce = (EAX >> 0) & 1;
|
||||||
BX_CPU_THIS_PTR msr.lme = (EAX >> 8) & 1;
|
BX_CPU_THIS_PTR efer.lme = (EAX >> 8) & 1;
|
||||||
BX_CPU_THIS_PTR msr.nxe = (EAX >> 11) & 1;
|
BX_CPU_THIS_PTR efer.nxe = (EAX >> 11) & 1;
|
||||||
BX_CPU_THIS_PTR msr.ffxsr = (EAX >> 14) & 1;
|
BX_CPU_THIS_PTR efer.ffxsr = (EAX >> 14) & 1;
|
||||||
return;
|
return;
|
||||||
|
|
||||||
case BX_MSR_STAR:
|
case BX_MSR_STAR:
|
||||||
@ -1966,13 +1970,13 @@ SYSCALL_LEGACY_MODE:
|
|||||||
|
|
||||||
BX_DEBUG(("Execute SYSCALL instruction"));
|
BX_DEBUG(("Execute SYSCALL instruction"));
|
||||||
|
|
||||||
if (!BX_CPU_THIS_PTR msr.sce) {
|
if (!BX_CPU_THIS_PTR efer.sce) {
|
||||||
exception(BX_UD_EXCEPTION, 0, 0);
|
exception(BX_UD_EXCEPTION, 0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
invalidate_prefetch_q();
|
invalidate_prefetch_q();
|
||||||
|
|
||||||
if (BX_CPU_THIS_PTR msr.lma)
|
if (BX_CPU_THIS_PTR efer.lma)
|
||||||
{
|
{
|
||||||
RCX = RIP;
|
RCX = RIP;
|
||||||
R11 = read_eflags() & ~(EFlagsRFMask);
|
R11 = read_eflags() & ~(EFlagsRFMask);
|
||||||
@ -2137,7 +2141,7 @@ SYSRET_NON_64BIT_MODE:
|
|||||||
|
|
||||||
BX_DEBUG(("Execute SYSRET instruction"));
|
BX_DEBUG(("Execute SYSRET instruction"));
|
||||||
|
|
||||||
if (!BX_CPU_THIS_PTR msr.sce) {
|
if (!BX_CPU_THIS_PTR efer.sce) {
|
||||||
exception(BX_UD_EXCEPTION, 0, 0);
|
exception(BX_UD_EXCEPTION, 0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: segment_ctrl_pro.cc,v 1.69 2007-03-14 21:15:15 sshwarts Exp $
|
// $Id: segment_ctrl_pro.cc,v 1.70 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||||
@ -41,7 +41,7 @@ BX_CPU_C::load_seg_reg(bx_segment_reg_t *seg, Bit16u new_value)
|
|||||||
if ((new_value & 0xfffc) == 0) { /* null selector */
|
if ((new_value & 0xfffc) == 0) { /* null selector */
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
// allow SS = 0 in 64 bit mode with cpl != 3
|
// allow SS = 0 in 64 bit mode with cpl != 3
|
||||||
if (BX_CPU_THIS_PTR msr.lma && CPL != 3) {
|
if (BX_CPU_THIS_PTR efer.lma && CPL != 3) {
|
||||||
seg->selector.index = 0;
|
seg->selector.index = 0;
|
||||||
seg->selector.ti = 0;
|
seg->selector.ti = 0;
|
||||||
seg->selector.rpl = 0;
|
seg->selector.rpl = 0;
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
// $Id: smm.cc,v 1.25 2007-07-09 15:16:13 sshwarts Exp $
|
// $Id: smm.cc,v 1.26 2007-09-10 20:47:08 sshwarts Exp $
|
||||||
/////////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////////
|
||||||
//
|
//
|
||||||
// Copyright (c) 2006 Stanislav Shwartsman
|
// Copyright (c) 2006 Stanislav Shwartsman
|
||||||
@ -142,10 +142,10 @@ void BX_CPU_C::enter_system_management_mode(void)
|
|||||||
BX_CPU_THIS_PTR cr4.setRegister(0);
|
BX_CPU_THIS_PTR cr4.setRegister(0);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// EFER.LME = 0, EFER.LME = 1
|
// EFER.LME = 0, EFER.LME = 0
|
||||||
#if BX_SUPPORT_X86_64
|
#if BX_SUPPORT_X86_64
|
||||||
BX_CPU_THIS_PTR msr.lme = 0;
|
BX_CPU_THIS_PTR efer.lme = 0;
|
||||||
BX_CPU_THIS_PTR msr.lma = 0;
|
BX_CPU_THIS_PTR efer.lma = 0;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
parse_selector(BX_CPU_THIS_PTR smbase >> 4,
|
parse_selector(BX_CPU_THIS_PTR smbase >> 4,
|
||||||
@ -359,26 +359,26 @@ bx_bool BX_CPU_C::smram_restore_state(const Bit32u *saved_state)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
BX_CPU_THIS_PTR msr.sce = (temp_efer >> 0) & 1;
|
BX_CPU_THIS_PTR efer.sce = (temp_efer >> 0) & 1;
|
||||||
BX_CPU_THIS_PTR msr.lme = (temp_efer >> 8) & 1;
|
BX_CPU_THIS_PTR efer.lme = (temp_efer >> 8) & 1;
|
||||||
BX_CPU_THIS_PTR msr.lma = (temp_efer >> 10) & 1;
|
BX_CPU_THIS_PTR efer.lma = (temp_efer >> 10) & 1;
|
||||||
BX_CPU_THIS_PTR msr.nxe = (temp_efer >> 11) & 1;
|
BX_CPU_THIS_PTR efer.nxe = (temp_efer >> 11) & 1;
|
||||||
BX_CPU_THIS_PTR msr.ffxsr = (temp_efer >> 14) & 1;
|
BX_CPU_THIS_PTR efer.ffxsr = (temp_efer >> 14) & 1;
|
||||||
|
|
||||||
if (BX_CPU_THIS_PTR msr.lma) {
|
if (BX_CPU_THIS_PTR efer.lma) {
|
||||||
if (temp_eflags & EFlagsVMMask) {
|
if (temp_eflags & EFlagsVMMask) {
|
||||||
BX_PANIC(("SMM restore: If EFER.LMA = 1 => RFLAGS.VM=0 !"));
|
BX_PANIC(("SMM restore: If EFER.LMA = 1 => RFLAGS.VM=0 !"));
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!BX_CPU_THIS_PTR cr4.get_PAE() || !pg || !pe || !BX_CPU_THIS_PTR msr.lme) {
|
if (!BX_CPU_THIS_PTR cr4.get_PAE() || !pg || !pe || !BX_CPU_THIS_PTR efer.lme) {
|
||||||
BX_PANIC(("SMM restore: If EFER.LMA = 1 <=> CR4.PAE, CR0.PG, CR0.PE, EFER.LME=1 !"));
|
BX_PANIC(("SMM restore: If EFER.LMA = 1 <=> CR4.PAE, CR0.PG, CR0.PE, EFER.LME=1 !"));
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (BX_CPU_THIS_PTR cr4.get_PAE() && pg && pe && BX_CPU_THIS_PTR msr.lme) {
|
if (BX_CPU_THIS_PTR cr4.get_PAE() && pg && pe && BX_CPU_THIS_PTR efer.lme) {
|
||||||
if (! BX_CPU_THIS_PTR msr.lma) {
|
if (! BX_CPU_THIS_PTR efer.lma) {
|
||||||
BX_PANIC(("SMM restore: If EFER.LMA = 1 <=> CR4.PAE, CR0.PG, CR0.PE, EFER.LME=1 !"));
|
BX_PANIC(("SMM restore: If EFER.LMA = 1 <=> CR4.PAE, CR0.PG, CR0.PE, EFER.LME=1 !"));
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user