REF: https://bugzilla.tianocore.org/show_bug.cgi?id=3737 Apply uncrustify changes to .c/.h files in the ShellPkg package Cc: Andrew Fish <afish@apple.com> Cc: Leif Lindholm <leif@nuviainc.com> Cc: Michael D Kinney <michael.d.kinney@intel.com> Signed-off-by: Michael Kubacki <michael.kubacki@microsoft.com> Reviewed-by: Ray Ni <ray.ni@intel.com>
		
			
				
	
	
		
			668 lines
		
	
	
		
			20 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			668 lines
		
	
	
		
			20 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
| /** @file
 | |
|   HMAT table parser
 | |
| 
 | |
|   Copyright (c) 2020, Arm Limited.
 | |
|   SPDX-License-Identifier: BSD-2-Clause-Patent
 | |
| 
 | |
|   @par Reference(s):
 | |
|     - ACPI 6.3 Specification - January 2019
 | |
| 
 | |
|   @par Glossary:
 | |
|     - MPDA  - Memory Proximity Domain Attributes
 | |
|     - SLLBI - System Locality Latency and Bandwidth Information
 | |
|     - MSCI  - Memory Side Cache Information
 | |
|     - Dom   - Domain
 | |
| **/
 | |
| 
 | |
| #include <Library/PrintLib.h>
 | |
| #include <Library/BaseLib.h>
 | |
| #include <Library/UefiLib.h>
 | |
| #include "AcpiParser.h"
 | |
| #include "AcpiView.h"
 | |
| 
 | |
| // Maximum Memory Domain matrix print size.
 | |
| #define MAX_MEMORY_DOMAIN_TARGET_PRINT_MATRIX  10
 | |
| 
 | |
| // Local variables
 | |
| STATIC CONST UINT16  *HmatStructureType;
 | |
| STATIC CONST UINT32  *HmatStructureLength;
 | |
| 
 | |
| STATIC CONST UINT32  *NumberInitiatorProximityDomain;
 | |
| STATIC CONST UINT32  *NumberTargetProximityDomain;
 | |
| STATIC CONST
 | |
| EFI_ACPI_6_4_HMAT_STRUCTURE_SYSTEM_LOCALITY_LATENCY_AND_BANDWIDTH_INFO_FLAGS *
 | |
|   SllbiFlags;
 | |
| 
 | |
| STATIC CONST UINT8   *SllbiDataType;
 | |
| STATIC CONST UINT16  *NumberSMBIOSHandles;
 | |
| 
 | |
| STATIC ACPI_DESCRIPTION_HEADER_INFO  AcpiHdrInfo;
 | |
| 
 | |
| /**
 | |
|   Names of System Locality Latency Bandwidth Information (SLLBI) data types
 | |
| **/
 | |
| STATIC CONST CHAR16  *SllbiNames[] = {
 | |
|   L"Access %sLatency%s",
 | |
|   L"Read %sLatency%s",
 | |
|   L"Write %sLatency%s",
 | |
|   L"Access %sBandwidth%s",
 | |
|   L"Read %sBandwidth%s",
 | |
|   L"Write %sBandwidth%s"
 | |
| };
 | |
| 
 | |
| /**
 | |
|   This function validates the Cache Attributes field.
 | |
| 
 | |
|   @param [in] Ptr     Pointer to the start of the field data.
 | |
|   @param [in] Context Pointer to context specific information e.g. this
 | |
|                       could be a pointer to the ACPI table header.
 | |
| **/
 | |
| STATIC
 | |
| VOID
 | |
| EFIAPI
 | |
| ValidateCacheAttributes (
 | |
|   IN UINT8  *Ptr,
 | |
|   IN VOID   *Context
 | |
|   )
 | |
