]> xenbits.xensource.com Git - ovmf.git/commitdiff
UefiCpuPkg/CpuPageTableLib: Add manual test to check Mask and Attr
authorDun Tan <dun.tan@intel.com>
Fri, 24 Feb 2023 07:25:09 +0000 (15:25 +0800)
committermergify[bot] <37929162+mergify[bot]@users.noreply.github.com>
Mon, 27 Mar 2023 08:21:58 +0000 (08:21 +0000)
Add manual test case to check input Mask and Attribute. The check
steps are:
1.Create Page table to cover [0, 2G]. All fields of MapMask should
  be set.
2.Update Page table to set [2G - 8K,2G] from present to non-present.
  All fields of MapMask except present should not be set.
3.Still set [2G - 8K, 2G] as not present, this case is permitted.
  But set [2G - 8K, 2G] as RW is not permitted.
4.Update Page table to set [2G - 8K, 2G] as present and RW. All
  fields of MapMask should be set.

Signed-off-by: Dun Tan <dun.tan@intel.com>
Cc: Eric Dong <eric.dong@intel.com>
Reviewed-by: Ray Ni <ray.ni@intel.com>
Cc: Rahul Kumar <rahul1.kumar@intel.com>
Tested-by: Gerd Hoffmann <kraxel@redhat.com>
Acked-by: Gerd Hoffmann <kraxel@redhat.com>
UefiCpuPkg/Library/CpuPageTableLib/UnitTest/CpuPageTableLibUnitTestHost.c

index 3014a032438467a3442259db60f64a6aec30d93f..52fae1864acc6c95495e20335a6cefb174b8ed13 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   Unit tests of the CpuPageTableLib instance of the CpuPageTableLib class\r
 \r
-  Copyright (c) 2022, Intel Corporation. All rights reserved.<BR>\r
+  Copyright (c) 2022 - 2023, Intel Corporation. All rights reserved.<BR>\r
   SPDX-License-Identifier: BSD-2-Clause-Patent\r
 \r
 **/\r
@@ -697,6 +697,131 @@ TestCaseManualChangeNx (
   return UNIT_TEST_PASSED;\r
 }\r
 \r
