1f556842eSJung-uk Kim /****************************************************************************** 2f556842eSJung-uk Kim * 3f556842eSJung-uk Kim * Module Name: dmextern - Support for External() ASL statements 4f556842eSJung-uk Kim * 5f556842eSJung-uk Kim *****************************************************************************/ 6f556842eSJung-uk Kim 7d244b227SJung-uk Kim /* 8ec3fc72fSJung-uk Kim * Copyright (C) 2000 - 2012, Intel Corp. 9f556842eSJung-uk Kim * All rights reserved. 10f556842eSJung-uk Kim * 11d244b227SJung-uk Kim * Redistribution and use in source and binary forms, with or without 12d244b227SJung-uk Kim * modification, are permitted provided that the following conditions 13d244b227SJung-uk Kim * are met: 14d244b227SJung-uk Kim * 1. Redistributions of source code must retain the above copyright 15d244b227SJung-uk Kim * notice, this list of conditions, and the following disclaimer, 16d244b227SJung-uk Kim * without modification. 17d244b227SJung-uk Kim * 2. Redistributions in binary form must reproduce at minimum a disclaimer 18d244b227SJung-uk Kim * substantially similar to the "NO WARRANTY" disclaimer below 19d244b227SJung-uk Kim * ("Disclaimer") and any redistribution must be conditioned upon 20d244b227SJung-uk Kim * including a substantially similar Disclaimer requirement for further 21d244b227SJung-uk Kim * binary redistribution. 22d244b227SJung-uk Kim * 3. Neither the names of the above-listed copyright holders nor the names 23d244b227SJung-uk Kim * of any contributors may be used to endorse or promote products derived 24d244b227SJung-uk Kim * from this software without specific prior written permission. 25f556842eSJung-uk Kim * 26d244b227SJung-uk Kim * Alternatively, this software may be distributed under the terms of the 27d244b227SJung-uk Kim * GNU General Public License ("GPL") version 2 as published by the Free 28d244b227SJung-uk Kim * Software Foundation. 29f556842eSJung-uk Kim * 30d244b227SJung-uk Kim * NO WARRANTY 31d244b227SJung-uk Kim * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 32d244b227SJung-uk Kim * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 33d244b227SJung-uk Kim * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR 34d244b227SJung-uk Kim * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 35d244b227SJung-uk Kim * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 36d244b227SJung-uk Kim * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 37d244b227SJung-uk Kim * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 38d244b227SJung-uk Kim * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 39d244b227SJung-uk Kim * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING 40d244b227SJung-uk Kim * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 41d244b227SJung-uk Kim * POSSIBILITY OF SUCH DAMAGES. 42d244b227SJung-uk Kim */ 43f556842eSJung-uk Kim 44f556842eSJung-uk Kim #include <contrib/dev/acpica/include/acpi.h> 45f556842eSJung-uk Kim #include <contrib/dev/acpica/include/accommon.h> 46f556842eSJung-uk Kim #include <contrib/dev/acpica/include/amlcode.h> 47f556842eSJung-uk Kim #include <contrib/dev/acpica/include/acnamesp.h> 48f556842eSJung-uk Kim #include <contrib/dev/acpica/include/acdisasm.h> 49f556842eSJung-uk Kim 50f556842eSJung-uk Kim 51f556842eSJung-uk Kim /* 52f556842eSJung-uk Kim * This module is used for application-level code (iASL disassembler) only. 53f556842eSJung-uk Kim * 54f556842eSJung-uk Kim * It contains the code to create and emit any necessary External() ASL 55f556842eSJung-uk Kim * statements for the module being disassembled. 56f556842eSJung-uk Kim */ 57f556842eSJung-uk Kim #define _COMPONENT ACPI_CA_DISASSEMBLER 58f556842eSJung-uk Kim ACPI_MODULE_NAME ("dmextern") 59f556842eSJung-uk Kim 60f556842eSJung-uk Kim 61f556842eSJung-uk Kim /* 62f556842eSJung-uk Kim * This table maps ACPI_OBJECT_TYPEs to the corresponding ASL 63f556842eSJung-uk Kim * ObjectTypeKeyword. Used to generate typed external declarations 64f556842eSJung-uk Kim */ 65f556842eSJung-uk Kim static const char *AcpiGbl_DmTypeNames[] = 66f556842eSJung-uk Kim { 67f556842eSJung-uk Kim /* 00 */ "", /* Type ANY */ 68f556842eSJung-uk Kim /* 01 */ ", IntObj", 69f556842eSJung-uk Kim /* 02 */ ", StrObj", 70f556842eSJung-uk Kim /* 03 */ ", BuffObj", 71f556842eSJung-uk Kim /* 04 */ ", PkgObj", 72f556842eSJung-uk Kim /* 05 */ ", FieldUnitObj", 73f556842eSJung-uk Kim /* 06 */ ", DeviceObj", 74f556842eSJung-uk Kim /* 07 */ ", EventObj", 75f556842eSJung-uk Kim /* 08 */ ", MethodObj", 76f556842eSJung-uk Kim /* 09 */ ", MutexObj", 77f556842eSJung-uk Kim /* 10 */ ", OpRegionObj", 78f556842eSJung-uk Kim /* 11 */ ", PowerResObj", 79f556842eSJung-uk Kim /* 12 */ ", ProcessorObj", 80f556842eSJung-uk Kim /* 13 */ ", ThermalZoneObj", 81f556842eSJung-uk Kim /* 14 */ ", BuffFieldObj", 82f556842eSJung-uk Kim /* 15 */ ", DDBHandleObj", 83f556842eSJung-uk Kim /* 16 */ "", /* Debug object */ 84f556842eSJung-uk Kim /* 17 */ ", FieldUnitObj", 85f556842eSJung-uk Kim /* 18 */ ", FieldUnitObj", 86f556842eSJung-uk Kim /* 19 */ ", FieldUnitObj" 87f556842eSJung-uk Kim }; 88f556842eSJung-uk Kim 89f556842eSJung-uk Kim 90f556842eSJung-uk Kim /* Local prototypes */ 91f556842eSJung-uk Kim 92f556842eSJung-uk Kim static const char * 93f556842eSJung-uk Kim AcpiDmGetObjectTypeName ( 94f556842eSJung-uk Kim ACPI_OBJECT_TYPE Type); 95f556842eSJung-uk Kim 96f556842eSJung-uk Kim static char * 97f556842eSJung-uk Kim AcpiDmNormalizeParentPrefix ( 98f556842eSJung-uk Kim ACPI_PARSE_OBJECT *Op, 99f556842eSJung-uk Kim char *Path); 100f556842eSJung-uk Kim 101f556842eSJung-uk Kim 102f556842eSJung-uk Kim /******************************************************************************* 103f556842eSJung-uk Kim * 104f556842eSJung-uk Kim * FUNCTION: AcpiDmGetObjectTypeName 105f556842eSJung-uk Kim * 106f556842eSJung-uk Kim * PARAMETERS: Type - An ACPI_OBJECT_TYPE 107f556842eSJung-uk Kim * 108f556842eSJung-uk Kim * RETURN: Pointer to a string 109f556842eSJung-uk Kim * 110f556842eSJung-uk Kim * DESCRIPTION: Map an object type to the ASL object type string. 111f556842eSJung-uk Kim * 112f556842eSJung-uk Kim ******************************************************************************/ 113f556842eSJung-uk Kim 114f556842eSJung-uk Kim static const char * 115f556842eSJung-uk Kim AcpiDmGetObjectTypeName ( 116f556842eSJung-uk Kim ACPI_OBJECT_TYPE Type) 117f556842eSJung-uk Kim { 118f556842eSJung-uk Kim 119f556842eSJung-uk Kim if (Type == ACPI_TYPE_LOCAL_SCOPE) 120f556842eSJung-uk Kim { 121f556842eSJung-uk Kim Type = ACPI_TYPE_DEVICE; 122f556842eSJung-uk Kim } 123f556842eSJung-uk Kim 124f556842eSJung-uk Kim else if (Type > ACPI_TYPE_LOCAL_INDEX_FIELD) 125f556842eSJung-uk Kim { 126f556842eSJung-uk Kim return (""); 127f556842eSJung-uk Kim } 128f556842eSJung-uk Kim 129f556842eSJung-uk Kim return (AcpiGbl_DmTypeNames[Type]); 130f556842eSJung-uk Kim } 131f556842eSJung-uk Kim 132f556842eSJung-uk Kim 133f556842eSJung-uk Kim /******************************************************************************* 134f556842eSJung-uk Kim * 135f556842eSJung-uk Kim * FUNCTION: AcpiDmNormalizeParentPrefix 136f556842eSJung-uk Kim * 137f556842eSJung-uk Kim * PARAMETERS: Op - Parse op 138f556842eSJung-uk Kim * Path - Path with parent prefix 139f556842eSJung-uk Kim * 140f556842eSJung-uk Kim * RETURN: The full pathname to the object (from the namespace root) 141f556842eSJung-uk Kim * 142f556842eSJung-uk Kim * DESCRIPTION: Returns the full pathname of a path with parent prefix 143f556842eSJung-uk Kim * The caller must free the fullpath returned. 144f556842eSJung-uk Kim * 145f556842eSJung-uk Kim ******************************************************************************/ 146f556842eSJung-uk Kim 147f556842eSJung-uk Kim static char * 148f556842eSJung-uk Kim AcpiDmNormalizeParentPrefix ( 149f556842eSJung-uk Kim ACPI_PARSE_OBJECT *Op, 150f556842eSJung-uk Kim char *Path) 151f556842eSJung-uk Kim { 152f556842eSJung-uk Kim ACPI_NAMESPACE_NODE *Node; 153f556842eSJung-uk Kim char *Fullpath; 154f556842eSJung-uk Kim char *ParentPath; 155f556842eSJung-uk Kim ACPI_SIZE Length; 156f556842eSJung-uk Kim 157f556842eSJung-uk Kim 158f556842eSJung-uk Kim /* Search upwards in the parse tree until we reach a namespace node */ 159f556842eSJung-uk Kim 160f556842eSJung-uk Kim while (Op) 161f556842eSJung-uk Kim { 162f556842eSJung-uk Kim if (Op->Common.Node) 163f556842eSJung-uk Kim { 164f556842eSJung-uk Kim break; 165f556842eSJung-uk Kim } 166f556842eSJung-uk Kim 167f556842eSJung-uk Kim Op = Op->Common.Parent; 168f556842eSJung-uk Kim } 169f556842eSJung-uk Kim 170f556842eSJung-uk Kim if (!Op) 171f556842eSJung-uk Kim { 172f556842eSJung-uk Kim return (NULL); 173f556842eSJung-uk Kim } 174f556842eSJung-uk Kim 175f556842eSJung-uk Kim /* 176f556842eSJung-uk Kim * Find the actual parent node for the reference: 177f556842eSJung-uk Kim * Remove all carat prefixes from the input path. 178f556842eSJung-uk Kim * There may be multiple parent prefixes (For example, ^^^M000) 179f556842eSJung-uk Kim */ 180f556842eSJung-uk Kim Node = Op->Common.Node; 181f556842eSJung-uk Kim while (Node && (*Path == (UINT8) AML_PARENT_PREFIX)) 182f556842eSJung-uk Kim { 183a88e22b7SJung-uk Kim Node = Node->Parent; 184f556842eSJung-uk Kim Path++; 185f556842eSJung-uk Kim } 186f556842eSJung-uk Kim 187f556842eSJung-uk Kim if (!Node) 188f556842eSJung-uk Kim { 189f556842eSJung-uk Kim return (NULL); 190f556842eSJung-uk Kim } 191f556842eSJung-uk Kim 192f556842eSJung-uk Kim /* Get the full pathname for the parent node */ 193f556842eSJung-uk Kim 194f556842eSJung-uk Kim ParentPath = AcpiNsGetExternalPathname (Node); 195f556842eSJung-uk Kim if (!ParentPath) 196f556842eSJung-uk Kim { 197f556842eSJung-uk Kim return (NULL); 198f556842eSJung-uk Kim } 199f556842eSJung-uk Kim 200f556842eSJung-uk Kim Length = (ACPI_STRLEN (ParentPath) + ACPI_STRLEN (Path) + 1); 2018c8be05fSJung-uk Kim if (ParentPath[1]) 2028c8be05fSJung-uk Kim { 2038c8be05fSJung-uk Kim /* 2048c8be05fSJung-uk Kim * If ParentPath is not just a simple '\', increment the length 2058c8be05fSJung-uk Kim * for the required dot separator (ParentPath.Path) 2068c8be05fSJung-uk Kim */ 2078c8be05fSJung-uk Kim Length++; 2088c8be05fSJung-uk Kim } 2098c8be05fSJung-uk Kim 210f556842eSJung-uk Kim Fullpath = ACPI_ALLOCATE_ZEROED (Length); 211f556842eSJung-uk Kim if (!Fullpath) 212f556842eSJung-uk Kim { 213f556842eSJung-uk Kim goto Cleanup; 214f556842eSJung-uk Kim } 215f556842eSJung-uk Kim 216f556842eSJung-uk Kim /* 217f556842eSJung-uk Kim * Concatenate parent fullpath and path. For example, 218f556842eSJung-uk Kim * parent fullpath "\_SB_", Path "^INIT", Fullpath "\_SB_.INIT" 219f556842eSJung-uk Kim * 220f556842eSJung-uk Kim * Copy the parent path 221f556842eSJung-uk Kim */ 222f556842eSJung-uk Kim ACPI_STRCAT (Fullpath, ParentPath); 223f556842eSJung-uk Kim 224f556842eSJung-uk Kim /* Add dot separator (don't need dot if parent fullpath is a single "\") */ 225f556842eSJung-uk Kim 226f556842eSJung-uk Kim if (ParentPath[1]) 227f556842eSJung-uk Kim { 228f556842eSJung-uk Kim ACPI_STRCAT (Fullpath, "."); 229f556842eSJung-uk Kim } 230f556842eSJung-uk Kim 231f556842eSJung-uk Kim /* Copy child path (carat parent prefix(es) were skipped above) */ 232f556842eSJung-uk Kim 233f556842eSJung-uk Kim ACPI_STRCAT (Fullpath, Path); 234f556842eSJung-uk Kim 235f556842eSJung-uk Kim Cleanup: 236f556842eSJung-uk Kim ACPI_FREE (ParentPath); 237f556842eSJung-uk Kim return (Fullpath); 238f556842eSJung-uk Kim } 239f556842eSJung-uk Kim 240f556842eSJung-uk Kim 241f556842eSJung-uk Kim /******************************************************************************* 242f556842eSJung-uk Kim * 243709fac06SJung-uk Kim * FUNCTION: AcpiDmAddToExternalFileList 244709fac06SJung-uk Kim * 245709fac06SJung-uk Kim * PARAMETERS: PathList - Single path or list separated by comma 246709fac06SJung-uk Kim * 247709fac06SJung-uk Kim * RETURN: None 248709fac06SJung-uk Kim * 249709fac06SJung-uk Kim * DESCRIPTION: Add external files to global list 250709fac06SJung-uk Kim * 251709fac06SJung-uk Kim ******************************************************************************/ 252709fac06SJung-uk Kim 253709fac06SJung-uk Kim ACPI_STATUS 254709fac06SJung-uk Kim AcpiDmAddToExternalFileList ( 255709fac06SJung-uk Kim char *PathList) 256709fac06SJung-uk Kim { 257709fac06SJung-uk Kim ACPI_EXTERNAL_FILE *ExternalFile; 258709fac06SJung-uk Kim char *Path; 259709fac06SJung-uk Kim char *TmpPath; 260709fac06SJung-uk Kim 261709fac06SJung-uk Kim 262709fac06SJung-uk Kim if (!PathList) 263709fac06SJung-uk Kim { 264709fac06SJung-uk Kim return (AE_OK); 265709fac06SJung-uk Kim } 266709fac06SJung-uk Kim 267709fac06SJung-uk Kim Path = strtok (PathList, ","); 268709fac06SJung-uk Kim 269709fac06SJung-uk Kim while (Path) 270709fac06SJung-uk Kim { 271709fac06SJung-uk Kim TmpPath = ACPI_ALLOCATE_ZEROED (ACPI_STRLEN (Path) + 1); 272709fac06SJung-uk Kim if (!TmpPath) 273709fac06SJung-uk Kim { 274709fac06SJung-uk Kim return (AE_NO_MEMORY); 275709fac06SJung-uk Kim } 276709fac06SJung-uk Kim 277709fac06SJung-uk Kim ACPI_STRCPY (TmpPath, Path); 278709fac06SJung-uk Kim 279709fac06SJung-uk Kim ExternalFile = ACPI_ALLOCATE_ZEROED (sizeof (ACPI_EXTERNAL_FILE)); 280709fac06SJung-uk Kim if (!ExternalFile) 281709fac06SJung-uk Kim { 282709fac06SJung-uk Kim ACPI_FREE (TmpPath); 283709fac06SJung-uk Kim return (AE_NO_MEMORY); 284709fac06SJung-uk Kim } 285709fac06SJung-uk Kim 286709fac06SJung-uk Kim ExternalFile->Path = TmpPath; 287709fac06SJung-uk Kim 288709fac06SJung-uk Kim if (AcpiGbl_ExternalFileList) 289709fac06SJung-uk Kim { 290709fac06SJung-uk Kim ExternalFile->Next = AcpiGbl_ExternalFileList; 291709fac06SJung-uk Kim } 292709fac06SJung-uk Kim 293709fac06SJung-uk Kim AcpiGbl_ExternalFileList = ExternalFile; 294709fac06SJung-uk Kim Path = strtok (NULL, ","); 295709fac06SJung-uk Kim } 296709fac06SJung-uk Kim 297709fac06SJung-uk Kim return (AE_OK); 298709fac06SJung-uk Kim } 299709fac06SJung-uk Kim 300709fac06SJung-uk Kim 301709fac06SJung-uk Kim /******************************************************************************* 302709fac06SJung-uk Kim * 303709fac06SJung-uk Kim * FUNCTION: AcpiDmClearExternalFileList 304709fac06SJung-uk Kim * 305709fac06SJung-uk Kim * PARAMETERS: None 306709fac06SJung-uk Kim * 307709fac06SJung-uk Kim * RETURN: None 308709fac06SJung-uk Kim * 309709fac06SJung-uk Kim * DESCRIPTION: Clear the external file list 310709fac06SJung-uk Kim * 311709fac06SJung-uk Kim ******************************************************************************/ 312709fac06SJung-uk Kim 313709fac06SJung-uk Kim void 314709fac06SJung-uk Kim AcpiDmClearExternalFileList ( 315709fac06SJung-uk Kim void) 316709fac06SJung-uk Kim { 317709fac06SJung-uk Kim ACPI_EXTERNAL_FILE *NextExternal; 318709fac06SJung-uk Kim 319709fac06SJung-uk Kim 320709fac06SJung-uk Kim while (AcpiGbl_ExternalFileList) 321709fac06SJung-uk Kim { 322709fac06SJung-uk Kim NextExternal = AcpiGbl_ExternalFileList->Next; 323709fac06SJung-uk Kim ACPI_FREE (AcpiGbl_ExternalFileList->Path); 324709fac06SJung-uk Kim ACPI_FREE (AcpiGbl_ExternalFileList); 325709fac06SJung-uk Kim AcpiGbl_ExternalFileList = NextExternal; 326709fac06SJung-uk Kim } 327709fac06SJung-uk Kim } 328709fac06SJung-uk Kim 329709fac06SJung-uk Kim 330709fac06SJung-uk Kim /******************************************************************************* 331709fac06SJung-uk Kim * 332f556842eSJung-uk Kim * FUNCTION: AcpiDmAddToExternalList 333f556842eSJung-uk Kim * 334f556842eSJung-uk Kim * PARAMETERS: Op - Current parser Op 335f556842eSJung-uk Kim * Path - Internal (AML) path to the object 336f556842eSJung-uk Kim * Type - ACPI object type to be added 337f556842eSJung-uk Kim * Value - Arg count if adding a Method object 338f556842eSJung-uk Kim * 339f556842eSJung-uk Kim * RETURN: None 340f556842eSJung-uk Kim * 341f556842eSJung-uk Kim * DESCRIPTION: Insert a new name into the global list of Externals which 342f556842eSJung-uk Kim * will in turn be later emitted as an External() declaration 343f556842eSJung-uk Kim * in the disassembled output. 344f556842eSJung-uk Kim * 345f556842eSJung-uk Kim ******************************************************************************/ 346f556842eSJung-uk Kim 347f556842eSJung-uk Kim void 348f556842eSJung-uk Kim AcpiDmAddToExternalList ( 349f556842eSJung-uk Kim ACPI_PARSE_OBJECT *Op, 350f556842eSJung-uk Kim char *Path, 351f556842eSJung-uk Kim UINT8 Type, 352f556842eSJung-uk Kim UINT32 Value) 353f556842eSJung-uk Kim { 354f556842eSJung-uk Kim char *ExternalPath; 355f556842eSJung-uk Kim char *Fullpath = NULL; 356f556842eSJung-uk Kim ACPI_EXTERNAL_LIST *NewExternal; 357f556842eSJung-uk Kim ACPI_EXTERNAL_LIST *NextExternal; 358f556842eSJung-uk Kim ACPI_EXTERNAL_LIST *PrevExternal = NULL; 359f556842eSJung-uk Kim ACPI_STATUS Status; 360f556842eSJung-uk Kim 361f556842eSJung-uk Kim 362f556842eSJung-uk Kim if (!Path) 363f556842eSJung-uk Kim { 364f556842eSJung-uk Kim return; 365f556842eSJung-uk Kim } 366f556842eSJung-uk Kim 367f556842eSJung-uk Kim /* Externalize the ACPI path */ 368f556842eSJung-uk Kim 369f556842eSJung-uk Kim Status = AcpiNsExternalizeName (ACPI_UINT32_MAX, Path, 370f556842eSJung-uk Kim NULL, &ExternalPath); 371f556842eSJung-uk Kim if (ACPI_FAILURE (Status)) 372f556842eSJung-uk Kim { 373f556842eSJung-uk Kim return; 374f556842eSJung-uk Kim } 375f556842eSJung-uk Kim 376f556842eSJung-uk Kim /* Get the full pathname from root if "Path" has a parent prefix */ 377f556842eSJung-uk Kim 378f556842eSJung-uk Kim if (*Path == (UINT8) AML_PARENT_PREFIX) 379f556842eSJung-uk Kim { 380f556842eSJung-uk Kim Fullpath = AcpiDmNormalizeParentPrefix (Op, ExternalPath); 381f556842eSJung-uk Kim if (Fullpath) 382f556842eSJung-uk Kim { 383f556842eSJung-uk Kim /* Set new external path */ 384f556842eSJung-uk Kim 385f556842eSJung-uk Kim ACPI_FREE (ExternalPath); 386f556842eSJung-uk Kim ExternalPath = Fullpath; 387f556842eSJung-uk Kim } 388f556842eSJung-uk Kim } 389f556842eSJung-uk Kim 390f556842eSJung-uk Kim /* Check all existing externals to ensure no duplicates */ 391f556842eSJung-uk Kim 392f556842eSJung-uk Kim NextExternal = AcpiGbl_ExternalList; 393f556842eSJung-uk Kim while (NextExternal) 394f556842eSJung-uk Kim { 395f556842eSJung-uk Kim if (!ACPI_STRCMP (ExternalPath, NextExternal->Path)) 396f556842eSJung-uk Kim { 397f556842eSJung-uk Kim /* Duplicate method, check that the Value (ArgCount) is the same */ 398f556842eSJung-uk Kim 399f556842eSJung-uk Kim if ((NextExternal->Type == ACPI_TYPE_METHOD) && 400f556842eSJung-uk Kim (NextExternal->Value != Value)) 401f556842eSJung-uk Kim { 402f556842eSJung-uk Kim ACPI_ERROR ((AE_INFO, 403ca3cf4faSJung-uk Kim "Argument count mismatch for method %s %u %u", 404f556842eSJung-uk Kim NextExternal->Path, NextExternal->Value, Value)); 405f556842eSJung-uk Kim } 406f556842eSJung-uk Kim 407f556842eSJung-uk Kim /* Allow upgrade of type from ANY */ 408f556842eSJung-uk Kim 409f556842eSJung-uk Kim else if (NextExternal->Type == ACPI_TYPE_ANY) 410f556842eSJung-uk Kim { 411f556842eSJung-uk Kim NextExternal->Type = Type; 412f556842eSJung-uk Kim NextExternal->Value = Value; 413f556842eSJung-uk Kim } 414f556842eSJung-uk Kim 415f556842eSJung-uk Kim ACPI_FREE (ExternalPath); 416f556842eSJung-uk Kim return; 417f556842eSJung-uk Kim } 418f556842eSJung-uk Kim 419f556842eSJung-uk Kim NextExternal = NextExternal->Next; 420f556842eSJung-uk Kim } 421f556842eSJung-uk Kim 422f556842eSJung-uk Kim /* Allocate and init a new External() descriptor */ 423f556842eSJung-uk Kim 424f556842eSJung-uk Kim NewExternal = ACPI_ALLOCATE_ZEROED (sizeof (ACPI_EXTERNAL_LIST)); 425f556842eSJung-uk Kim if (!NewExternal) 426f556842eSJung-uk Kim { 427f556842eSJung-uk Kim ACPI_FREE (ExternalPath); 428f556842eSJung-uk Kim return; 429f556842eSJung-uk Kim } 430f556842eSJung-uk Kim 431f556842eSJung-uk Kim NewExternal->Path = ExternalPath; 432f556842eSJung-uk Kim NewExternal->Type = Type; 433f556842eSJung-uk Kim NewExternal->Value = Value; 434f556842eSJung-uk Kim NewExternal->Length = (UINT16) ACPI_STRLEN (ExternalPath); 435f556842eSJung-uk Kim 436f556842eSJung-uk Kim /* Was the external path with parent prefix normalized to a fullpath? */ 437f556842eSJung-uk Kim 438f556842eSJung-uk Kim if (Fullpath == ExternalPath) 439f556842eSJung-uk Kim { 440f556842eSJung-uk Kim /* Get new internal path */ 441f556842eSJung-uk Kim 442f556842eSJung-uk Kim Status = AcpiNsInternalizeName (ExternalPath, &Path); 443f556842eSJung-uk Kim if (ACPI_FAILURE (Status)) 444f556842eSJung-uk Kim { 445f556842eSJung-uk Kim ACPI_FREE (ExternalPath); 446f556842eSJung-uk Kim ACPI_FREE (NewExternal); 447f556842eSJung-uk Kim return; 448f556842eSJung-uk Kim } 449f556842eSJung-uk Kim 450f556842eSJung-uk Kim /* Set flag to indicate External->InternalPath need to be freed */ 451f556842eSJung-uk Kim 452f556842eSJung-uk Kim NewExternal->Flags |= ACPI_IPATH_ALLOCATED; 453f556842eSJung-uk Kim } 454f556842eSJung-uk Kim 455f556842eSJung-uk Kim NewExternal->InternalPath = Path; 456f556842eSJung-uk Kim 457*a7a3b383SJung-uk Kim /* Link the new descriptor into the global list, alphabetically ordered */ 458f556842eSJung-uk Kim 459f556842eSJung-uk Kim NextExternal = AcpiGbl_ExternalList; 460f556842eSJung-uk Kim while (NextExternal) 461f556842eSJung-uk Kim { 462*a7a3b383SJung-uk Kim if (AcpiUtStricmp (NewExternal->Path, NextExternal->Path) < 0) 463f556842eSJung-uk Kim { 464f556842eSJung-uk Kim if (PrevExternal) 465f556842eSJung-uk Kim { 466f556842eSJung-uk Kim PrevExternal->Next = NewExternal; 467f556842eSJung-uk Kim } 468f556842eSJung-uk Kim else 469f556842eSJung-uk Kim { 470f556842eSJung-uk Kim AcpiGbl_ExternalList = NewExternal; 471f556842eSJung-uk Kim } 472f556842eSJung-uk Kim 473f556842eSJung-uk Kim NewExternal->Next = NextExternal; 474f556842eSJung-uk Kim return; 475f556842eSJung-uk Kim } 476f556842eSJung-uk Kim 477f556842eSJung-uk Kim PrevExternal = NextExternal; 478f556842eSJung-uk Kim NextExternal = NextExternal->Next; 479f556842eSJung-uk Kim } 480f556842eSJung-uk Kim 481f556842eSJung-uk Kim if (PrevExternal) 482f556842eSJung-uk Kim { 483f556842eSJung-uk Kim PrevExternal->Next = NewExternal; 484f556842eSJung-uk Kim } 485f556842eSJung-uk Kim else 486f556842eSJung-uk Kim { 487f556842eSJung-uk Kim AcpiGbl_ExternalList = NewExternal; 488f556842eSJung-uk Kim } 489f556842eSJung-uk Kim } 490f556842eSJung-uk Kim 491f556842eSJung-uk Kim 492f556842eSJung-uk Kim /******************************************************************************* 493f556842eSJung-uk Kim * 494f556842eSJung-uk Kim * FUNCTION: AcpiDmAddExternalsToNamespace 495f556842eSJung-uk Kim * 496f556842eSJung-uk Kim * PARAMETERS: None 497f556842eSJung-uk Kim * 498f556842eSJung-uk Kim * RETURN: None 499f556842eSJung-uk Kim * 500f556842eSJung-uk Kim * DESCRIPTION: Add all externals to the namespace. Allows externals to be 501f556842eSJung-uk Kim * "resolved". 502f556842eSJung-uk Kim * 503f556842eSJung-uk Kim ******************************************************************************/ 504f556842eSJung-uk Kim 505f556842eSJung-uk Kim void 506f556842eSJung-uk Kim AcpiDmAddExternalsToNamespace ( 507f556842eSJung-uk Kim void) 508f556842eSJung-uk Kim { 509f556842eSJung-uk Kim ACPI_STATUS Status; 510f556842eSJung-uk Kim ACPI_NAMESPACE_NODE *Node; 511*a7a3b383SJung-uk Kim ACPI_OPERAND_OBJECT *ObjDesc; 512f556842eSJung-uk Kim ACPI_EXTERNAL_LIST *External = AcpiGbl_ExternalList; 513f556842eSJung-uk Kim 514f556842eSJung-uk Kim 515f556842eSJung-uk Kim while (External) 516f556842eSJung-uk Kim { 517f556842eSJung-uk Kim /* Add the external name (object) into the namespace */ 518f556842eSJung-uk Kim 519f556842eSJung-uk Kim Status = AcpiNsLookup (NULL, External->InternalPath, External->Type, 520f556842eSJung-uk Kim ACPI_IMODE_LOAD_PASS1, 521f556842eSJung-uk Kim ACPI_NS_EXTERNAL | ACPI_NS_DONT_OPEN_SCOPE, 522f556842eSJung-uk Kim NULL, &Node); 523f556842eSJung-uk Kim 524f556842eSJung-uk Kim if (ACPI_FAILURE (Status)) 525f556842eSJung-uk Kim { 526f556842eSJung-uk Kim ACPI_EXCEPTION ((AE_INFO, Status, 527f556842eSJung-uk Kim "while adding external to namespace [%s]", 528f556842eSJung-uk Kim External->Path)); 529f556842eSJung-uk Kim } 530*a7a3b383SJung-uk Kim 531*a7a3b383SJung-uk Kim else switch (External->Type) 532f556842eSJung-uk Kim { 533*a7a3b383SJung-uk Kim case ACPI_TYPE_METHOD: 534*a7a3b383SJung-uk Kim 535f556842eSJung-uk Kim /* For methods, we need to save the argument count */ 536f556842eSJung-uk Kim 537*a7a3b383SJung-uk Kim ObjDesc = AcpiUtCreateInternalObject (ACPI_TYPE_METHOD); 538*a7a3b383SJung-uk Kim ObjDesc->Method.ParamCount = (UINT8) External->Value; 539*a7a3b383SJung-uk Kim Node->Object = ObjDesc; 540*a7a3b383SJung-uk Kim break; 541*a7a3b383SJung-uk Kim 542*a7a3b383SJung-uk Kim case ACPI_TYPE_REGION: 543*a7a3b383SJung-uk Kim 544*a7a3b383SJung-uk Kim /* Regions require a region sub-object */ 545*a7a3b383SJung-uk Kim 546*a7a3b383SJung-uk Kim ObjDesc = AcpiUtCreateInternalObject (ACPI_TYPE_REGION); 547*a7a3b383SJung-uk Kim ObjDesc->Region.Node = Node; 548*a7a3b383SJung-uk Kim Node->Object = ObjDesc; 549*a7a3b383SJung-uk Kim break; 550*a7a3b383SJung-uk Kim 551*a7a3b383SJung-uk Kim default: 552*a7a3b383SJung-uk Kim break; 553f556842eSJung-uk Kim } 554f556842eSJung-uk Kim 555f556842eSJung-uk Kim External = External->Next; 556f556842eSJung-uk Kim } 557f556842eSJung-uk Kim } 558f556842eSJung-uk Kim 559f556842eSJung-uk Kim 560f556842eSJung-uk Kim /******************************************************************************* 561f556842eSJung-uk Kim * 562f556842eSJung-uk Kim * FUNCTION: AcpiDmGetExternalMethodCount 563f556842eSJung-uk Kim * 564f556842eSJung-uk Kim * PARAMETERS: None 565f556842eSJung-uk Kim * 566f556842eSJung-uk Kim * RETURN: The number of control method externals in the external list 567f556842eSJung-uk Kim * 568f556842eSJung-uk Kim * DESCRIPTION: Return the number of method externals that have been generated. 569f556842eSJung-uk Kim * If any control method externals have been found, we must 570f556842eSJung-uk Kim * re-parse the entire definition block with the new information 571f556842eSJung-uk Kim * (number of arguments for the methods.) This is limitation of 572f556842eSJung-uk Kim * AML, we don't know the number of arguments from the control 573f556842eSJung-uk Kim * method invocation itself. 574f556842eSJung-uk Kim * 575f556842eSJung-uk Kim ******************************************************************************/ 576f556842eSJung-uk Kim 577f556842eSJung-uk Kim UINT32 578f556842eSJung-uk Kim AcpiDmGetExternalMethodCount ( 579f556842eSJung-uk Kim void) 580f556842eSJung-uk Kim { 581f556842eSJung-uk Kim ACPI_EXTERNAL_LIST *External = AcpiGbl_ExternalList; 582f556842eSJung-uk Kim UINT32 Count = 0; 583f556842eSJung-uk Kim 584f556842eSJung-uk Kim 585f556842eSJung-uk Kim while (External) 586f556842eSJung-uk Kim { 587f556842eSJung-uk Kim if (External->Type == ACPI_TYPE_METHOD) 588f556842eSJung-uk Kim { 589f556842eSJung-uk Kim Count++; 590f556842eSJung-uk Kim } 591f556842eSJung-uk Kim 592f556842eSJung-uk Kim External = External->Next; 593f556842eSJung-uk Kim } 594f556842eSJung-uk Kim 595f556842eSJung-uk Kim return (Count); 596f556842eSJung-uk Kim } 597f556842eSJung-uk Kim 598f556842eSJung-uk Kim 599f556842eSJung-uk Kim /******************************************************************************* 600f556842eSJung-uk Kim * 601f556842eSJung-uk Kim * FUNCTION: AcpiDmClearExternalList 602f556842eSJung-uk Kim * 603f556842eSJung-uk Kim * PARAMETERS: None 604f556842eSJung-uk Kim * 605f556842eSJung-uk Kim * RETURN: None 606f556842eSJung-uk Kim * 607f556842eSJung-uk Kim * DESCRIPTION: Free the entire External info list 608f556842eSJung-uk Kim * 609f556842eSJung-uk Kim ******************************************************************************/ 610f556842eSJung-uk Kim 611f556842eSJung-uk Kim void 612f556842eSJung-uk Kim AcpiDmClearExternalList ( 613f556842eSJung-uk Kim void) 614f556842eSJung-uk Kim { 615f556842eSJung-uk Kim ACPI_EXTERNAL_LIST *NextExternal; 616f556842eSJung-uk Kim 617f556842eSJung-uk Kim 618f556842eSJung-uk Kim while (AcpiGbl_ExternalList) 619f556842eSJung-uk Kim { 620f556842eSJung-uk Kim NextExternal = AcpiGbl_ExternalList->Next; 621f556842eSJung-uk Kim ACPI_FREE (AcpiGbl_ExternalList->Path); 622f556842eSJung-uk Kim ACPI_FREE (AcpiGbl_ExternalList); 623f556842eSJung-uk Kim AcpiGbl_ExternalList = NextExternal; 624f556842eSJung-uk Kim } 625f556842eSJung-uk Kim } 626f556842eSJung-uk Kim 627f556842eSJung-uk Kim 628f556842eSJung-uk Kim /******************************************************************************* 629f556842eSJung-uk Kim * 630f556842eSJung-uk Kim * FUNCTION: AcpiDmEmitExternals 631f556842eSJung-uk Kim * 632f556842eSJung-uk Kim * PARAMETERS: None 633f556842eSJung-uk Kim * 634f556842eSJung-uk Kim * RETURN: None 635f556842eSJung-uk Kim * 636f556842eSJung-uk Kim * DESCRIPTION: Emit an External() ASL statement for each of the externals in 637f556842eSJung-uk Kim * the global external info list. 638f556842eSJung-uk Kim * 639f556842eSJung-uk Kim ******************************************************************************/ 640f556842eSJung-uk Kim 641f556842eSJung-uk Kim void 642f556842eSJung-uk Kim AcpiDmEmitExternals ( 643f556842eSJung-uk Kim void) 644f556842eSJung-uk Kim { 645f556842eSJung-uk Kim ACPI_EXTERNAL_LIST *NextExternal; 646f556842eSJung-uk Kim 647f556842eSJung-uk Kim 648f556842eSJung-uk Kim if (!AcpiGbl_ExternalList) 649f556842eSJung-uk Kim { 650f556842eSJung-uk Kim return; 651f556842eSJung-uk Kim } 652f556842eSJung-uk Kim 653f556842eSJung-uk Kim /* 654f556842eSJung-uk Kim * Walk the list of externals (unresolved references) 655f556842eSJung-uk Kim * found during the AML parsing 656f556842eSJung-uk Kim */ 657f556842eSJung-uk Kim while (AcpiGbl_ExternalList) 658f556842eSJung-uk Kim { 659f556842eSJung-uk Kim AcpiOsPrintf (" External (%s%s", 660f556842eSJung-uk Kim AcpiGbl_ExternalList->Path, 661f556842eSJung-uk Kim AcpiDmGetObjectTypeName (AcpiGbl_ExternalList->Type)); 662f556842eSJung-uk Kim 663f556842eSJung-uk Kim if (AcpiGbl_ExternalList->Type == ACPI_TYPE_METHOD) 664f556842eSJung-uk Kim { 665a88e22b7SJung-uk Kim AcpiOsPrintf (") // %u Arguments\n", 666f556842eSJung-uk Kim AcpiGbl_ExternalList->Value); 667f556842eSJung-uk Kim } 668f556842eSJung-uk Kim else 669f556842eSJung-uk Kim { 670f556842eSJung-uk Kim AcpiOsPrintf (")\n"); 671f556842eSJung-uk Kim } 672f556842eSJung-uk Kim 673f556842eSJung-uk Kim /* Free this external info block and move on to next external */ 674f556842eSJung-uk Kim 675f556842eSJung-uk Kim NextExternal = AcpiGbl_ExternalList->Next; 676f556842eSJung-uk Kim if (AcpiGbl_ExternalList->Flags & ACPI_IPATH_ALLOCATED) 677f556842eSJung-uk Kim { 678f556842eSJung-uk Kim ACPI_FREE (AcpiGbl_ExternalList->InternalPath); 679f556842eSJung-uk Kim } 680f556842eSJung-uk Kim 681f556842eSJung-uk Kim ACPI_FREE (AcpiGbl_ExternalList->Path); 682f556842eSJung-uk Kim ACPI_FREE (AcpiGbl_ExternalList); 683f556842eSJung-uk Kim AcpiGbl_ExternalList = NextExternal; 684f556842eSJung-uk Kim } 685f556842eSJung-uk Kim 686f556842eSJung-uk Kim AcpiOsPrintf ("\n"); 687f556842eSJung-uk Kim } 688f556842eSJung-uk Kim 689