Home | History | Annotate | Line # | Download | only in dispatcher
dsobject.c revision 1.1.1.3
      1 /******************************************************************************
      2  *
      3  * Module Name: dsobject - Dispatcher object management routines
      4  *
      5  *****************************************************************************/
      6 
      7 /*
      8  * Copyright (C) 2000 - 2013, Intel Corp.
      9  * All rights reserved.
     10  *
     11  * Redistribution and use in source and binary forms, with or without
     12  * modification, are permitted provided that the following conditions
     13  * are met:
     14  * 1. Redistributions of source code must retain the above copyright
     15  *    notice, this list of conditions, and the following disclaimer,
     16  *    without modification.
     17  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
     18  *    substantially similar to the "NO WARRANTY" disclaimer below
     19  *    ("Disclaimer") and any redistribution must be conditioned upon
     20  *    including a substantially similar Disclaimer requirement for further
     21  *    binary redistribution.
     22  * 3. Neither the names of the above-listed copyright holders nor the names
     23  *    of any contributors may be used to endorse or promote products derived
     24  *    from this software without specific prior written permission.
     25  *
     26  * Alternatively, this software may be distributed under the terms of the
     27  * GNU General Public License ("GPL") version 2 as published by the Free
     28  * Software Foundation.
     29  *
     30  * NO WARRANTY
     31  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     32  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     33  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
     34  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     35  * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     36  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
     37  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     38  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
     39  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
     40  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     41  * POSSIBILITY OF SUCH DAMAGES.
     42  */
     43 
     44 #define __DSOBJECT_C__
     45 
     46 #include "acpi.h"
     47 #include "accommon.h"
     48 #include "acparser.h"
     49 #include "amlcode.h"
     50 #include "acdispat.h"
     51 #include "acnamesp.h"
     52 #include "acinterp.h"
     53 
     54 #define _COMPONENT          ACPI_DISPATCHER
     55         ACPI_MODULE_NAME    ("dsobject")
     56 
     57 /* Local prototypes */
     58 
     59 static ACPI_STATUS
     60 AcpiDsBuildInternalObject (
     61     ACPI_WALK_STATE         *WalkState,
     62     ACPI_PARSE_OBJECT       *Op,
     63     ACPI_OPERAND_OBJECT     **ObjDescPtr);
     64 
     65 
     66 #ifndef ACPI_NO_METHOD_EXECUTION
     67 /*******************************************************************************
     68  *
     69  * FUNCTION:    AcpiDsBuildInternalObject
     70  *
     71  * PARAMETERS:  WalkState       - Current walk state
     72  *              Op              - Parser object to be translated
     73  *              ObjDescPtr      - Where the ACPI internal object is returned
     74  *
     75  * RETURN:      Status
     76  *
     77  * DESCRIPTION: Translate a parser Op object to the equivalent namespace object
     78  *              Simple objects are any objects other than a package object!
     79  *
     80  ******************************************************************************/
     81 
     82 static ACPI_STATUS
     83 AcpiDsBuildInternalObject (
     84     ACPI_WALK_STATE         *WalkState,
     85     ACPI_PARSE_OBJECT       *Op,
     86     ACPI_OPERAND_OBJECT     **ObjDescPtr)
     87 {
     88     ACPI_OPERAND_OBJECT     *ObjDesc;
     89     ACPI_STATUS             Status;
     90     ACPI_OBJECT_TYPE        Type;
     91 
     92 
     93     ACPI_FUNCTION_TRACE (DsBuildInternalObject);
     94 
     95 
     96     *ObjDescPtr = NULL;
     97     if (Op->Common.AmlOpcode == AML_INT_NAMEPATH_OP)
     98     {
     99         /*
    100          * This is a named object reference. If this name was
    101          * previously looked up in the namespace, it was stored in this op.
    102          * Otherwise, go ahead and look it up now
    103          */
    104         if (!Op->Common.Node)
    105         {
    106             Status = AcpiNsLookup (WalkState->ScopeInfo,
    107                         Op->Common.Value.String,
    108                         ACPI_TYPE_ANY, ACPI_IMODE_EXECUTE,
    109                         ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE, NULL,
    110                         ACPI_CAST_INDIRECT_PTR (ACPI_NAMESPACE_NODE, &(Op->Common.Node)));
    111             if (ACPI_FAILURE (Status))
    112             {
    113                 /* Check if we are resolving a named reference within a package */
    114 
    115                 if ((Status == AE_NOT_FOUND) && (AcpiGbl_EnableInterpreterSlack) &&
    116 
    117                     ((Op->Common.Parent->Common.AmlOpcode == AML_PACKAGE_OP) ||
    118                      (Op->Common.Parent->Common.AmlOpcode == AML_VAR_PACKAGE_OP)))
    119                 {
    120                     /*
    121                      * We didn't find the target and we are populating elements
    122                      * of a package - ignore if slack enabled. Some ASL code
    123                      * contains dangling invalid references in packages and
    124                      * expects that no exception will be issued. Leave the
    125                      * element as a null element. It cannot be used, but it
    126                      * can be overwritten by subsequent ASL code - this is
    127                      * typically the case.
    128                      */
    129                     ACPI_DEBUG_PRINT ((ACPI_DB_INFO,
    130                         "Ignoring unresolved reference in package [%4.4s]\n",
    131                         WalkState->ScopeInfo->Scope.Node->Name.Ascii));
    132 
    133                     return_ACPI_STATUS (AE_OK);
    134                 }
    135                 else
    136                 {
    137                     ACPI_ERROR_NAMESPACE (Op->Common.Value.String, Status);
    138                 }
    139 
    140                 return_ACPI_STATUS (Status);
    141             }
    142         }
    143 
    144         /* Special object resolution for elements of a package */
    145 
    146         if ((Op->Common.Parent->Common.AmlOpcode == AML_PACKAGE_OP) ||
    147             (Op->Common.Parent->Common.AmlOpcode == AML_VAR_PACKAGE_OP))
    148         {
    149             /*
    150              * Attempt to resolve the node to a value before we insert it into
    151              * the package. If this is a reference to a common data type,
    152              * resolve it immediately. According to the ACPI spec, package
    153              * elements can only be "data objects" or method references.
    154              * Attempt to resolve to an Integer, Buffer, String or Package.
    155              * If cannot, return the named reference (for things like Devices,
    156              * Methods, etc.) Buffer Fields and Fields will resolve to simple
    157              * objects (int/buf/str/pkg).
    158              *
    159              * NOTE: References to things like Devices, Methods, Mutexes, etc.
    160              * will remain as named references. This behavior is not described
    161              * in the ACPI spec, but it appears to be an oversight.
    162              */
    163             ObjDesc = ACPI_CAST_PTR (ACPI_OPERAND_OBJECT, Op->Common.Node);
    164 
    165             Status = AcpiExResolveNodeToValue (
    166                         ACPI_CAST_INDIRECT_PTR (ACPI_NAMESPACE_NODE, &ObjDesc),
    167                         WalkState);
    168             if (ACPI_FAILURE (Status))
    169             {
    170                 return_ACPI_STATUS (Status);
    171             }
    172 
    173             /*
    174              * Special handling for Alias objects. We need to setup the type
    175              * and the Op->Common.Node to point to the Alias target. Note,
    176              * Alias has at most one level of indirection internally.
    177              */
    178             Type = Op->Common.Node->Type;
    179             if (Type == ACPI_TYPE_LOCAL_ALIAS)
    180             {
    181                 Type = ObjDesc->Common.Type;
    182                 Op->Common.Node = ACPI_CAST_PTR (ACPI_NAMESPACE_NODE,
    183                     Op->Common.Node->Object);
    184             }
    185 
    186             switch (Type)
    187             {
    188             /*
    189              * For these types, we need the actual node, not the subobject.
    190              * However, the subobject did not get an extra reference count above.
    191              *
    192              * TBD: should ExResolveNodeToValue be changed to fix this?
    193              */
    194             case ACPI_TYPE_DEVICE:
    195             case ACPI_TYPE_THERMAL:
    196 
    197                 AcpiUtAddReference (Op->Common.Node->Object);
    198 
    199                 /*lint -fallthrough */
    200             /*
    201              * For these types, we need the actual node, not the subobject.
    202              * The subobject got an extra reference count in ExResolveNodeToValue.
    203              */
    204             case ACPI_TYPE_MUTEX:
    205             case ACPI_TYPE_METHOD:
    206             case ACPI_TYPE_POWER:
    207             case ACPI_TYPE_PROCESSOR:
    208             case ACPI_TYPE_EVENT:
    209             case ACPI_TYPE_REGION:
    210 
    211                 /* We will create a reference object for these types below */
    212                 break;
    213 
    214             default:
    215                 /*
    216                  * All other types - the node was resolved to an actual
    217                  * object, we are done.
    218                  */
    219                 goto Exit;
    220             }
    221         }
    222     }
    223 
    224     /* Create and init a new internal ACPI object */
    225 
    226     ObjDesc = AcpiUtCreateInternalObject (
    227                 (AcpiPsGetOpcodeInfo (Op->Common.AmlOpcode))->ObjectType);
    228     if (!ObjDesc)
    229     {
    230         return_ACPI_STATUS (AE_NO_MEMORY);
    231     }
    232 
    233     Status = AcpiDsInitObjectFromOp (WalkState, Op, Op->Common.AmlOpcode,
    234                 &ObjDesc);
    235     if (ACPI_FAILURE (Status))
    236     {
    237         AcpiUtRemoveReference (ObjDesc);
    238         return_ACPI_STATUS (Status);
    239     }
    240 
    241 Exit:
    242     *ObjDescPtr = ObjDesc;
    243     return_ACPI_STATUS (Status);
    244 }
    245 
    246 
    247 /*******************************************************************************
    248  *
    249  * FUNCTION:    AcpiDsBuildInternalBufferObj
    250  *
    251  * PARAMETERS:  WalkState       - Current walk state
    252  *              Op              - Parser object to be translated
    253  *              BufferLength    - Length of the buffer
    254  *              ObjDescPtr      - Where the ACPI internal object is returned
    255  *
    256  * RETURN:      Status
    257  *
    258  * DESCRIPTION: Translate a parser Op package object to the equivalent
    259  *              namespace object
    260  *
    261  ******************************************************************************/
    262 
    263 ACPI_STATUS
    264 AcpiDsBuildInternalBufferObj (
    265     ACPI_WALK_STATE         *WalkState,
    266     ACPI_PARSE_OBJECT       *Op,
    267     UINT32                  BufferLength,
    268     ACPI_OPERAND_OBJECT     **ObjDescPtr)
    269 {
    270     ACPI_PARSE_OBJECT       *Arg;
    271     ACPI_OPERAND_OBJECT     *ObjDesc;
    272     ACPI_PARSE_OBJECT       *ByteList;
    273     UINT32                  ByteListLength = 0;
    274 
    275 
    276     ACPI_FUNCTION_TRACE (DsBuildInternalBufferObj);
    277 
    278 
    279     /*
    280      * If we are evaluating a Named buffer object "Name (xxxx, Buffer)".
    281      * The buffer object already exists (from the NS node), otherwise it must
    282      * be created.
    283      */
    284     ObjDesc = *ObjDescPtr;
    285     if (!ObjDesc)
    286     {
    287         /* Create a new buffer object */
    288 
    289         ObjDesc = AcpiUtCreateInternalObject (ACPI_TYPE_BUFFER);
    290         *ObjDescPtr = ObjDesc;
    291         if (!ObjDesc)
    292         {
    293             return_ACPI_STATUS (AE_NO_MEMORY);
    294         }
    295     }
    296 
    297     /*
    298      * Second arg is the buffer data (optional) ByteList can be either
    299      * individual bytes or a string initializer. In either case, a
    300      * ByteList appears in the AML.
    301      */
    302     Arg = Op->Common.Value.Arg;         /* skip first arg */
    303 
    304     ByteList = Arg->Named.Next;
    305     if (ByteList)
    306     {
    307         if (ByteList->Common.AmlOpcode != AML_INT_BYTELIST_OP)
    308         {
    309             ACPI_ERROR ((AE_INFO,
    310                 "Expecting bytelist, found AML opcode 0x%X in op %p",
    311                 ByteList->Common.AmlOpcode, ByteList));
    312 
    313             AcpiUtRemoveReference (ObjDesc);
    314             return (AE_TYPE);
    315         }
    316 
    317         ByteListLength = (UINT32) ByteList->Common.Value.Integer;
    318     }
    319 
    320     /*
    321      * The buffer length (number of bytes) will be the larger of:
    322      * 1) The specified buffer length and
    323      * 2) The length of the initializer byte list
    324      */
    325     ObjDesc->Buffer.Length = BufferLength;
    326     if (ByteListLength > BufferLength)
    327     {
    328         ObjDesc->Buffer.Length = ByteListLength;
    329     }
    330 
    331     /* Allocate the buffer */
    332 
    333     if (ObjDesc->Buffer.Length == 0)
    334     {
    335         ObjDesc->Buffer.Pointer = NULL;
    336         ACPI_DEBUG_PRINT ((ACPI_DB_EXEC,
    337             "Buffer defined with zero length in AML, creating\n"));
    338     }
    339     else
    340     {
    341         ObjDesc->Buffer.Pointer = ACPI_ALLOCATE_ZEROED (
    342                                         ObjDesc->Buffer.Length);
    343         if (!ObjDesc->Buffer.Pointer)
    344         {
    345             AcpiUtDeleteObjectDesc (ObjDesc);
    346             return_ACPI_STATUS (AE_NO_MEMORY);
    347         }
    348 
    349         /* Initialize buffer from the ByteList (if present) */
    350 
    351         if (ByteList)
    352         {
    353             ACPI_MEMCPY (ObjDesc->Buffer.Pointer, ByteList->Named.Data,
    354                          ByteListLength);
    355         }
    356     }
    357 
    358     ObjDesc->Buffer.Flags |= AOPOBJ_DATA_VALID;
    359     Op->Common.Node = ACPI_CAST_PTR (ACPI_NAMESPACE_NODE, ObjDesc);
    360     return_ACPI_STATUS (AE_OK);
    361 }
    362 
    363 
    364 /*******************************************************************************
    365  *
    366  * FUNCTION:    AcpiDsBuildInternalPackageObj
    367  *
    368  * PARAMETERS:  WalkState       - Current walk state
    369  *              Op              - Parser object to be translated
    370  *              ElementCount    - Number of elements in the package - this is
    371  *                                the NumElements argument to Package()
    372  *              ObjDescPtr      - Where the ACPI internal object is returned
    373  *
    374  * RETURN:      Status
    375  *
    376  * DESCRIPTION: Translate a parser Op package object to the equivalent
    377  *              namespace object
    378  *
    379  * NOTE: The number of elements in the package will be always be the NumElements
    380  * count, regardless of the number of elements in the package list. If
    381  * NumElements is smaller, only that many package list elements are used.
    382  * if NumElements is larger, the Package object is padded out with
    383  * objects of type Uninitialized (as per ACPI spec.)
    384  *
    385  * Even though the ASL compilers do not allow NumElements to be smaller
    386  * than the Package list length (for the fixed length package opcode), some
    387  * BIOS code modifies the AML on the fly to adjust the NumElements, and
    388  * this code compensates for that. This also provides compatibility with
    389  * other AML interpreters.
    390  *
    391  ******************************************************************************/
    392 
    393 ACPI_STATUS
    394 AcpiDsBuildInternalPackageObj (
    395     ACPI_WALK_STATE         *WalkState,
    396     ACPI_PARSE_OBJECT       *Op,
    397     UINT32                  ElementCount,
    398     ACPI_OPERAND_OBJECT     **ObjDescPtr)
    399 {
    400     ACPI_PARSE_OBJECT       *Arg;
    401     ACPI_PARSE_OBJECT       *Parent;
    402     ACPI_OPERAND_OBJECT     *ObjDesc = NULL;
    403     ACPI_STATUS             Status = AE_OK;
    404     UINT32                  i;
    405     UINT16                  Index;
    406     UINT16                  ReferenceCount;
    407 
    408 
    409     ACPI_FUNCTION_TRACE (DsBuildInternalPackageObj);
    410 
    411 
    412     /* Find the parent of a possibly nested package */
    413 
    414     Parent = Op->Common.Parent;
    415     while ((Parent->Common.AmlOpcode == AML_PACKAGE_OP) ||
    416            (Parent->Common.AmlOpcode == AML_VAR_PACKAGE_OP))
    417     {
    418         Parent = Parent->Common.Parent;
    419     }
    420 
    421     /*
    422      * If we are evaluating a Named package object "Name (xxxx, Package)",
    423      * the package object already exists, otherwise it must be created.
    424      */
    425     ObjDesc = *ObjDescPtr;
    426     if (!ObjDesc)
    427     {
    428         ObjDesc = AcpiUtCreateInternalObject (ACPI_TYPE_PACKAGE);
    429         *ObjDescPtr = ObjDesc;
    430         if (!ObjDesc)
    431         {
    432             return_ACPI_STATUS (AE_NO_MEMORY);
    433         }
    434 
    435         ObjDesc->Package.Node = Parent->Common.Node;
    436     }
    437 
    438     /*
    439      * Allocate the element array (array of pointers to the individual
    440      * objects) based on the NumElements parameter. Add an extra pointer slot
    441      * so that the list is always null terminated.
    442      */
    443     ObjDesc->Package.Elements = ACPI_ALLOCATE_ZEROED (
    444         ((ACPI_SIZE) ElementCount + 1) * sizeof (void *));
    445 
    446     if (!ObjDesc->Package.Elements)
    447     {
    448         AcpiUtDeleteObjectDesc (ObjDesc);
    449         return_ACPI_STATUS (AE_NO_MEMORY);
    450     }
    451 
    452     ObjDesc->Package.Count = ElementCount;
    453 
    454     /*
    455      * Initialize the elements of the package, up to the NumElements count.
    456      * Package is automatically padded with uninitialized (NULL) elements
    457      * if NumElements is greater than the package list length. Likewise,
    458      * Package is truncated if NumElements is less than the list length.
    459      */
    460     Arg = Op->Common.Value.Arg;
    461     Arg = Arg->Common.Next;
    462     for (i = 0; Arg && (i < ElementCount); i++)
    463     {
    464         if (Arg->Common.AmlOpcode == AML_INT_RETURN_VALUE_OP)
    465         {
    466             if (Arg->Common.Node->Type == ACPI_TYPE_METHOD)
    467             {
    468                 /*
    469                  * A method reference "looks" to the parser to be a method
    470                  * invocation, so we special case it here
    471                  */
    472                 Arg->Common.AmlOpcode = AML_INT_NAMEPATH_OP;
    473                 Status = AcpiDsBuildInternalObject (WalkState, Arg,
    474                             &ObjDesc->Package.Elements[i]);
    475             }
    476             else
    477             {
    478                 /* This package element is already built, just get it */
    479 
    480                 ObjDesc->Package.Elements[i] =
    481                     ACPI_CAST_PTR (ACPI_OPERAND_OBJECT, Arg->Common.Node);
    482             }
    483         }
    484         else
    485         {
    486             Status = AcpiDsBuildInternalObject (WalkState, Arg,
    487                         &ObjDesc->Package.Elements[i]);
    488         }
    489 
    490         if (*ObjDescPtr)
    491         {
    492             /* Existing package, get existing reference count */
    493 
    494             ReferenceCount = (*ObjDescPtr)->Common.ReferenceCount;
    495             if (ReferenceCount > 1)
    496             {
    497                 /* Make new element ref count match original ref count */
    498 
    499                 for (Index = 0; Index < (ReferenceCount - 1); Index++)
    500                 {
    501                     AcpiUtAddReference ((ObjDesc->Package.Elements[i]));
    502                 }
    503             }
    504         }
    505 
    506         Arg = Arg->Common.Next;
    507     }
    508 
    509     /* Check for match between NumElements and actual length of PackageList */
    510 
    511     if (Arg)
    512     {
    513         /*
    514          * NumElements was exhausted, but there are remaining elements in the
    515          * PackageList. Truncate the package to NumElements.
    516          *
    517          * Note: technically, this is an error, from ACPI spec: "It is an error
    518          * for NumElements to be less than the number of elements in the
    519          * PackageList". However, we just print a message and
    520          * no exception is returned. This provides Windows compatibility. Some
    521          * BIOSs will alter the NumElements on the fly, creating this type
    522          * of ill-formed package object.
    523          */
    524         while (Arg)
    525         {
    526             /*
    527              * We must delete any package elements that were created earlier
    528              * and are not going to be used because of the package truncation.
    529              */
    530             if (Arg->Common.Node)
    531             {
    532                 AcpiUtRemoveReference (
    533                     ACPI_CAST_PTR (ACPI_OPERAND_OBJECT, Arg->Common.Node));
    534                 Arg->Common.Node = NULL;
    535             }
    536 
    537             /* Find out how many elements there really are */
    538 
    539             i++;
    540             Arg = Arg->Common.Next;
    541         }
    542 
    543         ACPI_INFO ((AE_INFO,
    544             "Actual Package length (%u) is larger than NumElements field (%u), truncated",
    545             i, ElementCount));
    546     }
    547     else if (i < ElementCount)
    548     {
    549         /*
    550          * Arg list (elements) was exhausted, but we did not reach NumElements count.
    551          * Note: this is not an error, the package is padded out with NULLs.
    552          */
    553         ACPI_DEBUG_PRINT ((ACPI_DB_INFO,
    554             "Package List length (%u) smaller than NumElements count (%u), padded with null elements\n",
    555             i, ElementCount));
    556     }
    557 
    558     ObjDesc->Package.Flags |= AOPOBJ_DATA_VALID;
    559     Op->Common.Node = ACPI_CAST_PTR (ACPI_NAMESPACE_NODE, ObjDesc);
    560     return_ACPI_STATUS (Status);
    561 }
    562 
    563 
    564 /*******************************************************************************
    565  *
    566  * FUNCTION:    AcpiDsCreateNode
    567  *
    568  * PARAMETERS:  WalkState       - Current walk state
    569  *              Node            - NS Node to be initialized
    570  *              Op              - Parser object to be translated
    571  *
    572  * RETURN:      Status
    573  *
    574  * DESCRIPTION: Create the object to be associated with a namespace node
    575  *
    576  ******************************************************************************/
    577 
    578 ACPI_STATUS
    579 AcpiDsCreateNode (
    580     ACPI_WALK_STATE         *WalkState,
    581     ACPI_NAMESPACE_NODE     *Node,
    582     ACPI_PARSE_OBJECT       *Op)
    583 {
    584     ACPI_STATUS             Status;
    585     ACPI_OPERAND_OBJECT     *ObjDesc;
    586 
    587 
    588     ACPI_FUNCTION_TRACE_PTR (DsCreateNode, Op);
    589 
    590 
    591     /*
    592      * Because of the execution pass through the non-control-method
    593      * parts of the table, we can arrive here twice. Only init
    594      * the named object node the first time through
    595      */
    596     if (AcpiNsGetAttachedObject (Node))
    597     {
    598         return_ACPI_STATUS (AE_OK);
    599     }
    600 
    601     if (!Op->Common.Value.Arg)
    602     {
    603         /* No arguments, there is nothing to do */
    604 
    605         return_ACPI_STATUS (AE_OK);
    606     }
    607 
    608     /* Build an internal object for the argument(s) */
    609 
    610     Status = AcpiDsBuildInternalObject (WalkState, Op->Common.Value.Arg,
    611                 &ObjDesc);
    612     if (ACPI_FAILURE (Status))
    613     {
    614         return_ACPI_STATUS (Status);
    615     }
    616 
    617     /* Re-type the object according to its argument */
    618 
    619     Node->Type = ObjDesc->Common.Type;
    620 
    621     /* Attach obj to node */
    622 
    623     Status = AcpiNsAttachObject (Node, ObjDesc, Node->Type);
    624 
    625     /* Remove local reference to the object */
    626 
    627     AcpiUtRemoveReference (ObjDesc);
    628     return_ACPI_STATUS (Status);
    629 }
    630 
    631 #endif /* ACPI_NO_METHOD_EXECUTION */
    632 
    633 
    634 /*******************************************************************************
    635  *
    636  * FUNCTION:    AcpiDsInitObjectFromOp
    637  *
    638  * PARAMETERS:  WalkState       - Current walk state
    639  *              Op              - Parser op used to init the internal object
    640  *              Opcode          - AML opcode associated with the object
    641  *              RetObjDesc      - Namespace object to be initialized
    642  *
    643  * RETURN:      Status
    644  *
    645  * DESCRIPTION: Initialize a namespace object from a parser Op and its
    646  *              associated arguments. The namespace object is a more compact
    647  *              representation of the Op and its arguments.
    648  *
    649  ******************************************************************************/
    650 
    651 ACPI_STATUS
    652 AcpiDsInitObjectFromOp (
    653     ACPI_WALK_STATE         *WalkState,
    654     ACPI_PARSE_OBJECT       *Op,
    655     UINT16                  Opcode,
    656     ACPI_OPERAND_OBJECT     **RetObjDesc)
    657 {
    658     const ACPI_OPCODE_INFO  *OpInfo;
    659     ACPI_OPERAND_OBJECT     *ObjDesc;
    660     ACPI_STATUS             Status = AE_OK;
    661 
    662 
    663     ACPI_FUNCTION_TRACE (DsInitObjectFromOp);
    664 
    665 
    666     ObjDesc = *RetObjDesc;
    667     OpInfo = AcpiPsGetOpcodeInfo (Opcode);
    668     if (OpInfo->Class == AML_CLASS_UNKNOWN)
    669     {
    670         /* Unknown opcode */
    671 
    672         return_ACPI_STATUS (AE_TYPE);
    673     }
    674 
    675     /* Perform per-object initialization */
    676 
    677     switch (ObjDesc->Common.Type)
    678     {
    679     case ACPI_TYPE_BUFFER:
    680         /*
    681          * Defer evaluation of Buffer TermArg operand
    682          */
    683         ObjDesc->Buffer.Node      = ACPI_CAST_PTR (ACPI_NAMESPACE_NODE,
    684                                         WalkState->Operands[0]);
    685         ObjDesc->Buffer.AmlStart  = Op->Named.Data;
    686         ObjDesc->Buffer.AmlLength = Op->Named.Length;
    687         break;
    688 
    689     case ACPI_TYPE_PACKAGE:
    690         /*
    691          * Defer evaluation of Package TermArg operand
    692          */
    693         ObjDesc->Package.Node      = ACPI_CAST_PTR (ACPI_NAMESPACE_NODE,
    694                                         WalkState->Operands[0]);
    695         ObjDesc->Package.AmlStart  = Op->Named.Data;
    696         ObjDesc->Package.AmlLength = Op->Named.Length;
    697         break;
    698 
    699     case ACPI_TYPE_INTEGER:
    700 
    701         switch (OpInfo->Type)
    702         {
    703         case AML_TYPE_CONSTANT:
    704             /*
    705              * Resolve AML Constants here - AND ONLY HERE!
    706              * All constants are integers.
    707              * We mark the integer with a flag that indicates that it started
    708              * life as a constant -- so that stores to constants will perform
    709              * as expected (noop). ZeroOp is used as a placeholder for optional
    710              * target operands.
    711              */
    712             ObjDesc->Common.Flags = AOPOBJ_AML_CONSTANT;
    713 
    714             switch (Opcode)
    715             {
    716             case AML_ZERO_OP:
    717 
    718                 ObjDesc->Integer.Value = 0;
    719                 break;
    720 
    721             case AML_ONE_OP:
    722 
    723                 ObjDesc->Integer.Value = 1;
    724                 break;
    725 
    726             case AML_ONES_OP:
    727 
    728                 ObjDesc->Integer.Value = ACPI_UINT64_MAX;
    729 
    730                 /* Truncate value if we are executing from a 32-bit ACPI table */
    731 
    732 #ifndef ACPI_NO_METHOD_EXECUTION
    733                 (void) AcpiExTruncateFor32bitTable (ObjDesc);
    734 #endif
    735                 break;
    736 
    737             case AML_REVISION_OP:
    738 
    739                 ObjDesc->Integer.Value = ACPI_CA_VERSION;
    740                 break;
    741 
    742             default:
    743 
    744                 ACPI_ERROR ((AE_INFO,
    745                     "Unknown constant opcode 0x%X", Opcode));
    746                 Status = AE_AML_OPERAND_TYPE;
    747                 break;
    748             }
    749             break;
    750 
    751         case AML_TYPE_LITERAL:
    752 
    753             ObjDesc->Integer.Value = Op->Common.Value.Integer;
    754 
    755 #ifndef ACPI_NO_METHOD_EXECUTION
    756             if (AcpiExTruncateFor32bitTable (ObjDesc))
    757             {
    758                 /* Warn if we found a 64-bit constant in a 32-bit table */
    759 
    760                 ACPI_WARNING ((AE_INFO,
    761                     "Truncated 64-bit constant found in 32-bit table: %8.8X%8.8X => %8.8X",
    762                     ACPI_FORMAT_UINT64 (Op->Common.Value.Integer),
    763                     (UINT32) ObjDesc->Integer.Value));
    764             }
    765 #endif
    766             break;
    767 
    768         default:
    769 
    770             ACPI_ERROR ((AE_INFO, "Unknown Integer type 0x%X",
    771                 OpInfo->Type));
    772             Status = AE_AML_OPERAND_TYPE;
    773             break;
    774         }
    775         break;
    776 
    777     case ACPI_TYPE_STRING:
    778 
    779         ObjDesc->String.Pointer = Op->Common.Value.String;
    780         ObjDesc->String.Length = (UINT32) ACPI_STRLEN (Op->Common.Value.String);
    781 
    782         /*
    783          * The string is contained in the ACPI table, don't ever try
    784          * to delete it
    785          */
    786         ObjDesc->Common.Flags |= AOPOBJ_STATIC_POINTER;
    787         break;
    788 
    789     case ACPI_TYPE_METHOD:
    790         break;
    791 
    792     case ACPI_TYPE_LOCAL_REFERENCE:
    793 
    794         switch (OpInfo->Type)
    795         {
    796         case AML_TYPE_LOCAL_VARIABLE:
    797 
    798             /* Local ID (0-7) is (AML opcode - base AML_LOCAL_OP) */
    799 
    800             ObjDesc->Reference.Value = ((UINT32) Opcode) - AML_LOCAL_OP;
    801             ObjDesc->Reference.Class = ACPI_REFCLASS_LOCAL;
    802 
    803 #ifndef ACPI_NO_METHOD_EXECUTION
    804             Status = AcpiDsMethodDataGetNode (ACPI_REFCLASS_LOCAL,
    805                         ObjDesc->Reference.Value, WalkState,
    806                         ACPI_CAST_INDIRECT_PTR (ACPI_NAMESPACE_NODE,
    807                             &ObjDesc->Reference.Object));
    808 #endif
    809             break;
    810 
    811         case AML_TYPE_METHOD_ARGUMENT:
    812 
    813             /* Arg ID (0-6) is (AML opcode - base AML_ARG_OP) */
    814 
    815             ObjDesc->Reference.Value = ((UINT32) Opcode) - AML_ARG_OP;
    816             ObjDesc->Reference.Class = ACPI_REFCLASS_ARG;
    817 
    818 #ifndef ACPI_NO_METHOD_EXECUTION
    819             Status = AcpiDsMethodDataGetNode (ACPI_REFCLASS_ARG,
    820                         ObjDesc->Reference.Value, WalkState,
    821                         ACPI_CAST_INDIRECT_PTR (ACPI_NAMESPACE_NODE,
    822                             &ObjDesc->Reference.Object));
    823 #endif
    824             break;
    825 
    826         default: /* Object name or Debug object */
    827 
    828             switch (Op->Common.AmlOpcode)
    829             {
    830             case AML_INT_NAMEPATH_OP:
    831 
    832                 /* Node was saved in Op */
    833 
    834                 ObjDesc->Reference.Node = Op->Common.Node;
    835                 ObjDesc->Reference.Object = Op->Common.Node->Object;
    836                 ObjDesc->Reference.Class = ACPI_REFCLASS_NAME;
    837                 break;
    838 
    839             case AML_DEBUG_OP:
    840 
    841                 ObjDesc->Reference.Class = ACPI_REFCLASS_DEBUG;
    842                 break;
    843 
    844             default:
    845 
    846                 ACPI_ERROR ((AE_INFO,
    847                     "Unimplemented reference type for AML opcode: 0x%4.4X", Opcode));
    848                 return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
    849             }
    850             break;
    851         }
    852         break;
    853 
    854     default:
    855 
    856         ACPI_ERROR ((AE_INFO, "Unimplemented data type: 0x%X",
    857             ObjDesc->Common.Type));
    858 
    859         Status = AE_AML_OPERAND_TYPE;
    860         break;
    861     }
    862 
    863     return_ACPI_STATUS (Status);
    864 }
    865