1a9643ea8Slogwang /*******************************************************************************
2a9643ea8Slogwang  *
3a9643ea8Slogwang  * Module Name: dmopcode - AML disassembler, specific AML opcodes
4a9643ea8Slogwang  *
5a9643ea8Slogwang  ******************************************************************************/
6a9643ea8Slogwang 
7*22ce4affSfengbojiang /******************************************************************************
8*22ce4affSfengbojiang  *
9*22ce4affSfengbojiang  * 1. Copyright Notice
10*22ce4affSfengbojiang  *
11*22ce4affSfengbojiang  * Some or all of this work - Copyright (c) 1999 - 2020, Intel Corp.
12a9643ea8Slogwang  * All rights reserved.
13a9643ea8Slogwang  *
14*22ce4affSfengbojiang  * 2. License
15*22ce4affSfengbojiang  *
16*22ce4affSfengbojiang  * 2.1. This is your license from Intel Corp. under its intellectual property
17*22ce4affSfengbojiang  * rights. You may have additional license terms from the party that provided
18*22ce4affSfengbojiang  * you this software, covering your right to use that party's intellectual
19*22ce4affSfengbojiang  * property rights.
20*22ce4affSfengbojiang  *
21*22ce4affSfengbojiang  * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a
22*22ce4affSfengbojiang  * copy of the source code appearing in this file ("Covered Code") an
23*22ce4affSfengbojiang  * irrevocable, perpetual, worldwide license under Intel's copyrights in the
24*22ce4affSfengbojiang  * base code distributed originally by Intel ("Original Intel Code") to copy,
25*22ce4affSfengbojiang  * make derivatives, distribute, use and display any portion of the Covered
26*22ce4affSfengbojiang  * Code in any form, with the right to sublicense such rights; and
27*22ce4affSfengbojiang  *
28*22ce4affSfengbojiang  * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent
29*22ce4affSfengbojiang  * license (with the right to sublicense), under only those claims of Intel
30*22ce4affSfengbojiang  * patents that are infringed by the Original Intel Code, to make, use, sell,
31*22ce4affSfengbojiang  * offer to sell, and import the Covered Code and derivative works thereof
32*22ce4affSfengbojiang  * solely to the minimum extent necessary to exercise the above copyright
33*22ce4affSfengbojiang  * license, and in no event shall the patent license extend to any additions
34*22ce4affSfengbojiang  * to or modifications of the Original Intel Code. No other license or right
35*22ce4affSfengbojiang  * is granted directly or by implication, estoppel or otherwise;
36*22ce4affSfengbojiang  *
37*22ce4affSfengbojiang  * The above copyright and patent license is granted only if the following
38*22ce4affSfengbojiang  * conditions are met:
39*22ce4affSfengbojiang  *
40*22ce4affSfengbojiang  * 3. Conditions
41*22ce4affSfengbojiang  *
42*22ce4affSfengbojiang  * 3.1. Redistribution of Source with Rights to Further Distribute Source.
43*22ce4affSfengbojiang  * Redistribution of source code of any substantial portion of the Covered
44*22ce4affSfengbojiang  * Code or modification with rights to further distribute source must include
45*22ce4affSfengbojiang  * the above Copyright Notice, the above License, this list of Conditions,
46*22ce4affSfengbojiang  * and the following Disclaimer and Export Compliance provision. In addition,
47*22ce4affSfengbojiang  * Licensee must cause all Covered Code to which Licensee contributes to
48*22ce4affSfengbojiang  * contain a file documenting the changes Licensee made to create that Covered
49*22ce4affSfengbojiang  * Code and the date of any change. Licensee must include in that file the
50*22ce4affSfengbojiang  * documentation of any changes made by any predecessor Licensee. Licensee
51*22ce4affSfengbojiang  * must include a prominent statement that the modification is derived,
52*22ce4affSfengbojiang  * directly or indirectly, from Original Intel Code.
53*22ce4affSfengbojiang  *
54*22ce4affSfengbojiang  * 3.2. Redistribution of Source with no Rights to Further Distribute Source.
55*22ce4affSfengbojiang  * Redistribution of source code of any substantial portion of the Covered
56*22ce4affSfengbojiang  * Code or modification without rights to further distribute source must
57*22ce4affSfengbojiang  * include the following Disclaimer and Export Compliance provision in the
58*22ce4affSfengbojiang  * documentation and/or other materials provided with distribution. In
59*22ce4affSfengbojiang  * addition, Licensee may not authorize further sublicense of source of any
60*22ce4affSfengbojiang  * portion of the Covered Code, and must include terms to the effect that the
61*22ce4affSfengbojiang  * license from Licensee to its licensee is limited to the intellectual
62*22ce4affSfengbojiang  * property embodied in the software Licensee provides to its licensee, and
63*22ce4affSfengbojiang  * not to intellectual property embodied in modifications its licensee may
64*22ce4affSfengbojiang  * make.
65*22ce4affSfengbojiang  *
66*22ce4affSfengbojiang  * 3.3. Redistribution of Executable. Redistribution in executable form of any
67*22ce4affSfengbojiang  * substantial portion of the Covered Code or modification must reproduce the
68*22ce4affSfengbojiang  * above Copyright Notice, and the following Disclaimer and Export Compliance
69*22ce4affSfengbojiang  * provision in the documentation and/or other materials provided with the
70*22ce4affSfengbojiang  * distribution.
71*22ce4affSfengbojiang  *
72*22ce4affSfengbojiang  * 3.4. Intel retains all right, title, and interest in and to the Original
73*22ce4affSfengbojiang  * Intel Code.
74*22ce4affSfengbojiang  *
75*22ce4affSfengbojiang  * 3.5. Neither the name Intel nor any other trademark owned or controlled by
76*22ce4affSfengbojiang  * Intel shall be used in advertising or otherwise to promote the sale, use or
77*22ce4affSfengbojiang  * other dealings in products derived from or relating to the Covered Code
78*22ce4affSfengbojiang  * without prior written authorization from Intel.
79*22ce4affSfengbojiang  *
80*22ce4affSfengbojiang  * 4. Disclaimer and Export Compliance
81*22ce4affSfengbojiang  *
82*22ce4affSfengbojiang  * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED
83*22ce4affSfengbojiang  * HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE
84*22ce4affSfengbojiang  * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE,
85*22ce4affSfengbojiang  * INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY
86*22ce4affSfengbojiang  * UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY
87*22ce4affSfengbojiang  * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A
88*22ce4affSfengbojiang  * PARTICULAR PURPOSE.
89*22ce4affSfengbojiang  *
90*22ce4affSfengbojiang  * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES
91*22ce4affSfengbojiang  * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR
92*22ce4affSfengbojiang  * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT,
93*22ce4affSfengbojiang  * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY
94*22ce4affSfengbojiang  * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL
95*22ce4affSfengbojiang  * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS
96*22ce4affSfengbojiang  * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY
97*22ce4affSfengbojiang  * LIMITED REMEDY.
98*22ce4affSfengbojiang  *
99*22ce4affSfengbojiang  * 4.3. Licensee shall not export, either directly or indirectly, any of this
100*22ce4affSfengbojiang  * software or system incorporating such software without first obtaining any
101*22ce4affSfengbojiang  * required license or other approval from the U. S. Department of Commerce or
102*22ce4affSfengbojiang  * any other agency or department of the United States Government. In the
103*22ce4affSfengbojiang  * event Licensee exports any such software from the United States or
104*22ce4affSfengbojiang  * re-exports any such software from a foreign destination, Licensee shall
105*22ce4affSfengbojiang  * ensure that the distribution and export/re-export of the software is in
106*22ce4affSfengbojiang  * compliance with all laws, regulations, orders, or other restrictions of the
107*22ce4affSfengbojiang  * U.S. Export Administration Regulations. Licensee agrees that neither it nor
108*22ce4affSfengbojiang  * any of its subsidiaries will export/re-export any technical data, process,
109*22ce4affSfengbojiang  * software, or service, directly or indirectly, to any country for which the
110*22ce4affSfengbojiang  * United States government or any agency thereof requires an export license,
111*22ce4affSfengbojiang  * other governmental approval, or letter of assurance, without first obtaining
112*22ce4affSfengbojiang  * such license, approval or letter.
113*22ce4affSfengbojiang  *
114*22ce4affSfengbojiang  *****************************************************************************
115*22ce4affSfengbojiang  *
116*22ce4affSfengbojiang  * Alternatively, you may choose to be licensed under the terms of the
117*22ce4affSfengbojiang  * following license:
118*22ce4affSfengbojiang  *
119a9643ea8Slogwang  * Redistribution and use in source and binary forms, with or without
120a9643ea8Slogwang  * modification, are permitted provided that the following conditions
121a9643ea8Slogwang  * are met:
122a9643ea8Slogwang  * 1. Redistributions of source code must retain the above copyright
123a9643ea8Slogwang  *    notice, this list of conditions, and the following disclaimer,
124a9643ea8Slogwang  *    without modification.
125a9643ea8Slogwang  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
126a9643ea8Slogwang  *    substantially similar to the "NO WARRANTY" disclaimer below
127a9643ea8Slogwang  *    ("Disclaimer") and any redistribution must be conditioned upon
128a9643ea8Slogwang  *    including a substantially similar Disclaimer requirement for further
129a9643ea8Slogwang  *    binary redistribution.
130a9643ea8Slogwang  * 3. Neither the names of the above-listed copyright holders nor the names
131a9643ea8Slogwang  *    of any contributors may be used to endorse or promote products derived
132a9643ea8Slogwang  *    from this software without specific prior written permission.
133a9643ea8Slogwang  *
134*22ce4affSfengbojiang  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
135*22ce4affSfengbojiang  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
136*22ce4affSfengbojiang  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
137*22ce4affSfengbojiang  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
138*22ce4affSfengbojiang  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
139*22ce4affSfengbojiang  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
140*22ce4affSfengbojiang  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
141*22ce4affSfengbojiang  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
142*22ce4affSfengbojiang  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
143*22ce4affSfengbojiang  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
144*22ce4affSfengbojiang  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
145*22ce4affSfengbojiang  *
146*22ce4affSfengbojiang  * Alternatively, you may choose to be licensed under the terms of the
147a9643ea8Slogwang  * GNU General Public License ("GPL") version 2 as published by the Free
148a9643ea8Slogwang  * Software Foundation.
149a9643ea8Slogwang  *
150*22ce4affSfengbojiang  *****************************************************************************/
151a9643ea8Slogwang 
152a9643ea8Slogwang #include <contrib/dev/acpica/include/acpi.h>
153a9643ea8Slogwang #include <contrib/dev/acpica/include/accommon.h>
154a9643ea8Slogwang #include <contrib/dev/acpica/include/acparser.h>
155a9643ea8Slogwang #include <contrib/dev/acpica/include/amlcode.h>
156a9643ea8Slogwang #include <contrib/dev/acpica/include/acinterp.h>
157a9643ea8Slogwang #include <contrib/dev/acpica/include/acnamesp.h>
158a9643ea8Slogwang #include <contrib/dev/acpica/include/acdebug.h>
159*22ce4affSfengbojiang #include <contrib/dev/acpica/include/acconvert.h>
160a9643ea8Slogwang 
161a9643ea8Slogwang 
162a9643ea8Slogwang #define _COMPONENT          ACPI_CA_DEBUGGER
163a9643ea8Slogwang         ACPI_MODULE_NAME    ("dmopcode")
164a9643ea8Slogwang 
165a9643ea8Slogwang 
166a9643ea8Slogwang /* Local prototypes */
167a9643ea8Slogwang 
168a9643ea8Slogwang static void
169a9643ea8Slogwang AcpiDmMatchKeyword (
170a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op);
171a9643ea8Slogwang 
172a9643ea8Slogwang static void
173a9643ea8Slogwang AcpiDmConvertToElseIf (
174a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op);
175a9643ea8Slogwang 
176*22ce4affSfengbojiang static void
177*22ce4affSfengbojiang AcpiDmPromoteSubtree (
178*22ce4affSfengbojiang     ACPI_PARSE_OBJECT       *StartOp);
179a9643ea8Slogwang 
180a9643ea8Slogwang /*******************************************************************************
181a9643ea8Slogwang  *
182a9643ea8Slogwang  * FUNCTION:    AcpiDmDisplayTargetPathname
183a9643ea8Slogwang  *
184a9643ea8Slogwang  * PARAMETERS:  Op              - Parse object
185a9643ea8Slogwang  *
186a9643ea8Slogwang  * RETURN:      None
187a9643ea8Slogwang  *
188a9643ea8Slogwang  * DESCRIPTION: For AML opcodes that have a target operand, display the full
189a9643ea8Slogwang  *              pathname for the target, in a comment field. Handles Return()
190a9643ea8Slogwang  *              statements also.
191a9643ea8Slogwang  *
192a9643ea8Slogwang  ******************************************************************************/
193a9643ea8Slogwang 
194a9643ea8Slogwang void
AcpiDmDisplayTargetPathname(ACPI_PARSE_OBJECT * Op)195a9643ea8Slogwang AcpiDmDisplayTargetPathname (
196a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
197a9643ea8Slogwang {
198a9643ea8Slogwang     ACPI_PARSE_OBJECT       *NextOp;
199a9643ea8Slogwang     ACPI_PARSE_OBJECT       *PrevOp = NULL;
200a9643ea8Slogwang     char                    *Pathname;
201a9643ea8Slogwang     const ACPI_OPCODE_INFO  *OpInfo;
202a9643ea8Slogwang 
203a9643ea8Slogwang 
204a9643ea8Slogwang     if (Op->Common.AmlOpcode == AML_RETURN_OP)
205a9643ea8Slogwang     {
206a9643ea8Slogwang         PrevOp = Op->Asl.Value.Arg;
207a9643ea8Slogwang     }
208a9643ea8Slogwang     else
209a9643ea8Slogwang     {
210a9643ea8Slogwang         OpInfo = AcpiPsGetOpcodeInfo (Op->Common.AmlOpcode);
211a9643ea8Slogwang         if (!(OpInfo->Flags & AML_HAS_TARGET))
212a9643ea8Slogwang         {
213a9643ea8Slogwang             return;
214a9643ea8Slogwang         }
215a9643ea8Slogwang 
216a9643ea8Slogwang         /* Target is the last Op in the arg list */
217a9643ea8Slogwang 
218a9643ea8Slogwang         NextOp = Op->Asl.Value.Arg;
219a9643ea8Slogwang         while (NextOp)
220a9643ea8Slogwang         {
221a9643ea8Slogwang             PrevOp = NextOp;
222a9643ea8Slogwang             NextOp = PrevOp->Asl.Next;
223a9643ea8Slogwang         }
224a9643ea8Slogwang     }
225a9643ea8Slogwang 
226a9643ea8Slogwang     if (!PrevOp)
227a9643ea8Slogwang     {
228a9643ea8Slogwang         return;
229a9643ea8Slogwang     }
230a9643ea8Slogwang 
231a9643ea8Slogwang     /* We must have a namepath AML opcode */
232a9643ea8Slogwang 
233a9643ea8Slogwang     if (PrevOp->Asl.AmlOpcode != AML_INT_NAMEPATH_OP)
234a9643ea8Slogwang     {
235a9643ea8Slogwang         return;
236a9643ea8Slogwang     }
237a9643ea8Slogwang 
238a9643ea8Slogwang     /* A null string is the "no target specified" case */
239a9643ea8Slogwang 
240a9643ea8Slogwang     if (!PrevOp->Asl.Value.String)
241a9643ea8Slogwang     {
242a9643ea8Slogwang         return;
243a9643ea8Slogwang     }
244a9643ea8Slogwang 
245a9643ea8Slogwang     /* No node means "unresolved external reference" */
246a9643ea8Slogwang 
247a9643ea8Slogwang     if (!PrevOp->Asl.Node)
248a9643ea8Slogwang     {
249a9643ea8Slogwang         AcpiOsPrintf (" /* External reference */");
250a9643ea8Slogwang         return;
251a9643ea8Slogwang     }
252a9643ea8Slogwang 
253a9643ea8Slogwang     /* Ignore if path is already from the root */
254a9643ea8Slogwang 
255a9643ea8Slogwang     if (*PrevOp->Asl.Value.String == '\\')
256a9643ea8Slogwang     {
257a9643ea8Slogwang         return;
258a9643ea8Slogwang     }
259a9643ea8Slogwang 
260a9643ea8Slogwang     /* Now: we can get the full pathname */
261a9643ea8Slogwang 
262a9643ea8Slogwang     Pathname = AcpiNsGetExternalPathname (PrevOp->Asl.Node);
263a9643ea8Slogwang     if (!Pathname)
264a9643ea8Slogwang     {
265a9643ea8Slogwang         return;
266a9643ea8Slogwang     }
267a9643ea8Slogwang 
268a9643ea8Slogwang     AcpiOsPrintf (" /* %s */", Pathname);
269a9643ea8Slogwang     ACPI_FREE (Pathname);
270a9643ea8Slogwang }
271a9643ea8Slogwang 
272a9643ea8Slogwang 
273a9643ea8Slogwang /*******************************************************************************
274a9643ea8Slogwang  *
275a9643ea8Slogwang  * FUNCTION:    AcpiDmNotifyDescription
276a9643ea8Slogwang  *
277a9643ea8Slogwang  * PARAMETERS:  Op              - Name() parse object
278a9643ea8Slogwang  *
279a9643ea8Slogwang  * RETURN:      None
280a9643ea8Slogwang  *
281a9643ea8Slogwang  * DESCRIPTION: Emit a description comment for the value associated with a
282a9643ea8Slogwang  *              Notify() operator.
283a9643ea8Slogwang  *
284a9643ea8Slogwang  ******************************************************************************/
285a9643ea8Slogwang 
286a9643ea8Slogwang void
AcpiDmNotifyDescription(ACPI_PARSE_OBJECT * Op)287a9643ea8Slogwang AcpiDmNotifyDescription (
288a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
289a9643ea8Slogwang {
290a9643ea8Slogwang     ACPI_PARSE_OBJECT       *NextOp;
291a9643ea8Slogwang     ACPI_NAMESPACE_NODE     *Node;
292a9643ea8Slogwang     UINT8                   NotifyValue;
293a9643ea8Slogwang     UINT8                   Type = ACPI_TYPE_ANY;
294a9643ea8Slogwang 
295a9643ea8Slogwang 
296a9643ea8Slogwang     /* The notify value is the second argument */
297a9643ea8Slogwang 
298a9643ea8Slogwang     NextOp = Op->Asl.Value.Arg;
299a9643ea8Slogwang     NextOp = NextOp->Asl.Next;
300a9643ea8Slogwang 
301a9643ea8Slogwang     switch (NextOp->Common.AmlOpcode)
302a9643ea8Slogwang     {
303a9643ea8Slogwang     case AML_ZERO_OP:
304a9643ea8Slogwang     case AML_ONE_OP:
305a9643ea8Slogwang 
306a9643ea8Slogwang         NotifyValue = (UINT8) NextOp->Common.AmlOpcode;
307a9643ea8Slogwang         break;
308a9643ea8Slogwang 
309a9643ea8Slogwang     case AML_BYTE_OP:
310a9643ea8Slogwang 
311a9643ea8Slogwang         NotifyValue = (UINT8) NextOp->Asl.Value.Integer;
312a9643ea8Slogwang         break;
313a9643ea8Slogwang 
314a9643ea8Slogwang     default:
315a9643ea8Slogwang         return;
316a9643ea8Slogwang     }
317a9643ea8Slogwang 
318a9643ea8Slogwang     /*
319a9643ea8Slogwang      * Attempt to get the namespace node so we can determine the object type.
320a9643ea8Slogwang      * Some notify values are dependent on the object type (Device, Thermal,
321a9643ea8Slogwang      * or Processor).
322a9643ea8Slogwang      */
323a9643ea8Slogwang     Node = Op->Asl.Node;
324a9643ea8Slogwang     if (Node)
325a9643ea8Slogwang     {
326a9643ea8Slogwang         Type = Node->Type;
327a9643ea8Slogwang     }
328a9643ea8Slogwang 
329a9643ea8Slogwang     AcpiOsPrintf (" // %s", AcpiUtGetNotifyName (NotifyValue, Type));
330a9643ea8Slogwang }
331a9643ea8Slogwang 
332a9643ea8Slogwang 
333a9643ea8Slogwang /*******************************************************************************
334a9643ea8Slogwang  *
335a9643ea8Slogwang  * FUNCTION:    AcpiDmPredefinedDescription
336a9643ea8Slogwang  *
337a9643ea8Slogwang  * PARAMETERS:  Op              - Name() parse object
338a9643ea8Slogwang  *
339a9643ea8Slogwang  * RETURN:      None
340a9643ea8Slogwang  *
341a9643ea8Slogwang  * DESCRIPTION: Emit a description comment for a predefined ACPI name.
342a9643ea8Slogwang  *              Used for iASL compiler only.
343a9643ea8Slogwang  *
344a9643ea8Slogwang  ******************************************************************************/
345a9643ea8Slogwang 
346a9643ea8Slogwang void
AcpiDmPredefinedDescription(ACPI_PARSE_OBJECT * Op)347a9643ea8Slogwang AcpiDmPredefinedDescription (
348a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
349a9643ea8Slogwang {
350a9643ea8Slogwang #ifdef ACPI_ASL_COMPILER
351a9643ea8Slogwang     const AH_PREDEFINED_NAME    *Info;
352a9643ea8Slogwang     char                        *NameString;
353a9643ea8Slogwang     int                         LastCharIsDigit;
354a9643ea8Slogwang     int                         LastCharsAreHex;
355a9643ea8Slogwang 
356a9643ea8Slogwang 
357a9643ea8Slogwang     if (!Op)
358a9643ea8Slogwang     {
359a9643ea8Slogwang         return;
360a9643ea8Slogwang     }
361a9643ea8Slogwang 
362a9643ea8Slogwang     /* Ensure that the comment field is emitted only once */
363a9643ea8Slogwang 
364a9643ea8Slogwang     if (Op->Common.DisasmFlags & ACPI_PARSEOP_PREDEFINED_CHECKED)
365a9643ea8Slogwang     {
366a9643ea8Slogwang         return;
367a9643ea8Slogwang     }
368a9643ea8Slogwang     Op->Common.DisasmFlags |= ACPI_PARSEOP_PREDEFINED_CHECKED;
369a9643ea8Slogwang 
370a9643ea8Slogwang     /* Predefined name must start with an underscore */
371a9643ea8Slogwang 
372a9643ea8Slogwang     NameString = ACPI_CAST_PTR (char, &Op->Named.Name);
373a9643ea8Slogwang     if (NameString[0] != '_')
374a9643ea8Slogwang     {
375a9643ea8Slogwang         return;
376a9643ea8Slogwang     }
377a9643ea8Slogwang 
378a9643ea8Slogwang     /*
379a9643ea8Slogwang      * Check for the special ACPI names:
380a9643ea8Slogwang      * _ACd, _ALd, _EJd, _Exx, _Lxx, _Qxx, _Wxx, _T_a
381a9643ea8Slogwang      * (where d=decimal_digit, x=hex_digit, a=anything)
382a9643ea8Slogwang      *
383a9643ea8Slogwang      * Convert these to the generic name for table lookup.
384a9643ea8Slogwang      * Note: NameString is guaranteed to be upper case here.
385a9643ea8Slogwang      */
386a9643ea8Slogwang     LastCharIsDigit =
387a9643ea8Slogwang         (isdigit ((int) NameString[3]));    /* d */
388a9643ea8Slogwang     LastCharsAreHex =
389a9643ea8Slogwang         (isxdigit ((int) NameString[2]) &&  /* xx */
390a9643ea8Slogwang          isxdigit ((int) NameString[3]));
391a9643ea8Slogwang 
392a9643ea8Slogwang     switch (NameString[1])
393a9643ea8Slogwang     {
394a9643ea8Slogwang     case 'A':
395a9643ea8Slogwang 
396a9643ea8Slogwang         if ((NameString[2] == 'C') && (LastCharIsDigit))
397a9643ea8Slogwang         {
398a9643ea8Slogwang             NameString = "_ACx";
399a9643ea8Slogwang         }
400a9643ea8Slogwang         else if ((NameString[2] == 'L') && (LastCharIsDigit))
401a9643ea8Slogwang         {
402a9643ea8Slogwang             NameString = "_ALx";
403a9643ea8Slogwang         }
404a9643ea8Slogwang         break;
405a9643ea8Slogwang 
406a9643ea8Slogwang     case 'E':
407a9643ea8Slogwang 
408a9643ea8Slogwang         if ((NameString[2] == 'J') && (LastCharIsDigit))
409a9643ea8Slogwang         {
410a9643ea8Slogwang             NameString = "_EJx";
411a9643ea8Slogwang         }
412a9643ea8Slogwang         else if (LastCharsAreHex)
413a9643ea8Slogwang         {
414a9643ea8Slogwang             NameString = "_Exx";
415a9643ea8Slogwang         }
416a9643ea8Slogwang         break;
417a9643ea8Slogwang 
418a9643ea8Slogwang     case 'L':
419a9643ea8Slogwang 
420a9643ea8Slogwang         if (LastCharsAreHex)
421a9643ea8Slogwang         {
422a9643ea8Slogwang             NameString = "_Lxx";
423a9643ea8Slogwang         }
424a9643ea8Slogwang         break;
425a9643ea8Slogwang 
426a9643ea8Slogwang     case 'Q':
427a9643ea8Slogwang 
428a9643ea8Slogwang         if (LastCharsAreHex)
429a9643ea8Slogwang         {
430a9643ea8Slogwang             NameString = "_Qxx";
431a9643ea8Slogwang         }
432a9643ea8Slogwang         break;
433a9643ea8Slogwang 
434a9643ea8Slogwang     case 'T':
435a9643ea8Slogwang 
436a9643ea8Slogwang         if (NameString[2] == '_')
437a9643ea8Slogwang         {
438a9643ea8Slogwang             NameString = "_T_x";
439a9643ea8Slogwang         }
440a9643ea8Slogwang         break;
441a9643ea8Slogwang 
442a9643ea8Slogwang     case 'W':
443a9643ea8Slogwang 
444a9643ea8Slogwang         if (LastCharsAreHex)
445a9643ea8Slogwang         {
446a9643ea8Slogwang             NameString = "_Wxx";
447a9643ea8Slogwang         }
448a9643ea8Slogwang         break;
449a9643ea8Slogwang 
450a9643ea8Slogwang     default:
451a9643ea8Slogwang 
452a9643ea8Slogwang         break;
453a9643ea8Slogwang     }
454a9643ea8Slogwang 
455a9643ea8Slogwang     /* Match the name in the info table */
456a9643ea8Slogwang 
457a9643ea8Slogwang     Info = AcpiAhMatchPredefinedName (NameString);
458a9643ea8Slogwang     if (Info)
459a9643ea8Slogwang     {
460a9643ea8Slogwang         AcpiOsPrintf ("  // %4.4s: %s",
461a9643ea8Slogwang             NameString, ACPI_CAST_PTR (char, Info->Description));
462a9643ea8Slogwang     }
463a9643ea8Slogwang 
464a9643ea8Slogwang #endif
465a9643ea8Slogwang     return;
466a9643ea8Slogwang }
467a9643ea8Slogwang 
468a9643ea8Slogwang 
469a9643ea8Slogwang /*******************************************************************************
470a9643ea8Slogwang  *
471a9643ea8Slogwang  * FUNCTION:    AcpiDmFieldPredefinedDescription
472a9643ea8Slogwang  *
473a9643ea8Slogwang  * PARAMETERS:  Op              - Parse object
474a9643ea8Slogwang  *
475a9643ea8Slogwang  * RETURN:      None
476a9643ea8Slogwang  *
477a9643ea8Slogwang  * DESCRIPTION: Emit a description comment for a resource descriptor tag
478a9643ea8Slogwang  *              (which is a predefined ACPI name.) Used for iASL compiler only.
479a9643ea8Slogwang  *
480a9643ea8Slogwang  ******************************************************************************/
481a9643ea8Slogwang 
482a9643ea8Slogwang void
AcpiDmFieldPredefinedDescription(ACPI_PARSE_OBJECT * Op)483a9643ea8Slogwang AcpiDmFieldPredefinedDescription (
484a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
485a9643ea8Slogwang {
486a9643ea8Slogwang #ifdef ACPI_ASL_COMPILER
487a9643ea8Slogwang     ACPI_PARSE_OBJECT       *IndexOp;
488a9643ea8Slogwang     char                    *Tag;
489a9643ea8Slogwang     const ACPI_OPCODE_INFO  *OpInfo;
490a9643ea8Slogwang     const AH_PREDEFINED_NAME *Info;
491a9643ea8Slogwang 
492a9643ea8Slogwang 
493a9643ea8Slogwang     if (!Op)
494a9643ea8Slogwang     {
495a9643ea8Slogwang         return;
496a9643ea8Slogwang     }
497a9643ea8Slogwang 
498a9643ea8Slogwang     /* Ensure that the comment field is emitted only once */
499a9643ea8Slogwang 
500a9643ea8Slogwang     if (Op->Common.DisasmFlags & ACPI_PARSEOP_PREDEFINED_CHECKED)
501a9643ea8Slogwang     {
502a9643ea8Slogwang         return;
503a9643ea8Slogwang     }
504a9643ea8Slogwang     Op->Common.DisasmFlags |= ACPI_PARSEOP_PREDEFINED_CHECKED;
505a9643ea8Slogwang 
506a9643ea8Slogwang     /*
507a9643ea8Slogwang      * Op must be one of the Create* operators: CreateField, CreateBitField,
508a9643ea8Slogwang      * CreateByteField, CreateWordField, CreateDwordField, CreateQwordField
509a9643ea8Slogwang      */
510a9643ea8Slogwang     OpInfo = AcpiPsGetOpcodeInfo (Op->Common.AmlOpcode);
511a9643ea8Slogwang     if (!(OpInfo->Flags & AML_CREATE))
512a9643ea8Slogwang     {
513a9643ea8Slogwang         return;
514a9643ea8Slogwang     }
515a9643ea8Slogwang 
516a9643ea8Slogwang     /* Second argument is the Index argument */
517a9643ea8Slogwang 
518a9643ea8Slogwang     IndexOp = Op->Common.Value.Arg;
519a9643ea8Slogwang     IndexOp = IndexOp->Common.Next;
520a9643ea8Slogwang 
521a9643ea8Slogwang     /* Index argument must be a namepath */
522a9643ea8Slogwang 
523a9643ea8Slogwang     if (IndexOp->Common.AmlOpcode != AML_INT_NAMEPATH_OP)
524a9643ea8Slogwang     {
525a9643ea8Slogwang         return;
526a9643ea8Slogwang     }
527a9643ea8Slogwang 
528a9643ea8Slogwang     /* Major cheat: We previously put the Tag ptr in the Node field */
529a9643ea8Slogwang 
530a9643ea8Slogwang     Tag = ACPI_CAST_PTR (char, IndexOp->Common.Node);
531*22ce4affSfengbojiang     if (!Tag || (*Tag == 0))
532a9643ea8Slogwang     {
533a9643ea8Slogwang         return;
534a9643ea8Slogwang     }
535a9643ea8Slogwang 
536*22ce4affSfengbojiang     /* Is the tag a predefined name? */
537a9643ea8Slogwang 
538a9643ea8Slogwang     Info = AcpiAhMatchPredefinedName (Tag);
539*22ce4affSfengbojiang     if (!Info)
540a9643ea8Slogwang     {
541*22ce4affSfengbojiang         /* Not a predefined name (does not start with underscore) */
542*22ce4affSfengbojiang 
543*22ce4affSfengbojiang         return;
544a9643ea8Slogwang     }
545a9643ea8Slogwang 
546*22ce4affSfengbojiang     AcpiOsPrintf ("  // %4.4s: %s", Tag,
547*22ce4affSfengbojiang         ACPI_CAST_PTR (char, Info->Description));
548*22ce4affSfengbojiang 
549*22ce4affSfengbojiang     /* String contains the prefix path, free it */
550*22ce4affSfengbojiang 
551*22ce4affSfengbojiang     ACPI_FREE (IndexOp->Common.Value.String);
552*22ce4affSfengbojiang     IndexOp->Common.Value.String = NULL;
553a9643ea8Slogwang #endif
554*22ce4affSfengbojiang 
555a9643ea8Slogwang     return;
556a9643ea8Slogwang }
557a9643ea8Slogwang 
558a9643ea8Slogwang 
559a9643ea8Slogwang /*******************************************************************************
560a9643ea8Slogwang  *
561a9643ea8Slogwang  * FUNCTION:    AcpiDmMethodFlags
562a9643ea8Slogwang  *
563a9643ea8Slogwang  * PARAMETERS:  Op              - Method Object to be examined
564a9643ea8Slogwang  *
565a9643ea8Slogwang  * RETURN:      None
566a9643ea8Slogwang  *
567a9643ea8Slogwang  * DESCRIPTION: Decode control method flags
568a9643ea8Slogwang  *
569a9643ea8Slogwang  ******************************************************************************/
570a9643ea8Slogwang 
571a9643ea8Slogwang void
AcpiDmMethodFlags(ACPI_PARSE_OBJECT * Op)572a9643ea8Slogwang AcpiDmMethodFlags (
573a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
574a9643ea8Slogwang {
575a9643ea8Slogwang     UINT32                  Flags;
576a9643ea8Slogwang     UINT32                  Args;
577a9643ea8Slogwang 
578a9643ea8Slogwang 
579a9643ea8Slogwang     /* The next Op contains the flags */
580a9643ea8Slogwang 
581a9643ea8Slogwang     Op = AcpiPsGetDepthNext (NULL, Op);
582a9643ea8Slogwang     Flags = (UINT8) Op->Common.Value.Integer;
583a9643ea8Slogwang     Args = Flags & 0x07;
584a9643ea8Slogwang 
585a9643ea8Slogwang     /* Mark the Op as completed */
586a9643ea8Slogwang 
587a9643ea8Slogwang     Op->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE;
588a9643ea8Slogwang 
589a9643ea8Slogwang     /* 1) Method argument count */
590a9643ea8Slogwang 
591a9643ea8Slogwang     AcpiOsPrintf (", %u, ", Args);
592a9643ea8Slogwang 
593a9643ea8Slogwang     /* 2) Serialize rule */
594a9643ea8Slogwang 
595a9643ea8Slogwang     if (!(Flags & 0x08))
596a9643ea8Slogwang     {
597a9643ea8Slogwang         AcpiOsPrintf ("Not");
598a9643ea8Slogwang     }
599a9643ea8Slogwang 
600a9643ea8Slogwang     AcpiOsPrintf ("Serialized");
601a9643ea8Slogwang 
602a9643ea8Slogwang     /* 3) SyncLevel */
603a9643ea8Slogwang 
604a9643ea8Slogwang     if (Flags & 0xF0)
605a9643ea8Slogwang     {
606a9643ea8Slogwang         AcpiOsPrintf (", %u", Flags >> 4);
607a9643ea8Slogwang     }
608a9643ea8Slogwang }
609a9643ea8Slogwang 
610a9643ea8Slogwang 
611a9643ea8Slogwang /*******************************************************************************
612a9643ea8Slogwang  *
613a9643ea8Slogwang  * FUNCTION:    AcpiDmFieldFlags
614a9643ea8Slogwang  *
615a9643ea8Slogwang  * PARAMETERS:  Op              - Field Object to be examined
616a9643ea8Slogwang  *
617a9643ea8Slogwang  * RETURN:      None
618a9643ea8Slogwang  *
619a9643ea8Slogwang  * DESCRIPTION: Decode Field definition flags
620a9643ea8Slogwang  *
621a9643ea8Slogwang  ******************************************************************************/
622a9643ea8Slogwang 
623a9643ea8Slogwang void
AcpiDmFieldFlags(ACPI_PARSE_OBJECT * Op)624a9643ea8Slogwang AcpiDmFieldFlags (
625a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
626a9643ea8Slogwang {
627a9643ea8Slogwang     UINT32                  Flags;
628a9643ea8Slogwang 
629a9643ea8Slogwang 
630a9643ea8Slogwang     Op = Op->Common.Next;
631a9643ea8Slogwang     Flags = (UINT8) Op->Common.Value.Integer;
632a9643ea8Slogwang 
633a9643ea8Slogwang     /* Mark the Op as completed */
634a9643ea8Slogwang 
635a9643ea8Slogwang     Op->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE;
636a9643ea8Slogwang 
637a9643ea8Slogwang     AcpiOsPrintf ("%s, ", AcpiGbl_AccessTypes [Flags & 0x07]);
638a9643ea8Slogwang     AcpiOsPrintf ("%s, ", AcpiGbl_LockRule [(Flags & 0x10) >> 4]);
639a9643ea8Slogwang     AcpiOsPrintf ("%s)",  AcpiGbl_UpdateRules [(Flags & 0x60) >> 5]);
640a9643ea8Slogwang }
641a9643ea8Slogwang 
642a9643ea8Slogwang 
643a9643ea8Slogwang /*******************************************************************************
644a9643ea8Slogwang  *
645a9643ea8Slogwang  * FUNCTION:    AcpiDmAddressSpace
646a9643ea8Slogwang  *
647a9643ea8Slogwang  * PARAMETERS:  SpaceId         - ID to be translated
648a9643ea8Slogwang  *
649a9643ea8Slogwang  * RETURN:      None
650a9643ea8Slogwang  *
651a9643ea8Slogwang  * DESCRIPTION: Decode a SpaceId to an AddressSpaceKeyword
652a9643ea8Slogwang  *
653a9643ea8Slogwang  ******************************************************************************/
654a9643ea8Slogwang 
655a9643ea8Slogwang void
AcpiDmAddressSpace(UINT8 SpaceId)656a9643ea8Slogwang AcpiDmAddressSpace (
657a9643ea8Slogwang     UINT8                   SpaceId)
658a9643ea8Slogwang {
659a9643ea8Slogwang 
660a9643ea8Slogwang     if (SpaceId >= ACPI_NUM_PREDEFINED_REGIONS)
661a9643ea8Slogwang     {
662a9643ea8Slogwang         if (SpaceId == 0x7F)
663a9643ea8Slogwang         {
664a9643ea8Slogwang             AcpiOsPrintf ("FFixedHW, ");
665a9643ea8Slogwang         }
666a9643ea8Slogwang         else
667a9643ea8Slogwang         {
668a9643ea8Slogwang             AcpiOsPrintf ("0x%.2X, ", SpaceId);
669a9643ea8Slogwang         }
670a9643ea8Slogwang     }
671a9643ea8Slogwang     else
672a9643ea8Slogwang     {
673a9643ea8Slogwang         AcpiOsPrintf ("%s, ", AcpiGbl_RegionTypes [SpaceId]);
674a9643ea8Slogwang     }
675a9643ea8Slogwang }
676a9643ea8Slogwang 
677a9643ea8Slogwang 
678a9643ea8Slogwang /*******************************************************************************
679a9643ea8Slogwang  *
680a9643ea8Slogwang  * FUNCTION:    AcpiDmRegionFlags
681a9643ea8Slogwang  *
682a9643ea8Slogwang  * PARAMETERS:  Op              - Object to be examined
683a9643ea8Slogwang  *
684a9643ea8Slogwang  * RETURN:      None
685a9643ea8Slogwang  *
686a9643ea8Slogwang  * DESCRIPTION: Decode OperationRegion flags
687a9643ea8Slogwang  *
688a9643ea8Slogwang  ******************************************************************************/
689a9643ea8Slogwang 
690a9643ea8Slogwang void
AcpiDmRegionFlags(ACPI_PARSE_OBJECT * Op)691a9643ea8Slogwang AcpiDmRegionFlags (
692a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
693a9643ea8Slogwang {
694a9643ea8Slogwang 
695a9643ea8Slogwang     /* The next Op contains the SpaceId */
696a9643ea8Slogwang 
697a9643ea8Slogwang     Op = AcpiPsGetDepthNext (NULL, Op);
698a9643ea8Slogwang 
699a9643ea8Slogwang     /* Mark the Op as completed */
700a9643ea8Slogwang 
701a9643ea8Slogwang     Op->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE;
702a9643ea8Slogwang 
703a9643ea8Slogwang     AcpiOsPrintf (", ");
704a9643ea8Slogwang     AcpiDmAddressSpace ((UINT8) Op->Common.Value.Integer);
705a9643ea8Slogwang }
706a9643ea8Slogwang 
707a9643ea8Slogwang 
708a9643ea8Slogwang /*******************************************************************************
709a9643ea8Slogwang  *
710a9643ea8Slogwang  * FUNCTION:    AcpiDmMatchOp
711a9643ea8Slogwang  *
712a9643ea8Slogwang  * PARAMETERS:  Op              - Match Object to be examined
713a9643ea8Slogwang  *
714a9643ea8Slogwang  * RETURN:      None
715a9643ea8Slogwang  *
716a9643ea8Slogwang  * DESCRIPTION: Decode Match opcode operands
717a9643ea8Slogwang  *
718a9643ea8Slogwang  ******************************************************************************/
719a9643ea8Slogwang 
720a9643ea8Slogwang void
AcpiDmMatchOp(ACPI_PARSE_OBJECT * Op)721a9643ea8Slogwang AcpiDmMatchOp (
722a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
723a9643ea8Slogwang {
724a9643ea8Slogwang     ACPI_PARSE_OBJECT       *NextOp;
725a9643ea8Slogwang 
726a9643ea8Slogwang 
727a9643ea8Slogwang     NextOp = AcpiPsGetDepthNext (NULL, Op);
728a9643ea8Slogwang     NextOp = NextOp->Common.Next;
729a9643ea8Slogwang 
730a9643ea8Slogwang     if (!NextOp)
731a9643ea8Slogwang     {
732a9643ea8Slogwang         /* Handle partial tree during single-step */
733a9643ea8Slogwang 
734a9643ea8Slogwang         return;
735a9643ea8Slogwang     }
736a9643ea8Slogwang 
737a9643ea8Slogwang     /* Mark the two nodes that contain the encoding for the match keywords */
738a9643ea8Slogwang 
739a9643ea8Slogwang     NextOp->Common.DisasmOpcode = ACPI_DASM_MATCHOP;
740a9643ea8Slogwang 
741a9643ea8Slogwang     NextOp = NextOp->Common.Next;
742a9643ea8Slogwang     NextOp = NextOp->Common.Next;
743a9643ea8Slogwang     NextOp->Common.DisasmOpcode = ACPI_DASM_MATCHOP;
744a9643ea8Slogwang }
745a9643ea8Slogwang 
746a9643ea8Slogwang 
747a9643ea8Slogwang /*******************************************************************************
748a9643ea8Slogwang  *
749a9643ea8Slogwang  * FUNCTION:    AcpiDmMatchKeyword
750a9643ea8Slogwang  *
751a9643ea8Slogwang  * PARAMETERS:  Op              - Match Object to be examined
752a9643ea8Slogwang  *
753a9643ea8Slogwang  * RETURN:      None
754a9643ea8Slogwang  *
755a9643ea8Slogwang  * DESCRIPTION: Decode Match opcode operands
756a9643ea8Slogwang  *
757a9643ea8Slogwang  ******************************************************************************/
758a9643ea8Slogwang 
759a9643ea8Slogwang static void
AcpiDmMatchKeyword(ACPI_PARSE_OBJECT * Op)760a9643ea8Slogwang AcpiDmMatchKeyword (
761a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
762a9643ea8Slogwang {
763a9643ea8Slogwang 
764a9643ea8Slogwang     if (((UINT32) Op->Common.Value.Integer) > ACPI_MAX_MATCH_OPCODE)
765a9643ea8Slogwang     {
766a9643ea8Slogwang         AcpiOsPrintf ("/* Unknown Match Keyword encoding */");
767a9643ea8Slogwang     }
768a9643ea8Slogwang     else
769a9643ea8Slogwang     {
770a9643ea8Slogwang         AcpiOsPrintf ("%s",
771a9643ea8Slogwang             AcpiGbl_MatchOps[(ACPI_SIZE) Op->Common.Value.Integer]);
772a9643ea8Slogwang     }
773a9643ea8Slogwang }
774a9643ea8Slogwang 
775a9643ea8Slogwang 
776a9643ea8Slogwang /*******************************************************************************
777a9643ea8Slogwang  *
778a9643ea8Slogwang  * FUNCTION:    AcpiDmDisassembleOneOp
779a9643ea8Slogwang  *
780a9643ea8Slogwang  * PARAMETERS:  WalkState           - Current walk info
781a9643ea8Slogwang  *              Info                - Parse tree walk info
782a9643ea8Slogwang  *              Op                  - Op that is to be printed
783a9643ea8Slogwang  *
784a9643ea8Slogwang  * RETURN:      None
785a9643ea8Slogwang  *
786a9643ea8Slogwang  * DESCRIPTION: Disassemble a single AML opcode
787a9643ea8Slogwang  *
788a9643ea8Slogwang  ******************************************************************************/
789a9643ea8Slogwang 
790a9643ea8Slogwang void
AcpiDmDisassembleOneOp(ACPI_WALK_STATE * WalkState,ACPI_OP_WALK_INFO * Info,ACPI_PARSE_OBJECT * Op)791a9643ea8Slogwang AcpiDmDisassembleOneOp (
792a9643ea8Slogwang     ACPI_WALK_STATE         *WalkState,
793a9643ea8Slogwang     ACPI_OP_WALK_INFO       *Info,
794a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Op)
795a9643ea8Slogwang {
796a9643ea8Slogwang     const ACPI_OPCODE_INFO  *OpInfo = NULL;
797a9643ea8Slogwang     UINT32                  Offset;
798a9643ea8Slogwang     UINT32                  Length;
799a9643ea8Slogwang     ACPI_PARSE_OBJECT       *Child;
800a9643ea8Slogwang     ACPI_STATUS             Status;
801a9643ea8Slogwang     UINT8                   *Aml;
802a9643ea8Slogwang     const AH_DEVICE_ID      *IdInfo;
803a9643ea8Slogwang 
804a9643ea8Slogwang 
805a9643ea8Slogwang     if (!Op)
806a9643ea8Slogwang     {
807a9643ea8Slogwang         AcpiOsPrintf ("<NULL OP PTR>");
808a9643ea8Slogwang         return;
809a9643ea8Slogwang     }
810a9643ea8Slogwang 
811a9643ea8Slogwang     if (Op->Common.DisasmFlags & ACPI_PARSEOP_ELSEIF)
812a9643ea8Slogwang     {
813a9643ea8Slogwang         return; /* ElseIf macro was already emitted */
814a9643ea8Slogwang     }
815a9643ea8Slogwang 
816a9643ea8Slogwang     switch (Op->Common.DisasmOpcode)
817a9643ea8Slogwang     {
818a9643ea8Slogwang     case ACPI_DASM_MATCHOP:
819a9643ea8Slogwang 
820a9643ea8Slogwang         AcpiDmMatchKeyword (Op);
821a9643ea8Slogwang         return;
822a9643ea8Slogwang 
823a9643ea8Slogwang     case ACPI_DASM_LNOT_SUFFIX:
824a9643ea8Slogwang 
825a9643ea8Slogwang         if (!AcpiGbl_CstyleDisassembly)
826a9643ea8Slogwang         {
827a9643ea8Slogwang             switch (Op->Common.AmlOpcode)
828a9643ea8Slogwang             {
829*22ce4affSfengbojiang             case AML_LOGICAL_EQUAL_OP:
830a9643ea8Slogwang                 AcpiOsPrintf ("LNotEqual");
831a9643ea8Slogwang                 break;
832a9643ea8Slogwang 
833*22ce4affSfengbojiang             case AML_LOGICAL_GREATER_OP:
834a9643ea8Slogwang                 AcpiOsPrintf ("LLessEqual");
835a9643ea8Slogwang                 break;
836a9643ea8Slogwang 
837*22ce4affSfengbojiang             case AML_LOGICAL_LESS_OP:
838a9643ea8Slogwang                 AcpiOsPrintf ("LGreaterEqual");
839a9643ea8Slogwang                 break;
840a9643ea8Slogwang 
841a9643ea8Slogwang             default:
842a9643ea8Slogwang                 break;
843a9643ea8Slogwang             }
844a9643ea8Slogwang         }
845a9643ea8Slogwang 
846a9643ea8Slogwang         Op->Common.DisasmOpcode = 0;
847a9643ea8Slogwang         Op->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE;
848a9643ea8Slogwang         return;
849a9643ea8Slogwang 
850a9643ea8Slogwang     default:
851a9643ea8Slogwang         break;
852a9643ea8Slogwang     }
853a9643ea8Slogwang 
854a9643ea8Slogwang     OpInfo = AcpiPsGetOpcodeInfo (Op->Common.AmlOpcode);
855a9643ea8Slogwang 
856a9643ea8Slogwang     /* The op and arguments */
857a9643ea8Slogwang 
858a9643ea8Slogwang     switch (Op->Common.AmlOpcode)
859a9643ea8Slogwang     {
860*22ce4affSfengbojiang     case AML_LOGICAL_NOT_OP:
861a9643ea8Slogwang 
862a9643ea8Slogwang         Child = Op->Common.Value.Arg;
863*22ce4affSfengbojiang         if ((Child->Common.AmlOpcode == AML_LOGICAL_EQUAL_OP) ||
864*22ce4affSfengbojiang             (Child->Common.AmlOpcode == AML_LOGICAL_GREATER_OP) ||
865*22ce4affSfengbojiang             (Child->Common.AmlOpcode == AML_LOGICAL_LESS_OP))
866a9643ea8Slogwang         {
867a9643ea8Slogwang             Child->Common.DisasmOpcode = ACPI_DASM_LNOT_SUFFIX;
868a9643ea8Slogwang             Op->Common.DisasmOpcode = ACPI_DASM_LNOT_PREFIX;
869a9643ea8Slogwang         }
870a9643ea8Slogwang         else
871a9643ea8Slogwang         {
872a9643ea8Slogwang             AcpiOsPrintf ("%s", OpInfo->Name);
873a9643ea8Slogwang         }
874a9643ea8Slogwang         break;
875a9643ea8Slogwang 
876a9643ea8Slogwang     case AML_BYTE_OP:
877a9643ea8Slogwang 
878a9643ea8Slogwang         AcpiOsPrintf ("0x%2.2X", (UINT32) Op->Common.Value.Integer);
879a9643ea8Slogwang         break;
880a9643ea8Slogwang 
881a9643ea8Slogwang     case AML_WORD_OP:
882a9643ea8Slogwang 
883a9643ea8Slogwang         if (Op->Common.DisasmOpcode == ACPI_DASM_EISAID)
884a9643ea8Slogwang         {
885a9643ea8Slogwang             AcpiDmDecompressEisaId ((UINT32) Op->Common.Value.Integer);
886a9643ea8Slogwang         }
887a9643ea8Slogwang         else
888a9643ea8Slogwang         {
889a9643ea8Slogwang             AcpiOsPrintf ("0x%4.4X", (UINT32) Op->Common.Value.Integer);
890a9643ea8Slogwang         }
891a9643ea8Slogwang         break;
892a9643ea8Slogwang 
893a9643ea8Slogwang     case AML_DWORD_OP:
894a9643ea8Slogwang 
895a9643ea8Slogwang         if (Op->Common.DisasmOpcode == ACPI_DASM_EISAID)
896a9643ea8Slogwang         {
897a9643ea8Slogwang             AcpiDmDecompressEisaId ((UINT32) Op->Common.Value.Integer);
898a9643ea8Slogwang         }
899a9643ea8Slogwang         else
900a9643ea8Slogwang         {
901a9643ea8Slogwang             AcpiOsPrintf ("0x%8.8X", (UINT32) Op->Common.Value.Integer);
902a9643ea8Slogwang         }
903a9643ea8Slogwang         break;
904a9643ea8Slogwang 
905a9643ea8Slogwang     case AML_QWORD_OP:
906a9643ea8Slogwang 
907a9643ea8Slogwang         AcpiOsPrintf ("0x%8.8X%8.8X",
908a9643ea8Slogwang             ACPI_FORMAT_UINT64 (Op->Common.Value.Integer));
909a9643ea8Slogwang         break;
910a9643ea8Slogwang 
911a9643ea8Slogwang     case AML_STRING_OP:
912a9643ea8Slogwang 
913a9643ea8Slogwang         AcpiUtPrintString (Op->Common.Value.String, ACPI_UINT16_MAX);
914a9643ea8Slogwang 
915a9643ea8Slogwang         /* For _HID/_CID strings, attempt to output a descriptive comment */
916a9643ea8Slogwang 
917a9643ea8Slogwang         if (Op->Common.DisasmOpcode == ACPI_DASM_HID_STRING)
918a9643ea8Slogwang         {
919a9643ea8Slogwang             /* If we know about the ID, emit the description */
920a9643ea8Slogwang 
921a9643ea8Slogwang             IdInfo = AcpiAhMatchHardwareId (Op->Common.Value.String);
922a9643ea8Slogwang             if (IdInfo)
923a9643ea8Slogwang             {
924a9643ea8Slogwang                 AcpiOsPrintf (" /* %s */", IdInfo->Description);
925a9643ea8Slogwang             }
926a9643ea8Slogwang         }
927a9643ea8Slogwang         break;
928a9643ea8Slogwang 
929a9643ea8Slogwang     case AML_BUFFER_OP:
930a9643ea8Slogwang         /*
931a9643ea8Slogwang          * Determine the type of buffer. We can have one of the following:
932a9643ea8Slogwang          *
933a9643ea8Slogwang          * 1) ResourceTemplate containing Resource Descriptors.
934a9643ea8Slogwang          * 2) Unicode String buffer
935a9643ea8Slogwang          * 3) ASCII String buffer
936a9643ea8Slogwang          * 4) Raw data buffer (if none of the above)
937a9643ea8Slogwang          *
938a9643ea8Slogwang          * Since there are no special AML opcodes to differentiate these
939a9643ea8Slogwang          * types of buffers, we have to closely look at the data in the
940a9643ea8Slogwang          * buffer to determine the type.
941a9643ea8Slogwang          */
942a9643ea8Slogwang         if (!AcpiGbl_NoResourceDisassembly)
943a9643ea8Slogwang         {
944a9643ea8Slogwang             Status = AcpiDmIsResourceTemplate (WalkState, Op);
945a9643ea8Slogwang             if (ACPI_SUCCESS (Status))
946a9643ea8Slogwang             {
947a9643ea8Slogwang                 Op->Common.DisasmOpcode = ACPI_DASM_RESOURCE;
948a9643ea8Slogwang                 AcpiOsPrintf ("ResourceTemplate");
949a9643ea8Slogwang                 break;
950a9643ea8Slogwang             }
951a9643ea8Slogwang             else if (Status == AE_AML_NO_RESOURCE_END_TAG)
952a9643ea8Slogwang             {
953a9643ea8Slogwang                 AcpiOsPrintf (
954a9643ea8Slogwang                     "/**** Is ResourceTemplate, "
955a9643ea8Slogwang                     "but EndTag not at buffer end ****/ ");
956a9643ea8Slogwang             }
957a9643ea8Slogwang         }
958a9643ea8Slogwang 
959a9643ea8Slogwang         if (AcpiDmIsUuidBuffer (Op))
960a9643ea8Slogwang         {
961a9643ea8Slogwang             Op->Common.DisasmOpcode = ACPI_DASM_UUID;
962a9643ea8Slogwang             AcpiOsPrintf ("ToUUID (");
963a9643ea8Slogwang         }
964a9643ea8Slogwang         else if (AcpiDmIsUnicodeBuffer (Op))
965a9643ea8Slogwang         {
966a9643ea8Slogwang             Op->Common.DisasmOpcode = ACPI_DASM_UNICODE;
967a9643ea8Slogwang             AcpiOsPrintf ("Unicode (");
968a9643ea8Slogwang         }
969a9643ea8Slogwang         else if (AcpiDmIsStringBuffer (Op))
970a9643ea8Slogwang         {
971a9643ea8Slogwang             Op->Common.DisasmOpcode = ACPI_DASM_STRING;
972a9643ea8Slogwang             AcpiOsPrintf ("Buffer");
973a9643ea8Slogwang         }
974a9643ea8Slogwang         else if (AcpiDmIsPldBuffer (Op))
975a9643ea8Slogwang         {
976a9643ea8Slogwang             Op->Common.DisasmOpcode = ACPI_DASM_PLD_METHOD;
977a9643ea8Slogwang             AcpiOsPrintf ("ToPLD (");
978a9643ea8Slogwang         }
979a9643ea8Slogwang         else
980a9643ea8Slogwang         {
981a9643ea8Slogwang             Op->Common.DisasmOpcode = ACPI_DASM_BUFFER;
982a9643ea8Slogwang             AcpiOsPrintf ("Buffer");
983a9643ea8Slogwang         }
984a9643ea8Slogwang         break;
985a9643ea8Slogwang 
986a9643ea8Slogwang     case AML_INT_NAMEPATH_OP:
987a9643ea8Slogwang 
988a9643ea8Slogwang         AcpiDmNamestring (Op->Common.Value.Name);
989a9643ea8Slogwang         break;
990a9643ea8Slogwang 
991a9643ea8Slogwang     case AML_INT_NAMEDFIELD_OP:
992a9643ea8Slogwang 
993a9643ea8Slogwang         Length = AcpiDmDumpName (Op->Named.Name);
994*22ce4affSfengbojiang 
995*22ce4affSfengbojiang         AcpiOsPrintf (",");
996*22ce4affSfengbojiang         ASL_CV_PRINT_ONE_COMMENT (Op, AML_NAMECOMMENT, NULL, 0);
997*22ce4affSfengbojiang         AcpiOsPrintf ("%*.s  %u", (unsigned) (5 - Length), " ",
998a9643ea8Slogwang             (UINT32) Op->Common.Value.Integer);
999*22ce4affSfengbojiang 
1000a9643ea8Slogwang         AcpiDmCommaIfFieldMember (Op);
1001a9643ea8Slogwang 
1002a9643ea8Slogwang         Info->BitOffset += (UINT32) Op->Common.Value.Integer;
1003a9643ea8Slogwang         break;
1004a9643ea8Slogwang 
1005a9643ea8Slogwang     case AML_INT_RESERVEDFIELD_OP:
1006a9643ea8Slogwang 
1007a9643ea8Slogwang         /* Offset() -- Must account for previous offsets */
1008a9643ea8Slogwang 
1009a9643ea8Slogwang         Offset = (UINT32) Op->Common.Value.Integer;
1010a9643ea8Slogwang         Info->BitOffset += Offset;
1011a9643ea8Slogwang 
1012a9643ea8Slogwang         if (Info->BitOffset % 8 == 0)
1013a9643ea8Slogwang         {
1014a9643ea8Slogwang             AcpiOsPrintf ("Offset (0x%.2X)", ACPI_DIV_8 (Info->BitOffset));
1015a9643ea8Slogwang         }
1016a9643ea8Slogwang         else
1017a9643ea8Slogwang         {
1018a9643ea8Slogwang             AcpiOsPrintf ("    ,   %u", Offset);
1019a9643ea8Slogwang         }
1020a9643ea8Slogwang 
1021a9643ea8Slogwang         AcpiDmCommaIfFieldMember (Op);
1022a9643ea8Slogwang         break;
1023a9643ea8Slogwang 
1024a9643ea8Slogwang     case AML_INT_ACCESSFIELD_OP:
1025a9643ea8Slogwang     case AML_INT_EXTACCESSFIELD_OP:
1026a9643ea8Slogwang 
1027a9643ea8Slogwang         AcpiOsPrintf ("AccessAs (%s, ",
1028a9643ea8Slogwang             AcpiGbl_AccessTypes [(UINT32) (Op->Common.Value.Integer & 0x7)]);
1029a9643ea8Slogwang 
1030a9643ea8Slogwang         AcpiDmDecodeAttribute ((UINT8) (Op->Common.Value.Integer >> 8));
1031a9643ea8Slogwang 
1032a9643ea8Slogwang         if (Op->Common.AmlOpcode == AML_INT_EXTACCESSFIELD_OP)
1033a9643ea8Slogwang         {
1034a9643ea8Slogwang             AcpiOsPrintf (" (0x%2.2X)", (unsigned)
1035a9643ea8Slogwang                 ((Op->Common.Value.Integer >> 16) & 0xFF));
1036a9643ea8Slogwang         }
1037a9643ea8Slogwang 
1038a9643ea8Slogwang         AcpiOsPrintf (")");
1039a9643ea8Slogwang         AcpiDmCommaIfFieldMember (Op);
1040*22ce4affSfengbojiang         ASL_CV_PRINT_ONE_COMMENT (Op, AML_COMMENT_END_NODE, NULL, 0);
1041a9643ea8Slogwang         break;
1042a9643ea8Slogwang 
1043a9643ea8Slogwang     case AML_INT_CONNECTION_OP:
1044a9643ea8Slogwang         /*
1045a9643ea8Slogwang          * Two types of Connection() - one with a buffer object, the
1046a9643ea8Slogwang          * other with a namestring that points to a buffer object.
1047a9643ea8Slogwang          */
1048a9643ea8Slogwang         AcpiOsPrintf ("Connection (");
1049a9643ea8Slogwang         Child = Op->Common.Value.Arg;
1050a9643ea8Slogwang 
1051a9643ea8Slogwang         if (Child->Common.AmlOpcode == AML_INT_BYTELIST_OP)
1052a9643ea8Slogwang         {
1053a9643ea8Slogwang             AcpiOsPrintf ("\n");
1054a9643ea8Slogwang 
1055a9643ea8Slogwang             Aml = Child->Named.Data;
1056a9643ea8Slogwang             Length = (UINT32) Child->Common.Value.Integer;
1057a9643ea8Slogwang 
1058a9643ea8Slogwang             Info->Level += 1;
1059a9643ea8Slogwang             Info->MappingOp = Op;
1060a9643ea8Slogwang             Op->Common.DisasmOpcode = ACPI_DASM_RESOURCE;
1061a9643ea8Slogwang 
1062a9643ea8Slogwang             AcpiDmResourceTemplate (Info, Op->Common.Parent, Aml, Length);
1063a9643ea8Slogwang 
1064a9643ea8Slogwang             Info->Level -= 1;
1065a9643ea8Slogwang             AcpiDmIndent (Info->Level);
1066a9643ea8Slogwang         }
1067a9643ea8Slogwang         else
1068a9643ea8Slogwang         {
1069a9643ea8Slogwang             AcpiDmNamestring (Child->Common.Value.Name);
1070a9643ea8Slogwang         }
1071a9643ea8Slogwang 
1072a9643ea8Slogwang         AcpiOsPrintf (")");
1073a9643ea8Slogwang         AcpiDmCommaIfFieldMember (Op);
1074*22ce4affSfengbojiang         ASL_CV_PRINT_ONE_COMMENT (Op, AML_COMMENT_END_NODE, NULL, 0);
1075*22ce4affSfengbojiang         ASL_CV_PRINT_ONE_COMMENT (Op, AMLCOMMENT_INLINE, NULL, 0);
1076a9643ea8Slogwang         AcpiOsPrintf ("\n");
1077a9643ea8Slogwang 
1078a9643ea8Slogwang         Op->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE; /* for now, ignore in AcpiDmAscendingOp */
1079a9643ea8Slogwang         Child->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE;
1080a9643ea8Slogwang         break;
1081a9643ea8Slogwang 
1082a9643ea8Slogwang     case AML_INT_BYTELIST_OP:
1083a9643ea8Slogwang 
1084a9643ea8Slogwang         AcpiDmByteList (Info, Op);
1085a9643ea8Slogwang         break;
1086a9643ea8Slogwang 
1087a9643ea8Slogwang     case AML_INT_METHODCALL_OP:
1088a9643ea8Slogwang 
1089a9643ea8Slogwang         Op = AcpiPsGetDepthNext (NULL, Op);
1090a9643ea8Slogwang         Op->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE;
1091a9643ea8Slogwang 
1092a9643ea8Slogwang         AcpiDmNamestring (Op->Common.Value.Name);
1093a9643ea8Slogwang         break;
1094a9643ea8Slogwang 
1095*22ce4affSfengbojiang     case AML_WHILE_OP:
1096*22ce4affSfengbojiang 
1097*22ce4affSfengbojiang         if (Op->Common.DisasmOpcode == ACPI_DASM_SWITCH)
1098*22ce4affSfengbojiang         {
1099*22ce4affSfengbojiang             AcpiOsPrintf ("%s", "Switch");
1100*22ce4affSfengbojiang             break;
1101*22ce4affSfengbojiang         }
1102*22ce4affSfengbojiang 
1103*22ce4affSfengbojiang         AcpiOsPrintf ("%s", OpInfo->Name);
1104*22ce4affSfengbojiang         break;
1105*22ce4affSfengbojiang 
1106*22ce4affSfengbojiang     case AML_IF_OP:
1107*22ce4affSfengbojiang 
1108*22ce4affSfengbojiang         if (Op->Common.DisasmOpcode == ACPI_DASM_CASE)
1109*22ce4affSfengbojiang         {
1110*22ce4affSfengbojiang             AcpiOsPrintf ("%s", "Case");
1111*22ce4affSfengbojiang             break;
1112*22ce4affSfengbojiang         }
1113*22ce4affSfengbojiang 
1114*22ce4affSfengbojiang         AcpiOsPrintf ("%s", OpInfo->Name);
1115*22ce4affSfengbojiang         break;
1116*22ce4affSfengbojiang 
1117a9643ea8Slogwang     case AML_ELSE_OP:
1118a9643ea8Slogwang 
1119a9643ea8Slogwang         AcpiDmConvertToElseIf (Op);
1120a9643ea8Slogwang         break;
1121a9643ea8Slogwang 
1122a9643ea8Slogwang     case AML_EXTERNAL_OP:
1123a9643ea8Slogwang 
1124a9643ea8Slogwang         if (AcpiGbl_DmEmitExternalOpcodes)
1125a9643ea8Slogwang         {
1126*22ce4affSfengbojiang             AcpiDmEmitExternal (Op, AcpiPsGetArg(Op, 0));
1127*22ce4affSfengbojiang         }
1128a9643ea8Slogwang 
1129a9643ea8Slogwang         break;
1130a9643ea8Slogwang 
1131a9643ea8Slogwang     default:
1132a9643ea8Slogwang 
1133a9643ea8Slogwang         /* Just get the opcode name and print it */
1134a9643ea8Slogwang 
1135a9643ea8Slogwang         AcpiOsPrintf ("%s", OpInfo->Name);
1136a9643ea8Slogwang 
1137a9643ea8Slogwang 
1138a9643ea8Slogwang #ifdef ACPI_DEBUGGER
1139a9643ea8Slogwang 
1140a9643ea8Slogwang         if ((Op->Common.AmlOpcode == AML_INT_RETURN_VALUE_OP) &&
1141a9643ea8Slogwang             (WalkState) &&
1142a9643ea8Slogwang             (WalkState->Results) &&
1143a9643ea8Slogwang             (WalkState->ResultCount))
1144a9643ea8Slogwang         {
1145a9643ea8Slogwang             AcpiDbDecodeInternalObject (
1146a9643ea8Slogwang                 WalkState->Results->Results.ObjDesc [
1147a9643ea8Slogwang                     (WalkState->ResultCount - 1) %
1148a9643ea8Slogwang                         ACPI_RESULTS_FRAME_OBJ_NUM]);
1149a9643ea8Slogwang         }
1150a9643ea8Slogwang #endif
1151a9643ea8Slogwang 
1152a9643ea8Slogwang         break;
1153a9643ea8Slogwang     }
1154a9643ea8Slogwang }
1155a9643ea8Slogwang 
1156a9643ea8Slogwang 
1157a9643ea8Slogwang /*******************************************************************************
1158a9643ea8Slogwang  *
1159a9643ea8Slogwang  * FUNCTION:    AcpiDmConvertToElseIf
1160a9643ea8Slogwang  *
1161a9643ea8Slogwang  * PARAMETERS:  OriginalElseOp          - ELSE Object to be examined
1162a9643ea8Slogwang  *
1163a9643ea8Slogwang  * RETURN:      None. Emits either an "Else" or an "ElseIf" ASL operator.
1164a9643ea8Slogwang  *
1165a9643ea8Slogwang  * DESCRIPTION: Detect and convert an If..Else..If sequence to If..ElseIf
1166a9643ea8Slogwang  *
1167a9643ea8Slogwang  * EXAMPLE:
1168a9643ea8Slogwang  *
1169a9643ea8Slogwang  * This If..Else..If nested sequence:
1170a9643ea8Slogwang  *
1171a9643ea8Slogwang  *        If (Arg0 == 1)
1172a9643ea8Slogwang  *        {
1173a9643ea8Slogwang  *            Local0 = 4
1174a9643ea8Slogwang  *        }
1175a9643ea8Slogwang  *        Else
1176a9643ea8Slogwang  *        {
1177a9643ea8Slogwang  *            If (Arg0 == 2)
1178a9643ea8Slogwang  *            {
1179a9643ea8Slogwang  *                Local0 = 5
1180a9643ea8Slogwang  *            }
1181a9643ea8Slogwang  *        }
1182a9643ea8Slogwang  *
1183a9643ea8Slogwang  * Is converted to this simpler If..ElseIf sequence:
1184a9643ea8Slogwang  *
1185a9643ea8Slogwang  *        If (Arg0 == 1)
1186a9643ea8Slogwang  *        {
1187a9643ea8Slogwang  *            Local0 = 4
1188a9643ea8Slogwang  *        }
1189a9643ea8Slogwang  *        ElseIf (Arg0 == 2)
1190a9643ea8Slogwang  *        {
1191a9643ea8Slogwang  *            Local0 = 5
1192a9643ea8Slogwang  *        }
1193a9643ea8Slogwang  *
1194a9643ea8Slogwang  * NOTE: There is no actual ElseIf AML opcode. ElseIf is essentially an ASL
1195a9643ea8Slogwang  * macro that emits an Else opcode followed by an If opcode. This function
1196a9643ea8Slogwang  * reverses these AML sequences back to an ElseIf macro where possible. This
1197a9643ea8Slogwang  * can make the disassembled ASL code simpler and more like the original code.
1198a9643ea8Slogwang  *
1199a9643ea8Slogwang  ******************************************************************************/
1200a9643ea8Slogwang 
1201a9643ea8Slogwang static void
AcpiDmConvertToElseIf(ACPI_PARSE_OBJECT * OriginalElseOp)1202a9643ea8Slogwang AcpiDmConvertToElseIf (
1203a9643ea8Slogwang     ACPI_PARSE_OBJECT       *OriginalElseOp)
1204a9643ea8Slogwang {
1205a9643ea8Slogwang     ACPI_PARSE_OBJECT       *IfOp;
1206a9643ea8Slogwang     ACPI_PARSE_OBJECT       *ElseOp;
1207a9643ea8Slogwang 
1208a9643ea8Slogwang 
1209a9643ea8Slogwang     /*
1210a9643ea8Slogwang      * To be able to perform the conversion, two conditions must be satisfied:
1211a9643ea8Slogwang      * 1) The first child of the Else must be an If statement.
1212a9643ea8Slogwang      * 2) The If block can only be followed by an Else block and these must
1213a9643ea8Slogwang      *    be the only blocks under the original Else.
1214a9643ea8Slogwang      */
1215a9643ea8Slogwang     IfOp = OriginalElseOp->Common.Value.Arg;
1216*22ce4affSfengbojiang 
1217a9643ea8Slogwang     if (!IfOp ||
1218a9643ea8Slogwang         (IfOp->Common.AmlOpcode != AML_IF_OP) ||
1219a9643ea8Slogwang         (IfOp->Asl.Next && (IfOp->Asl.Next->Common.AmlOpcode != AML_ELSE_OP)))
1220a9643ea8Slogwang     {
1221*22ce4affSfengbojiang         /* Not a proper Else..If sequence, cannot convert to ElseIf */
1222*22ce4affSfengbojiang 
1223*22ce4affSfengbojiang         if (OriginalElseOp->Common.DisasmOpcode == ACPI_DASM_DEFAULT)
1224*22ce4affSfengbojiang         {
1225*22ce4affSfengbojiang             AcpiOsPrintf ("%s", "Default");
1226*22ce4affSfengbojiang             return;
1227*22ce4affSfengbojiang         }
1228a9643ea8Slogwang 
1229a9643ea8Slogwang         AcpiOsPrintf ("%s", "Else");
1230a9643ea8Slogwang         return;
1231a9643ea8Slogwang     }
1232a9643ea8Slogwang 
1233*22ce4affSfengbojiang     /* Cannot have anything following the If...Else block */
1234*22ce4affSfengbojiang 
1235*22ce4affSfengbojiang     ElseOp = IfOp->Common.Next;
1236*22ce4affSfengbojiang     if (ElseOp && ElseOp->Common.Next)
1237*22ce4affSfengbojiang     {
1238*22ce4affSfengbojiang         if (OriginalElseOp->Common.DisasmOpcode == ACPI_DASM_DEFAULT)
1239*22ce4affSfengbojiang         {
1240*22ce4affSfengbojiang             AcpiOsPrintf ("%s", "Default");
1241*22ce4affSfengbojiang             return;
1242*22ce4affSfengbojiang         }
1243*22ce4affSfengbojiang 
1244*22ce4affSfengbojiang         AcpiOsPrintf ("%s", "Else");
1245*22ce4affSfengbojiang         return;
1246*22ce4affSfengbojiang     }
1247*22ce4affSfengbojiang 
1248*22ce4affSfengbojiang     if (OriginalElseOp->Common.DisasmOpcode == ACPI_DASM_DEFAULT)
1249*22ce4affSfengbojiang     {
1250*22ce4affSfengbojiang         /*
1251*22ce4affSfengbojiang          * There is an ElseIf but in this case the Else is actually
1252*22ce4affSfengbojiang          * a Default block for a Switch/Case statement. No conversion.
1253*22ce4affSfengbojiang          */
1254*22ce4affSfengbojiang         AcpiOsPrintf ("%s", "Default");
1255*22ce4affSfengbojiang         return;
1256*22ce4affSfengbojiang     }
1257*22ce4affSfengbojiang 
1258*22ce4affSfengbojiang     if (OriginalElseOp->Common.DisasmOpcode == ACPI_DASM_CASE)
1259*22ce4affSfengbojiang     {
1260*22ce4affSfengbojiang         /*
1261*22ce4affSfengbojiang          * This ElseIf is actually a Case block for a Switch/Case
1262*22ce4affSfengbojiang          * statement. Print Case but do not return so that we can
1263*22ce4affSfengbojiang          * promote the subtree and keep the indentation level.
1264*22ce4affSfengbojiang          */
1265*22ce4affSfengbojiang         AcpiOsPrintf ("%s", "Case");
1266*22ce4affSfengbojiang     }
1267*22ce4affSfengbojiang     else
1268*22ce4affSfengbojiang     {
1269a9643ea8Slogwang        /* Emit ElseIf, mark the IF as now an ELSEIF */
1270a9643ea8Slogwang 
1271a9643ea8Slogwang         AcpiOsPrintf ("%s", "ElseIf");
1272*22ce4affSfengbojiang     }
1273*22ce4affSfengbojiang 
1274a9643ea8Slogwang     IfOp->Common.DisasmFlags |= ACPI_PARSEOP_ELSEIF;
1275a9643ea8Slogwang 
1276a9643ea8Slogwang     /* The IF parent will now be the same as the original ELSE parent */
1277a9643ea8Slogwang 
1278a9643ea8Slogwang     IfOp->Common.Parent = OriginalElseOp->Common.Parent;
1279a9643ea8Slogwang 
1280a9643ea8Slogwang     /*
1281a9643ea8Slogwang      * Update the NEXT pointers to restructure the parse tree, essentially
1282a9643ea8Slogwang      * promoting an If..Else block up to the same level as the original
1283a9643ea8Slogwang      * Else.
1284a9643ea8Slogwang      *
1285a9643ea8Slogwang      * Check if the IF has a corresponding ELSE peer
1286a9643ea8Slogwang      */
1287a9643ea8Slogwang     ElseOp = IfOp->Common.Next;
1288a9643ea8Slogwang     if (ElseOp &&
1289a9643ea8Slogwang         (ElseOp->Common.AmlOpcode == AML_ELSE_OP))
1290a9643ea8Slogwang     {
1291a9643ea8Slogwang         /* If an ELSE matches the IF, promote it also */
1292a9643ea8Slogwang 
1293a9643ea8Slogwang         ElseOp->Common.Parent = OriginalElseOp->Common.Parent;
1294*22ce4affSfengbojiang 
1295*22ce4affSfengbojiang         /* Promote the entire block under the ElseIf (All Next OPs) */
1296*22ce4affSfengbojiang 
1297*22ce4affSfengbojiang         AcpiDmPromoteSubtree (OriginalElseOp);
1298a9643ea8Slogwang     }
1299a9643ea8Slogwang     else
1300a9643ea8Slogwang     {
1301a9643ea8Slogwang         /* Otherwise, set the IF NEXT to the original ELSE NEXT */
1302a9643ea8Slogwang 
1303a9643ea8Slogwang         IfOp->Common.Next = OriginalElseOp->Common.Next;
1304a9643ea8Slogwang     }
1305a9643ea8Slogwang 
1306a9643ea8Slogwang     /* Detach the child IF block from the original ELSE */
1307a9643ea8Slogwang 
1308a9643ea8Slogwang     OriginalElseOp->Common.Value.Arg = NULL;
1309a9643ea8Slogwang 
1310a9643ea8Slogwang     /* Ignore the original ELSE from now on */
1311a9643ea8Slogwang 
1312a9643ea8Slogwang     OriginalElseOp->Common.DisasmFlags |= ACPI_PARSEOP_IGNORE;
1313a9643ea8Slogwang     OriginalElseOp->Common.DisasmOpcode = ACPI_DASM_LNOT_PREFIX;
1314a9643ea8Slogwang 
1315a9643ea8Slogwang     /* Insert IF (now ELSEIF) as next peer of the original ELSE */
1316a9643ea8Slogwang 
1317a9643ea8Slogwang     OriginalElseOp->Common.Next = IfOp;
1318a9643ea8Slogwang }
1319*22ce4affSfengbojiang 
1320*22ce4affSfengbojiang 
1321*22ce4affSfengbojiang /*******************************************************************************
1322*22ce4affSfengbojiang  *
1323*22ce4affSfengbojiang  * FUNCTION:    AcpiDmPromoteSubtree
1324*22ce4affSfengbojiang  *
1325*22ce4affSfengbojiang  * PARAMETERS:  StartOpOp           - Original parent of the entire subtree
1326*22ce4affSfengbojiang  *
1327*22ce4affSfengbojiang  * RETURN:      None
1328*22ce4affSfengbojiang  *
1329*22ce4affSfengbojiang  * DESCRIPTION: Promote an entire parse subtree up one level.
1330*22ce4affSfengbojiang  *
1331*22ce4affSfengbojiang  ******************************************************************************/
1332*22ce4affSfengbojiang 
1333*22ce4affSfengbojiang static void
AcpiDmPromoteSubtree(ACPI_PARSE_OBJECT * StartOp)1334*22ce4affSfengbojiang AcpiDmPromoteSubtree (
1335*22ce4affSfengbojiang     ACPI_PARSE_OBJECT       *StartOp)
1336*22ce4affSfengbojiang {
1337*22ce4affSfengbojiang     ACPI_PARSE_OBJECT       *Op;
1338*22ce4affSfengbojiang     ACPI_PARSE_OBJECT       *ParentOp;
1339*22ce4affSfengbojiang 
1340*22ce4affSfengbojiang 
1341*22ce4affSfengbojiang     /* New parent for subtree elements */
1342*22ce4affSfengbojiang 
1343*22ce4affSfengbojiang     ParentOp = StartOp->Common.Parent;
1344*22ce4affSfengbojiang 
1345*22ce4affSfengbojiang     /* First child starts the subtree */
1346*22ce4affSfengbojiang 
1347*22ce4affSfengbojiang     Op = StartOp->Common.Value.Arg;
1348*22ce4affSfengbojiang 
1349*22ce4affSfengbojiang     /* Walk the top-level elements of the subtree */
1350*22ce4affSfengbojiang 
1351*22ce4affSfengbojiang     while (Op)
1352*22ce4affSfengbojiang     {
1353*22ce4affSfengbojiang         Op->Common.Parent = ParentOp;
1354*22ce4affSfengbojiang         if (!Op->Common.Next)
1355*22ce4affSfengbojiang         {
1356*22ce4affSfengbojiang             /* Last Op in list, update its next field */
1357*22ce4affSfengbojiang 
1358*22ce4affSfengbojiang             Op->Common.Next = StartOp->Common.Next;
1359*22ce4affSfengbojiang             break;
1360*22ce4affSfengbojiang         }
1361*22ce4affSfengbojiang         Op = Op->Common.Next;
1362*22ce4affSfengbojiang     }
1363*22ce4affSfengbojiang }
1364