15f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** @file 25f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ACPI Table Protocol Implementation 35f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4f0071740ec3c7a536201cb02cec013442805760aStar Zeng Copyright (c) 2006 - 2015, Intel Corporation. All rights reserved.<BR> 5e5eed7d3641d71d7ea539e5379ea9c6a5cd97004hhtian This program and the accompanying materials 65f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten are licensed and made available under the terms and conditions of the BSD License 75f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten which accompanies this distribution. The full text of the license may be found at 85f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten http://opensource.org/licenses/bsd-license.php 95f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten// 165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten// Includes 175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten// 185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten#include "AcpiTable.h" 19da935a5c97f733f0662b83464abbbfa0acab76d1jchen// 20da935a5c97f733f0662b83464abbbfa0acab76d1jchen// The maximum number of tables that pre-allocated. 21da935a5c97f733f0662b83464abbbfa0acab76d1jchen// 22da935a5c97f733f0662b83464abbbfa0acab76d1jchenUINTN mEfiAcpiMaxNumTables = EFI_ACPI_MAX_NUM_TABLES; 235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function adds an ACPI table to the table list. It will detect FACS and 265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten allocate the correct type of memory and properly align the table. 275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Instance of the protocol. 295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Table Table to add. 305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Checksum Does the table require checksumming. 315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Version The version of the list to add the table to. 325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Handle Pointer for returning the handle. 335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_OUT_OF_RESOURCES Could not allocate a required resource. 365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_ABORTED The table is a duplicate of a table that is required 375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten to be unique. 385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenAddTableToList ( 425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance, 435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN VOID *Table, 445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN BOOLEAN Checksum, 455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_VERSION Version, 465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OUT UINTN *Handle 475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function finds and removes the table specified by the handle. 515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Instance of the protocol. 535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Version Bitmask of which versions to remove. 545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Handle Table to remove. 555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_ABORTED An error occurred. 585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_NOT_FOUND Handle not found in table list. 595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenRemoveTableFromList ( 635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance, 645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_VERSION Version, 655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN UINTN Handle 665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function calculates and updates an UINT8 checksum. 705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Buffer Pointer to buffer to checksum 725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Size Number of bytes to checksum 735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param ChecksumOffset Offset to place the checksum result in 745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenAcpiPlatformChecksum ( 795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN VOID *Buffer, 805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN UINTN Size, 815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN UINTN ChecksumOffset 825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum all versions of the common tables, RSDP, RSDT, XSDT. 865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Protocol instance private data. 885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenChecksumCommonTables ( 945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN OUT EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance 955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten// 985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten// Protocol function implementations. 995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten// 1005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 1025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function publishes the specified versions of the ACPI tables by 1035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten installing EFI configuration table entries for them. Any combination of 1045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten table versions can be published. 1055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Instance of the protocol. 1075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Version Version(s) to publish. 1085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 1105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_ABORTED The function could not complete successfully. 1115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 1135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 1145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFIAPI 1155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenPublishTables ( 1165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance, 1175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_VERSION Version 1185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 1195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 1205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_STATUS Status; 1215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT32 *CurrentRsdtEntry; 1225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten VOID *CurrentXsdtEntry; 1235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT64 Buffer64; 1245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Reorder tables as some operating systems don't seem to find the 1275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // FADT correctly if it is not in the first few entries 1285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add FADT as the first entry 1325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 1345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentRsdtEntry = (UINT32 *) ((UINT8 *) AcpiTableInstance->Rsdt1 + sizeof (EFI_ACPI_DESCRIPTION_HEADER)); 1355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten *CurrentRsdtEntry = (UINT32) (UINTN) AcpiTableInstance->Fadt1; 1365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 137f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 1385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentRsdtEntry = (UINT32 *) ((UINT8 *) AcpiTableInstance->Rsdt3 + sizeof (EFI_ACPI_DESCRIPTION_HEADER)); 1395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten *CurrentRsdtEntry = (UINT32) (UINTN) AcpiTableInstance->Fadt3; 1405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentXsdtEntry = (VOID *) ((UINT8 *) AcpiTableInstance->Xsdt + sizeof (EFI_ACPI_DESCRIPTION_HEADER)); 1415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add entry to XSDT, XSDT expects 64 bit pointers, but 1435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // the table pointers in XSDT are not aligned on 8 byte boundary. 1445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Buffer64 = (UINT64) (UINTN) AcpiTableInstance->Fadt3; 1465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem ( 1475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentXsdtEntry, 1485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &Buffer64, 1495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (UINT64) 1505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 1515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 1525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Do checksum again because Dsdt/Xsdt is updated. 1555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ChecksumCommonTables (AcpiTableInstance); 1575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add the RSD_PTR to the system table and store that we have installed the 1605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // tables. 1615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16201267e224b8f3247e3b360851f6781be6bb80129Star Zeng if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 1635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = gBS->InstallConfigurationTable (&gEfiAcpi10TableGuid, AcpiTableInstance->Rsdp1); 1645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (EFI_ERROR (Status)) { 1655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_ABORTED; 1665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 1675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 1685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16901267e224b8f3247e3b360851f6781be6bb80129Star Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 1705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = gBS->InstallConfigurationTable (&gEfiAcpiTableGuid, AcpiTableInstance->Rsdp3); 1715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (EFI_ERROR (Status)) { 1725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_ABORTED; 1735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 1745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 1755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 1775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 1785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 1815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Installs an ACPI table into the RSDT/XSDT. 1822fd3009fb25d79d53cc6ae6cdd872d78b41e4bc1eric_tian Note that the ACPI table should be checksumed before installing it. 1832fd3009fb25d79d53cc6ae6cdd872d78b41e4bc1eric_tian Otherwise it will assert. 1845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param This Protocol instance pointer. 1865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableBuffer A pointer to a buffer containing the ACPI table to be installed. 1875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableBufferSize Specifies the size, in bytes, of the AcpiTableBuffer buffer. 1885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param TableKey Reurns a key to refer to the ACPI table. 1895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The table was successfully inserted. 1915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_INVALID_PARAMETER Either AcpiTableBuffer is NULL, TableKey is NULL, or AcpiTableBufferSize 1925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten and the size field embedded in the ACPI table pointed to by AcpiTableBuffer 1935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten are not in sync. 1945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_OUT_OF_RESOURCES Insufficient resources exist to complete the request. 1955966402ed51c5b611bf437c812047dc9c432a47eStar Zeng @retval EFI_ACCESS_DENIED The table signature matches a table already 1965966402ed51c5b611bf437c812047dc9c432a47eStar Zeng present in the system and platform policy 1975966402ed51c5b611bf437c812047dc9c432a47eStar Zeng does not allow duplicate tables of this type. 1985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 2005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 2015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFIAPI 2025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenInstallAcpiTable ( 203db0f0d3c7945dbdc90d5f7ca1612565d7cebb4e3erictian IN EFI_ACPI_TABLE_PROTOCOL *This, 204db0f0d3c7945dbdc90d5f7ca1612565d7cebb4e3erictian IN VOID *AcpiTableBuffer, 205db0f0d3c7945dbdc90d5f7ca1612565d7cebb4e3erictian IN UINTN AcpiTableBufferSize, 206db0f0d3c7945dbdc90d5f7ca1612565d7cebb4e3erictian OUT UINTN *TableKey 2075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 2085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 2095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance; 2105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_STATUS Status; 2115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten VOID *AcpiTableBufferConst; 2125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check for invalid input parameters 2155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((AcpiTableBuffer == NULL) || (TableKey == NULL) 2175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten || (((EFI_ACPI_DESCRIPTION_HEADER *) AcpiTableBuffer)->Length != AcpiTableBufferSize)) { 2185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_INVALID_PARAMETER; 2195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 2205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Get the instance of the ACPI table protocol 2235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance = EFI_ACPI_TABLE_INSTANCE_FROM_THIS (This); 2255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Install the ACPI table 2285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableBufferConst = AllocateCopyPool (AcpiTableBufferSize,AcpiTableBuffer); 2305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten *TableKey = 0; 2315966402ed51c5b611bf437c812047dc9c432a47eStar Zeng Status = AddTableToList ( 2325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance, 2335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableBufferConst, 23471824dd8dbcf54019de02a8ec112266222afb98ejyao TRUE, 235f0071740ec3c7a536201cb02cec013442805760aStar Zeng EFI_ACPI_TABLE_VERSION_1_0B | ACPI_TABLE_VERSION_GTE_2_0, 2365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten TableKey 2375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 2385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (!EFI_ERROR (Status)) { 2395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = PublishTables ( 2405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance, 241f0071740ec3c7a536201cb02cec013442805760aStar Zeng EFI_ACPI_TABLE_VERSION_1_0B | ACPI_TABLE_VERSION_GTE_2_0 2425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 2435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 2445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten FreePool (AcpiTableBufferConst); 2455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2463dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao // 2473dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao // Add a new table successfully, notify registed callback 2483dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao // 2493dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao if (FeaturePcdGet (PcdInstallAcpiSdtProtocol)) { 2503dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao if (!EFI_ERROR (Status)) { 2513dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao SdtNotifyAcpiList ( 2523dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao AcpiTableInstance, 253f0071740ec3c7a536201cb02cec013442805760aStar Zeng EFI_ACPI_TABLE_VERSION_1_0B | ACPI_TABLE_VERSION_GTE_2_0, 2543dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao *TableKey 2553dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao ); 2563dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao } 2573dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao } 2583dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao 2595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return Status; 2605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 2615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 2645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Removes an ACPI table from the RSDT/XSDT. 2655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param This Protocol instance pointer. 2675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param TableKey Specifies the table to uninstall. The key was returned from InstallAcpiTable(). 2685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The table was successfully uninstalled. 2705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_NOT_FOUND TableKey does not refer to a valid key for a table entry. 2715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 2735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 2745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFIAPI 2755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenUninstallAcpiTable ( 276db0f0d3c7945dbdc90d5f7ca1612565d7cebb4e3erictian IN EFI_ACPI_TABLE_PROTOCOL *This, 277db0f0d3c7945dbdc90d5f7ca1612565d7cebb4e3erictian IN UINTN TableKey 2785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 2795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 2805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance; 2815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_STATUS Status; 2825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Get the instance of the ACPI table protocol 2855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance = EFI_ACPI_TABLE_INSTANCE_FROM_THIS (This); 2875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 2885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Uninstall the ACPI table 2905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 2915966402ed51c5b611bf437c812047dc9c432a47eStar Zeng Status = RemoveTableFromList ( 2925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance, 293f0071740ec3c7a536201cb02cec013442805760aStar Zeng EFI_ACPI_TABLE_VERSION_1_0B | ACPI_TABLE_VERSION_GTE_2_0, 2945966402ed51c5b611bf437c812047dc9c432a47eStar Zeng TableKey 2955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 2965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (!EFI_ERROR (Status)) { 2975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = PublishTables ( 2985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance, 299f0071740ec3c7a536201cb02cec013442805760aStar Zeng EFI_ACPI_TABLE_VERSION_1_0B | ACPI_TABLE_VERSION_GTE_2_0 3005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 3015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 3025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 3035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (EFI_ERROR (Status)) { 3045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_NOT_FOUND; 3055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } else { 3065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 3075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 3085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 3095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 310da935a5c97f733f0662b83464abbbfa0acab76d1jchen/** 311da935a5c97f733f0662b83464abbbfa0acab76d1jchen If the number of APCI tables exceeds the preallocated max table number, enlarge the table buffer. 312da935a5c97f733f0662b83464abbbfa0acab76d1jchen 313da935a5c97f733f0662b83464abbbfa0acab76d1jchen @param AcpiTableInstance ACPI table protocol instance data structure. 314da935a5c97f733f0662b83464abbbfa0acab76d1jchen 315da935a5c97f733f0662b83464abbbfa0acab76d1jchen @return EFI_SUCCESS reallocate the table beffer successfully. 316da935a5c97f733f0662b83464abbbfa0acab76d1jchen @return EFI_OUT_OF_RESOURCES Unable to allocate required resources. 317da935a5c97f733f0662b83464abbbfa0acab76d1jchen 318da935a5c97f733f0662b83464abbbfa0acab76d1jchen**/ 319da935a5c97f733f0662b83464abbbfa0acab76d1jchenEFI_STATUS 320da935a5c97f733f0662b83464abbbfa0acab76d1jchenReallocateAcpiTableBuffer ( 321da935a5c97f733f0662b83464abbbfa0acab76d1jchen IN EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance 322da935a5c97f733f0662b83464abbbfa0acab76d1jchen ) 323da935a5c97f733f0662b83464abbbfa0acab76d1jchen{ 324da935a5c97f733f0662b83464abbbfa0acab76d1jchen UINTN NewMaxTableNumber; 325da935a5c97f733f0662b83464abbbfa0acab76d1jchen UINTN TotalSize; 326da935a5c97f733f0662b83464abbbfa0acab76d1jchen UINT8 *Pointer; 327da935a5c97f733f0662b83464abbbfa0acab76d1jchen EFI_PHYSICAL_ADDRESS PageAddress; 328da935a5c97f733f0662b83464abbbfa0acab76d1jchen EFI_ACPI_TABLE_INSTANCE TempPrivateData; 329da935a5c97f733f0662b83464abbbfa0acab76d1jchen EFI_STATUS Status; 330da935a5c97f733f0662b83464abbbfa0acab76d1jchen UINT64 CurrentData; 331da935a5c97f733f0662b83464abbbfa0acab76d1jchen 332da935a5c97f733f0662b83464abbbfa0acab76d1jchen CopyMem (&TempPrivateData, AcpiTableInstance, sizeof (EFI_ACPI_TABLE_INSTANCE)); 333da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 334da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Enlarge the max table number from mEfiAcpiMaxNumTables to mEfiAcpiMaxNumTables + EFI_ACPI_MAX_NUM_TABLES 335da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 336da935a5c97f733f0662b83464abbbfa0acab76d1jchen NewMaxTableNumber = mEfiAcpiMaxNumTables + EFI_ACPI_MAX_NUM_TABLES; 337da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 33837abfb7ea1ce909c0cab34c98fd92841634dab9dlgao // Create RSDT, XSDT structures and allocate buffers. 339da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 34037abfb7ea1ce909c0cab34c98fd92841634dab9dlgao TotalSize = sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 1.0 RSDT 34137abfb7ea1ce909c0cab34c98fd92841634dab9dlgao NewMaxTableNumber * sizeof (UINT32) + 34237abfb7ea1ce909c0cab34c98fd92841634dab9dlgao sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 2.0/3.0 RSDT 34337abfb7ea1ce909c0cab34c98fd92841634dab9dlgao NewMaxTableNumber * sizeof (UINT32) + 34437abfb7ea1ce909c0cab34c98fd92841634dab9dlgao sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 2.0/3.0 XSDT 34537abfb7ea1ce909c0cab34c98fd92841634dab9dlgao NewMaxTableNumber * sizeof (UINT64); 346da935a5c97f733f0662b83464abbbfa0acab76d1jchen 347da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 348da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Allocate memory in the lower 32 bit of address range for 349da935a5c97f733f0662b83464abbbfa0acab76d1jchen // compatibility with ACPI 1.0 OS. 350da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 351da935a5c97f733f0662b83464abbbfa0acab76d1jchen // This is done because ACPI 1.0 pointers are 32 bit values. 352da935a5c97f733f0662b83464abbbfa0acab76d1jchen // ACPI 2.0 OS and all 64 bit OS must use the 64 bit ACPI table addresses. 353da935a5c97f733f0662b83464abbbfa0acab76d1jchen // There is no architectural reason these should be below 4GB, it is purely 354da935a5c97f733f0662b83464abbbfa0acab76d1jchen // for convenience of implementation that we force memory below 4GB. 355da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 356da935a5c97f733f0662b83464abbbfa0acab76d1jchen PageAddress = 0xFFFFFFFF; 357da935a5c97f733f0662b83464abbbfa0acab76d1jchen Status = gBS->AllocatePages ( 358da935a5c97f733f0662b83464abbbfa0acab76d1jchen AllocateMaxAddress, 359da935a5c97f733f0662b83464abbbfa0acab76d1jchen EfiACPIReclaimMemory, 360da935a5c97f733f0662b83464abbbfa0acab76d1jchen EFI_SIZE_TO_PAGES (TotalSize), 361da935a5c97f733f0662b83464abbbfa0acab76d1jchen &PageAddress 362da935a5c97f733f0662b83464abbbfa0acab76d1jchen ); 363da935a5c97f733f0662b83464abbbfa0acab76d1jchen 364da935a5c97f733f0662b83464abbbfa0acab76d1jchen if (EFI_ERROR (Status)) { 365da935a5c97f733f0662b83464abbbfa0acab76d1jchen return EFI_OUT_OF_RESOURCES; 366da935a5c97f733f0662b83464abbbfa0acab76d1jchen } 367da935a5c97f733f0662b83464abbbfa0acab76d1jchen 368da935a5c97f733f0662b83464abbbfa0acab76d1jchen Pointer = (UINT8 *) (UINTN) PageAddress; 369da935a5c97f733f0662b83464abbbfa0acab76d1jchen ZeroMem (Pointer, TotalSize); 370da935a5c97f733f0662b83464abbbfa0acab76d1jchen 371da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Rsdt1 = (EFI_ACPI_DESCRIPTION_HEADER *) Pointer; 372da935a5c97f733f0662b83464abbbfa0acab76d1jchen Pointer += (sizeof (EFI_ACPI_DESCRIPTION_HEADER) + NewMaxTableNumber * sizeof (UINT32)); 373da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Rsdt3 = (EFI_ACPI_DESCRIPTION_HEADER *) Pointer; 374da935a5c97f733f0662b83464abbbfa0acab76d1jchen Pointer += (sizeof (EFI_ACPI_DESCRIPTION_HEADER) + NewMaxTableNumber * sizeof (UINT32)); 375da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Xsdt = (EFI_ACPI_DESCRIPTION_HEADER *) Pointer; 3765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 377da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 37837abfb7ea1ce909c0cab34c98fd92841634dab9dlgao // Update RSDP to point to the new Rsdt and Xsdt address. 379da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 380da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Rsdp1->RsdtAddress = (UINT32) (UINTN) AcpiTableInstance->Rsdt1; 381da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Rsdp3->RsdtAddress = (UINT32) (UINTN) AcpiTableInstance->Rsdt3; 382da935a5c97f733f0662b83464abbbfa0acab76d1jchen CurrentData = (UINT64) (UINTN) AcpiTableInstance->Xsdt; 383da935a5c97f733f0662b83464abbbfa0acab76d1jchen CopyMem (&AcpiTableInstance->Rsdp3->XsdtAddress, &CurrentData, sizeof (UINT64)); 384da935a5c97f733f0662b83464abbbfa0acab76d1jchen 385da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 386da935a5c97f733f0662b83464abbbfa0acab76d1jchen // copy the original Rsdt1, Rsdt3 and Xsdt structure to new buffer 387da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 388da935a5c97f733f0662b83464abbbfa0acab76d1jchen CopyMem (AcpiTableInstance->Rsdt1, TempPrivateData.Rsdt1, (sizeof (EFI_ACPI_DESCRIPTION_HEADER) + mEfiAcpiMaxNumTables * sizeof (UINT32))); 389da935a5c97f733f0662b83464abbbfa0acab76d1jchen CopyMem (AcpiTableInstance->Rsdt3, TempPrivateData.Rsdt3, (sizeof (EFI_ACPI_DESCRIPTION_HEADER) + mEfiAcpiMaxNumTables * sizeof (UINT32))); 390da935a5c97f733f0662b83464abbbfa0acab76d1jchen CopyMem (AcpiTableInstance->Xsdt, TempPrivateData.Xsdt, (sizeof (EFI_ACPI_DESCRIPTION_HEADER) + mEfiAcpiMaxNumTables * sizeof (UINT64))); 391da935a5c97f733f0662b83464abbbfa0acab76d1jchen 392da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 393da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Calculate orignal ACPI table buffer size 394da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 39537abfb7ea1ce909c0cab34c98fd92841634dab9dlgao TotalSize = sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 1.0 RSDT 39637abfb7ea1ce909c0cab34c98fd92841634dab9dlgao mEfiAcpiMaxNumTables * sizeof (UINT32) + 39737abfb7ea1ce909c0cab34c98fd92841634dab9dlgao sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 2.0/3.0 RSDT 39837abfb7ea1ce909c0cab34c98fd92841634dab9dlgao mEfiAcpiMaxNumTables * sizeof (UINT32) + 39937abfb7ea1ce909c0cab34c98fd92841634dab9dlgao sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 2.0/3.0 XSDT 40037abfb7ea1ce909c0cab34c98fd92841634dab9dlgao mEfiAcpiMaxNumTables * sizeof (UINT64); 40137abfb7ea1ce909c0cab34c98fd92841634dab9dlgao gBS->FreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)TempPrivateData.Rsdt1, EFI_SIZE_TO_PAGES (TotalSize)); 402da935a5c97f733f0662b83464abbbfa0acab76d1jchen 403da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 404da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Update the Max ACPI table number 405da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 406da935a5c97f733f0662b83464abbbfa0acab76d1jchen mEfiAcpiMaxNumTables = NewMaxTableNumber; 407da935a5c97f733f0662b83464abbbfa0acab76d1jchen return EFI_SUCCESS; 408da935a5c97f733f0662b83464abbbfa0acab76d1jchen} 4095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 4105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function adds an ACPI table to the table list. It will detect FACS and 4115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten allocate the correct type of memory and properly align the table. 4125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Instance of the protocol. 4145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Table Table to add. 4155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Checksum Does the table require checksumming. 4165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Version The version of the list to add the table to. 4175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Handle Pointer for returning the handle. 4185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 4205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_OUT_OF_RESOURCES Could not allocate a required resource. 4215966402ed51c5b611bf437c812047dc9c432a47eStar Zeng @retval EFI_ACCESS_DENIED The table signature matches a table already 4225966402ed51c5b611bf437c812047dc9c432a47eStar Zeng present in the system and platform policy 4235966402ed51c5b611bf437c812047dc9c432a47eStar Zeng does not allow duplicate tables of this type. 4245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 4265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 4275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenAddTableToList ( 4285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance, 4295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN VOID *Table, 4305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN BOOLEAN Checksum, 4315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_VERSION Version, 4325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OUT UINTN *Handle 4335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 4345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 4355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_STATUS Status; 4365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_ACPI_TABLE_LIST *CurrentTableList; 4375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT32 CurrentTableSignature; 4385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT32 CurrentTableSize; 4395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT32 *CurrentRsdtEntry; 4405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten VOID *CurrentXsdtEntry; 4415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT64 Buffer64; 4425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten BOOLEAN AddToRsdt; 4435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check for invalid input parameters 4465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (AcpiTableInstance); 4485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (Table); 4495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (Handle); 4505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Init locals 4535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AddToRsdt = TRUE; 4555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Create a new list entry 4585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList = AllocatePool (sizeof (EFI_ACPI_TABLE_LIST)); 4605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (CurrentTableList); 4615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Determine table type and size 4645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableSignature = ((EFI_ACPI_COMMON_HEADER *) Table)->Signature; 4665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableSize = ((EFI_ACPI_COMMON_HEADER *) Table)->Length; 4675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Allocate a buffer for the table. All tables are allocated in the lower 32 bits of address space 4705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // for backwards compatibility with ACPI 1.0 OS. 4715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // This is done because ACPI 1.0 pointers are 32 bit values. 4735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // ACPI 2.0 OS and all 64 bit OS must use the 64 bit ACPI table addresses. 4745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // There is no architectural reason these should be below 4GB, it is purely 4755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // for convenience of implementation that we force memory below 4GB. 4765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->PageAddress = 0xFFFFFFFF; 4785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->NumberOfPages = EFI_SIZE_TO_PAGES (CurrentTableSize); 4795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 4805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Allocation memory type depends on the type of the table 4825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 48336d58153b16c21a097b9a11a085dd064f5112a05jyao if ((CurrentTableSignature == EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE) || 48436d58153b16c21a097b9a11a085dd064f5112a05jyao (CurrentTableSignature == EFI_ACPI_4_0_UEFI_ACPI_DATA_TABLE_SIGNATURE)) { 4855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Allocate memory for the FACS. This structure must be aligned 4875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // on a 64 byte boundary and must be ACPI NVS memory. 4885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Using AllocatePages should ensure that it is always aligned. 48936d58153b16c21a097b9a11a085dd064f5112a05jyao // Do not change signature for new ACPI version because they are same. 49036d58153b16c21a097b9a11a085dd064f5112a05jyao // 49136d58153b16c21a097b9a11a085dd064f5112a05jyao // UEFI table also need to be in ACPI NVS memory, because some data field 49236d58153b16c21a097b9a11a085dd064f5112a05jyao // could be updated by OS present agent. For example, BufferPtrAddress in 49336d58153b16c21a097b9a11a085dd064f5112a05jyao // SMM communication ACPI table. 4945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 4955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT ((EFI_PAGE_SIZE % 64) == 0); 4965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = gBS->AllocatePages ( 4975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AllocateMaxAddress, 4985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EfiACPIMemoryNVS, 4995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->NumberOfPages, 5005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &CurrentTableList->PageAddress 5015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 5025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } else { 5035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // All other tables are ACPI reclaim memory, no alignment requirements. 5055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = gBS->AllocatePages ( 5075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AllocateMaxAddress, 5085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EfiACPIReclaimMemory, 5095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->NumberOfPages, 5105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &CurrentTableList->PageAddress 5115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 5125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 5135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check return value from memory alloc. 5155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (EFI_ERROR (Status)) { 5175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePool (CurrentTableList); 5185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_OUT_OF_RESOURCES; 5195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 5205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update the table pointer with the allocated memory start 5225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Table = (EFI_ACPI_COMMON_HEADER *) (UINTN) CurrentTableList->PageAddress; 5245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Initialize the table contents 5275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Signature = EFI_ACPI_TABLE_LIST_SIGNATURE; 5295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (CurrentTableList->Table, Table, CurrentTableSize); 5305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Handle = AcpiTableInstance->CurrentHandle++; 5315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten *Handle = CurrentTableList->Handle; 5325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Version = Version; 5335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update internal pointers if this is a required table. If it is a required 5365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // table and a table of that type already exists, return an error. 5375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Calculate the checksum if the table is not FACS. 5395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten switch (CurrentTableSignature) { 5415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten case EFI_ACPI_1_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE: 5435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We don't add the FADT in the standard way because some 5455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // OS expect the FADT to be early in the table list. 5465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // So we always add it as the first element in the list. 5475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AddToRsdt = FALSE; 5495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check that the table has not been previously added. 5525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Fadt1 != NULL) || 554f0071740ec3c7a536201cb02cec013442805760aStar Zeng ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Fadt3 != NULL) 5555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) { 5565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePages (CurrentTableList->PageAddress, CurrentTableList->NumberOfPages); 5575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePool (CurrentTableList); 5585966402ed51c5b611bf437c812047dc9c432a47eStar Zeng return EFI_ACCESS_DENIED; 5595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 5605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add the table to the appropriate table version 5625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 5645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Save a pointer to the table 5665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1 = (EFI_ACPI_1_0_FIXED_ACPI_DESCRIPTION_TABLE *) CurrentTableList->Table; 5685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update pointers in FADT. If tables don't exist this will put NULL pointers there. 5715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->FirmwareCtrl = (UINT32) (UINTN) AcpiTableInstance->Facs1; 5735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->Dsdt = (UINT32) (UINTN) AcpiTableInstance->Dsdt1; 5745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // RSDP OEM information is updated to match the FADT OEM information 5775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem ( 5795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->Rsdp1->OemId, 5805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->Fadt1->Header.OemId, 5815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 6 5825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 5835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // RSDT OEM information is updated to match the FADT OEM information. 5865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 5875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem ( 5885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->Rsdt1->OemId, 5895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->Fadt1->Header.OemId, 5905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 6 5915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 5925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 5935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem ( 5945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->Rsdt1->OemTableId, 5955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->Fadt1->Header.OemTableId, 5965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (UINT64) 5975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 5985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1->OemRevision = AcpiTableInstance->Fadt1->Header.OemRevision; 5995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 6005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 601f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 6025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Save a pointer to the table 6045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3 = (EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE *) CurrentTableList->Table; 6065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 6075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update pointers in FADT. If tables don't exist this will put NULL pointers there. 609c93776c2d47b23b5e64691753efc7ab47ba257c0jyao // Note: If the FIRMWARE_CTRL is non-zero, then X_FIRMWARE_CTRL must be zero, and 610c93776c2d47b23b5e64691753efc7ab47ba257c0jyao // vice-versa. 6115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 61210342a643f4a6f89a86746c42f2ebcc1f02359f0jyao if ((UINT64)(UINTN)AcpiTableInstance->Facs3 < BASE_4GB) { 613c93776c2d47b23b5e64691753efc7ab47ba257c0jyao AcpiTableInstance->Fadt3->FirmwareCtrl = (UINT32) (UINTN) AcpiTableInstance->Facs3; 614f798e8bff773c833837c71fa806a7604fff7b503Laszlo Ersek ZeroMem (&AcpiTableInstance->Fadt3->XFirmwareCtrl, sizeof (UINT64)); 615c93776c2d47b23b5e64691753efc7ab47ba257c0jyao } else { 616c93776c2d47b23b5e64691753efc7ab47ba257c0jyao Buffer64 = (UINT64) (UINTN) AcpiTableInstance->Facs3; 617c93776c2d47b23b5e64691753efc7ab47ba257c0jyao CopyMem ( 618c93776c2d47b23b5e64691753efc7ab47ba257c0jyao &AcpiTableInstance->Fadt3->XFirmwareCtrl, 619c93776c2d47b23b5e64691753efc7ab47ba257c0jyao &Buffer64, 620c93776c2d47b23b5e64691753efc7ab47ba257c0jyao sizeof (UINT64) 621c93776c2d47b23b5e64691753efc7ab47ba257c0jyao ); 622f798e8bff773c833837c71fa806a7604fff7b503Laszlo Ersek AcpiTableInstance->Fadt3->FirmwareCtrl = 0; 623c93776c2d47b23b5e64691753efc7ab47ba257c0jyao } 624f0c855b26386c16ba0a70600d72cd09c090db0e0rsun AcpiTableInstance->Fadt3->Dsdt = (UINT32) (UINTN) AcpiTableInstance->Dsdt3; 625f0c855b26386c16ba0a70600d72cd09c090db0e0rsun Buffer64 = (UINT64) (UINTN) AcpiTableInstance->Dsdt3; 626f0c855b26386c16ba0a70600d72cd09c090db0e0rsun CopyMem ( 627f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Fadt3->XDsdt, 628f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &Buffer64, 629f0c855b26386c16ba0a70600d72cd09c090db0e0rsun sizeof (UINT64) 630f0c855b26386c16ba0a70600d72cd09c090db0e0rsun ); 6315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 632f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // 633f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // RSDP OEM information is updated to match the FADT OEM information 634f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // 635f0c855b26386c16ba0a70600d72cd09c090db0e0rsun CopyMem ( 636f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Rsdp3->OemId, 637f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Fadt3->Header.OemId, 638f0c855b26386c16ba0a70600d72cd09c090db0e0rsun 6 639f0c855b26386c16ba0a70600d72cd09c090db0e0rsun ); 640f0c855b26386c16ba0a70600d72cd09c090db0e0rsun 641f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // 642f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // RSDT OEM information is updated to match FADT OEM information. 643f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // 644f0c855b26386c16ba0a70600d72cd09c090db0e0rsun CopyMem ( 645f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Rsdt3->OemId, 646f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Fadt3->Header.OemId, 647f0c855b26386c16ba0a70600d72cd09c090db0e0rsun 6 648f0c855b26386c16ba0a70600d72cd09c090db0e0rsun ); 649f0c855b26386c16ba0a70600d72cd09c090db0e0rsun CopyMem ( 650f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Rsdt3->OemTableId, 651f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Fadt3->Header.OemTableId, 652f0c855b26386c16ba0a70600d72cd09c090db0e0rsun sizeof (UINT64) 653f0c855b26386c16ba0a70600d72cd09c090db0e0rsun ); 654f0c855b26386c16ba0a70600d72cd09c090db0e0rsun AcpiTableInstance->Rsdt3->OemRevision = AcpiTableInstance->Fadt3->Header.OemRevision; 655f0c855b26386c16ba0a70600d72cd09c090db0e0rsun 656f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // 657f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // XSDT OEM information is updated to match FADT OEM information. 658f0c855b26386c16ba0a70600d72cd09c090db0e0rsun // 659f0c855b26386c16ba0a70600d72cd09c090db0e0rsun CopyMem ( 660f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Xsdt->OemId, 661f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Fadt3->Header.OemId, 662f0c855b26386c16ba0a70600d72cd09c090db0e0rsun 6 663f0c855b26386c16ba0a70600d72cd09c090db0e0rsun ); 664f0c855b26386c16ba0a70600d72cd09c090db0e0rsun CopyMem ( 665f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Xsdt->OemTableId, 666f0c855b26386c16ba0a70600d72cd09c090db0e0rsun &AcpiTableInstance->Fadt3->Header.OemTableId, 667f0c855b26386c16ba0a70600d72cd09c090db0e0rsun sizeof (UINT64) 668f0c855b26386c16ba0a70600d72cd09c090db0e0rsun ); 669f0c855b26386c16ba0a70600d72cd09c090db0e0rsun AcpiTableInstance->Xsdt->OemRevision = AcpiTableInstance->Fadt3->Header.OemRevision; 6705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 6715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum the table 6735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Checksum) { 6755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 6765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Table, 6775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Table->Length, 6785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 6795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 6805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 6815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 6825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 6835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 6845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten case EFI_ACPI_1_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE: 6855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check that the table has not been previously added. 6875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Facs1 != NULL) || 689f0071740ec3c7a536201cb02cec013442805760aStar Zeng ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Facs3 != NULL) 6905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) { 6915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePages (CurrentTableList->PageAddress, CurrentTableList->NumberOfPages); 6925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePool (CurrentTableList); 6935966402ed51c5b611bf437c812047dc9c432a47eStar Zeng return EFI_ACCESS_DENIED; 6945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 6955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // FACS is referenced by FADT and is not part of RSDT 6975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 6985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AddToRsdt = FALSE; 6995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add the table to the appropriate table version 7025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 7045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Save a pointer to the table 7065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Facs1 = (EFI_ACPI_1_0_FIRMWARE_ACPI_CONTROL_STRUCTURE *) CurrentTableList->Table; 7085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // If FADT already exists, update table pointers. 7115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt1 != NULL) { 7135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->FirmwareCtrl = (UINT32) (UINTN) AcpiTableInstance->Facs1; 7145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum FADT table 7175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 7195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1, 7205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->Header.Length, 7215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 7225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 7235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 7245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 7255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 7265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 727f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 7285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Save a pointer to the table 7305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Facs3 = (EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE *) CurrentTableList->Table; 7325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // If FADT already exists, update table pointers. 7355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt3 != NULL) { 737c93776c2d47b23b5e64691753efc7ab47ba257c0jyao // 738c93776c2d47b23b5e64691753efc7ab47ba257c0jyao // Note: If the FIRMWARE_CTRL is non-zero, then X_FIRMWARE_CTRL must be zero, and 739c93776c2d47b23b5e64691753efc7ab47ba257c0jyao // vice-versa. 740c93776c2d47b23b5e64691753efc7ab47ba257c0jyao // 74110342a643f4a6f89a86746c42f2ebcc1f02359f0jyao if ((UINT64)(UINTN)AcpiTableInstance->Facs3 < BASE_4GB) { 742c93776c2d47b23b5e64691753efc7ab47ba257c0jyao AcpiTableInstance->Fadt3->FirmwareCtrl = (UINT32) (UINTN) AcpiTableInstance->Facs3; 743f798e8bff773c833837c71fa806a7604fff7b503Laszlo Ersek ZeroMem (&AcpiTableInstance->Fadt3->XFirmwareCtrl, sizeof (UINT64)); 744c93776c2d47b23b5e64691753efc7ab47ba257c0jyao } else { 745c93776c2d47b23b5e64691753efc7ab47ba257c0jyao Buffer64 = (UINT64) (UINTN) AcpiTableInstance->Facs3; 746c93776c2d47b23b5e64691753efc7ab47ba257c0jyao CopyMem ( 747c93776c2d47b23b5e64691753efc7ab47ba257c0jyao &AcpiTableInstance->Fadt3->XFirmwareCtrl, 748c93776c2d47b23b5e64691753efc7ab47ba257c0jyao &Buffer64, 749c93776c2d47b23b5e64691753efc7ab47ba257c0jyao sizeof (UINT64) 750c93776c2d47b23b5e64691753efc7ab47ba257c0jyao ); 751f798e8bff773c833837c71fa806a7604fff7b503Laszlo Ersek AcpiTableInstance->Fadt3->FirmwareCtrl = 0; 752c93776c2d47b23b5e64691753efc7ab47ba257c0jyao } 7535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum FADT table 7565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 7585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3, 7595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3->Header.Length, 7605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 7615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 7625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 7635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 7645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 7655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 7675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten case EFI_ACPI_1_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE: 7695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check that the table has not been previously added. 7715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0 && AcpiTableInstance->Dsdt1 != NULL) || 773f0071740ec3c7a536201cb02cec013442805760aStar Zeng ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0 && AcpiTableInstance->Dsdt3 != NULL) 7745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) { 7755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePages (CurrentTableList->PageAddress, CurrentTableList->NumberOfPages); 7765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePool (CurrentTableList); 7775966402ed51c5b611bf437c812047dc9c432a47eStar Zeng return EFI_ACCESS_DENIED; 7785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 7795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // DSDT is referenced by FADT and is not part of RSDT 7815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AddToRsdt = FALSE; 7835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add the table to the appropriate table version 7865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 7885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Save a pointer to the table 7905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Dsdt1 = (EFI_ACPI_DESCRIPTION_HEADER *) CurrentTableList->Table; 7925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // If FADT already exists, update table pointers. 7955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 7965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt1 != NULL) { 7975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->Dsdt = (UINT32) (UINTN) AcpiTableInstance->Dsdt1; 7985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 7995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum FADT table 8015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 8035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1, 8045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->Header.Length, 8055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 8065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 8075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 8085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 8095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 8105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 811f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 8125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Save a pointer to the table 8145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Dsdt3 = (EFI_ACPI_DESCRIPTION_HEADER *) CurrentTableList->Table; 8165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 8175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // If FADT already exists, update table pointers. 8195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt3 != NULL) { 8215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3->Dsdt = (UINT32) (UINTN) AcpiTableInstance->Dsdt3; 8225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Buffer64 = (UINT64) (UINTN) AcpiTableInstance->Dsdt3; 8235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem ( 8245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->Fadt3->XDsdt, 8255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &Buffer64, 8265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (UINT64) 8275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 8285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 8295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum FADT table 8315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 8335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3, 8345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3->Header.Length, 8355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 8365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 8375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 8385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 8395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 8405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum the table 8425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Checksum) { 8445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 8455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Table, 8465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Table->Length, 8475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 8485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 8495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 8505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 8515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 8525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 8535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten default: 8545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum the table 8565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Checksum) { 8585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 8595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Table, 8605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableList->Table->Length, 8615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 8625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 8635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 8645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 8655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 8665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 8675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add the table to the current list of tables 8695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten InsertTailList (&AcpiTableInstance->TableList, &CurrentTableList->Link); 8715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 8725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add the table to RSDT and/or XSDT table entry lists. 8745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Add to ACPI 1.0b table tree 8775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 8795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AddToRsdt) { 8805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 881da935a5c97f733f0662b83464abbbfa0acab76d1jchen // If the table number exceed the gEfiAcpiMaxNumTables, enlarge the table buffer 8825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 883da935a5c97f733f0662b83464abbbfa0acab76d1jchen if (AcpiTableInstance->NumberOfTableEntries1 >= mEfiAcpiMaxNumTables) { 884da935a5c97f733f0662b83464abbbfa0acab76d1jchen Status = ReallocateAcpiTableBuffer (AcpiTableInstance); 885da935a5c97f733f0662b83464abbbfa0acab76d1jchen ASSERT_EFI_ERROR (Status); 886da935a5c97f733f0662b83464abbbfa0acab76d1jchen } 8875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentRsdtEntry = (UINT32 *) 8885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ( 889da935a5c97f733f0662b83464abbbfa0acab76d1jchen (UINT8 *) AcpiTableInstance->Rsdt1 + 8905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (EFI_ACPI_DESCRIPTION_HEADER) + 891da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->NumberOfTableEntries1 * 8925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (UINT32) 8935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 8945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 8955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 896da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Add entry to the RSDT unless its the FACS or DSDT 8975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 8985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten *CurrentRsdtEntry = (UINT32) (UINTN) CurrentTableList->Table; 8995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 9005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 9015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update RSDT length 9025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 903da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Rsdt1->Length = AcpiTableInstance->Rsdt1->Length + sizeof (UINT32); 9045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 905da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->NumberOfTableEntries1++; 906da935a5c97f733f0662b83464abbbfa0acab76d1jchen } 907da935a5c97f733f0662b83464abbbfa0acab76d1jchen } 908da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 909da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Add to ACPI 2.0/3.0 table tree 910da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 911f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 912da935a5c97f733f0662b83464abbbfa0acab76d1jchen if (AddToRsdt) { 913da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 914da935a5c97f733f0662b83464abbbfa0acab76d1jchen // If the table number exceed the gEfiAcpiMaxNumTables, enlarge the table buffer 915da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 916da935a5c97f733f0662b83464abbbfa0acab76d1jchen if (AcpiTableInstance->NumberOfTableEntries3 >= mEfiAcpiMaxNumTables) { 917da935a5c97f733f0662b83464abbbfa0acab76d1jchen Status = ReallocateAcpiTableBuffer (AcpiTableInstance); 918da935a5c97f733f0662b83464abbbfa0acab76d1jchen ASSERT_EFI_ERROR (Status); 919da935a5c97f733f0662b83464abbbfa0acab76d1jchen } 920da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 921da935a5c97f733f0662b83464abbbfa0acab76d1jchen // At this time, it is assumed that RSDT and XSDT maintain parallel lists of tables. 922da935a5c97f733f0662b83464abbbfa0acab76d1jchen // If it becomes necessary to maintain separate table lists, changes will be required. 923da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 924da935a5c97f733f0662b83464abbbfa0acab76d1jchen CurrentRsdtEntry = (UINT32 *) 925da935a5c97f733f0662b83464abbbfa0acab76d1jchen ( 926da935a5c97f733f0662b83464abbbfa0acab76d1jchen (UINT8 *) AcpiTableInstance->Rsdt3 + 927da935a5c97f733f0662b83464abbbfa0acab76d1jchen sizeof (EFI_ACPI_DESCRIPTION_HEADER) + 928da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->NumberOfTableEntries3 * 929da935a5c97f733f0662b83464abbbfa0acab76d1jchen sizeof (UINT32) 930da935a5c97f733f0662b83464abbbfa0acab76d1jchen ); 931da935a5c97f733f0662b83464abbbfa0acab76d1jchen 932da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 933da935a5c97f733f0662b83464abbbfa0acab76d1jchen // This pointer must not be directly dereferenced as the XSDT entries may not 934da935a5c97f733f0662b83464abbbfa0acab76d1jchen // be 64 bit aligned resulting in a possible fault. Use CopyMem to update. 935da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 936da935a5c97f733f0662b83464abbbfa0acab76d1jchen CurrentXsdtEntry = (VOID *) 937da935a5c97f733f0662b83464abbbfa0acab76d1jchen ( 938da935a5c97f733f0662b83464abbbfa0acab76d1jchen (UINT8 *) AcpiTableInstance->Xsdt + 939da935a5c97f733f0662b83464abbbfa0acab76d1jchen sizeof (EFI_ACPI_DESCRIPTION_HEADER) + 940da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->NumberOfTableEntries3 * 941da935a5c97f733f0662b83464abbbfa0acab76d1jchen sizeof (UINT64) 942da935a5c97f733f0662b83464abbbfa0acab76d1jchen ); 943da935a5c97f733f0662b83464abbbfa0acab76d1jchen 944da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 945da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Add entry to the RSDT 946da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 947da935a5c97f733f0662b83464abbbfa0acab76d1jchen *CurrentRsdtEntry = (UINT32) (UINTN) CurrentTableList->Table; 948da935a5c97f733f0662b83464abbbfa0acab76d1jchen 949da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 950da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Update RSDT length 951da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 952da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Rsdt3->Length = AcpiTableInstance->Rsdt3->Length + sizeof (UINT32); 953da935a5c97f733f0662b83464abbbfa0acab76d1jchen 954da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 955da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Add entry to XSDT, XSDT expects 64 bit pointers, but 956da935a5c97f733f0662b83464abbbfa0acab76d1jchen // the table pointers in XSDT are not aligned on 8 byte boundary. 957da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 958da935a5c97f733f0662b83464abbbfa0acab76d1jchen Buffer64 = (UINT64) (UINTN) CurrentTableList->Table; 959da935a5c97f733f0662b83464abbbfa0acab76d1jchen CopyMem ( 960da935a5c97f733f0662b83464abbbfa0acab76d1jchen CurrentXsdtEntry, 961da935a5c97f733f0662b83464abbbfa0acab76d1jchen &Buffer64, 962da935a5c97f733f0662b83464abbbfa0acab76d1jchen sizeof (UINT64) 963da935a5c97f733f0662b83464abbbfa0acab76d1jchen ); 964da935a5c97f733f0662b83464abbbfa0acab76d1jchen 965da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 966da935a5c97f733f0662b83464abbbfa0acab76d1jchen // Update length 967da935a5c97f733f0662b83464abbbfa0acab76d1jchen // 968da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->Xsdt->Length = AcpiTableInstance->Xsdt->Length + sizeof (UINT64); 969da935a5c97f733f0662b83464abbbfa0acab76d1jchen 970da935a5c97f733f0662b83464abbbfa0acab76d1jchen AcpiTableInstance->NumberOfTableEntries3++; 9715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 9725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 9735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 9745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ChecksumCommonTables (AcpiTableInstance); 9755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 9765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 9775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 9785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 9795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 9805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function finds the table specified by the handle and returns a pointer to it. 9815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten If the handle is not found, EFI_NOT_FOUND is returned and the contents of Table are 9825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten undefined. 9835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 9845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Handle Table to find. 9855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param TableList Table list to search 9865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Table Pointer to table found. 9875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 9885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 9895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_NOT_FOUND No table found matching the handle specified. 9905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 9915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 9925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 9935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenFindTableByHandle ( 9945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN UINTN Handle, 9955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN LIST_ENTRY *TableList, 9965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OUT EFI_ACPI_TABLE_LIST **Table 9975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 9985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 9995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten LIST_ENTRY *CurrentLink; 10005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_ACPI_TABLE_LIST *CurrentTable; 10015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check for invalid input parameters 10045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (Table); 10065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Find the table 10095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentLink = TableList->ForwardLink; 10115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten while (CurrentLink != TableList) { 10135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTable = EFI_ACPI_TABLE_LIST_FROM_LINK (CurrentLink); 10145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (CurrentTable->Handle == Handle) { 10155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Found handle, so return this table. 10175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten *Table = CurrentTable; 10195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 10205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 10215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentLink = CurrentLink->ForwardLink; 10235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 10245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Table not found 10265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_NOT_FOUND; 10285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 10295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 10325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function removes a basic table from the RSDT and/or XSDT. 10335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten For Acpi 1.0 tables, pass in the Rsdt. 10345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten For Acpi 2.0 tables, pass in both Rsdt and Xsdt. 10355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Table Pointer to table found. 10375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param NumberOfTableEntries Current number of table entries in the RSDT/XSDT 10385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Rsdt Pointer to the RSDT to remove from 10395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Xsdt Pointer to the Xsdt to remove from 10405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 10425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_INVALID_PARAMETER The table was not found in both Rsdt and Xsdt. 10435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 10455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 10465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenRemoveTableFromRsdt ( 10475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN OUT EFI_ACPI_TABLE_LIST * Table, 10485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN OUT UINTN *NumberOfTableEntries, 10495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN OUT EFI_ACPI_DESCRIPTION_HEADER * Rsdt, 10505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN OUT EFI_ACPI_DESCRIPTION_HEADER * Xsdt OPTIONAL 10515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 10525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 10535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT32 *CurrentRsdtEntry; 10545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten VOID *CurrentXsdtEntry; 10555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT64 CurrentTablePointer64; 10565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINTN Index; 10575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check for invalid input parameters 10605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (Table); 10625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (NumberOfTableEntries); 10635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (Rsdt); 10645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Find the table entry in the RSDT and XSDT 10675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten for (Index = 0; Index < *NumberOfTableEntries; Index++) { 10695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // At this time, it is assumed that RSDT and XSDT maintain parallel lists of tables. 10715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // If it becomes necessary to maintain separate table lists, changes will be required. 10725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentRsdtEntry = (UINT32 *) ((UINT8 *) Rsdt + sizeof (EFI_ACPI_DESCRIPTION_HEADER) + Index * sizeof (UINT32)); 10745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Xsdt != NULL) { 10755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // This pointer must not be directly dereferenced as the XSDT entries may not 10775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // be 64 bit aligned resulting in a possible fault. Use CopyMem to update. 10785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentXsdtEntry = (VOID *) ((UINT8 *) Xsdt + sizeof (EFI_ACPI_DESCRIPTION_HEADER) + Index * sizeof (UINT64)); 10805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 10815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Read the entry value out of the XSDT 10835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (&CurrentTablePointer64, CurrentXsdtEntry, sizeof (UINT64)); 10855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } else { 10865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Initialize to NULL 10885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentXsdtEntry = 0; 10905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTablePointer64 = 0; 10915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 10925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check if we have found the corresponding entry in both RSDT and XSDT 10945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (*CurrentRsdtEntry == (UINT32) (UINTN) Table->Table && 10965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ((Xsdt == NULL) || CurrentTablePointer64 == (UINT64) (UINTN) Table->Table) 10975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) { 10985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 10995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Found entry, so copy all following entries and shrink table 11005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We actually copy all + 1 to copy the initialized value of memory over 11015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // the last entry. 11025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (CurrentRsdtEntry, CurrentRsdtEntry + 1, (*NumberOfTableEntries - Index) * sizeof (UINT32)); 11045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Rsdt->Length = Rsdt->Length - sizeof (UINT32); 11055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Xsdt != NULL) { 11065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (CurrentXsdtEntry, ((UINT64 *) CurrentXsdtEntry) + 1, (*NumberOfTableEntries - Index) * sizeof (UINT64)); 11075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Xsdt->Length = Xsdt->Length - sizeof (UINT64); 11085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 11095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 11105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } else if (Index + 1 == *NumberOfTableEntries) { 11115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // At the last entry, and table not found 11135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_INVALID_PARAMETER; 11155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 11165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 11175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum the tables 11195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 11215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Rsdt, 11225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Rsdt->Length, 11235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 11245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 11255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 11265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Xsdt != NULL) { 11285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 11295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Xsdt, 11305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Xsdt->Length, 11315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 11325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 11335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 11345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 11355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Decrement the number of tables 11375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten (*NumberOfTableEntries)--; 11395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 11415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 11425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 11455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function removes a table and frees any associated memory. 11465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Instance of the protocol. 11485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Version Version(s) to delete. 11495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Table Pointer to table found. 11505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 11525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 11545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 11555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenDeleteTable ( 11565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance, 11575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_VERSION Version, 11585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN OUT EFI_ACPI_TABLE_LIST *Table 11595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 11605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 11615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT32 CurrentTableSignature; 11625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten BOOLEAN RemoveFromRsdt; 11635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check for invalid input parameters 11665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (AcpiTableInstance); 11685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (Table); 11695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Init locals 11725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten RemoveFromRsdt = TRUE; 11746198c34621b38815bbfb116f8fcf656a54470920vanjeff // 11756198c34621b38815bbfb116f8fcf656a54470920vanjeff // Check for Table->Table 11766198c34621b38815bbfb116f8fcf656a54470920vanjeff // 11776198c34621b38815bbfb116f8fcf656a54470920vanjeff ASSERT (Table->Table != NULL); 11785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentTableSignature = ((EFI_ACPI_COMMON_HEADER *) Table->Table)->Signature; 11795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 11805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Basic tasks to accomplish delete are: 11825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Determine removal requirements (in RSDT/XSDT or not) 11835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove entry from RSDT/XSDT 11845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove any table references to the table 11855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // If no one is using the table 11865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Free the table (removing pointers from private data and tables) 11875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove from list 11885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Free list structure 11895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Determine if this table is in the RSDT or XSDT 11925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 11935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((CurrentTableSignature == EFI_ACPI_1_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE) || 11945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten (CurrentTableSignature == EFI_ACPI_2_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE) || 11955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten (CurrentTableSignature == EFI_ACPI_3_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE) 11965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) { 11975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten RemoveFromRsdt = FALSE; 11985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 11995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We don't remove the FADT in the standard way because some 12015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // OS expect the FADT to be early in the table list. 12025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // So we always put it as the first element in the list. 12035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (CurrentTableSignature == EFI_ACPI_1_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE) { 12055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten RemoveFromRsdt = FALSE; 12065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove the table from RSDT and XSDT 12105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Table->Table != NULL) { 12125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // This is a basic table, remove it from any lists and the Rsdt and/or Xsdt 12145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Version & EFI_ACPI_TABLE_VERSION_NONE & Table->Version) { 12165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove this version from the table 12185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Table->Version = Table->Version &~EFI_ACPI_TABLE_VERSION_NONE; 12205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Version & EFI_ACPI_TABLE_VERSION_1_0B & Table->Version) { 12235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove this version from the table 12255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Table->Version = Table->Version &~EFI_ACPI_TABLE_VERSION_1_0B; 12275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove from Rsdt. We don't care about the return value because it is 12305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // acceptable for the table to not exist in Rsdt. 12315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We didn't add some tables so we don't remove them. 12325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (RemoveFromRsdt) { 12345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten RemoveTableFromRsdt ( 12355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Table, 12365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->NumberOfTableEntries1, 12375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1, 12385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten NULL 12395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 12405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1243f0071740ec3c7a536201cb02cec013442805760aStar Zeng if (Version & ACPI_TABLE_VERSION_GTE_2_0 & Table->Version) { 12445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove this version from the table 12465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 1247f0071740ec3c7a536201cb02cec013442805760aStar Zeng Table->Version = Table->Version &~(Version & ACPI_TABLE_VERSION_GTE_2_0); 12485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove from Rsdt and Xsdt. We don't care about the return value 12515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // because it is acceptable for the table to not exist in Rsdt/Xsdt. 12525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We didn't add some tables so we don't remove them. 12535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (RemoveFromRsdt) { 12555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten RemoveTableFromRsdt ( 12565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Table, 12575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->NumberOfTableEntries3, 12585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3, 12595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt 12605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 12615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Free the table, clean up any dependent tables and our private data pointers. 12655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten switch (Table->Table->Signature) { 12675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten case EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE: 12695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 12705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1 = NULL; 12715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1273f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 12745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3 = NULL; 12755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 12775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten case EFI_ACPI_3_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE: 12795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 12805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Facs1 = NULL; 12815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update FADT table pointers 12845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt1 != NULL) { 12865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->FirmwareCtrl = 0; 12875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 12885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum table 12905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 12915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 12925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1, 12935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->Header.Length, 12945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 12955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 12965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 12975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 12995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1300f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 13015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Facs3 = NULL; 13025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update FADT table pointers 13055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt3 != NULL) { 13075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3->FirmwareCtrl = 0; 13085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ZeroMem (&AcpiTableInstance->Fadt3->XFirmwareCtrl, sizeof (UINT64)); 13095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum table 13125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 13145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3, 13155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3->Header.Length, 13165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 13175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 13185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 13195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 13225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten case EFI_ACPI_3_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE: 13245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if ((Version & EFI_ACPI_TABLE_VERSION_1_0B) != 0) { 13255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Dsdt1 = NULL; 13265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update FADT table pointers 13295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt1 != NULL) { 13315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->Dsdt = 0; 13325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum table 13355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 13375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1, 13385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt1->Header.Length, 13395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 13405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 13415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 13425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1346f0071740ec3c7a536201cb02cec013442805760aStar Zeng if ((Version & ACPI_TABLE_VERSION_GTE_2_0) != 0) { 13475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Dsdt3 = NULL; 13485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Update FADT table pointers 13515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (AcpiTableInstance->Fadt3 != NULL) { 13535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3->Dsdt = 0; 13545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ZeroMem (&AcpiTableInstance->Fadt3->XDsdt, sizeof (UINT64)); 13555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Checksum table 13585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 13605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3, 13615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Fadt3->Header.Length, 13625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 13635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 13645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 13655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 13685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten default: 13705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Do nothing 13725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten break; 13745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // If no version is using this table anymore, remove and free list entry. 13785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (Table->Version == 0) { 13805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Free the Table 13825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePages (Table->PageAddress, Table->NumberOfPages); 13845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten RemoveEntryList (&(Table->Link)); 13855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten gBS->FreePool (Table); 13865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 13875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Done 13895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 13905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 13915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 13925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 13955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function finds and removes the table specified by the handle. 13965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 13975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Instance of the protocol. 13985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Version Bitmask of which versions to remove. 13995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Handle Table to remove. 14005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 14025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_ABORTED An error occurred. 14035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_NOT_FOUND Handle not found in table list. 14045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 14065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 14075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenRemoveTableFromList ( 14085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance, 14095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN EFI_ACPI_TABLE_VERSION Version, 14105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN UINTN Handle 14115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 14125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 14135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_ACPI_TABLE_LIST *Table; 14145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_STATUS Status; 14155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1416b474ed4944e20485d730bcb91bdf5ae6f8ca70f6jljusten Table = (EFI_ACPI_TABLE_LIST*) NULL; 1417b474ed4944e20485d730bcb91bdf5ae6f8ca70f6jljusten 14185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check for invalid input parameters 14205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (AcpiTableInstance); 14225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Find the table 14255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = FindTableByHandle ( 14275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Handle, 14285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &AcpiTableInstance->TableList, 14295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &Table 14305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 14315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (EFI_ERROR (Status)) { 14325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_NOT_FOUND; 14335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 14345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Remove the table 14365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = DeleteTable (AcpiTableInstance, Version, Table); 14385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (EFI_ERROR (Status)) { 14395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_ABORTED; 14405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 14415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Completed successfully 14435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 14455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 14465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 14495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten This function calculates and updates an UINT8 checksum. 14505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Buffer Pointer to buffer to checksum 14525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param Size Number of bytes to checksum 14535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param ChecksumOffset Offset to place the checksum result in 14545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 14565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 14585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 14595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenAcpiPlatformChecksum ( 14605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN VOID *Buffer, 14615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN UINTN Size, 14625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN UINTN ChecksumOffset 14635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 14645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 14655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT8 Sum; 14665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT8 *Ptr; 14675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Sum = 0; 14695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Initialize pointer 14715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Ptr = Buffer; 14735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // set checksum to 0 first 14765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Ptr[ChecksumOffset] = 0; 14785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // add all content of buffer 14815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten while ((Size--) != 0) { 14835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Sum = (UINT8) (Sum + (*Ptr++)); 14845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 14855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // set checksum 14875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 14885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Ptr = Buffer; 14895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Ptr[ChecksumOffset] = (UINT8) (0xff - Sum + 1); 14905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 14925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 14935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 14965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum all versions of the common tables, RSDP, RSDT, XSDT. 14975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 14985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Protocol instance private data. 14995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS The function completed successfully. 15015f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15025f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 15035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 15045f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenChecksumCommonTables ( 15055f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten IN OUT EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance 15065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 15075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 15085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // RSDP ACPI 1.0 checksum for 1.0 table. This is only the first 20 bytes of the structure 15105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 15125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp1, 15135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER), 15145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER, 15155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 15165f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 15175f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15195f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // RSDP ACPI 1.0 checksum for 2.0/3.0 table. This is only the first 20 bytes of the structure 15205f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15215f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 15225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp3, 15235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER), 15245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER, 15255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 15265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 15275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // RSDP ACPI 2.0/3.0 checksum, this is the entire table 15305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 15325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp3, 15335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten sizeof (EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER), 15345f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER, 15355f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ExtendedChecksum) 15365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 15375f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15385f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15395f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // RSDT checksums 15405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 15425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1, 15435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1->Length, 15445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 15455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 15465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 15475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 15495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3, 15505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3->Length, 15515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 15525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 15535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 15545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // XSDT checksum 15575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiPlatformChecksum ( 15595f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt, 15605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt->Length, 15615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten OFFSET_OF (EFI_ACPI_DESCRIPTION_HEADER, 15625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Checksum) 15635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 15645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 15665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 15675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten/** 15705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Constructor for the ACPI table protocol. Initializes instance 15715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten data. 15725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @param AcpiTableInstance Instance to construct 15745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_SUCCESS Instance initialized. 15765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten @return EFI_OUT_OF_RESOURCES Unable to allocate required resources. 15775f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten**/ 15795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenEFI_STATUS 15805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljustenAcpiTableAcpiTableConstructor ( 15815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_ACPI_TABLE_INSTANCE *AcpiTableInstance 15825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ) 15835f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten{ 15845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_STATUS Status; 15855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT64 CurrentData; 15865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINTN TotalSize; 158737abfb7ea1ce909c0cab34c98fd92841634dab9dlgao UINTN RsdpTableSize; 15885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten UINT8 *Pointer; 15895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_PHYSICAL_ADDRESS PageAddress; 15905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Check for invalid input parameters 15935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 15945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ASSERT (AcpiTableInstance); 15955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten InitializeListHead (&AcpiTableInstance->TableList); 15975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->CurrentHandle = 1; 15985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 15995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->AcpiTableProtocol.InstallAcpiTable = InstallAcpiTable; 16005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->AcpiTableProtocol.UninstallAcpiTable = UninstallAcpiTable; 16013dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao 16023dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao if (FeaturePcdGet (PcdInstallAcpiSdtProtocol)) { 16033dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao SdtAcpiTableAcpiSdtConstructor (AcpiTableInstance); 16043dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao } 16053dc8585e0a9fd4b2cb383f3ceb4961c7a88a8e71jyao 16065f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 160737abfb7ea1ce909c0cab34c98fd92841634dab9dlgao // Create RSDP table 160837abfb7ea1ce909c0cab34c98fd92841634dab9dlgao // 160937abfb7ea1ce909c0cab34c98fd92841634dab9dlgao RsdpTableSize = sizeof (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER) + 161037abfb7ea1ce909c0cab34c98fd92841634dab9dlgao sizeof (EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER); 161137abfb7ea1ce909c0cab34c98fd92841634dab9dlgao 161237abfb7ea1ce909c0cab34c98fd92841634dab9dlgao PageAddress = 0xFFFFFFFF; 161337abfb7ea1ce909c0cab34c98fd92841634dab9dlgao Status = gBS->AllocatePages ( 161437abfb7ea1ce909c0cab34c98fd92841634dab9dlgao AllocateMaxAddress, 161537abfb7ea1ce909c0cab34c98fd92841634dab9dlgao EfiACPIReclaimMemory, 161637abfb7ea1ce909c0cab34c98fd92841634dab9dlgao EFI_SIZE_TO_PAGES (RsdpTableSize), 161737abfb7ea1ce909c0cab34c98fd92841634dab9dlgao &PageAddress 161837abfb7ea1ce909c0cab34c98fd92841634dab9dlgao ); 161937abfb7ea1ce909c0cab34c98fd92841634dab9dlgao 162037abfb7ea1ce909c0cab34c98fd92841634dab9dlgao if (EFI_ERROR (Status)) { 162137abfb7ea1ce909c0cab34c98fd92841634dab9dlgao return EFI_OUT_OF_RESOURCES; 162237abfb7ea1ce909c0cab34c98fd92841634dab9dlgao } 162337abfb7ea1ce909c0cab34c98fd92841634dab9dlgao 162437abfb7ea1ce909c0cab34c98fd92841634dab9dlgao Pointer = (UINT8 *) (UINTN) PageAddress; 162537abfb7ea1ce909c0cab34c98fd92841634dab9dlgao ZeroMem (Pointer, RsdpTableSize); 162637abfb7ea1ce909c0cab34c98fd92841634dab9dlgao 162737abfb7ea1ce909c0cab34c98fd92841634dab9dlgao AcpiTableInstance->Rsdp1 = (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER *) Pointer; 162837abfb7ea1ce909c0cab34c98fd92841634dab9dlgao Pointer += sizeof (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER); 162937abfb7ea1ce909c0cab34c98fd92841634dab9dlgao AcpiTableInstance->Rsdp3 = (EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER *) Pointer; 163037abfb7ea1ce909c0cab34c98fd92841634dab9dlgao 163137abfb7ea1ce909c0cab34c98fd92841634dab9dlgao // 163237abfb7ea1ce909c0cab34c98fd92841634dab9dlgao // Create RSDT, XSDT structures 16335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 163437abfb7ea1ce909c0cab34c98fd92841634dab9dlgao TotalSize = sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 1.0 RSDT 163537abfb7ea1ce909c0cab34c98fd92841634dab9dlgao mEfiAcpiMaxNumTables * sizeof (UINT32) + 163637abfb7ea1ce909c0cab34c98fd92841634dab9dlgao sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 2.0/3.0 RSDT 163737abfb7ea1ce909c0cab34c98fd92841634dab9dlgao mEfiAcpiMaxNumTables * sizeof (UINT32) + 163837abfb7ea1ce909c0cab34c98fd92841634dab9dlgao sizeof (EFI_ACPI_DESCRIPTION_HEADER) + // for ACPI 2.0/3.0 XSDT 163937abfb7ea1ce909c0cab34c98fd92841634dab9dlgao mEfiAcpiMaxNumTables * sizeof (UINT64); 16405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Allocate memory in the lower 32 bit of address range for 16435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // compatibility with ACPI 1.0 OS. 16445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // This is done because ACPI 1.0 pointers are 32 bit values. 16465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // ACPI 2.0 OS and all 64 bit OS must use the 64 bit ACPI table addresses. 16475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // There is no architectural reason these should be below 4GB, it is purely 16485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // for convenience of implementation that we force memory below 4GB. 16495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten PageAddress = 0xFFFFFFFF; 16515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Status = gBS->AllocatePages ( 16525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AllocateMaxAddress, 16535f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EfiACPIReclaimMemory, 16545f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten EFI_SIZE_TO_PAGES (TotalSize), 16555f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten &PageAddress 16565f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ); 16575f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16585f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten if (EFI_ERROR (Status)) { 165937abfb7ea1ce909c0cab34c98fd92841634dab9dlgao gBS->FreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)AcpiTableInstance->Rsdp1, EFI_SIZE_TO_PAGES (RsdpTableSize)); 16605f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_OUT_OF_RESOURCES; 16615f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten } 16625f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16635f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Pointer = (UINT8 *) (UINTN) PageAddress; 16645f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ZeroMem (Pointer, TotalSize); 16655f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16665f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1 = (EFI_ACPI_DESCRIPTION_HEADER *) Pointer; 16675f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Pointer += (sizeof (EFI_ACPI_DESCRIPTION_HEADER) + EFI_ACPI_MAX_NUM_TABLES * sizeof (UINT32)); 16685f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3 = (EFI_ACPI_DESCRIPTION_HEADER *) Pointer; 16695f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten Pointer += (sizeof (EFI_ACPI_DESCRIPTION_HEADER) + EFI_ACPI_MAX_NUM_TABLES * sizeof (UINT32)); 16705f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt = (EFI_ACPI_DESCRIPTION_HEADER *) Pointer; 16715f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16725f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16735f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Initialize RSDP 16745f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16755f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentData = EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER_SIGNATURE; 16765f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (&AcpiTableInstance->Rsdp1->Signature, &CurrentData, sizeof (UINT64)); 1677e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CopyMem (AcpiTableInstance->Rsdp1->OemId, PcdGetPtr (PcdAcpiDefaultOemId), sizeof (AcpiTableInstance->Rsdp1->OemId)); 16785f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp1->Reserved = EFI_ACPI_RESERVED_BYTE; 16795f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp1->RsdtAddress = (UINT32) (UINTN) AcpiTableInstance->Rsdt1; 16805f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16815f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentData = EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER_SIGNATURE; 16825f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (&AcpiTableInstance->Rsdp3->Signature, &CurrentData, sizeof (UINT64)); 1683e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CopyMem (AcpiTableInstance->Rsdp3->OemId, PcdGetPtr (PcdAcpiDefaultOemId), sizeof (AcpiTableInstance->Rsdp3->OemId)); 16845f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp3->Revision = EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER_REVISION; 16855f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp3->RsdtAddress = (UINT32) (UINTN) AcpiTableInstance->Rsdt3; 16865f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdp3->Length = sizeof (EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER); 16875f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CurrentData = (UINT64) (UINTN) AcpiTableInstance->Xsdt; 16885f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (&AcpiTableInstance->Rsdp3->XsdtAddress, &CurrentData, sizeof (UINT64)); 16895f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten SetMem (AcpiTableInstance->Rsdp3->Reserved, 3, EFI_ACPI_RESERVED_BYTE); 16905f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 16915f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16925f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Initialize Rsdt 16935f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16945f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Note that we "reserve" one entry for the FADT so it can always be 16955f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // at the beginning of the list of tables. Some OS don't seem 16965f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // to find it correctly if it is too far down the list. 16975f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 16985f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1->Signature = EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_TABLE_SIGNATURE; 16995f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1->Length = sizeof (EFI_ACPI_DESCRIPTION_HEADER); 17005f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1->Revision = EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_TABLE_REVISION; 1701e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CopyMem (AcpiTableInstance->Rsdt1->OemId, PcdGetPtr (PcdAcpiDefaultOemId), sizeof (AcpiTableInstance->Rsdt1->OemId)); 1702e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CurrentData = PcdGet64 (PcdAcpiDefaultOemTableId); 17035f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (&AcpiTableInstance->Rsdt1->OemTableId, &CurrentData, sizeof (UINT64)); 1704e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Rsdt1->OemRevision = PcdGet32 (PcdAcpiDefaultOemRevision); 1705e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Rsdt1->CreatorId = PcdGet32 (PcdAcpiDefaultCreatorId); 1706e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Rsdt1->CreatorRevision = PcdGet32 (PcdAcpiDefaultCreatorRevision); 17075f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17085f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We always reserve first one for FADT 17095f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17105f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->NumberOfTableEntries1 = 1; 17115f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt1->Length = AcpiTableInstance->Rsdt1->Length + sizeof(UINT32); 17125f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 17135f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3->Signature = EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_TABLE_SIGNATURE; 17145f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3->Length = sizeof (EFI_ACPI_DESCRIPTION_HEADER); 17155f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3->Revision = EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_TABLE_REVISION; 1716e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CopyMem (AcpiTableInstance->Rsdt3->OemId, PcdGetPtr (PcdAcpiDefaultOemId), sizeof (AcpiTableInstance->Rsdt3->OemId)); 1717e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CurrentData = PcdGet64 (PcdAcpiDefaultOemTableId); 17185f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (&AcpiTableInstance->Rsdt3->OemTableId, &CurrentData, sizeof (UINT64)); 1719e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Rsdt3->OemRevision = PcdGet32 (PcdAcpiDefaultOemRevision); 1720e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Rsdt3->CreatorId = PcdGet32 (PcdAcpiDefaultCreatorId); 1721e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Rsdt3->CreatorRevision = PcdGet32 (PcdAcpiDefaultCreatorRevision); 17225f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17235f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We always reserve first one for FADT 17245f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17255f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->NumberOfTableEntries3 = 1; 17265f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Rsdt3->Length = AcpiTableInstance->Rsdt3->Length + sizeof(UINT32); 17275f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 17285f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17295f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Initialize Xsdt 17305f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17315f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt->Signature = EFI_ACPI_3_0_EXTENDED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE; 17325f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt->Length = sizeof (EFI_ACPI_DESCRIPTION_HEADER); 17335f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt->Revision = EFI_ACPI_3_0_EXTENDED_SYSTEM_DESCRIPTION_TABLE_REVISION; 1734e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CopyMem (AcpiTableInstance->Xsdt->OemId, PcdGetPtr (PcdAcpiDefaultOemId), sizeof (AcpiTableInstance->Xsdt->OemId)); 1735e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng CurrentData = PcdGet64 (PcdAcpiDefaultOemTableId); 17365f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten CopyMem (&AcpiTableInstance->Xsdt->OemTableId, &CurrentData, sizeof (UINT64)); 1737e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Xsdt->OemRevision = PcdGet32 (PcdAcpiDefaultOemRevision); 1738e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Xsdt->CreatorId = PcdGet32 (PcdAcpiDefaultCreatorId); 1739e84f07b5fc919fcb13292aa6c33925c81f642e32Star Zeng AcpiTableInstance->Xsdt->CreatorRevision = PcdGet32 (PcdAcpiDefaultCreatorRevision); 17405f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17415f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // We always reserve first one for FADT 17425f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17435f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten AcpiTableInstance->Xsdt->Length = AcpiTableInstance->Xsdt->Length + sizeof(UINT64); 17445f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 17455f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten ChecksumCommonTables (AcpiTableInstance); 17465f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 17475f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17485f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // Completed successfully 17495f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten // 17505f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten return EFI_SUCCESS; 17515f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten} 17525f55c7004666d6bf8cb421b09781cbd1ceb9eddcjljusten 1753