diff --git a/source/components/namespace/nspredef.c b/source/components/namespace/nspredef.c index 19662680125c..3a61aa3666e8 100644 --- a/source/components/namespace/nspredef.c +++ b/source/components/namespace/nspredef.c @@ -1,1243 +1,1243 @@ /****************************************************************************** * * Module Name: nspredef - Validation of ACPI predefined methods and objects * *****************************************************************************/ /* * Copyright (C) 2000 - 2012, Intel Corp. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions, and the following disclaimer, * without modification. * 2. Redistributions in binary form must reproduce at minimum a disclaimer * substantially similar to the "NO WARRANTY" disclaimer below * ("Disclaimer") and any redistribution must be conditioned upon * including a substantially similar Disclaimer requirement for further * binary redistribution. * 3. Neither the names of the above-listed copyright holders nor the names * of any contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * Alternatively, this software may be distributed under the terms of the * GNU General Public License ("GPL") version 2 as published by the Free * Software Foundation. * * NO WARRANTY * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGES. */ #define ACPI_CREATE_PREDEFINED_TABLE #include "acpi.h" #include "accommon.h" #include "acnamesp.h" #include "acpredef.h" #define _COMPONENT ACPI_NAMESPACE ACPI_MODULE_NAME ("nspredef") /******************************************************************************* * * This module validates predefined ACPI objects that appear in the namespace, * at the time they are evaluated (via AcpiEvaluateObject). The purpose of this * validation is to detect problems with BIOS-exposed predefined ACPI objects * before the results are returned to the ACPI-related drivers. * * There are several areas that are validated: * * 1) The number of input arguments as defined by the method/object in the * ASL is validated against the ACPI specification. * 2) The type of the return object (if any) is validated against the ACPI * specification. * 3) For returned package objects, the count of package elements is * validated, as well as the type of each package element. Nested * packages are supported. * * For any problems found, a warning message is issued. * ******************************************************************************/ /* Local prototypes */ static ACPI_STATUS AcpiNsCheckPackage ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT **ReturnObjectPtr); static ACPI_STATUS AcpiNsCheckPackageList ( ACPI_PREDEFINED_DATA *Data, const ACPI_PREDEFINED_INFO *Package, ACPI_OPERAND_OBJECT **Elements, UINT32 Count); static ACPI_STATUS AcpiNsCheckPackageElements ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT **Elements, UINT8 Type1, UINT32 Count1, UINT8 Type2, UINT32 Count2, UINT32 StartIndex); static ACPI_STATUS AcpiNsCheckObjectType ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT **ReturnObjectPtr, UINT32 ExpectedBtypes, UINT32 PackageIndex); static ACPI_STATUS AcpiNsCheckReference ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT *ReturnObject); static void AcpiNsGetExpectedTypes ( char *Buffer, UINT32 ExpectedBtypes); /* * Names for the types that can be returned by the predefined objects. * Used for warning messages. Must be in the same order as the ACPI_RTYPEs */ static const char *AcpiRtypeNames[] = { "/Integer", "/String", "/Buffer", "/Package", "/Reference", }; /******************************************************************************* * * FUNCTION: AcpiNsCheckPredefinedNames * * PARAMETERS: Node - Namespace node for the method/object * UserParamCount - Number of parameters actually passed * ReturnStatus - Status from the object evaluation * ReturnObjectPtr - Pointer to the object returned from the * evaluation of a method or object * * RETURN: Status * * DESCRIPTION: Check an ACPI name for a match in the predefined name list. * ******************************************************************************/ ACPI_STATUS AcpiNsCheckPredefinedNames ( ACPI_NAMESPACE_NODE *Node, UINT32 UserParamCount, ACPI_STATUS ReturnStatus, ACPI_OPERAND_OBJECT **ReturnObjectPtr) { ACPI_OPERAND_OBJECT *ReturnObject = *ReturnObjectPtr; ACPI_STATUS Status = AE_OK; const ACPI_PREDEFINED_INFO *Predefined; char *Pathname; ACPI_PREDEFINED_DATA *Data; /* Match the name for this method/object against the predefined list */ Predefined = AcpiNsCheckForPredefinedName (Node); /* Get the full pathname to the object, for use in warning messages */ Pathname = AcpiNsGetExternalPathname (Node); if (!Pathname) { return (AE_OK); /* Could not get pathname, ignore */ } /* * Check that the parameter count for this method matches the ASL * definition. For predefined names, ensure that both the caller and * the method itself are in accordance with the ACPI specification. */ AcpiNsCheckParameterCount (Pathname, Node, UserParamCount, Predefined); /* If not a predefined name, we cannot validate the return object */ if (!Predefined) { goto Cleanup; } /* * If the method failed or did not actually return an object, we cannot * validate the return object */ if ((ReturnStatus != AE_OK) && (ReturnStatus != AE_CTRL_RETURN_VALUE)) { goto Cleanup; } /* * If there is no return value, check if we require a return value for * this predefined name. Either one return value is expected, or none, * for both methods and other objects. * * Exit now if there is no return object. Warning if one was expected. */ if (!ReturnObject) { if ((Predefined->Info.ExpectedBtypes) && (!(Predefined->Info.ExpectedBtypes & ACPI_RTYPE_NONE))) { ACPI_WARN_PREDEFINED ((AE_INFO, Pathname, ACPI_WARN_ALWAYS, "Missing expected return value")); Status = AE_AML_NO_RETURN_VALUE; } goto Cleanup; } /* * Return value validation and possible repair. * * 1) Don't perform return value validation/repair if this feature * has been disabled via a global option. * * 2) We have a return value, but if one wasn't expected, just exit, * this is not a problem. For example, if the "Implicit Return" * feature is enabled, methods will always return a value. * * 3) If the return value can be of any type, then we cannot perform * any validation, just exit. */ if (AcpiGbl_DisableAutoRepair || (!Predefined->Info.ExpectedBtypes) || (Predefined->Info.ExpectedBtypes == ACPI_RTYPE_ALL)) { goto Cleanup; } /* Create the parameter data block for object validation */ Data = ACPI_ALLOCATE_ZEROED (sizeof (ACPI_PREDEFINED_DATA)); if (!Data) { goto Cleanup; } Data->Predefined = Predefined; Data->Node = Node; Data->NodeFlags = Node->Flags; Data->Pathname = Pathname; /* * Check that the type of the main return object is what is expected * for this predefined name */ Status = AcpiNsCheckObjectType (Data, ReturnObjectPtr, Predefined->Info.ExpectedBtypes, ACPI_NOT_PACKAGE_ELEMENT); if (ACPI_FAILURE (Status)) { goto Exit; } /* * For returned Package objects, check the type of all sub-objects. * Note: Package may have been newly created by call above. */ if ((*ReturnObjectPtr)->Common.Type == ACPI_TYPE_PACKAGE) { Data->ParentPackage = *ReturnObjectPtr; Status = AcpiNsCheckPackage (Data, ReturnObjectPtr); if (ACPI_FAILURE (Status)) { goto Exit; } } /* * The return object was OK, or it was successfully repaired above. * Now make some additional checks such as verifying that package * objects are sorted correctly (if required) or buffer objects have * the correct data width (bytes vs. dwords). These repairs are * performed on a per-name basis, i.e., the code is specific to * particular predefined names. */ Status = AcpiNsComplexRepairs (Data, Node, Status, ReturnObjectPtr); Exit: /* * If the object validation failed or if we successfully repaired one * or more objects, mark the parent node to suppress further warning * messages during the next evaluation of the same method/object. */ if (ACPI_FAILURE (Status) || (Data->Flags & ACPI_OBJECT_REPAIRED)) { Node->Flags |= ANOBJ_EVALUATED; } ACPI_FREE (Data); Cleanup: ACPI_FREE (Pathname); return (Status); } /******************************************************************************* * * FUNCTION: AcpiNsCheckParameterCount * * PARAMETERS: Pathname - Full pathname to the node (for error msgs) * Node - Namespace node for the method/object * UserParamCount - Number of args passed in by the caller * Predefined - Pointer to entry in predefined name table * * RETURN: None * * DESCRIPTION: Check that the declared (in ASL/AML) parameter count for a * predefined name is what is expected (i.e., what is defined in * the ACPI specification for this predefined name.) * ******************************************************************************/ void AcpiNsCheckParameterCount ( char *Pathname, ACPI_NAMESPACE_NODE *Node, UINT32 UserParamCount, const ACPI_PREDEFINED_INFO *Predefined) { UINT32 ParamCount; UINT32 RequiredParamsCurrent; UINT32 RequiredParamsOld; /* Methods have 0-7 parameters. All other types have zero. */ ParamCount = 0; if (Node->Type == ACPI_TYPE_METHOD) { ParamCount = Node->Object->Method.ParamCount; } if (!Predefined) { /* * Check the parameter count for non-predefined methods/objects. * * Warning if too few or too many arguments have been passed by the * caller. An incorrect number of arguments may not cause the method * to fail. However, the method will fail if there are too few * arguments and the method attempts to use one of the missing ones. */ if (UserParamCount < ParamCount) { ACPI_WARN_PREDEFINED ((AE_INFO, Pathname, ACPI_WARN_ALWAYS, "Insufficient arguments - needs %u, found %u", ParamCount, UserParamCount)); } else if (UserParamCount > ParamCount) { ACPI_WARN_PREDEFINED ((AE_INFO, Pathname, ACPI_WARN_ALWAYS, "Excess arguments - needs %u, found %u", ParamCount, UserParamCount)); } return; } /* * Validate the user-supplied parameter count. * Allow two different legal argument counts (_SCP, etc.) */ RequiredParamsCurrent = Predefined->Info.ParamCount & 0x0F; RequiredParamsOld = Predefined->Info.ParamCount >> 4; if (UserParamCount != ACPI_UINT32_MAX) { if ((UserParamCount != RequiredParamsCurrent) && (UserParamCount != RequiredParamsOld)) { ACPI_WARN_PREDEFINED ((AE_INFO, Pathname, ACPI_WARN_ALWAYS, "Parameter count mismatch - " "caller passed %u, ACPI requires %u", UserParamCount, RequiredParamsCurrent)); } } /* * Check that the ASL-defined parameter count is what is expected for * this predefined name (parameter count as defined by the ACPI * specification) */ if ((ParamCount != RequiredParamsCurrent) && (ParamCount != RequiredParamsOld)) { ACPI_WARN_PREDEFINED ((AE_INFO, Pathname, Node->Flags, "Parameter count mismatch - ASL declared %u, ACPI requires %u", ParamCount, RequiredParamsCurrent)); } } /******************************************************************************* * * FUNCTION: AcpiNsCheckForPredefinedName * * PARAMETERS: Node - Namespace node for the method/object * * RETURN: Pointer to entry in predefined table. NULL indicates not found. * * DESCRIPTION: Check an object name against the predefined object list. * ******************************************************************************/ const ACPI_PREDEFINED_INFO * AcpiNsCheckForPredefinedName ( ACPI_NAMESPACE_NODE *Node) { const ACPI_PREDEFINED_INFO *ThisName; /* Quick check for a predefined name, first character must be underscore */ if (Node->Name.Ascii[0] != '_') { return (NULL); } /* Search info table for a predefined method/object name */ ThisName = PredefinedNames; while (ThisName->Info.Name[0]) { if (ACPI_COMPARE_NAME (Node->Name.Ascii, ThisName->Info.Name)) { return (ThisName); } /* * Skip next entry in the table if this name returns a Package * (next entry contains the package info) */ if (ThisName->Info.ExpectedBtypes & ACPI_RTYPE_PACKAGE) { ThisName++; } ThisName++; } return (NULL); /* Not found */ } /******************************************************************************* * * FUNCTION: AcpiNsCheckPackage * * PARAMETERS: Data - Pointer to validation data structure * ReturnObjectPtr - Pointer to the object returned from the * evaluation of a method or object * * RETURN: Status * * DESCRIPTION: Check a returned package object for the correct count and * correct type of all sub-objects. * ******************************************************************************/ static ACPI_STATUS AcpiNsCheckPackage ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT **ReturnObjectPtr) { ACPI_OPERAND_OBJECT *ReturnObject = *ReturnObjectPtr; const ACPI_PREDEFINED_INFO *Package; ACPI_OPERAND_OBJECT **Elements; ACPI_STATUS Status = AE_OK; UINT32 ExpectedCount; UINT32 Count; UINT32 i; ACPI_FUNCTION_NAME (NsCheckPackage); /* The package info for this name is in the next table entry */ Package = Data->Predefined + 1; ACPI_DEBUG_PRINT ((ACPI_DB_NAMES, "%s Validating return Package of Type %X, Count %X\n", Data->Pathname, Package->RetInfo.Type, ReturnObject->Package.Count)); /* * For variable-length Packages, we can safely remove all embedded * and trailing NULL package elements */ AcpiNsRemoveNullElements (Data, Package->RetInfo.Type, ReturnObject); /* Extract package count and elements array */ Elements = ReturnObject->Package.Elements; Count = ReturnObject->Package.Count; /* The package must have at least one element, else invalid */ if (!Count) { ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Return Package has no elements (empty)")); return (AE_AML_OPERAND_VALUE); } /* * Decode the type of the expected package contents * * PTYPE1 packages contain no subpackages * PTYPE2 packages contain sub-packages */ switch (Package->RetInfo.Type) { case ACPI_PTYPE1_FIXED: /* * The package count is fixed and there are no sub-packages * * If package is too small, exit. * If package is larger than expected, issue warning but continue */ ExpectedCount = Package->RetInfo.Count1 + Package->RetInfo.Count2; if (Count < ExpectedCount) { goto PackageTooSmall; } else if (Count > ExpectedCount) { ACPI_DEBUG_PRINT ((ACPI_DB_REPAIR, "%s: Return Package is larger than needed - " "found %u, expected %u\n", Data->Pathname, Count, ExpectedCount)); } /* Validate all elements of the returned package */ Status = AcpiNsCheckPackageElements (Data, Elements, Package->RetInfo.ObjectType1, Package->RetInfo.Count1, Package->RetInfo.ObjectType2, Package->RetInfo.Count2, 0); break; case ACPI_PTYPE1_VAR: /* * The package count is variable, there are no sub-packages, and all * elements must be of the same type */ for (i = 0; i < Count; i++) { Status = AcpiNsCheckObjectType (Data, Elements, Package->RetInfo.ObjectType1, i); if (ACPI_FAILURE (Status)) { return (Status); } Elements++; } break; case ACPI_PTYPE1_OPTION: /* * The package count is variable, there are no sub-packages. There are * a fixed number of required elements, and a variable number of * optional elements. * * Check if package is at least as large as the minimum required */ ExpectedCount = Package->RetInfo3.Count; if (Count < ExpectedCount) { goto PackageTooSmall; } /* Variable number of sub-objects */ for (i = 0; i < Count; i++) { if (i < Package->RetInfo3.Count) { /* These are the required package elements (0, 1, or 2) */ Status = AcpiNsCheckObjectType (Data, Elements, Package->RetInfo3.ObjectType[i], i); if (ACPI_FAILURE (Status)) { return (Status); } } else { /* These are the optional package elements */ Status = AcpiNsCheckObjectType (Data, Elements, Package->RetInfo3.TailObjectType, i); if (ACPI_FAILURE (Status)) { return (Status); } } Elements++; } break; case ACPI_PTYPE2_REV_FIXED: /* First element is the (Integer) revision */ Status = AcpiNsCheckObjectType (Data, Elements, ACPI_RTYPE_INTEGER, 0); if (ACPI_FAILURE (Status)) { return (Status); } Elements++; Count--; /* Examine the sub-packages */ Status = AcpiNsCheckPackageList (Data, Package, Elements, Count); break; case ACPI_PTYPE2_PKG_COUNT: /* First element is the (Integer) count of sub-packages to follow */ Status = AcpiNsCheckObjectType (Data, Elements, ACPI_RTYPE_INTEGER, 0); if (ACPI_FAILURE (Status)) { return (Status); } /* * Count cannot be larger than the parent package length, but allow it * to be smaller. The >= accounts for the Integer above. */ ExpectedCount = (UINT32) (*Elements)->Integer.Value; if (ExpectedCount >= Count) { goto PackageTooSmall; } Count = ExpectedCount; Elements++; /* Examine the sub-packages */ Status = AcpiNsCheckPackageList (Data, Package, Elements, Count); break; case ACPI_PTYPE2: case ACPI_PTYPE2_FIXED: case ACPI_PTYPE2_MIN: case ACPI_PTYPE2_COUNT: case ACPI_PTYPE2_FIX_VAR: /* * These types all return a single Package that consists of a * variable number of sub-Packages. * * First, ensure that the first element is a sub-Package. If not, * the BIOS may have incorrectly returned the object as a single * package instead of a Package of Packages (a common error if * there is only one entry). We may be able to repair this by * wrapping the returned Package with a new outer Package. */ if (*Elements && ((*Elements)->Common.Type != ACPI_TYPE_PACKAGE)) { /* Create the new outer package and populate it */ - Status = AcpiNsRepairPackageList (Data, ReturnObjectPtr); + Status = AcpiNsWrapWithPackage (Data, *Elements, ReturnObjectPtr); if (ACPI_FAILURE (Status)) { return (Status); } /* Update locals to point to the new package (of 1 element) */ ReturnObject = *ReturnObjectPtr; Elements = ReturnObject->Package.Elements; Count = 1; } /* Examine the sub-packages */ Status = AcpiNsCheckPackageList (Data, Package, Elements, Count); break; default: /* Should not get here if predefined info table is correct */ ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Invalid internal return type in table entry: %X", Package->RetInfo.Type)); return (AE_AML_INTERNAL); } return (Status); PackageTooSmall: /* Error exit for the case with an incorrect package count */ ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Return Package is too small - found %u elements, expected %u", Count, ExpectedCount)); return (AE_AML_OPERAND_VALUE); } /******************************************************************************* * * FUNCTION: AcpiNsCheckPackageList * * PARAMETERS: Data - Pointer to validation data structure * Package - Pointer to package-specific info for method * Elements - Element list of parent package. All elements * of this list should be of type Package. * Count - Count of subpackages * * RETURN: Status * * DESCRIPTION: Examine a list of subpackages * ******************************************************************************/ static ACPI_STATUS AcpiNsCheckPackageList ( ACPI_PREDEFINED_DATA *Data, const ACPI_PREDEFINED_INFO *Package, ACPI_OPERAND_OBJECT **Elements, UINT32 Count) { ACPI_OPERAND_OBJECT *SubPackage; ACPI_OPERAND_OBJECT **SubElements; ACPI_STATUS Status; UINT32 ExpectedCount; UINT32 i; UINT32 j; /* * Validate each sub-Package in the parent Package * * NOTE: assumes list of sub-packages contains no NULL elements. * Any NULL elements should have been removed by earlier call * to AcpiNsRemoveNullElements. */ for (i = 0; i < Count; i++) { SubPackage = *Elements; SubElements = SubPackage->Package.Elements; Data->ParentPackage = SubPackage; /* Each sub-object must be of type Package */ Status = AcpiNsCheckObjectType (Data, &SubPackage, ACPI_RTYPE_PACKAGE, i); if (ACPI_FAILURE (Status)) { return (Status); } /* Examine the different types of expected sub-packages */ Data->ParentPackage = SubPackage; switch (Package->RetInfo.Type) { case ACPI_PTYPE2: case ACPI_PTYPE2_PKG_COUNT: case ACPI_PTYPE2_REV_FIXED: /* Each subpackage has a fixed number of elements */ ExpectedCount = Package->RetInfo.Count1 + Package->RetInfo.Count2; if (SubPackage->Package.Count < ExpectedCount) { goto PackageTooSmall; } Status = AcpiNsCheckPackageElements (Data, SubElements, Package->RetInfo.ObjectType1, Package->RetInfo.Count1, Package->RetInfo.ObjectType2, Package->RetInfo.Count2, 0); if (ACPI_FAILURE (Status)) { return (Status); } break; case ACPI_PTYPE2_FIX_VAR: /* * Each subpackage has a fixed number of elements and an * optional element */ ExpectedCount = Package->RetInfo.Count1 + Package->RetInfo.Count2; if (SubPackage->Package.Count < ExpectedCount) { goto PackageTooSmall; } Status = AcpiNsCheckPackageElements (Data, SubElements, Package->RetInfo.ObjectType1, Package->RetInfo.Count1, Package->RetInfo.ObjectType2, SubPackage->Package.Count - Package->RetInfo.Count1, 0); if (ACPI_FAILURE (Status)) { return (Status); } break; case ACPI_PTYPE2_FIXED: /* Each sub-package has a fixed length */ ExpectedCount = Package->RetInfo2.Count; if (SubPackage->Package.Count < ExpectedCount) { goto PackageTooSmall; } /* Check the type of each sub-package element */ for (j = 0; j < ExpectedCount; j++) { Status = AcpiNsCheckObjectType (Data, &SubElements[j], Package->RetInfo2.ObjectType[j], j); if (ACPI_FAILURE (Status)) { return (Status); } } break; case ACPI_PTYPE2_MIN: /* Each sub-package has a variable but minimum length */ ExpectedCount = Package->RetInfo.Count1; if (SubPackage->Package.Count < ExpectedCount) { goto PackageTooSmall; } /* Check the type of each sub-package element */ Status = AcpiNsCheckPackageElements (Data, SubElements, Package->RetInfo.ObjectType1, SubPackage->Package.Count, 0, 0, 0); if (ACPI_FAILURE (Status)) { return (Status); } break; case ACPI_PTYPE2_COUNT: /* * First element is the (Integer) count of elements, including * the count field (the ACPI name is NumElements) */ Status = AcpiNsCheckObjectType (Data, SubElements, ACPI_RTYPE_INTEGER, 0); if (ACPI_FAILURE (Status)) { return (Status); } /* * Make sure package is large enough for the Count and is * is as large as the minimum size */ ExpectedCount = (UINT32) (*SubElements)->Integer.Value; if (SubPackage->Package.Count < ExpectedCount) { goto PackageTooSmall; } if (SubPackage->Package.Count < Package->RetInfo.Count1) { ExpectedCount = Package->RetInfo.Count1; goto PackageTooSmall; } if (ExpectedCount == 0) { /* * Either the NumEntries element was originally zero or it was * a NULL element and repaired to an Integer of value zero. * In either case, repair it by setting NumEntries to be the * actual size of the subpackage. */ ExpectedCount = SubPackage->Package.Count; (*SubElements)->Integer.Value = ExpectedCount; } /* Check the type of each sub-package element */ Status = AcpiNsCheckPackageElements (Data, (SubElements + 1), Package->RetInfo.ObjectType1, (ExpectedCount - 1), 0, 0, 1); if (ACPI_FAILURE (Status)) { return (Status); } break; default: /* Should not get here, type was validated by caller */ return (AE_AML_INTERNAL); } Elements++; } return (AE_OK); PackageTooSmall: /* The sub-package count was smaller than required */ ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Return Sub-Package[%u] is too small - found %u elements, expected %u", i, SubPackage->Package.Count, ExpectedCount)); return (AE_AML_OPERAND_VALUE); } /******************************************************************************* * * FUNCTION: AcpiNsCheckPackageElements * * PARAMETERS: Data - Pointer to validation data structure * Elements - Pointer to the package elements array * Type1 - Object type for first group * Count1 - Count for first group * Type2 - Object type for second group * Count2 - Count for second group * StartIndex - Start of the first group of elements * * RETURN: Status * * DESCRIPTION: Check that all elements of a package are of the correct object * type. Supports up to two groups of different object types. * ******************************************************************************/ static ACPI_STATUS AcpiNsCheckPackageElements ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT **Elements, UINT8 Type1, UINT32 Count1, UINT8 Type2, UINT32 Count2, UINT32 StartIndex) { ACPI_OPERAND_OBJECT **ThisElement = Elements; ACPI_STATUS Status; UINT32 i; /* * Up to two groups of package elements are supported by the data * structure. All elements in each group must be of the same type. * The second group can have a count of zero. */ for (i = 0; i < Count1; i++) { Status = AcpiNsCheckObjectType (Data, ThisElement, Type1, i + StartIndex); if (ACPI_FAILURE (Status)) { return (Status); } ThisElement++; } for (i = 0; i < Count2; i++) { Status = AcpiNsCheckObjectType (Data, ThisElement, Type2, (i + Count1 + StartIndex)); if (ACPI_FAILURE (Status)) { return (Status); } ThisElement++; } return (AE_OK); } /******************************************************************************* * * FUNCTION: AcpiNsCheckObjectType * * PARAMETERS: Data - Pointer to validation data structure * ReturnObjectPtr - Pointer to the object returned from the * evaluation of a method or object * ExpectedBtypes - Bitmap of expected return type(s) * PackageIndex - Index of object within parent package (if * applicable - ACPI_NOT_PACKAGE_ELEMENT * otherwise) * * RETURN: Status * * DESCRIPTION: Check the type of the return object against the expected object * type(s). Use of Btype allows multiple expected object types. * ******************************************************************************/ static ACPI_STATUS AcpiNsCheckObjectType ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT **ReturnObjectPtr, UINT32 ExpectedBtypes, UINT32 PackageIndex) { ACPI_OPERAND_OBJECT *ReturnObject = *ReturnObjectPtr; ACPI_STATUS Status = AE_OK; UINT32 ReturnBtype; char TypeBuffer[48]; /* Room for 5 types */ /* * If we get a NULL ReturnObject here, it is a NULL package element. * Since all extraneous NULL package elements were removed earlier by a * call to AcpiNsRemoveNullElements, this is an unexpected NULL element. * We will attempt to repair it. */ if (!ReturnObject) { Status = AcpiNsRepairNullElement (Data, ExpectedBtypes, PackageIndex, ReturnObjectPtr); if (ACPI_SUCCESS (Status)) { return (AE_OK); /* Repair was successful */ } goto TypeErrorExit; } /* A Namespace node should not get here, but make sure */ if (ACPI_GET_DESCRIPTOR_TYPE (ReturnObject) == ACPI_DESC_TYPE_NAMED) { ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Invalid return type - Found a Namespace node [%4.4s] type %s", ReturnObject->Node.Name.Ascii, AcpiUtGetTypeName (ReturnObject->Node.Type))); return (AE_AML_OPERAND_TYPE); } /* * Convert the object type (ACPI_TYPE_xxx) to a bitmapped object type. * The bitmapped type allows multiple possible return types. * * Note, the cases below must handle all of the possible types returned * from all of the predefined names (including elements of returned * packages) */ switch (ReturnObject->Common.Type) { case ACPI_TYPE_INTEGER: ReturnBtype = ACPI_RTYPE_INTEGER; break; case ACPI_TYPE_BUFFER: ReturnBtype = ACPI_RTYPE_BUFFER; break; case ACPI_TYPE_STRING: ReturnBtype = ACPI_RTYPE_STRING; break; case ACPI_TYPE_PACKAGE: ReturnBtype = ACPI_RTYPE_PACKAGE; break; case ACPI_TYPE_LOCAL_REFERENCE: ReturnBtype = ACPI_RTYPE_REFERENCE; break; default: /* Not one of the supported objects, must be incorrect */ goto TypeErrorExit; } /* Is the object one of the expected types? */ if (ReturnBtype & ExpectedBtypes) { /* For reference objects, check that the reference type is correct */ if (ReturnObject->Common.Type == ACPI_TYPE_LOCAL_REFERENCE) { Status = AcpiNsCheckReference (Data, ReturnObject); } return (Status); } /* Type mismatch -- attempt repair of the returned object */ Status = AcpiNsRepairObject (Data, ExpectedBtypes, PackageIndex, ReturnObjectPtr); if (ACPI_SUCCESS (Status)) { return (AE_OK); /* Repair was successful */ } TypeErrorExit: /* Create a string with all expected types for this predefined object */ AcpiNsGetExpectedTypes (TypeBuffer, ExpectedBtypes); if (PackageIndex == ACPI_NOT_PACKAGE_ELEMENT) { ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Return type mismatch - found %s, expected %s", AcpiUtGetObjectTypeName (ReturnObject), TypeBuffer)); } else { ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Return Package type mismatch at index %u - " "found %s, expected %s", PackageIndex, AcpiUtGetObjectTypeName (ReturnObject), TypeBuffer)); } return (AE_AML_OPERAND_TYPE); } /******************************************************************************* * * FUNCTION: AcpiNsCheckReference * * PARAMETERS: Data - Pointer to validation data structure * ReturnObject - Object returned from the evaluation of a * method or object * * RETURN: Status * * DESCRIPTION: Check a returned reference object for the correct reference * type. The only reference type that can be returned from a * predefined method is a named reference. All others are invalid. * ******************************************************************************/ static ACPI_STATUS AcpiNsCheckReference ( ACPI_PREDEFINED_DATA *Data, ACPI_OPERAND_OBJECT *ReturnObject) { /* * Check the reference object for the correct reference type (opcode). * The only type of reference that can be converted to an ACPI_OBJECT is * a reference to a named object (reference class: NAME) */ if (ReturnObject->Reference.Class == ACPI_REFCLASS_NAME) { return (AE_OK); } ACPI_WARN_PREDEFINED ((AE_INFO, Data->Pathname, Data->NodeFlags, "Return type mismatch - unexpected reference object type [%s] %2.2X", AcpiUtGetReferenceName (ReturnObject), ReturnObject->Reference.Class)); return (AE_AML_OPERAND_TYPE); } /******************************************************************************* * * FUNCTION: AcpiNsGetExpectedTypes * * PARAMETERS: Buffer - Pointer to where the string is returned * ExpectedBtypes - Bitmap of expected return type(s) * * RETURN: Buffer is populated with type names. * * DESCRIPTION: Translate the expected types bitmap into a string of ascii * names of expected types, for use in warning messages. * ******************************************************************************/ static void AcpiNsGetExpectedTypes ( char *Buffer, UINT32 ExpectedBtypes) { UINT32 ThisRtype; UINT32 i; UINT32 j; j = 1; Buffer[0] = 0; ThisRtype = ACPI_RTYPE_INTEGER; for (i = 0; i < ACPI_NUM_RTYPES; i++) { /* If one of the expected types, concatenate the name of this type */ if (ExpectedBtypes & ThisRtype) { ACPI_STRCAT (Buffer, &AcpiRtypeNames[i][j]); j = 0; /* Use name separator from now on */ } ThisRtype <<= 1; /* Next Rtype */ } } diff --git a/source/components/namespace/nsrepair.c b/source/components/namespace/nsrepair.c index d820834e881e..be9d3e889db8 100644 --- a/source/components/namespace/nsrepair.c +++ b/source/components/namespace/nsrepair.c @@ -1,802 +1,752 @@ /****************************************************************************** * * Module Name: nsrepair - Repair for objects returned by predefined methods * *****************************************************************************/ /* * Copyright (C) 2000 - 2012, Intel Corp. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions, and the following disclaimer, * without modification. * 2. Redistributions in binary form must reproduce at minimum a disclaimer * substantially similar to the "NO WARRANTY" disclaimer below * ("Disclaimer") and any redistribution must be conditioned upon * including a substantially similar Disclaimer requirement for further * binary redistribution. * 3. Neither the names of the above-listed copyright holders nor the names * of any contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * Alternatively, this software may be distributed under the terms of the * GNU General Public License ("GPL") version 2 as published by the Free * Software Foundation. * * NO WARRANTY * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGES. */ #define __NSREPAIR_C__ #include "acpi.h" #include "accommon.h" #include "acnamesp.h" #include "acinterp.h" #include "acpredef.h" #define _COMPONENT ACPI_NAMESPACE ACPI_MODULE_NAME ("nsrepair") /******************************************************************************* * * This module attempts to repair or convert objects returned by the * predefined methods to an object type that is expected, as per the ACPI * specification. The need for this code is dictated by the many machines that * return incorrect types for the standard predefined methods. Performing these * conversions here, in one place, eliminates the need for individual ACPI * device drivers to do the same. Note: Most of these conversions are different * than the internal object conversion routines used for implicit object * conversion. * * The following conversions can be performed as necessary: * * Integer -> String * Integer -> Buffer * String -> Integer * String -> Buffer * Buffer -> Integer * Buffer -> String * Buffer -> Package of Integers * Package -> Package of one Package + * An incorrect standalone object is wrapped with required outer package * * Additional possible repairs: - * * Required package elements that are NULL replaced by Integer/String/Buffer - * Incorrect standalone package wrapped with required outer package * ******************************************************************************/ /* Local prototypes */ static ACPI_STATUS AcpiNsConvertToInteger ( ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ReturnObject); static ACPI_STATUS AcpiNsConvertToString ( ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ReturnObject); static ACPI_STATUS AcpiNsConvertToBuffer ( ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ReturnObject); -static ACPI_STATUS -AcpiNsConvertToPackage ( - ACPI_OPERAND_OBJECT *OriginalObject, - ACPI_OPERAND_OBJECT **ReturnObject); - /******************************************************************************* * * FUNCTION: AcpiNsRepairObject * * PARAMETERS: Data - Pointer to validation data structure * ExpectedBtypes - Object types expected * PackageIndex - Index of object within parent package (if * applicable - ACPI_NOT_PACKAGE_ELEMENT * otherwise) * ReturnObjectPtr - Pointer to the object returned from the * evaluation of a method or object * * RETURN: Status. AE_OK if repair was successful. * * DESCRIPTION: Attempt to repair/convert a return object of a type that was * not expected. * ******************************************************************************/ ACPI_STATUS AcpiNsRepairObject ( ACPI_PREDEFINED_DATA *Data, UINT32 ExpectedBtypes, UINT32 PackageIndex, ACPI_OPERAND_OBJECT **ReturnObjectPtr) { ACPI_OPERAND_OBJECT *ReturnObject = *ReturnObjectPtr; ACPI_OPERAND_OBJECT *NewObject; ACPI_STATUS Status; ACPI_FUNCTION_NAME (NsRepairObject); /* * At this point, we know that the type of the returned object was not * one of the expected types for this predefined name. Attempt to * repair the object by converting it to one of the expected object * types for this predefined name. */ if (ExpectedBtypes & ACPI_RTYPE_INTEGER) { Status = AcpiNsConvertToInteger (ReturnObject, &NewObject); if (ACPI_SUCCESS (Status)) { goto ObjectRepaired; } } if (ExpectedBtypes & ACPI_RTYPE_STRING) { Status = AcpiNsConvertToString (ReturnObject, &NewObject); if (ACPI_SUCCESS (Status)) { goto ObjectRepaired; } } if (ExpectedBtypes & ACPI_RTYPE_BUFFER) { Status = AcpiNsConvertToBuffer (ReturnObject, &NewObject); if (ACPI_SUCCESS (Status)) { goto ObjectRepaired; } } if (ExpectedBtypes & ACPI_RTYPE_PACKAGE) { - Status = AcpiNsConvertToPackage (ReturnObject, &NewObject); + /* + * A package is expected. We will wrap the existing object with a + * new package object. It is often the case that if a variable-length + * package is required, but there is only a single object needed, the + * BIOS will return that object instead of wrapping it with a Package + * object. Note: after the wrapping, the package will be validated + * for correct contents (expected object type or types). + */ + Status = AcpiNsWrapWithPackage (Data, ReturnObject, &NewObject); if (ACPI_SUCCESS (Status)) { - goto ObjectRepaired; + /* + * The original object just had its reference count + * incremented for being inserted into the new package. + */ + *ReturnObjectPtr = NewObject; /* New Package object */ + Data->Flags |= ACPI_OBJECT_REPAIRED; + return (AE_OK); } } /* We cannot repair this object */ return (AE_AML_OPERAND_TYPE); ObjectRepaired: /* Object was successfully repaired */ - /* - * If the original object is a package element, we need to: - * 1. Set the reference count of the new object to match the - * reference count of the old object. - * 2. Decrement the reference count of the original object. - */ if (PackageIndex != ACPI_NOT_PACKAGE_ELEMENT) { - NewObject->Common.ReferenceCount = - ReturnObject->Common.ReferenceCount; - - if (ReturnObject->Common.ReferenceCount > 1) + /* + * The original object is a package element. We need to + * decrement the reference count of the original object, + * for removing it from the package. + * + * However, if the original object was just wrapped with a + * package object as part of the repair, we don't need to + * change the reference count. + */ + if (!(Data->Flags & ACPI_OBJECT_WRAPPED)) { - ReturnObject->Common.ReferenceCount--; + NewObject->Common.ReferenceCount = + ReturnObject->Common.ReferenceCount; + + if (ReturnObject->Common.ReferenceCount > 1) + { + ReturnObject->Common.ReferenceCount--; + } } ACPI_DEBUG_PRINT ((ACPI_DB_REPAIR, - "%s: Converted %s to expected %s at index %u\n", + "%s: Converted %s to expected %s at Package index %u\n", Data->Pathname, AcpiUtGetObjectTypeName (ReturnObject), AcpiUtGetObjectTypeName (NewObject), PackageIndex)); } else { ACPI_DEBUG_PRINT ((ACPI_DB_REPAIR, "%s: Converted %s to expected %s\n", Data->Pathname, AcpiUtGetObjectTypeName (ReturnObject), AcpiUtGetObjectTypeName (NewObject))); } /* Delete old object, install the new return object */ AcpiUtRemoveReference (ReturnObject); *ReturnObjectPtr = NewObject; Data->Flags |= ACPI_OBJECT_REPAIRED; return (AE_OK); } /******************************************************************************* * * FUNCTION: AcpiNsConvertToInteger * * PARAMETERS: OriginalObject - Object to be converted * ReturnObject - Where the new converted object is returned * * RETURN: Status. AE_OK if conversion was successful. * * DESCRIPTION: Attempt to convert a String/Buffer object to an Integer. * ******************************************************************************/ static ACPI_STATUS AcpiNsConvertToInteger ( ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ReturnObject) { ACPI_OPERAND_OBJECT *NewObject; ACPI_STATUS Status; UINT64 Value = 0; UINT32 i; switch (OriginalObject->Common.Type) { case ACPI_TYPE_STRING: /* String-to-Integer conversion */ Status = AcpiUtStrtoul64 (OriginalObject->String.Pointer, ACPI_ANY_BASE, &Value); if (ACPI_FAILURE (Status)) { return (Status); } break; case ACPI_TYPE_BUFFER: /* Buffer-to-Integer conversion. Max buffer size is 64 bits. */ if (OriginalObject->Buffer.Length > 8) { return (AE_AML_OPERAND_TYPE); } /* Extract each buffer byte to create the integer */ for (i = 0; i < OriginalObject->Buffer.Length; i++) { Value |= ((UINT64) OriginalObject->Buffer.Pointer[i] << (i * 8)); } break; default: return (AE_AML_OPERAND_TYPE); } NewObject = AcpiUtCreateIntegerObject (Value); if (!NewObject) { return (AE_NO_MEMORY); } *ReturnObject = NewObject; return (AE_OK); } /******************************************************************************* * * FUNCTION: AcpiNsConvertToString * * PARAMETERS: OriginalObject - Object to be converted * ReturnObject - Where the new converted object is returned * * RETURN: Status. AE_OK if conversion was successful. * * DESCRIPTION: Attempt to convert a Integer/Buffer object to a String. * ******************************************************************************/ static ACPI_STATUS AcpiNsConvertToString ( ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ReturnObject) { ACPI_OPERAND_OBJECT *NewObject; ACPI_SIZE Length; ACPI_STATUS Status; switch (OriginalObject->Common.Type) { case ACPI_TYPE_INTEGER: /* * Integer-to-String conversion. Commonly, convert * an integer of value 0 to a NULL string. The last element of * _BIF and _BIX packages occasionally need this fix. */ if (OriginalObject->Integer.Value == 0) { /* Allocate a new NULL string object */ NewObject = AcpiUtCreateStringObject (0); if (!NewObject) { return (AE_NO_MEMORY); } } else { Status = AcpiExConvertToString (OriginalObject, &NewObject, ACPI_IMPLICIT_CONVERT_HEX); if (ACPI_FAILURE (Status)) { return (Status); } } break; case ACPI_TYPE_BUFFER: /* * Buffer-to-String conversion. Use a ToString * conversion, no transform performed on the buffer data. The best * example of this is the _BIF method, where the string data from * the battery is often (incorrectly) returned as buffer object(s). */ Length = 0; while ((Length < OriginalObject->Buffer.Length) && (OriginalObject->Buffer.Pointer[Length])) { Length++; } /* Allocate a new string object */ NewObject = AcpiUtCreateStringObject (Length); if (!NewObject) { return (AE_NO_MEMORY); } /* * Copy the raw buffer data with no transform. String is already NULL * terminated at Length+1. */ ACPI_MEMCPY (NewObject->String.Pointer, OriginalObject->Buffer.Pointer, Length); break; default: return (AE_AML_OPERAND_TYPE); } *ReturnObject = NewObject; return (AE_OK); } /******************************************************************************* * * FUNCTION: AcpiNsConvertToBuffer * * PARAMETERS: OriginalObject - Object to be converted * ReturnObject - Where the new converted object is returned * * RETURN: Status. AE_OK if conversion was successful. * * DESCRIPTION: Attempt to convert a Integer/String/Package object to a Buffer. * ******************************************************************************/ static ACPI_STATUS AcpiNsConvertToBuffer ( ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ReturnObject) { ACPI_OPERAND_OBJECT *NewObject; ACPI_STATUS Status; ACPI_OPERAND_OBJECT **Elements; UINT32 *DwordBuffer; UINT32 Count; UINT32 i; switch (OriginalObject->Common.Type) { case ACPI_TYPE_INTEGER: /* * Integer-to-Buffer conversion. * Convert the Integer to a packed-byte buffer. _MAT and other * objects need this sometimes, if a read has been performed on a * Field object that is less than or equal to the global integer * size (32 or 64 bits). */ Status = AcpiExConvertToBuffer (OriginalObject, &NewObject); if (ACPI_FAILURE (Status)) { return (Status); } break; case ACPI_TYPE_STRING: /* String-to-Buffer conversion. Simple data copy */ NewObject = AcpiUtCreateBufferObject (OriginalObject->String.Length); if (!NewObject) { return (AE_NO_MEMORY); } ACPI_MEMCPY (NewObject->Buffer.Pointer, OriginalObject->String.Pointer, OriginalObject->String.Length); break; case ACPI_TYPE_PACKAGE: /* * This case is often seen for predefined names that must return a * Buffer object with multiple DWORD integers within. For example, * _FDE and _GTM. The Package can be converted to a Buffer. */ /* All elements of the Package must be integers */ Elements = OriginalObject->Package.Elements; Count = OriginalObject->Package.Count; for (i = 0; i < Count; i++) { if ((!*Elements) || ((*Elements)->Common.Type != ACPI_TYPE_INTEGER)) { return (AE_AML_OPERAND_TYPE); } Elements++; } /* Create the new buffer object to replace the Package */ NewObject = AcpiUtCreateBufferObject (ACPI_MUL_4 (Count)); if (!NewObject) { return (AE_NO_MEMORY); } /* Copy the package elements (integers) to the buffer as DWORDs */ Elements = OriginalObject->Package.Elements; DwordBuffer = ACPI_CAST_PTR (UINT32, NewObject->Buffer.Pointer); for (i = 0; i < Count; i++) { *DwordBuffer = (UINT32) (*Elements)->Integer.Value; DwordBuffer++; Elements++; } break; default: return (AE_AML_OPERAND_TYPE); } *ReturnObject = NewObject; return (AE_OK); } -/******************************************************************************* - * - * FUNCTION: AcpiNsConvertToPackage - * - * PARAMETERS: OriginalObject - Object to be converted - * ReturnObject - Where the new converted object is returned - * - * RETURN: Status. AE_OK if conversion was successful. - * - * DESCRIPTION: Attempt to convert a Buffer object to a Package. Each byte of - * the buffer is converted to a single integer package element. - * - ******************************************************************************/ - -static ACPI_STATUS -AcpiNsConvertToPackage ( - ACPI_OPERAND_OBJECT *OriginalObject, - ACPI_OPERAND_OBJECT **ReturnObject) -{ - ACPI_OPERAND_OBJECT *NewObject; - ACPI_OPERAND_OBJECT **Elements; - UINT32 Length; - UINT8 *Buffer; - - - switch (OriginalObject->Common.Type) - { - case ACPI_TYPE_BUFFER: - - /* Buffer-to-Package conversion */ - - Length = OriginalObject->Buffer.Length; - NewObject = AcpiUtCreatePackageObject (Length); - if (!NewObject) - { - return (AE_NO_MEMORY); - } - - /* Convert each buffer byte to an integer package element */ - - Elements = NewObject->Package.Elements; - Buffer = OriginalObject->Buffer.Pointer; - - while (Length--) - { - *Elements = AcpiUtCreateIntegerObject ((UINT64) *Buffer); - if (!*Elements) - { - AcpiUtRemoveReference (NewObject); - return (AE_NO_MEMORY); - } - Elements++; - Buffer++; - } - break; - - default: - return (AE_AML_OPERAND_TYPE); - } - - *ReturnObject = NewObject; - return (AE_OK); -} - - /******************************************************************************* * * FUNCTION: AcpiNsRepairNullElement * * PARAMETERS: Data - Pointer to validation data structure * ExpectedBtypes - Object types expected * PackageIndex - Index of object within parent package (if * applicable - ACPI_NOT_PACKAGE_ELEMENT * otherwise) * ReturnObjectPtr - Pointer to the object returned from the * evaluation of a method or object * * RETURN: Status. AE_OK if repair was successful. * * DESCRIPTION: Attempt to repair a NULL element of a returned Package object. * ******************************************************************************/ ACPI_STATUS AcpiNsRepairNullElement ( ACPI_PREDEFINED_DATA *Data, UINT32 ExpectedBtypes, UINT32 PackageIndex, ACPI_OPERAND_OBJECT **ReturnObjectPtr) { ACPI_OPERAND_OBJECT *ReturnObject = *ReturnObjectPtr; ACPI_OPERAND_OBJECT *NewObject; ACPI_FUNCTION_NAME (NsRepairNullElement); /* No repair needed if return object is non-NULL */ if (ReturnObject) { return (AE_OK); } /* * Attempt to repair a NULL element of a Package object. This applies to * predefined names that return a fixed-length package and each element * is required. It does not apply to variable-length packages where NULL * elements are allowed, especially at the end of the package. */ if (ExpectedBtypes & ACPI_RTYPE_INTEGER) { /* Need an Integer - create a zero-value integer */ NewObject = AcpiUtCreateIntegerObject ((UINT64) 0); } else if (ExpectedBtypes & ACPI_RTYPE_STRING) { /* Need a String - create a NULL string */ NewObject = AcpiUtCreateStringObject (0); } else if (ExpectedBtypes & ACPI_RTYPE_BUFFER) { /* Need a Buffer - create a zero-length buffer */ NewObject = AcpiUtCreateBufferObject (0); } else { /* Error for all other expected types */ return (AE_AML_OPERAND_TYPE); } if (!NewObject) { return (AE_NO_MEMORY); } /* Set the reference count according to the parent Package object */ NewObject->Common.ReferenceCount = Data->ParentPackage->Common.ReferenceCount; ACPI_DEBUG_PRINT ((ACPI_DB_REPAIR, "%s: Converted NULL package element to expected %s at index %u\n", Data->Pathname, AcpiUtGetObjectTypeName (NewObject), PackageIndex)); *ReturnObjectPtr = NewObject; Data->Flags |= ACPI_OBJECT_REPAIRED; return (AE_OK); } /****************************************************************************** * * FUNCTION: AcpiNsRemoveNullElements * * PARAMETERS: Data - Pointer to validation data structure * PackageType - An AcpiReturnPackageTypes value * ObjDesc - A Package object * * RETURN: None. * * DESCRIPTION: Remove all NULL package elements from packages that contain * a variable number of sub-packages. For these types of * packages, NULL elements can be safely removed. * *****************************************************************************/ void AcpiNsRemoveNullElements ( ACPI_PREDEFINED_DATA *Data, UINT8 PackageType, ACPI_OPERAND_OBJECT *ObjDesc) { ACPI_OPERAND_OBJECT **Source; ACPI_OPERAND_OBJECT **Dest; UINT32 Count; UINT32 NewCount; UINT32 i; ACPI_FUNCTION_NAME (NsRemoveNullElements); /* * We can safely remove all NULL elements from these package types: * PTYPE1_VAR packages contain a variable number of simple data types. * PTYPE2 packages contain a variable number of sub-packages. */ switch (PackageType) { case ACPI_PTYPE1_VAR: case ACPI_PTYPE2: case ACPI_PTYPE2_COUNT: case ACPI_PTYPE2_PKG_COUNT: case ACPI_PTYPE2_FIXED: case ACPI_PTYPE2_MIN: case ACPI_PTYPE2_REV_FIXED: case ACPI_PTYPE2_FIX_VAR: break; default: case ACPI_PTYPE1_FIXED: case ACPI_PTYPE1_OPTION: return; } Count = ObjDesc->Package.Count; NewCount = Count; Source = ObjDesc->Package.Elements; Dest = Source; /* Examine all elements of the package object, remove nulls */ for (i = 0; i < Count; i++) { if (!*Source) { NewCount--; } else { *Dest = *Source; Dest++; } Source++; } /* Update parent package if any null elements were removed */ if (NewCount < Count) { ACPI_DEBUG_PRINT ((ACPI_DB_REPAIR, "%s: Found and removed %u NULL elements\n", Data->Pathname, (Count - NewCount))); /* NULL terminate list and update the package count */ *Dest = NULL; ObjDesc->Package.Count = NewCount; } } /******************************************************************************* * - * FUNCTION: AcpiNsRepairPackageList + * FUNCTION: AcpiNsWrapWithPackage * * PARAMETERS: Data - Pointer to validation data structure - * ObjDescPtr - Pointer to the object to repair. The new - * package object is returned here, - * overwriting the old object. + * OriginalObject - Pointer to the object to repair. + * ObjDescPtr - The new package object is returned here * * RETURN: Status, new object in *ObjDescPtr * - * DESCRIPTION: Repair a common problem with objects that are defined to return - * a variable-length Package of Packages. If the variable-length - * is one, some BIOS code mistakenly simply declares a single - * Package instead of a Package with one sub-Package. This - * function attempts to repair this error by wrapping a Package - * object around the original Package, creating the correct - * Package with one sub-Package. + * DESCRIPTION: Repair a common problem with objects that are defined to + * return a variable-length Package of sub-objects. If there is + * only one sub-object, some BIOS code mistakenly simply declares + * the single object instead of a Package with one sub-object. + * This function attempts to repair this error by wrapping a + * Package object around the original object, creating the + * correct and expected Package with one sub-object. * * Names that can be repaired in this manner include: - * _ALR, _CSD, _HPX, _MLS, _PRT, _PSS, _TRT, TSS + * _ALR, _CSD, _HPX, _MLS, _PLD, _PRT, _PSS, _TRT, _TSS, + * _BCL, _DOD, _FIX, _Sx * ******************************************************************************/ ACPI_STATUS -AcpiNsRepairPackageList ( +AcpiNsWrapWithPackage ( ACPI_PREDEFINED_DATA *Data, + ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ObjDescPtr) { ACPI_OPERAND_OBJECT *PkgObjDesc; - ACPI_FUNCTION_NAME (NsRepairPackageList); + ACPI_FUNCTION_NAME (NsWrapWithPackage); /* * Create the new outer package and populate it. The new package will - * have a single element, the lone subpackage. + * have a single element, the lone sub-object. */ PkgObjDesc = AcpiUtCreatePackageObject (1); if (!PkgObjDesc) { return (AE_NO_MEMORY); } - PkgObjDesc->Package.Elements[0] = *ObjDescPtr; + PkgObjDesc->Package.Elements[0] = OriginalObject; + + ACPI_DEBUG_PRINT ((ACPI_DB_REPAIR, + "%s: Wrapped %s with expected Package object\n", + Data->Pathname, AcpiUtGetObjectTypeName (OriginalObject))); /* Return the new object in the object pointer */ *ObjDescPtr = PkgObjDesc; - Data->Flags |= ACPI_OBJECT_REPAIRED; - - ACPI_DEBUG_PRINT ((ACPI_DB_REPAIR, - "%s: Repaired incorrectly formed Package\n", Data->Pathname)); - + Data->Flags |= ACPI_OBJECT_REPAIRED | ACPI_OBJECT_WRAPPED; return (AE_OK); } diff --git a/source/include/aclocal.h b/source/include/aclocal.h index d29a72157639..30c648dcdbab 100644 --- a/source/include/aclocal.h +++ b/source/include/aclocal.h @@ -1,1302 +1,1303 @@ /****************************************************************************** * * Name: aclocal.h - Internal data types used across the ACPI subsystem * *****************************************************************************/ /* * Copyright (C) 2000 - 2012, Intel Corp. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions, and the following disclaimer, * without modification. * 2. Redistributions in binary form must reproduce at minimum a disclaimer * substantially similar to the "NO WARRANTY" disclaimer below * ("Disclaimer") and any redistribution must be conditioned upon * including a substantially similar Disclaimer requirement for further * binary redistribution. * 3. Neither the names of the above-listed copyright holders nor the names * of any contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * Alternatively, this software may be distributed under the terms of the * GNU General Public License ("GPL") version 2 as published by the Free * Software Foundation. * * NO WARRANTY * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGES. */ #ifndef __ACLOCAL_H__ #define __ACLOCAL_H__ /* acpisrc:StructDefs -- for acpisrc conversion */ #define ACPI_SERIALIZED 0xFF typedef UINT32 ACPI_MUTEX_HANDLE; #define ACPI_GLOBAL_LOCK (ACPI_SEMAPHORE) (-1) /* Total number of aml opcodes defined */ #define AML_NUM_OPCODES 0x81 /* Forward declarations */ struct acpi_walk_state; struct acpi_obj_mutex; union acpi_parse_object; /***************************************************************************** * * Mutex typedefs and structs * ****************************************************************************/ /* * Predefined handles for the mutex objects used within the subsystem * All mutex objects are automatically created by AcpiUtMutexInitialize. * * The acquire/release ordering protocol is implied via this list. Mutexes * with a lower value must be acquired before mutexes with a higher value. * * NOTE: any changes here must be reflected in the AcpiGbl_MutexNames * table below also! */ #define ACPI_MTX_INTERPRETER 0 /* AML Interpreter, main lock */ #define ACPI_MTX_NAMESPACE 1 /* ACPI Namespace */ #define ACPI_MTX_TABLES 2 /* Data for ACPI tables */ #define ACPI_MTX_EVENTS 3 /* Data for ACPI events */ #define ACPI_MTX_CACHES 4 /* Internal caches, general purposes */ #define ACPI_MTX_MEMORY 5 /* Debug memory tracking lists */ #define ACPI_MTX_DEBUG_CMD_COMPLETE 6 /* AML debugger */ #define ACPI_MTX_DEBUG_CMD_READY 7 /* AML debugger */ #define ACPI_MAX_MUTEX 7 #define ACPI_NUM_MUTEX ACPI_MAX_MUTEX+1 /* Lock structure for reader/writer interfaces */ typedef struct acpi_rw_lock { ACPI_MUTEX WriterMutex; ACPI_MUTEX ReaderMutex; UINT32 NumReaders; } ACPI_RW_LOCK; /* * Predefined handles for spinlocks used within the subsystem. * These spinlocks are created by AcpiUtMutexInitialize */ #define ACPI_LOCK_GPES 0 #define ACPI_LOCK_HARDWARE 1 #define ACPI_MAX_LOCK 1 #define ACPI_NUM_LOCK ACPI_MAX_LOCK+1 /* This Thread ID means that the mutex is not in use (unlocked) */ #define ACPI_MUTEX_NOT_ACQUIRED (ACPI_THREAD_ID) -1 /* Table for the global mutexes */ typedef struct acpi_mutex_info { ACPI_MUTEX Mutex; UINT32 UseCount; ACPI_THREAD_ID ThreadId; } ACPI_MUTEX_INFO; /* Lock flag parameter for various interfaces */ #define ACPI_MTX_DO_NOT_LOCK 0 #define ACPI_MTX_LOCK 1 /* Field access granularities */ #define ACPI_FIELD_BYTE_GRANULARITY 1 #define ACPI_FIELD_WORD_GRANULARITY 2 #define ACPI_FIELD_DWORD_GRANULARITY 4 #define ACPI_FIELD_QWORD_GRANULARITY 8 #define ACPI_ENTRY_NOT_FOUND NULL /***************************************************************************** * * Namespace typedefs and structs * ****************************************************************************/ /* Operational modes of the AML interpreter/scanner */ typedef enum { ACPI_IMODE_LOAD_PASS1 = 0x01, ACPI_IMODE_LOAD_PASS2 = 0x02, ACPI_IMODE_EXECUTE = 0x03 } ACPI_INTERPRETER_MODE; /* * The Namespace Node describes a named object that appears in the AML. * DescriptorType is used to differentiate between internal descriptors. * * The node is optimized for both 32-bit and 64-bit platforms: * 20 bytes for the 32-bit case, 32 bytes for the 64-bit case. * * Note: The DescriptorType and Type fields must appear in the identical * position in both the ACPI_NAMESPACE_NODE and ACPI_OPERAND_OBJECT * structures. */ typedef struct acpi_namespace_node { union acpi_operand_object *Object; /* Interpreter object */ UINT8 DescriptorType; /* Differentiate object descriptor types */ UINT8 Type; /* ACPI Type associated with this name */ UINT8 Flags; /* Miscellaneous flags */ ACPI_OWNER_ID OwnerId; /* Node creator */ ACPI_NAME_UNION Name; /* ACPI Name, always 4 chars per ACPI spec */ struct acpi_namespace_node *Parent; /* Parent node */ struct acpi_namespace_node *Child; /* First child */ struct acpi_namespace_node *Peer; /* First peer */ /* * The following fields are used by the ASL compiler and disassembler only */ #ifdef ACPI_LARGE_NAMESPACE_NODE union acpi_parse_object *Op; UINT32 Value; UINT32 Length; #endif } ACPI_NAMESPACE_NODE; /* Namespace Node flags */ #define ANOBJ_RESERVED 0x01 /* Available for use */ #define ANOBJ_TEMPORARY 0x02 /* Node is create by a method and is temporary */ #define ANOBJ_METHOD_ARG 0x04 /* Node is a method argument */ #define ANOBJ_METHOD_LOCAL 0x08 /* Node is a method local */ #define ANOBJ_SUBTREE_HAS_INI 0x10 /* Used to optimize device initialization */ #define ANOBJ_EVALUATED 0x20 /* Set on first evaluation of node */ #define ANOBJ_ALLOCATED_BUFFER 0x40 /* Method AML buffer is dynamic (InstallMethod) */ #define ANOBJ_IS_EXTERNAL 0x08 /* iASL only: This object created via External() */ #define ANOBJ_METHOD_NO_RETVAL 0x10 /* iASL only: Method has no return value */ #define ANOBJ_METHOD_SOME_NO_RETVAL 0x20 /* iASL only: Method has at least one return value */ #define ANOBJ_IS_REFERENCED 0x80 /* iASL only: Object was referenced */ /* Internal ACPI table management - master table list */ typedef struct acpi_table_list { ACPI_TABLE_DESC *Tables; /* Table descriptor array */ UINT32 CurrentTableCount; /* Tables currently in the array */ UINT32 MaxTableCount; /* Max tables array will hold */ UINT8 Flags; } ACPI_TABLE_LIST; /* Flags for above */ #define ACPI_ROOT_ORIGIN_UNKNOWN (0) /* ~ORIGIN_ALLOCATED */ #define ACPI_ROOT_ORIGIN_ALLOCATED (1) #define ACPI_ROOT_ALLOW_RESIZE (2) /* Predefined (fixed) table indexes */ #define ACPI_TABLE_INDEX_DSDT (0) #define ACPI_TABLE_INDEX_FACS (1) typedef struct acpi_find_context { char *SearchFor; ACPI_HANDLE *List; UINT32 *Count; } ACPI_FIND_CONTEXT; typedef struct acpi_ns_search_data { ACPI_NAMESPACE_NODE *Node; } ACPI_NS_SEARCH_DATA; /* Object types used during package copies */ #define ACPI_COPY_TYPE_SIMPLE 0 #define ACPI_COPY_TYPE_PACKAGE 1 /* Info structure used to convert external<->internal namestrings */ typedef struct acpi_namestring_info { const char *ExternalName; const char *NextExternalChar; char *InternalName; UINT32 Length; UINT32 NumSegments; UINT32 NumCarats; BOOLEAN FullyQualified; } ACPI_NAMESTRING_INFO; /* Field creation info */ typedef struct acpi_create_field_info { ACPI_NAMESPACE_NODE *RegionNode; ACPI_NAMESPACE_NODE *FieldNode; ACPI_NAMESPACE_NODE *RegisterNode; ACPI_NAMESPACE_NODE *DataRegisterNode; ACPI_NAMESPACE_NODE *ConnectionNode; UINT8 *ResourceBuffer; UINT32 BankValue; UINT32 FieldBitPosition; UINT32 FieldBitLength; UINT16 ResourceLength; UINT8 FieldFlags; UINT8 Attribute; UINT8 FieldType; UINT8 AccessLength; } ACPI_CREATE_FIELD_INFO; typedef ACPI_STATUS (*ACPI_INTERNAL_METHOD) ( struct acpi_walk_state *WalkState); /* * Bitmapped ACPI types. Used internally only */ #define ACPI_BTYPE_ANY 0x00000000 #define ACPI_BTYPE_INTEGER 0x00000001 #define ACPI_BTYPE_STRING 0x00000002 #define ACPI_BTYPE_BUFFER 0x00000004 #define ACPI_BTYPE_PACKAGE 0x00000008 #define ACPI_BTYPE_FIELD_UNIT 0x00000010 #define ACPI_BTYPE_DEVICE 0x00000020 #define ACPI_BTYPE_EVENT 0x00000040 #define ACPI_BTYPE_METHOD 0x00000080 #define ACPI_BTYPE_MUTEX 0x00000100 #define ACPI_BTYPE_REGION 0x00000200 #define ACPI_BTYPE_POWER 0x00000400 #define ACPI_BTYPE_PROCESSOR 0x00000800 #define ACPI_BTYPE_THERMAL 0x00001000 #define ACPI_BTYPE_BUFFER_FIELD 0x00002000 #define ACPI_BTYPE_DDB_HANDLE 0x00004000 #define ACPI_BTYPE_DEBUG_OBJECT 0x00008000 #define ACPI_BTYPE_REFERENCE 0x00010000 #define ACPI_BTYPE_RESOURCE 0x00020000 #define ACPI_BTYPE_COMPUTE_DATA (ACPI_BTYPE_INTEGER | ACPI_BTYPE_STRING | ACPI_BTYPE_BUFFER) #define ACPI_BTYPE_DATA (ACPI_BTYPE_COMPUTE_DATA | ACPI_BTYPE_PACKAGE) #define ACPI_BTYPE_DATA_REFERENCE (ACPI_BTYPE_DATA | ACPI_BTYPE_REFERENCE | ACPI_BTYPE_DDB_HANDLE) #define ACPI_BTYPE_DEVICE_OBJECTS (ACPI_BTYPE_DEVICE | ACPI_BTYPE_THERMAL | ACPI_BTYPE_PROCESSOR) #define ACPI_BTYPE_OBJECTS_AND_REFS 0x0001FFFF /* ARG or LOCAL */ #define ACPI_BTYPE_ALL_OBJECTS 0x0000FFFF /* * Information structure for ACPI predefined names. * Each entry in the table contains the following items: * * Name - The ACPI reserved name * ParamCount - Number of arguments to the method * ExpectedReturnBtypes - Allowed type(s) for the return value */ typedef struct acpi_name_info { char Name[ACPI_NAME_SIZE]; UINT8 ParamCount; UINT8 ExpectedBtypes; } ACPI_NAME_INFO; /* * Secondary information structures for ACPI predefined objects that return * package objects. This structure appears as the next entry in the table * after the NAME_INFO structure above. * * The reason for this is to minimize the size of the predefined name table. */ /* * Used for ACPI_PTYPE1_FIXED, ACPI_PTYPE1_VAR, ACPI_PTYPE2, * ACPI_PTYPE2_MIN, ACPI_PTYPE2_PKG_COUNT, ACPI_PTYPE2_COUNT, * ACPI_PTYPE2_FIX_VAR */ typedef struct acpi_package_info { UINT8 Type; UINT8 ObjectType1; UINT8 Count1; UINT8 ObjectType2; UINT8 Count2; UINT8 Reserved; } ACPI_PACKAGE_INFO; /* Used for ACPI_PTYPE2_FIXED */ typedef struct acpi_package_info2 { UINT8 Type; UINT8 Count; UINT8 ObjectType[4]; } ACPI_PACKAGE_INFO2; /* Used for ACPI_PTYPE1_OPTION */ typedef struct acpi_package_info3 { UINT8 Type; UINT8 Count; UINT8 ObjectType[2]; UINT8 TailObjectType; UINT8 Reserved; } ACPI_PACKAGE_INFO3; typedef union acpi_predefined_info { ACPI_NAME_INFO Info; ACPI_PACKAGE_INFO RetInfo; ACPI_PACKAGE_INFO2 RetInfo2; ACPI_PACKAGE_INFO3 RetInfo3; } ACPI_PREDEFINED_INFO; /* Data block used during object validation */ typedef struct acpi_predefined_data { char *Pathname; const ACPI_PREDEFINED_INFO *Predefined; union acpi_operand_object *ParentPackage; ACPI_NAMESPACE_NODE *Node; UINT32 Flags; UINT8 NodeFlags; } ACPI_PREDEFINED_DATA; /* Defines for Flags field above */ #define ACPI_OBJECT_REPAIRED 1 +#define ACPI_OBJECT_WRAPPED 2 /* * Bitmapped return value types * Note: the actual data types must be contiguous, a loop in nspredef.c * depends on this. */ #define ACPI_RTYPE_ANY 0x00 #define ACPI_RTYPE_NONE 0x01 #define ACPI_RTYPE_INTEGER 0x02 #define ACPI_RTYPE_STRING 0x04 #define ACPI_RTYPE_BUFFER 0x08 #define ACPI_RTYPE_PACKAGE 0x10 #define ACPI_RTYPE_REFERENCE 0x20 #define ACPI_RTYPE_ALL 0x3F #define ACPI_NUM_RTYPES 5 /* Number of actual object types */ /***************************************************************************** * * Event typedefs and structs * ****************************************************************************/ /* Dispatch info for each GPE -- either a method or handler, cannot be both */ typedef struct acpi_gpe_handler_info { ACPI_GPE_HANDLER Address; /* Address of handler, if any */ void *Context; /* Context to be passed to handler */ ACPI_NAMESPACE_NODE *MethodNode; /* Method node for this GPE level (saved) */ UINT8 OriginalFlags; /* Original (pre-handler) GPE info */ BOOLEAN OriginallyEnabled; /* True if GPE was originally enabled */ } ACPI_GPE_HANDLER_INFO; /* * GPE dispatch info. At any time, the GPE can have at most one type * of dispatch - Method, Handler, or Implicit Notify. */ typedef union acpi_gpe_dispatch_info { ACPI_NAMESPACE_NODE *MethodNode; /* Method node for this GPE level */ struct acpi_gpe_handler_info *Handler; /* Installed GPE handler */ ACPI_NAMESPACE_NODE *DeviceNode; /* Parent _PRW device for implicit notify */ } ACPI_GPE_DISPATCH_INFO; /* * Information about a GPE, one per each GPE in an array. * NOTE: Important to keep this struct as small as possible. */ typedef struct acpi_gpe_event_info { union acpi_gpe_dispatch_info Dispatch; /* Either Method or Handler */ struct acpi_gpe_register_info *RegisterInfo; /* Backpointer to register info */ UINT8 Flags; /* Misc info about this GPE */ UINT8 GpeNumber; /* This GPE */ UINT8 RuntimeCount; /* References to a run GPE */ } ACPI_GPE_EVENT_INFO; /* Information about a GPE register pair, one per each status/enable pair in an array */ typedef struct acpi_gpe_register_info { ACPI_GENERIC_ADDRESS StatusAddress; /* Address of status reg */ ACPI_GENERIC_ADDRESS EnableAddress; /* Address of enable reg */ UINT8 EnableForWake; /* GPEs to keep enabled when sleeping */ UINT8 EnableForRun; /* GPEs to keep enabled when running */ UINT8 BaseGpeNumber; /* Base GPE number for this register */ } ACPI_GPE_REGISTER_INFO; /* * Information about a GPE register block, one per each installed block -- * GPE0, GPE1, and one per each installed GPE Block Device. */ typedef struct acpi_gpe_block_info { ACPI_NAMESPACE_NODE *Node; struct acpi_gpe_block_info *Previous; struct acpi_gpe_block_info *Next; struct acpi_gpe_xrupt_info *XruptBlock; /* Backpointer to interrupt block */ ACPI_GPE_REGISTER_INFO *RegisterInfo; /* One per GPE register pair */ ACPI_GPE_EVENT_INFO *EventInfo; /* One for each GPE */ ACPI_GENERIC_ADDRESS BlockAddress; /* Base address of the block */ UINT32 RegisterCount; /* Number of register pairs in block */ UINT16 GpeCount; /* Number of individual GPEs in block */ UINT8 BlockBaseNumber;/* Base GPE number for this block */ BOOLEAN Initialized; /* TRUE if this block is initialized */ } ACPI_GPE_BLOCK_INFO; /* Information about GPE interrupt handlers, one per each interrupt level used for GPEs */ typedef struct acpi_gpe_xrupt_info { struct acpi_gpe_xrupt_info *Previous; struct acpi_gpe_xrupt_info *Next; ACPI_GPE_BLOCK_INFO *GpeBlockListHead; /* List of GPE blocks for this xrupt */ UINT32 InterruptNumber; /* System interrupt number */ } ACPI_GPE_XRUPT_INFO; typedef struct acpi_gpe_walk_info { ACPI_NAMESPACE_NODE *GpeDevice; ACPI_GPE_BLOCK_INFO *GpeBlock; UINT16 Count; ACPI_OWNER_ID OwnerId; BOOLEAN ExecuteByOwnerId; } ACPI_GPE_WALK_INFO; typedef struct acpi_gpe_device_info { UINT32 Index; UINT32 NextBlockBaseIndex; ACPI_STATUS Status; ACPI_NAMESPACE_NODE *GpeDevice; } ACPI_GPE_DEVICE_INFO; typedef ACPI_STATUS (*ACPI_GPE_CALLBACK) ( ACPI_GPE_XRUPT_INFO *GpeXruptInfo, ACPI_GPE_BLOCK_INFO *GpeBlock, void *Context); /* Information about each particular fixed event */ typedef struct acpi_fixed_event_handler { ACPI_EVENT_HANDLER Handler; /* Address of handler. */ void *Context; /* Context to be passed to handler */ } ACPI_FIXED_EVENT_HANDLER; typedef struct acpi_fixed_event_info { UINT8 StatusRegisterId; UINT8 EnableRegisterId; UINT16 StatusBitMask; UINT16 EnableBitMask; } ACPI_FIXED_EVENT_INFO; /* Information used during field processing */ typedef struct acpi_field_info { UINT8 SkipField; UINT8 FieldFlag; UINT32 PkgLength; } ACPI_FIELD_INFO; /***************************************************************************** * * Generic "state" object for stacks * ****************************************************************************/ #define ACPI_CONTROL_NORMAL 0xC0 #define ACPI_CONTROL_CONDITIONAL_EXECUTING 0xC1 #define ACPI_CONTROL_PREDICATE_EXECUTING 0xC2 #define ACPI_CONTROL_PREDICATE_FALSE 0xC3 #define ACPI_CONTROL_PREDICATE_TRUE 0xC4 #define ACPI_STATE_COMMON \ void *Next; \ UINT8 DescriptorType; /* To differentiate various internal objs */\ UINT8 Flags; \ UINT16 Value; \ UINT16 State; /* There are 2 bytes available here until the next natural alignment boundary */ typedef struct acpi_common_state { ACPI_STATE_COMMON } ACPI_COMMON_STATE; /* * Update state - used to traverse complex objects such as packages */ typedef struct acpi_update_state { ACPI_STATE_COMMON union acpi_operand_object *Object; } ACPI_UPDATE_STATE; /* * Pkg state - used to traverse nested package structures */ typedef struct acpi_pkg_state { ACPI_STATE_COMMON UINT16 Index; union acpi_operand_object *SourceObject; union acpi_operand_object *DestObject; struct acpi_walk_state *WalkState; void *ThisTargetObj; UINT32 NumPackages; } ACPI_PKG_STATE; /* * Control state - one per if/else and while constructs. * Allows nesting of these constructs */ typedef struct acpi_control_state { ACPI_STATE_COMMON UINT16 Opcode; union acpi_parse_object *PredicateOp; UINT8 *AmlPredicateStart; /* Start of if/while predicate */ UINT8 *PackageEnd; /* End of if/while block */ UINT32 LoopCount; /* While() loop counter */ } ACPI_CONTROL_STATE; /* * Scope state - current scope during namespace lookups */ typedef struct acpi_scope_state { ACPI_STATE_COMMON ACPI_NAMESPACE_NODE *Node; } ACPI_SCOPE_STATE; typedef struct acpi_pscope_state { ACPI_STATE_COMMON UINT32 ArgCount; /* Number of fixed arguments */ union acpi_parse_object *Op; /* Current op being parsed */ UINT8 *ArgEnd; /* Current argument end */ UINT8 *PkgEnd; /* Current package end */ UINT32 ArgList; /* Next argument to parse */ } ACPI_PSCOPE_STATE; /* * Thread state - one per thread across multiple walk states. Multiple walk * states are created when there are nested control methods executing. */ typedef struct acpi_thread_state { ACPI_STATE_COMMON UINT8 CurrentSyncLevel; /* Mutex Sync (nested acquire) level */ struct acpi_walk_state *WalkStateList; /* Head of list of WalkStates for this thread */ union acpi_operand_object *AcquiredMutexList; /* List of all currently acquired mutexes */ ACPI_THREAD_ID ThreadId; /* Running thread ID */ } ACPI_THREAD_STATE; /* * Result values - used to accumulate the results of nested * AML arguments */ typedef struct acpi_result_values { ACPI_STATE_COMMON union acpi_operand_object *ObjDesc [ACPI_RESULTS_FRAME_OBJ_NUM]; } ACPI_RESULT_VALUES; typedef ACPI_STATUS (*ACPI_PARSE_DOWNWARDS) ( struct acpi_walk_state *WalkState, union acpi_parse_object **OutOp); typedef ACPI_STATUS (*ACPI_PARSE_UPWARDS) ( struct acpi_walk_state *WalkState); /* * Notify info - used to pass info to the deferred notify * handler/dispatcher. */ typedef struct acpi_notify_info { ACPI_STATE_COMMON ACPI_NAMESPACE_NODE *Node; union acpi_operand_object *HandlerObj; } ACPI_NOTIFY_INFO; /* Generic state is union of structs above */ typedef union acpi_generic_state { ACPI_COMMON_STATE Common; ACPI_CONTROL_STATE Control; ACPI_UPDATE_STATE Update; ACPI_SCOPE_STATE Scope; ACPI_PSCOPE_STATE ParseScope; ACPI_PKG_STATE Pkg; ACPI_THREAD_STATE Thread; ACPI_RESULT_VALUES Results; ACPI_NOTIFY_INFO Notify; } ACPI_GENERIC_STATE; /***************************************************************************** * * Interpreter typedefs and structs * ****************************************************************************/ typedef ACPI_STATUS (*ACPI_EXECUTE_OP) ( struct acpi_walk_state *WalkState); /* Address Range info block */ typedef struct acpi_address_range { struct acpi_address_range *Next; ACPI_NAMESPACE_NODE *RegionNode; ACPI_PHYSICAL_ADDRESS StartAddress; ACPI_PHYSICAL_ADDRESS EndAddress; } ACPI_ADDRESS_RANGE; /***************************************************************************** * * Parser typedefs and structs * ****************************************************************************/ /* * AML opcode, name, and argument layout */ typedef struct acpi_opcode_info { #if defined(ACPI_DISASSEMBLER) || defined(ACPI_DEBUG_OUTPUT) char *Name; /* Opcode name (disassembler/debug only) */ #endif UINT32 ParseArgs; /* Grammar/Parse time arguments */ UINT32 RuntimeArgs; /* Interpret time arguments */ UINT16 Flags; /* Misc flags */ UINT8 ObjectType; /* Corresponding internal object type */ UINT8 Class; /* Opcode class */ UINT8 Type; /* Opcode type */ } ACPI_OPCODE_INFO; /* Structure for Resource Tag information */ typedef struct acpi_tag_info { UINT32 BitOffset; UINT32 BitLength; } ACPI_TAG_INFO; /* Value associated with the parse object */ typedef union acpi_parse_value { UINT64 Integer; /* Integer constant (Up to 64 bits) */ UINT32 Size; /* bytelist or field size */ char *String; /* NULL terminated string */ UINT8 *Buffer; /* buffer or string */ char *Name; /* NULL terminated string */ union acpi_parse_object *Arg; /* arguments and contained ops */ ACPI_TAG_INFO Tag; /* Resource descriptor tag info */ } ACPI_PARSE_VALUE; #ifdef ACPI_DISASSEMBLER #define ACPI_DISASM_ONLY_MEMBERS(a) a; #else #define ACPI_DISASM_ONLY_MEMBERS(a) #endif #define ACPI_PARSE_COMMON \ union acpi_parse_object *Parent; /* Parent op */\ UINT8 DescriptorType; /* To differentiate various internal objs */\ UINT8 Flags; /* Type of Op */\ UINT16 AmlOpcode; /* AML opcode */\ UINT32 AmlOffset; /* Offset of declaration in AML */\ union acpi_parse_object *Next; /* Next op */\ ACPI_NAMESPACE_NODE *Node; /* For use by interpreter */\ ACPI_PARSE_VALUE Value; /* Value or args associated with the opcode */\ UINT8 ArgListLength; /* Number of elements in the arg list */\ ACPI_DISASM_ONLY_MEMBERS (\ UINT8 DisasmFlags; /* Used during AML disassembly */\ UINT8 DisasmOpcode; /* Subtype used for disassembly */\ char AmlOpName[16]) /* Op name (debug only) */ #define ACPI_DASM_BUFFER 0x00 #define ACPI_DASM_RESOURCE 0x01 #define ACPI_DASM_STRING 0x02 #define ACPI_DASM_UNICODE 0x03 #define ACPI_DASM_EISAID 0x04 #define ACPI_DASM_MATCHOP 0x05 #define ACPI_DASM_LNOT_PREFIX 0x06 #define ACPI_DASM_LNOT_SUFFIX 0x07 #define ACPI_DASM_IGNORE 0x08 /* * Generic operation (for example: If, While, Store) */ typedef struct acpi_parse_obj_common { ACPI_PARSE_COMMON } ACPI_PARSE_OBJ_COMMON; /* * Extended Op for named ops (Scope, Method, etc.), deferred ops (Methods and OpRegions), * and bytelists. */ typedef struct acpi_parse_obj_named { ACPI_PARSE_COMMON UINT8 *Path; UINT8 *Data; /* AML body or bytelist data */ UINT32 Length; /* AML length */ UINT32 Name; /* 4-byte name or zero if no name */ } ACPI_PARSE_OBJ_NAMED; /* This version is used by the iASL compiler only */ #define ACPI_MAX_PARSEOP_NAME 20 typedef struct acpi_parse_obj_asl { ACPI_PARSE_COMMON union acpi_parse_object *Child; union acpi_parse_object *ParentMethod; char *Filename; char *ExternalName; char *Namepath; char NameSeg[4]; UINT32 ExtraValue; UINT32 Column; UINT32 LineNumber; UINT32 LogicalLineNumber; UINT32 LogicalByteOffset; UINT32 EndLine; UINT32 EndLogicalLine; UINT32 AcpiBtype; UINT32 AmlLength; UINT32 AmlSubtreeLength; UINT32 FinalAmlLength; UINT32 FinalAmlOffset; UINT32 CompileFlags; UINT16 ParseOpcode; UINT8 AmlOpcodeLength; UINT8 AmlPkgLenBytes; UINT8 Extra; char ParseOpName[ACPI_MAX_PARSEOP_NAME]; } ACPI_PARSE_OBJ_ASL; typedef union acpi_parse_object { ACPI_PARSE_OBJ_COMMON Common; ACPI_PARSE_OBJ_NAMED Named; ACPI_PARSE_OBJ_ASL Asl; } ACPI_PARSE_OBJECT; /* * Parse state - one state per parser invocation and each control * method. */ typedef struct acpi_parse_state { UINT8 *AmlStart; /* First AML byte */ UINT8 *Aml; /* Next AML byte */ UINT8 *AmlEnd; /* (last + 1) AML byte */ UINT8 *PkgStart; /* Current package begin */ UINT8 *PkgEnd; /* Current package end */ union acpi_parse_object *StartOp; /* Root of parse tree */ struct acpi_namespace_node *StartNode; union acpi_generic_state *Scope; /* Current scope */ union acpi_parse_object *StartScope; UINT32 AmlSize; } ACPI_PARSE_STATE; /* Parse object flags */ #define ACPI_PARSEOP_GENERIC 0x01 #define ACPI_PARSEOP_NAMED 0x02 #define ACPI_PARSEOP_DEFERRED 0x04 #define ACPI_PARSEOP_BYTELIST 0x08 #define ACPI_PARSEOP_IN_STACK 0x10 #define ACPI_PARSEOP_TARGET 0x20 #define ACPI_PARSEOP_IN_CACHE 0x80 /* Parse object DisasmFlags */ #define ACPI_PARSEOP_IGNORE 0x01 #define ACPI_PARSEOP_PARAMLIST 0x02 #define ACPI_PARSEOP_EMPTY_TERMLIST 0x04 #define ACPI_PARSEOP_SPECIAL 0x10 /***************************************************************************** * * Hardware (ACPI registers) and PNP * ****************************************************************************/ typedef struct acpi_bit_register_info { UINT8 ParentRegister; UINT8 BitPosition; UINT16 AccessBitMask; } ACPI_BIT_REGISTER_INFO; /* * Some ACPI registers have bits that must be ignored -- meaning that they * must be preserved. */ #define ACPI_PM1_STATUS_PRESERVED_BITS 0x0800 /* Bit 11 */ /* Write-only bits must be zeroed by software */ #define ACPI_PM1_CONTROL_WRITEONLY_BITS 0x2004 /* Bits 13, 2 */ /* For control registers, both ignored and reserved bits must be preserved */ /* * For PM1 control, the SCI enable bit (bit 0, SCI_EN) is defined by the * ACPI specification to be a "preserved" bit - "OSPM always preserves this * bit position", section 4.7.3.2.1. However, on some machines the OS must * write a one to this bit after resume for the machine to work properly. * To enable this, we no longer attempt to preserve this bit. No machines * are known to fail if the bit is not preserved. (May 2009) */ #define ACPI_PM1_CONTROL_IGNORED_BITS 0x0200 /* Bit 9 */ #define ACPI_PM1_CONTROL_RESERVED_BITS 0xC1F8 /* Bits 14-15, 3-8 */ #define ACPI_PM1_CONTROL_PRESERVED_BITS \ (ACPI_PM1_CONTROL_IGNORED_BITS | ACPI_PM1_CONTROL_RESERVED_BITS) #define ACPI_PM2_CONTROL_PRESERVED_BITS 0xFFFFFFFE /* All except bit 0 */ /* * Register IDs * These are the full ACPI registers */ #define ACPI_REGISTER_PM1_STATUS 0x01 #define ACPI_REGISTER_PM1_ENABLE 0x02 #define ACPI_REGISTER_PM1_CONTROL 0x03 #define ACPI_REGISTER_PM2_CONTROL 0x04 #define ACPI_REGISTER_PM_TIMER 0x05 #define ACPI_REGISTER_PROCESSOR_BLOCK 0x06 #define ACPI_REGISTER_SMI_COMMAND_BLOCK 0x07 /* Masks used to access the BitRegisters */ #define ACPI_BITMASK_TIMER_STATUS 0x0001 #define ACPI_BITMASK_BUS_MASTER_STATUS 0x0010 #define ACPI_BITMASK_GLOBAL_LOCK_STATUS 0x0020 #define ACPI_BITMASK_POWER_BUTTON_STATUS 0x0100 #define ACPI_BITMASK_SLEEP_BUTTON_STATUS 0x0200 #define ACPI_BITMASK_RT_CLOCK_STATUS 0x0400 #define ACPI_BITMASK_PCIEXP_WAKE_STATUS 0x4000 /* ACPI 3.0 */ #define ACPI_BITMASK_WAKE_STATUS 0x8000 #define ACPI_BITMASK_ALL_FIXED_STATUS (\ ACPI_BITMASK_TIMER_STATUS | \ ACPI_BITMASK_BUS_MASTER_STATUS | \ ACPI_BITMASK_GLOBAL_LOCK_STATUS | \ ACPI_BITMASK_POWER_BUTTON_STATUS | \ ACPI_BITMASK_SLEEP_BUTTON_STATUS | \ ACPI_BITMASK_RT_CLOCK_STATUS | \ ACPI_BITMASK_PCIEXP_WAKE_STATUS | \ ACPI_BITMASK_WAKE_STATUS) #define ACPI_BITMASK_TIMER_ENABLE 0x0001 #define ACPI_BITMASK_GLOBAL_LOCK_ENABLE 0x0020 #define ACPI_BITMASK_POWER_BUTTON_ENABLE 0x0100 #define ACPI_BITMASK_SLEEP_BUTTON_ENABLE 0x0200 #define ACPI_BITMASK_RT_CLOCK_ENABLE 0x0400 #define ACPI_BITMASK_PCIEXP_WAKE_DISABLE 0x4000 /* ACPI 3.0 */ #define ACPI_BITMASK_SCI_ENABLE 0x0001 #define ACPI_BITMASK_BUS_MASTER_RLD 0x0002 #define ACPI_BITMASK_GLOBAL_LOCK_RELEASE 0x0004 #define ACPI_BITMASK_SLEEP_TYPE 0x1C00 #define ACPI_BITMASK_SLEEP_ENABLE 0x2000 #define ACPI_BITMASK_ARB_DISABLE 0x0001 /* Raw bit position of each BitRegister */ #define ACPI_BITPOSITION_TIMER_STATUS 0x00 #define ACPI_BITPOSITION_BUS_MASTER_STATUS 0x04 #define ACPI_BITPOSITION_GLOBAL_LOCK_STATUS 0x05 #define ACPI_BITPOSITION_POWER_BUTTON_STATUS 0x08 #define ACPI_BITPOSITION_SLEEP_BUTTON_STATUS 0x09 #define ACPI_BITPOSITION_RT_CLOCK_STATUS 0x0A #define ACPI_BITPOSITION_PCIEXP_WAKE_STATUS 0x0E /* ACPI 3.0 */ #define ACPI_BITPOSITION_WAKE_STATUS 0x0F #define ACPI_BITPOSITION_TIMER_ENABLE 0x00 #define ACPI_BITPOSITION_GLOBAL_LOCK_ENABLE 0x05 #define ACPI_BITPOSITION_POWER_BUTTON_ENABLE 0x08 #define ACPI_BITPOSITION_SLEEP_BUTTON_ENABLE 0x09 #define ACPI_BITPOSITION_RT_CLOCK_ENABLE 0x0A #define ACPI_BITPOSITION_PCIEXP_WAKE_DISABLE 0x0E /* ACPI 3.0 */ #define ACPI_BITPOSITION_SCI_ENABLE 0x00 #define ACPI_BITPOSITION_BUS_MASTER_RLD 0x01 #define ACPI_BITPOSITION_GLOBAL_LOCK_RELEASE 0x02 #define ACPI_BITPOSITION_SLEEP_TYPE 0x0A #define ACPI_BITPOSITION_SLEEP_ENABLE 0x0D #define ACPI_BITPOSITION_ARB_DISABLE 0x00 /* Structs and definitions for _OSI support and I/O port validation */ #define ACPI_OSI_WIN_2000 0x01 #define ACPI_OSI_WIN_XP 0x02 #define ACPI_OSI_WIN_XP_SP1 0x03 #define ACPI_OSI_WINSRV_2003 0x04 #define ACPI_OSI_WIN_XP_SP2 0x05 #define ACPI_OSI_WINSRV_2003_SP1 0x06 #define ACPI_OSI_WIN_VISTA 0x07 #define ACPI_OSI_WINSRV_2008 0x08 #define ACPI_OSI_WIN_VISTA_SP1 0x09 #define ACPI_OSI_WIN_VISTA_SP2 0x0A #define ACPI_OSI_WIN_7 0x0B #define ACPI_ALWAYS_ILLEGAL 0x00 typedef struct acpi_interface_info { char *Name; struct acpi_interface_info *Next; UINT8 Flags; UINT8 Value; } ACPI_INTERFACE_INFO; #define ACPI_OSI_INVALID 0x01 #define ACPI_OSI_DYNAMIC 0x02 typedef struct acpi_port_info { char *Name; UINT16 Start; UINT16 End; UINT8 OsiDependency; } ACPI_PORT_INFO; /***************************************************************************** * * Resource descriptors * ****************************************************************************/ /* ResourceType values */ #define ACPI_ADDRESS_TYPE_MEMORY_RANGE 0 #define ACPI_ADDRESS_TYPE_IO_RANGE 1 #define ACPI_ADDRESS_TYPE_BUS_NUMBER_RANGE 2 /* Resource descriptor types and masks */ #define ACPI_RESOURCE_NAME_LARGE 0x80 #define ACPI_RESOURCE_NAME_SMALL 0x00 #define ACPI_RESOURCE_NAME_SMALL_MASK 0x78 /* Bits 6:3 contain the type */ #define ACPI_RESOURCE_NAME_SMALL_LENGTH_MASK 0x07 /* Bits 2:0 contain the length */ #define ACPI_RESOURCE_NAME_LARGE_MASK 0x7F /* Bits 6:0 contain the type */ /* * Small resource descriptor "names" as defined by the ACPI specification. * Note: Bits 2:0 are used for the descriptor length */ #define ACPI_RESOURCE_NAME_IRQ 0x20 #define ACPI_RESOURCE_NAME_DMA 0x28 #define ACPI_RESOURCE_NAME_START_DEPENDENT 0x30 #define ACPI_RESOURCE_NAME_END_DEPENDENT 0x38 #define ACPI_RESOURCE_NAME_IO 0x40 #define ACPI_RESOURCE_NAME_FIXED_IO 0x48 #define ACPI_RESOURCE_NAME_FIXED_DMA 0x50 #define ACPI_RESOURCE_NAME_RESERVED_S2 0x58 #define ACPI_RESOURCE_NAME_RESERVED_S3 0x60 #define ACPI_RESOURCE_NAME_RESERVED_S4 0x68 #define ACPI_RESOURCE_NAME_VENDOR_SMALL 0x70 #define ACPI_RESOURCE_NAME_END_TAG 0x78 /* * Large resource descriptor "names" as defined by the ACPI specification. * Note: includes the Large Descriptor bit in bit[7] */ #define ACPI_RESOURCE_NAME_MEMORY24 0x81 #define ACPI_RESOURCE_NAME_GENERIC_REGISTER 0x82 #define ACPI_RESOURCE_NAME_RESERVED_L1 0x83 #define ACPI_RESOURCE_NAME_VENDOR_LARGE 0x84 #define ACPI_RESOURCE_NAME_MEMORY32 0x85 #define ACPI_RESOURCE_NAME_FIXED_MEMORY32 0x86 #define ACPI_RESOURCE_NAME_ADDRESS32 0x87 #define ACPI_RESOURCE_NAME_ADDRESS16 0x88 #define ACPI_RESOURCE_NAME_EXTENDED_IRQ 0x89 #define ACPI_RESOURCE_NAME_ADDRESS64 0x8A #define ACPI_RESOURCE_NAME_EXTENDED_ADDRESS64 0x8B #define ACPI_RESOURCE_NAME_GPIO 0x8C #define ACPI_RESOURCE_NAME_SERIAL_BUS 0x8E #define ACPI_RESOURCE_NAME_LARGE_MAX 0x8E /***************************************************************************** * * Miscellaneous * ****************************************************************************/ #define ACPI_ASCII_ZERO 0x30 /***************************************************************************** * * Disassembler * ****************************************************************************/ typedef struct acpi_external_list { char *Path; char *InternalPath; struct acpi_external_list *Next; UINT32 Value; UINT16 Length; UINT8 Type; UINT8 Flags; } ACPI_EXTERNAL_LIST; /* Values for Flags field above */ #define ACPI_IPATH_ALLOCATED 0x01 typedef struct acpi_external_file { char *Path; struct acpi_external_file *Next; } ACPI_EXTERNAL_FILE; /***************************************************************************** * * Debugger * ****************************************************************************/ typedef struct acpi_db_method_info { ACPI_HANDLE MainThreadGate; ACPI_HANDLE ThreadCompleteGate; ACPI_HANDLE InfoGate; ACPI_THREAD_ID *Threads; UINT32 NumThreads; UINT32 NumCreated; UINT32 NumCompleted; char *Name; UINT32 Flags; UINT32 NumLoops; char Pathname[128]; char **Args; ACPI_OBJECT_TYPE *Types; /* * Arguments to be passed to method for the command * Threads - * the Number of threads, ID of current thread and * Index of current thread inside all them created. */ char InitArgs; ACPI_OBJECT_TYPE ArgTypes[4]; char *Arguments[4]; char NumThreadsStr[11]; char IdOfThreadStr[11]; char IndexOfThreadStr[11]; } ACPI_DB_METHOD_INFO; typedef struct acpi_integrity_info { UINT32 Nodes; UINT32 Objects; } ACPI_INTEGRITY_INFO; #define ACPI_DB_REDIRECTABLE_OUTPUT 0x01 #define ACPI_DB_CONSOLE_OUTPUT 0x02 #define ACPI_DB_DUPLICATE_OUTPUT 0x03 /***************************************************************************** * * Debug * ****************************************************************************/ /* Entry for a memory allocation (debug only) */ #define ACPI_MEM_MALLOC 0 #define ACPI_MEM_CALLOC 1 #define ACPI_MAX_MODULE_NAME 16 #define ACPI_COMMON_DEBUG_MEM_HEADER \ struct acpi_debug_mem_block *Previous; \ struct acpi_debug_mem_block *Next; \ UINT32 Size; \ UINT32 Component; \ UINT32 Line; \ char Module[ACPI_MAX_MODULE_NAME]; \ UINT8 AllocType; typedef struct acpi_debug_mem_header { ACPI_COMMON_DEBUG_MEM_HEADER } ACPI_DEBUG_MEM_HEADER; typedef struct acpi_debug_mem_block { ACPI_COMMON_DEBUG_MEM_HEADER UINT64 UserSpace; } ACPI_DEBUG_MEM_BLOCK; #define ACPI_MEM_LIST_GLOBAL 0 #define ACPI_MEM_LIST_NSNODE 1 #define ACPI_MEM_LIST_MAX 1 #define ACPI_NUM_MEM_LISTS 2 #endif /* __ACLOCAL_H__ */ diff --git a/source/include/acnamesp.h b/source/include/acnamesp.h index 5e22cb538895..4a91108eae42 100644 --- a/source/include/acnamesp.h +++ b/source/include/acnamesp.h @@ -1,477 +1,478 @@ /****************************************************************************** * * Name: acnamesp.h - Namespace subcomponent prototypes and defines * *****************************************************************************/ /* * Copyright (C) 2000 - 2012, Intel Corp. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions, and the following disclaimer, * without modification. * 2. Redistributions in binary form must reproduce at minimum a disclaimer * substantially similar to the "NO WARRANTY" disclaimer below * ("Disclaimer") and any redistribution must be conditioned upon * including a substantially similar Disclaimer requirement for further * binary redistribution. * 3. Neither the names of the above-listed copyright holders nor the names * of any contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * Alternatively, this software may be distributed under the terms of the * GNU General Public License ("GPL") version 2 as published by the Free * Software Foundation. * * NO WARRANTY * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGES. */ #ifndef __ACNAMESP_H__ #define __ACNAMESP_H__ /* To search the entire name space, pass this as SearchBase */ #define ACPI_NS_ALL ((ACPI_HANDLE)0) /* * Elements of AcpiNsProperties are bit significant * and should be one-to-one with values of ACPI_OBJECT_TYPE */ #define ACPI_NS_NORMAL 0 #define ACPI_NS_NEWSCOPE 1 /* a definition of this type opens a name scope */ #define ACPI_NS_LOCAL 2 /* suppress search of enclosing scopes */ /* Flags for AcpiNsLookup, AcpiNsSearchAndEnter */ #define ACPI_NS_NO_UPSEARCH 0 #define ACPI_NS_SEARCH_PARENT 0x01 #define ACPI_NS_DONT_OPEN_SCOPE 0x02 #define ACPI_NS_NO_PEER_SEARCH 0x04 #define ACPI_NS_ERROR_IF_FOUND 0x08 #define ACPI_NS_PREFIX_IS_SCOPE 0x10 #define ACPI_NS_EXTERNAL 0x20 #define ACPI_NS_TEMPORARY 0x40 /* Flags for AcpiNsWalkNamespace */ #define ACPI_NS_WALK_NO_UNLOCK 0 #define ACPI_NS_WALK_UNLOCK 0x01 #define ACPI_NS_WALK_TEMP_NODES 0x02 /* Object is not a package element */ #define ACPI_NOT_PACKAGE_ELEMENT ACPI_UINT32_MAX /* Always emit warning message, not dependent on node flags */ #define ACPI_WARN_ALWAYS 0 /* * nsinit - Namespace initialization */ ACPI_STATUS AcpiNsInitializeObjects ( void); ACPI_STATUS AcpiNsInitializeDevices ( void); /* * nsload - Namespace loading */ ACPI_STATUS AcpiNsLoadNamespace ( void); ACPI_STATUS AcpiNsLoadTable ( UINT32 TableIndex, ACPI_NAMESPACE_NODE *Node); /* * nswalk - walk the namespace */ ACPI_STATUS AcpiNsWalkNamespace ( ACPI_OBJECT_TYPE Type, ACPI_HANDLE StartObject, UINT32 MaxDepth, UINT32 Flags, ACPI_WALK_CALLBACK PreOrderVisit, ACPI_WALK_CALLBACK PostOrderVisit, void *Context, void **ReturnValue); ACPI_NAMESPACE_NODE * AcpiNsGetNextNode ( ACPI_NAMESPACE_NODE *Parent, ACPI_NAMESPACE_NODE *Child); ACPI_NAMESPACE_NODE * AcpiNsGetNextNodeTyped ( ACPI_OBJECT_TYPE Type, ACPI_NAMESPACE_NODE *Parent, ACPI_NAMESPACE_NODE *Child); /* * nsparse - table parsing */ ACPI_STATUS AcpiNsParseTable ( UINT32 TableIndex, ACPI_NAMESPACE_NODE *StartNode); ACPI_STATUS AcpiNsOneCompleteParse ( UINT32 PassNumber, UINT32 TableIndex, ACPI_NAMESPACE_NODE *StartNode); /* * nsaccess - Top-level namespace access */ ACPI_STATUS AcpiNsRootInitialize ( void); ACPI_STATUS AcpiNsLookup ( ACPI_GENERIC_STATE *ScopeInfo, char *Name, ACPI_OBJECT_TYPE Type, ACPI_INTERPRETER_MODE InterpreterMode, UINT32 Flags, ACPI_WALK_STATE *WalkState, ACPI_NAMESPACE_NODE **RetNode); /* * nsalloc - Named object allocation/deallocation */ ACPI_NAMESPACE_NODE * AcpiNsCreateNode ( UINT32 Name); void AcpiNsDeleteNode ( ACPI_NAMESPACE_NODE *Node); void AcpiNsRemoveNode ( ACPI_NAMESPACE_NODE *Node); void AcpiNsDeleteNamespaceSubtree ( ACPI_NAMESPACE_NODE *ParentHandle); void AcpiNsDeleteNamespaceByOwner ( ACPI_OWNER_ID OwnerId); void AcpiNsDetachObject ( ACPI_NAMESPACE_NODE *Node); void AcpiNsDeleteChildren ( ACPI_NAMESPACE_NODE *Parent); int AcpiNsCompareNames ( char *Name1, char *Name2); /* * nsdump - Namespace dump/print utilities */ void AcpiNsDumpTables ( ACPI_HANDLE SearchBase, UINT32 MaxDepth); void AcpiNsDumpEntry ( ACPI_HANDLE Handle, UINT32 DebugLevel); void AcpiNsDumpPathname ( ACPI_HANDLE Handle, char *Msg, UINT32 Level, UINT32 Component); void AcpiNsPrintPathname ( UINT32 NumSegments, char *Pathname); ACPI_STATUS AcpiNsDumpOneObject ( ACPI_HANDLE ObjHandle, UINT32 Level, void *Context, void **ReturnValue); void AcpiNsDumpObjects ( ACPI_OBJECT_TYPE Type, UINT8 DisplayType, UINT32 MaxDepth, ACPI_OWNER_ID OwnerId, ACPI_HANDLE StartHandle); /* * nseval - Namespace evaluation functions */ ACPI_STATUS AcpiNsEvaluate ( ACPI_EVALUATE_INFO *Info); void AcpiNsExecModuleCodeList ( void); /* * nspredef - Support for predefined/reserved names */ ACPI_STATUS AcpiNsCheckPredefinedNames ( ACPI_NAMESPACE_NODE *Node, UINT32 UserParamCount, ACPI_STATUS ReturnStatus, ACPI_OPERAND_OBJECT **ReturnObject); const ACPI_PREDEFINED_INFO * AcpiNsCheckForPredefinedName ( ACPI_NAMESPACE_NODE *Node); void AcpiNsCheckParameterCount ( char *Pathname, ACPI_NAMESPACE_NODE *Node, UINT32 UserParamCount, const ACPI_PREDEFINED_INFO *Info); /* * nsnames - Name and Scope manipulation */ UINT32 AcpiNsOpensScope ( ACPI_OBJECT_TYPE Type); ACPI_STATUS AcpiNsBuildExternalPath ( ACPI_NAMESPACE_NODE *Node, ACPI_SIZE Size, char *NameBuffer); char * AcpiNsGetExternalPathname ( ACPI_NAMESPACE_NODE *Node); char * AcpiNsNameOfCurrentScope ( ACPI_WALK_STATE *WalkState); ACPI_STATUS AcpiNsHandleToPathname ( ACPI_HANDLE TargetHandle, ACPI_BUFFER *Buffer); BOOLEAN AcpiNsPatternMatch ( ACPI_NAMESPACE_NODE *ObjNode, char *SearchFor); ACPI_STATUS AcpiNsGetNode ( ACPI_NAMESPACE_NODE *PrefixNode, const char *ExternalPathname, UINT32 Flags, ACPI_NAMESPACE_NODE **OutNode); ACPI_SIZE AcpiNsGetPathnameLength ( ACPI_NAMESPACE_NODE *Node); /* * nsobject - Object management for namespace nodes */ ACPI_STATUS AcpiNsAttachObject ( ACPI_NAMESPACE_NODE *Node, ACPI_OPERAND_OBJECT *Object, ACPI_OBJECT_TYPE Type); ACPI_OPERAND_OBJECT * AcpiNsGetAttachedObject ( ACPI_NAMESPACE_NODE *Node); ACPI_OPERAND_OBJECT * AcpiNsGetSecondaryObject ( ACPI_OPERAND_OBJECT *ObjDesc); ACPI_STATUS AcpiNsAttachData ( ACPI_NAMESPACE_NODE *Node, ACPI_OBJECT_HANDLER Handler, void *Data); ACPI_STATUS AcpiNsDetachData ( ACPI_NAMESPACE_NODE *Node, ACPI_OBJECT_HANDLER Handler); ACPI_STATUS AcpiNsGetAttachedData ( ACPI_NAMESPACE_NODE *Node, ACPI_OBJECT_HANDLER Handler, void **Data); /* * nsrepair - General return object repair for all * predefined methods/objects */ ACPI_STATUS AcpiNsRepairObject ( ACPI_PREDEFINED_DATA *Data, UINT32 ExpectedBtypes, UINT32 PackageIndex, ACPI_OPERAND_OBJECT **ReturnObjectPtr); ACPI_STATUS -AcpiNsRepairPackageList ( +AcpiNsWrapWithPackage ( ACPI_PREDEFINED_DATA *Data, + ACPI_OPERAND_OBJECT *OriginalObject, ACPI_OPERAND_OBJECT **ObjDescPtr); ACPI_STATUS AcpiNsRepairNullElement ( ACPI_PREDEFINED_DATA *Data, UINT32 ExpectedBtypes, UINT32 PackageIndex, ACPI_OPERAND_OBJECT **ReturnObjectPtr); void AcpiNsRemoveNullElements ( ACPI_PREDEFINED_DATA *Data, UINT8 PackageType, ACPI_OPERAND_OBJECT *ObjDesc); /* * nsrepair2 - Return object repair for specific * predefined methods/objects */ ACPI_STATUS AcpiNsComplexRepairs ( ACPI_PREDEFINED_DATA *Data, ACPI_NAMESPACE_NODE *Node, ACPI_STATUS ValidateStatus, ACPI_OPERAND_OBJECT **ReturnObjectPtr); /* * nssearch - Namespace searching and entry */ ACPI_STATUS AcpiNsSearchAndEnter ( UINT32 EntryName, ACPI_WALK_STATE *WalkState, ACPI_NAMESPACE_NODE *Node, ACPI_INTERPRETER_MODE InterpreterMode, ACPI_OBJECT_TYPE Type, UINT32 Flags, ACPI_NAMESPACE_NODE **RetNode); ACPI_STATUS AcpiNsSearchOneScope ( UINT32 EntryName, ACPI_NAMESPACE_NODE *Node, ACPI_OBJECT_TYPE Type, ACPI_NAMESPACE_NODE **RetNode); void AcpiNsInstallNode ( ACPI_WALK_STATE *WalkState, ACPI_NAMESPACE_NODE *ParentNode, ACPI_NAMESPACE_NODE *Node, ACPI_OBJECT_TYPE Type); /* * nsutils - Utility functions */ BOOLEAN AcpiNsValidRootPrefix ( char Prefix); ACPI_OBJECT_TYPE AcpiNsGetType ( ACPI_NAMESPACE_NODE *Node); UINT32 AcpiNsLocal ( ACPI_OBJECT_TYPE Type); void AcpiNsPrintNodePathname ( ACPI_NAMESPACE_NODE *Node, const char *Msg); ACPI_STATUS AcpiNsBuildInternalName ( ACPI_NAMESTRING_INFO *Info); void AcpiNsGetInternalNameLength ( ACPI_NAMESTRING_INFO *Info); ACPI_STATUS AcpiNsInternalizeName ( const char *DottedName, char **ConvertedName); ACPI_STATUS AcpiNsExternalizeName ( UINT32 InternalNameLength, const char *InternalName, UINT32 *ConvertedNameLength, char **ConvertedName); ACPI_NAMESPACE_NODE * AcpiNsValidateHandle ( ACPI_HANDLE Handle); void AcpiNsTerminate ( void); #endif /* __ACNAMESP_H__ */