| {
 | |
|   EFI_ACPI_6_4_HMAT_STRUCTURE_MEMORY_SIDE_CACHE_INFO_CACHE_ATTRIBUTES *
 | |
|     Attributes;
 | |
| 
 | |
|   Attributes =
 | |
|     (EFI_ACPI_6_4_HMAT_STRUCTURE_MEMORY_SIDE_CACHE_INFO_CACHE_ATTRIBUTES *)Ptr;
 | |
| 
 | |
|   if (Attributes->TotalCacheLevels > 0x3) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"\nERROR: Attributes bits [3:0] have invalid value: 0x%x",
 | |
|       Attributes->TotalCacheLevels
 | |
|       );
 | |
|   }
 | |
| 
 | |
|   if (Attributes->CacheLevel > 0x3) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"\nERROR: Attributes bits [7:4] have invalid value: 0x%x",
 | |
|       Attributes->CacheLevel
 | |
|       );
 | |
|   }
 | |
| 
 | |
|   if (Attributes->CacheAssociativity > 0x2) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"\nERROR: Attributes bits [11:8] have invalid value: 0x%x",
 | |
|       Attributes->CacheAssociativity
 | |
|       );
 | |
|   }
 | |
| 
 | |
|   if (Attributes->WritePolicy > 0x2) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"\nERROR: Attributes bits [15:12] have invalid value: 0x%x",
 | |
|       Attributes->WritePolicy
 | |
|       );
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|   Dumps the cache attributes field
 | |
| 
 | |
|   @param [in] Format  Optional format string for tracing the data.
 | |
|   @param [in] Ptr     Pointer to the start of the buffer.
 | |
| **/
 | |
| STATIC
 | |
| VOID
 | |
| EFIAPI
 | |
| DumpCacheAttributes (
 | |
|   IN CONST CHAR16  *Format OPTIONAL,
 | |
|   IN UINT8         *Ptr
 | |
|   )
 | |
| {
 | |
|   EFI_ACPI_6_4_HMAT_STRUCTURE_MEMORY_SIDE_CACHE_INFO_CACHE_ATTRIBUTES *
 | |
|     Attributes;
 | |
| 
 | |
|   Attributes =
 | |
|     (EFI_ACPI_6_4_HMAT_STRUCTURE_MEMORY_SIDE_CACHE_INFO_CACHE_ATTRIBUTES *)Ptr;
 | |
| 
 | |
|   Print (L"\n");
 | |
|   PrintFieldName (4, L"Total Cache Levels");
 | |
|   Print (L"%d\n", Attributes->TotalCacheLevels);
 | |
|   PrintFieldName (4, L"Cache Level");
 | |
|   Print (L"%d\n", Attributes->CacheLevel);
 | |
|   PrintFieldName (4, L"Cache Associativity");
 | |
|   Print (L"%d\n", Attributes->CacheAssociativity);
 | |
|   PrintFieldName (4, L"Write Policy");
 | |
|   Print (L"%d\n", Attributes->WritePolicy);
 | |
|   PrintFieldName (4, L"Cache Line Size");
 | |
|   Print (L"%d\n", Attributes->CacheLineSize);
 | |
| }
 | |
| 
 | |
| /**
 | |
|   An ACPI_PARSER array describing the ACPI HMAT Table.
 | |
| */
 | |
| STATIC CONST ACPI_PARSER  HmatParser[] = {
 | |
|   PARSE_ACPI_HEADER (&AcpiHdrInfo),
 | |
|   { L"Reserved",                   4,36, NULL, NULL, NULL, NULL, NULL }
 | |
| };
 | |
| 
 | |
| /**
 | |
|   An ACPI_PARSER array describing the HMAT structure header.
 | |
| */
 | |
| STATIC CONST ACPI_PARSER  HmatStructureHeaderParser[] = {
 | |
|   { L"Type",     2, 0, NULL, NULL, (VOID **)&HmatStructureType,   NULL, NULL },
 | |
|   { L"Reserved", 2, 2, NULL, NULL, NULL,                          NULL, NULL },
 | |
|   { L"Length",   4, 4, NULL, NULL, (VOID **)&HmatStructureLength, NULL, NULL }
 | |
| };
 | |
