1*385cc6b4SJerry Jelinek /****************************************************************************** 2*385cc6b4SJerry Jelinek * 3*385cc6b4SJerry Jelinek * Module Name: apdump - Dump routines for ACPI tables (acpidump) 4*385cc6b4SJerry Jelinek * 5*385cc6b4SJerry Jelinek *****************************************************************************/ 6*385cc6b4SJerry Jelinek 7*385cc6b4SJerry Jelinek /* 8*385cc6b4SJerry Jelinek * Copyright (C) 2000 - 2016, Intel Corp. 9*385cc6b4SJerry Jelinek * All rights reserved. 10*385cc6b4SJerry Jelinek * 11*385cc6b4SJerry Jelinek * Redistribution and use in source and binary forms, with or without 12*385cc6b4SJerry Jelinek * modification, are permitted provided that the following conditions 13*385cc6b4SJerry Jelinek * are met: 14*385cc6b4SJerry Jelinek * 1. Redistributions of source code must retain the above copyright 15*385cc6b4SJerry Jelinek * notice, this list of conditions, and the following disclaimer, 16*385cc6b4SJerry Jelinek * without modification. 17*385cc6b4SJerry Jelinek * 2. Redistributions in binary form must reproduce at minimum a disclaimer 18*385cc6b4SJerry Jelinek * substantially similar to the "NO WARRANTY" disclaimer below 19*385cc6b4SJerry Jelinek * ("Disclaimer") and any redistribution must be conditioned upon 20*385cc6b4SJerry Jelinek * including a substantially similar Disclaimer requirement for further 21*385cc6b4SJerry Jelinek * binary redistribution. 22*385cc6b4SJerry Jelinek * 3. Neither the names of the above-listed copyright holders nor the names 23*385cc6b4SJerry Jelinek * of any contributors may be used to endorse or promote products derived 24*385cc6b4SJerry Jelinek * from this software without specific prior written permission. 25*385cc6b4SJerry Jelinek * 26*385cc6b4SJerry Jelinek * Alternatively, this software may be distributed under the terms of the 27*385cc6b4SJerry Jelinek * GNU General Public License ("GPL") version 2 as published by the Free 28*385cc6b4SJerry Jelinek * Software Foundation. 29*385cc6b4SJerry Jelinek * 30*385cc6b4SJerry Jelinek * NO WARRANTY 31*385cc6b4SJerry Jelinek * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 32*385cc6b4SJerry Jelinek * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 33*385cc6b4SJerry Jelinek * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR 34*385cc6b4SJerry Jelinek * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 35*385cc6b4SJerry Jelinek * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 36*385cc6b4SJerry Jelinek * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 37*385cc6b4SJerry Jelinek * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 38*385cc6b4SJerry Jelinek * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 39*385cc6b4SJerry Jelinek * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING 40*385cc6b4SJerry Jelinek * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 41*385cc6b4SJerry Jelinek * POSSIBILITY OF SUCH DAMAGES. 42*385cc6b4SJerry Jelinek */ 43*385cc6b4SJerry Jelinek 44*385cc6b4SJerry Jelinek #include "acpidump.h" 45*385cc6b4SJerry Jelinek 46*385cc6b4SJerry Jelinek 47*385cc6b4SJerry Jelinek /* Local prototypes */ 48*385cc6b4SJerry Jelinek 49*385cc6b4SJerry Jelinek static int 50*385cc6b4SJerry Jelinek ApDumpTableBuffer ( 51*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table, 52*385cc6b4SJerry Jelinek UINT32 Instance, 53*385cc6b4SJerry Jelinek ACPI_PHYSICAL_ADDRESS Address); 54*385cc6b4SJerry Jelinek 55*385cc6b4SJerry Jelinek 56*385cc6b4SJerry Jelinek /****************************************************************************** 57*385cc6b4SJerry Jelinek * 58*385cc6b4SJerry Jelinek * FUNCTION: ApIsValidHeader 59*385cc6b4SJerry Jelinek * 60*385cc6b4SJerry Jelinek * PARAMETERS: Table - Pointer to table to be validated 61*385cc6b4SJerry Jelinek * 62*385cc6b4SJerry Jelinek * RETURN: TRUE if the header appears to be valid. FALSE otherwise 63*385cc6b4SJerry Jelinek * 64*385cc6b4SJerry Jelinek * DESCRIPTION: Check for a valid ACPI table header 65*385cc6b4SJerry Jelinek * 66*385cc6b4SJerry Jelinek ******************************************************************************/ 67*385cc6b4SJerry Jelinek 68*385cc6b4SJerry Jelinek BOOLEAN 69*385cc6b4SJerry Jelinek ApIsValidHeader ( 70*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table) 71*385cc6b4SJerry Jelinek { 72*385cc6b4SJerry Jelinek 73*385cc6b4SJerry Jelinek if (!ACPI_VALIDATE_RSDP_SIG (Table->Signature)) 74*385cc6b4SJerry Jelinek { 75*385cc6b4SJerry Jelinek /* Make sure signature is all ASCII and a valid ACPI name */ 76*385cc6b4SJerry Jelinek 77*385cc6b4SJerry Jelinek if (!AcpiUtValidNameseg (Table->Signature)) 78*385cc6b4SJerry Jelinek { 79*385cc6b4SJerry Jelinek AcpiLogError ("Table signature (0x%8.8X) is invalid\n", 80*385cc6b4SJerry Jelinek *(UINT32 *) Table->Signature); 81*385cc6b4SJerry Jelinek return (FALSE); 82*385cc6b4SJerry Jelinek } 83*385cc6b4SJerry Jelinek 84*385cc6b4SJerry Jelinek /* Check for minimum table length */ 85*385cc6b4SJerry Jelinek 86*385cc6b4SJerry Jelinek if (Table->Length < sizeof (ACPI_TABLE_HEADER)) 87*385cc6b4SJerry Jelinek { 88*385cc6b4SJerry Jelinek AcpiLogError ("Table length (0x%8.8X) is invalid\n", 89*385cc6b4SJerry Jelinek Table->Length); 90*385cc6b4SJerry Jelinek return (FALSE); 91*385cc6b4SJerry Jelinek } 92*385cc6b4SJerry Jelinek } 93*385cc6b4SJerry Jelinek 94*385cc6b4SJerry Jelinek return (TRUE); 95*385cc6b4SJerry Jelinek } 96*385cc6b4SJerry Jelinek 97*385cc6b4SJerry Jelinek 98*385cc6b4SJerry Jelinek /****************************************************************************** 99*385cc6b4SJerry Jelinek * 100*385cc6b4SJerry Jelinek * FUNCTION: ApIsValidChecksum 101*385cc6b4SJerry Jelinek * 102*385cc6b4SJerry Jelinek * PARAMETERS: Table - Pointer to table to be validated 103*385cc6b4SJerry Jelinek * 104*385cc6b4SJerry Jelinek * RETURN: TRUE if the checksum appears to be valid. FALSE otherwise. 105*385cc6b4SJerry Jelinek * 106*385cc6b4SJerry Jelinek * DESCRIPTION: Check for a valid ACPI table checksum. 107*385cc6b4SJerry Jelinek * 108*385cc6b4SJerry Jelinek ******************************************************************************/ 109*385cc6b4SJerry Jelinek 110*385cc6b4SJerry Jelinek BOOLEAN 111*385cc6b4SJerry Jelinek ApIsValidChecksum ( 112*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table) 113*385cc6b4SJerry Jelinek { 114*385cc6b4SJerry Jelinek ACPI_STATUS Status; 115*385cc6b4SJerry Jelinek ACPI_TABLE_RSDP *Rsdp; 116*385cc6b4SJerry Jelinek 117*385cc6b4SJerry Jelinek 118*385cc6b4SJerry Jelinek if (ACPI_VALIDATE_RSDP_SIG (Table->Signature)) 119*385cc6b4SJerry Jelinek { 120*385cc6b4SJerry Jelinek /* 121*385cc6b4SJerry Jelinek * Checksum for RSDP. 122*385cc6b4SJerry Jelinek * Note: Other checksums are computed during the table dump. 123*385cc6b4SJerry Jelinek */ 124*385cc6b4SJerry Jelinek Rsdp = ACPI_CAST_PTR (ACPI_TABLE_RSDP, Table); 125*385cc6b4SJerry Jelinek Status = AcpiTbValidateRsdp (Rsdp); 126*385cc6b4SJerry Jelinek } 127*385cc6b4SJerry Jelinek else 128*385cc6b4SJerry Jelinek { 129*385cc6b4SJerry Jelinek Status = AcpiTbVerifyChecksum (Table, Table->Length); 130*385cc6b4SJerry Jelinek } 131*385cc6b4SJerry Jelinek 132*385cc6b4SJerry Jelinek if (ACPI_FAILURE (Status)) 133*385cc6b4SJerry Jelinek { 134*385cc6b4SJerry Jelinek AcpiLogError ("%4.4s: Warning: wrong checksum in table\n", 135*385cc6b4SJerry Jelinek Table->Signature); 136*385cc6b4SJerry Jelinek } 137*385cc6b4SJerry Jelinek 138*385cc6b4SJerry Jelinek return (AE_OK); 139*385cc6b4SJerry Jelinek } 140*385cc6b4SJerry Jelinek 141*385cc6b4SJerry Jelinek 142*385cc6b4SJerry Jelinek /****************************************************************************** 143*385cc6b4SJerry Jelinek * 144*385cc6b4SJerry Jelinek * FUNCTION: ApGetTableLength 145*385cc6b4SJerry Jelinek * 146*385cc6b4SJerry Jelinek * PARAMETERS: Table - Pointer to the table 147*385cc6b4SJerry Jelinek * 148*385cc6b4SJerry Jelinek * RETURN: Table length 149*385cc6b4SJerry Jelinek * 150*385cc6b4SJerry Jelinek * DESCRIPTION: Obtain table length according to table signature. 151*385cc6b4SJerry Jelinek * 152*385cc6b4SJerry Jelinek ******************************************************************************/ 153*385cc6b4SJerry Jelinek 154*385cc6b4SJerry Jelinek UINT32 155*385cc6b4SJerry Jelinek ApGetTableLength ( 156*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table) 157*385cc6b4SJerry Jelinek { 158*385cc6b4SJerry Jelinek ACPI_TABLE_RSDP *Rsdp; 159*385cc6b4SJerry Jelinek 160*385cc6b4SJerry Jelinek 161*385cc6b4SJerry Jelinek /* Check if table is valid */ 162*385cc6b4SJerry Jelinek 163*385cc6b4SJerry Jelinek if (!ApIsValidHeader (Table)) 164*385cc6b4SJerry Jelinek { 165*385cc6b4SJerry Jelinek return (0); 166*385cc6b4SJerry Jelinek } 167*385cc6b4SJerry Jelinek 168*385cc6b4SJerry Jelinek if (ACPI_VALIDATE_RSDP_SIG (Table->Signature)) 169*385cc6b4SJerry Jelinek { 170*385cc6b4SJerry Jelinek Rsdp = ACPI_CAST_PTR (ACPI_TABLE_RSDP, Table); 171*385cc6b4SJerry Jelinek return (AcpiTbGetRsdpLength (Rsdp)); 172*385cc6b4SJerry Jelinek } 173*385cc6b4SJerry Jelinek 174*385cc6b4SJerry Jelinek /* Normal ACPI table */ 175*385cc6b4SJerry Jelinek 176*385cc6b4SJerry Jelinek return (Table->Length); 177*385cc6b4SJerry Jelinek } 178*385cc6b4SJerry Jelinek 179*385cc6b4SJerry Jelinek 180*385cc6b4SJerry Jelinek /****************************************************************************** 181*385cc6b4SJerry Jelinek * 182*385cc6b4SJerry Jelinek * FUNCTION: ApDumpTableBuffer 183*385cc6b4SJerry Jelinek * 184*385cc6b4SJerry Jelinek * PARAMETERS: Table - ACPI table to be dumped 185*385cc6b4SJerry Jelinek * Instance - ACPI table instance no. to be dumped 186*385cc6b4SJerry Jelinek * Address - Physical address of the table 187*385cc6b4SJerry Jelinek * 188*385cc6b4SJerry Jelinek * RETURN: None 189*385cc6b4SJerry Jelinek * 190*385cc6b4SJerry Jelinek * DESCRIPTION: Dump an ACPI table in standard ASCII hex format, with a 191*385cc6b4SJerry Jelinek * header that is compatible with the AcpiXtract utility. 192*385cc6b4SJerry Jelinek * 193*385cc6b4SJerry Jelinek ******************************************************************************/ 194*385cc6b4SJerry Jelinek 195*385cc6b4SJerry Jelinek static int 196*385cc6b4SJerry Jelinek ApDumpTableBuffer ( 197*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table, 198*385cc6b4SJerry Jelinek UINT32 Instance, 199*385cc6b4SJerry Jelinek ACPI_PHYSICAL_ADDRESS Address) 200*385cc6b4SJerry Jelinek { 201*385cc6b4SJerry Jelinek UINT32 TableLength; 202*385cc6b4SJerry Jelinek 203*385cc6b4SJerry Jelinek 204*385cc6b4SJerry Jelinek TableLength = ApGetTableLength (Table); 205*385cc6b4SJerry Jelinek 206*385cc6b4SJerry Jelinek /* Print only the header if requested */ 207*385cc6b4SJerry Jelinek 208*385cc6b4SJerry Jelinek if (Gbl_SummaryMode) 209*385cc6b4SJerry Jelinek { 210*385cc6b4SJerry Jelinek AcpiTbPrintTableHeader (Address, Table); 211*385cc6b4SJerry Jelinek return (0); 212*385cc6b4SJerry Jelinek } 213*385cc6b4SJerry Jelinek 214*385cc6b4SJerry Jelinek /* Dump to binary file if requested */ 215*385cc6b4SJerry Jelinek 216*385cc6b4SJerry Jelinek if (Gbl_BinaryMode) 217*385cc6b4SJerry Jelinek { 218*385cc6b4SJerry Jelinek return (ApWriteToBinaryFile (Table, Instance)); 219*385cc6b4SJerry Jelinek } 220*385cc6b4SJerry Jelinek 221*385cc6b4SJerry Jelinek /* 222*385cc6b4SJerry Jelinek * Dump the table with header for use with acpixtract utility. 223*385cc6b4SJerry Jelinek * Note: simplest to just always emit a 64-bit address. AcpiXtract 224*385cc6b4SJerry Jelinek * utility can handle this. 225*385cc6b4SJerry Jelinek */ 226*385cc6b4SJerry Jelinek AcpiUtFilePrintf (Gbl_OutputFile, "%4.4s @ 0x%8.8X%8.8X\n", 227*385cc6b4SJerry Jelinek Table->Signature, ACPI_FORMAT_UINT64 (Address)); 228*385cc6b4SJerry Jelinek 229*385cc6b4SJerry Jelinek AcpiUtDumpBufferToFile (Gbl_OutputFile, 230*385cc6b4SJerry Jelinek ACPI_CAST_PTR (UINT8, Table), TableLength, 231*385cc6b4SJerry Jelinek DB_BYTE_DISPLAY, 0); 232*385cc6b4SJerry Jelinek AcpiUtFilePrintf (Gbl_OutputFile, "\n"); 233*385cc6b4SJerry Jelinek return (0); 234*385cc6b4SJerry Jelinek } 235*385cc6b4SJerry Jelinek 236*385cc6b4SJerry Jelinek 237*385cc6b4SJerry Jelinek /****************************************************************************** 238*385cc6b4SJerry Jelinek * 239*385cc6b4SJerry Jelinek * FUNCTION: ApDumpAllTables 240*385cc6b4SJerry Jelinek * 241*385cc6b4SJerry Jelinek * PARAMETERS: None 242*385cc6b4SJerry Jelinek * 243*385cc6b4SJerry Jelinek * RETURN: Status 244*385cc6b4SJerry Jelinek * 245*385cc6b4SJerry Jelinek * DESCRIPTION: Get all tables from the RSDT/XSDT (or at least all of the 246*385cc6b4SJerry Jelinek * tables that we can possibly get). 247*385cc6b4SJerry Jelinek * 248*385cc6b4SJerry Jelinek ******************************************************************************/ 249*385cc6b4SJerry Jelinek 250*385cc6b4SJerry Jelinek int 251*385cc6b4SJerry Jelinek ApDumpAllTables ( 252*385cc6b4SJerry Jelinek void) 253*385cc6b4SJerry Jelinek { 254*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table; 255*385cc6b4SJerry Jelinek UINT32 Instance = 0; 256*385cc6b4SJerry Jelinek ACPI_PHYSICAL_ADDRESS Address; 257*385cc6b4SJerry Jelinek ACPI_STATUS Status; 258*385cc6b4SJerry Jelinek int TableStatus; 259*385cc6b4SJerry Jelinek UINT32 i; 260*385cc6b4SJerry Jelinek 261*385cc6b4SJerry Jelinek 262*385cc6b4SJerry Jelinek /* Get and dump all available ACPI tables */ 263*385cc6b4SJerry Jelinek 264*385cc6b4SJerry Jelinek for (i = 0; i < AP_MAX_ACPI_FILES; i++) 265*385cc6b4SJerry Jelinek { 266*385cc6b4SJerry Jelinek Status = AcpiOsGetTableByIndex (i, &Table, &Instance, &Address); 267*385cc6b4SJerry Jelinek if (ACPI_FAILURE (Status)) 268*385cc6b4SJerry Jelinek { 269*385cc6b4SJerry Jelinek /* AE_LIMIT means that no more tables are available */ 270*385cc6b4SJerry Jelinek 271*385cc6b4SJerry Jelinek if (Status == AE_LIMIT) 272*385cc6b4SJerry Jelinek { 273*385cc6b4SJerry Jelinek return (0); 274*385cc6b4SJerry Jelinek } 275*385cc6b4SJerry Jelinek else if (i == 0) 276*385cc6b4SJerry Jelinek { 277*385cc6b4SJerry Jelinek AcpiLogError ("Could not get ACPI tables, %s\n", 278*385cc6b4SJerry Jelinek AcpiFormatException (Status)); 279*385cc6b4SJerry Jelinek return (-1); 280*385cc6b4SJerry Jelinek } 281*385cc6b4SJerry Jelinek else 282*385cc6b4SJerry Jelinek { 283*385cc6b4SJerry Jelinek AcpiLogError ("Could not get ACPI table at index %u, %s\n", 284*385cc6b4SJerry Jelinek i, AcpiFormatException (Status)); 285*385cc6b4SJerry Jelinek continue; 286*385cc6b4SJerry Jelinek } 287*385cc6b4SJerry Jelinek } 288*385cc6b4SJerry Jelinek 289*385cc6b4SJerry Jelinek TableStatus = ApDumpTableBuffer (Table, Instance, Address); 290*385cc6b4SJerry Jelinek ACPI_FREE (Table); 291*385cc6b4SJerry Jelinek 292*385cc6b4SJerry Jelinek if (TableStatus) 293*385cc6b4SJerry Jelinek { 294*385cc6b4SJerry Jelinek break; 295*385cc6b4SJerry Jelinek } 296*385cc6b4SJerry Jelinek } 297*385cc6b4SJerry Jelinek 298*385cc6b4SJerry Jelinek /* Something seriously bad happened if the loop terminates here */ 299*385cc6b4SJerry Jelinek 300*385cc6b4SJerry Jelinek return (-1); 301*385cc6b4SJerry Jelinek } 302*385cc6b4SJerry Jelinek 303*385cc6b4SJerry Jelinek 304*385cc6b4SJerry Jelinek /****************************************************************************** 305*385cc6b4SJerry Jelinek * 306*385cc6b4SJerry Jelinek * FUNCTION: ApDumpTableByAddress 307*385cc6b4SJerry Jelinek * 308*385cc6b4SJerry Jelinek * PARAMETERS: AsciiAddress - Address for requested ACPI table 309*385cc6b4SJerry Jelinek * 310*385cc6b4SJerry Jelinek * RETURN: Status 311*385cc6b4SJerry Jelinek * 312*385cc6b4SJerry Jelinek * DESCRIPTION: Get an ACPI table via a physical address and dump it. 313*385cc6b4SJerry Jelinek * 314*385cc6b4SJerry Jelinek ******************************************************************************/ 315*385cc6b4SJerry Jelinek 316*385cc6b4SJerry Jelinek int 317*385cc6b4SJerry Jelinek ApDumpTableByAddress ( 318*385cc6b4SJerry Jelinek char *AsciiAddress) 319*385cc6b4SJerry Jelinek { 320*385cc6b4SJerry Jelinek ACPI_PHYSICAL_ADDRESS Address; 321*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table; 322*385cc6b4SJerry Jelinek ACPI_STATUS Status; 323*385cc6b4SJerry Jelinek int TableStatus; 324*385cc6b4SJerry Jelinek UINT64 LongAddress; 325*385cc6b4SJerry Jelinek 326*385cc6b4SJerry Jelinek 327*385cc6b4SJerry Jelinek /* Convert argument to an integer physical address */ 328*385cc6b4SJerry Jelinek 329*385cc6b4SJerry Jelinek Status = AcpiUtStrtoul64 (AsciiAddress, ACPI_ANY_BASE, 330*385cc6b4SJerry Jelinek ACPI_MAX64_BYTE_WIDTH, &LongAddress); 331*385cc6b4SJerry Jelinek if (ACPI_FAILURE (Status)) 332*385cc6b4SJerry Jelinek { 333*385cc6b4SJerry Jelinek AcpiLogError ("%s: Could not convert to a physical address\n", 334*385cc6b4SJerry Jelinek AsciiAddress); 335*385cc6b4SJerry Jelinek return (-1); 336*385cc6b4SJerry Jelinek } 337*385cc6b4SJerry Jelinek 338*385cc6b4SJerry Jelinek Address = (ACPI_PHYSICAL_ADDRESS) LongAddress; 339*385cc6b4SJerry Jelinek Status = AcpiOsGetTableByAddress (Address, &Table); 340*385cc6b4SJerry Jelinek if (ACPI_FAILURE (Status)) 341*385cc6b4SJerry Jelinek { 342*385cc6b4SJerry Jelinek AcpiLogError ("Could not get table at 0x%8.8X%8.8X, %s\n", 343*385cc6b4SJerry Jelinek ACPI_FORMAT_UINT64 (Address), 344*385cc6b4SJerry Jelinek AcpiFormatException (Status)); 345*385cc6b4SJerry Jelinek return (-1); 346*385cc6b4SJerry Jelinek } 347*385cc6b4SJerry Jelinek 348*385cc6b4SJerry Jelinek TableStatus = ApDumpTableBuffer (Table, 0, Address); 349*385cc6b4SJerry Jelinek ACPI_FREE (Table); 350*385cc6b4SJerry Jelinek return (TableStatus); 351*385cc6b4SJerry Jelinek } 352*385cc6b4SJerry Jelinek 353*385cc6b4SJerry Jelinek 354*385cc6b4SJerry Jelinek /****************************************************************************** 355*385cc6b4SJerry Jelinek * 356*385cc6b4SJerry Jelinek * FUNCTION: ApDumpTableByName 357*385cc6b4SJerry Jelinek * 358*385cc6b4SJerry Jelinek * PARAMETERS: Signature - Requested ACPI table signature 359*385cc6b4SJerry Jelinek * 360*385cc6b4SJerry Jelinek * RETURN: Status 361*385cc6b4SJerry Jelinek * 362*385cc6b4SJerry Jelinek * DESCRIPTION: Get an ACPI table via a signature and dump it. Handles 363*385cc6b4SJerry Jelinek * multiple tables with the same signature (SSDTs). 364*385cc6b4SJerry Jelinek * 365*385cc6b4SJerry Jelinek ******************************************************************************/ 366*385cc6b4SJerry Jelinek 367*385cc6b4SJerry Jelinek int 368*385cc6b4SJerry Jelinek ApDumpTableByName ( 369*385cc6b4SJerry Jelinek char *Signature) 370*385cc6b4SJerry Jelinek { 371*385cc6b4SJerry Jelinek char LocalSignature [ACPI_NAME_SIZE + 1]; 372*385cc6b4SJerry Jelinek UINT32 Instance; 373*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table; 374*385cc6b4SJerry Jelinek ACPI_PHYSICAL_ADDRESS Address; 375*385cc6b4SJerry Jelinek ACPI_STATUS Status; 376*385cc6b4SJerry Jelinek int TableStatus; 377*385cc6b4SJerry Jelinek 378*385cc6b4SJerry Jelinek 379*385cc6b4SJerry Jelinek if (strlen (Signature) != ACPI_NAME_SIZE) 380*385cc6b4SJerry Jelinek { 381*385cc6b4SJerry Jelinek AcpiLogError ( 382*385cc6b4SJerry Jelinek "Invalid table signature [%s]: must be exactly 4 characters\n", 383*385cc6b4SJerry Jelinek Signature); 384*385cc6b4SJerry Jelinek return (-1); 385*385cc6b4SJerry Jelinek } 386*385cc6b4SJerry Jelinek 387*385cc6b4SJerry Jelinek /* Table signatures are expected to be uppercase */ 388*385cc6b4SJerry Jelinek 389*385cc6b4SJerry Jelinek strcpy (LocalSignature, Signature); 390*385cc6b4SJerry Jelinek AcpiUtStrupr (LocalSignature); 391*385cc6b4SJerry Jelinek 392*385cc6b4SJerry Jelinek /* To be friendly, handle tables whose signatures do not match the name */ 393*385cc6b4SJerry Jelinek 394*385cc6b4SJerry Jelinek if (ACPI_COMPARE_NAME (LocalSignature, "FADT")) 395*385cc6b4SJerry Jelinek { 396*385cc6b4SJerry Jelinek strcpy (LocalSignature, ACPI_SIG_FADT); 397*385cc6b4SJerry Jelinek } 398*385cc6b4SJerry Jelinek else if (ACPI_COMPARE_NAME (LocalSignature, "MADT")) 399*385cc6b4SJerry Jelinek { 400*385cc6b4SJerry Jelinek strcpy (LocalSignature, ACPI_SIG_MADT); 401*385cc6b4SJerry Jelinek } 402*385cc6b4SJerry Jelinek 403*385cc6b4SJerry Jelinek /* Dump all instances of this signature (to handle multiple SSDTs) */ 404*385cc6b4SJerry Jelinek 405*385cc6b4SJerry Jelinek for (Instance = 0; Instance < AP_MAX_ACPI_FILES; Instance++) 406*385cc6b4SJerry Jelinek { 407*385cc6b4SJerry Jelinek Status = AcpiOsGetTableByName (LocalSignature, Instance, 408*385cc6b4SJerry Jelinek &Table, &Address); 409*385cc6b4SJerry Jelinek if (ACPI_FAILURE (Status)) 410*385cc6b4SJerry Jelinek { 411*385cc6b4SJerry Jelinek /* AE_LIMIT means that no more tables are available */ 412*385cc6b4SJerry Jelinek 413*385cc6b4SJerry Jelinek if (Status == AE_LIMIT) 414*385cc6b4SJerry Jelinek { 415*385cc6b4SJerry Jelinek return (0); 416*385cc6b4SJerry Jelinek } 417*385cc6b4SJerry Jelinek 418*385cc6b4SJerry Jelinek AcpiLogError ( 419*385cc6b4SJerry Jelinek "Could not get ACPI table with signature [%s], %s\n", 420*385cc6b4SJerry Jelinek LocalSignature, AcpiFormatException (Status)); 421*385cc6b4SJerry Jelinek return (-1); 422*385cc6b4SJerry Jelinek } 423*385cc6b4SJerry Jelinek 424*385cc6b4SJerry Jelinek TableStatus = ApDumpTableBuffer (Table, Instance, Address); 425*385cc6b4SJerry Jelinek ACPI_FREE (Table); 426*385cc6b4SJerry Jelinek 427*385cc6b4SJerry Jelinek if (TableStatus) 428*385cc6b4SJerry Jelinek { 429*385cc6b4SJerry Jelinek break; 430*385cc6b4SJerry Jelinek } 431*385cc6b4SJerry Jelinek } 432*385cc6b4SJerry Jelinek 433*385cc6b4SJerry Jelinek /* Something seriously bad happened if the loop terminates here */ 434*385cc6b4SJerry Jelinek 435*385cc6b4SJerry Jelinek return (-1); 436*385cc6b4SJerry Jelinek } 437*385cc6b4SJerry Jelinek 438*385cc6b4SJerry Jelinek 439*385cc6b4SJerry Jelinek /****************************************************************************** 440*385cc6b4SJerry Jelinek * 441*385cc6b4SJerry Jelinek * FUNCTION: ApDumpTableFromFile 442*385cc6b4SJerry Jelinek * 443*385cc6b4SJerry Jelinek * PARAMETERS: Pathname - File containing the binary ACPI table 444*385cc6b4SJerry Jelinek * 445*385cc6b4SJerry Jelinek * RETURN: Status 446*385cc6b4SJerry Jelinek * 447*385cc6b4SJerry Jelinek * DESCRIPTION: Dump an ACPI table from a binary file 448*385cc6b4SJerry Jelinek * 449*385cc6b4SJerry Jelinek ******************************************************************************/ 450*385cc6b4SJerry Jelinek 451*385cc6b4SJerry Jelinek int 452*385cc6b4SJerry Jelinek ApDumpTableFromFile ( 453*385cc6b4SJerry Jelinek char *Pathname) 454*385cc6b4SJerry Jelinek { 455*385cc6b4SJerry Jelinek ACPI_TABLE_HEADER *Table; 456*385cc6b4SJerry Jelinek UINT32 FileSize = 0; 457*385cc6b4SJerry Jelinek int TableStatus = -1; 458*385cc6b4SJerry Jelinek 459*385cc6b4SJerry Jelinek 460*385cc6b4SJerry Jelinek /* Get the entire ACPI table from the file */ 461*385cc6b4SJerry Jelinek 462*385cc6b4SJerry Jelinek Table = ApGetTableFromFile (Pathname, &FileSize); 463*385cc6b4SJerry Jelinek if (!Table) 464*385cc6b4SJerry Jelinek { 465*385cc6b4SJerry Jelinek return (-1); 466*385cc6b4SJerry Jelinek } 467*385cc6b4SJerry Jelinek 468*385cc6b4SJerry Jelinek if (!AcpiUtValidNameseg (Table->Signature)) 469*385cc6b4SJerry Jelinek { 470*385cc6b4SJerry Jelinek AcpiLogError ( 471*385cc6b4SJerry Jelinek "No valid ACPI signature was found in input file %s\n", 472*385cc6b4SJerry Jelinek Pathname); 473*385cc6b4SJerry Jelinek } 474*385cc6b4SJerry Jelinek 475*385cc6b4SJerry Jelinek /* File must be at least as long as the table length */ 476*385cc6b4SJerry Jelinek 477*385cc6b4SJerry Jelinek if (Table->Length > FileSize) 478*385cc6b4SJerry Jelinek { 479*385cc6b4SJerry Jelinek AcpiLogError ( 480*385cc6b4SJerry Jelinek "Table length (0x%X) is too large for input file (0x%X) %s\n", 481*385cc6b4SJerry Jelinek Table->Length, FileSize, Pathname); 482*385cc6b4SJerry Jelinek goto Exit; 483*385cc6b4SJerry Jelinek } 484*385cc6b4SJerry Jelinek 485*385cc6b4SJerry Jelinek if (Gbl_VerboseMode) 486*385cc6b4SJerry Jelinek { 487*385cc6b4SJerry Jelinek AcpiLogError ( 488*385cc6b4SJerry Jelinek "Input file: %s contains table [%4.4s], 0x%X (%u) bytes\n", 489*385cc6b4SJerry Jelinek Pathname, Table->Signature, FileSize, FileSize); 490*385cc6b4SJerry Jelinek } 491*385cc6b4SJerry Jelinek 492*385cc6b4SJerry Jelinek TableStatus = ApDumpTableBuffer (Table, 0, 0); 493*385cc6b4SJerry Jelinek 494*385cc6b4SJerry Jelinek Exit: 495*385cc6b4SJerry Jelinek ACPI_FREE (Table); 496*385cc6b4SJerry Jelinek return (TableStatus); 497*385cc6b4SJerry Jelinek } 498