Leaked source code of windows server 2003
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
|
|
/*++
Copyright (c) 1989 Microsoft Corporation
Module Name:
checkpte.c
Abstract:
This module contains routines for sanity checking the page directory.
Author:
Lou Perazzoli (loup) 25-Apr-1989 Landy Wang (landyw) 02-June-1997
Revision History:
--*/
#include "mi.h"
#if DBG
VOID CheckValidPte ( IN PMMPTE PointerPte );
VOID MiCheckPte ( VOID )
/*++
Routine Description:
This routine checks each page table page in an address space to ensure it is in the proper state.
Arguments:
None.
Return Value:
None.
Environment:
Kernel mode, APCs disabled.
--*/
{ ULONG i; ULONG j; PMMPTE PointerPte; PMMPTE PointerPde; PMMPFN Pfn1; ULONG ValidCount; ULONG TransitionCount; KIRQL OldIrql; PEPROCESS TargetProcess; USHORT UsedPages;
TargetProcess = PsGetCurrentProcess ();
PointerPde = MiGetPdeAddress (NULL);
UsedPages = 0;
LOCK_WS (TargetProcess); LOCK_PFN (OldIrql);
for (i = 0; i < PDE_PER_PAGE; i += 1) {
if (PointerPde->u.Hard.Valid) { ValidCount = 0; TransitionCount = 0; CheckValidPte (PointerPde);
PointerPte = MiGetVirtualAddressMappedByPte (PointerPde);
for (j = 0; j < PTE_PER_PAGE; j += 1) {
if ((PointerPte >= MiGetPteAddress(HYPER_SPACE)) && (PointerPte < MiGetPteAddress(WORKING_SET_LIST))) {
goto endloop; }
if (PointerPte->u.Hard.Valid) { ValidCount += 1; CheckValidPte (PointerPte); } else {
if ((PointerPte->u.Soft.Transition == 1) && (PointerPte->u.Soft.Prototype == 0)) {
//
// Transition PTE, up the transition count.
//
TransitionCount += 1; } }
if (PointerPte->u.Long != 0) { UsedPages += 1; } endloop: PointerPte += 1; } if ((i < 512) || (i == 896)) { #if !defined (_WIN64)
if (MmWorkingSetList->UsedPageTableEntries[i] != UsedPages) { DbgPrint("used pages and page table used not equal %lx %lx %lx\n", i,MmWorkingSetList->UsedPageTableEntries[i], UsedPages); } #endif
}
//
// Check the share count for the page table page.
//
if ((i < 511) || (i == 896)) { Pfn1 = MI_PFN_ELEMENT (PointerPde->u.Hard.PageFrameNumber); if (Pfn1->u2.ShareCount != ((ULONG)1+ValidCount+TransitionCount)) { DbgPrint("share count for page table page bad - %lx %lx %lx\n", i,ValidCount, TransitionCount); MiFormatPfn(Pfn1); } } } PointerPde += 1; UsedPages = 0; }
UNLOCK_PFN (OldIrql); UNLOCK_WS (TargetProcess);
return; }
VOID CheckValidPte ( IN PMMPTE PointerPte )
{ PMMPFN Pfn1; PMMPTE PointerPde;
if (MI_GET_PAGE_FRAME_FROM_PTE (PointerPte) > MmNumberOfPhysicalPages) { return; }
Pfn1 = MI_PFN_ELEMENT(PointerPte->u.Hard.PageFrameNumber);
#if 0
if (PointerPte->u.Hard.PageFrameNumber == 0) { DbgPrint("physical page zero mapped\n"); MiFormatPte(PointerPte); MiFormatPfn(Pfn1); } #endif
if (Pfn1->u3.e1.PageLocation != ActiveAndValid) { DbgPrint("valid PTE with page frame not active and valid\n"); MiFormatPfn(Pfn1); MiFormatPte(PointerPte); }
if (Pfn1->u3.e1.PrototypePte == 0) {
//
// This is not a prototype PTE.
//
if (Pfn1->PteAddress != PointerPte) { DbgPrint("checkpte - Pfn PTE address and PTE address not equal\n"); MiFormatPte(PointerPte); MiFormatPfn(Pfn1); return; } }
if (!MmIsAddressValid(Pfn1->PteAddress)) { return; }
PointerPde = MiGetPteAddress (Pfn1->PteAddress);
if (PointerPde->u.Hard.Valid == 1) { if (MI_GET_PAGE_FRAME_FROM_PTE (PointerPde) != Pfn1->u4.PteFrame) { DbgPrint("checkpte - pteframe not right\n"); MiFormatPfn(Pfn1); MiFormatPte(PointerPte); MiFormatPte(PointerPde); } }
return; }
#endif
|