| 
 | |
| /**
 | |
|   An ACPI PARSER array describing the Memory Proximity Domain Attributes
 | |
|   Structure - Type 0.
 | |
| */
 | |
| STATIC CONST ACPI_PARSER  MemProximityDomainAttributeParser[] = {
 | |
|   { L"Type",                        2, 0,  L"0x%x",  NULL, NULL, NULL, NULL },
 | |
|   { L"Reserved",                    2, 2,  L"0x%x",  NULL, NULL, NULL, NULL },
 | |
|   { L"Length",                      4, 4,  L"%d",    NULL, NULL, NULL, NULL },
 | |
|   { L"Flags",                       2, 8,  L"0x%x",  NULL, NULL, NULL, NULL },
 | |
|   { L"Reserved",                    2, 10, L"0x%x",  NULL, NULL, NULL, NULL },
 | |
|   { L"Proximity Dom for initiator", 4, 12, L"0x%x",  NULL, NULL, NULL, NULL },
 | |
|   { L"Proximity Dom for memory",    4, 16, L"0x%x",  NULL, NULL, NULL, NULL },
 | |
|   { L"Reserved",                    4, 20, L"0x%x",  NULL, NULL, NULL, NULL },
 | |
|   { L"Reserved",                    8, 24, L"0x%lx", NULL, NULL, NULL, NULL },
 | |
|   { L"Reserved",                    8, 32, L"0x%lx", NULL, NULL, NULL, NULL }
 | |
| };
 | |
| 
 | |
| /**
 | |
|   An ACPI PARSER array describing the System Locality Latency and Bandwidth
 | |
|   Information Structure - Type 1.
 | |
| */
 | |
| STATIC CONST ACPI_PARSER  SllbiParser[] = {
 | |
|   { L"Type",                          2, 0,  L"0x%x",  NULL, NULL,                    NULL, NULL },
 | |
|   { L"Reserved",                      2, 2,  L"0x%x",  NULL, NULL,                    NULL, NULL },
 | |
|   { L"Length",                        4, 4,  L"%d",    NULL, NULL,                    NULL, NULL },
 | |
|   { L"Flags",                         1, 8,  L"0x%x",  NULL, (VOID **)&SllbiFlags,    NULL, NULL },
 | |
|   { L"Data type",                     1, 9,  L"0x%x",  NULL, (VOID **)&SllbiDataType, NULL, NULL },
 | |
|   { L"Min Transfer Size",             1, 10, L"%d",    NULL, NULL,                    NULL, NULL },
 | |
|   { L"Reserved",                      1, 11, L"0x%x",  NULL, NULL,                    NULL, NULL },
 | |
|   { L"Initiator Proximity Dom Count", 4, 12, L"%d",    NULL,
 | |
|     (VOID **)&NumberInitiatorProximityDomain, NULL, NULL },
 | |
|   { L"Target Proximity Dom Count",    4, 16, L"%d",    NULL,
 | |
|     (VOID **)&NumberTargetProximityDomain, NULL, NULL },
 | |
|   { L"Reserved",                      4, 20, L"0x%x",  NULL, NULL,                    NULL, NULL },
 | |
|   { L"Entry Base Unit",               8, 24, L"0x%lx", NULL, NULL,                    NULL, NULL }
 | |
|   // initiator Proximity Domain list ...
 | |
|   // target Proximity Domain list ...
 | |
|   // Latency/Bandwidth matrix ...
 | |
| };
 | |
| 
 | |
| /**
 | |
|   An ACPI PARSER array describing the Memory Side Cache Information
 | |
|   Structure - Type 2.
 | |
| */
 | |
