From c44218e5f40880e3100bdf4d112672e8dd56b94a Mon Sep 17 00:00:00 2001 From: Jian J Wang Date: Wed, 20 Dec 2017 16:47:15 +0800 Subject: MdeModulePkg/Core: Fix heap guard issues Three issues addressed here: a. Make NX memory protection and heap guard to be compatible The solution is to check PcdDxeNxMemoryProtectionPolicy in Heap Guard to see if the free memory should be set to NX, and set the Guard page to NX before it's freed back to memory pool. This can solve the issue which NX setting would be overwritten by Heap Guard feature in certain configuration. b. Returned pool address was not 8-byte aligned sometimes This happened only when BIT7 is not set in PcdHeapGuardPropertyMask. Since 8-byte alignment is UEFI spec required, letting allocated pool adjacent to tail guard page cannot be guaranteed. c. NULL address handling due to allocation failure When allocation failure, normally a NULL will be returned. But Heap Guard code will still try to adjust the starting address of it, which will cause a non-NULL pointer returned. Cc: Star Zeng Cc: Eric Dong Cc: Jiewen Yao Contributed-under: TianoCore Contribution Agreement 1.1 Signed-off-by: Jian J Wang Reviewed-by: Jiewen Yao --- MdeModulePkg/Core/PiSmmCore/HeapGuard.c | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) (limited to 'MdeModulePkg/Core/PiSmmCore') diff --git a/MdeModulePkg/Core/PiSmmCore/HeapGuard.c b/MdeModulePkg/Core/PiSmmCore/HeapGuard.c index 04fa1747a1..063a330b18 100644 --- a/MdeModulePkg/Core/PiSmmCore/HeapGuard.c +++ b/MdeModulePkg/Core/PiSmmCore/HeapGuard.c @@ -877,6 +877,15 @@ AdjustMemoryS ( { UINT64 Target; + // + // UEFI spec requires that allocated pool must be 8-byte aligned. If it's + // indicated to put the pool near the Tail Guard, we need extra bytes to + // make sure alignment of the returned pool address. + // + if ((PcdGet8 (PcdHeapGuardPropertyMask) & BIT7) == 0) { + SizeRequested = ALIGN_VALUE(SizeRequested, 8); + } + Target = Start + Size - SizeRequested; // @@ -1060,7 +1069,7 @@ AdjustPoolHeadA ( IN UINTN Size ) { - if ((PcdGet8 (PcdHeapGuardPropertyMask) & BIT7) != 0) { + if (Memory == 0 || (PcdGet8 (PcdHeapGuardPropertyMask) & BIT7) != 0) { // // Pool head is put near the head Guard // @@ -1070,6 +1079,7 @@ AdjustPoolHeadA ( // // Pool head is put near the tail Guard // + Size = ALIGN_VALUE (Size, 8); return (VOID *)(UINTN)(Memory + EFI_PAGES_TO_SIZE (NoPages) - Size); } @@ -1085,7 +1095,7 @@ AdjustPoolHeadF ( IN EFI_PHYSICAL_ADDRESS Memory ) { - if ((PcdGet8 (PcdHeapGuardPropertyMask) & BIT7) != 0) { + if (Memory == 0 || (PcdGet8 (PcdHeapGuardPropertyMask) & BIT7) != 0) { // // Pool head is put near the head Guard // -- cgit v1.2.3