^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /******************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) * Module Name: tbfind - find table
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) * Copyright (C) 2000 - 2020, Intel Corp.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) *****************************************************************************/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <acpi/acpi.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include "accommon.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include "actables.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #define _COMPONENT ACPI_TABLES
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) ACPI_MODULE_NAME("tbfind")
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) /*******************************************************************************
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) * FUNCTION: acpi_tb_find_table
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) * PARAMETERS: signature - String with ACPI table signature
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) * oem_id - String with the table OEM ID
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * oem_table_id - String with the OEM Table ID
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) * table_index - Where the table index is returned
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) * RETURN: Status and table index
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) * DESCRIPTION: Find an ACPI table (in the RSDT/XSDT) that matches the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) * Signature, OEM ID and OEM Table ID. Returns an index that can
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) * be used to get the table header or entire table.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) ******************************************************************************/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) acpi_status
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) acpi_tb_find_table(char *signature,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) char *oem_id, char *oem_table_id, u32 *table_index)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) acpi_status status = AE_OK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) struct acpi_table_header header;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) u32 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) ACPI_FUNCTION_TRACE(tb_find_table);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) /* Validate the input table signature */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) if (!acpi_ut_valid_nameseg(signature)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) return_ACPI_STATUS(AE_BAD_SIGNATURE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) /* Don't allow the OEM strings to be too long */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) if ((strlen(oem_id) > ACPI_OEM_ID_SIZE) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) (strlen(oem_table_id) > ACPI_OEM_TABLE_ID_SIZE)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) return_ACPI_STATUS(AE_AML_STRING_LIMIT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) /* Normalize the input strings */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) memset(&header, 0, sizeof(struct acpi_table_header));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) ACPI_COPY_NAMESEG(header.signature, signature);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) strncpy(header.oem_id, oem_id, ACPI_OEM_ID_SIZE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) strncpy(header.oem_table_id, oem_table_id, ACPI_OEM_TABLE_ID_SIZE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) /* Search for the table */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) for (i = 0; i < acpi_gbl_root_table_list.current_table_count; ++i) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) if (memcmp(&(acpi_gbl_root_table_list.tables[i].signature),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) header.signature, ACPI_NAMESEG_SIZE)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) /* Not the requested table */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) /* Table with matching signature has been found */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) if (!acpi_gbl_root_table_list.tables[i].pointer) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) /* Table is not currently mapped, map it */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) status =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) acpi_tb_validate_table(&acpi_gbl_root_table_list.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) tables[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) if (ACPI_FAILURE(status)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) goto unlock_and_exit;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) if (!acpi_gbl_root_table_list.tables[i].pointer) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) /* Check for table match on all IDs */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) if (!memcmp
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) (acpi_gbl_root_table_list.tables[i].pointer->signature,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) header.signature, ACPI_NAMESEG_SIZE) && (!oem_id[0]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) !memcmp
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) (acpi_gbl_root_table_list.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) tables[i].
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) pointer->oem_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) header.oem_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) ACPI_OEM_ID_SIZE))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) && (!oem_table_id[0]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) || !memcmp(acpi_gbl_root_table_list.tables[i].pointer->
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) oem_table_id, header.oem_table_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) ACPI_OEM_TABLE_ID_SIZE))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) *table_index = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) ACPI_DEBUG_PRINT((ACPI_DB_TABLES,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) "Found table [%4.4s]\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) header.signature));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) goto unlock_and_exit;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) status = AE_NOT_FOUND;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) unlock_and_exit:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) (void)acpi_ut_release_mutex(ACPI_MTX_TABLES);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) return_ACPI_STATUS(status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) }