| STATIC CONST ACPI_PARSER  MemSideCacheInfoParser[] = {
 | |
|   { L"Type",                     2, 0,  L"0x%x",  NULL,                NULL, NULL, NULL },
 | |
|   { L"Reserved",                 2, 2,  L"0x%x",  NULL,                NULL, NULL, NULL },
 | |
|   { L"Length",                   4, 4,  L"%d",    NULL,                NULL, NULL, NULL },
 | |
|   { L"Proximity Dom for memory", 4, 8,  L"0x%x",  NULL,                NULL, NULL, NULL },
 | |
|   { L"Reserved",                 4, 12, L"0x%x",  NULL,                NULL, NULL, NULL },
 | |
|   { L"Memory Side Cache Size",   8, 16, L"0x%lx", NULL,                NULL, NULL, NULL },
 | |
|   { L"Cache Attributes",         4, 24, NULL,     DumpCacheAttributes, NULL,
 | |
|     ValidateCacheAttributes, NULL },
 | |
|   { L"Reserved",                 2, 28, L"0x%x",  NULL,                NULL, NULL, NULL },
 | |
|   { L"SMBIOS Handle Count",      2, 30, L"%d",    NULL,
 | |
|     (VOID **)&NumberSMBIOSHandles, NULL, NULL }
 | |
|   // SMBIOS handles List ...
 | |
| };
 | |
| 
 | |
| /**
 | |
|   This function parses the Memory Proximity Domain Attributes
 | |
|   Structure (Type 0).
 | |
| 
 | |
|   @param [in] Ptr     Pointer to the start of the Memory Proximity Domain
 | |
|                       Attributes Structure data.
 | |
|   @param [in] Length  Length of the Memory Proximity Domain Attributes
 | |
|                       Structure.
 | |
| **/
 | |
| STATIC
 | |
| VOID
 | |
| DumpMpda (
 | |
|   IN UINT8   *Ptr,
 | |
|   IN UINT32  Length
 | |
|   )
 | |
| {
 | |
|   ParseAcpi (
 | |
|     TRUE,
 | |
|     2,
 | |
|     "Memory Proximity Domain Attributes Structure",
 | |
|     Ptr,
 | |
|     Length,
 | |
|     PARSER_PARAMS (MemProximityDomainAttributeParser)
 | |
|     );
 | |
| }
 | |
| 
 | |
| /**
 | |
|   This function parses the System Locality Latency and Bandwidth Information
 | |
|   Structure (Type 1).
 | |
| 
 | |
|   @param [in] Ptr     Pointer to the start of the System Locality Latency and
 | |
|                       Bandwidth Information Structure data.
 | |
|   @param [in] Length  Length of the System Locality Latency and Bandwidth
 | |
|                       Information Structure.
 | |
| **/
 | |
| STATIC
 | |
| VOID
 | |
| DumpSllbi (
 | |
|   IN UINT8   *Ptr,
 | |
|   IN UINT32  Length
 | |
|   )
 | |
