From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received-SPF: Pass (sender SPF authorized) identity=mailfrom; client-ip=192.55.52.115; helo=mga14.intel.com; envelope-from=hao.a.wu@intel.com; receiver=edk2-devel@lists.01.org Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ml01.01.org (Postfix) with ESMTPS id C61BA21BADAB3 for ; Thu, 19 Jul 2018 22:26:32 -0700 (PDT) X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from orsmga002.jf.intel.com ([10.7.209.21]) by fmsmga103.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 19 Jul 2018 22:26:32 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.51,377,1526367600"; d="scan'208";a="76331890" Received: from shwdeopenpsi014.ccr.corp.intel.com ([10.239.9.19]) by orsmga002.jf.intel.com with ESMTP; 19 Jul 2018 22:26:29 -0700 From: Hao Wu To: edk2-devel@lists.01.org Cc: Jiewen Yao , Star Zeng Date: Fri, 20 Jul 2018 13:26:21 +0800 Message-Id: <20180720052626.24932-2-hao.a.wu@intel.com> X-Mailer: git-send-email 2.12.0.windows.1 In-Reply-To: <20180720052626.24932-1-hao.a.wu@intel.com> References: <20180720052626.24932-1-hao.a.wu@intel.com> Subject: [PATCH 1/6] MdePkg/SmmMemLib: Check for untested memory in GCD X-BeenThere: edk2-devel@lists.01.org X-Mailman-Version: 2.1.27 Precedence: list List-Id: EDK II Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 20 Jul 2018 05:26:33 -0000 From: Jiewen Yao It treats GCD untested memory as invalid SMM communication buffer. Cc: Star Zeng Contributed-under: TianoCore Contribution Agreement 1.1 Signed-off-by: Jiewen Yao --- MdePkg/Library/SmmMemLib/SmmMemLib.c | 96 +++++++++++++++++++- MdePkg/Library/SmmMemLib/SmmMemLib.inf | 1 + 2 files changed, 92 insertions(+), 5 deletions(-) diff --git a/MdePkg/Library/SmmMemLib/SmmMemLib.c b/MdePkg/Library/SmmMemLib/SmmMemLib.c index 8c78a0b426..3f79e46d46 100644 --- a/MdePkg/Library/SmmMemLib/SmmMemLib.c +++ b/MdePkg/Library/SmmMemLib/SmmMemLib.c @@ -25,12 +25,20 @@ #include #include #include +#include #include #include #include #include #include +// +// attributes for reserved memory before it is promoted to system memory +// +#define EFI_MEMORY_PRESENT 0x0100000000000000ULL +#define EFI_MEMORY_INITIALIZED 0x0200000000000000ULL +#define EFI_MEMORY_TESTED 0x0400000000000000ULL + #define NEXT_MEMORY_DESCRIPTOR(MemoryDescriptor, Size) \ ((EFI_MEMORY_DESCRIPTOR *)((UINT8 *)(MemoryDescriptor) + (Size))) @@ -46,10 +54,13 @@ UINTN mMemoryMapEntryCount; EFI_MEMORY_DESCRIPTOR *mMemoryMap; UINTN mDescriptorSize; +EFI_GCD_MEMORY_SPACE_DESCRIPTOR *mSmmMemLibGcdMemSpace = NULL; +UINTN mSmmMemLibGcdMemNumberOfDesc = 0; + VOID *mRegistrationEndOfDxe; VOID *mRegistrationReadyToLock; -BOOLEAN mSmmReadyToLock = FALSE; +BOOLEAN mSmmMemLibSmmReadyToLock = FALSE; /** Calculate and save the maximum support address. @@ -154,7 +165,7 @@ SmmIsBufferOutsideSmmValid ( // // Check override for Valid Communication Region // - if (mSmmReadyToLock) { + if (mSmmMemLibSmmReadyToLock) { EFI_MEMORY_DESCRIPTOR *MemoryMap; BOOLEAN InValidCommunicationRegion; @@ -171,12 +182,28 @@ SmmIsBufferOutsideSmmValid ( if (!InValidCommunicationRegion) { DEBUG (( EFI_D_ERROR, - "SmmIsBufferOutsideSmmValid: Not in ValidCommunicationRegion: Buffer (0x%lx) - Length (0x%lx), ", + "SmmIsBufferOutsideSmmValid: Not in ValidCommunicationRegion: Buffer (0x%lx) - Length (0x%lx)\n", Buffer, Length )); return FALSE; } + + // + // Check untested memory as invalid communication buffer. + // + for (Index = 0; Index < mSmmMemLibGcdMemNumberOfDesc; Index++) { + if (((Buffer >= mSmmMemLibGcdMemSpace[Index].BaseAddress) && (Buffer < mSmmMemLibGcdMemSpace[Index].BaseAddress + mSmmMemLibGcdMemSpace[Index].Length)) || + ((mSmmMemLibGcdMemSpace[Index].BaseAddress >= Buffer) && (mSmmMemLibGcdMemSpace[Index].BaseAddress < Buffer + Length))) { + DEBUG (( + EFI_D_ERROR, + "SmmIsBufferOutsideSmmValid: In Untested Memory Region: Buffer (0x%lx) - Length (0x%lx)\n", + Buffer, + Length + )); + return FALSE; + } + } } return TRUE; } @@ -317,6 +344,61 @@ SmmSetMem ( return EFI_SUCCESS; } +/** + Get GCD memory map. + Only record untested memory as invalid communication buffer. +**/ +VOID +SmmMemLibInternalGetGcdMemoryMap ( + VOID + ) +{ + UINTN NumberOfDescriptors; + EFI_GCD_MEMORY_SPACE_DESCRIPTOR *MemSpaceMap; + EFI_STATUS Status; + UINTN Index; + + Status = gDS->GetMemorySpaceMap (&NumberOfDescriptors, &MemSpaceMap); + if (EFI_ERROR (Status)) { + return ; + } + + mSmmMemLibGcdMemNumberOfDesc = 0; + for (Index = 0; Index < NumberOfDescriptors; Index++) { + if (MemSpaceMap[Index].GcdMemoryType == EfiGcdMemoryTypeReserved && + (MemSpaceMap[Index].Capabilities & (EFI_MEMORY_PRESENT | EFI_MEMORY_INITIALIZED | EFI_MEMORY_TESTED)) == + (EFI_MEMORY_PRESENT | EFI_MEMORY_INITIALIZED) + ) { + mSmmMemLibGcdMemNumberOfDesc++; + } + } + + mSmmMemLibGcdMemSpace = AllocateZeroPool (mSmmMemLibGcdMemNumberOfDesc * sizeof (EFI_GCD_MEMORY_SPACE_DESCRIPTOR)); + ASSERT (mSmmMemLibGcdMemSpace != NULL); + if (mSmmMemLibGcdMemSpace == NULL) { + mSmmMemLibGcdMemNumberOfDesc = 0; + gBS->FreePool (MemSpaceMap); + return ; + } + + mSmmMemLibGcdMemNumberOfDesc = 0; + for (Index = 0; Index < NumberOfDescriptors; Index++) { + if (MemSpaceMap[Index].GcdMemoryType == EfiGcdMemoryTypeReserved && + (MemSpaceMap[Index].Capabilities & (EFI_MEMORY_PRESENT | EFI_MEMORY_INITIALIZED | EFI_MEMORY_TESTED)) == + (EFI_MEMORY_PRESENT | EFI_MEMORY_INITIALIZED) + ) { + CopyMem ( + &mSmmMemLibGcdMemSpace[mSmmMemLibGcdMemNumberOfDesc], + &MemSpaceMap[Index], + sizeof(EFI_GCD_MEMORY_SPACE_DESCRIPTOR) + ); + mSmmMemLibGcdMemNumberOfDesc++; + } + } + + gBS->FreePool (MemSpaceMap); +} + /** Notification for SMM EndOfDxe protocol. @@ -415,10 +497,14 @@ SmmLibInternalEndOfDxeNotify ( gBS->FreePool (MemoryMap); + // + // Get additional information from GCD memory map. + // + SmmMemLibInternalGetGcdMemoryMap (); + return EFI_SUCCESS; } - /** Notification for SMM ReadyToLock protocol. @@ -436,7 +522,7 @@ SmmLibInternalReadyToLockNotify ( IN EFI_HANDLE Handle ) { - mSmmReadyToLock = TRUE; + mSmmMemLibSmmReadyToLock = TRUE; return EFI_SUCCESS; } /** diff --git a/MdePkg/Library/SmmMemLib/SmmMemLib.inf b/MdePkg/Library/SmmMemLib/SmmMemLib.inf index e4edad3af2..36576a4f2f 100644 --- a/MdePkg/Library/SmmMemLib/SmmMemLib.inf +++ b/MdePkg/Library/SmmMemLib/SmmMemLib.inf @@ -43,6 +43,7 @@ [LibraryClasses] SmmServicesTableLib UefiBootServicesTableLib + DxeServicesTableLib DebugLib BaseMemoryLib HobLib -- 2.16.2.windows.1