mirror of
https://github.com/reactos/reactos.git
synced 2025-05-28 21:48:19 +00:00
[NTOS]: When grabbing physically contigous pages from the zero or free list, make sure to re-initialize their PFN entries correctly, since their data might be stale. Fixes potential weird memory corruption bugs.
[NTOS]: Physically contiguous memory allocations are not guaranteed to be zeroed, so do not zero the pages. [NTOS]: When allocating contigous memory, mark the PFN entries appropriately after mapping the I/O ranges. [NTOS]: When freeing contiguous memory, assert that all the freed pages correspond to PFN entries that we expect to have allocated for this purpose. Detects (not neccessarily fixes) memory corruption issues in contiguous memory allocations. [NTOS]: These changes mostly affect certain network card and sound card systems/real hardware, they fix possible bugs and detect corruption that was otherwise going by unnoticed. svn path=/trunk/; revision=47186
This commit is contained in:
parent
b320b4bcb1
commit
3a80da9a3e
1 changed files with 48 additions and 34 deletions
|
@ -132,22 +132,13 @@ MiFindContiguousPages(IN PFN_NUMBER LowestPfn,
|
|||
//
|
||||
MiUnlinkFreeOrZeroedPage(Pfn1);
|
||||
Pfn1->u3.e2.ReferenceCount = 1;
|
||||
|
||||
//
|
||||
// Check if it was already zeroed
|
||||
//
|
||||
if (Pfn1->u3.e1.PageLocation != ZeroedPageList)
|
||||
{
|
||||
//
|
||||
// It wasn't, so zero it
|
||||
//
|
||||
MiZeroPage(MiGetPfnEntryIndex(Pfn1));
|
||||
}
|
||||
|
||||
//
|
||||
// Mark it in use
|
||||
//
|
||||
Pfn1->u2.ShareCount = 1;
|
||||
Pfn1->u3.e1.PageLocation = ActiveAndValid;
|
||||
Pfn1->u3.e1.StartOfAllocation = 0;
|
||||
Pfn1->u3.e1.EndOfAllocation = 0;
|
||||
Pfn1->u3.e1.PrototypePte = 0;
|
||||
Pfn1->u4.VerifierAllocation = 0;
|
||||
Pfn1->PteAddress = (PVOID)0xBAADF00D;
|
||||
|
||||
//
|
||||
// Check if this is the last PFN, otherwise go on
|
||||
|
@ -331,7 +322,10 @@ MiFindContiguousMemory(IN PFN_NUMBER LowestPfn,
|
|||
{
|
||||
PFN_NUMBER Page;
|
||||
PHYSICAL_ADDRESS PhysicalAddress;
|
||||
PAGED_CODE ();
|
||||
PMMPFN Pfn1, EndPfn;
|
||||
PMMPTE PointerPte;
|
||||
PVOID BaseAddress;
|
||||
PAGED_CODE();
|
||||
ASSERT(SizeInPages != 0);
|
||||
|
||||
//
|
||||
|
@ -348,7 +342,22 @@ MiFindContiguousMemory(IN PFN_NUMBER LowestPfn,
|
|||
// We'll just piggyback on the I/O memory mapper
|
||||
//
|
||||
PhysicalAddress.QuadPart = Page << PAGE_SHIFT;
|
||||
return MmMapIoSpace(PhysicalAddress, SizeInPages << PAGE_SHIFT, CacheType);
|
||||
BaseAddress = MmMapIoSpace(PhysicalAddress, SizeInPages << PAGE_SHIFT, CacheType);
|
||||
ASSERT(BaseAddress);
|
||||
|
||||
/* Loop the PFN entries */
|
||||
Pfn1 = MiGetPfnEntry(Page);
|
||||
EndPfn = Pfn1 + SizeInPages;
|
||||
PointerPte = MiAddressToPte(BaseAddress);
|
||||
do
|
||||
{
|
||||
/* Write the PTE address */
|
||||
Pfn1->PteAddress = PointerPte++;
|
||||
Pfn1->u4.PteFrame = PFN_FROM_PTE(MiAddressToPte(PointerPte));
|
||||
} while (Pfn1++ < EndPfn);
|
||||
|
||||
/* Return the address */
|
||||
return BaseAddress;
|
||||
}
|
||||
|
||||
PVOID
|
||||
|
@ -437,6 +446,7 @@ MiFreeContiguousMemory(IN PVOID BaseAddress)
|
|||
KIRQL OldIrql;
|
||||
PFN_NUMBER PageFrameIndex, LastPage, PageCount;
|
||||
PMMPFN Pfn1, StartPfn;
|
||||
PMMPTE PointerPte;
|
||||
PAGED_CODE();
|
||||
|
||||
//
|
||||
|
@ -455,10 +465,9 @@ MiFreeContiguousMemory(IN PVOID BaseAddress)
|
|||
return;
|
||||
}
|
||||
|
||||
//
|
||||
// Otherwise, get the PTE and page number for the allocation
|
||||
//
|
||||
PageFrameIndex = PFN_FROM_PTE(MiAddressToPte(BaseAddress));
|
||||
/* Get the PTE and frame number for the allocation*/
|
||||
PointerPte = MiAddressToPte(BaseAddress);
|
||||
PageFrameIndex = PFN_FROM_PTE(PointerPte);
|
||||
|
||||
//
|
||||
// Now get the PFN entry for this, and make sure it's the correct one
|
||||
|
@ -469,7 +478,7 @@ MiFreeContiguousMemory(IN PVOID BaseAddress)
|
|||
//
|
||||
// This probably means you did a free on an address that was in between
|
||||
//
|
||||
KeBugCheckEx (BAD_POOL_CALLER,
|
||||
KeBugCheckEx(BAD_POOL_CALLER,
|
||||
0x60,
|
||||
(ULONG_PTR)BaseAddress,
|
||||
0,
|
||||
|
@ -482,14 +491,19 @@ MiFreeContiguousMemory(IN PVOID BaseAddress)
|
|||
StartPfn = Pfn1;
|
||||
Pfn1->u3.e1.StartOfAllocation = 0;
|
||||
|
||||
//
|
||||
// Look the PFNs
|
||||
//
|
||||
/* Look the PFNs until we find the one that marks the end of the allocation */
|
||||
do
|
||||
{
|
||||
//
|
||||
// Until we find the one that marks the end of the allocation
|
||||
//
|
||||
/* Make sure these are the pages we setup in the allocation routine */
|
||||
ASSERT(Pfn1->u3.e2.ReferenceCount == 1);
|
||||
ASSERT(Pfn1->u2.ShareCount == 1);
|
||||
ASSERT(Pfn1->PteAddress == PointerPte);
|
||||
ASSERT(Pfn1->u3.e1.PageLocation == ActiveAndValid);
|
||||
ASSERT(Pfn1->u4.VerifierAllocation == 0);
|
||||
ASSERT(Pfn1->u3.e1.PrototypePte == 0);
|
||||
|
||||
/* Keep going for assertions */
|
||||
PointerPte++;
|
||||
} while (Pfn1++->u3.e1.EndOfAllocation == 0);
|
||||
|
||||
//
|
||||
|
|
Loading…
Reference in a new issue