| {
 | |
|   CONST UINT32  *InitiatorProximityDomainList;
 | |
|   CONST UINT32  *TargetProximityDomainList;
 | |
|   CONST UINT16  *LatencyBandwidthMatrix;
 | |
|   UINT32        Offset;
 | |
|   CHAR16        Buffer[OUTPUT_FIELD_COLUMN_WIDTH];
 | |
|   CHAR16        SecondBuffer[OUTPUT_FIELD_COLUMN_WIDTH];
 | |
|   UINT32        RequiredTableSize;
 | |
|   UINT32        Index;
 | |
|   UINT32        IndexInitiator;
 | |
|   UINT32        IndexTarget;
 | |
|   UINT32        TargetStartOffset;
 | |
| 
 | |
|   Offset = ParseAcpi (
 | |
|              TRUE,
 | |
|              2,
 | |
|              "System Locality Latency and Bandwidth Information Structure",
 | |
|              Ptr,
 | |
|              Length,
 | |
|              PARSER_PARAMS (SllbiParser)
 | |
|              );
 | |
| 
 | |
|   // Check if the values used to control the parsing logic have been
 | |
|   // successfully read.
 | |
|   if ((SllbiFlags == NULL)                     ||
 | |
|       (SllbiDataType == NULL)                  ||
 | |
|       (NumberInitiatorProximityDomain == NULL) ||
 | |
|       (NumberTargetProximityDomain == NULL))
 | |
|   {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"ERROR: Insufficient remaining table buffer length to read the " \
 | |
|       L"SLLBI structure header. Length = %d.\n",
 | |
|       Length
 | |
|       );
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   RequiredTableSize = (*NumberInitiatorProximityDomain * sizeof (UINT32)) +
 | |
|                       (*NumberTargetProximityDomain * sizeof (UINT32)) +
 | |
|                       (*NumberInitiatorProximityDomain *
 | |
|                        *NumberTargetProximityDomain * sizeof (UINT16)) +
 | |
|                       Offset;
 | |
| 
 | |
|   if (RequiredTableSize > Length) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"ERROR: Insufficient System Locality Latency and Bandwidth" \
 | |
|       L"Information Structure length. TableLength = %d. " \
 | |
|       L"RequiredTableLength = %d.\n",
 | |
|       Length,
 | |
|       RequiredTableSize
 | |
|       );
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   InitiatorProximityDomainList = (UINT32 *)(Ptr + Offset);
 | |
|   TargetProximityDomainList    = InitiatorProximityDomainList +
 | |
|                                  *NumberInitiatorProximityDomain;
 | |
|   LatencyBandwidthMatrix = (UINT16 *)(TargetProximityDomainList +
 | |
|                                       *NumberTargetProximityDomain);
 | |
| 
 | |
|   // Display each element of the Initiator Proximity Domain list
 | |
|   for (Index = 0; Index < *NumberInitiatorProximityDomain; Index++) {
 | |
|     UnicodeSPrint (
 | |
|       Buffer,
 | |
|       sizeof (Buffer),
 | |
|       L"Initiator Proximity Dom [%d]",
 | |
|       Index
 | |
|       );
 | |
| 
 | |
|     PrintFieldName (4, Buffer);
 | |
|     Print (
 | |
|       L"0x%x\n",
 | |
|       InitiatorProximityDomainList[Index]
 | |
|       );
 | |
|   }
 | |
| 
 | |
|   // Display each element of the Target Proximity Domain list
 | |
|   for (Index = 0; Index < *NumberTargetProximityDomain; Index++) {
 | |
|     UnicodeSPrint (
 | |
|       Buffer,
 | |
|       sizeof (Buffer),
 | |
|       L"Target Proximity Dom [%d]",
 | |
|       Index
 | |
|       );
 | |
| 
 | |
|     PrintFieldName (4, Buffer);
 | |
|     Print (
 | |
|       L"0x%x\n",
 | |
|       TargetProximityDomainList[Index]
 | |
|       );
 | |
|   }
 | |
| 
 | |
|   // Create base name depending on Data Type in this Structure
 | |
|   if (*SllbiDataType >= ARRAY_SIZE (SllbiNames)) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (L"Error: Unkown Data Type. DataType = 0x%x.\n", *SllbiDataType);
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   StrCpyS (Buffer, sizeof (Buffer), SllbiNames[*SllbiDataType]);
 | |
| 
 | |
|   // Adjust base name depending on Memory Hierarchy in this Structure
 | |
|   switch (SllbiFlags->MemoryHierarchy) {
 | |
|     case 0:
 | |
|       UnicodeSPrint (
 | |
|         SecondBuffer,
 | |
|         sizeof (SecondBuffer),
 | |
|         Buffer,
 | |
|         L"",
 | |
|         L"%s"
 | |
|         );
 | |
|       break;
 | |
|     case 1:
 | |
|     case 2:
 | |
|     case 3:
 | |
|       UnicodeSPrint (
 | |
|         SecondBuffer,
 | |
|         sizeof (SecondBuffer),
 | |
|         Buffer,
 | |
|         L"Hit ",
 | |
|         L"%s"
 | |
|         );
 | |
|       break;
 | |
|     default:
 | |
|       IncrementErrorCount ();
 | |
|       Print (
 | |
|         L"Error: Invalid Memory Hierarchy. MemoryHierarchy = %d.\n",
 | |
|         SllbiFlags->MemoryHierarchy
 | |
|         );
 | |
|       return;
 | |
|   } // switch
 | |
