Back to home page

LXR

 
 

    


File indexing completed on 2025-05-11 08:24:03

0001 /******************************************************************************
0002  *
0003  * Module Name: psargs - Parse AML opcode arguments
0004  *
0005  *****************************************************************************/
0006 
0007 /******************************************************************************
0008  *
0009  * 1. Copyright Notice
0010  *
0011  * Some or all of this work - Copyright (c) 1999 - 2024, Intel Corp.
0012  * All rights reserved.
0013  *
0014  * 2. License
0015  *
0016  * 2.1. This is your license from Intel Corp. under its intellectual property
0017  * rights. You may have additional license terms from the party that provided
0018  * you this software, covering your right to use that party's intellectual
0019  * property rights.
0020  *
0021  * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a
0022  * copy of the source code appearing in this file ("Covered Code") an
0023  * irrevocable, perpetual, worldwide license under Intel's copyrights in the
0024  * base code distributed originally by Intel ("Original Intel Code") to copy,
0025  * make derivatives, distribute, use and display any portion of the Covered
0026  * Code in any form, with the right to sublicense such rights; and
0027  *
0028  * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent
0029  * license (with the right to sublicense), under only those claims of Intel
0030  * patents that are infringed by the Original Intel Code, to make, use, sell,
0031  * offer to sell, and import the Covered Code and derivative works thereof
0032  * solely to the minimum extent necessary to exercise the above copyright
0033  * license, and in no event shall the patent license extend to any additions
0034  * to or modifications of the Original Intel Code. No other license or right
0035  * is granted directly or by implication, estoppel or otherwise;
0036  *
0037  * The above copyright and patent license is granted only if the following
0038  * conditions are met:
0039  *
0040  * 3. Conditions
0041  *
0042  * 3.1. Redistribution of Source with Rights to Further Distribute Source.
0043  * Redistribution of source code of any substantial portion of the Covered
0044  * Code or modification with rights to further distribute source must include
0045  * the above Copyright Notice, the above License, this list of Conditions,
0046  * and the following Disclaimer and Export Compliance provision. In addition,
0047  * Licensee must cause all Covered Code to which Licensee contributes to
0048  * contain a file documenting the changes Licensee made to create that Covered
0049  * Code and the date of any change. Licensee must include in that file the
0050  * documentation of any changes made by any predecessor Licensee. Licensee
0051  * must include a prominent statement that the modification is derived,
0052  * directly or indirectly, from Original Intel Code.
0053  *
0054  * 3.2. Redistribution of Source with no Rights to Further Distribute Source.
0055  * Redistribution of source code of any substantial portion of the Covered
0056  * Code or modification without rights to further distribute source must
0057  * include the following Disclaimer and Export Compliance provision in the
0058  * documentation and/or other materials provided with distribution. In
0059  * addition, Licensee may not authorize further sublicense of source of any
0060  * portion of the Covered Code, and must include terms to the effect that the
0061  * license from Licensee to its licensee is limited to the intellectual
0062  * property embodied in the software Licensee provides to its licensee, and
0063  * not to intellectual property embodied in modifications its licensee may
0064  * make.
0065  *
0066  * 3.3. Redistribution of Executable. Redistribution in executable form of any
0067  * substantial portion of the Covered Code or modification must reproduce the
0068  * above Copyright Notice, and the following Disclaimer and Export Compliance
0069  * provision in the documentation and/or other materials provided with the
0070  * distribution.
0071  *
0072  * 3.4. Intel retains all right, title, and interest in and to the Original
0073  * Intel Code.
0074  *
0075  * 3.5. Neither the name Intel nor any other trademark owned or controlled by
0076  * Intel shall be used in advertising or otherwise to promote the sale, use or
0077  * other dealings in products derived from or relating to the Covered Code
0078  * without prior written authorization from Intel.
0079  *
0080  * 4. Disclaimer and Export Compliance
0081  *
0082  * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED
0083  * HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE
0084  * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE,
0085  * INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY
0086  * UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY
0087  * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A
0088  * PARTICULAR PURPOSE.
0089  *
0090  * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES
0091  * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR
0092  * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT,
0093  * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY
0094  * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL
0095  * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS
0096  * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY
0097  * LIMITED REMEDY.
0098  *
0099  * 4.3. Licensee shall not export, either directly or indirectly, any of this
0100  * software or system incorporating such software without first obtaining any
0101  * required license or other approval from the U. S. Department of Commerce or
0102  * any other agency or department of the United States Government. In the
0103  * event Licensee exports any such software from the United States or
0104  * re-exports any such software from a foreign destination, Licensee shall
0105  * ensure that the distribution and export/re-export of the software is in
0106  * compliance with all laws, regulations, orders, or other restrictions of the
0107  * U.S. Export Administration Regulations. Licensee agrees that neither it nor
0108  * any of its subsidiaries will export/re-export any technical data, process,
0109  * software, or service, directly or indirectly, to any country for which the
0110  * United States government or any agency thereof requires an export license,
0111  * other governmental approval, or letter of assurance, without first obtaining
0112  * such license, approval or letter.
0113  *
0114  *****************************************************************************
0115  *
0116  * Alternatively, you may choose to be licensed under the terms of the
0117  * following license:
0118  *
0119  * Redistribution and use in source and binary forms, with or without
0120  * modification, are permitted provided that the following conditions
0121  * are met:
0122  * 1. Redistributions of source code must retain the above copyright
0123  *    notice, this list of conditions, and the following disclaimer,
0124  *    without modification.
0125  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
0126  *    substantially similar to the "NO WARRANTY" disclaimer below
0127  *    ("Disclaimer") and any redistribution must be conditioned upon
0128  *    including a substantially similar Disclaimer requirement for further
0129  *    binary redistribution.
0130  * 3. Neither the names of the above-listed copyright holders nor the names
0131  *    of any contributors may be used to endorse or promote products derived
0132  *    from this software without specific prior written permission.
0133  *
0134  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
0135  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
0136  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
0137  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
0138  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
0139  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
0140  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
0141  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
0142  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
0143  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
0144  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
0145  *
0146  * Alternatively, you may choose to be licensed under the terms of the
0147  * GNU General Public License ("GPL") version 2 as published by the Free
0148  * Software Foundation.
0149  *
0150  *****************************************************************************/
0151 
0152 #include "acpi.h"
0153 #include "accommon.h"
0154 #include "acparser.h"
0155 #include "amlcode.h"
0156 #include "acnamesp.h"
0157 #include "acdispat.h"
0158 #include "acconvert.h"
0159 
0160 #define _COMPONENT          ACPI_PARSER
0161         ACPI_MODULE_NAME    ("psargs")
0162 
0163 /* Local prototypes */
0164 
0165 static UINT32
0166 AcpiPsGetNextPackageLength (
0167     ACPI_PARSE_STATE        *ParserState);
0168 
0169 static ACPI_PARSE_OBJECT *
0170 AcpiPsGetNextField (
0171     ACPI_PARSE_STATE        *ParserState);
0172 
0173 static void
0174 AcpiPsFreeFieldList (
0175     ACPI_PARSE_OBJECT       *Start);
0176 
0177 
0178 /*******************************************************************************
0179  *
0180  * FUNCTION:    AcpiPsGetNextPackageLength
0181  *
0182  * PARAMETERS:  ParserState         - Current parser state object
0183  *
0184  * RETURN:      Decoded package length. On completion, the AML pointer points
0185  *              past the length byte or bytes.
0186  *
0187  * DESCRIPTION: Decode and return a package length field.
0188  *              Note: Largest package length is 28 bits, from ACPI specification
0189  *
0190  ******************************************************************************/
0191 
0192 static UINT32
0193 AcpiPsGetNextPackageLength (
0194     ACPI_PARSE_STATE        *ParserState)
0195 {
0196     UINT8                   *Aml = ParserState->Aml;
0197     UINT32                  PackageLength = 0;
0198     UINT32                  ByteCount;
0199     UINT8                   ByteZeroMask = 0x3F; /* Default [0:5] */
0200 
0201 
0202     ACPI_FUNCTION_TRACE (PsGetNextPackageLength);
0203 
0204 
0205     /*
0206      * Byte 0 bits [6:7] contain the number of additional bytes
0207      * used to encode the package length, either 0,1,2, or 3
0208      */
0209     ByteCount = (Aml[0] >> 6);
0210     ParserState->Aml += ((ACPI_SIZE) ByteCount + 1);
0211 
0212     /* Get bytes 3, 2, 1 as needed */
0213 
0214     while (ByteCount)
0215     {
0216         /*
0217          * Final bit positions for the package length bytes:
0218          *      Byte3->[20:27]
0219          *      Byte2->[12:19]
0220          *      Byte1->[04:11]
0221          *      Byte0->[00:03]
0222          */
0223         PackageLength |= (Aml[ByteCount] << ((ByteCount << 3) - 4));
0224 
0225         ByteZeroMask = 0x0F; /* Use bits [0:3] of byte 0 */
0226         ByteCount--;
0227     }
0228 
0229     /* Byte 0 is a special case, either bits [0:3] or [0:5] are used */
0230 
0231     PackageLength |= (Aml[0] & ByteZeroMask);
0232     return_UINT32 (PackageLength);
0233 }
0234 
0235 
0236 /*******************************************************************************
0237  *
0238  * FUNCTION:    AcpiPsGetNextPackageEnd
0239  *
0240  * PARAMETERS:  ParserState         - Current parser state object
0241  *
0242  * RETURN:      Pointer to end-of-package +1
0243  *
0244  * DESCRIPTION: Get next package length and return a pointer past the end of
0245  *              the package. Consumes the package length field
0246  *
0247  ******************************************************************************/
0248 
0249 UINT8 *
0250 AcpiPsGetNextPackageEnd (
0251     ACPI_PARSE_STATE        *ParserState)
0252 {
0253     UINT8                   *Start = ParserState->Aml;
0254     UINT32                  PackageLength;
0255 
0256 
0257     ACPI_FUNCTION_TRACE (PsGetNextPackageEnd);
0258 
0259 
0260     /* Function below updates ParserState->Aml */
0261 
0262     PackageLength = AcpiPsGetNextPackageLength (ParserState);
0263 
0264     return_PTR (Start + PackageLength); /* end of package */
0265 }
0266 
0267 
0268 /*******************************************************************************
0269  *
0270  * FUNCTION:    AcpiPsGetNextNamestring
0271  *
0272  * PARAMETERS:  ParserState         - Current parser state object
0273  *
0274  * RETURN:      Pointer to the start of the name string (pointer points into
0275  *              the AML.
0276  *
0277  * DESCRIPTION: Get next raw namestring within the AML stream. Handles all name
0278  *              prefix characters. Set parser state to point past the string.
0279  *              (Name is consumed from the AML.)
0280  *
0281  ******************************************************************************/
0282 
0283 char *
0284 AcpiPsGetNextNamestring (
0285     ACPI_PARSE_STATE        *ParserState)
0286 {
0287     UINT8                   *Start = ParserState->Aml;
0288     UINT8                   *End = ParserState->Aml;
0289 
0290 
0291     ACPI_FUNCTION_TRACE (PsGetNextNamestring);
0292 
0293 
0294     /* Point past any namestring prefix characters (backslash or carat) */
0295 
0296     while (ACPI_IS_ROOT_PREFIX (*End) ||
0297            ACPI_IS_PARENT_PREFIX (*End))
0298     {
0299         End++;
0300     }
0301 
0302     /* Decode the path prefix character */
0303 
0304     switch (*End)
0305     {
0306     case 0:
0307 
0308         /* NullName */
0309 
0310         if (End == Start)
0311         {
0312             Start = NULL;
0313         }
0314         End++;
0315         break;
0316 
0317     case AML_DUAL_NAME_PREFIX:
0318 
0319         /* Two name segments */
0320 
0321         End += 1 + (2 * ACPI_NAMESEG_SIZE);
0322         break;
0323 
0324     case AML_MULTI_NAME_PREFIX:
0325 
0326         /* Multiple name segments, 4 chars each, count in next byte */
0327 
0328         End += 2 + (*(End + 1) * ACPI_NAMESEG_SIZE);
0329         break;
0330 
0331     default:
0332 
0333         /* Single name segment */
0334 
0335         End += ACPI_NAMESEG_SIZE;
0336         break;
0337     }
0338 
0339     ParserState->Aml = End;
0340     return_PTR ((char *) Start);
0341 }
0342 
0343 
0344 /*******************************************************************************
0345  *
0346  * FUNCTION:    AcpiPsGetNextNamepath
0347  *
0348  * PARAMETERS:  ParserState         - Current parser state object
0349  *              Arg                 - Where the namepath will be stored
0350  *              ArgCount            - If the namepath points to a control method
0351  *                                    the method's argument is returned here.
0352  *              PossibleMethodCall  - Whether the namepath can possibly be the
0353  *                                    start of a method call
0354  *
0355  * RETURN:      Status
0356  *
0357  * DESCRIPTION: Get next name (if method call, return # of required args).
0358  *              Names are looked up in the internal namespace to determine
0359  *              if the name represents a control method. If a method
0360  *              is found, the number of arguments to the method is returned.
0361  *              This information is critical for parsing to continue correctly.
0362  *
0363  ******************************************************************************/
0364 
0365 ACPI_STATUS
0366 AcpiPsGetNextNamepath (
0367     ACPI_WALK_STATE         *WalkState,
0368     ACPI_PARSE_STATE        *ParserState,
0369     ACPI_PARSE_OBJECT       *Arg,
0370     BOOLEAN                 PossibleMethodCall)
0371 {
0372     ACPI_STATUS             Status;
0373     char                    *Path;
0374     ACPI_PARSE_OBJECT       *NameOp;
0375     ACPI_OPERAND_OBJECT     *MethodDesc;
0376     ACPI_NAMESPACE_NODE     *Node;
0377     UINT8                   *Start = ParserState->Aml;
0378 
0379 
0380     ACPI_FUNCTION_TRACE (PsGetNextNamepath);
0381 
0382 
0383     Path = AcpiPsGetNextNamestring (ParserState);
0384     AcpiPsInitOp (Arg, AML_INT_NAMEPATH_OP);
0385 
0386     /* Null path case is allowed, just exit */
0387 
0388     if (!Path)
0389     {
0390         Arg->Common.Value.Name = Path;
0391         return_ACPI_STATUS (AE_OK);
0392     }
0393 
0394     /*
0395      * Lookup the name in the internal namespace, starting with the current
0396      * scope. We don't want to add anything new to the namespace here,
0397      * however, so we use MODE_EXECUTE.
0398      * Allow searching of the parent tree, but don't open a new scope -
0399      * we just want to lookup the object (must be mode EXECUTE to perform
0400      * the upsearch)
0401      */
0402     Status = AcpiNsLookup (WalkState->ScopeInfo, Path,
0403         ACPI_TYPE_ANY, ACPI_IMODE_EXECUTE,
0404         ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE, NULL, &Node);
0405 
0406     /*
0407      * If this name is a control method invocation, we must
0408      * setup the method call
0409      */
0410     if (ACPI_SUCCESS (Status) &&
0411         PossibleMethodCall &&
0412         (Node->Type == ACPI_TYPE_METHOD))
0413     {
0414         if ((GET_CURRENT_ARG_TYPE (WalkState->ArgTypes) == ARGP_SUPERNAME) ||
0415             (GET_CURRENT_ARG_TYPE (WalkState->ArgTypes) == ARGP_TARGET))
0416         {
0417             /*
0418              * AcpiPsGetNextNamestring has increased the AML pointer past
0419              * the method invocation namestring, so we need to restore the
0420              * saved AML pointer back to the original method invocation
0421              * namestring.
0422              */
0423             WalkState->ParserState.Aml = Start;
0424             WalkState->ArgCount = 1;
0425             AcpiPsInitOp (Arg, AML_INT_METHODCALL_OP);
0426         }
0427 
0428         /* This name is actually a control method invocation */
0429 
0430         MethodDesc = AcpiNsGetAttachedObject (Node);
0431         ACPI_DEBUG_PRINT ((ACPI_DB_PARSE,
0432             "Control Method invocation %4.4s - %p Desc %p Path=%p\n",
0433             Node->Name.Ascii, Node, MethodDesc, Path));
0434 
0435         NameOp = AcpiPsAllocOp (AML_INT_NAMEPATH_OP, Start);
0436         if (!NameOp)
0437         {
0438             return_ACPI_STATUS (AE_NO_MEMORY);
0439         }
0440 
0441         /* Change Arg into a METHOD CALL and attach name to it */
0442 
0443         AcpiPsInitOp (Arg, AML_INT_METHODCALL_OP);
0444         NameOp->Common.Value.Name = Path;
0445 
0446         /* Point METHODCALL/NAME to the METHOD Node */
0447 
0448         NameOp->Common.Node = Node;
0449         AcpiPsAppendArg (Arg, NameOp);
0450 
0451         if (!MethodDesc)
0452         {
0453             ACPI_ERROR ((AE_INFO,
0454                 "Control Method %p has no attached object",
0455                 Node));
0456             return_ACPI_STATUS (AE_AML_INTERNAL);
0457         }
0458 
0459         ACPI_DEBUG_PRINT ((ACPI_DB_PARSE,
0460             "Control Method - %p Args %X\n",
0461             Node, MethodDesc->Method.ParamCount));
0462 
0463         /* Get the number of arguments to expect */
0464 
0465         WalkState->ArgCount = MethodDesc->Method.ParamCount;
0466         return_ACPI_STATUS (AE_OK);
0467     }
0468 
0469     /*
0470      * Special handling if the name was not found during the lookup -
0471      * some NotFound cases are allowed
0472      */
0473     if (Status == AE_NOT_FOUND)
0474     {
0475         /* 1) NotFound is ok during load pass 1/2 (allow forward references) */
0476 
0477         if ((WalkState->ParseFlags & ACPI_PARSE_MODE_MASK) !=
0478             ACPI_PARSE_EXECUTE)
0479         {
0480             Status = AE_OK;
0481         }
0482 
0483         /* 2) NotFound during a CondRefOf(x) is ok by definition */
0484 
0485         else if (WalkState->Op->Common.AmlOpcode == AML_CONDITIONAL_REF_OF_OP)
0486         {
0487             Status = AE_OK;
0488         }
0489 
0490         /*
0491          * 3) NotFound while building a Package is ok at this point, we
0492          * may flag as an error later if slack mode is not enabled.
0493          * (Some ASL code depends on allowing this behavior)
0494          */
0495         else if ((Arg->Common.Parent) &&
0496             ((Arg->Common.Parent->Common.AmlOpcode == AML_PACKAGE_OP) ||
0497              (Arg->Common.Parent->Common.AmlOpcode == AML_VARIABLE_PACKAGE_OP)))
0498         {
0499             Status = AE_OK;
0500         }
0501     }
0502 
0503     /* Final exception check (may have been changed from code above) */
0504 
0505     if (ACPI_FAILURE (Status))
0506     {
0507         ACPI_ERROR_NAMESPACE (WalkState->ScopeInfo, Path, Status);
0508 
0509         if ((WalkState->ParseFlags & ACPI_PARSE_MODE_MASK) ==
0510             ACPI_PARSE_EXECUTE)
0511         {
0512             /* Report a control method execution error */
0513 
0514             Status = AcpiDsMethodError (Status, WalkState);
0515         }
0516     }
0517 
0518     /* Save the namepath */
0519 
0520     Arg->Common.Value.Name = Path;
0521     return_ACPI_STATUS (Status);
0522 }
0523 
0524 
0525 /*******************************************************************************
0526  *
0527  * FUNCTION:    AcpiPsGetNextSimpleArg
0528  *
0529  * PARAMETERS:  ParserState         - Current parser state object
0530  *              ArgType             - The argument type (AML_*_ARG)
0531  *              Arg                 - Where the argument is returned
0532  *
0533  * RETURN:      None
0534  *
0535  * DESCRIPTION: Get the next simple argument (constant, string, or namestring)
0536  *
0537  ******************************************************************************/
0538 
0539 void
0540 AcpiPsGetNextSimpleArg (
0541     ACPI_PARSE_STATE        *ParserState,
0542     UINT32                  ArgType,
0543     ACPI_PARSE_OBJECT       *Arg)
0544 {
0545     UINT32                  Length;
0546     UINT16                  Opcode;
0547     UINT8                   *Aml = ParserState->Aml;
0548 
0549 
0550     ACPI_FUNCTION_TRACE_U32 (PsGetNextSimpleArg, ArgType);
0551 
0552 
0553     switch (ArgType)
0554     {
0555     case ARGP_BYTEDATA:
0556 
0557         /* Get 1 byte from the AML stream */
0558 
0559         Opcode = AML_BYTE_OP;
0560         Arg->Common.Value.Integer = (UINT64) *Aml;
0561         Length = 1;
0562         break;
0563 
0564     case ARGP_WORDDATA:
0565 
0566         /* Get 2 bytes from the AML stream */
0567 
0568         Opcode = AML_WORD_OP;
0569         ACPI_MOVE_16_TO_64 (&Arg->Common.Value.Integer, Aml);
0570         Length = 2;
0571         break;
0572 
0573     case ARGP_DWORDDATA:
0574 
0575         /* Get 4 bytes from the AML stream */
0576 
0577         Opcode = AML_DWORD_OP;
0578         ACPI_MOVE_32_TO_64 (&Arg->Common.Value.Integer, Aml);
0579         Length = 4;
0580         break;
0581 
0582     case ARGP_QWORDDATA:
0583 
0584         /* Get 8 bytes from the AML stream */
0585 
0586         Opcode = AML_QWORD_OP;
0587         ACPI_MOVE_64_TO_64 (&Arg->Common.Value.Integer, Aml);
0588         Length = 8;
0589         break;
0590 
0591     case ARGP_CHARLIST:
0592 
0593         /* Get a pointer to the string, point past the string */
0594 
0595         Opcode = AML_STRING_OP;
0596         Arg->Common.Value.String = ACPI_CAST_PTR (char, Aml);
0597 
0598         /* Find the null terminator */
0599 
0600         Length = 0;
0601         while (Aml[Length])
0602         {
0603             Length++;
0604         }
0605         Length++;
0606         break;
0607 
0608     case ARGP_NAME:
0609     case ARGP_NAMESTRING:
0610 
0611         AcpiPsInitOp (Arg, AML_INT_NAMEPATH_OP);
0612         Arg->Common.Value.Name = AcpiPsGetNextNamestring (ParserState);
0613         return_VOID;
0614 
0615     default:
0616 
0617         ACPI_ERROR ((AE_INFO, "Invalid ArgType 0x%X", ArgType));
0618         return_VOID;
0619     }
0620 
0621     AcpiPsInitOp (Arg, Opcode);
0622     ParserState->Aml += Length;
0623     return_VOID;
0624 }
0625 
0626 
0627 /*******************************************************************************
0628  *
0629  * FUNCTION:    AcpiPsGetNextField
0630  *
0631  * PARAMETERS:  ParserState         - Current parser state object
0632  *
0633  * RETURN:      A newly allocated FIELD op
0634  *
0635  * DESCRIPTION: Get next field (NamedField, ReservedField, or AccessField)
0636  *
0637  ******************************************************************************/
0638 
0639 static ACPI_PARSE_OBJECT *
0640 AcpiPsGetNextField (
0641     ACPI_PARSE_STATE        *ParserState)
0642 {
0643     UINT8                   *Aml;
0644     ACPI_PARSE_OBJECT       *Field;
0645     ACPI_PARSE_OBJECT       *Arg = NULL;
0646     UINT16                  Opcode;
0647     UINT32                  Name;
0648     UINT8                   AccessType;
0649     UINT8                   AccessAttribute;
0650     UINT8                   AccessLength;
0651     UINT32                  PkgLength;
0652     UINT8                   *PkgEnd;
0653     UINT32                  BufferLength;
0654 
0655 
0656     ACPI_FUNCTION_TRACE (PsGetNextField);
0657 
0658 
0659     ASL_CV_CAPTURE_COMMENTS_ONLY (ParserState);
0660     Aml = ParserState->Aml;
0661 
0662     /* Determine field type */
0663 
0664     switch (ACPI_GET8 (ParserState->Aml))
0665     {
0666     case AML_FIELD_OFFSET_OP:
0667 
0668         Opcode = AML_INT_RESERVEDFIELD_OP;
0669         ParserState->Aml++;
0670         break;
0671 
0672     case AML_FIELD_ACCESS_OP:
0673 
0674         Opcode = AML_INT_ACCESSFIELD_OP;
0675         ParserState->Aml++;
0676         break;
0677 
0678     case AML_FIELD_CONNECTION_OP:
0679 
0680         Opcode = AML_INT_CONNECTION_OP;
0681         ParserState->Aml++;
0682         break;
0683 
0684     case AML_FIELD_EXT_ACCESS_OP:
0685 
0686         Opcode = AML_INT_EXTACCESSFIELD_OP;
0687         ParserState->Aml++;
0688         break;
0689 
0690     default:
0691 
0692         Opcode = AML_INT_NAMEDFIELD_OP;
0693         break;
0694     }
0695 
0696     /* Allocate a new field op */
0697 
0698     Field = AcpiPsAllocOp (Opcode, Aml);
0699     if (!Field)
0700     {
0701         return_PTR (NULL);
0702     }
0703 
0704     /* Decode the field type */
0705 
0706     ASL_CV_CAPTURE_COMMENTS_ONLY (ParserState);
0707     switch (Opcode)
0708     {
0709     case AML_INT_NAMEDFIELD_OP:
0710 
0711         /* Get the 4-character name */
0712 
0713         ACPI_MOVE_32_TO_32 (&Name, ParserState->Aml);
0714         AcpiPsSetName (Field, Name);
0715         ParserState->Aml += ACPI_NAMESEG_SIZE;
0716 
0717 
0718         ASL_CV_CAPTURE_COMMENTS_ONLY (ParserState);
0719 
0720 #ifdef ACPI_ASL_COMPILER
0721         /*
0722          * Because the package length isn't represented as a parse tree object,
0723          * take comments surrounding this and add to the previously created
0724          * parse node.
0725          */
0726         if (Field->Common.InlineComment)
0727         {
0728             Field->Common.NameComment = Field->Common.InlineComment;
0729         }
0730         Field->Common.InlineComment  = AcpiGbl_CurrentInlineComment;
0731         AcpiGbl_CurrentInlineComment = NULL;
0732 #endif
0733 
0734         /* Get the length which is encoded as a package length */
0735 
0736         Field->Common.Value.Size = AcpiPsGetNextPackageLength (ParserState);
0737         break;
0738 
0739 
0740     case AML_INT_RESERVEDFIELD_OP:
0741 
0742         /* Get the length which is encoded as a package length */
0743 
0744         Field->Common.Value.Size = AcpiPsGetNextPackageLength (ParserState);
0745         break;
0746 
0747 
0748     case AML_INT_ACCESSFIELD_OP:
0749     case AML_INT_EXTACCESSFIELD_OP:
0750 
0751         /*
0752          * Get AccessType and AccessAttrib and merge into the field Op
0753          * AccessType is first operand, AccessAttribute is second. stuff
0754          * these bytes into the node integer value for convenience.
0755          */
0756 
0757         /* Get the two bytes (Type/Attribute) */
0758 
0759         AccessType = ACPI_GET8 (ParserState->Aml);
0760         ParserState->Aml++;
0761         AccessAttribute = ACPI_GET8 (ParserState->Aml);
0762         ParserState->Aml++;
0763 
0764         Field->Common.Value.Integer = (UINT8) AccessType;
0765         Field->Common.Value.Integer |= (UINT16) (AccessAttribute << 8);
0766 
0767         /* This opcode has a third byte, AccessLength */
0768 
0769         if (Opcode == AML_INT_EXTACCESSFIELD_OP)
0770         {
0771             AccessLength = ACPI_GET8 (ParserState->Aml);
0772             ParserState->Aml++;
0773 
0774             Field->Common.Value.Integer |= (UINT32) (AccessLength << 16);
0775         }
0776         break;
0777 
0778 
0779     case AML_INT_CONNECTION_OP:
0780 
0781         /*
0782          * Argument for Connection operator can be either a Buffer
0783          * (resource descriptor), or a NameString.
0784          */
0785         Aml = ParserState->Aml;
0786         if (ACPI_GET8 (ParserState->Aml) == AML_BUFFER_OP)
0787         {
0788             ParserState->Aml++;
0789 
0790             ASL_CV_CAPTURE_COMMENTS_ONLY (ParserState);
0791             PkgEnd = ParserState->Aml;
0792             PkgLength = AcpiPsGetNextPackageLength (ParserState);
0793             PkgEnd += PkgLength;
0794 
0795             ASL_CV_CAPTURE_COMMENTS_ONLY (ParserState);
0796             if (ParserState->Aml < PkgEnd)
0797             {
0798                 /* Non-empty list */
0799 
0800                 Arg = AcpiPsAllocOp (AML_INT_BYTELIST_OP, Aml);
0801                 if (!Arg)
0802                 {
0803                     AcpiPsFreeOp (Field);
0804                     return_PTR (NULL);
0805                 }
0806 
0807                 /* Get the actual buffer length argument */
0808 
0809                 Opcode = ACPI_GET8 (ParserState->Aml);
0810                 ParserState->Aml++;
0811 
0812                 ASL_CV_CAPTURE_COMMENTS_ONLY (ParserState);
0813                 switch (Opcode)
0814                 {
0815                 case AML_BYTE_OP:       /* AML_BYTEDATA_ARG */
0816 
0817                     BufferLength = ACPI_GET8 (ParserState->Aml);
0818                     ParserState->Aml += 1;
0819                     break;
0820 
0821                 case AML_WORD_OP:       /* AML_WORDDATA_ARG */
0822 
0823                     BufferLength = ACPI_GET16 (ParserState->Aml);
0824                     ParserState->Aml += 2;
0825                     break;
0826 
0827                 case AML_DWORD_OP:      /* AML_DWORDATA_ARG */
0828 
0829                     BufferLength = ACPI_GET32 (ParserState->Aml);
0830                     ParserState->Aml += 4;
0831                     break;
0832 
0833                 default:
0834 
0835                     BufferLength = 0;
0836                     break;
0837                 }
0838 
0839                 /* Fill in bytelist data */
0840 
0841                 ASL_CV_CAPTURE_COMMENTS_ONLY (ParserState);
0842                 Arg->Named.Value.Size = BufferLength;
0843                 Arg->Named.Data = ParserState->Aml;
0844             }
0845 
0846             /* Skip to End of byte data */
0847 
0848             ParserState->Aml = PkgEnd;
0849         }
0850         else
0851         {
0852             Arg = AcpiPsAllocOp (AML_INT_NAMEPATH_OP, Aml);
0853             if (!Arg)
0854             {
0855                 AcpiPsFreeOp (Field);
0856                 return_PTR (NULL);
0857             }
0858 
0859             /* Get the Namestring argument */
0860 
0861             Arg->Common.Value.Name = AcpiPsGetNextNamestring (ParserState);
0862         }
0863 
0864         /* Link the buffer/namestring to parent (CONNECTION_OP) */
0865 
0866         AcpiPsAppendArg (Field, Arg);
0867         break;
0868 
0869 
0870     default:
0871 
0872         /* Opcode was set in previous switch */
0873         break;
0874     }
0875 
0876     return_PTR (Field);
0877 }
0878 
0879 /*******************************************************************************
0880  *
0881  * FUNCTION:    AcpiPsFreeFieldList
0882  *
0883  * PARAMETERS:  Start               - First Op in field list
0884  *
0885  * RETURN:      None.
0886  *
0887  * DESCRIPTION: Free all Op objects inside a field list.
0888  *
0889  ******************************************************************************/
0890 
0891 static void
0892 AcpiPsFreeFieldList (
0893     ACPI_PARSE_OBJECT   *Start)
0894 {
0895     ACPI_PARSE_OBJECT *Current = Start;
0896     ACPI_PARSE_OBJECT *Next;
0897     ACPI_PARSE_OBJECT *Arg;
0898 
0899     while (Current)
0900     {
0901         Next = Current->Common.Next;
0902 
0903         /* AML_INT_CONNECTION_OP can have a single argument */
0904 
0905         Arg = AcpiPsGetArg (Current, 0);
0906         if (Arg)
0907         {
0908             AcpiPsFreeOp (Arg);
0909         }
0910 
0911         AcpiPsFreeOp(Current);
0912         Current = Next;
0913     }
0914 }
0915 
0916 
0917 /*******************************************************************************
0918  *
0919  * FUNCTION:    AcpiPsGetNextArg
0920  *
0921  * PARAMETERS:  WalkState           - Current state
0922  *              ParserState         - Current parser state object
0923  *              ArgType             - The argument type (AML_*_ARG)
0924  *              ReturnArg           - Where the next arg is returned
0925  *
0926  * RETURN:      Status, and an op object containing the next argument.
0927  *
0928  * DESCRIPTION: Get next argument (including complex list arguments that require
0929  *              pushing the parser stack)
0930  *
0931  ******************************************************************************/
0932 
0933 ACPI_STATUS
0934 AcpiPsGetNextArg (
0935     ACPI_WALK_STATE         *WalkState,
0936     ACPI_PARSE_STATE        *ParserState,
0937     UINT32                  ArgType,
0938     ACPI_PARSE_OBJECT       **ReturnArg)
0939 {
0940     ACPI_PARSE_OBJECT       *Arg = NULL;
0941     ACPI_PARSE_OBJECT       *Prev = NULL;
0942     ACPI_PARSE_OBJECT       *Field;
0943     UINT32                  Subop;
0944     ACPI_STATUS             Status = AE_OK;
0945 
0946 
0947     ACPI_FUNCTION_TRACE_PTR (PsGetNextArg, ParserState);
0948 
0949 
0950     ACPI_DEBUG_PRINT ((ACPI_DB_PARSE,
0951         "Expected argument type ARGP: %s (%2.2X)\n",
0952         AcpiUtGetArgumentTypeName (ArgType), ArgType));
0953 
0954     switch (ArgType)
0955     {
0956     case ARGP_BYTEDATA:
0957     case ARGP_WORDDATA:
0958     case ARGP_DWORDDATA:
0959     case ARGP_CHARLIST:
0960     case ARGP_NAME:
0961     case ARGP_NAMESTRING:
0962 
0963         /* Constants, strings, and namestrings are all the same size */
0964 
0965         Arg = AcpiPsAllocOp (AML_BYTE_OP, ParserState->Aml);
0966         if (!Arg)
0967         {
0968             return_ACPI_STATUS (AE_NO_MEMORY);
0969         }
0970 
0971         AcpiPsGetNextSimpleArg (ParserState, ArgType, Arg);
0972         break;
0973 
0974     case ARGP_PKGLENGTH:
0975 
0976         /* Package length, nothing returned */
0977 
0978         ParserState->PkgEnd = AcpiPsGetNextPackageEnd (ParserState);
0979         break;
0980 
0981     case ARGP_FIELDLIST:
0982 
0983         if (ParserState->Aml < ParserState->PkgEnd)
0984         {
0985             /* Non-empty list */
0986 
0987             while (ParserState->Aml < ParserState->PkgEnd)
0988             {
0989                 Field = AcpiPsGetNextField (ParserState);
0990                 if (!Field)
0991                 {
0992                     if (Arg)
0993                     {
0994                         AcpiPsFreeFieldList(Arg);
0995                     }
0996 
0997                     return_ACPI_STATUS (AE_NO_MEMORY);
0998                 }
0999 
1000                 if (Prev)
1001                 {
1002                     Prev->Common.Next = Field;
1003                 }
1004                 else
1005                 {
1006                     Arg = Field;
1007                 }
1008                 Prev = Field;
1009             }
1010 
1011             /* Skip to End of byte data */
1012 
1013             ParserState->Aml = ParserState->PkgEnd;
1014         }
1015         break;
1016 
1017     case ARGP_BYTELIST:
1018 
1019         if (ParserState->Aml < ParserState->PkgEnd)
1020         {
1021             /* Non-empty list */
1022 
1023             Arg = AcpiPsAllocOp (AML_INT_BYTELIST_OP,
1024                 ParserState->Aml);
1025             if (!Arg)
1026             {
1027                 return_ACPI_STATUS (AE_NO_MEMORY);
1028             }
1029 
1030             /* Fill in bytelist data */
1031 
1032             Arg->Common.Value.Size = (UINT32)
1033                 ACPI_PTR_DIFF (ParserState->PkgEnd, ParserState->Aml);
1034             Arg->Named.Data = ParserState->Aml;
1035 
1036             /* Skip to End of byte data */
1037 
1038             ParserState->Aml = ParserState->PkgEnd;
1039         }
1040         break;
1041 
1042     case ARGP_SIMPLENAME:
1043     case ARGP_NAME_OR_REF:
1044 
1045         ACPI_DEBUG_PRINT ((ACPI_DB_PARSE,
1046             "**** SimpleName/NameOrRef: %s (%2.2X)\n",
1047             AcpiUtGetArgumentTypeName (ArgType), ArgType));
1048 
1049         Subop = AcpiPsPeekOpcode (ParserState);
1050         if (Subop == 0                  ||
1051             AcpiPsIsLeadingChar (Subop) ||
1052             ACPI_IS_ROOT_PREFIX (Subop) ||
1053             ACPI_IS_PARENT_PREFIX (Subop))
1054         {
1055             /* NullName or NameString */
1056 
1057             Arg = AcpiPsAllocOp (AML_INT_NAMEPATH_OP, ParserState->Aml);
1058             if (!Arg)
1059             {
1060                 return_ACPI_STATUS (AE_NO_MEMORY);
1061             }
1062 
1063             Status = AcpiPsGetNextNamepath (WalkState, ParserState,
1064                 Arg, ACPI_NOT_METHOD_CALL);
1065             if (ACPI_FAILURE(Status))
1066             {
1067                 AcpiPsFreeOp (Arg);
1068                 return_ACPI_STATUS (Status);
1069             }
1070         }
1071         else
1072         {
1073             /* Single complex argument, nothing returned */
1074 
1075             WalkState->ArgCount = 1;
1076         }
1077         break;
1078 
1079     case ARGP_TARGET:
1080     case ARGP_SUPERNAME:
1081 
1082         ACPI_DEBUG_PRINT ((ACPI_DB_PARSE,
1083             "**** Target/Supername: %s (%2.2X)\n",
1084             AcpiUtGetArgumentTypeName (ArgType), ArgType));
1085 
1086         Subop = AcpiPsPeekOpcode (ParserState);
1087         if (Subop == 0                  ||
1088             AcpiPsIsLeadingChar (Subop) ||
1089             ACPI_IS_ROOT_PREFIX (Subop) ||
1090             ACPI_IS_PARENT_PREFIX (Subop))
1091         {
1092             /* NULL target (zero). Convert to a NULL namepath */
1093 
1094             Arg = AcpiPsAllocOp (AML_INT_NAMEPATH_OP, ParserState->Aml);
1095             if (!Arg)
1096             {
1097                 return_ACPI_STATUS (AE_NO_MEMORY);
1098             }
1099 
1100             Status = AcpiPsGetNextNamepath (WalkState, ParserState,
1101                 Arg, ACPI_POSSIBLE_METHOD_CALL);
1102             if (ACPI_FAILURE(Status))
1103             {
1104                 AcpiPsFreeOp (Arg);
1105                 return_ACPI_STATUS (Status);
1106             }
1107 
1108             if (Arg->Common.AmlOpcode == AML_INT_METHODCALL_OP)
1109             {
1110                 /* Free method call op and corresponding namestring sub-ob */
1111 
1112                 AcpiPsFreeOp (Arg->Common.Value.Arg);
1113                 AcpiPsFreeOp (Arg);
1114                 Arg = NULL;
1115                 WalkState->ArgCount = 1;
1116             }
1117         }
1118         else
1119         {
1120             /* Single complex argument, nothing returned */
1121 
1122             WalkState->ArgCount = 1;
1123         }
1124         break;
1125 
1126     case ARGP_DATAOBJ:
1127     case ARGP_TERMARG:
1128 
1129         ACPI_DEBUG_PRINT ((ACPI_DB_PARSE,
1130             "**** TermArg/DataObj: %s (%2.2X)\n",
1131             AcpiUtGetArgumentTypeName (ArgType), ArgType));
1132 
1133         /* Single complex argument, nothing returned */
1134 
1135         WalkState->ArgCount = 1;
1136         break;
1137 
1138     case ARGP_DATAOBJLIST:
1139     case ARGP_TERMLIST:
1140     case ARGP_OBJLIST:
1141 
1142         if (ParserState->Aml < ParserState->PkgEnd)
1143         {
1144             /* Non-empty list of variable arguments, nothing returned */
1145 
1146             WalkState->ArgCount = ACPI_VAR_ARGS;
1147         }
1148         break;
1149 
1150     default:
1151 
1152         ACPI_ERROR ((AE_INFO, "Invalid ArgType: 0x%X", ArgType));
1153         Status = AE_AML_OPERAND_TYPE;
1154         break;
1155     }
1156 
1157     *ReturnArg = Arg;
1158     return_ACPI_STATUS (Status);
1159 }