10d02842fSSascha Wildner /*******************************************************************************
20d02842fSSascha Wildner *
30d02842fSSascha Wildner * Module Name: dsutils - Dispatcher utilities
40d02842fSSascha Wildner *
50d02842fSSascha Wildner ******************************************************************************/
60d02842fSSascha Wildner
7b4315fc7SSascha Wildner /******************************************************************************
8b4315fc7SSascha Wildner *
9b4315fc7SSascha Wildner * 1. Copyright Notice
10b4315fc7SSascha Wildner *
11*383048acSSascha Wildner * Some or all of this work - Copyright (c) 1999 - 2021, Intel Corp.
120d02842fSSascha Wildner * All rights reserved.
130d02842fSSascha Wildner *
14b4315fc7SSascha Wildner * 2. License
15b4315fc7SSascha Wildner *
16b4315fc7SSascha Wildner * 2.1. This is your license from Intel Corp. under its intellectual property
17b4315fc7SSascha Wildner * rights. You may have additional license terms from the party that provided
18b4315fc7SSascha Wildner * you this software, covering your right to use that party's intellectual
19b4315fc7SSascha Wildner * property rights.
20b4315fc7SSascha Wildner *
21b4315fc7SSascha Wildner * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a
22b4315fc7SSascha Wildner * copy of the source code appearing in this file ("Covered Code") an
23b4315fc7SSascha Wildner * irrevocable, perpetual, worldwide license under Intel's copyrights in the
24b4315fc7SSascha Wildner * base code distributed originally by Intel ("Original Intel Code") to copy,
25b4315fc7SSascha Wildner * make derivatives, distribute, use and display any portion of the Covered
26b4315fc7SSascha Wildner * Code in any form, with the right to sublicense such rights; and
27b4315fc7SSascha Wildner *
28b4315fc7SSascha Wildner * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent
29b4315fc7SSascha Wildner * license (with the right to sublicense), under only those claims of Intel
30b4315fc7SSascha Wildner * patents that are infringed by the Original Intel Code, to make, use, sell,
31b4315fc7SSascha Wildner * offer to sell, and import the Covered Code and derivative works thereof
32b4315fc7SSascha Wildner * solely to the minimum extent necessary to exercise the above copyright
33b4315fc7SSascha Wildner * license, and in no event shall the patent license extend to any additions
34b4315fc7SSascha Wildner * to or modifications of the Original Intel Code. No other license or right
35b4315fc7SSascha Wildner * is granted directly or by implication, estoppel or otherwise;
36b4315fc7SSascha Wildner *
37b4315fc7SSascha Wildner * The above copyright and patent license is granted only if the following
38b4315fc7SSascha Wildner * conditions are met:
39b4315fc7SSascha Wildner *
40b4315fc7SSascha Wildner * 3. Conditions
41b4315fc7SSascha Wildner *
42b4315fc7SSascha Wildner * 3.1. Redistribution of Source with Rights to Further Distribute Source.
43b4315fc7SSascha Wildner * Redistribution of source code of any substantial portion of the Covered
44b4315fc7SSascha Wildner * Code or modification with rights to further distribute source must include
45b4315fc7SSascha Wildner * the above Copyright Notice, the above License, this list of Conditions,
46b4315fc7SSascha Wildner * and the following Disclaimer and Export Compliance provision. In addition,
47b4315fc7SSascha Wildner * Licensee must cause all Covered Code to which Licensee contributes to
48b4315fc7SSascha Wildner * contain a file documenting the changes Licensee made to create that Covered
49b4315fc7SSascha Wildner * Code and the date of any change. Licensee must include in that file the
50b4315fc7SSascha Wildner * documentation of any changes made by any predecessor Licensee. Licensee
51b4315fc7SSascha Wildner * must include a prominent statement that the modification is derived,
52b4315fc7SSascha Wildner * directly or indirectly, from Original Intel Code.
53b4315fc7SSascha Wildner *
54b4315fc7SSascha Wildner * 3.2. Redistribution of Source with no Rights to Further Distribute Source.
55b4315fc7SSascha Wildner * Redistribution of source code of any substantial portion of the Covered
56b4315fc7SSascha Wildner * Code or modification without rights to further distribute source must
57b4315fc7SSascha Wildner * include the following Disclaimer and Export Compliance provision in the
58b4315fc7SSascha Wildner * documentation and/or other materials provided with distribution. In
59b4315fc7SSascha Wildner * addition, Licensee may not authorize further sublicense of source of any
60b4315fc7SSascha Wildner * portion of the Covered Code, and must include terms to the effect that the
61b4315fc7SSascha Wildner * license from Licensee to its licensee is limited to the intellectual
62b4315fc7SSascha Wildner * property embodied in the software Licensee provides to its licensee, and
63b4315fc7SSascha Wildner * not to intellectual property embodied in modifications its licensee may
64b4315fc7SSascha Wildner * make.
65b4315fc7SSascha Wildner *
66b4315fc7SSascha Wildner * 3.3. Redistribution of Executable. Redistribution in executable form of any
67b4315fc7SSascha Wildner * substantial portion of the Covered Code or modification must reproduce the
68b4315fc7SSascha Wildner * above Copyright Notice, and the following Disclaimer and Export Compliance
69b4315fc7SSascha Wildner * provision in the documentation and/or other materials provided with the
70b4315fc7SSascha Wildner * distribution.
71b4315fc7SSascha Wildner *
72b4315fc7SSascha Wildner * 3.4. Intel retains all right, title, and interest in and to the Original
73b4315fc7SSascha Wildner * Intel Code.
74b4315fc7SSascha Wildner *
75b4315fc7SSascha Wildner * 3.5. Neither the name Intel nor any other trademark owned or controlled by
76b4315fc7SSascha Wildner * Intel shall be used in advertising or otherwise to promote the sale, use or
77b4315fc7SSascha Wildner * other dealings in products derived from or relating to the Covered Code
78b4315fc7SSascha Wildner * without prior written authorization from Intel.
79b4315fc7SSascha Wildner *
80b4315fc7SSascha Wildner * 4. Disclaimer and Export Compliance
81b4315fc7SSascha Wildner *
82b4315fc7SSascha Wildner * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED
83b4315fc7SSascha Wildner * HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE
84b4315fc7SSascha Wildner * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE,
85b4315fc7SSascha Wildner * INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY
86b4315fc7SSascha Wildner * UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY
87b4315fc7SSascha Wildner * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A
88b4315fc7SSascha Wildner * PARTICULAR PURPOSE.
89b4315fc7SSascha Wildner *
90b4315fc7SSascha Wildner * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES
91b4315fc7SSascha Wildner * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR
92b4315fc7SSascha Wildner * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT,
93b4315fc7SSascha Wildner * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY
94b4315fc7SSascha Wildner * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL
95b4315fc7SSascha Wildner * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS
96b4315fc7SSascha Wildner * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY
97b4315fc7SSascha Wildner * LIMITED REMEDY.
98b4315fc7SSascha Wildner *
99b4315fc7SSascha Wildner * 4.3. Licensee shall not export, either directly or indirectly, any of this
100b4315fc7SSascha Wildner * software or system incorporating such software without first obtaining any
101b4315fc7SSascha Wildner * required license or other approval from the U. S. Department of Commerce or
102b4315fc7SSascha Wildner * any other agency or department of the United States Government. In the
103b4315fc7SSascha Wildner * event Licensee exports any such software from the United States or
104b4315fc7SSascha Wildner * re-exports any such software from a foreign destination, Licensee shall
105b4315fc7SSascha Wildner * ensure that the distribution and export/re-export of the software is in
106b4315fc7SSascha Wildner * compliance with all laws, regulations, orders, or other restrictions of the
107b4315fc7SSascha Wildner * U.S. Export Administration Regulations. Licensee agrees that neither it nor
108b4315fc7SSascha Wildner * any of its subsidiaries will export/re-export any technical data, process,
109b4315fc7SSascha Wildner * software, or service, directly or indirectly, to any country for which the
110b4315fc7SSascha Wildner * United States government or any agency thereof requires an export license,
111b4315fc7SSascha Wildner * other governmental approval, or letter of assurance, without first obtaining
112b4315fc7SSascha Wildner * such license, approval or letter.
113b4315fc7SSascha Wildner *
114b4315fc7SSascha Wildner *****************************************************************************
115b4315fc7SSascha Wildner *
116b4315fc7SSascha Wildner * Alternatively, you may choose to be licensed under the terms of the
117b4315fc7SSascha Wildner * following license:
118b4315fc7SSascha Wildner *
1190d02842fSSascha Wildner * Redistribution and use in source and binary forms, with or without
1200d02842fSSascha Wildner * modification, are permitted provided that the following conditions
1210d02842fSSascha Wildner * are met:
1220d02842fSSascha Wildner * 1. Redistributions of source code must retain the above copyright
1230d02842fSSascha Wildner * notice, this list of conditions, and the following disclaimer,
1240d02842fSSascha Wildner * without modification.
1250d02842fSSascha Wildner * 2. Redistributions in binary form must reproduce at minimum a disclaimer
1260d02842fSSascha Wildner * substantially similar to the "NO WARRANTY" disclaimer below
1270d02842fSSascha Wildner * ("Disclaimer") and any redistribution must be conditioned upon
1280d02842fSSascha Wildner * including a substantially similar Disclaimer requirement for further
1290d02842fSSascha Wildner * binary redistribution.
1300d02842fSSascha Wildner * 3. Neither the names of the above-listed copyright holders nor the names
1310d02842fSSascha Wildner * of any contributors may be used to endorse or promote products derived
1320d02842fSSascha Wildner * from this software without specific prior written permission.
1330d02842fSSascha Wildner *
134b4315fc7SSascha Wildner * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
135b4315fc7SSascha Wildner * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
136b4315fc7SSascha Wildner * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
137b4315fc7SSascha Wildner * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
138b4315fc7SSascha Wildner * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
139b4315fc7SSascha Wildner * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
140b4315fc7SSascha Wildner * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
141b4315fc7SSascha Wildner * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
142b4315fc7SSascha Wildner * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
143b4315fc7SSascha Wildner * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
144b4315fc7SSascha Wildner * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
145b4315fc7SSascha Wildner *
146b4315fc7SSascha Wildner * Alternatively, you may choose to be licensed under the terms of the
1470d02842fSSascha Wildner * GNU General Public License ("GPL") version 2 as published by the Free
1480d02842fSSascha Wildner * Software Foundation.
1490d02842fSSascha Wildner *
150b4315fc7SSascha Wildner *****************************************************************************/
1510d02842fSSascha Wildner
1520d02842fSSascha Wildner #include "acpi.h"
1530d02842fSSascha Wildner #include "accommon.h"
1540d02842fSSascha Wildner #include "acparser.h"
1550d02842fSSascha Wildner #include "amlcode.h"
1560d02842fSSascha Wildner #include "acdispat.h"
1570d02842fSSascha Wildner #include "acinterp.h"
1580d02842fSSascha Wildner #include "acnamesp.h"
1590d02842fSSascha Wildner #include "acdebug.h"
1600d02842fSSascha Wildner
1610d02842fSSascha Wildner #define _COMPONENT ACPI_DISPATCHER
1620d02842fSSascha Wildner ACPI_MODULE_NAME ("dsutils")
1630d02842fSSascha Wildner
1640d02842fSSascha Wildner
1650d02842fSSascha Wildner /*******************************************************************************
1660d02842fSSascha Wildner *
1670d02842fSSascha Wildner * FUNCTION: AcpiDsClearImplicitReturn
1680d02842fSSascha Wildner *
1690d02842fSSascha Wildner * PARAMETERS: WalkState - Current State
1700d02842fSSascha Wildner *
1710d02842fSSascha Wildner * RETURN: None.
1720d02842fSSascha Wildner *
1730d02842fSSascha Wildner * DESCRIPTION: Clear and remove a reference on an implicit return value. Used
1740d02842fSSascha Wildner * to delete "stale" return values (if enabled, the return value
1750d02842fSSascha Wildner * from every operator is saved at least momentarily, in case the
1760d02842fSSascha Wildner * parent method exits.)
1770d02842fSSascha Wildner *
1780d02842fSSascha Wildner ******************************************************************************/
1790d02842fSSascha Wildner
1800d02842fSSascha Wildner void
AcpiDsClearImplicitReturn(ACPI_WALK_STATE * WalkState)1810d02842fSSascha Wildner AcpiDsClearImplicitReturn (
1820d02842fSSascha Wildner ACPI_WALK_STATE *WalkState)
1830d02842fSSascha Wildner {
1840d02842fSSascha Wildner ACPI_FUNCTION_NAME (DsClearImplicitReturn);
1850d02842fSSascha Wildner
1860d02842fSSascha Wildner
1870d02842fSSascha Wildner /*
1880d02842fSSascha Wildner * Slack must be enabled for this feature
1890d02842fSSascha Wildner */
1900d02842fSSascha Wildner if (!AcpiGbl_EnableInterpreterSlack)
1910d02842fSSascha Wildner {
1920d02842fSSascha Wildner return;
1930d02842fSSascha Wildner }
1940d02842fSSascha Wildner
1950d02842fSSascha Wildner if (WalkState->ImplicitReturnObj)
1960d02842fSSascha Wildner {
1970d02842fSSascha Wildner /*
1980d02842fSSascha Wildner * Delete any "stale" implicit return. However, in
1990d02842fSSascha Wildner * complex statements, the implicit return value can be
2000d02842fSSascha Wildner * bubbled up several levels.
2010d02842fSSascha Wildner */
2020d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
2030d02842fSSascha Wildner "Removing reference on stale implicit return obj %p\n",
2040d02842fSSascha Wildner WalkState->ImplicitReturnObj));
2050d02842fSSascha Wildner
2060d02842fSSascha Wildner AcpiUtRemoveReference (WalkState->ImplicitReturnObj);
2070d02842fSSascha Wildner WalkState->ImplicitReturnObj = NULL;
2080d02842fSSascha Wildner }
2090d02842fSSascha Wildner }
2100d02842fSSascha Wildner
2110d02842fSSascha Wildner
2120d02842fSSascha Wildner /*******************************************************************************
2130d02842fSSascha Wildner *
2140d02842fSSascha Wildner * FUNCTION: AcpiDsDoImplicitReturn
2150d02842fSSascha Wildner *
2160d02842fSSascha Wildner * PARAMETERS: ReturnDesc - The return value
2170d02842fSSascha Wildner * WalkState - Current State
2180d02842fSSascha Wildner * AddReference - True if a reference should be added to the
2190d02842fSSascha Wildner * return object
2200d02842fSSascha Wildner *
2210d02842fSSascha Wildner * RETURN: TRUE if implicit return enabled, FALSE otherwise
2220d02842fSSascha Wildner *
2230d02842fSSascha Wildner * DESCRIPTION: Implements the optional "implicit return". We save the result
2240d02842fSSascha Wildner * of every ASL operator and control method invocation in case the
2250d02842fSSascha Wildner * parent method exit. Before storing a new return value, we
2260d02842fSSascha Wildner * delete the previous return value.
2270d02842fSSascha Wildner *
2280d02842fSSascha Wildner ******************************************************************************/
2290d02842fSSascha Wildner
2300d02842fSSascha Wildner BOOLEAN
AcpiDsDoImplicitReturn(ACPI_OPERAND_OBJECT * ReturnDesc,ACPI_WALK_STATE * WalkState,BOOLEAN AddReference)2310d02842fSSascha Wildner AcpiDsDoImplicitReturn (
2320d02842fSSascha Wildner ACPI_OPERAND_OBJECT *ReturnDesc,
2330d02842fSSascha Wildner ACPI_WALK_STATE *WalkState,
2340d02842fSSascha Wildner BOOLEAN AddReference)
2350d02842fSSascha Wildner {
2360d02842fSSascha Wildner ACPI_FUNCTION_NAME (DsDoImplicitReturn);
2370d02842fSSascha Wildner
2380d02842fSSascha Wildner
2390d02842fSSascha Wildner /*
2400d02842fSSascha Wildner * Slack must be enabled for this feature, and we must
2410d02842fSSascha Wildner * have a valid return object
2420d02842fSSascha Wildner */
2430d02842fSSascha Wildner if ((!AcpiGbl_EnableInterpreterSlack) ||
2440d02842fSSascha Wildner (!ReturnDesc))
2450d02842fSSascha Wildner {
2460d02842fSSascha Wildner return (FALSE);
2470d02842fSSascha Wildner }
2480d02842fSSascha Wildner
2490d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
2500d02842fSSascha Wildner "Result %p will be implicitly returned; Prev=%p\n",
2510d02842fSSascha Wildner ReturnDesc,
2520d02842fSSascha Wildner WalkState->ImplicitReturnObj));
2530d02842fSSascha Wildner
2540d02842fSSascha Wildner /*
2550d02842fSSascha Wildner * Delete any "stale" implicit return value first. However, in
2560d02842fSSascha Wildner * complex statements, the implicit return value can be
2570d02842fSSascha Wildner * bubbled up several levels, so we don't clear the value if it
2580d02842fSSascha Wildner * is the same as the ReturnDesc.
2590d02842fSSascha Wildner */
2600d02842fSSascha Wildner if (WalkState->ImplicitReturnObj)
2610d02842fSSascha Wildner {
2620d02842fSSascha Wildner if (WalkState->ImplicitReturnObj == ReturnDesc)
2630d02842fSSascha Wildner {
2640d02842fSSascha Wildner return (TRUE);
2650d02842fSSascha Wildner }
2660d02842fSSascha Wildner AcpiDsClearImplicitReturn (WalkState);
2670d02842fSSascha Wildner }
2680d02842fSSascha Wildner
2690d02842fSSascha Wildner /* Save the implicit return value, add a reference if requested */
2700d02842fSSascha Wildner
2710d02842fSSascha Wildner WalkState->ImplicitReturnObj = ReturnDesc;
2720d02842fSSascha Wildner if (AddReference)
2730d02842fSSascha Wildner {
2740d02842fSSascha Wildner AcpiUtAddReference (ReturnDesc);
2750d02842fSSascha Wildner }
2760d02842fSSascha Wildner
2770d02842fSSascha Wildner return (TRUE);
2780d02842fSSascha Wildner }
2790d02842fSSascha Wildner
2800d02842fSSascha Wildner
2810d02842fSSascha Wildner /*******************************************************************************
2820d02842fSSascha Wildner *
2830d02842fSSascha Wildner * FUNCTION: AcpiDsIsResultUsed
2840d02842fSSascha Wildner *
2850d02842fSSascha Wildner * PARAMETERS: Op - Current Op
2860d02842fSSascha Wildner * WalkState - Current State
2870d02842fSSascha Wildner *
2880d02842fSSascha Wildner * RETURN: TRUE if result is used, FALSE otherwise
2890d02842fSSascha Wildner *
2900d02842fSSascha Wildner * DESCRIPTION: Check if a result object will be used by the parent
2910d02842fSSascha Wildner *
2920d02842fSSascha Wildner ******************************************************************************/
2930d02842fSSascha Wildner
2940d02842fSSascha Wildner BOOLEAN
AcpiDsIsResultUsed(ACPI_PARSE_OBJECT * Op,ACPI_WALK_STATE * WalkState)2950d02842fSSascha Wildner AcpiDsIsResultUsed (
2960d02842fSSascha Wildner ACPI_PARSE_OBJECT *Op,
2970d02842fSSascha Wildner ACPI_WALK_STATE *WalkState)
2980d02842fSSascha Wildner {
2990d02842fSSascha Wildner const ACPI_OPCODE_INFO *ParentInfo;
3000d02842fSSascha Wildner
3010d02842fSSascha Wildner ACPI_FUNCTION_TRACE_PTR (DsIsResultUsed, Op);
3020d02842fSSascha Wildner
3030d02842fSSascha Wildner
3040d02842fSSascha Wildner /* Must have both an Op and a Result Object */
3050d02842fSSascha Wildner
3060d02842fSSascha Wildner if (!Op)
3070d02842fSSascha Wildner {
3080d02842fSSascha Wildner ACPI_ERROR ((AE_INFO, "Null Op"));
3090d02842fSSascha Wildner return_UINT8 (TRUE);
3100d02842fSSascha Wildner }
3110d02842fSSascha Wildner
3120d02842fSSascha Wildner /*
3130d02842fSSascha Wildner * We know that this operator is not a
3140d02842fSSascha Wildner * Return() operator (would not come here.) The following code is the
3150d02842fSSascha Wildner * optional support for a so-called "implicit return". Some AML code
3160d02842fSSascha Wildner * assumes that the last value of the method is "implicitly" returned
3170d02842fSSascha Wildner * to the caller. Just save the last result as the return value.
3180d02842fSSascha Wildner * NOTE: this is optional because the ASL language does not actually
3190d02842fSSascha Wildner * support this behavior.
3200d02842fSSascha Wildner */
3210d02842fSSascha Wildner (void) AcpiDsDoImplicitReturn (WalkState->ResultObj, WalkState, TRUE);
3220d02842fSSascha Wildner
3230d02842fSSascha Wildner /*
3240d02842fSSascha Wildner * Now determine if the parent will use the result
3250d02842fSSascha Wildner *
3260d02842fSSascha Wildner * If there is no parent, or the parent is a ScopeOp, we are executing
3270d02842fSSascha Wildner * at the method level. An executing method typically has no parent,
3280d02842fSSascha Wildner * since each method is parsed separately. A method invoked externally
3290d02842fSSascha Wildner * via ExecuteControlMethod has a ScopeOp as the parent.
3300d02842fSSascha Wildner */
3310d02842fSSascha Wildner if ((!Op->Common.Parent) ||
3320d02842fSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_SCOPE_OP))
3330d02842fSSascha Wildner {
3340d02842fSSascha Wildner /* No parent, the return value cannot possibly be used */
3350d02842fSSascha Wildner
3360d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
3370d02842fSSascha Wildner "At Method level, result of [%s] not used\n",
3380d02842fSSascha Wildner AcpiPsGetOpcodeName (Op->Common.AmlOpcode)));
3390d02842fSSascha Wildner return_UINT8 (FALSE);
3400d02842fSSascha Wildner }
3410d02842fSSascha Wildner
3420d02842fSSascha Wildner /* Get info on the parent. The RootOp is AML_SCOPE */
3430d02842fSSascha Wildner
3440d02842fSSascha Wildner ParentInfo = AcpiPsGetOpcodeInfo (Op->Common.Parent->Common.AmlOpcode);
3450d02842fSSascha Wildner if (ParentInfo->Class == AML_CLASS_UNKNOWN)
3460d02842fSSascha Wildner {
3470d02842fSSascha Wildner ACPI_ERROR ((AE_INFO,
3480d02842fSSascha Wildner "Unknown parent opcode Op=%p", Op));
3490d02842fSSascha Wildner return_UINT8 (FALSE);
3500d02842fSSascha Wildner }
3510d02842fSSascha Wildner
3520d02842fSSascha Wildner /*
3530d02842fSSascha Wildner * Decide what to do with the result based on the parent. If
3540d02842fSSascha Wildner * the parent opcode will not use the result, delete the object.
3550d02842fSSascha Wildner * Otherwise leave it as is, it will be deleted when it is used
3560d02842fSSascha Wildner * as an operand later.
3570d02842fSSascha Wildner */
3580d02842fSSascha Wildner switch (ParentInfo->Class)
3590d02842fSSascha Wildner {
3600d02842fSSascha Wildner case AML_CLASS_CONTROL:
3610d02842fSSascha Wildner
3620d02842fSSascha Wildner switch (Op->Common.Parent->Common.AmlOpcode)
3630d02842fSSascha Wildner {
3640d02842fSSascha Wildner case AML_RETURN_OP:
3650d02842fSSascha Wildner
3660d02842fSSascha Wildner /* Never delete the return value associated with a return opcode */
3670d02842fSSascha Wildner
3680d02842fSSascha Wildner goto ResultUsed;
3690d02842fSSascha Wildner
3700d02842fSSascha Wildner case AML_IF_OP:
3710d02842fSSascha Wildner case AML_WHILE_OP:
3720d02842fSSascha Wildner /*
3730d02842fSSascha Wildner * If we are executing the predicate AND this is the predicate op,
3740d02842fSSascha Wildner * we will use the return value
3750d02842fSSascha Wildner */
376820c5b08SSascha Wildner if ((WalkState->ControlState->Common.State ==
377820c5b08SSascha Wildner ACPI_CONTROL_PREDICATE_EXECUTING) &&
3780d02842fSSascha Wildner (WalkState->ControlState->Control.PredicateOp == Op))
3790d02842fSSascha Wildner {
3800d02842fSSascha Wildner goto ResultUsed;
3810d02842fSSascha Wildner }
3820d02842fSSascha Wildner break;
3830d02842fSSascha Wildner
3840d02842fSSascha Wildner default:
3850d02842fSSascha Wildner
3860d02842fSSascha Wildner /* Ignore other control opcodes */
3870d02842fSSascha Wildner
3880d02842fSSascha Wildner break;
3890d02842fSSascha Wildner }
3900d02842fSSascha Wildner
3910d02842fSSascha Wildner /* The general control opcode returns no result */
3920d02842fSSascha Wildner
3930d02842fSSascha Wildner goto ResultNotUsed;
3940d02842fSSascha Wildner
3950d02842fSSascha Wildner case AML_CLASS_CREATE:
3960d02842fSSascha Wildner /*
3970d02842fSSascha Wildner * These opcodes allow TermArg(s) as operands and therefore
3980d02842fSSascha Wildner * the operands can be method calls. The result is used.
3990d02842fSSascha Wildner */
4000d02842fSSascha Wildner goto ResultUsed;
4010d02842fSSascha Wildner
4020d02842fSSascha Wildner case AML_CLASS_NAMED_OBJECT:
4030d02842fSSascha Wildner
4040d02842fSSascha Wildner if ((Op->Common.Parent->Common.AmlOpcode == AML_REGION_OP) ||
4050d02842fSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_DATA_REGION_OP) ||
4060d02842fSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_PACKAGE_OP) ||
4070d02842fSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_BUFFER_OP) ||
408d638c6eeSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_VARIABLE_PACKAGE_OP) ||
4090d02842fSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_INT_EVAL_SUBTREE_OP) ||
4100d02842fSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_BANK_FIELD_OP))
4110d02842fSSascha Wildner {
4120d02842fSSascha Wildner /*
4130d02842fSSascha Wildner * These opcodes allow TermArg(s) as operands and therefore
4140d02842fSSascha Wildner * the operands can be method calls. The result is used.
4150d02842fSSascha Wildner */
4160d02842fSSascha Wildner goto ResultUsed;
4170d02842fSSascha Wildner }
4180d02842fSSascha Wildner
4190d02842fSSascha Wildner goto ResultNotUsed;
4200d02842fSSascha Wildner
4210d02842fSSascha Wildner default:
4220d02842fSSascha Wildner /*
4230d02842fSSascha Wildner * In all other cases. the parent will actually use the return
4240d02842fSSascha Wildner * object, so keep it.
4250d02842fSSascha Wildner */
4260d02842fSSascha Wildner goto ResultUsed;
4270d02842fSSascha Wildner }
4280d02842fSSascha Wildner
4290d02842fSSascha Wildner
4300d02842fSSascha Wildner ResultUsed:
4310d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
4320d02842fSSascha Wildner "Result of [%s] used by Parent [%s] Op=%p\n",
4330d02842fSSascha Wildner AcpiPsGetOpcodeName (Op->Common.AmlOpcode),
4340d02842fSSascha Wildner AcpiPsGetOpcodeName (Op->Common.Parent->Common.AmlOpcode), Op));
4350d02842fSSascha Wildner
4360d02842fSSascha Wildner return_UINT8 (TRUE);
4370d02842fSSascha Wildner
4380d02842fSSascha Wildner
4390d02842fSSascha Wildner ResultNotUsed:
4400d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
4410d02842fSSascha Wildner "Result of [%s] not used by Parent [%s] Op=%p\n",
4420d02842fSSascha Wildner AcpiPsGetOpcodeName (Op->Common.AmlOpcode),
4430d02842fSSascha Wildner AcpiPsGetOpcodeName (Op->Common.Parent->Common.AmlOpcode), Op));
4440d02842fSSascha Wildner
4450d02842fSSascha Wildner return_UINT8 (FALSE);
4460d02842fSSascha Wildner }
4470d02842fSSascha Wildner
4480d02842fSSascha Wildner
4490d02842fSSascha Wildner /*******************************************************************************
4500d02842fSSascha Wildner *
4510d02842fSSascha Wildner * FUNCTION: AcpiDsDeleteResultIfNotUsed
4520d02842fSSascha Wildner *
4530d02842fSSascha Wildner * PARAMETERS: Op - Current parse Op
4540d02842fSSascha Wildner * ResultObj - Result of the operation
4550d02842fSSascha Wildner * WalkState - Current state
4560d02842fSSascha Wildner *
4570d02842fSSascha Wildner * RETURN: Status
4580d02842fSSascha Wildner *
4590d02842fSSascha Wildner * DESCRIPTION: Used after interpretation of an opcode. If there is an internal
4600d02842fSSascha Wildner * result descriptor, check if the parent opcode will actually use
4610d02842fSSascha Wildner * this result. If not, delete the result now so that it will
4620d02842fSSascha Wildner * not become orphaned.
4630d02842fSSascha Wildner *
4640d02842fSSascha Wildner ******************************************************************************/
4650d02842fSSascha Wildner
4660d02842fSSascha Wildner void
AcpiDsDeleteResultIfNotUsed(ACPI_PARSE_OBJECT * Op,ACPI_OPERAND_OBJECT * ResultObj,ACPI_WALK_STATE * WalkState)4670d02842fSSascha Wildner AcpiDsDeleteResultIfNotUsed (
4680d02842fSSascha Wildner ACPI_PARSE_OBJECT *Op,
4690d02842fSSascha Wildner ACPI_OPERAND_OBJECT *ResultObj,
4700d02842fSSascha Wildner ACPI_WALK_STATE *WalkState)
4710d02842fSSascha Wildner {
4720d02842fSSascha Wildner ACPI_OPERAND_OBJECT *ObjDesc;
4730d02842fSSascha Wildner ACPI_STATUS Status;
4740d02842fSSascha Wildner
4750d02842fSSascha Wildner
4760d02842fSSascha Wildner ACPI_FUNCTION_TRACE_PTR (DsDeleteResultIfNotUsed, ResultObj);
4770d02842fSSascha Wildner
4780d02842fSSascha Wildner
4790d02842fSSascha Wildner if (!Op)
4800d02842fSSascha Wildner {
4810d02842fSSascha Wildner ACPI_ERROR ((AE_INFO, "Null Op"));
4820d02842fSSascha Wildner return_VOID;
4830d02842fSSascha Wildner }
4840d02842fSSascha Wildner
4850d02842fSSascha Wildner if (!ResultObj)
4860d02842fSSascha Wildner {
4870d02842fSSascha Wildner return_VOID;
4880d02842fSSascha Wildner }
4890d02842fSSascha Wildner
4900d02842fSSascha Wildner if (!AcpiDsIsResultUsed (Op, WalkState))
4910d02842fSSascha Wildner {
4920d02842fSSascha Wildner /* Must pop the result stack (ObjDesc should be equal to ResultObj) */
4930d02842fSSascha Wildner
4940d02842fSSascha Wildner Status = AcpiDsResultPop (&ObjDesc, WalkState);
4950d02842fSSascha Wildner if (ACPI_SUCCESS (Status))
4960d02842fSSascha Wildner {
4970d02842fSSascha Wildner AcpiUtRemoveReference (ResultObj);
4980d02842fSSascha Wildner }
4990d02842fSSascha Wildner }
5000d02842fSSascha Wildner
5010d02842fSSascha Wildner return_VOID;
5020d02842fSSascha Wildner }
5030d02842fSSascha Wildner
5040d02842fSSascha Wildner
5050d02842fSSascha Wildner /*******************************************************************************
5060d02842fSSascha Wildner *
5070d02842fSSascha Wildner * FUNCTION: AcpiDsResolveOperands
5080d02842fSSascha Wildner *
5090d02842fSSascha Wildner * PARAMETERS: WalkState - Current walk state with operands on stack
5100d02842fSSascha Wildner *
5110d02842fSSascha Wildner * RETURN: Status
5120d02842fSSascha Wildner *
5130d02842fSSascha Wildner * DESCRIPTION: Resolve all operands to their values. Used to prepare
5140d02842fSSascha Wildner * arguments to a control method invocation (a call from one
5150d02842fSSascha Wildner * method to another.)
5160d02842fSSascha Wildner *
5170d02842fSSascha Wildner ******************************************************************************/
5180d02842fSSascha Wildner
5190d02842fSSascha Wildner ACPI_STATUS
AcpiDsResolveOperands(ACPI_WALK_STATE * WalkState)5200d02842fSSascha Wildner AcpiDsResolveOperands (
5210d02842fSSascha Wildner ACPI_WALK_STATE *WalkState)
5220d02842fSSascha Wildner {
5230d02842fSSascha Wildner UINT32 i;
5240d02842fSSascha Wildner ACPI_STATUS Status = AE_OK;
5250d02842fSSascha Wildner
5260d02842fSSascha Wildner
5270d02842fSSascha Wildner ACPI_FUNCTION_TRACE_PTR (DsResolveOperands, WalkState);
5280d02842fSSascha Wildner
5290d02842fSSascha Wildner
5300d02842fSSascha Wildner /*
5310d02842fSSascha Wildner * Attempt to resolve each of the valid operands
5320d02842fSSascha Wildner * Method arguments are passed by reference, not by value. This means
5330d02842fSSascha Wildner * that the actual objects are passed, not copies of the objects.
5340d02842fSSascha Wildner */
5350d02842fSSascha Wildner for (i = 0; i < WalkState->NumOperands; i++)
5360d02842fSSascha Wildner {
5370d02842fSSascha Wildner Status = AcpiExResolveToValue (&WalkState->Operands[i], WalkState);
5380d02842fSSascha Wildner if (ACPI_FAILURE (Status))
5390d02842fSSascha Wildner {
5400d02842fSSascha Wildner break;
5410d02842fSSascha Wildner }
5420d02842fSSascha Wildner }
5430d02842fSSascha Wildner
5440d02842fSSascha Wildner return_ACPI_STATUS (Status);
5450d02842fSSascha Wildner }
5460d02842fSSascha Wildner
5470d02842fSSascha Wildner
5480d02842fSSascha Wildner /*******************************************************************************
5490d02842fSSascha Wildner *
5500d02842fSSascha Wildner * FUNCTION: AcpiDsClearOperands
5510d02842fSSascha Wildner *
5520d02842fSSascha Wildner * PARAMETERS: WalkState - Current walk state with operands on stack
5530d02842fSSascha Wildner *
5540d02842fSSascha Wildner * RETURN: None
5550d02842fSSascha Wildner *
5560d02842fSSascha Wildner * DESCRIPTION: Clear all operands on the current walk state operand stack.
5570d02842fSSascha Wildner *
5580d02842fSSascha Wildner ******************************************************************************/
5590d02842fSSascha Wildner
5600d02842fSSascha Wildner void
AcpiDsClearOperands(ACPI_WALK_STATE * WalkState)5610d02842fSSascha Wildner AcpiDsClearOperands (
5620d02842fSSascha Wildner ACPI_WALK_STATE *WalkState)
5630d02842fSSascha Wildner {
5640d02842fSSascha Wildner UINT32 i;
5650d02842fSSascha Wildner
5660d02842fSSascha Wildner
5670d02842fSSascha Wildner ACPI_FUNCTION_TRACE_PTR (DsClearOperands, WalkState);
5680d02842fSSascha Wildner
5690d02842fSSascha Wildner
5700d02842fSSascha Wildner /* Remove a reference on each operand on the stack */
5710d02842fSSascha Wildner
5720d02842fSSascha Wildner for (i = 0; i < WalkState->NumOperands; i++)
5730d02842fSSascha Wildner {
5740d02842fSSascha Wildner /*
5750d02842fSSascha Wildner * Remove a reference to all operands, including both
5760d02842fSSascha Wildner * "Arguments" and "Targets".
5770d02842fSSascha Wildner */
5780d02842fSSascha Wildner AcpiUtRemoveReference (WalkState->Operands[i]);
5790d02842fSSascha Wildner WalkState->Operands[i] = NULL;
5800d02842fSSascha Wildner }
5810d02842fSSascha Wildner
5820d02842fSSascha Wildner WalkState->NumOperands = 0;
5830d02842fSSascha Wildner return_VOID;
5840d02842fSSascha Wildner }
5850d02842fSSascha Wildner
5860d02842fSSascha Wildner
5870d02842fSSascha Wildner /*******************************************************************************
5880d02842fSSascha Wildner *
5890d02842fSSascha Wildner * FUNCTION: AcpiDsCreateOperand
5900d02842fSSascha Wildner *
5910d02842fSSascha Wildner * PARAMETERS: WalkState - Current walk state
5920d02842fSSascha Wildner * Arg - Parse object for the argument
5930d02842fSSascha Wildner * ArgIndex - Which argument (zero based)
5940d02842fSSascha Wildner *
5950d02842fSSascha Wildner * RETURN: Status
5960d02842fSSascha Wildner *
5970d02842fSSascha Wildner * DESCRIPTION: Translate a parse tree object that is an argument to an AML
5980d02842fSSascha Wildner * opcode to the equivalent interpreter object. This may include
5990d02842fSSascha Wildner * looking up a name or entering a new name into the internal
6000d02842fSSascha Wildner * namespace.
6010d02842fSSascha Wildner *
6020d02842fSSascha Wildner ******************************************************************************/
6030d02842fSSascha Wildner
6040d02842fSSascha Wildner ACPI_STATUS
AcpiDsCreateOperand(ACPI_WALK_STATE * WalkState,ACPI_PARSE_OBJECT * Arg,UINT32 ArgIndex)6050d02842fSSascha Wildner AcpiDsCreateOperand (
6060d02842fSSascha Wildner ACPI_WALK_STATE *WalkState,
6070d02842fSSascha Wildner ACPI_PARSE_OBJECT *Arg,
6080d02842fSSascha Wildner UINT32 ArgIndex)
6090d02842fSSascha Wildner {
6100d02842fSSascha Wildner ACPI_STATUS Status = AE_OK;
6110d02842fSSascha Wildner char *NameString;
6120d02842fSSascha Wildner UINT32 NameLength;
6130d02842fSSascha Wildner ACPI_OPERAND_OBJECT *ObjDesc;
6140d02842fSSascha Wildner ACPI_PARSE_OBJECT *ParentOp;
6150d02842fSSascha Wildner UINT16 Opcode;
6160d02842fSSascha Wildner ACPI_INTERPRETER_MODE InterpreterMode;
6170d02842fSSascha Wildner const ACPI_OPCODE_INFO *OpInfo;
6180d02842fSSascha Wildner
6190d02842fSSascha Wildner
6200d02842fSSascha Wildner ACPI_FUNCTION_TRACE_PTR (DsCreateOperand, Arg);
6210d02842fSSascha Wildner
6220d02842fSSascha Wildner
6230d02842fSSascha Wildner /* A valid name must be looked up in the namespace */
6240d02842fSSascha Wildner
6250d02842fSSascha Wildner if ((Arg->Common.AmlOpcode == AML_INT_NAMEPATH_OP) &&
6260d02842fSSascha Wildner (Arg->Common.Value.String) &&
6270d02842fSSascha Wildner !(Arg->Common.Flags & ACPI_PARSEOP_IN_STACK))
6280d02842fSSascha Wildner {
6290d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Getting a name: Arg=%p\n", Arg));
6300d02842fSSascha Wildner
6310d02842fSSascha Wildner /* Get the entire name string from the AML stream */
6320d02842fSSascha Wildner
633820c5b08SSascha Wildner Status = AcpiExGetNameString (ACPI_TYPE_ANY,
634820c5b08SSascha Wildner Arg->Common.Value.Buffer, &NameString, &NameLength);
6350d02842fSSascha Wildner
6360d02842fSSascha Wildner if (ACPI_FAILURE (Status))
6370d02842fSSascha Wildner {
6380d02842fSSascha Wildner return_ACPI_STATUS (Status);
6390d02842fSSascha Wildner }
6400d02842fSSascha Wildner
6410d02842fSSascha Wildner /* All prefixes have been handled, and the name is in NameString */
6420d02842fSSascha Wildner
6430d02842fSSascha Wildner /*
6440d02842fSSascha Wildner * Special handling for BufferField declarations. This is a deferred
6450d02842fSSascha Wildner * opcode that unfortunately defines the field name as the last
6460d02842fSSascha Wildner * parameter instead of the first. We get here when we are performing
6470d02842fSSascha Wildner * the deferred execution, so the actual name of the field is already
6480d02842fSSascha Wildner * in the namespace. We don't want to attempt to look it up again
6490d02842fSSascha Wildner * because we may be executing in a different scope than where the
6500d02842fSSascha Wildner * actual opcode exists.
6510d02842fSSascha Wildner */
6520d02842fSSascha Wildner if ((WalkState->DeferredNode) &&
6530d02842fSSascha Wildner (WalkState->DeferredNode->Type == ACPI_TYPE_BUFFER_FIELD) &&
654820c5b08SSascha Wildner (ArgIndex == (UINT32)
655820c5b08SSascha Wildner ((WalkState->Opcode == AML_CREATE_FIELD_OP) ? 3 : 2)))
6560d02842fSSascha Wildner {
6570d02842fSSascha Wildner ObjDesc = ACPI_CAST_PTR (
6580d02842fSSascha Wildner ACPI_OPERAND_OBJECT, WalkState->DeferredNode);
6590d02842fSSascha Wildner Status = AE_OK;
6600d02842fSSascha Wildner }
6610d02842fSSascha Wildner else /* All other opcodes */
6620d02842fSSascha Wildner {
6630d02842fSSascha Wildner /*
6640d02842fSSascha Wildner * Differentiate between a namespace "create" operation
6650d02842fSSascha Wildner * versus a "lookup" operation (IMODE_LOAD_PASS2 vs.
6660d02842fSSascha Wildner * IMODE_EXECUTE) in order to support the creation of
6670d02842fSSascha Wildner * namespace objects during the execution of control methods.
6680d02842fSSascha Wildner */
6690d02842fSSascha Wildner ParentOp = Arg->Common.Parent;
6700d02842fSSascha Wildner OpInfo = AcpiPsGetOpcodeInfo (ParentOp->Common.AmlOpcode);
671820c5b08SSascha Wildner
6720d02842fSSascha Wildner if ((OpInfo->Flags & AML_NSNODE) &&
6730d02842fSSascha Wildner (ParentOp->Common.AmlOpcode != AML_INT_METHODCALL_OP) &&
6740d02842fSSascha Wildner (ParentOp->Common.AmlOpcode != AML_REGION_OP) &&
6750d02842fSSascha Wildner (ParentOp->Common.AmlOpcode != AML_INT_NAMEPATH_OP))
6760d02842fSSascha Wildner {
6770d02842fSSascha Wildner /* Enter name into namespace if not found */
6780d02842fSSascha Wildner
6790d02842fSSascha Wildner InterpreterMode = ACPI_IMODE_LOAD_PASS2;
6800d02842fSSascha Wildner }
6810d02842fSSascha Wildner else
6820d02842fSSascha Wildner {
6830d02842fSSascha Wildner /* Return a failure if name not found */
6840d02842fSSascha Wildner
6850d02842fSSascha Wildner InterpreterMode = ACPI_IMODE_EXECUTE;
6860d02842fSSascha Wildner }
6870d02842fSSascha Wildner
6880d02842fSSascha Wildner Status = AcpiNsLookup (WalkState->ScopeInfo, NameString,
6890d02842fSSascha Wildner ACPI_TYPE_ANY, InterpreterMode,
690820c5b08SSascha Wildner ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE, WalkState,
6910d02842fSSascha Wildner ACPI_CAST_INDIRECT_PTR (ACPI_NAMESPACE_NODE, &ObjDesc));
6920d02842fSSascha Wildner /*
6930d02842fSSascha Wildner * The only case where we pass through (ignore) a NOT_FOUND
6940d02842fSSascha Wildner * error is for the CondRefOf opcode.
6950d02842fSSascha Wildner */
6960d02842fSSascha Wildner if (Status == AE_NOT_FOUND)
6970d02842fSSascha Wildner {
698d638c6eeSSascha Wildner if (ParentOp->Common.AmlOpcode == AML_CONDITIONAL_REF_OF_OP)
6990d02842fSSascha Wildner {
7000d02842fSSascha Wildner /*
7010d02842fSSascha Wildner * For the Conditional Reference op, it's OK if
7020d02842fSSascha Wildner * the name is not found; We just need a way to
7030d02842fSSascha Wildner * indicate this to the interpreter, set the
7040d02842fSSascha Wildner * object to the root
7050d02842fSSascha Wildner */
7060d02842fSSascha Wildner ObjDesc = ACPI_CAST_PTR (
7070d02842fSSascha Wildner ACPI_OPERAND_OBJECT, AcpiGbl_RootNode);
7080d02842fSSascha Wildner Status = AE_OK;
7090d02842fSSascha Wildner }
7105943f66cSSascha Wildner else if (ParentOp->Common.AmlOpcode == AML_EXTERNAL_OP)
7115943f66cSSascha Wildner {
7122adac2b8SSascha Wildner /*
7132adac2b8SSascha Wildner * This opcode should never appear here. It is used only
7142adac2b8SSascha Wildner * by AML disassemblers and is surrounded by an If(0)
7152adac2b8SSascha Wildner * by the ASL compiler.
7162adac2b8SSascha Wildner *
7172adac2b8SSascha Wildner * Therefore, if we see it here, it is a serious error.
7182adac2b8SSascha Wildner */
7192adac2b8SSascha Wildner Status = AE_AML_BAD_OPCODE;
7205943f66cSSascha Wildner }
7210d02842fSSascha Wildner else
7220d02842fSSascha Wildner {
7230d02842fSSascha Wildner /*
7240d02842fSSascha Wildner * We just plain didn't find it -- which is a
7250d02842fSSascha Wildner * very serious error at this point
7260d02842fSSascha Wildner */
7270d02842fSSascha Wildner Status = AE_AML_NAME_NOT_FOUND;
7280d02842fSSascha Wildner }
7290d02842fSSascha Wildner }
7300d02842fSSascha Wildner
7310d02842fSSascha Wildner if (ACPI_FAILURE (Status))
7320d02842fSSascha Wildner {
7337bcb6cafSSascha Wildner ACPI_ERROR_NAMESPACE (WalkState->ScopeInfo,
7347bcb6cafSSascha Wildner NameString, Status);
7350d02842fSSascha Wildner }
7360d02842fSSascha Wildner }
7370d02842fSSascha Wildner
7380d02842fSSascha Wildner /* Free the namestring created above */
7390d02842fSSascha Wildner
7400d02842fSSascha Wildner ACPI_FREE (NameString);
7410d02842fSSascha Wildner
7420d02842fSSascha Wildner /* Check status from the lookup */
7430d02842fSSascha Wildner
7440d02842fSSascha Wildner if (ACPI_FAILURE (Status))
7450d02842fSSascha Wildner {
7460d02842fSSascha Wildner return_ACPI_STATUS (Status);
7470d02842fSSascha Wildner }
7480d02842fSSascha Wildner
7490d02842fSSascha Wildner /* Put the resulting object onto the current object stack */
7500d02842fSSascha Wildner
7510d02842fSSascha Wildner Status = AcpiDsObjStackPush (ObjDesc, WalkState);
7520d02842fSSascha Wildner if (ACPI_FAILURE (Status))
7530d02842fSSascha Wildner {
7540d02842fSSascha Wildner return_ACPI_STATUS (Status);
7550d02842fSSascha Wildner }
756820c5b08SSascha Wildner
757820c5b08SSascha Wildner AcpiDbDisplayArgumentObject (ObjDesc, WalkState);
7580d02842fSSascha Wildner }
7590d02842fSSascha Wildner else
7600d02842fSSascha Wildner {
7610d02842fSSascha Wildner /* Check for null name case */
7620d02842fSSascha Wildner
7630d02842fSSascha Wildner if ((Arg->Common.AmlOpcode == AML_INT_NAMEPATH_OP) &&
7640d02842fSSascha Wildner !(Arg->Common.Flags & ACPI_PARSEOP_IN_STACK))
7650d02842fSSascha Wildner {
7660d02842fSSascha Wildner /*
7670d02842fSSascha Wildner * If the name is null, this means that this is an
7680d02842fSSascha Wildner * optional result parameter that was not specified
7690d02842fSSascha Wildner * in the original ASL. Create a Zero Constant for a
7700d02842fSSascha Wildner * placeholder. (Store to a constant is a Noop.)
7710d02842fSSascha Wildner */
7720d02842fSSascha Wildner Opcode = AML_ZERO_OP; /* Has no arguments! */
7730d02842fSSascha Wildner
7740d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
7750d02842fSSascha Wildner "Null namepath: Arg=%p\n", Arg));
7760d02842fSSascha Wildner }
7770d02842fSSascha Wildner else
7780d02842fSSascha Wildner {
7790d02842fSSascha Wildner Opcode = Arg->Common.AmlOpcode;
7800d02842fSSascha Wildner }
7810d02842fSSascha Wildner
7820d02842fSSascha Wildner /* Get the object type of the argument */
7830d02842fSSascha Wildner
7840d02842fSSascha Wildner OpInfo = AcpiPsGetOpcodeInfo (Opcode);
7850d02842fSSascha Wildner if (OpInfo->ObjectType == ACPI_TYPE_INVALID)
7860d02842fSSascha Wildner {
7870d02842fSSascha Wildner return_ACPI_STATUS (AE_NOT_IMPLEMENTED);
7880d02842fSSascha Wildner }
7890d02842fSSascha Wildner
790820c5b08SSascha Wildner if ((OpInfo->Flags & AML_HAS_RETVAL) ||
791820c5b08SSascha Wildner (Arg->Common.Flags & ACPI_PARSEOP_IN_STACK))
7920d02842fSSascha Wildner {
7930d02842fSSascha Wildner /*
7940d02842fSSascha Wildner * Use value that was already previously returned
7950d02842fSSascha Wildner * by the evaluation of this argument
7960d02842fSSascha Wildner */
7970d02842fSSascha Wildner Status = AcpiDsResultPop (&ObjDesc, WalkState);
7980d02842fSSascha Wildner if (ACPI_FAILURE (Status))
7990d02842fSSascha Wildner {
8000d02842fSSascha Wildner /*
8010d02842fSSascha Wildner * Only error is underflow, and this indicates
8020d02842fSSascha Wildner * a missing or null operand!
8030d02842fSSascha Wildner */
8040d02842fSSascha Wildner ACPI_EXCEPTION ((AE_INFO, Status,
8050d02842fSSascha Wildner "Missing or null operand"));
8060d02842fSSascha Wildner return_ACPI_STATUS (Status);
8070d02842fSSascha Wildner }
8080d02842fSSascha Wildner }
8090d02842fSSascha Wildner else
8100d02842fSSascha Wildner {
8110d02842fSSascha Wildner /* Create an ACPI_INTERNAL_OBJECT for the argument */
8120d02842fSSascha Wildner
8130d02842fSSascha Wildner ObjDesc = AcpiUtCreateInternalObject (OpInfo->ObjectType);
8140d02842fSSascha Wildner if (!ObjDesc)
8150d02842fSSascha Wildner {
8160d02842fSSascha Wildner return_ACPI_STATUS (AE_NO_MEMORY);
8170d02842fSSascha Wildner }
8180d02842fSSascha Wildner
8190d02842fSSascha Wildner /* Initialize the new object */
8200d02842fSSascha Wildner
8210d02842fSSascha Wildner Status = AcpiDsInitObjectFromOp (
8220d02842fSSascha Wildner WalkState, Arg, Opcode, &ObjDesc);
8230d02842fSSascha Wildner if (ACPI_FAILURE (Status))
8240d02842fSSascha Wildner {
8250d02842fSSascha Wildner AcpiUtDeleteObjectDesc (ObjDesc);
8260d02842fSSascha Wildner return_ACPI_STATUS (Status);
8270d02842fSSascha Wildner }
8280d02842fSSascha Wildner }
8290d02842fSSascha Wildner
8300d02842fSSascha Wildner /* Put the operand object on the object stack */
8310d02842fSSascha Wildner
8320d02842fSSascha Wildner Status = AcpiDsObjStackPush (ObjDesc, WalkState);
8330d02842fSSascha Wildner if (ACPI_FAILURE (Status))
8340d02842fSSascha Wildner {
8350d02842fSSascha Wildner return_ACPI_STATUS (Status);
8360d02842fSSascha Wildner }
8370d02842fSSascha Wildner
838820c5b08SSascha Wildner AcpiDbDisplayArgumentObject (ObjDesc, WalkState);
8390d02842fSSascha Wildner }
8400d02842fSSascha Wildner
8410d02842fSSascha Wildner return_ACPI_STATUS (AE_OK);
8420d02842fSSascha Wildner }
8430d02842fSSascha Wildner
8440d02842fSSascha Wildner
8450d02842fSSascha Wildner /*******************************************************************************
8460d02842fSSascha Wildner *
8470d02842fSSascha Wildner * FUNCTION: AcpiDsCreateOperands
8480d02842fSSascha Wildner *
8490d02842fSSascha Wildner * PARAMETERS: WalkState - Current state
8500d02842fSSascha Wildner * FirstArg - First argument of a parser argument tree
8510d02842fSSascha Wildner *
8520d02842fSSascha Wildner * RETURN: Status
8530d02842fSSascha Wildner *
8540d02842fSSascha Wildner * DESCRIPTION: Convert an operator's arguments from a parse tree format to
8550d02842fSSascha Wildner * namespace objects and place those argument object on the object
8560d02842fSSascha Wildner * stack in preparation for evaluation by the interpreter.
8570d02842fSSascha Wildner *
8580d02842fSSascha Wildner ******************************************************************************/
8590d02842fSSascha Wildner
8600d02842fSSascha Wildner ACPI_STATUS
AcpiDsCreateOperands(ACPI_WALK_STATE * WalkState,ACPI_PARSE_OBJECT * FirstArg)8610d02842fSSascha Wildner AcpiDsCreateOperands (
8620d02842fSSascha Wildner ACPI_WALK_STATE *WalkState,
8630d02842fSSascha Wildner ACPI_PARSE_OBJECT *FirstArg)
8640d02842fSSascha Wildner {
8650d02842fSSascha Wildner ACPI_STATUS Status = AE_OK;
8660d02842fSSascha Wildner ACPI_PARSE_OBJECT *Arg;
8670d02842fSSascha Wildner ACPI_PARSE_OBJECT *Arguments[ACPI_OBJ_NUM_OPERANDS];
8680d02842fSSascha Wildner UINT32 ArgCount = 0;
8690d02842fSSascha Wildner UINT32 Index = WalkState->NumOperands;
8700d02842fSSascha Wildner UINT32 i;
8710d02842fSSascha Wildner
8720d02842fSSascha Wildner
8730d02842fSSascha Wildner ACPI_FUNCTION_TRACE_PTR (DsCreateOperands, FirstArg);
8740d02842fSSascha Wildner
8750d02842fSSascha Wildner
8760d02842fSSascha Wildner /* Get all arguments in the list */
8770d02842fSSascha Wildner
8780d02842fSSascha Wildner Arg = FirstArg;
8790d02842fSSascha Wildner while (Arg)
8800d02842fSSascha Wildner {
8810d02842fSSascha Wildner if (Index >= ACPI_OBJ_NUM_OPERANDS)
8820d02842fSSascha Wildner {
8830d02842fSSascha Wildner return_ACPI_STATUS (AE_BAD_DATA);
8840d02842fSSascha Wildner }
8850d02842fSSascha Wildner
8860d02842fSSascha Wildner Arguments[Index] = Arg;
8870d02842fSSascha Wildner WalkState->Operands [Index] = NULL;
8880d02842fSSascha Wildner
8890d02842fSSascha Wildner /* Move on to next argument, if any */
8900d02842fSSascha Wildner
8910d02842fSSascha Wildner Arg = Arg->Common.Next;
8920d02842fSSascha Wildner ArgCount++;
8930d02842fSSascha Wildner Index++;
8940d02842fSSascha Wildner }
8950d02842fSSascha Wildner
8960d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
8970d02842fSSascha Wildner "NumOperands %d, ArgCount %d, Index %d\n",
8980d02842fSSascha Wildner WalkState->NumOperands, ArgCount, Index));
8990d02842fSSascha Wildner
9000d02842fSSascha Wildner /* Create the interpreter arguments, in reverse order */
9010d02842fSSascha Wildner
9020d02842fSSascha Wildner Index--;
9030d02842fSSascha Wildner for (i = 0; i < ArgCount; i++)
9040d02842fSSascha Wildner {
9050d02842fSSascha Wildner Arg = Arguments[Index];
9060d02842fSSascha Wildner WalkState->OperandIndex = (UINT8) Index;
9070d02842fSSascha Wildner
9080d02842fSSascha Wildner Status = AcpiDsCreateOperand (WalkState, Arg, Index);
9090d02842fSSascha Wildner if (ACPI_FAILURE (Status))
9100d02842fSSascha Wildner {
9110d02842fSSascha Wildner goto Cleanup;
9120d02842fSSascha Wildner }
9130d02842fSSascha Wildner
9140d02842fSSascha Wildner ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH,
9150d02842fSSascha Wildner "Created Arg #%u (%p) %u args total\n",
9160d02842fSSascha Wildner Index, Arg, ArgCount));
9170d02842fSSascha Wildner Index--;
9180d02842fSSascha Wildner }
9190d02842fSSascha Wildner
9200d02842fSSascha Wildner return_ACPI_STATUS (Status);
9210d02842fSSascha Wildner
9220d02842fSSascha Wildner
9230d02842fSSascha Wildner Cleanup:
9240d02842fSSascha Wildner /*
9250d02842fSSascha Wildner * We must undo everything done above; meaning that we must
9260d02842fSSascha Wildner * pop everything off of the operand stack and delete those
9270d02842fSSascha Wildner * objects
9280d02842fSSascha Wildner */
9290d02842fSSascha Wildner AcpiDsObjStackPopAndDelete (ArgCount, WalkState);
9300d02842fSSascha Wildner
9310d02842fSSascha Wildner ACPI_EXCEPTION ((AE_INFO, Status, "While creating Arg %u", Index));
9320d02842fSSascha Wildner return_ACPI_STATUS (Status);
9330d02842fSSascha Wildner }
9340d02842fSSascha Wildner
9350d02842fSSascha Wildner
9360d02842fSSascha Wildner /*****************************************************************************
9370d02842fSSascha Wildner *
9380d02842fSSascha Wildner * FUNCTION: AcpiDsEvaluateNamePath
9390d02842fSSascha Wildner *
9400d02842fSSascha Wildner * PARAMETERS: WalkState - Current state of the parse tree walk,
9410d02842fSSascha Wildner * the opcode of current operation should be
9420d02842fSSascha Wildner * AML_INT_NAMEPATH_OP
9430d02842fSSascha Wildner *
9440d02842fSSascha Wildner * RETURN: Status
9450d02842fSSascha Wildner *
9460d02842fSSascha Wildner * DESCRIPTION: Translate the -NamePath- parse tree object to the equivalent
9470d02842fSSascha Wildner * interpreter object, convert it to value, if needed, duplicate
9480d02842fSSascha Wildner * it, if needed, and push it onto the current result stack.
9490d02842fSSascha Wildner *
9500d02842fSSascha Wildner ****************************************************************************/
9510d02842fSSascha Wildner
9520d02842fSSascha Wildner ACPI_STATUS
AcpiDsEvaluateNamePath(ACPI_WALK_STATE * WalkState)9530d02842fSSascha Wildner AcpiDsEvaluateNamePath (
9540d02842fSSascha Wildner ACPI_WALK_STATE *WalkState)
9550d02842fSSascha Wildner {
9560d02842fSSascha Wildner ACPI_STATUS Status = AE_OK;
9570d02842fSSascha Wildner ACPI_PARSE_OBJECT *Op = WalkState->Op;
9580d02842fSSascha Wildner ACPI_OPERAND_OBJECT **Operand = &WalkState->Operands[0];
9590d02842fSSascha Wildner ACPI_OPERAND_OBJECT *NewObjDesc;
9600d02842fSSascha Wildner UINT8 Type;
9610d02842fSSascha Wildner
9620d02842fSSascha Wildner
9630d02842fSSascha Wildner ACPI_FUNCTION_TRACE_PTR (DsEvaluateNamePath, WalkState);
9640d02842fSSascha Wildner
9650d02842fSSascha Wildner
9660d02842fSSascha Wildner if (!Op->Common.Parent)
9670d02842fSSascha Wildner {
9680d02842fSSascha Wildner /* This happens after certain exception processing */
9690d02842fSSascha Wildner
9700d02842fSSascha Wildner goto Exit;
9710d02842fSSascha Wildner }
9720d02842fSSascha Wildner
9730d02842fSSascha Wildner if ((Op->Common.Parent->Common.AmlOpcode == AML_PACKAGE_OP) ||
974d638c6eeSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_VARIABLE_PACKAGE_OP) ||
9750d02842fSSascha Wildner (Op->Common.Parent->Common.AmlOpcode == AML_REF_OF_OP))
9760d02842fSSascha Wildner {
9770d02842fSSascha Wildner /* TBD: Should we specify this feature as a bit of OpInfo->Flags of these opcodes? */
9780d02842fSSascha Wildner
9790d02842fSSascha Wildner goto Exit;
9800d02842fSSascha Wildner }
9810d02842fSSascha Wildner
9820d02842fSSascha Wildner Status = AcpiDsCreateOperand (WalkState, Op, 0);
9830d02842fSSascha Wildner if (ACPI_FAILURE (Status))
9840d02842fSSascha Wildner {
9850d02842fSSascha Wildner goto Exit;
9860d02842fSSascha Wildner }
9870d02842fSSascha Wildner
9880d02842fSSascha Wildner if (Op->Common.Flags & ACPI_PARSEOP_TARGET)
9890d02842fSSascha Wildner {
9900d02842fSSascha Wildner NewObjDesc = *Operand;
9910d02842fSSascha Wildner goto PushResult;
9920d02842fSSascha Wildner }
9930d02842fSSascha Wildner
9940d02842fSSascha Wildner Type = (*Operand)->Common.Type;
9950d02842fSSascha Wildner
9960d02842fSSascha Wildner Status = AcpiExResolveToValue (Operand, WalkState);
9970d02842fSSascha Wildner if (ACPI_FAILURE (Status))
9980d02842fSSascha Wildner {
9990d02842fSSascha Wildner goto Exit;
10000d02842fSSascha Wildner }
10010d02842fSSascha Wildner
10020d02842fSSascha Wildner if (Type == ACPI_TYPE_INTEGER)
10030d02842fSSascha Wildner {
10040d02842fSSascha Wildner /* It was incremented by AcpiExResolveToValue */
10050d02842fSSascha Wildner
10060d02842fSSascha Wildner AcpiUtRemoveReference (*Operand);
10070d02842fSSascha Wildner
1008820c5b08SSascha Wildner Status = AcpiUtCopyIobjectToIobject (
1009820c5b08SSascha Wildner *Operand, &NewObjDesc, WalkState);
10100d02842fSSascha Wildner if (ACPI_FAILURE (Status))
10110d02842fSSascha Wildner {
10120d02842fSSascha Wildner goto Exit;
10130d02842fSSascha Wildner }
10140d02842fSSascha Wildner }
10150d02842fSSascha Wildner else
10160d02842fSSascha Wildner {
10170d02842fSSascha Wildner /*
10180d02842fSSascha Wildner * The object either was anew created or is
10190d02842fSSascha Wildner * a Namespace node - don't decrement it.
10200d02842fSSascha Wildner */
10210d02842fSSascha Wildner NewObjDesc = *Operand;
10220d02842fSSascha Wildner }
10230d02842fSSascha Wildner
10240d02842fSSascha Wildner /* Cleanup for name-path operand */
10250d02842fSSascha Wildner
10260d02842fSSascha Wildner Status = AcpiDsObjStackPop (1, WalkState);
10270d02842fSSascha Wildner if (ACPI_FAILURE (Status))
10280d02842fSSascha Wildner {
10290d02842fSSascha Wildner WalkState->ResultObj = NewObjDesc;
10300d02842fSSascha Wildner goto Exit;
10310d02842fSSascha Wildner }
10320d02842fSSascha Wildner
10330d02842fSSascha Wildner PushResult:
10340d02842fSSascha Wildner
10350d02842fSSascha Wildner WalkState->ResultObj = NewObjDesc;
10360d02842fSSascha Wildner
10370d02842fSSascha Wildner Status = AcpiDsResultPush (WalkState->ResultObj, WalkState);
10380d02842fSSascha Wildner if (ACPI_SUCCESS (Status))
10390d02842fSSascha Wildner {
10400d02842fSSascha Wildner /* Force to take it from stack */
10410d02842fSSascha Wildner
10420d02842fSSascha Wildner Op->Common.Flags |= ACPI_PARSEOP_IN_STACK;
10430d02842fSSascha Wildner }
10440d02842fSSascha Wildner
10450d02842fSSascha Wildner Exit:
10460d02842fSSascha Wildner
10470d02842fSSascha Wildner return_ACPI_STATUS (Status);
10480d02842fSSascha Wildner }
1049