xref: /freebsd/sys/contrib/dev/acpica/components/parser/psutils.c (revision a159c266a93c3c4f229864954c5f963acd8f60f2)
1*a159c266SJung-uk Kim /******************************************************************************
2*a159c266SJung-uk Kim  *
3*a159c266SJung-uk Kim  * Module Name: psutils - Parser miscellaneous utilities (Parser only)
4*a159c266SJung-uk Kim  *
5*a159c266SJung-uk Kim  *****************************************************************************/
6*a159c266SJung-uk Kim 
7*a159c266SJung-uk Kim /*
8*a159c266SJung-uk Kim  * Copyright (C) 2000 - 2012, Intel Corp.
9*a159c266SJung-uk Kim  * All rights reserved.
10*a159c266SJung-uk Kim  *
11*a159c266SJung-uk Kim  * Redistribution and use in source and binary forms, with or without
12*a159c266SJung-uk Kim  * modification, are permitted provided that the following conditions
13*a159c266SJung-uk Kim  * are met:
14*a159c266SJung-uk Kim  * 1. Redistributions of source code must retain the above copyright
15*a159c266SJung-uk Kim  *    notice, this list of conditions, and the following disclaimer,
16*a159c266SJung-uk Kim  *    without modification.
17*a159c266SJung-uk Kim  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18*a159c266SJung-uk Kim  *    substantially similar to the "NO WARRANTY" disclaimer below
19*a159c266SJung-uk Kim  *    ("Disclaimer") and any redistribution must be conditioned upon
20*a159c266SJung-uk Kim  *    including a substantially similar Disclaimer requirement for further
21*a159c266SJung-uk Kim  *    binary redistribution.
22*a159c266SJung-uk Kim  * 3. Neither the names of the above-listed copyright holders nor the names
23*a159c266SJung-uk Kim  *    of any contributors may be used to endorse or promote products derived
24*a159c266SJung-uk Kim  *    from this software without specific prior written permission.
25*a159c266SJung-uk Kim  *
26*a159c266SJung-uk Kim  * Alternatively, this software may be distributed under the terms of the
27*a159c266SJung-uk Kim  * GNU General Public License ("GPL") version 2 as published by the Free
28*a159c266SJung-uk Kim  * Software Foundation.
29*a159c266SJung-uk Kim  *
30*a159c266SJung-uk Kim  * NO WARRANTY
31*a159c266SJung-uk Kim  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32*a159c266SJung-uk Kim  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
33*a159c266SJung-uk Kim  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
34*a159c266SJung-uk Kim  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35*a159c266SJung-uk Kim  * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36*a159c266SJung-uk Kim  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37*a159c266SJung-uk Kim  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38*a159c266SJung-uk Kim  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39*a159c266SJung-uk Kim  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40*a159c266SJung-uk Kim  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41*a159c266SJung-uk Kim  * POSSIBILITY OF SUCH DAMAGES.
42*a159c266SJung-uk Kim  */
43*a159c266SJung-uk Kim 
44*a159c266SJung-uk Kim 
45*a159c266SJung-uk Kim #include <contrib/dev/acpica/include/acpi.h>
46*a159c266SJung-uk Kim #include <contrib/dev/acpica/include/accommon.h>
47*a159c266SJung-uk Kim #include <contrib/dev/acpica/include/acparser.h>
48*a159c266SJung-uk Kim #include <contrib/dev/acpica/include/amlcode.h>
49*a159c266SJung-uk Kim 
50*a159c266SJung-uk Kim #define _COMPONENT          ACPI_PARSER
51*a159c266SJung-uk Kim         ACPI_MODULE_NAME    ("psutils")
52*a159c266SJung-uk Kim 
53*a159c266SJung-uk Kim 
54*a159c266SJung-uk Kim /*******************************************************************************
55*a159c266SJung-uk Kim  *
56*a159c266SJung-uk Kim  * FUNCTION:    AcpiPsCreateScopeOp
57*a159c266SJung-uk Kim  *
58*a159c266SJung-uk Kim  * PARAMETERS:  None
59*a159c266SJung-uk Kim  *
60*a159c266SJung-uk Kim  * RETURN:      A new Scope object, null on failure
61*a159c266SJung-uk Kim  *
62*a159c266SJung-uk Kim  * DESCRIPTION: Create a Scope and associated namepath op with the root name
63*a159c266SJung-uk Kim  *
64*a159c266SJung-uk Kim  ******************************************************************************/
65*a159c266SJung-uk Kim 
66*a159c266SJung-uk Kim ACPI_PARSE_OBJECT *
67*a159c266SJung-uk Kim AcpiPsCreateScopeOp (
68*a159c266SJung-uk Kim     void)
69*a159c266SJung-uk Kim {
70*a159c266SJung-uk Kim     ACPI_PARSE_OBJECT       *ScopeOp;
71*a159c266SJung-uk Kim 
72*a159c266SJung-uk Kim 
73*a159c266SJung-uk Kim     ScopeOp = AcpiPsAllocOp (AML_SCOPE_OP);
74*a159c266SJung-uk Kim     if (!ScopeOp)
75*a159c266SJung-uk Kim     {
76*a159c266SJung-uk Kim         return (NULL);
77*a159c266SJung-uk Kim     }
78*a159c266SJung-uk Kim 
79*a159c266SJung-uk Kim     ScopeOp->Named.Name = ACPI_ROOT_NAME;
80*a159c266SJung-uk Kim     return (ScopeOp);
81*a159c266SJung-uk Kim }
82*a159c266SJung-uk Kim 
83*a159c266SJung-uk Kim 
84*a159c266SJung-uk Kim /*******************************************************************************
85*a159c266SJung-uk Kim  *
86*a159c266SJung-uk Kim  * FUNCTION:    AcpiPsInitOp
87*a159c266SJung-uk Kim  *
88*a159c266SJung-uk Kim  * PARAMETERS:  Op              - A newly allocated Op object
89*a159c266SJung-uk Kim  *              Opcode          - Opcode to store in the Op
90*a159c266SJung-uk Kim  *
91*a159c266SJung-uk Kim  * RETURN:      None
92*a159c266SJung-uk Kim  *
93*a159c266SJung-uk Kim  * DESCRIPTION: Initialize a parse (Op) object
94*a159c266SJung-uk Kim  *
95*a159c266SJung-uk Kim  ******************************************************************************/
96*a159c266SJung-uk Kim 
97*a159c266SJung-uk Kim void
98*a159c266SJung-uk Kim AcpiPsInitOp (
99*a159c266SJung-uk Kim     ACPI_PARSE_OBJECT       *Op,
100*a159c266SJung-uk Kim     UINT16                  Opcode)
101*a159c266SJung-uk Kim {
102*a159c266SJung-uk Kim     ACPI_FUNCTION_ENTRY ();
103*a159c266SJung-uk Kim 
104*a159c266SJung-uk Kim 
105*a159c266SJung-uk Kim     Op->Common.DescriptorType = ACPI_DESC_TYPE_PARSER;
106*a159c266SJung-uk Kim     Op->Common.AmlOpcode = Opcode;
107*a159c266SJung-uk Kim 
108*a159c266SJung-uk Kim     ACPI_DISASM_ONLY_MEMBERS (ACPI_STRNCPY (Op->Common.AmlOpName,
109*a159c266SJung-uk Kim             (AcpiPsGetOpcodeInfo (Opcode))->Name,
110*a159c266SJung-uk Kim                 sizeof (Op->Common.AmlOpName)));
111*a159c266SJung-uk Kim }
112*a159c266SJung-uk Kim 
113*a159c266SJung-uk Kim 
114*a159c266SJung-uk Kim /*******************************************************************************
115*a159c266SJung-uk Kim  *
116*a159c266SJung-uk Kim  * FUNCTION:    AcpiPsAllocOp
117*a159c266SJung-uk Kim  *
118*a159c266SJung-uk Kim  * PARAMETERS:  Opcode          - Opcode that will be stored in the new Op
119*a159c266SJung-uk Kim  *
120*a159c266SJung-uk Kim  * RETURN:      Pointer to the new Op, null on failure
121*a159c266SJung-uk Kim  *
122*a159c266SJung-uk Kim  * DESCRIPTION: Allocate an acpi_op, choose op type (and thus size) based on
123*a159c266SJung-uk Kim  *              opcode.  A cache of opcodes is available for the pure
124*a159c266SJung-uk Kim  *              GENERIC_OP, since this is by far the most commonly used.
125*a159c266SJung-uk Kim  *
126*a159c266SJung-uk Kim  ******************************************************************************/
127*a159c266SJung-uk Kim 
128*a159c266SJung-uk Kim ACPI_PARSE_OBJECT*
129*a159c266SJung-uk Kim AcpiPsAllocOp (
130*a159c266SJung-uk Kim     UINT16                  Opcode)
131*a159c266SJung-uk Kim {
132*a159c266SJung-uk Kim     ACPI_PARSE_OBJECT       *Op;
133*a159c266SJung-uk Kim     const ACPI_OPCODE_INFO  *OpInfo;
134*a159c266SJung-uk Kim     UINT8                   Flags = ACPI_PARSEOP_GENERIC;
135*a159c266SJung-uk Kim 
136*a159c266SJung-uk Kim 
137*a159c266SJung-uk Kim     ACPI_FUNCTION_ENTRY ();
138*a159c266SJung-uk Kim 
139*a159c266SJung-uk Kim 
140*a159c266SJung-uk Kim     OpInfo = AcpiPsGetOpcodeInfo (Opcode);
141*a159c266SJung-uk Kim 
142*a159c266SJung-uk Kim     /* Determine type of ParseOp required */
143*a159c266SJung-uk Kim 
144*a159c266SJung-uk Kim     if (OpInfo->Flags & AML_DEFER)
145*a159c266SJung-uk Kim     {
146*a159c266SJung-uk Kim         Flags = ACPI_PARSEOP_DEFERRED;
147*a159c266SJung-uk Kim     }
148*a159c266SJung-uk Kim     else if (OpInfo->Flags & AML_NAMED)
149*a159c266SJung-uk Kim     {
150*a159c266SJung-uk Kim         Flags = ACPI_PARSEOP_NAMED;
151*a159c266SJung-uk Kim     }
152*a159c266SJung-uk Kim     else if (Opcode == AML_INT_BYTELIST_OP)
153*a159c266SJung-uk Kim     {
154*a159c266SJung-uk Kim         Flags = ACPI_PARSEOP_BYTELIST;
155*a159c266SJung-uk Kim     }
156*a159c266SJung-uk Kim 
157*a159c266SJung-uk Kim     /* Allocate the minimum required size object */
158*a159c266SJung-uk Kim 
159*a159c266SJung-uk Kim     if (Flags == ACPI_PARSEOP_GENERIC)
160*a159c266SJung-uk Kim     {
161*a159c266SJung-uk Kim         /* The generic op (default) is by far the most common (16 to 1) */
162*a159c266SJung-uk Kim 
163*a159c266SJung-uk Kim         Op = AcpiOsAcquireObject (AcpiGbl_PsNodeCache);
164*a159c266SJung-uk Kim     }
165*a159c266SJung-uk Kim     else
166*a159c266SJung-uk Kim     {
167*a159c266SJung-uk Kim         /* Extended parseop */
168*a159c266SJung-uk Kim 
169*a159c266SJung-uk Kim         Op = AcpiOsAcquireObject (AcpiGbl_PsNodeExtCache);
170*a159c266SJung-uk Kim     }
171*a159c266SJung-uk Kim 
172*a159c266SJung-uk Kim     /* Initialize the Op */
173*a159c266SJung-uk Kim 
174*a159c266SJung-uk Kim     if (Op)
175*a159c266SJung-uk Kim     {
176*a159c266SJung-uk Kim         AcpiPsInitOp (Op, Opcode);
177*a159c266SJung-uk Kim         Op->Common.Flags = Flags;
178*a159c266SJung-uk Kim     }
179*a159c266SJung-uk Kim 
180*a159c266SJung-uk Kim     return (Op);
181*a159c266SJung-uk Kim }
182*a159c266SJung-uk Kim 
183*a159c266SJung-uk Kim 
184*a159c266SJung-uk Kim /*******************************************************************************
185*a159c266SJung-uk Kim  *
186*a159c266SJung-uk Kim  * FUNCTION:    AcpiPsFreeOp
187*a159c266SJung-uk Kim  *
188*a159c266SJung-uk Kim  * PARAMETERS:  Op              - Op to be freed
189*a159c266SJung-uk Kim  *
190*a159c266SJung-uk Kim  * RETURN:      None.
191*a159c266SJung-uk Kim  *
192*a159c266SJung-uk Kim  * DESCRIPTION: Free an Op object.  Either put it on the GENERIC_OP cache list
193*a159c266SJung-uk Kim  *              or actually free it.
194*a159c266SJung-uk Kim  *
195*a159c266SJung-uk Kim  ******************************************************************************/
196*a159c266SJung-uk Kim 
197*a159c266SJung-uk Kim void
198*a159c266SJung-uk Kim AcpiPsFreeOp (
199*a159c266SJung-uk Kim     ACPI_PARSE_OBJECT       *Op)
200*a159c266SJung-uk Kim {
201*a159c266SJung-uk Kim     ACPI_FUNCTION_NAME (PsFreeOp);
202*a159c266SJung-uk Kim 
203*a159c266SJung-uk Kim 
204*a159c266SJung-uk Kim     if (Op->Common.AmlOpcode == AML_INT_RETURN_VALUE_OP)
205*a159c266SJung-uk Kim     {
206*a159c266SJung-uk Kim         ACPI_DEBUG_PRINT ((ACPI_DB_ALLOCATIONS, "Free retval op: %p\n", Op));
207*a159c266SJung-uk Kim     }
208*a159c266SJung-uk Kim 
209*a159c266SJung-uk Kim     if (Op->Common.Flags & ACPI_PARSEOP_GENERIC)
210*a159c266SJung-uk Kim     {
211*a159c266SJung-uk Kim         (void) AcpiOsReleaseObject (AcpiGbl_PsNodeCache, Op);
212*a159c266SJung-uk Kim     }
213*a159c266SJung-uk Kim     else
214*a159c266SJung-uk Kim     {
215*a159c266SJung-uk Kim         (void) AcpiOsReleaseObject (AcpiGbl_PsNodeExtCache, Op);
216*a159c266SJung-uk Kim     }
217*a159c266SJung-uk Kim }
218*a159c266SJung-uk Kim 
219*a159c266SJung-uk Kim 
220*a159c266SJung-uk Kim /*******************************************************************************
221*a159c266SJung-uk Kim  *
222*a159c266SJung-uk Kim  * FUNCTION:    Utility functions
223*a159c266SJung-uk Kim  *
224*a159c266SJung-uk Kim  * DESCRIPTION: Low level character and object functions
225*a159c266SJung-uk Kim  *
226*a159c266SJung-uk Kim  ******************************************************************************/
227*a159c266SJung-uk Kim 
228*a159c266SJung-uk Kim 
229*a159c266SJung-uk Kim /*
230*a159c266SJung-uk Kim  * Is "c" a namestring lead character?
231*a159c266SJung-uk Kim  */
232*a159c266SJung-uk Kim BOOLEAN
233*a159c266SJung-uk Kim AcpiPsIsLeadingChar (
234*a159c266SJung-uk Kim     UINT32                  c)
235*a159c266SJung-uk Kim {
236*a159c266SJung-uk Kim     return ((BOOLEAN) (c == '_' || (c >= 'A' && c <= 'Z')));
237*a159c266SJung-uk Kim }
238*a159c266SJung-uk Kim 
239*a159c266SJung-uk Kim 
240*a159c266SJung-uk Kim /*
241*a159c266SJung-uk Kim  * Is "c" a namestring prefix character?
242*a159c266SJung-uk Kim  */
243*a159c266SJung-uk Kim BOOLEAN
244*a159c266SJung-uk Kim AcpiPsIsPrefixChar (
245*a159c266SJung-uk Kim     UINT32                  c)
246*a159c266SJung-uk Kim {
247*a159c266SJung-uk Kim     return ((BOOLEAN) (c == '\\' || c == '^'));
248*a159c266SJung-uk Kim }
249*a159c266SJung-uk Kim 
250*a159c266SJung-uk Kim 
251*a159c266SJung-uk Kim /*
252*a159c266SJung-uk Kim  * Get op's name (4-byte name segment) or 0 if unnamed
253*a159c266SJung-uk Kim  */
254*a159c266SJung-uk Kim UINT32
255*a159c266SJung-uk Kim AcpiPsGetName (
256*a159c266SJung-uk Kim     ACPI_PARSE_OBJECT       *Op)
257*a159c266SJung-uk Kim {
258*a159c266SJung-uk Kim 
259*a159c266SJung-uk Kim     /* The "generic" object has no name associated with it */
260*a159c266SJung-uk Kim 
261*a159c266SJung-uk Kim     if (Op->Common.Flags & ACPI_PARSEOP_GENERIC)
262*a159c266SJung-uk Kim     {
263*a159c266SJung-uk Kim         return (0);
264*a159c266SJung-uk Kim     }
265*a159c266SJung-uk Kim 
266*a159c266SJung-uk Kim     /* Only the "Extended" parse objects have a name */
267*a159c266SJung-uk Kim 
268*a159c266SJung-uk Kim     return (Op->Named.Name);
269*a159c266SJung-uk Kim }
270*a159c266SJung-uk Kim 
271*a159c266SJung-uk Kim 
272*a159c266SJung-uk Kim /*
273*a159c266SJung-uk Kim  * Set op's name
274*a159c266SJung-uk Kim  */
275*a159c266SJung-uk Kim void
276*a159c266SJung-uk Kim AcpiPsSetName (
277*a159c266SJung-uk Kim     ACPI_PARSE_OBJECT       *Op,
278*a159c266SJung-uk Kim     UINT32                  name)
279*a159c266SJung-uk Kim {
280*a159c266SJung-uk Kim 
281*a159c266SJung-uk Kim     /* The "generic" object has no name associated with it */
282*a159c266SJung-uk Kim 
283*a159c266SJung-uk Kim     if (Op->Common.Flags & ACPI_PARSEOP_GENERIC)
284*a159c266SJung-uk Kim     {
285*a159c266SJung-uk Kim         return;
286*a159c266SJung-uk Kim     }
287*a159c266SJung-uk Kim 
288*a159c266SJung-uk Kim     Op->Named.Name = name;
289*a159c266SJung-uk Kim }
290*a159c266SJung-uk Kim 
291