/** @file WSMT table parser Copyright (c) 2024, Arm Limited. All rights reserved. Copyright (C) 2024 Advanced Micro Devices, Inc. All rights reserved. SPDX-License-Identifier: BSD-2-Clause-Patent @par Reference(s): - Windows SMM Security Mitigation Table spec, version 1.0 **/ #include #include #include "AcpiParser.h" STATIC ACPI_DESCRIPTION_HEADER_INFO AcpiHdrInfo; /** This function validates the WSMT Protection flag. @param [in] Ptr Pointer to the start of the buffer. @param [in] Length Length of the field. @param [in] Context Pointer to context specific information e.g. this could be a pointer to the ACPI table header. **/ STATIC VOID EFIAPI ValidateWsmtProtectionFlag ( IN UINT8 *Ptr, IN UINT32 Length, IN VOID *Context ) { UINT32 ProtectionFlag; ProtectionFlag = *(UINT32 *)Ptr; if ((ProtectionFlag & EFI_WSMT_PROTECTION_FLAGS_COMM_BUFFER_NESTED_PTR_PROTECTION) \ == EFI_WSMT_PROTECTION_FLAGS_COMM_BUFFER_NESTED_PTR_PROTECTION) { if ((ProtectionFlag & EFI_WSMT_PROTECTION_FLAGS_FIXED_COMM_BUFFERS) \ != EFI_WSMT_PROTECTION_FLAGS_FIXED_COMM_BUFFERS) { IncrementErrorCount (); Print (L"ERROR: COMM_BUFFER_NESTED_PTR_PROTECTION is set but FIXED_COMM_BUFFERS is not set.\n"); } } } /** This function validates the reserved bits in the WSMT Protection flag. @param [in] Ptr Pointer to the start of the buffer. @param [in] Length Length of the field. @param [in] Context Pointer to context specific information e.g. this could be a pointer to the ACPI table header. **/ STATIC VOID EFIAPI ValidateReserved ( IN UINT8 *Ptr, IN UINT32 Length, IN VOID *Context ) { UINT32 ProtectionFlag; ProtectionFlag = *(UINT32 *)Ptr; if ((ProtectionFlag & 0xFFFFFFF8) != 0) { IncrementErrorCount (); Print (L"ERROR: Reserved bits are not zero.\n"); } } /** An ACPI_PARSER array describing the WSMT Protection flag . **/ STATIC CONST ACPI_PARSER WsmtProtectionFlagParser[] = { { L"FIXED_COMM_BUFFERS ", 1, 0, L"0x%x", NULL, NULL, NULL, NULL }, { L"COMM_BUFFER_NESTED_PTR_PROTECTION ", 1, 1, L"0x%x", NULL, NULL, NULL, NULL }, { L"SYSTEM_RESOURCE_PROTECTION ", 1, 2, L"0x%x", NULL, NULL, NULL, NULL }, { L"Reserved ", 29, 3, L"0x%x", NULL, NULL, ValidateReserved, NULL }, }; /** This function prints WSMT Protection flag. If no format string is specified the Format must be NULL. @param [in] Format Optional format string for tracing the data. @param [in] Ptr Pointer to the start of the buffer. **/ VOID EFIAPI DumpWsmtProtectionFlag ( IN CONST CHAR16 *Format OPTIONAL, IN UINT8 *Ptr, IN UINT32 Length ) { if (Format != NULL) { Print (Format, *(UINT32 *)Ptr); return; } Print (L"0x%X\n", *(UINT32 *)Ptr); ParseAcpiBitFields ( TRUE, 2, NULL, Ptr, 4, PARSER_PARAMS (WsmtProtectionFlagParser) ); } /** An ACPI_PARSER array describing the ACPI WSMT Table. **/ STATIC CONST ACPI_PARSER WsmtParser[] = { PARSE_ACPI_HEADER (&AcpiHdrInfo), { L"Protection Flag", 4,36, NULL, DumpWsmtProtectionFlag, NULL, ValidateWsmtProtectionFlag, NULL } }; /** This function parses the ACPI WSMT table. @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 ParseAcpiWsmt ( IN BOOLEAN Trace, IN UINT8 *Ptr, IN UINT32 AcpiTableLength, IN UINT8 AcpiTableRevision ) { ParseAcpi ( Trace, 0, "WSMT", Ptr, AcpiTableLength, PARSER_PARAMS (WsmtParser) ); }