]> git.proxmox.com Git - mirror_edk2.git/commitdiff
ShellPkg: acpiview: SLIT: Validate System Locality count
authorKrzysztof Koch <krzysztof.koch@arm.com>
Mon, 20 Jan 2020 11:13:45 +0000 (19:13 +0800)
committermergify[bot] <37929162+mergify[bot]@users.noreply.github.com>
Tue, 11 Feb 2020 02:12:45 +0000 (02:12 +0000)
1. Check if the 'Number of System Localities' provided can be
represented in the SLIT table. The table 'Length' field is a 32-bit
value while the 'Number of System Localities' field is 64-bit long.

2. Check if the SLIT matrix fits in the table buffer. If N is the SLIT
locality count, then the matrix used to represent the localities is
N*N bytes long. The ACPI table length must be big enough to fit the
matrix.

3. Remove (now) redundant 64x64 bit multiplication.

Signed-off-by: Krzysztof Koch <krzysztof.koch@arm.com>
ShellPkg/Library/UefiShellAcpiViewCommandLib/Parsers/Slit/SlitParser.c

index 17e2166a09d8615b714e0c51d4d93d293fcdf601..e4625ee8b13907893a9b6990ecb956baf91cc3b9 100644 (file)
@@ -30,7 +30,7 @@ STATIC CONST ACPI_PARSER SlitParser[] = {
 /**\r
   Macro to get the value of a System Locality\r
 **/\r
-#define SLIT_ELEMENT(Ptr, i, j) *(Ptr + (MultU64x64 (i, LocalityCount)) + j)\r
+#define SLIT_ELEMENT(Ptr, i, j) *(Ptr + (i * LocalityCount) + j)\r
 \r
 /**\r
   This function parses the ACPI SLIT table.\r
@@ -57,9 +57,9 @@ ParseAcpiSlit (
   )\r
 {\r
   UINT32 Offset;\r
-  UINT64 Count;\r
-  UINT64 Index;\r
-  UINT64 LocalityCount;\r
+  UINT32 Count;\r
+  UINT32 Index;\r
+  UINT32 LocalityCount;\r
   UINT8* LocalityPtr;\r
   CHAR16 Buffer[80];  // Used for AsciiName param of ParseAcpi\r
 \r
@@ -87,8 +87,45 @@ ParseAcpiSlit (
     return;\r
   }\r
 \r
+  /*\r
+    Despite the 'Number of System Localities' being a 64-bit field in SLIT,\r
+    the maximum number of localities that can be represented in SLIT is limited\r
+    by the 'Length' field of the ACPI table.\r
+\r
+    Since the ACPI table length field is 32-bit wide. The maximum number of\r
+    localities that can be represented in SLIT can be calculated as:\r
+\r
+    MaxLocality = sqrt (MAX_UINT32 - sizeof (EFI_ACPI_6_3_SYSTEM_LOCALITY_DISTANCE_INFORMATION_TABLE_HEADER))\r
+                = 65535\r
+                = MAX_UINT16\r
+  */\r
+  if (*SlitSystemLocalityCount > MAX_UINT16) {\r
+    IncrementErrorCount ();\r
+    Print (\r
+      L"ERROR: The Number of System Localities provided can't be represented " \\r
+        L"in the SLIT table. SlitSystemLocalityCount = %ld. " \\r
+        L"MaxLocalityCountAllowed = %d.\n",\r
+      *SlitSystemLocalityCount,\r
+      MAX_UINT16\r
+      );\r
+    return;\r
+  }\r
+\r
+  LocalityCount = (UINT32)*SlitSystemLocalityCount;\r
+\r
+  // Make sure system localities fit in the table buffer provided\r
+  if (Offset + (LocalityCount * LocalityCount) > AcpiTableLength) {\r
+    IncrementErrorCount ();\r
+    Print (\r
+      L"ERROR: Invalid Number of System Localities. " \\r
+        L"SlitSystemLocalityCount = %ld. AcpiTableLength = %d.\n",\r
+      *SlitSystemLocalityCount,\r
+      AcpiTableLength\r
+      );\r
+    return;\r
+  }\r
+\r
   LocalityPtr = Ptr + Offset;\r
-  LocalityCount = *SlitSystemLocalityCount;\r
 \r
   // We only print the Localities if the count is less than 16\r
   // If the locality count is more than 16 then refer to the\r