PGMAllGst.h revision 88d5f0bc071bee7aabc1019c9bec949780abe7d2
5b281ba489ca18f0380d7efc7a5108b606cce449vboxsync * VBox - Page Manager, Guest Paging Template - All context code.
1c94c0a63ba68be1a7b2c640e70d7a06464e4fcavboxsync * Copyright (C) 2006-2007 innotek GmbH
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsync * available from http://www.virtualbox.org. This file is free software;
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsync * you can redistribute it and/or modify it under the terms of the GNU
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * General Public License (GPL) as published by the Free Software
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync/*******************************************************************************
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync* Defined Constants And Macros *
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync*******************************************************************************/
8e034cd2a6b0c86697554278e970163287003bb9vboxsync# define GST_BIG_PAGE_OFFSET_MASK X86_PAGE_4M_OFFSET_MASK
089c21a647af46044cad04a78cfdcfae814d2105vboxsync# define GST_BIG_PAGE_OFFSET_MASK X86_PAGE_2M_OFFSET_MASK
8e034cd2a6b0c86697554278e970163287003bb9vboxsync# define GST_TOTAL_PD_ENTRIES (X86_PG_PAE_ENTRIES*4)
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsync/*******************************************************************************
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsync* Internal Functions *
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsync*******************************************************************************/
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, GetPage)(PVM pVM, RTGCUINTPTR GCPtr, uint64_t *pfFlags, PRTGCPHYS pGCPhys);
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, ModifyPage)(PVM pVM, RTGCUINTPTR GCPtr, size_t cb, uint64_t fFlags, uint64_t fMask);
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, GetPDE)(PVM pVM, RTGCUINTPTR GCPtr, PX86PDEPAE pPDE);
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, MapCR3)(PVM pVM, RTGCPHYS GCPhysCR3);
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, MonitorCR3)(PVM pVM, RTGCPHYS GCPhysCR3);
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(bool, HandlerVirtualUpdate)(PVM pVM, uint32_t cr4);
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, WriteHandlerCR3)(PVM pVM, RTGCUINT uErrorCode, PCPUMCTXCORE pRegFrame, RTGCPTR pvFault, RTGCPHYS GCPhysFault, void *pvUser);
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, PAEWriteHandlerPD)(PVM pVM, RTGCUINT uErrorCode, PCPUMCTXCORE pRegFrame, RTGCPTR pvFault, RTGCPHYS GCPhysFault, void *pvUser);
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * Gets effective Guest OS page information.
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * When GCPtr is in a big page, the function will return as if it was a normal
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * 4KB page. If the need for distinguishing between big and normal page becomes
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * necessary at a later point, a PGMGstGetPage Ex() will be created for that
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * @returns VBox status.
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * @param pVM VM Handle.
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * @param GCPtr Guest Context virtual address of the page. Page aligned!
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * @param pfFlags Where to store the flags. These are X86_PTE_*, even for big pages.
8e034cd2a6b0c86697554278e970163287003bb9vboxsync * @param pGCPhys Where to store the GC physical address of the page.
2c203bb219df5391ed7f3888c85e12a4e47817davboxsync * This is page aligned. The fact that the
29bdc01040c07a3dd482a94a2cb8f0a90f8587a7vboxsyncPGM_GST_DECL(int, GetPage)(PVM pVM, RTGCUINTPTR GCPtr, uint64_t *pfFlags, PRTGCPHYS pGCPhys)
if (pfFlags)
if (pGCPhys)
return VINF_SUCCESS;
AssertFailed();
return VERR_NOT_IMPLEMENTED;
return VERR_PAGE_TABLE_NOT_PRESENT;
return rc;
return VERR_PAGE_NOT_PRESENT;
if (pfFlags)
if (pGCPhys)
if (pfFlags)
if (pGCPhys)
*pGCPhys = (Pde.u & GST_PDE4M_PG_MASK) | (GCPtr & (~GST_PDE4M_PG_MASK ^ ~GST_PTE_PG_MASK)); /** @todo pse36 */
return VINF_SUCCESS;
return VERR_NOT_SUPPORTED;
PGM_GST_DECL(int, ModifyPage)(PVM pVM, RTGCUINTPTR GCPtr, size_t cb, uint64_t fFlags, uint64_t fMask)
AssertFailed();
return VERR_NOT_IMPLEMENTED;
if (!pPde)
return VERR_PAGE_TABLE_NOT_PRESENT;
return VERR_PAGE_TABLE_NOT_PRESENT;
return rc;
if (!cb)
return VINF_SUCCESS;
iPTE++;
Pde.u = (Pde.u & (fMask | ((fMask & X86_PTE_PAT) << X86_PDE4M_PAT_SHIFT) | X86_PDE4M_PAE_PG_MASK | X86_PDE4M_PS)) /** @todo pse36 */
return VINF_SUCCESS;
return VINF_SUCCESS;
AssertFailed();
return VERR_NOT_IMPLEMENTED;
return VINF_SUCCESS;
AssertFailed();
return VERR_NOT_IMPLEMENTED;
int rc = pgmRamGCPhys2HCPtrAndHCPhysWithFlags(&pVM->pgm.s, GCPhysCR3, &HCPtrGuestCR3, &HCPhysGuestCR3);
rc = PGMMap(pVM, (RTGCUINTPTR)pVM->pgm.s.GCPtrCR3Mapping, HCPhysGuestCR3 & X86_PTE_PAE_PG_MASK, PAGE_SIZE, 0);
return rc;
/** PAE todo: pVM->pgm.s.apGstPaePDsHC? -> unmap?? */
AssertFailed();
return rc;
# ifndef PGMPOOL_WITH_MIXED_PT_CR3
rc = PGMHandlerPhysicalModify(pVM, pVM->pgm.s.GCPhysGstCR3Monitored, GCPhysCR3, GCPhysCR3 + cbCR3Stuff - 1);
rc = PGMHandlerPhysicalRegisterEx(pVM, PGMPHYSHANDLERTYPE_PHYSICAL_WRITE, GCPhysCR3, GCPhysCR3 + cbCR3Stuff - 1,
AssertMsgFailed(("PGMHandlerPhysicalModify/PGMR3HandlerPhysicalRegister failed, rc=%Rrc GCPhysGstCR3Monitored=%RGp GCPhysCR3=%RGp\n",
return rc;
# ifndef PGMPOOL_WITH_MIXED_PT_CR3
rc = PGMHandlerPhysicalModify(pVM, pVM->pgm.s.aGCPhysGstPaePDsMonitored[i], GCPhys, GCPhys + PAGE_SIZE - 1);
rc = PGMHandlerPhysicalRegisterEx(pVM, PGMPHYSHANDLERTYPE_PHYSICAL_WRITE, GCPhys, GCPhys + PAGE_SIZE - 1,
AssertFailed();
GCPhys);
AssertMsgFailed(("PGMHandlerPhysicalModify/PGMR3HandlerPhysicalRegister failed, rc=%Rrc GCPhysGstCR3Monitored=%RGp GCPhysCR3=%RGp\n",
return rc;
return rc;
# ifndef PGMPOOL_WITH_MIXED_PT_CR3
: PGMPOOL_IDX_PD);
# ifndef PGMPOOL_WITH_MIXED_PT_CR3
AssertFailed();
: PGMPOOL_IDX_PD);
return rc;
* @param pvUser Pointer to a PGMVHUARGS structure (see PGM.cpp).
static DECLCALLBACK(int) PGM_GST_NAME(VirtHandlerUpdateOne)(PAVLROGCPTRNODECORE pNode, void *pvUser)
unsigned fFlags;
case PGMVIRTHANDLERTYPE_WRITE: fFlags = MM_RAM_FLAGS_VIRTUAL_HANDLER | MM_RAM_FLAGS_VIRTUAL_WRITE; break;
case PGMVIRTHANDLERTYPE_ALL: fFlags = MM_RAM_FLAGS_VIRTUAL_HANDLER | MM_RAM_FLAGS_VIRTUAL_ALL; break;
unsigned iPage = 0;
("{.Core.Key=%VGp, .Core.KeyLast=%VGp, .offVirtHandler=%#RX32, .offNextAlias=%#RX32} GCPhysNew=%VGp\n",
offPage = 0;
("{.Core.Key=%VGp, .Core.KeyLast=%VGp, .offVirtHandler=%#RX32, .offNextAlias=%#RX32} GCPhysNew=%VGp\n",
offPage = 0;
AssertFailed();
RTAvlroGCPtrDoWithAll(&pVM->pgm.s.CTXSUFF(pTrees)->VirtHandlers, true, PGM_GST_NAME(VirtHandlerUpdateOne), &State);
RTAvlroGCPtrDoWithAll(&pVM->pgm.s.CTXSUFF(pTrees)->VirtHandlers, true, pgmHandlerVirtualResetOne, pVM);
PGM_GST_DECL(int, WriteHandlerCR3)(PVM pVM, RTGCUINT uErrorCode, PCPUMCTXCORE pRegFrame, RTGCPTR pvFault, RTGCPHYS GCPhysFault, void *pvUser)
#ifdef DEBUG
Log(("pgmXXGst32BitWriteHandlerCR3: emulated change to PD %#x addr=%VGv\n", iPD1, iPD1 << X86_PD_SHIFT));
Log(("pgmXXGst32BitWriteHandlerCR3: emulated change to PD %#x addr=%VGv\n", iPD2, iPD2 << X86_PD_SHIFT));
Log(("pgmXXGst32BitWriteHandlerCR3: detected conflict iPD1=%#x iPD2=%#x - returns %Rrc\n", iPD1, iPD2, rc));
return rc;
return rc;
PGM_GST_DECL(int, WriteHandlerCR3)(PVM pVM, RTGCUINT uErrorCode, PCPUMCTXCORE pRegFrame, RTGCPTR pvFault, RTGCPHYS GCPhysFault, void *pvUser)
return rc;
PGM_GST_DECL(int, WriteHandlerPD)(PVM pVM, RTGCUINT uErrorCode, PCPUMCTXCORE pRegFrame, RTGCPTR pvFault, RTGCPHYS GCPhysFault, void *pvUser)
RTGCUINTPTR i;
#ifdef DEBUG
return VINF_PGM_SYNC_CR3;
return rc;