+/**\r
+  Check if the input Mask and Attribute is as expected when creating new page table or\r
+  updating existing page table.\r
+\r
+  @param[in]  Context    [Optional] An optional parameter that enables:\r
+                         1) test-case reuse with varied parameters and\r
+                         2) test-case re-entry for Target tests that need a\r
+                         reboot.  This parameter is a VOID* and it is the\r
+                         responsibility of the test author to ensure that the\r
+                         contents are well understood by all test cases that may\r
+                         consume it.\r
+\r
+  @retval  UNIT_TEST_PASSED             The Unit test has completed and the test\r
+                                        case was successful.\r
+  @retval  UNIT_TEST_ERROR_TEST_FAILED  A test case assertion has failed.\r
+**/\r
+UNIT_TEST_STATUS\r
+EFIAPI\r
+TestCaseToCheckMapMaskAndAttr (\r
+  IN UNIT_TEST_CONTEXT  Context\r
+  )\r
+{\r
+  UINTN               PageTable;\r
+  PAGING_MODE         PagingMode;\r
+  VOID                *Buffer;\r
+  UINTN               PageTableBufferSize;\r
+  IA32_MAP_ATTRIBUTE  MapAttribute;\r
+  IA32_MAP_ATTRIBUTE  ExpectedMapAttribute;\r
+  IA32_MAP_ATTRIBUTE  MapMask;\r
+  RETURN_STATUS       Status;\r
+  IA32_MAP_ENTRY      *Map;\r
+  UINTN               MapCount;\r
+\r
+  PagingMode                = Paging4Level;\r
+  PageTableBufferSize       = 0;\r
+  PageTable                 = 0;\r
+  Buffer                    = NULL;\r
+  MapAttribute.Uint64       = 0;\r
+  MapAttribute.Bits.Present = 1;\r
+  MapMask.Uint64            = 0;\r
+  MapMask.Bits.Present      = 1;\r
+  //\r
+  // Create Page table to cover [0, 2G]. All fields of MapMask should be set.\r
+  //\r
+  Status = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, 0, SIZE_2GB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_INVALID_PARAMETER);\r
+  MapMask.Uint64 = MAX_UINT64;\r
+  Status         = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, 0, SIZE_2GB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_BUFFER_TOO_SMALL);\r
+  Buffer = AllocatePages (EFI_SIZE_TO_PAGES (PageTableBufferSize));\r
+  Status = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, 0, SIZE_2GB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_SUCCESS);\r
+\r
+  //\r
+  // Update Page table to set [2G - 8K, 2G] from present to non-present. All fields of MapMask except present should not be set.\r
+  //\r
+  PageTableBufferSize    = 0;\r
+  MapAttribute.Uint64    = SIZE_2GB - SIZE_8KB;\r
+  MapMask.Uint64         = 0;\r
+  MapMask.Bits.Present   = 1;\r
+  MapMask.Bits.ReadWrite = 1;\r
+  Status                 = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, SIZE_2GB - SIZE_8KB, SIZE_8KB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_INVALID_PARAMETER);\r
+  MapMask.Bits.ReadWrite = 0;\r
+  Status                 = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, SIZE_2GB - SIZE_8KB, SIZE_8KB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_BUFFER_TOO_SMALL);\r
+  Buffer = AllocatePages (EFI_SIZE_TO_PAGES (PageTableBufferSize));\r
+  Status = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, 0, SIZE_2GB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_SUCCESS);\r
+\r
+  //\r
+  // Still set [2G - 8K, 2G] as not present, this case is permitted. But set [2G - 8K, 2G] as RW is not permitted.\r
+  //\r
+  PageTableBufferSize  = 0;\r
+  MapAttribute.Uint64  = 0;\r
+  MapMask.Uint64       = 0;\r
+  MapMask.Bits.Present = 1;\r
+  Status               = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, SIZE_2GB - SIZE_8KB, SIZE_8KB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_SUCCESS);\r
+  MapAttribute.Bits.ReadWrite = 1;\r
+  MapMask.Bits.ReadWrite      = 1;\r
+  Status                      = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, SIZE_2GB - SIZE_8KB, SIZE_8KB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_INVALID_PARAMETER);\r
+\r
+  //\r
+  // Update Page table to set [2G - 8K, 2G] as present and RW. All fields of MapMask should be set.\r
+  //\r
+  PageTableBufferSize         = 0;\r
+  MapAttribute.Uint64         = SIZE_2GB - SIZE_8KB;\r
+  MapAttribute.Bits.ReadWrite = 1;\r
+  MapAttribute.Bits.Present   = 1;\r
+  MapMask.Uint64              = 0;\r
+  MapMask.Bits.ReadWrite      = 1;\r
+  MapMask.Bits.Present        = 1;\r
+  Status                      = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, SIZE_2GB - SIZE_8KB, SIZE_8KB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_INVALID_PARAMETER);\r
+  MapMask.Uint64 = MAX_UINT64;\r
+  Status         = PageTableMap (&PageTable, PagingMode, Buffer, &PageTableBufferSize, SIZE_2GB - SIZE_8KB, SIZE_8KB, &MapAttribute, &MapMask);\r
+  UT_ASSERT_EQUAL (Status, RETURN_SUCCESS);\r
+\r
+  MapCount = 0;\r
+  Status   = PageTableParse (PageTable, PagingMode, NULL, &MapCount);\r
+  UT_ASSERT_EQUAL (Status, RETURN_BUFFER_TOO_SMALL);\r
+  Map    = AllocatePages (EFI_SIZE_TO_PAGES (MapCount* sizeof (IA32_MAP_ENTRY)));\r
+  Status = PageTableParse (PageTable, PagingMode, Map, &MapCount);\r
+  UT_ASSERT_EQUAL (Status, RETURN_SUCCESS);\r
+\r
+  //\r
+  // There should be two ranges [0, 2G-8k] with RW = 0 and [2G-8k, 2G] with RW = 1\r
+  //\r
+  UT_ASSERT_EQUAL (MapCount, 2);\r
+  UT_ASSERT_EQUAL (Map[0].LinearAddress, 0);\r
+  UT_ASSERT_EQUAL (Map[0].Length, SIZE_2GB - SIZE_8KB);\r
+  ExpectedMapAttribute.Uint64       =  0;\r
+  ExpectedMapAttribute.Bits.Present =  1;\r
+  UT_ASSERT_EQUAL (Map[0].Attribute.Uint64, ExpectedMapAttribute.Uint64);\r
+  UT_ASSERT_EQUAL (Map[1].LinearAddress, SIZE_2GB - SIZE_8KB);\r
+  UT_ASSERT_EQUAL (Map[1].Length, SIZE_8KB);\r
+  ExpectedMapAttribute.Uint64         =   SIZE_2GB - SIZE_8KB;\r
+  ExpectedMapAttribute.Bits.Present   = 1;\r
+  ExpectedMapAttribute.Bits.ReadWrite = 1;\r
+  UT_ASSERT_EQUAL (Map[1].Attribute.Uint64, ExpectedMapAttribute.Uint64);\r
+  return UNIT_TEST_PASSED;\r
+}\r
+\r
 /**\r
   Initialize the unit test framework, suite, and unit tests for the\r
   sample unit tests and run the unit tests.\r
@@ -746,7 +871,7 @@ UefiTestMain (
   AddTestCase (ManualTestCase, "Check if the parent entry has different ReadWrite attribute", "Manual Test Case5", TestCaseManualChangeReadWrite, NULL, NULL, NULL);\r
   AddTestCase (ManualTestCase, "Check if the parent entry has different Nx attribute", "Manual Test Case6", TestCaseManualChangeNx, NULL, NULL, NULL);\r
   AddTestCase (ManualTestCase, "Check if the needed size is expected", "Manual Test Case7", TestCaseManualSizeNotMatch, NULL, NULL, NULL);\r
-\r
+  AddTestCase (ManualTestCase, "Check MapMask when creating new page table or mapping not-present range", "Manual Test Case8", TestCaseToCheckMapMaskAndAttr, NULL, NULL, NULL);\r
   //\r
   // Populate the Random Test Cases.\r
   //\r