From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91449+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91449+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150327; cv=none; d=zohomail.com; s=zohoarc; b=HQ+EDTP6DF2Nhy1H/HD2mvEA1p6/FiZMmF7+62HkoZBB7pW8kWJvWwQKX5URmERjux5EmEzL+LnyeRaGfsxPdaeXda0J9TPNcf309xiTiYrR0mWmBCM1TtXsd3oGvuHfg6E4AOxOUGFbUTnSKGGg0NodcaPcnOYHxa0adL5lxYE= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150327; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=MBEjrzkMaNPVLiVJS8nz3SwKWpA2+NW7eSghuu+bBg8=; b=FeDwN/khlqCA1Y5jZNz5Mu7TjzfW/Q3cefGBHJUXvvCqhDDbdm81BX2Y6drp0Vx0+hnw/TLzIjwnzGN5+Q+xbqktfqMwE4yOBMrv0lKHT214/KW6E74dfCyuwCfHVMVfn023r8N2SbNEHYE2UbC4IDjWrv7A5IGN5uH5jn+q9bQ= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91449+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 165815032740176.74836566823365; Mon, 18 Jul 2022 06:18:47 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id 2cj4YY1788612xq9LPcEpJFL; Mon, 18 Jul 2022 06:18:47 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web12.27079.1658150325580236005 for ; Mon, 18 Jul 2022 06:18:45 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363886" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363886" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:40 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624724945" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:39 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Eric Dong Subject: [edk2-devel] [PATCH 01/10] UefiCpuPkg: Create CpuPageTableLib for manipulating X86 paging structs Date: Mon, 18 Jul 2022 21:18:22 +0800 Message-Id: <20220718131831.660-2-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: 9OrY0YpLp7BbCO73HuzroELux1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150327; bh=R2el/dOZ9s2lAhcVYwUoExabZktTm6mIFdw6DyBM6ao=; h=Cc:Date:From:Reply-To:Subject:To; b=VMljbiGLdTjeGU5u4eQ5w1NpobvgdMAxB5H9gU4QZILS5HA/tG6yncTmue2Vq51ja6U BSP5pkEkro1cX4pJQ/urcYr4Atwi9uqK/AwRI1cUsAazURcIm7Yu+Rmqcnz+z8HW10F3b 3xlrfgRsgtDcVctqsdBzONjzyeH4KaaHLWY= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150329601100012 Content-Type: text/plain; charset="utf-8" The lib includes two APIs: * PageTableMap It creates/updates mapping from LA to PA. The implementation only supports paging structures used in 64bit mode now. PAE paging structure support will be added in future. * PageTableParse It parses the page table and returns the mapping relations in an array of IA32_MAP_ENTRY. It passed some stress tests. These test code will be upstreamed in other patches following edk2 Unit Test framework. Signed-off-by: Ray Ni Cc: Eric Dong Reviewed-by: Eric Dong --- UefiCpuPkg/Include/Library/CpuPageTableLib.h | 129 +++++ .../Library/CpuPageTableLib/CpuPageTable.h | 204 +++++++ .../CpuPageTableLib/CpuPageTableLib.inf | 35 ++ .../Library/CpuPageTableLib/CpuPageTableMap.c | 543 ++++++++++++++++++ .../CpuPageTableLib/CpuPageTableParse.c | 330 +++++++++++ UefiCpuPkg/UefiCpuPkg.dec | 3 + UefiCpuPkg/UefiCpuPkg.dsc | 4 +- 7 files changed, 1247 insertions(+), 1 deletion(-) create mode 100644 UefiCpuPkg/Include/Library/CpuPageTableLib.h create mode 100644 UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h create mode 100644 UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf create mode 100644 UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c create mode 100644 UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableParse.c diff --git a/UefiCpuPkg/Include/Library/CpuPageTableLib.h b/UefiCpuPkg/Incl= ude/Library/CpuPageTableLib.h new file mode 100644 index 0000000000..2dc9b7d18e --- /dev/null +++ b/UefiCpuPkg/Include/Library/CpuPageTableLib.h @@ -0,0 +1,129 @@ +/** @file + Public include file for PageTableLib library. + + Copyright (c) 2022, Intel Corporation. All rights reserved.
+ SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +#ifndef PAGE_TABLE_LIB_H_ +#define PAGE_TABLE_LIB_H_ + +typedef union { + struct { + UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory + UINT64 ReadWrite : 1; // 0 =3D Read-Only, 1=3D Read/Write + UINT64 UserSupervisor : 1; // 0 =3D Supervisor, 1=3DUser + UINT64 WriteThrough : 1; // 0 =3D Write-Back caching, 1=3DW= rite-Through caching + UINT64 CacheDisabled : 1; // 0 =3D Cached, 1=3DNon-Cached + UINT64 Accessed : 1; // 0 =3D Not accessed, 1 =3D Acces= sed (set by CPU) + UINT64 Dirty : 1; // 0 =3D Not dirty, 1 =3D Dirty (s= et by CPU) + UINT64 Pat : 1; // PAT + + UINT64 Global : 1; // 0 =3D Not global, 1 =3D Global = (if CR4.PGE =3D 1) + UINT64 Reserved1 : 3; // Ignored + + UINT64 PageTableBaseAddress : 40; // Page Table Base Address + UINT64 Reserved2 : 7; // Ignored + UINT64 ProtectionKey : 4; // Protection key + UINT64 Nx : 1; // No Execute bit + } Bits; + UINT64 Uint64; +} IA32_MAP_ATTRIBUTE; + +#define IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS_MASK 0xFFFFFFFFFF000ull +#define IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS(pa) ((pa)->Uint64 & IA= 32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS_MASK) +#define IA32_MAP_ATTRIBUTE_ATTRIBUTES(pa) ((pa)->Uint64 & ~I= A32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS_MASK) + +// +// Below enum follows "4.1.1 Four Paging Modes" in Chapter 4 Paging of SDM= Volume 3. +// Page1GB is only supported in 4-level and 5-level. +// +typedef enum { + Paging32bit, + + // + // High byte in paging mode indicates the max levels of the page table. + // Low byte in paging mode indicates the max level that can be a leaf en= try. + // + PagingPae =3D 0x0302, + + Paging4Level =3D 0x0402, + Paging4Level1GB =3D 0x0403, + + Paging5Level =3D 0x0502, + Paging5Level1GB =3D 0x0503, + + PagingModeMax +} PAGING_MODE; + +/** + Create or update page table to map [LinearAddress, LinearAddress + Lengt= h) with specified attribute. + + @param[in, out] PageTable The pointer to the page table to update, = or pointer to NULL if a new page table is to be created. + @param[in] PagingMode The paging mode. + @param[in] Buffer The free buffer to be used for page table= creation/updating. + @param[in, out] BufferSize The buffer size. + On return, the remaining buffer size. + The free buffer is used from the end so c= aller can supply the same Buffer pointer with an updated + BufferSize in the second call to this API. + @param[in] LinearAddress The start of the linear address range. + @param[in] Length The length of the linear address range. + @param[in] Attribute The attribute of the linear address range. + All non-reserved fields in IA32_MAP_ATTRI= BUTE are supported to set in the page table. + Page table entries that map the linear ad= dress range are reset to 0 before set to the new attribute + when a new physical base address is set. + @param[in] Mask The mask used for attribute. The correspo= nding field in Attribute is ignored if that in Mask is 0. + + @retval RETURN_UNSUPPORTED PagingMode is not supported. + @retval RETURN_INVALID_PARAMETER PageTable, BufferSize, Attribute or Ma= sk is NULL. + @retval RETURN_INVALID_PARAMETER *BufferSize is not multiple of 4KB. + @retval RETURN_BUFFER_TOO_SMALL The buffer is too small for page table= creation/updating. + BufferSize is updated to indicate the = expected buffer size. + Caller may still get RETURN_BUFFER_TOO= _SMALL with the new BufferSize. + @retval RETURN_SUCCESS PageTable is created/updated successfu= lly. +**/ +RETURN_STATUS +EFIAPI +PageTableMap ( + IN OUT UINTN *PageTable OPTIONAL, + IN PAGING_MODE PagingMode, + IN VOID *Buffer, + IN OUT UINTN *BufferSize, + IN UINT64 LinearAddress, + IN UINT64 Length, + IN IA32_MAP_ATTRIBUTE *Attribute, + IN IA32_MAP_ATTRIBUTE *Mask + ); + +typedef struct { + UINT64 LinearAddress; + UINT64 Length; + IA32_MAP_ATTRIBUTE Attribute; +} IA32_MAP_ENTRY; + +/** + Parse page table. + + @param[in] PageTable Pointer to the page table. + @param[in] PagingMode The paging mode. + @param[out] Map Return an array that describes multiple linea= r address ranges. + @param[in, out] MapCount On input, the maximum number of entries that = Map can hold. + On output, the number of entries in Map. + + @retval RETURN_UNSUPPORTED PageLevel is not 5 or 4. + @retval RETURN_INVALID_PARAMETER MapCount is NULL. + @retval RETURN_INVALID_PARAMETER *MapCount is not 0 but Map is NULL. + @retval RETURN_BUFFER_TOO_SMALL *MapCount is too small. + @retval RETURN_SUCCESS Page table is parsed successfully. +**/ +RETURN_STATUS +EFIAPI +PageTableParse ( + IN UINTN PageTable, + IN PAGING_MODE PagingMode, + IN IA32_MAP_ENTRY *Map, + IN OUT UINTN *MapCount + ); + +#endif diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h b/UefiCpuPkg= /Library/CpuPageTableLib/CpuPageTable.h new file mode 100644 index 0000000000..c041ea3f56 --- /dev/null +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h @@ -0,0 +1,204 @@ +/** @file + Internal header for CpuPageTableLib. + + Copyright (c) 2022, Intel Corporation. All rights reserved.
+ SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +#ifndef CPU_PAGE_TABLE_H_ +#define CPU_PAGE_TABLE_H_ + +#include +#include +#include +#include +#include + +#define IA32_PE_BASE_ADDRESS_MASK_40 0xFFFFFFFFFF000ull +#define IA32_PE_BASE_ADDRESS_MASK_39 0xFFFFFFFFFE000ull + +#define REGION_LENGTH(l) LShiftU64 (1, (l) * 9 + 3) + +typedef struct { + UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory +} IA32_PAGE_COMMON_ENTRY; + +/// +/// Format of a non-leaf entry that references a page table entry +/// +typedef union { + struct { + UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory + UINT64 ReadWrite : 1; // 0 =3D Read-Only, 1=3D Read/Write + UINT64 UserSupervisor : 1; // 0 =3D Supervisor, 1=3DUser + UINT64 WriteThrough : 1; // 0 =3D Write-Back caching, 1=3DW= rite-Through caching + UINT64 CacheDisabled : 1; // 0 =3D Cached, 1=3DNon-Cached + UINT64 Accessed : 1; // 0 =3D Not accessed, 1 =3D Acces= sed (set by CPU) + UINT64 Available0 : 1; // Ignored + UINT64 MustBeZero : 1; // Must Be Zero + + UINT64 Available2 : 4; // Ignored + + UINT64 PageTableBaseAddress : 40; // Page Table Base Address + UINT64 Available3 : 11; // Ignored + UINT64 Nx : 1; // No Execute bit + } Bits; + UINT64 Uint64; +} IA32_PAGE_NON_LEAF_ENTRY; + +#define IA32_PNLE_PAGE_TABLE_BASE_ADDRESS(pa) ((pa)->Uint64 & IA32_PE_BAS= E_ADDRESS_MASK_40) + +/// +/// Format of a PML5 Entry (PML5E) that References a PML4 Table +/// +typedef IA32_PAGE_NON_LEAF_ENTRY IA32_PML5E; + +/// +/// Format of a PML4 Entry (PML4E) that References a Page-Directory-Pointe= r Table +/// +typedef IA32_PAGE_NON_LEAF_ENTRY IA32_PML4E; + +/// +/// Format of a Page-Directory-Pointer-Table Entry (PDPTE) that References= a Page Directory +/// +typedef IA32_PAGE_NON_LEAF_ENTRY IA32_PDPTE; + +/// +/// Format of a Page-Directory Entry that References a Page Table +/// +typedef IA32_PAGE_NON_LEAF_ENTRY IA32_PDE; + +/// +/// Format of a leaf entry that Maps a 1-Gbyte or 2-MByte Page +/// +typedef union { + struct { + UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory + UINT64 ReadWrite : 1; // 0 =3D Read-Only, 1=3D Read/Write + UINT64 UserSupervisor : 1; // 0 =3D Supervisor, 1=3DUser + UINT64 WriteThrough : 1; // 0 =3D Write-Back caching, 1=3DW= rite-Through caching + UINT64 CacheDisabled : 1; // 0 =3D Cached, 1=3DNon-Cached + UINT64 Accessed : 1; // 0 =3D Not accessed, 1 =3D Acces= sed (set by CPU) + UINT64 Dirty : 1; // 0 =3D Not dirty, 1 =3D Dirty (s= et by CPU) + UINT64 MustBeOne : 1; // Page Size. Must Be One + + UINT64 Global : 1; // 0 =3D Not global, 1 =3D Global = (if CR4.PGE =3D 1) + UINT64 Available1 : 3; // Ignored + UINT64 Pat : 1; // PAT + + UINT64 PageTableBaseAddress : 39; // Page Table Base Address + UINT64 Available3 : 7; // Ignored + UINT64 ProtectionKey : 4; // Protection key + UINT64 Nx : 1; // No Execute bit + } Bits; + UINT64 Uint64; +} IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE; +#define IA32_PLEB_PAGE_TABLE_BASE_ADDRESS(pa) ((pa)->Uint64 & IA32_PE_BAS= E_ADDRESS_MASK_39) + +/// +/// Format of a Page-Directory Entry that Maps a 2-MByte Page +/// +typedef IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE IA32_PDE_2M; + +/// +/// Format of a Page-Directory-Pointer-Table Entry (PDPTE) that Maps a 1-G= Byte Page +/// +typedef IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE IA32_PDPTE_1G; + +/// +/// Format of a Page-Table Entry that Maps a 4-KByte Page +/// +typedef union { + struct { + UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory + UINT64 ReadWrite : 1; // 0 =3D Read-Only, 1=3D Read/Write + UINT64 UserSupervisor : 1; // 0 =3D Supervisor, 1=3DUser + UINT64 WriteThrough : 1; // 0 =3D Write-Back caching, 1=3DW= rite-Through caching + UINT64 CacheDisabled : 1; // 0 =3D Cached, 1=3DNon-Cached + UINT64 Accessed : 1; // 0 =3D Not accessed, 1 =3D Acces= sed (set by CPU) + UINT64 Dirty : 1; // 0 =3D Not dirty, 1 =3D Dirty (s= et by CPU) + UINT64 Pat : 1; // PAT + + UINT64 Global : 1; // 0 =3D Not global, 1 =3D Global = (if CR4.PGE =3D 1) + UINT64 Available1 : 3; // Ignored + + UINT64 PageTableBaseAddress : 40; // Page Table Base Address + UINT64 Available3 : 7; // Ignored + UINT64 ProtectionKey : 4; // Protection key + UINT64 Nx : 1; // No Execute bit + } Bits; + UINT64 Uint64; +} IA32_PTE_4K; +#define IA32_PTE4K_PAGE_TABLE_BASE_ADDRESS(pa) ((pa)->Uint64 & IA32_PE_BA= SE_ADDRESS_MASK_40) + +/// +/// Format of a Page-Directory-Pointer-Table Entry (PDPTE) that References= a Page Directory (32bit PAE specific) +/// +typedef union { + struct { + UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory + UINT64 MustBeZero : 2; // Must Be Zero + UINT64 WriteThrough : 1; // 0 =3D Write-Back caching, 1=3DW= rite-Through caching + UINT64 CacheDisabled : 1; // 0 =3D Cached, 1=3DNon-Cached + UINT64 MustBeZero2 : 4; // Must Be Zero + + UINT64 Available : 3; // Ignored + + UINT64 PageTableBaseAddress : 40; // Page Table Base Address + UINT64 MustBeZero3 : 12; // Must Be Zero + } Bits; + UINT64 Uint64; +} IA32_PDPTE_PAE; + +typedef union { + IA32_PAGE_NON_LEAF_ENTRY Pnle; // To access Pml5, Pml4, Pdpt= e and Pde. + IA32_PML5E Pml5; + IA32_PML4E Pml4; + IA32_PDPTE Pdpte; + IA32_PDE Pde; + + IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE PleB; // to access Pdpte1G and Pde2= M. + IA32_PDPTE_1G Pdpte1G; + IA32_PDE_2M Pde2M; + + IA32_PTE_4K Pte4K; + + IA32_PDPTE_PAE PdptePae; + IA32_PAGE_COMMON_ENTRY Pce; // To access all common bits i= n above entries. + + UINT64 Uint64; + UINTN Uintn; +} IA32_PAGING_ENTRY; + +/** + Return TRUE when the page table entry is a leaf entry that points to the= physical address memory. + Return FALSE when the page table entry is a non-leaf entry that points t= o the page table entries. + + @param[in] PagingEntry Pointer to the page table entry. + @param[in] Level Page level where the page table entry resides in. + + @retval TRUE It's a leaf entry. + @retval FALSE It's a non-leaf entry. +**/ +BOOLEAN +IsPle ( + IN IA32_PAGING_ENTRY *PagingEntry, + IN UINTN Level + ); + +/** + Return the attribute of a 2M/1G page table entry. + + @param[in] PleB Pointer to a 2M/1G page table entry. + @param[in] ParentMapAttribute Pointer to the parent attribute. + + @return Attribute of the 2M/1G page table entry. +**/ +UINT64 +PageTableLibGetPleBMapAttribute ( + IN IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE *PleB, + IN IA32_MAP_ATTRIBUTE *ParentMapAttribute + ); + +#endif diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf b/UefiC= puPkg/Library/CpuPageTableLib/CpuPageTableLib.inf new file mode 100644 index 0000000000..e4ead7441c --- /dev/null +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf @@ -0,0 +1,35 @@ +## @file +# This library implements CpuPageTableLib that are generic for IA32 famil= y CPU. +# +# Copyright (c) 2022, Intel Corporation. All rights reserved.
+# SPDX-License-Identifier: BSD-2-Clause-Patent +# +## + +[Defines] + INF_VERSION =3D 0x00010005 + BASE_NAME =3D CpuPageTableLib + FILE_GUID =3D 524ed6a1-f661-451b-929b-b54d755c914a + MODULE_TYPE =3D BASE + VERSION_STRING =3D 1.0 + LIBRARY_CLASS =3D CpuPageTableLib + +# +# The following information is for reference only and not required by the = build tools. +# +# VALID_ARCHITECTURES =3D IA32 X64 +# + +[Sources] + CpuPageTableMap.c + CpuPageTableParse.c + CpuPageTable.h + +[Packages] + MdePkg/MdePkg.dec + UefiCpuPkg/UefiCpuPkg.dec + +[LibraryClasses] + BaseLib + BaseMemoryLib + DebugLib diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c new file mode 100644 index 0000000000..25e13a6f6f --- /dev/null +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -0,0 +1,543 @@ +/** @file + This library implements CpuPageTableLib that are generic for IA32 family= CPU. + + Copyright (c) 2022, Intel Corporation. All rights reserved.
+ SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +#include "CpuPageTable.h" + +/** + Set the IA32_PTE_4K. + + @param[in] Pte4K Pointer to IA32_PTE_4K. + @param[in] Offset The offset within the linear address range. + @param[in] Attribute The attribute of the linear address range. + All non-reserved fields in IA32_MAP_ATTRIBUTE are s= upported to set in the page table. + Page table entry is reset to 0 before set to the ne= w attribute when a new physical base address is set. + @param[in] Mask The mask used for attribute. The corresponding fiel= d in Attribute is ignored if that in Mask is 0. +**/ +VOID +PageTableLibSetPte4K ( + IN IA32_PTE_4K *Pte4K, + IN UINT64 Offset, + IN IA32_MAP_ATTRIBUTE *Attribute, + IN IA32_MAP_ATTRIBUTE *Mask + ) +{ + if (Mask->Bits.PageTableBaseAddress) { + // + // Reset all attributes when the physical address is changed. + // + Pte4K->Uint64 =3D IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribut= e) + Offset; + } + + if (Mask->Bits.Present) { + Pte4K->Bits.Present =3D Attribute->Bits.Present; + } + + if (Mask->Bits.ReadWrite) { + Pte4K->Bits.ReadWrite =3D Attribute->Bits.ReadWrite; + } + + if (Mask->Bits.UserSupervisor) { + Pte4K->Bits.UserSupervisor =3D Attribute->Bits.UserSupervisor; + } + + if (Mask->Bits.WriteThrough) { + Pte4K->Bits.WriteThrough =3D Attribute->Bits.WriteThrough; + } + + if (Mask->Bits.CacheDisabled) { + Pte4K->Bits.CacheDisabled =3D Attribute->Bits.CacheDisabled; + } + + if (Mask->Bits.Accessed) { + Pte4K->Bits.Accessed =3D Attribute->Bits.Accessed; + } + + if (Mask->Bits.Dirty) { + Pte4K->Bits.Dirty =3D Attribute->Bits.Dirty; + } + + if (Mask->Bits.Pat) { + Pte4K->Bits.Pat =3D Attribute->Bits.Pat; + } + + if (Mask->Bits.Global) { + Pte4K->Bits.Global =3D Attribute->Bits.Global; + } + + if (Mask->Bits.ProtectionKey) { + Pte4K->Bits.ProtectionKey =3D Attribute->Bits.ProtectionKey; + } + + if (Mask->Bits.Nx) { + Pte4K->Bits.Nx =3D Attribute->Bits.Nx; + } +} + +/** + Set the IA32_PDPTE_1G or IA32_PDE_2M. + + @param[in] PleB Pointer to PDPTE_1G or PDE_2M. Both share the same = structure definition. + @param[in] Offset The offset within the linear address range. + @param[in] Attribute The attribute of the linear address range. + All non-reserved fields in IA32_MAP_ATTRIBUTE are s= upported to set in the page table. + Page table entry is reset to 0 before set to the ne= w attribute when a new physical base address is set. + @param[in] Mask The mask used for attribute. The corresponding fiel= d in Attribute is ignored if that in Mask is 0. +**/ +VOID +PageTableLibSetPleB ( + IN IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE *PleB, + IN UINT64 Offset, + IN IA32_MAP_ATTRIBUTE *Attribute, + IN IA32_MAP_ATTRIBUTE *Mask + ) +{ + if (Mask->Bits.PageTableBaseAddress) { + // + // Reset all attributes when the physical address is changed. + // + PleB->Uint64 =3D IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribute= ) + Offset; + } + + PleB->Bits.MustBeOne =3D 1; + + if (Mask->Bits.Present) { + PleB->Bits.Present =3D Attribute->Bits.Present; + } + + if (Mask->Bits.ReadWrite) { + PleB->Bits.ReadWrite =3D Attribute->Bits.ReadWrite; + } + + if (Mask->Bits.UserSupervisor) { + PleB->Bits.UserSupervisor =3D Attribute->Bits.UserSupervisor; + } + + if (Mask->Bits.WriteThrough) { + PleB->Bits.WriteThrough =3D Attribute->Bits.WriteThrough; + } + + if (Mask->Bits.CacheDisabled) { + PleB->Bits.CacheDisabled =3D Attribute->Bits.CacheDisabled; + } + + if (Mask->Bits.Accessed) { + PleB->Bits.Accessed =3D Attribute->Bits.Accessed; + } + + if (Mask->Bits.Dirty) { + PleB->Bits.Dirty =3D Attribute->Bits.Dirty; + } + + if (Mask->Bits.Pat) { + PleB->Bits.Pat =3D Attribute->Bits.Pat; + } + + if (Mask->Bits.Global) { + PleB->Bits.Global =3D Attribute->Bits.Global; + } + + if (Mask->Bits.ProtectionKey) { + PleB->Bits.ProtectionKey =3D Attribute->Bits.ProtectionKey; + } + + if (Mask->Bits.Nx) { + PleB->Bits.Nx =3D Attribute->Bits.Nx; + } +} + +/** + Set the IA32_PDPTE_1G, IA32_PDE_2M or IA32_PTE_4K. + + @param[in] Level 3, 2 or 1. + @param[in] Ple Pointer to PDPTE_1G, PDE_2M or IA32_PTE_4K, dependi= ng on the Level. + @param[in] Offset The offset within the linear address range. + @param[in] Attribute The attribute of the linear address range. + All non-reserved fields in IA32_MAP_ATTRIBUTE are s= upported to set in the page table. + Page table entry is reset to 0 before set to the ne= w attribute when a new physical base address is set. + @param[in] Mask The mask used for attribute. The corresponding fiel= d in Attribute is ignored if that in Mask is 0. +**/ +VOID +PageTableLibSetPle ( + IN UINTN Level, + IN IA32_PAGING_ENTRY *Ple, + IN UINT64 Offset, + IN IA32_MAP_ATTRIBUTE *Attribute, + IN IA32_MAP_ATTRIBUTE *Mask + ) +{ + if (Level =3D=3D 1) { + PageTableLibSetPte4K (&Ple->Pte4K, Offset, Attribute, Mask); + } else { + ASSERT (Level =3D=3D 2 || Level =3D=3D 3); + PageTableLibSetPleB (&Ple->PleB, Offset, Attribute, Mask); + } +} + +/** + Set the IA32_PML5, IA32_PML4, IA32_PDPTE or IA32_PDE. + + @param[in] Pnle Pointer to IA32_PML5, IA32_PML4, IA32_PDPTE or IA32= _PDE. All share the same structure definition. + @param[in] Attribute The attribute of the page directory referenced by t= he non-leaf. +**/ +VOID +PageTableLibSetPnle ( + IN IA32_PAGE_NON_LEAF_ENTRY *Pnle, + IN IA32_MAP_ATTRIBUTE *Attribute + ) +{ + Pnle->Bits.Present =3D Attribute->Bits.Present; + Pnle->Bits.ReadWrite =3D Attribute->Bits.ReadWrite; + Pnle->Bits.UserSupervisor =3D Attribute->Bits.UserSupervisor; + Pnle->Bits.Nx =3D Attribute->Bits.Nx; + Pnle->Bits.Accessed =3D 0; + + // + // Set the attributes (WT, CD, A) to 0. + // WT and CD determin the memory type used to access the 4K page directo= ry referenced by this entry. + // So, it implictly requires PAT[0] is Write Back. + // Create a new parameter if caller requires to use a different memory t= ype for accessing page directories. + // + Pnle->Bits.WriteThrough =3D 0; + Pnle->Bits.CacheDisabled =3D 0; +} + +/** + Update page table to map [LinearAddress, LinearAddress + Length) with sp= ecified attribute in the specified level. + + @param[in] ParentPagingEntry The pointer to the page table entry to= update. + @param[in] Modify FALSE to indicate Buffer is not used a= nd BufferSize is increased by the required buffer size. + @param[in] Buffer The free buffer to be used for page ta= ble creation/updating. + When Modify is TRUE, it's used from th= e end. + When Modify is FALSE, it's ignored. + @param[in, out] BufferSize The available buffer size. + Return the remaining buffer size. + @param[in] Level Page table level. Could be 5, 4, 3, 2,= or 1. + @param[in] MaxLeafLevel Maximum level that can be a leaf entry= . Could be 1, 2 or 3 (if Page 1G is supported). + @param[in] LinearAddress The start of the linear address range. + @param[in] Length The length of the linear address range. + @param[in] Offset The offset within the linear address r= ange. + @param[in] Attribute The attribute of the linear address ra= nge. + All non-reserved fields in IA32_MAP_AT= TRIBUTE are supported to set in the page table. + Page table entries that map the linear= address range are reset to 0 before set to the new attribute + when a new physical base address is se= t. + @param[in] Mask The mask used for attribute. The corre= sponding field in Attribute is ignored if that in Mask is 0. + + @retval RETURN_SUCCESS PageTable is created/updated successfu= lly. +**/ +RETURN_STATUS +PageTableLibMapInLevel ( + IN IA32_PAGING_ENTRY *ParentPagingEntry, + IN BOOLEAN Modify, + IN VOID *Buffer, + IN OUT INTN *BufferSize, + IN UINTN Level, + IN UINTN MaxLeafLevel, + IN UINT64 LinearAddress, + IN UINT64 Length, + IN UINT64 Offset, + IN IA32_MAP_ATTRIBUTE *Attribute, + IN IA32_MAP_ATTRIBUTE *Mask + ) +{ + RETURN_STATUS Status; + UINTN BitStart; + UINTN Index; + IA32_PAGING_ENTRY *PagingEntry; + UINT64 RegionLength; + UINT64 SubLength; + UINT64 SubOffset; + UINT64 RegionMask; + UINT64 RegionStart; + IA32_MAP_ATTRIBUTE AllOneMask; + IA32_MAP_ATTRIBUTE PleBAttribute; + IA32_MAP_ATTRIBUTE NopAttribute; + BOOLEAN CreateNew; + IA32_PAGING_ENTRY OneOfPagingEntry; + + ASSERT (Level !=3D 0); + ASSERT ((Attribute !=3D NULL) && (Mask !=3D NULL)); + + CreateNew =3D FALSE; + AllOneMask.Uint64 =3D ~0ull; + + NopAttribute.Uint64 =3D 0; + NopAttribute.Bits.Present =3D 1; + NopAttribute.Bits.ReadWrite =3D 1; + NopAttribute.Bits.UserSupervisor =3D 1; + + // + // ParentPagingEntry ONLY is deferenced for checking Present and MustBeO= ne bits + // when Modify is FALSE. + // + + if (ParentPagingEntry->Pce.Present =3D=3D 0) { + // + // The parent entry is CR3 or PML5E/PML4E/PDPTE/PDE. + // It does NOT point to an existing page directory. + // + ASSERT (Buffer =3D=3D NULL || *BufferSize >=3D SIZE_4KB); + CreateNew =3D TRUE; + *BufferSize -=3D SIZE_4KB; + + if (Modify) { + ParentPagingEntry->Uintn =3D (UINTN)Buffer + *BufferSize; + ZeroMem ((VOID *)ParentPagingEntry->Uintn, SIZE_4KB); + // + // Set default attribute bits for PML5E/PML4E/PDPTE/PDE. + // + PageTableLibSetPnle (&ParentPagingEntry->Pnle, &NopAttribute); + } else { + // + // Just make sure Present and MustBeZero (PageSize) bits are accurat= e. + // + OneOfPagingEntry.Pnle.Uint64 =3D 0; + } + } else if (IsPle (ParentPagingEntry, Level + 1)) { + // + // The parent entry is a PDPTE_1G or PDE_2M. Split to 2M or 4K pages. + // Note: it's impossible the parent entry is a PTE_4K. + // + // + // Use NOP attributes as the attribute of grand-parents because CPU wi= ll consider + // the actual attributes of grand-parents when determing the memory ty= pe. + // + PleBAttribute.Uint64 =3D PageTableLibGetPleBMapAttribute (&ParentPagin= gEntry->PleB, &NopAttribute); + if ((IA32_MAP_ATTRIBUTE_ATTRIBUTES (&PleBAttribute) & IA32_MAP_ATTRIBU= TE_ATTRIBUTES (Mask)) + =3D=3D IA32_MAP_ATTRIBUTE_ATTRIBUTES (Attribute)) + { + // + // This function is called when the memory length is less than the r= egion length of the parent level. + // No need to split the page when the attributes equal. + // + return RETURN_SUCCESS; + } + + ASSERT (Buffer =3D=3D NULL || *BufferSize >=3D SIZE_4KB); + CreateNew =3D TRUE; + *BufferSize -=3D SIZE_4KB; + PageTableLibSetPle (Level, &OneOfPagingEntry, 0, &PleBAttribute, &AllO= neMask); + if (Modify) { + // + // Create 512 child-level entries that map to 2M/4K. + // + ParentPagingEntry->Uintn =3D (UINTN)Buffer + *BufferSize; + ZeroMem ((VOID *)ParentPagingEntry->Uintn, SIZE_4KB); + + // + // Set NOP attributes + // Note: Should NOT inherit the attributes from the original entry b= ecause a zero RW bit + // will make the entire region read-only even the child entrie= s set the RW bit. + // + PageTableLibSetPnle (&ParentPagingEntry->Pnle, &NopAttribute); + + RegionLength =3D REGION_LENGTH (Level); + PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)IA32_PNLE_PAGE_TABLE_BA= SE_ADDRESS (&ParentPagingEntry->Pnle); + for (SubOffset =3D 0, Index =3D 0; Index < 512; Index++) { + PagingEntry[Index].Uint64 =3D OneOfPagingEntry.Uint64 + SubOffset; + SubOffset +=3D RegionLength; + } + } + } + + // + // RegionLength: 256T (1 << 48) 512G (1 << 39), 1G (1 << 30), 2M (1 << 2= 1) or 4K (1 << 12). + // RegionStart: points to the linear address that's aligned on RegionLe= ngth and lower than (LinearAddress + Offset). + // + BitStart =3D 12 + (Level - 1) * 9; + Index =3D BitFieldRead64 (LinearAddress + Offset, BitStart, BitSt= art + 9 - 1); + RegionLength =3D LShiftU64 (1, BitStart); + RegionMask =3D RegionLength - 1; + RegionStart =3D (LinearAddress + Offset) & ~RegionMask; + + // + // Apply the attribute. + // + PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)IA32_PNLE_PAGE_TABLE_BASE_AD= DRESS (&ParentPagingEntry->Pnle); + while (Offset < Length && Index < 512) { + SubLength =3D MIN (Length - Offset, RegionStart + RegionLength - (Line= arAddress + Offset)); + if ((Level <=3D MaxLeafLevel) && (LinearAddress + Offset =3D=3D Region= Start) && (SubLength =3D=3D RegionLength)) { + // + // Create one entry mapping the entire region (1G, 2M or 4K). + // + if (Modify) { + PageTableLibSetPle (Level, &PagingEntry[Index], Offset, Attribute,= Mask); + } + } else { + // + // Recursively call to create page table. + // There are 3 cases: + // a. Level cannot be a leaf entry which points to physical memory. + // a. Level can be a leaf entry but (LinearAddress + Offset) is NO= T aligned on the RegionStart. + // b. Level can be a leaf entry and (LinearAddress + Offset) is al= igned on RegionStart, + // but the length is SMALLER than the RegionLength. + // + Status =3D PageTableLibMapInLevel ( + (!Modify && CreateNew) ? &OneOfPagingEntry : &PagingEntry= [Index], + Modify, + Buffer, + BufferSize, + Level - 1, + MaxLeafLevel, + LinearAddress, + Length, + Offset, + Attribute, + Mask + ); + if (RETURN_ERROR (Status)) { + return Status; + } + } + + Offset +=3D SubLength; + RegionStart +=3D RegionLength; + Index++; + } + + return RETURN_SUCCESS; +} + +/** + Create or update page table to map [LinearAddress, LinearAddress + Lengt= h) with specified attribute. + + @param[in, out] PageTable The pointer to the page table to update, = or pointer to NULL if a new page table is to be created. + @param[in] PagingMode The paging mode. + @param[in] Buffer The free buffer to be used for page table= creation/updating. + @param[in, out] BufferSize The buffer size. + On return, the remaining buffer size. + The free buffer is used from the end so c= aller can supply the same Buffer pointer with an updated + BufferSize in the second call to this API. + @param[in] LinearAddress The start of the linear address range. + @param[in] Length The length of the linear address range. + @param[in] Attribute The attribute of the linear address range. + All non-reserved fields in IA32_MAP_ATTRI= BUTE are supported to set in the page table. + Page table entries that map the linear ad= dress range are reset to 0 before set to the new attribute + when a new physical base address is set. + @param[in] Mask The mask used for attribute. The correspo= nding field in Attribute is ignored if that in Mask is 0. + + @retval RETURN_UNSUPPORTED PagingMode is not supported. + @retval RETURN_INVALID_PARAMETER PageTable, BufferSize, Attribute or Ma= sk is NULL. + @retval RETURN_INVALID_PARAMETER *BufferSize is not multiple of 4KB. + @retval RETURN_BUFFER_TOO_SMALL The buffer is too small for page table= creation/updating. + BufferSize is updated to indicate the = expected buffer size. + Caller may still get RETURN_BUFFER_TOO= _SMALL with the new BufferSize. + @retval RETURN_SUCCESS PageTable is created/updated successfu= lly. +**/ +RETURN_STATUS +EFIAPI +PageTableMap ( + IN OUT UINTN *PageTable OPTIONAL, + IN PAGING_MODE PagingMode, + IN VOID *Buffer, + IN OUT UINTN *BufferSize, + IN UINT64 LinearAddress, + IN UINT64 Length, + IN IA32_MAP_ATTRIBUTE *Attribute, + IN IA32_MAP_ATTRIBUTE *Mask + ) +{ + RETURN_STATUS Status; + IA32_PAGING_ENTRY TopPagingEntry; + INTN RequiredSize; + UINT64 MaxLinearAddress; + UINTN MaxLevel; + UINTN MaxLeafLevel; + + if ((PagingMode =3D=3D Paging32bit) || (PagingMode =3D=3D PagingPae) || = (PagingMode >=3D PagingModeMax)) { + // + // 32bit paging is never supported. + // PAE paging will be supported later. + // + return RETURN_UNSUPPORTED; + } + + if ((PageTable =3D=3D NULL) || (BufferSize =3D=3D NULL) || (Attribute = =3D=3D NULL) || (Mask =3D=3D NULL)) { + return RETURN_INVALID_PARAMETER; + } + + if (*BufferSize % SIZE_4KB !=3D 0) { + // + // BufferSize should be multiple of 4K. + // + return RETURN_INVALID_PARAMETER; + } + + if ((*BufferSize !=3D 0) && (Buffer =3D=3D NULL)) { + return RETURN_INVALID_PARAMETER; + } + + MaxLeafLevel =3D (UINT8)PagingMode; + MaxLevel =3D (UINT8)(PagingMode >> 8); + MaxLinearAddress =3D LShiftU64 (1, 12 + MaxLevel * 9); + + if ((LinearAddress > MaxLinearAddress) || (Length > MaxLinearAddress - L= inearAddress)) { + // + // Maximum linear address is (1 << 48) or (1 << 57) + // + return RETURN_INVALID_PARAMETER; + } + + TopPagingEntry.Uintn =3D *PageTable; + if (TopPagingEntry.Uintn !=3D 0) { + TopPagingEntry.Pce.Present =3D 1; + } + + // + // Query the required buffer size without modifying the page table. + // + RequiredSize =3D 0; + Status =3D PageTableLibMapInLevel ( + &TopPagingEntry, + FALSE, + NULL, + &RequiredSize, + MaxLevel, + MaxLeafLevel, + LinearAddress, + Length, + 0, + Attribute, + Mask + ); + if (RETURN_ERROR (Status)) { + return Status; + } + + RequiredSize =3D -RequiredSize; + + if ((UINTN)RequiredSize > *BufferSize) { + *BufferSize =3D RequiredSize; + return RETURN_BUFFER_TOO_SMALL; + } + + if ((RequiredSize !=3D 0) && (Buffer =3D=3D NULL)) { + return RETURN_INVALID_PARAMETER; + } + + // + // Update the page table when the supplied buffer is sufficient. + // + Status =3D PageTableLibMapInLevel ( + &TopPagingEntry, + TRUE, + Buffer, + BufferSize, + MaxLevel, + MaxLeafLevel, + LinearAddress, + Length, + 0, + Attribute, + Mask + ); + if (!RETURN_ERROR (Status)) { + *PageTable =3D (UINTN)(TopPagingEntry.Uintn & IA32_PE_BASE_ADDRESS_MAS= K_40); + } + + return Status; +} diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableParse.c b/UefiC= puPkg/Library/CpuPageTableLib/CpuPageTableParse.c new file mode 100644 index 0000000000..e66961e122 --- /dev/null +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableParse.c @@ -0,0 +1,330 @@ +/** @file + This library implements CpuPageTableLib that are generic for IA32 family= CPU. + + Copyright (c) 2022, Intel Corporation. All rights reserved.
+ SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +#include "CpuPageTable.h" + +/** + Return the attribute of a 2M/1G page table entry. + + @param[in] PleB Pointer to a 2M/1G page table entry. + @param[in] ParentMapAttribute Pointer to the parent attribute. + + @return Attribute of the 2M/1G page table entry. +**/ +UINT64 +PageTableLibGetPleBMapAttribute ( + IN IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE *PleB, + IN IA32_MAP_ATTRIBUTE *ParentMapAttribute + ) +{ + IA32_MAP_ATTRIBUTE MapAttribute; + + // + // PageTableBaseAddress cannot be assigned field to field + // because their bit positions are different in IA32_MAP_ATTRIBUTE and I= A32_PAGE_LEAF_ENTRY_BIG_PAGESIZE. + // + MapAttribute.Uint64 =3D IA32_PLEB_PAGE_TABLE_BASE_ADDRESS (PleB); + + MapAttribute.Bits.Present =3D ParentMapAttribute->Bits.Present & = PleB->Bits.Present; + MapAttribute.Bits.ReadWrite =3D ParentMapAttribute->Bits.ReadWrite = & PleB->Bits.ReadWrite; + MapAttribute.Bits.UserSupervisor =3D ParentMapAttribute->Bits.UserSuperv= isor & PleB->Bits.UserSupervisor; + MapAttribute.Bits.Nx =3D ParentMapAttribute->Bits.Nx | PleB-= >Bits.Nx; + MapAttribute.Bits.WriteThrough =3D PleB->Bits.WriteThrough; + MapAttribute.Bits.CacheDisabled =3D PleB->Bits.CacheDisabled; + MapAttribute.Bits.Accessed =3D PleB->Bits.Accessed; + + MapAttribute.Bits.Pat =3D PleB->Bits.Pat; + MapAttribute.Bits.Dirty =3D PleB->Bits.Dirty; + MapAttribute.Bits.Global =3D PleB->Bits.Global; + MapAttribute.Bits.ProtectionKey =3D PleB->Bits.ProtectionKey; + + return MapAttribute.Uint64; +} + +/** + Return the attribute of a 4K page table entry. + + @param[in] Pte4K Pointer to a 4K page table entry. + @param[in] ParentMapAttribute Pointer to the parent attribute. + + @return Attribute of the 4K page table entry. +**/ +UINT64 +PageTableLibGetPte4KMapAttribute ( + IN IA32_PTE_4K *Pte4K, + IN IA32_MAP_ATTRIBUTE *ParentMapAttribute + ) +{ + IA32_MAP_ATTRIBUTE MapAttribute; + + MapAttribute.Uint64 =3D IA32_PTE4K_PAGE_TABLE_BASE_ADDRESS (Pte4K); + + MapAttribute.Bits.Present =3D ParentMapAttribute->Bits.Present & = Pte4K->Bits.Present; + MapAttribute.Bits.ReadWrite =3D ParentMapAttribute->Bits.ReadWrite = & Pte4K->Bits.ReadWrite; + MapAttribute.Bits.UserSupervisor =3D ParentMapAttribute->Bits.UserSuperv= isor & Pte4K->Bits.UserSupervisor; + MapAttribute.Bits.Nx =3D ParentMapAttribute->Bits.Nx | Pte4K= ->Bits.Nx; + MapAttribute.Bits.WriteThrough =3D Pte4K->Bits.WriteThrough; + MapAttribute.Bits.CacheDisabled =3D Pte4K->Bits.CacheDisabled; + MapAttribute.Bits.Accessed =3D Pte4K->Bits.Accessed; + + MapAttribute.Bits.Pat =3D Pte4K->Bits.Pat; + MapAttribute.Bits.Dirty =3D Pte4K->Bits.Dirty; + MapAttribute.Bits.Global =3D Pte4K->Bits.Global; + MapAttribute.Bits.ProtectionKey =3D Pte4K->Bits.ProtectionKey; + + return MapAttribute.Uint64; +} + +/** + Return the attribute of a non-leaf page table entry. + + @param[in] Pnle Pointer to a non-leaf page table entry. + @param[in] ParentMapAttribute Pointer to the parent attribute. + + @return Attribute of the non-leaf page table entry. +**/ +UINT64 +PageTableLibGetPnleMapAttribute ( + IN IA32_PAGE_NON_LEAF_ENTRY *Pnle, + IN IA32_MAP_ATTRIBUTE *ParentMapAttribute + ) +{ + IA32_MAP_ATTRIBUTE MapAttribute; + + MapAttribute.Uint64 =3D Pnle->Uint64; + + MapAttribute.Bits.Present =3D ParentMapAttribute->Bits.Present & = Pnle->Bits.Present; + MapAttribute.Bits.ReadWrite =3D ParentMapAttribute->Bits.ReadWrite = & Pnle->Bits.ReadWrite; + MapAttribute.Bits.UserSupervisor =3D ParentMapAttribute->Bits.UserSuperv= isor & Pnle->Bits.UserSupervisor; + MapAttribute.Bits.Nx =3D ParentMapAttribute->Bits.Nx | Pnle-= >Bits.Nx; + MapAttribute.Bits.WriteThrough =3D Pnle->Bits.WriteThrough; + MapAttribute.Bits.CacheDisabled =3D Pnle->Bits.CacheDisabled; + MapAttribute.Bits.Accessed =3D Pnle->Bits.Accessed; + return MapAttribute.Uint64; +} + +/** + Return TRUE when the page table entry is a leaf entry that points to the= physical address memory. + Return FALSE when the page table entry is a non-leaf entry that points t= o the page table entries. + + @param[in] PagingEntry Pointer to the page table entry. + @param[in] Level Page level where the page table entry resides in. + + @retval TRUE It's a leaf entry. + @retval FALSE It's a non-leaf entry. +**/ +BOOLEAN +IsPle ( + IN IA32_PAGING_ENTRY *PagingEntry, + IN UINTN Level + ) +{ + // + // PML5E and PML4E are always non-leaf entries. + // + if (Level =3D=3D 1) { + return TRUE; + } + + if (((Level =3D=3D 3) || (Level =3D=3D 2))) { + if (PagingEntry->PleB.Bits.MustBeOne =3D=3D 1) { + return TRUE; + } + } + + return FALSE; +} + +/** + Recursively parse the non-leaf page table entries. + + @param[in] PageTableBaseAddress The base address of the 512 non-lea= f page table entries in the specified level. + @param[in] Level Page level. Could be 5, 4, 3, 2, 1. + @param[in] RegionStart The base linear address of the regi= on covered by the non-leaf page table entries. + @param[in] ParentMapAttribute The mapping attribute of the parent= entries. + @param[in, out] Map Pointer to an array that describes = multiple linear address ranges. + @param[in, out] MapCount Pointer to a UINTN that hold the ac= tual number of entries in the Map. + @param[in] MapCapacity The maximum number of entries the M= ap can hold. + @param[in] LastEntry Pointer to last map entry. + @param[in] OneEntry Pointer to a library internal stora= ge that holds one map entry. + It's used when Map array is used up. +**/ +VOID +PageTableLibParsePnle ( + IN UINT64 PageTableBaseAddress, + IN UINTN Level, + IN UINT64 RegionStart, + IN IA32_MAP_ATTRIBUTE *ParentMapAttribute, + IN OUT IA32_MAP_ENTRY *Map, + IN OUT UINTN *MapCount, + IN UINTN MapCapacity, + IN IA32_MAP_ENTRY **LastEntry, + IN IA32_MAP_ENTRY *OneEntry + ) +{ + IA32_PAGING_ENTRY *PagingEntry; + UINTN Index; + IA32_MAP_ATTRIBUTE MapAttribute; + UINT64 RegionLength; + + ASSERT (OneEntry !=3D NULL); + + PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)PageTableBaseAddress; + RegionLength =3D REGION_LENGTH (Level); + + for (Index =3D 0; Index < 512; Index++, RegionStart +=3D RegionLength) { + if (PagingEntry[Index].Pce.Present =3D=3D 0) { + continue; + } + + if (IsPle (&PagingEntry[Index], Level)) { + ASSERT (Level =3D=3D 1 || Level =3D=3D 2 || Level =3D=3D 3); + + if (Level =3D=3D 1) { + MapAttribute.Uint64 =3D PageTableLibGetPte4KMapAttribute (&PagingE= ntry[Index].Pte4K, ParentMapAttribute); + } else { + MapAttribute.Uint64 =3D PageTableLibGetPleBMapAttribute (&PagingEn= try[Index].PleB, ParentMapAttribute); + } + + if ((*LastEntry !=3D NULL) && + ((*LastEntry)->LinearAddress + (*LastEntry)->Length =3D=3D Regio= nStart) && + (IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (&(*LastEntry)->Attr= ibute) + (*LastEntry)->Length + =3D=3D IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (&MapAttribut= e)) && + (IA32_MAP_ATTRIBUTE_ATTRIBUTES (&(*LastEntry)->Attribute) =3D=3D= IA32_MAP_ATTRIBUTE_ATTRIBUTES (&MapAttribute)) + ) + { + // + // Extend LastEntry. + // + (*LastEntry)->Length +=3D RegionLength; + } else { + if (*MapCount < MapCapacity) { + // + // LastEntry points to next map entry in the array. + // + *LastEntry =3D &Map[*MapCount]; + } else { + // + // LastEntry points to library internal map entry. + // + *LastEntry =3D OneEntry; + } + + // + // Set LastEntry. + // + (*LastEntry)->LinearAddress =3D RegionStart; + (*LastEntry)->Length =3D RegionLength; + (*LastEntry)->Attribute.Uint64 =3D MapAttribute.Uint64; + (*MapCount)++; + } + } else { + MapAttribute.Uint64 =3D PageTableLibGetPnleMapAttribute (&PagingEntr= y[Index].Pnle, ParentMapAttribute); + PageTableLibParsePnle ( + IA32_PNLE_PAGE_TABLE_BASE_ADDRESS (&PagingEntry[Index].Pnle), + Level - 1, + RegionStart, + &MapAttribute, + Map, + MapCount, + MapCapacity, + LastEntry, + OneEntry + ); + } + } +} + +/** + Parse page table. + + @param[in] PageTable Pointer to the page table. + @param[in] PagingMode The paging mode. + @param[out] Map Return an array that describes multiple linea= r address ranges. + @param[in, out] MapCount On input, the maximum number of entries that = Map can hold. + On output, the number of entries in Map. + + @retval RETURN_UNSUPPORTED PageLevel is not 5 or 4. + @retval RETURN_INVALID_PARAMETER MapCount is NULL. + @retval RETURN_INVALID_PARAMETER *MapCount is not 0 but Map is NULL. + @retval RETURN_BUFFER_TOO_SMALL *MapCount is too small. + @retval RETURN_SUCCESS Page table is parsed successfully. +**/ +RETURN_STATUS +EFIAPI +PageTableParse ( + IN UINTN PageTable, + IN PAGING_MODE PagingMode, + OUT IA32_MAP_ENTRY *Map, + IN OUT UINTN *MapCount + ) +{ + UINTN MapCapacity; + IA32_MAP_ATTRIBUTE NopAttribute; + IA32_MAP_ENTRY *LastEntry; + IA32_MAP_ENTRY OneEntry; + UINTN MaxLevel; + + if ((PagingMode =3D=3D Paging32bit) || (PagingMode =3D=3D PagingPae) || = (PagingMode >=3D PagingModeMax)) { + // + // 32bit paging is never supported. + // PAE paging will be supported later. + // + return RETURN_UNSUPPORTED; + } + + if (MapCount =3D=3D NULL) { + return RETURN_INVALID_PARAMETER; + } + + if ((*MapCount !=3D 0) && (Map =3D=3D NULL)) { + return RETURN_INVALID_PARAMETER; + } + + if (PageTable =3D=3D 0) { + *MapCount =3D 0; + return RETURN_SUCCESS; + } + + // + // Page table layout is as below: + // + // [IA32_CR3] + // | + // | + // V + // [IA32_PML5E] + // ... + // [IA32_PML5E] --> [IA32_PML4E] + // ... + // [IA32_PML4E] --> [IA32_PDPTE_1G] --> 1G aligned phys= ical address + // ... + // [IA32_PDPTE] --> [IA32_PDE_2M] --> = 2M aligned physical address + // ... + // [IA32_PDE] --> [IA= 32_PTE_4K] --> 4K aligned physical address + // ... + // [IA= 32_PTE_4K] --> 4K aligned physical address + // + + NopAttribute.Uint64 =3D 0; + NopAttribute.Bits.Present =3D 1; + NopAttribute.Bits.ReadWrite =3D 1; + NopAttribute.Bits.UserSupervisor =3D 1; + + MaxLevel =3D (UINT8)(PagingMode >> 8); + MapCapacity =3D *MapCount; + *MapCount =3D 0; + LastEntry =3D NULL; + PageTableLibParsePnle ((UINT64)PageTable, MaxLevel, 0, &NopAttribute, Ma= p, MapCount, MapCapacity, &LastEntry, &OneEntry); + + if (*MapCount > MapCapacity) { + return RETURN_BUFFER_TOO_SMALL; + } + + return RETURN_SUCCESS; +} diff --git a/UefiCpuPkg/UefiCpuPkg.dec b/UefiCpuPkg/UefiCpuPkg.dec index 1951eb294c..4fe79cecbf 100644 --- a/UefiCpuPkg/UefiCpuPkg.dec +++ b/UefiCpuPkg/UefiCpuPkg.dec @@ -62,6 +62,9 @@ ## @libraryclass Provides function for loading microcode. MicrocodeLib|Include/Library/MicrocodeLib.h =20 + ## @libraryclass Provides function for manipulating x86 paging structu= res. + CpuPageTableLib|Include/Library/CpuPageTableLib.h + [Guids] gUefiCpuPkgTokenSpaceGuid =3D { 0xac05bf33, 0x995a, 0x4ed4, { 0xaa,= 0xb8, 0xef, 0x7a, 0xe8, 0xf, 0x5c, 0xb0 }} gMsegSmramGuid =3D { 0x5802bce4, 0xeeee, 0x4e33, { 0xa1,= 0x30, 0xeb, 0xad, 0x27, 0xf0, 0xe4, 0x39 }} diff --git a/UefiCpuPkg/UefiCpuPkg.dsc b/UefiCpuPkg/UefiCpuPkg.dsc index a0bbde9985..f694b3a77c 100644 --- a/UefiCpuPkg/UefiCpuPkg.dsc +++ b/UefiCpuPkg/UefiCpuPkg.dsc @@ -1,7 +1,7 @@ ## @file # UefiCpuPkg Package # -# Copyright (c) 2007 - 2021, Intel Corporation. All rights reserved.
+# Copyright (c) 2007 - 2022, Intel Corporation. All rights reserved.
# # SPDX-License-Identifier: BSD-2-Clause-Patent # @@ -62,6 +62,7 @@ VmgExitLib|UefiCpuPkg/Library/VmgExitLibNull/VmgExitLibNull.inf MicrocodeLib|UefiCpuPkg/Library/MicrocodeLib/MicrocodeLib.inf SmmCpuRendezvousLib|UefiCpuPkg/Library/SmmCpuRendezvousLib/SmmCpuRendezv= ousLib.inf + CpuPageTableLib|UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf =20 [LibraryClasses.common.SEC] PlatformSecLib|UefiCpuPkg/Library/PlatformSecLibNull/PlatformSecLibNull.= inf @@ -175,6 +176,7 @@ UefiCpuPkg/Universal/Acpi/S3Resume2Pei/S3Resume2Pei.inf UefiCpuPkg/ResetVector/Vtf0/Bin/ResetVector.inf UefiCpuPkg/Library/SmmCpuRendezvousLib/SmmCpuRendezvousLib.inf + UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf =20 [BuildOptions] *_*_*_CC_FLAGS =3D -D DISABLE_NEW_DEPRECATED_INTERFACES --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91449): https://edk2.groups.io/g/devel/message/91449 Mute This Topic: https://groups.io/mt/92458154/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91450+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91450+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150327; cv=none; d=zohomail.com; s=zohoarc; b=QVxFvlnV/buN1J8GqXJrKKD7EsjEtz/lBdJOBj/BzQpe4j5sLouRU8GXPswUsDrjyA0Ky1MTS+jKrOY4+yZUmEYNdwkYYuTosmuljZpQtNV/Ia8R0dKp+EyMBY3a4IMQfYy+FBwePRTIxvImmKfgtf6vsdTLae/HYgctoeX5uAk= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150327; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=pU53j9pnQTA+kKhKRxIu99r/PAw2CsX1lYvM66Lqj7o=; b=ZOqDz8e8G3csaJkOJNWN+9nvC9m+bA/Ym+MAirnKTmRll9xbCH+U/Y4MdKKIzNbkhlf4niqNK6udKoFnByAp7uosneOySo52ayujRpCwR6r5etnyz7SXRkvRXhv3WlRzx7nusDK/SBs+ZT0RCyqQ7OUueujeplqeghEY78IFXRY= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91450+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150326998170.030423511065; Mon, 18 Jul 2022 06:18:46 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id 0eIZYY1788612xYuwaxnC0VL; Mon, 18 Jul 2022 06:18:46 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web12.27079.1658150325580236005 for ; Mon, 18 Jul 2022 06:18:46 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363888" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363888" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:42 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624724957" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:41 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 02/10] UefiCpuPkg/CpuPageTableLib: Return error on invalid parameters Date: Mon, 18 Jul 2022 21:18:23 +0800 Message-Id: <20220718131831.660-3-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: utV2cumq9xoOYQPF3HCGIaVpx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150326; bh=8UqBfexbuUqQfZC8WA6QdSupkDrXpaR5S0yGilnnIKk=; h=Cc:Date:From:Reply-To:Subject:To; b=WP3rswRU0LFQjedkk+FlN40o++0r08VhqW/TDIji4C1Rpov6ri4lZZ5H6cnCvEP0g6h u68ZZ8MwPXJEIGRIvOaepYBHkfRO+xNO+zTcAjicNdXTVhuh4PPsbEvbI0WOtkOW94XnW kedo6XNNcJv/IWiw0SWTCkPEHdg1rmNKgjI= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150327628100001 Content-Type: text/plain; charset="utf-8" When LinearAddress or Length is not aligned on 4KB, PageTableMap() should return Invalid Parameter. Signed-off-by: Zhiguang Liu Reviewed-by: Ray Ni Cc: Eric Dong Reviewed-by: Eric Dong --- UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index 25e13a6f6f..17bca5e351 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -467,6 +467,13 @@ PageTableMap ( return RETURN_INVALID_PARAMETER; } =20 + if ((LinearAddress % SIZE_4KB !=3D 0) || (Length % SIZE_4KB !=3D 0)) { + // + // LinearAddress and Length should be multiple of 4K. + // + return RETURN_INVALID_PARAMETER; + } + if ((*BufferSize !=3D 0) && (Buffer =3D=3D NULL)) { return RETURN_INVALID_PARAMETER; } --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91450): https://edk2.groups.io/g/devel/message/91450 Mute This Topic: https://groups.io/mt/92458155/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91454+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91454+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150328; cv=none; d=zohomail.com; s=zohoarc; b=ZBzHp4Wm0/t8hf7lAhPOYJfImsLG645uInaH+7OEHSTRRCZB7xyY6gIjGdmlMhGfA5mWsxS6J76IyZD3sVvV+K1eN/Tfw54UvyYf17++dcJg4X1odM/Y7R2bxjlkj+9MUf2VkazS/GtUSumv+UGNoNEzKLRBF2kpGLJeTYIDFTU= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150328; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=NH9pPbtUpJgMByPzHbw3dUuZ7/fl1KugRLoukySgQL4=; b=KV9LYdME9hGorOeuF6fSrr5zc4jg5YNmCWoP+3NyFn4e3RRceL0rDMevoR7f6kG31VxWx8/pKjJyf/YELroCN0B23IX3CkgtNY/vZ3P86LGYnZeFb5BdNrc2tGhRgYu25MhbsBLh33LwhZ4TOI3Ylgo22EazP9RArXN3+rBy4sQ= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91454+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150328440820.9923995129944; Mon, 18 Jul 2022 06:18:48 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id v35DYY1788612xPeSLQNO4jK; Mon, 18 Jul 2022 06:18:48 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web11.26914.1658150326443022020 for ; Mon, 18 Jul 2022 06:18:46 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363892" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363892" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:43 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624724967" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:42 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 03/10] CpuPageTableLib: Fix a bug when a bit is 1 in Attribute, 0 in Mask Date: Mon, 18 Jul 2022 21:18:24 +0800 Message-Id: <20220718131831.660-4-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: 8NI1VCF8te0tfCbG4jCAOqZOx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150328; bh=jLG01Yy0J8Xj8oeogHSXF7cC2ez4kBii3hAiOaWP5fc=; h=Cc:Date:From:Reply-To:Subject:To; b=wlF6tiZE5mi+o6OCU5WJcRlcC30KGXhPYdNOTvP7MaQ8IyxnZO8AXMYDSlYt9TzodL+ h5GcSSK3YvnLqdcjV2IrUSRvSGg8+OcWZWj7NFL1DAmFiK8tj03v8U4sOzHUqm7XeuHTn OPgYkpKBU0LuwBqb7Q9qp12bhfn+c/3/LYM= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150329545100011 Content-Type: text/plain; charset="utf-8" To reproduce the issue: UINTN PageTable; VOID *Buffer; UINTN PageTableBufferSize; IA32_MAP_ATTRIBUTE Attribute; IA32_MAP_ATTRIBUTE Mask; RETURN_STATUS Status; Attribute.Uint64 =3D 0; Mask.Uint64 =3D 0; PageTableBufferSize =3D 0; PageTable =3D 0; Buffer =3D NULL; Attribute.Bits.Present =3D 1; Attribute.Bits.Nx =3D 1; Mask.Bits.Present =3D 1; Mask.Uint64 =3D MAX_UINT64; // // Create page table to cover [0, 10M) // Status =3D PageTableMap ( &PageTable, PagingMode, Buffer, &PageTableBufferSize, 0, (UINT64)SIZE_2MB * 5, &Attribute, &Mask ); ASSERT (Status =3D=3D RETURN_BUFFER_TOO_SMALL); Buffer =3D AllocatePages (EFI_SIZE_TO_PAGES (PageTableBufferSize)); Status =3D PageTableMap ( &PageTable, PagingMode, Buffer, &PageTableBufferSize, 0, (UINT64)SIZE_2MB * 5, &Attribute, &Mask ); ASSERT (Status =3D=3D RETURN_SUCCESS); // // Change the mapping for [0, 4KB) // No change actually. Just clear Nx bit in Mask. // Mask.Bits.Nx =3D 0; PageTableBufferSize =3D 0; Status =3D PageTableMap ( &PageTable, PagingMode, NULL, &PageTableBufferSize, 0, (UINT64)SIZE_4KB, &Attribute, &Mask ); ASSERT (Status =3D=3D RETURN_SUCCESS); // FAIL!! The root cause is when comparing the existing mapping attributes against the requested one, Mask is not used but it should be used. Signed-off-by: Zhiguang Liu Reviewed-by: Ray Ni Cc: Eric Dong Reviewed-by: Eric Dong --- UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index 17bca5e351..429b014b7b 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -308,7 +308,7 @@ PageTableLibMapInLevel ( // PleBAttribute.Uint64 =3D PageTableLibGetPleBMapAttribute (&ParentPagin= gEntry->PleB, &NopAttribute); if ((IA32_MAP_ATTRIBUTE_ATTRIBUTES (&PleBAttribute) & IA32_MAP_ATTRIBU= TE_ATTRIBUTES (Mask)) - =3D=3D IA32_MAP_ATTRIBUTE_ATTRIBUTES (Attribute)) + =3D=3D (IA32_MAP_ATTRIBUTE_ATTRIBUTES (Attribute) & IA32_MAP_ATTRI= BUTE_ATTRIBUTES (Mask))) { // // This function is called when the memory length is less than the r= egion length of the parent level. --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91454): https://edk2.groups.io/g/devel/message/91454 Mute This Topic: https://groups.io/mt/92458159/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91452+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91452+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150328; cv=none; d=zohomail.com; s=zohoarc; b=iZqNk7GlEHcFXHSpfRANvyuCJMlQvqOCvalnbWpCzh4GzrZxsXT7Q/UukcYmeJI43fVBkSEt4qRH51I9ubbVQ4q9s3aR/Oh7XSeNBGo3e60fWBB9kDCPSEQM/4oW8++ppTkRTkRQXwY1kFDVLIQWcoGArPl/8AX1M0+TvwnSo38= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150328; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=B/IWVfdc6Cy6EhB3qBRmrTgHIdWD5sWG1QZIefAdDNg=; b=hUUqCVBuY3trLtY0RhYe8oThH2x/a3BEjoShTjaRohm2Y8J4aD6FVUEIUuAI5V+Hm0nXCycexif2EVf3sNnDvmJMp/wx1mozZYzO3GWNc397KwSYOUjx90vk/bfnnoRCKqN+yRWYeKcRPEIZhO+PL03Ia6nOZkTx4Jb7rUSwtBA= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91452+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150328151528.323012877917; Mon, 18 Jul 2022 06:18:48 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id NmCrYY1788612xnUPcZvpy28; Mon, 18 Jul 2022 06:18:47 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web12.27079.1658150325580236005 for ; Mon, 18 Jul 2022 06:18:46 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363898" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363898" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:44 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624724973" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:43 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 04/10] CpuPageTableLib: Refactor the logic Date: Mon, 18 Jul 2022 21:18:25 +0800 Message-Id: <20220718131831.660-5-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: n2exPOw3cW7Tv2yBfdGu3S3Xx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150327; bh=rax9bZt/LdLNN5ia7FiSHMJJ3fkwZ/1YVyhHN1e5iVQ=; h=Cc:Date:From:Reply-To:Subject:To; b=F3qSGMS4oOLz+feLiHK4xcxPa+H4vJW9j9bMo4aniX0s0CMK2V7OS9UbZzy/3J7zio0 nUGSJJ2NPCQZ4AUAG/f9MEIBqP8OPE0ME8zWS7Nw2OaiRIftVBhgdAfWROChzPr4OVVCR L/dktbrDpOG+cilCmFF6h+H+raxxtcwByDI= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150329533100009 Content-Type: text/plain; charset="utf-8" The patch replaces LinearAddress + Offset =3D=3D RegionStart with ((LinearAddress + Offset) & RegionMask) =3D=3D 0 The replace should not cause any behavior change. Because: 1. In first loop of while when LinearAddress + Offset =3D=3D RegionStart, because the lower "BitStart" bits of RegionStart are all-zero, all lower "BitStart" bits of (LinearAddress + Offset) are all-zero. Because all lower "BitStart" bits of RegionMask is all-one and bits are all-zero, ((LinearAddress + Offset) & RegionMask) =3D=3D 0. 2. In following loops of the while, even RegionStart is increased by RegionLength, the lower "BitStart" bits are still all-zero. So the two expressions still semantically equal to each other. Signed-off-by: Ray Ni Cc: Zhiguang Liu Cc: Eric Dong Reviewed-by: Eric Dong --- UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index 429b014b7b..509fa5f7bd 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -360,7 +360,7 @@ PageTableLibMapInLevel ( PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)IA32_PNLE_PAGE_TABLE_BASE_AD= DRESS (&ParentPagingEntry->Pnle); while (Offset < Length && Index < 512) { SubLength =3D MIN (Length - Offset, RegionStart + RegionLength - (Line= arAddress + Offset)); - if ((Level <=3D MaxLeafLevel) && (LinearAddress + Offset =3D=3D Region= Start) && (SubLength =3D=3D RegionLength)) { + if ((Level <=3D MaxLeafLevel) && (((LinearAddress + Offset) & RegionMa= sk) =3D=3D 0) && (SubLength =3D=3D RegionLength)) { // // Create one entry mapping the entire region (1G, 2M or 4K). // --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91452): https://edk2.groups.io/g/devel/message/91452 Mute This Topic: https://groups.io/mt/92458157/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91453+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91453+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150329; cv=none; d=zohomail.com; s=zohoarc; b=LyOVzSGJ9mBvFSxNmjEHOYH8RyMsaMecXXQ0zjHktiYO20prYNo4U7y14/hGvOWGBHit0VzpWN4o/av7iqWCgrOUH676/QtAWT6Qbg/j5PJ0Ci9B2e94q/L+72E6bqRnBSnx1laGDV+au8kAX8tTx4L15VA/73wS7U5OxsX5Qa0= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150329; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=LgEBONytyF/mWFkAGPRQenSdoASId3Frd2jwkWinHeY=; b=UtmqS8S7fInHCFUV3HnyxAvAfg+aYejfzQ7cDCSaySYYEhKB7x8DHYMnPjKphl1B1XYo3IoiwZbkCss0YKyQ2FhUF9d9AZZG8/sp6HoKx32v0zpfobxbLshO9+Yhr8vD1UGoEjtm0+/1MVUfgroA+/8INQ04Mwwdajjib5uLnmk= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91453+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 165815032914467.93179150551555; Mon, 18 Jul 2022 06:18:49 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id OIlIYY1788612xnbN4703xLa; Mon, 18 Jul 2022 06:18:48 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web12.27079.1658150325580236005 for ; Mon, 18 Jul 2022 06:18:46 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363901" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363901" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:45 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624724978" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:44 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 05/10] CpuPageTableLib: Split the page entry when LA is aligned but PA is not Date: Mon, 18 Jul 2022 21:18:26 +0800 Message-Id: <20220718131831.660-6-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: lvFcOECB71I5a3O50scDgMXmx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150328; bh=Y/9P4k0h15Xov/gJg8sEqyFC9bmDXhya4O4oafJNGrk=; h=Cc:Date:From:Reply-To:Subject:To; b=IQoFUyh9f2SmVhFwK8OcxVQDonKSSw7IKpeD3HCPKCb9SRUn995edvtPKb5FDJyOVE9 J/Oh8C6QC/LdfCDtXG6Psu6ewfKGc9o8MTbBVsOnTRd4nZ9A+xxrXGCUquLU3PplZUhb/ pDBjHsYmhOpvYbuxbf/BDW1Vjt/FH2BTW6I= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150331549100028 Content-Type: text/plain; charset="utf-8" When PageTableMap() is called to create non 1:1 mapping such as [0, 1G) to [8K, 1G+8K), it should split the page entry to the 4K page level, but old logic has a bug that it just uses 1G page entry. The patch fixes the bug. Signed-off-by: Zhiguang Liu Cc: Ray Ni Cc: Eric Dong Reviewed-by: Eric Dong --- UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index 509fa5f7bd..dc37ca3647 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -360,7 +360,12 @@ PageTableLibMapInLevel ( PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)IA32_PNLE_PAGE_TABLE_BASE_AD= DRESS (&ParentPagingEntry->Pnle); while (Offset < Length && Index < 512) { SubLength =3D MIN (Length - Offset, RegionStart + RegionLength - (Line= arAddress + Offset)); - if ((Level <=3D MaxLeafLevel) && (((LinearAddress + Offset) & RegionMa= sk) =3D=3D 0) && (SubLength =3D=3D RegionLength)) { + if ((Level <=3D MaxLeafLevel) && + (((LinearAddress + Offset) & RegionMask) =3D=3D 0) && + (((IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribute) + Offset= ) & RegionMask) =3D=3D 0) && + (SubLength =3D=3D RegionLength) + ) + { // // Create one entry mapping the entire region (1G, 2M or 4K). // --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91453): https://edk2.groups.io/g/devel/message/91453 Mute This Topic: https://groups.io/mt/92458158/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91455+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91455+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150330; cv=none; d=zohomail.com; s=zohoarc; b=G8X1FgyLiJwXdtZHbUMzoLzWxwKY6w0xsG4NuDmVmZcTxSCK596C9UBcYNM19+9y4g7LjGMKPiM+q/5jTOwmMQkNaD374JkkXB4uPsHMvdnD6RXugsh95clDa7Un5gVJcomPfsVeI0wTGaz1kkSNLOkVGbLb62t2Ha22VcPjU4g= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150330; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=qwztI07HWZ7VTD4+k4W6rrTvyPOSb1oZfmAd963eHDY=; b=cyFt6L0YBLxvoejc76tPZ6JWoMhW3LQHrbx7gPZmkYSlB+LAeDwQlO23J/b92KSA2mOPmuoAUnP7l0YBek2C/7cJwg6xg1WON0+8s1sDWA06538HXWkRmpA3uREZFouqHW0dl++wh30hOiSEsTc6fzCDRs74PZMSWS7RcAA0FsA= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91455+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150330299839.7482578044004; Mon, 18 Jul 2022 06:18:50 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id CARvYY1788612xbnO5k6toPe; Mon, 18 Jul 2022 06:18:49 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web08.27105.1658150328221476289 for ; Mon, 18 Jul 2022 06:18:48 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363915" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363915" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:47 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624724982" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:46 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 06/10] CpuPageTableLib: Avoid treating non-leaf entry as leaf one Date: Mon, 18 Jul 2022 21:18:27 +0800 Message-Id: <20220718131831.660-7-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: BAOUbZP7Sl0SP8VVFiGLp2Dnx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150329; bh=uL5c7Od8QYGrg2mDA/bD/TwGKqoYwCG9IC2jRK6MA2o=; h=Cc:Date:From:Reply-To:Subject:To; b=xPrHh47nNbBtFvPHKpemChKn19QEbu6m31HNUowuCX8J9fYoT6R5e+hFK4ML36Vwr59 KEGEzP/XAWDUlRvjEmse4UEWcNMmAoOnpBPyqik70M/VBztu/S9NBrmLknHzVfSmDIAeY dmPiT4uIWdQQvTDkoK28VATk/M1zJt0lIYM= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150331549100027 Content-Type: text/plain; charset="utf-8" Today's logic wrongly treats the non-leaf entry as leaf entry and updates its paging attributes. The patch fixes the bug to only update paging attributes for non-present entries or leaf entries. Signed-off-by: Ray Ni Signed-off-by: Zhiguang Liu Cc: Eric Dong Reviewed-by: Eric Dong --- UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index dc37ca3647..a6aa1a352b 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -248,6 +248,7 @@ PageTableLibMapInLevel ( UINTN BitStart; UINTN Index; IA32_PAGING_ENTRY *PagingEntry; + IA32_PAGING_ENTRY *CurrentPagingEntry; UINT64 RegionLength; UINT64 SubLength; UINT64 SubOffset; @@ -359,18 +360,20 @@ PageTableLibMapInLevel ( // PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)IA32_PNLE_PAGE_TABLE_BASE_AD= DRESS (&ParentPagingEntry->Pnle); while (Offset < Length && Index < 512) { - SubLength =3D MIN (Length - Offset, RegionStart + RegionLength - (Line= arAddress + Offset)); + CurrentPagingEntry =3D (!Modify && CreateNew) ? &OneOfPagingEntry : &P= agingEntry[Index]; + SubLength =3D MIN (Length - Offset, RegionStart + RegionLengt= h - (LinearAddress + Offset)); if ((Level <=3D MaxLeafLevel) && (((LinearAddress + Offset) & RegionMask) =3D=3D 0) && (((IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribute) + Offset= ) & RegionMask) =3D=3D 0) && - (SubLength =3D=3D RegionLength) + (SubLength =3D=3D RegionLength) && + ((CurrentPagingEntry->Pce.Present =3D=3D 0) || IsPle (CurrentPagin= gEntry, Level)) ) { // // Create one entry mapping the entire region (1G, 2M or 4K). // if (Modify) { - PageTableLibSetPle (Level, &PagingEntry[Index], Offset, Attribute,= Mask); + PageTableLibSetPle (Level, CurrentPagingEntry, Offset, Attribute, = Mask); } } else { // @@ -382,7 +385,7 @@ PageTableLibMapInLevel ( // but the length is SMALLER than the RegionLength. // Status =3D PageTableLibMapInLevel ( - (!Modify && CreateNew) ? &OneOfPagingEntry : &PagingEntry= [Index], + CurrentPagingEntry, Modify, Buffer, BufferSize, --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91455): https://edk2.groups.io/g/devel/message/91455 Mute This Topic: https://groups.io/mt/92458160/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91456+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91456+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150331; cv=none; d=zohomail.com; s=zohoarc; b=f3shFHaGHza539Pb4Lo3Ff+Zb5MwU7MU9X5Z556DNedESJwvpgBBJ8F+c92PzELFrAXnjZQaUnd03w5mS82YR1Ef9pyGYA++K0/LLimZAj8lW4DJx9hW3jEUTBXoSEOb5SPhFxBIW/pX45TE579KMKolLdtvatsHKuAumcunwhg= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150331; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=4blp9329xkGDPeZiy2ovKKD2kmaaPzfdEwY5J/pUxDQ=; b=WkG7pSadjmUTx8pNu6pyz41+GFj0Nozn5+LhPB3EdFigpd2mIaUzKUaXGUrlbgo1GECvmauI3uk4fB1MyPr+ClvcC/K7rtAvdd20p4piaOD+c87pJyFq2ln4c7JErxZToIDyfKHL9LMdhQLzoOawNIpLU0GwZ7Tf3wJRQQCl/XU= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91456+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150331835864.5682142361478; Mon, 18 Jul 2022 06:18:51 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id udaBYY1788612xgxm2zhFozi; Mon, 18 Jul 2022 06:18:50 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web08.27105.1658150328221476289 for ; Mon, 18 Jul 2022 06:18:50 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363943" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363943" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:48 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624724995" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:47 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 07/10] CpuPageTableLib: Fix parent attributes are not inherited properly Date: Mon, 18 Jul 2022 21:18:28 +0800 Message-Id: <20220718131831.660-8-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: xDYePfWNkWDUDPaI1IdDmxg2x1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150330; bh=safMdYypUMnB6VwhCtw5K5GLvA9AHCSK29FS0yUWGcI=; h=Cc:Date:From:Reply-To:Subject:To; b=F2bHOUJDJ56yUmK7zhyaiZBWZbYb80fgjpEb3u4gH7gUsJOrlayMWiqJN27HMtWMfDT opwDOpBjxVb3iPRdfG285z91hkzR+RnURq6lupv3caLp/D3M1+/s8VyjjntXnN/lsLleD g+hbUpebtXdjD87BBAgIYFrPnvz20GdH8HQ= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150333604100033 Content-Type: text/plain; charset="utf-8" With the following paging structure that maps [0, 2G] with ReadWrite bit set. PML4[0] --> PDPTE[0] --> PDE[0-255] \-> PDPTE[1] --> PDE[0-255] If ReadWrite bit is cleared in PML4[0] and PageTableMap() is called to change [0, 2M] as writable, today's logic doesn't inherit the parent entry's attributes when determining the child entry's attributes. It just sets the PDPTE[0].PDE[0].ReadWrite bit. But since the PML4[0].ReadWrite is 0, [0, 2M] is still read-only. The change fixes the bug. If the inheritable attributes in ParentPagingEntry conflicts with the requested attributes, let the child entries take the parent attributes and loosen the attribute in the parent entry. E.g.: when PDPTE[0].ReadWrite =3D 0 but caller wants to map [0-2MB as ReadWrite =3D 1 (PDE[0].ReadWrite =3D 1), we need to change PDPTE[0].ReadWrite =3D 1 and let all PDE[0-255].ReadWrite =3D 0 first. Then change PDE[0].ReadWrite =3D 1. Signed-off-by: Zhiguang Liu Signed-off-by: Ray Ni Cc: Eric Dong Reviewed-by: Eric Dong --- .../Library/CpuPageTableLib/CpuPageTable.h | 20 ++- .../Library/CpuPageTableLib/CpuPageTableMap.c | 144 ++++++++++++++++-- 2 files changed, 147 insertions(+), 17 deletions(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h b/UefiCpuPkg= /Library/CpuPageTableLib/CpuPageTable.h index c041ea3f56..627f84e4e2 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h @@ -21,7 +21,11 @@ #define REGION_LENGTH(l) LShiftU64 (1, (l) * 9 + 3) =20 typedef struct { - UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory + UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory + UINT64 ReadWrite : 1; // 0 =3D Read-Only, 1=3D Read/Write + UINT64 UserSupervisor : 1; // 0 =3D Supervisor, 1=3DUser + UINT64 Reserved : 58; + UINT64 Nx : 1; // No Execute bit } IA32_PAGE_COMMON_ENTRY; =20 /// @@ -201,4 +205,18 @@ PageTableLibGetPleBMapAttribute ( IN IA32_MAP_ATTRIBUTE *ParentMapAttribute ); =20 +/** + Return the attribute of a non-leaf page table entry. + + @param[in] Pnle Pointer to a non-leaf page table entry. + @param[in] ParentMapAttribute Pointer to the parent attribute. + + @return Attribute of the non-leaf page table entry. +**/ +UINT64 +PageTableLibGetPnleMapAttribute ( + IN IA32_PAGE_NON_LEAF_ENTRY *Pnle, + IN IA32_MAP_ATTRIBUTE *ParentMapAttribute + ); + #endif diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index a6aa1a352b..ac5d1c79f4 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -183,18 +183,32 @@ PageTableLibSetPle ( =20 @param[in] Pnle Pointer to IA32_PML5, IA32_PML4, IA32_PDPTE or IA32= _PDE. All share the same structure definition. @param[in] Attribute The attribute of the page directory referenced by t= he non-leaf. + @param[in] Mask The mask of the page directory referenced by the no= n-leaf. **/ VOID PageTableLibSetPnle ( IN IA32_PAGE_NON_LEAF_ENTRY *Pnle, - IN IA32_MAP_ATTRIBUTE *Attribute + IN IA32_MAP_ATTRIBUTE *Attribute, + IN IA32_MAP_ATTRIBUTE *Mask ) { - Pnle->Bits.Present =3D Attribute->Bits.Present; - Pnle->Bits.ReadWrite =3D Attribute->Bits.ReadWrite; - Pnle->Bits.UserSupervisor =3D Attribute->Bits.UserSupervisor; - Pnle->Bits.Nx =3D Attribute->Bits.Nx; - Pnle->Bits.Accessed =3D 0; + if (Mask->Bits.Present) { + Pnle->Bits.Present =3D Attribute->Bits.Present; + } + + if (Mask->Bits.ReadWrite) { + Pnle->Bits.ReadWrite =3D Attribute->Bits.ReadWrite; + } + + if (Mask->Bits.UserSupervisor) { + Pnle->Bits.UserSupervisor =3D Attribute->Bits.UserSupervisor; + } + + if (Mask->Bits.Nx) { + Pnle->Bits.Nx =3D Attribute->Bits.Nx; + } + + Pnle->Bits.Accessed =3D 0; =20 // // Set the attributes (WT, CD, A) to 0. @@ -210,6 +224,7 @@ PageTableLibSetPnle ( Update page table to map [LinearAddress, LinearAddress + Length) with sp= ecified attribute in the specified level. =20 @param[in] ParentPagingEntry The pointer to the page table entry to= update. + @param[in] ParentAttribute The accumulated attribute of all paren= ts' attribute. @param[in] Modify FALSE to indicate Buffer is not used a= nd BufferSize is increased by the required buffer size. @param[in] Buffer The free buffer to be used for page ta= ble creation/updating. When Modify is TRUE, it's used from th= e end. @@ -232,6 +247,7 @@ PageTableLibSetPnle ( RETURN_STATUS PageTableLibMapInLevel ( IN IA32_PAGING_ENTRY *ParentPagingEntry, + IN IA32_MAP_ATTRIBUTE *ParentAttribute, IN BOOLEAN Modify, IN VOID *Buffer, IN OUT INTN *BufferSize, @@ -259,6 +275,8 @@ PageTableLibMapInLevel ( IA32_MAP_ATTRIBUTE NopAttribute; BOOLEAN CreateNew; IA32_PAGING_ENTRY OneOfPagingEntry; + IA32_MAP_ATTRIBUTE ChildAttribute; + IA32_MAP_ATTRIBUTE ChildMask; =20 ASSERT (Level !=3D 0); ASSERT ((Attribute !=3D NULL) && (Mask !=3D NULL)); @@ -291,7 +309,7 @@ PageTableLibMapInLevel ( // // Set default attribute bits for PML5E/PML4E/PDPTE/PDE. // - PageTableLibSetPnle (&ParentPagingEntry->Pnle, &NopAttribute); + PageTableLibSetPnle (&ParentPagingEntry->Pnle, &NopAttribute, &AllOn= eMask); } else { // // Just make sure Present and MustBeZero (PageSize) bits are accurat= e. @@ -307,7 +325,7 @@ PageTableLibMapInLevel ( // Use NOP attributes as the attribute of grand-parents because CPU wi= ll consider // the actual attributes of grand-parents when determing the memory ty= pe. // - PleBAttribute.Uint64 =3D PageTableLibGetPleBMapAttribute (&ParentPagin= gEntry->PleB, &NopAttribute); + PleBAttribute.Uint64 =3D PageTableLibGetPleBMapAttribute (&ParentPagin= gEntry->PleB, ParentAttribute); if ((IA32_MAP_ATTRIBUTE_ATTRIBUTES (&PleBAttribute) & IA32_MAP_ATTRIBU= TE_ATTRIBUTES (Mask)) =3D=3D (IA32_MAP_ATTRIBUTE_ATTRIBUTES (Attribute) & IA32_MAP_ATTRI= BUTE_ATTRIBUTES (Mask))) { @@ -334,7 +352,7 @@ PageTableLibMapInLevel ( // Note: Should NOT inherit the attributes from the original entry b= ecause a zero RW bit // will make the entire region read-only even the child entrie= s set the RW bit. // - PageTableLibSetPnle (&ParentPagingEntry->Pnle, &NopAttribute); + PageTableLibSetPnle (&ParentPagingEntry->Pnle, &NopAttribute, &AllOn= eMask); =20 RegionLength =3D REGION_LENGTH (Level); PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)IA32_PNLE_PAGE_TABLE_BA= SE_ADDRESS (&ParentPagingEntry->Pnle); @@ -343,6 +361,77 @@ PageTableLibMapInLevel ( SubOffset +=3D RegionLength; } } + } else { + // + // It's a non-leaf entry + // + ChildAttribute.Uint64 =3D 0; + ChildMask.Uint64 =3D 0; + + // + // If the inheritable attributes in the parent entry conflicts with th= e requested attributes, + // let the child entries take the parent attributes and + // loosen the attribute in the parent entry + // E.g.: when PDPTE[0].ReadWrite =3D 0 but caller wants to map [0-2MB]= as ReadWrite =3D 1 (PDE[0].ReadWrite =3D 1) + // we need to change PDPTE[0].ReadWrite =3D 1 and let all P= DE[0-255].ReadWrite =3D 0 in this step. + // when PDPTE[0].Nx =3D 1 but caller wants to map [0-2MB] as Nx = =3D 0 (PDT[0].Nx =3D 0) + // we need to change PDPTE[0].Nx =3D 0 and let all PDE[0-25= 5].Nx =3D 1 in this step. + if ((ParentPagingEntry->Pnle.Bits.Present =3D=3D 0) && (Mask->Bits.Pre= sent =3D=3D 1) && (Attribute->Bits.Present =3D=3D 1)) { + if (Modify) { + ParentPagingEntry->Pnle.Bits.Present =3D 1; + } + + ChildAttribute.Bits.Present =3D 0; + ChildMask.Bits.Present =3D 1; + } + + if ((ParentPagingEntry->Pnle.Bits.ReadWrite =3D=3D 0) && (Mask->Bits.R= eadWrite =3D=3D 1) && (Attribute->Bits.ReadWrite =3D=3D 1)) { + if (Modify) { + ParentPagingEntry->Pnle.Bits.ReadWrite =3D 1; + } + + ChildAttribute.Bits.ReadWrite =3D 0; + ChildMask.Bits.ReadWrite =3D 1; + } + + if ((ParentPagingEntry->Pnle.Bits.UserSupervisor =3D=3D 0) && (Mask->B= its.UserSupervisor =3D=3D 1) && (Attribute->Bits.UserSupervisor =3D=3D 1)) { + if (Modify) { + ParentPagingEntry->Pnle.Bits.UserSupervisor =3D 1; + } + + ChildAttribute.Bits.UserSupervisor =3D 0; + ChildMask.Bits.UserSupervisor =3D 1; + } + + if ((ParentPagingEntry->Pnle.Bits.Nx =3D=3D 1) && (Mask->Bits.Nx =3D= =3D 1) && (Attribute->Bits.Nx =3D=3D 0)) { + if (Modify) { + ParentPagingEntry->Pnle.Bits.Nx =3D 0; + } + + ChildAttribute.Bits.Nx =3D 1; + ChildMask.Bits.Nx =3D 1; + } + + if (ChildMask.Uint64 !=3D 0) { + if (Modify) { + // + // Update child entries to use restrictive attribute inherited fro= m parent. + // e.g.: Set PDE[0-255].ReadWrite =3D 0 + // + PagingEntry =3D (IA32_PAGING_ENTRY *)(UINTN)IA32_PNLE_PAGE_TABLE_B= ASE_ADDRESS (&ParentPagingEntry->Pnle); + for (Index =3D 0; Index < 512; Index++) { + if (PagingEntry[Index].Pce.Present =3D=3D 0) { + continue; + } + + if (IsPle (&PagingEntry[Index], Level)) { + PageTableLibSetPle (Level - 1, &PagingEntry[Index], 0, &ChildA= ttribute, &ChildMask); + } else { + PageTableLibSetPnle (&PagingEntry[Index].Pnle, &ChildAttribute= , &ChildMask); + } + } + } + } } =20 // @@ -355,6 +444,8 @@ PageTableLibMapInLevel ( RegionMask =3D RegionLength - 1; RegionStart =3D (LinearAddress + Offset) & ~RegionMask; =20 + ParentAttribute->Uint64 =3D PageTableLibGetPnleMapAttribute (&ParentPagi= ngEntry->Pnle, ParentAttribute); + // // Apply the attribute. // @@ -386,6 +477,7 @@ PageTableLibMapInLevel ( // Status =3D PageTableLibMapInLevel ( CurrentPagingEntry, + ParentAttribute, Modify, Buffer, BufferSize, @@ -449,12 +541,13 @@ PageTableMap ( IN IA32_MAP_ATTRIBUTE *Mask ) { - RETURN_STATUS Status; - IA32_PAGING_ENTRY TopPagingEntry; - INTN RequiredSize; - UINT64 MaxLinearAddress; - UINTN MaxLevel; - UINTN MaxLeafLevel; + RETURN_STATUS Status; + IA32_PAGING_ENTRY TopPagingEntry; + INTN RequiredSize; + UINT64 MaxLinearAddress; + UINTN MaxLevel; + UINTN MaxLeafLevel; + IA32_MAP_ATTRIBUTE ParentAttribute; =20 if ((PagingMode =3D=3D Paging32bit) || (PagingMode =3D=3D PagingPae) || = (PagingMode >=3D PagingModeMax)) { // @@ -499,15 +592,26 @@ PageTableMap ( =20 TopPagingEntry.Uintn =3D *PageTable; if (TopPagingEntry.Uintn !=3D 0) { - TopPagingEntry.Pce.Present =3D 1; + TopPagingEntry.Pce.Present =3D 1; + TopPagingEntry.Pce.ReadWrite =3D 1; + TopPagingEntry.Pce.UserSupervisor =3D 1; + TopPagingEntry.Pce.Nx =3D 0; } =20 + ParentAttribute.Uint64 =3D 0; + ParentAttribute.Bits.PageTableBaseAddress =3D 1; + ParentAttribute.Bits.Present =3D 1; + ParentAttribute.Bits.ReadWrite =3D 1; + ParentAttribute.Bits.UserSupervisor =3D 1; + ParentAttribute.Bits.Nx =3D 0; + // // Query the required buffer size without modifying the page table. // RequiredSize =3D 0; Status =3D PageTableLibMapInLevel ( &TopPagingEntry, + &ParentAttribute, FALSE, NULL, &RequiredSize, @@ -537,8 +641,16 @@ PageTableMap ( // // Update the page table when the supplied buffer is sufficient. // + ParentAttribute.Uint64 =3D 0; + ParentAttribute.Bits.PageTableBaseAddress =3D 1; + ParentAttribute.Bits.Present =3D 1; + ParentAttribute.Bits.ReadWrite =3D 1; + ParentAttribute.Bits.UserSupervisor =3D 1; + ParentAttribute.Bits.Nx =3D 0; + Status =3D PageTableLibMapInLevel ( &TopPagingEntry, + &ParentAttribute, TRUE, Buffer, BufferSize, --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91456): https://edk2.groups.io/g/devel/message/91456 Mute This Topic: https://groups.io/mt/92458161/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91457+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91457+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150333; cv=none; d=zohomail.com; s=zohoarc; b=JzK+bIxcQXAJkZODvEW1brU7AmbjGiQndwEiujl1ONNwNtt86xBf1tT33EXRORKD2wRZWO3rnB8mctbGC4mYMd+gDiS2BL9T4NFWJ6c+4Nl3vbX/a1FB6SFFzao5o9DOgqIAarOQXstZz55T3Pm8/AFKxZKLtPJ7OUlLefyzkvE= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150333; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=pu6EjbWf7ypMo+Bo/RkZOOqBCoRrb3UrtMzdPNyxDAs=; b=nOOEvHw4BOd+QPytBZjcfv5r2vDN0ynR1csxQuJjGLi/myWu/UvP3l3CQy+HaUoDKoht0G3h+/PjCQq3dAheIlcG0sme5ZSbLmqKWvGQUv0PyWALahICQMPmweRViKN45HHH1RZjR9JajsghnFEUP8xFKKp4eZnizfAQNpiwDTk= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91457+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150333776351.97202724486226; Mon, 18 Jul 2022 06:18:53 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id 21VtYY1788612xhogeqcJ0d2; Mon, 18 Jul 2022 06:18:52 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web08.27105.1658150328221476289 for ; Mon, 18 Jul 2022 06:18:51 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363967" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363967" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:50 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624725005" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:49 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 08/10] CpuPageTableLib: Fix a bug to avoid unnecessary changing to page table Date: Mon, 18 Jul 2022 21:18:29 +0800 Message-Id: <20220718131831.660-9-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: COQZgOcP5QhoXibHcotZZo9px1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150332; bh=dPnlKJ22Sx7+UqNKX8xRaKB3AbF1yrPSVuMNvsOb6QQ=; h=Cc:Date:From:Reply-To:Subject:To; b=rnF48pfZLLEO23sxF8o4wJ8kbhoSrpcwbchqA9ddvFLTR7iP6Q1VnBewvPL2+4Ajo/l +ZoKaI8vU5uLumbHCth8L9MtyGk4oA8NYaNZ7Fp7AyKCDVcAItkhFE+BpLgjirCuJb95p OAH3tgNJ5En7e+LUmm/vT64J+T1ijrt5EDU= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150335588100042 Content-Type: text/plain; charset="utf-8" With the following paging structure that maps [0, 2G] with ReadWrite bit set. PML4[0] --> PDPTE[0] --> PDE[0-255] \-> PDPTE[1] --> PDE[0-255] If ReadWrite bit is cleared in PML4[0] and PageTableMap() is called to change [0, 2M] as read-only, today's logic unnecessarily changes the paging structure in 2 aspects: 1. When setting PageTableBaseAddress in the entry, the code clears all attributes. 2. Even the ReadWrite bit in parent entry is not set, the code clears the ReadWrite bit in the leaf entry. First change is wrong. It should not change other attributes when setting the PA. Second change is unnecessary. Because the parent entry already declares the whole region as read-only, there is no need to clear ReadWrite bit in the leaf entry again. Signed-off-by: Zhiguang Liu Signed-off-by: Ray Ni Cc: Eric Dong Reviewed-by: Eric Dong --- .../Library/CpuPageTableLib/CpuPageTableMap.c | 41 +++++++++++++++---- 1 file changed, 32 insertions(+), 9 deletions(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index ac5d1c79f4..1205119fc8 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -27,10 +27,7 @@ PageTableLibSetPte4K ( ) { if (Mask->Bits.PageTableBaseAddress) { - // - // Reset all attributes when the physical address is changed. - // - Pte4K->Uint64 =3D IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribut= e) + Offset; + Pte4K->Uint64 =3D (IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribu= te) + Offset) | (Pte4K->Uint64 & ~IA32_PE_BASE_ADDRESS_MASK_40); } =20 if (Mask->Bits.Present) { @@ -97,10 +94,7 @@ PageTableLibSetPleB ( ) { if (Mask->Bits.PageTableBaseAddress) { - // - // Reset all attributes when the physical address is changed. - // - PleB->Uint64 =3D IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribute= ) + Offset; + PleB->Uint64 =3D (IA32_MAP_ATTRIBUTE_PAGE_TABLE_BASE_ADDRESS (Attribut= e) + Offset) | (PleB->Uint64 & ~IA32_PE_BASE_ADDRESS_MASK_39); } =20 PleB->Bits.MustBeOne =3D 1; @@ -277,6 +271,7 @@ PageTableLibMapInLevel ( IA32_PAGING_ENTRY OneOfPagingEntry; IA32_MAP_ATTRIBUTE ChildAttribute; IA32_MAP_ATTRIBUTE ChildMask; + IA32_MAP_ATTRIBUTE CurrentMask; =20 ASSERT (Level !=3D 0); ASSERT ((Attribute !=3D NULL) && (Mask !=3D NULL)); @@ -464,7 +459,35 @@ PageTableLibMapInLevel ( // Create one entry mapping the entire region (1G, 2M or 4K). // if (Modify) { - PageTableLibSetPle (Level, CurrentPagingEntry, Offset, Attribute, = Mask); + // + // When the inheritable attributes in parent entry could override = the child attributes, + // e.g.: Present/ReadWrite/UserSupervisor is 0 in parent entry, or + // Nx is 1 in parent entry, + // we just skip setting any value to these attributes in child. + // We add assertion to make sure the requested settings don't conf= lict with parent attributes in this case. + // + CurrentMask.Uint64 =3D Mask->Uint64; + if (ParentAttribute->Bits.Present =3D=3D 0) { + CurrentMask.Bits.Present =3D 0; + ASSERT (CreateNew || (Mask->Bits.Present =3D=3D 0) || (Attribute= ->Bits.Present =3D=3D 0)); + } + + if (ParentAttribute->Bits.ReadWrite =3D=3D 0) { + CurrentMask.Bits.ReadWrite =3D 0; + ASSERT (CreateNew || (Mask->Bits.ReadWrite =3D=3D 0) || (Attribu= te->Bits.ReadWrite =3D=3D 0)); + } + + if (ParentAttribute->Bits.UserSupervisor =3D=3D 0) { + CurrentMask.Bits.UserSupervisor =3D 0; + ASSERT (CreateNew || (Mask->Bits.UserSupervisor =3D=3D 0) || (At= tribute->Bits.UserSupervisor =3D=3D 0)); + } + + if (ParentAttribute->Bits.Nx =3D=3D 1) { + CurrentMask.Bits.Nx =3D 0; + ASSERT (CreateNew || (Mask->Bits.Nx =3D=3D 0) || (Attribute->Bit= s.Nx =3D=3D 1)); + } + + PageTableLibSetPle (Level, CurrentPagingEntry, Offset, Attribute, = &CurrentMask); } } else { // --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91457): https://edk2.groups.io/g/devel/message/91457 Mute This Topic: https://groups.io/mt/92458166/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91458+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91458+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150333; cv=none; d=zohomail.com; s=zohoarc; b=WlJ/2hqSPiViGR/eASrV2+IXNo8vwa25xPuZnGV/9OK+X6zdnOSVPuTYfzCjcz3/hQnCGiTnj2ixCgjT4BRTvhRdovYTD4DPTSOEym/UDDDF5fghBvBRca6nVQff1wMvkDcW4UKMeDsgBIJ6BVccNDHCCq85qIHeApRyJMBmHEk= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150333; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=3RYuJkjhD8qxFhIS7EHYINdqH5xxf/lwmGqrD2sKiEg=; b=lY5c6NxmvSj2szXmq3ngQMbe1OWcfQJXx9S8CMPqP19xVIi/BMLZAxA1sXNrYrrXId81wq17eHmBLNYrbS7WEwB1OYmnUcgz/T6RpAPTxluE7r/tNCqkDz0dVJ4MgnUdRExf9Qrz0hAAEV0NNByDLHSunbpdH3Ig7vCGLDUU2rw= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91458+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150333571818.7291638005823; Mon, 18 Jul 2022 06:18:53 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id tS8WYY1788612xY61vcHlC6k; Mon, 18 Jul 2022 06:18:53 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web08.27105.1658150328221476289 for ; Mon, 18 Jul 2022 06:18:52 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287363982" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287363982" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:51 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624725037" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:50 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 09/10] CpuPageTableLib: Fix bug that wrongly requires extra size for mapping Date: Mon, 18 Jul 2022 21:18:30 +0800 Message-Id: <20220718131831.660-10-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: vOcmdVjo7RBclytku9wMJPGtx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150333; bh=FKXzjuzsFGcsmjzlJtu6W8Q1RvuU4WYa0OqO7jxVq2s=; h=Cc:Date:From:Reply-To:Subject:To; b=DxnooW0iKfjwAKVyVdNcsF+Ys1xU0DHrn1/l6WAmHAfu89nQJbxDhRmasPTs+dgFYMg 3XGkjRBCQgCGoUUQsHWjQo+sFFTZZ5N8tHaGIepmZy7//hKVXoi6lHSlaZdP5c+kOdeha Sfzocc7f75XB0RhsibLv5XpGKAcZQ8PodeI= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150335562100041 Content-Type: text/plain; charset="utf-8" With following paging structure to map [2M-4K, 2M] as P =3D 1, RW =3D 0, [2M, 4M] as P =3D 1, RW =3D 1: PML4[0] -> PDPTE[0] -> PDE[0](RW =3D 0) -> PTE[255](P =3D 0, RW =3D 0) -> PDE[1](RW =3D 1) When a new request to map [2M-4K, 2M+4K] as P =3D 1, RW =3D 1, CpuPageTableMap() wrongly requests 4K buffer size for the new mapping request. But in fact, for [2M-4K, 2M] request, PTE[255] can be changed in place, for [2M, 2M+4K], no change is needed because PDE[1].RW =3D 1 already. The change fixes the bug. Signed-off-by: Ray Ni Signed-off-by: Zhiguang Liu Cc: Eric Dong Reviewed-by: Eric Dong --- .../Library/CpuPageTableLib/CpuPageTableMap.c | 13 +++++-------- 1 file changed, 5 insertions(+), 8 deletions(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index 1205119fc8..16e6697ed4 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -272,6 +272,7 @@ PageTableLibMapInLevel ( IA32_MAP_ATTRIBUTE ChildAttribute; IA32_MAP_ATTRIBUTE ChildMask; IA32_MAP_ATTRIBUTE CurrentMask; + IA32_MAP_ATTRIBUTE LocalParentAttribute; =20 ASSERT (Level !=3D 0); ASSERT ((Attribute !=3D NULL) && (Mask !=3D NULL)); @@ -284,6 +285,9 @@ PageTableLibMapInLevel ( NopAttribute.Bits.ReadWrite =3D 1; NopAttribute.Bits.UserSupervisor =3D 1; =20 + LocalParentAttribute.Uint64 =3D ParentAttribute->Uint64; + ParentAttribute =3D &LocalParentAttribute; + // // ParentPagingEntry ONLY is deferenced for checking Present and MustBeO= ne bits // when Modify is FALSE. @@ -420,7 +424,7 @@ PageTableLibMapInLevel ( } =20 if (IsPle (&PagingEntry[Index], Level)) { - PageTableLibSetPle (Level - 1, &PagingEntry[Index], 0, &ChildA= ttribute, &ChildMask); + PageTableLibSetPle (Level, &PagingEntry[Index], 0, &ChildAttri= bute, &ChildMask); } else { PageTableLibSetPnle (&PagingEntry[Index].Pnle, &ChildAttribute= , &ChildMask); } @@ -664,13 +668,6 @@ PageTableMap ( // // Update the page table when the supplied buffer is sufficient. // - ParentAttribute.Uint64 =3D 0; - ParentAttribute.Bits.PageTableBaseAddress =3D 1; - ParentAttribute.Bits.Present =3D 1; - ParentAttribute.Bits.ReadWrite =3D 1; - ParentAttribute.Bits.UserSupervisor =3D 1; - ParentAttribute.Bits.Nx =3D 0; - Status =3D PageTableLibMapInLevel ( &TopPagingEntry, &ParentAttribute, --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91458): https://edk2.groups.io/g/devel/message/91458 Mute This Topic: https://groups.io/mt/92458167/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- From nobody Sat May 18 07:48:55 2024 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+91459+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91459+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1658150335; cv=none; d=zohomail.com; s=zohoarc; b=aEfjcMYxZi+OgO84rXm1w0RVCgciayYTtIVvLIx5VaS1lNsQTs4gJ4onrIr8YkgKNko5suDvDdCupV4agYY31ySpfahbbySucf2W1c/G7NirOCxmHrR1IqcAlFsosx2+VYF6NthwlWDYYJiPI0s/IkD5kpkC9rc8ZHGQsbagOFs= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1658150335; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Id:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=lToTeRd9a5bG+0dICSB/QeBKhvMMHudsKURpztHRcQA=; b=C91AFxREhDh2PvmdEgrhgoMfJOma+SJ/m9NJL4qlHTkogROeIqAPCDkB3QTPVczAIkwYKlwEpYKE63vVwhfu9LCcLHIwxQeBPNIgRQpF7lNxpXy3PpV3dHVmQMN8IFNnEomlbjhT2m7lA5eAjulFASSkebmWCAKk6kUMkZtH0TU= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+91459+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1658150335647307.0080385177273; Mon, 18 Jul 2022 06:18:55 -0700 (PDT) Return-Path: X-Received: by 127.0.0.2 with SMTP id en5bYY1788612xVM1qdjBkfI; Mon, 18 Jul 2022 06:18:54 -0700 X-Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) by mx.groups.io with SMTP id smtpd.web08.27105.1658150328221476289 for ; Mon, 18 Jul 2022 06:18:53 -0700 X-IronPort-AV: E=McAfee;i="6400,9594,10411"; a="287364008" X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="287364008" X-Received: from orsmga008.jf.intel.com ([10.7.209.65]) by orsmga103.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 18 Jul 2022 06:18:52 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.92,281,1650956400"; d="scan'208";a="624725057" X-Received: from shwdeopenlab706.ccr.corp.intel.com ([10.239.183.102]) by orsmga008.jf.intel.com with ESMTP; 18 Jul 2022 06:18:51 -0700 From: "Ni, Ray" To: devel@edk2.groups.io Cc: Zhiguang Liu , Eric Dong Subject: [edk2-devel] [PATCH 10/10] CpuPageTableLib: define IA32_PAGE_LEVEL enum type internally Date: Mon, 18 Jul 2022 21:18:31 +0800 Message-Id: <20220718131831.660-11-ray.ni@intel.com> In-Reply-To: <20220718131831.660-1-ray.ni@intel.com> References: <20220718131831.660-1-ray.ni@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,ray.ni@intel.com X-Gm-Message-State: TzwJEcOogTrKwUUSSDRbKh5dx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1658150334; bh=6vrkjOtW3qfs9m7TTZ13S70MehrkCGsKlHJrvPO9+DI=; h=Cc:Date:From:Reply-To:Subject:To; b=GCTMOJiXIWEhiJFM1VLDcCISUJNGr0eOKLZDQdIKovAZPzxpH2TYSUzc2NCbQDAXpTD Itm8S0BTzcd1GTUjJxwndi+N+cGn3H2WteSC7BQQ1SSXH1+7rwDFq+WVpzljFAFtqPVIN Ro85iZW6p3D8hzwcRs6cS7bTC6jksI0yRmY= X-ZohoMail-DKIM: pass (identity @groups.io) X-ZM-MESSAGEID: 1658150337575100045 Content-Type: text/plain; charset="utf-8" The change doesn't change functionality behavior. Signed-off-by: Ray Ni Cc: Zhiguang Liu Cc: Eric Dong Reviewed-by: Eric Dong --- UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h | 8 ++++++++ UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c | 12 ++++++------ 2 files changed, 14 insertions(+), 6 deletions(-) diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h b/UefiCpuPkg= /Library/CpuPageTableLib/CpuPageTable.h index 627f84e4e2..8d856d7c7e 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTable.h @@ -20,6 +20,14 @@ =20 #define REGION_LENGTH(l) LShiftU64 (1, (l) * 9 + 3) =20 +typedef enum { + Pte =3D 1, + Pde =3D 2, + Pdpte =3D 3, + Pml4 =3D 4, + Pml5 =3D 5 +} IA32_PAGE_LEVEL; + typedef struct { UINT64 Present : 1; // 0 =3D Not present in memory, 1 = =3D Present in memory UINT64 ReadWrite : 1; // 0 =3D Read-Only, 1=3D Read/Write diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c b/UefiCpu= Pkg/Library/CpuPageTableLib/CpuPageTableMap.c index 16e6697ed4..d3fdf13429 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableMap.c @@ -245,8 +245,8 @@ PageTableLibMapInLevel ( IN BOOLEAN Modify, IN VOID *Buffer, IN OUT INTN *BufferSize, - IN UINTN Level, - IN UINTN MaxLeafLevel, + IN IA32_PAGE_LEVEL Level, + IN IA32_PAGE_LEVEL MaxLeafLevel, IN UINT64 LinearAddress, IN UINT64 Length, IN UINT64 Offset, @@ -572,8 +572,8 @@ PageTableMap ( IA32_PAGING_ENTRY TopPagingEntry; INTN RequiredSize; UINT64 MaxLinearAddress; - UINTN MaxLevel; - UINTN MaxLeafLevel; + IA32_PAGE_LEVEL MaxLevel; + IA32_PAGE_LEVEL MaxLeafLevel; IA32_MAP_ATTRIBUTE ParentAttribute; =20 if ((PagingMode =3D=3D Paging32bit) || (PagingMode =3D=3D PagingPae) || = (PagingMode >=3D PagingModeMax)) { @@ -606,8 +606,8 @@ PageTableMap ( return RETURN_INVALID_PARAMETER; } =20 - MaxLeafLevel =3D (UINT8)PagingMode; - MaxLevel =3D (UINT8)(PagingMode >> 8); + MaxLeafLevel =3D (IA32_PAGE_LEVEL)(UINT8)PagingMode; + MaxLevel =3D (IA32_PAGE_LEVEL)(UINT8)(PagingMode >> 8); MaxLinearAddress =3D LShiftU64 (1, 12 + MaxLevel * 9); =20 if ((LinearAddress > MaxLinearAddress) || (Length > MaxLinearAddress - L= inearAddress)) { --=20 2.35.1.windows.2 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#91459): https://edk2.groups.io/g/devel/message/91459 Mute This Topic: https://groups.io/mt/92458168/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-