| 
 | |
|   if (*NumberTargetProximityDomain <= MAX_MEMORY_DOMAIN_TARGET_PRINT_MATRIX) {
 | |
|     // Display the latency/bandwidth matrix as a matrix
 | |
|     UnicodeSPrint (
 | |
|       Buffer,
 | |
|       sizeof (Buffer),
 | |
|       SecondBuffer,
 | |
|       L""
 | |
|       );
 | |
|     PrintFieldName (4, Buffer);
 | |
| 
 | |
|     Print (L"\n      Target    : X-axis (Horizontal)");
 | |
|     Print (L"\n      Initiator : Y-axis (Vertical)");
 | |
|     Print (L"\n         |");
 | |
| 
 | |
|     for (IndexTarget = 0;
 | |
|          IndexTarget < *NumberTargetProximityDomain;
 | |
|          IndexTarget++)
 | |
|     {
 | |
|       Print (L"    %2d", IndexTarget);
 | |
|     }
 | |
| 
 | |
|     Print (L"\n      ---+");
 | |
|     for (IndexTarget = 0;
 | |
|          IndexTarget < *NumberTargetProximityDomain;
 | |
|          IndexTarget++)
 | |
|     {
 | |
|       Print (L"------");
 | |
|     }
 | |
| 
 | |
|     Print (L"\n");
 | |
| 
 | |
|     TargetStartOffset = 0;
 | |
|     for (IndexInitiator = 0;
 | |
|          IndexInitiator < *NumberInitiatorProximityDomain;
 | |
|          IndexInitiator++)
 | |
|     {
 | |
|       Print (L"      %2d |", IndexInitiator);
 | |
|       for (IndexTarget = 0;
 | |
|            IndexTarget < *NumberTargetProximityDomain;
 | |
|            IndexTarget++)
 | |
|       {
 | |
|         Print (
 | |
|           L" %5d",
 | |
|           LatencyBandwidthMatrix[TargetStartOffset + IndexTarget]
 | |
|           );
 | |
|       } // for Target
 | |
| 
 | |
|       Print (L"\n");
 | |
|       TargetStartOffset += (*NumberTargetProximityDomain);
 | |
|     } // for Initiator
 | |
| 
 | |
|     Print (L"\n");
 | |
|   } else {
 | |
|     // Display the latency/bandwidth matrix as a list
 | |
|     UnicodeSPrint (
 | |
|       Buffer,
 | |
|       sizeof (Buffer),
 | |
|       SecondBuffer,
 | |
|       L" [%d][%d]"
 | |
|       );
 | |
| 
 | |
|     TargetStartOffset = 0;
 | |
|     for (IndexInitiator = 0;
 | |
|          IndexInitiator < *NumberInitiatorProximityDomain;
 | |
|          IndexInitiator++)
 | |
|     {
 | |
|       for (IndexTarget = 0;
 | |
|            IndexTarget < *NumberTargetProximityDomain;
 | |
|            IndexTarget++)
 | |
|       {
 | |
|         UnicodeSPrint (
 | |
|           SecondBuffer,
 | |
|           sizeof (SecondBuffer),
 | |
|           Buffer,
 | |
|           IndexInitiator,
 | |
|           IndexTarget
 | |
|           );
 | |
| 
 | |
|         PrintFieldName (4, SecondBuffer);
 | |
|         Print (
 | |
|           L"%d\n",
 | |
|           LatencyBandwidthMatrix[TargetStartOffset + IndexTarget]
 | |
|           );
 | |
|       } // for Target
 | |
| 
 | |
|       TargetStartOffset += (*NumberTargetProximityDomain);
 | |
|     } // for Initiator
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|   This function parses the Memory Side Cache Information Structure (Type 2).
 | |
| 
 | |
|   @param [in] Ptr     Pointer to the start of the Memory Side Cache Information
 | |
|                       Structure data.
 | |
|   @param [in] Length  Length of the Memory Side Cache Information Structure.
 | |
| **/
 | |
| STATIC
 | |
| VOID
 | |
| DumpMsci (
 | |
|   IN UINT8   *Ptr,
 | |
|   IN UINT32  Length
 | |
|   )
 | |
| {
 | |
|   CONST UINT16  *SMBIOSHandlesList;
 | |
|   CHAR16        Buffer[OUTPUT_FIELD_COLUMN_WIDTH];
 | |
|   UINT32        Offset;
 | |
|   UINT16        Index;
 | |
| 
 | |
|   Offset = ParseAcpi (
 | |
|              TRUE,
 | |
|              2,
 | |
|              "Memory Side Cache Information Structure",
 | |
|              Ptr,
 | |
|              Length,
 | |
|              PARSER_PARAMS (MemSideCacheInfoParser)
 | |
|              );
 | |
| 
 | |
|   // Check if the values used to control the parsing logic have been
 | |
|   // successfully read.
 | |
|   if (NumberSMBIOSHandles == NULL) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"ERROR: Insufficient remaining table buffer length to read the " \
 | |
|       L"MSCI structure header. Length = %d.\n",
 | |
|       Length
 | |
|       );
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   if ((*NumberSMBIOSHandles * sizeof (UINT16)) > (Length - Offset)) {
 | |
|     IncrementErrorCount ();
 | |
|     Print (
 | |
|       L"ERROR: Invalid Number of SMBIOS Handles. SMBIOSHandlesCount = %d." \
 | |
|       L"RemainingBufferLength = %d.\n",
 | |
|       *NumberSMBIOSHandles,
 | |
|       Length - Offset
 | |
|       );
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   SMBIOSHandlesList = (UINT16 *)(Ptr + Offset);
 | |
| 
 | |
|   for (Index = 0; Index < *NumberSMBIOSHandles; Index++) {
 | |
|     UnicodeSPrint (
 | |
|       Buffer,
 | |
|       sizeof (Buffer),
 | |
|       L"SMBIOS Handles [%d]",
 | |
|       Index
 | |
|       );
 | |
| 
 | |
|     PrintFieldName (4, Buffer);
 | |
|     Print (
 | |
|       L"0x%x\n",
 | |
|       SMBIOSHandlesList[Index]
 | |
|       );
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|   This function parses the ACPI HMAT table.
 | |
|   When trace is enabled this function parses the HMAT table and
 | |
|   traces the ACPI table fields.
 | |
| 
 | |
|   This function parses the following HMAT structures:
 | |
|     - Memory Proximity Domain Attributes Structure (Type 0)
 | |
|     - System Locality Latency and Bandwidth Info Structure (Type 1)
 | |
|     - Memory Side Cache Info structure (Type 2)
 | |
| 
 | |
|   This function also performs validation of the ACPI table fields.
 | |
| 
 | |
|   @param [in] Trace              If TRUE, trace the ACPI fields.
 | |
|   @param [in] Ptr                Pointer to the start of the buffer.
 | |
|   @param [in] AcpiTableLength    Length of the ACPI table.
 | |
|   @param [in] AcpiTableRevision  Revision of the ACPI table.
 | |
| **/
 | |
| VOID
 | |
| EFIAPI
 | |
| ParseAcpiHmat (
 | |
|   IN BOOLEAN  Trace,
 | |
|   IN UINT8    *Ptr,
 | |
|   IN UINT32   AcpiTableLength,
 | |
|   IN UINT8    AcpiTableRevision
 | |
|   )
 | |
| {
 | |
|   UINT32  Offset;
 | |
|   UINT8   *HmatStructurePtr;
 | |
| 
 | |
|   if (!Trace) {
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   Offset = ParseAcpi (
 | |
|              Trace,
 | |
|              0,
 | |
|              "HMAT",
 | |
|              Ptr,
 | |
|              AcpiTableLength,
 | |
|              PARSER_PARAMS (HmatParser)
 | |
|              );
 | |
| 
 | |
|   HmatStructurePtr = Ptr + Offset;
 | |
| 
 | |
|   while (Offset < AcpiTableLength) {
 | |
|     // Parse HMAT Structure Header to obtain Type and Length.
 | |
|     ParseAcpi (
 | |
|       FALSE,
 | |
|       0,
 | |
|       NULL,
 | |
|       HmatStructurePtr,
 | |
|       AcpiTableLength - Offset,
 | |
|       PARSER_PARAMS (HmatStructureHeaderParser)
 | |
|       );
 | |
| 
 | |
|     // Check if the values used to control the parsing logic have been
 | |
|     // successfully read.
 | |
|     if ((HmatStructureType == NULL) ||
 | |
|         (HmatStructureLength == NULL))
 | |
|     {
 | |
|       IncrementErrorCount ();
 | |
|       Print (
 | |
|         L"ERROR: Insufficient remaining table buffer length to read the " \
 | |
|         L"HMAT structure header. Length = %d.\n",
 | |
|         AcpiTableLength - Offset
 | |
|         );
 | |
|       return;
 | |
|     }
 | |
| 
 | |
|     // Validate HMAT Structure length.
 | |
|     if ((*HmatStructureLength == 0) ||
 | |
|         ((Offset + (*HmatStructureLength)) > AcpiTableLength))
 | |
|     {
 | |
|       IncrementErrorCount ();
 | |
|       Print (
 | |
|         L"ERROR: Invalid HMAT Structure length. " \
 | |
|         L"Length = %d. Offset = %d. AcpiTableLength = %d.\n",
 | |
|         *HmatStructureLength,
 | |
|         Offset,
 | |
|         AcpiTableLength
 | |
|         );
 | |
|       return;
 | |
|     }
 | |
| 
 | |
|     switch (*HmatStructureType) {
 | |
|       case EFI_ACPI_6_4_HMAT_TYPE_MEMORY_PROXIMITY_DOMAIN_ATTRIBUTES:
 | |
|         DumpMpda (
 | |
|           HmatStructurePtr,
 | |
|           *HmatStructureLength
 | |
|           );
 | |
|         break;
 | |
|       case EFI_ACPI_6_4_HMAT_TYPE_SYSTEM_LOCALITY_LATENCY_AND_BANDWIDTH_INFO:
 | |
|         DumpSllbi (
 | |
|           HmatStructurePtr,
 | |
|           *HmatStructureLength
 | |
|           );
 | |
|         break;
 | |
|       case EFI_ACPI_6_4_HMAT_TYPE_MEMORY_SIDE_CACHE_INFO:
 | |
|         DumpMsci (
 | |
|           HmatStructurePtr,
 | |
|           *HmatStructureLength
 | |
|           );
 | |
|         break;
 | |
|       default:
 | |
|         IncrementErrorCount ();
 | |
|         Print (
 | |
|           L"ERROR: Unknown HMAT structure:"
 | |
|           L" Type = %d, Length = %d\n",
 | |
|           *HmatStructureType,
 | |
|           *HmatStructureLength
 | |
|           );
 | |
|         break;
 | |
|     } // switch
 | |
| 
 | |
|     HmatStructurePtr += *HmatStructureLength;
 | |
|     Offset           += *HmatStructureLength;
 | |
|   } // while
 | |
| }
 |