exresolv.c revision 241973
167754Smsmith/******************************************************************************
267754Smsmith *
377424Smsmith * Module Name: exresolv - AML Interpreter object resolution
467754Smsmith *
567754Smsmith *****************************************************************************/
667754Smsmith
7217365Sjkim/*
8229989Sjkim * Copyright (C) 2000 - 2012, Intel Corp.
970243Smsmith * All rights reserved.
1067754Smsmith *
11217365Sjkim * Redistribution and use in source and binary forms, with or without
12217365Sjkim * modification, are permitted provided that the following conditions
13217365Sjkim * are met:
14217365Sjkim * 1. Redistributions of source code must retain the above copyright
15217365Sjkim *    notice, this list of conditions, and the following disclaimer,
16217365Sjkim *    without modification.
17217365Sjkim * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18217365Sjkim *    substantially similar to the "NO WARRANTY" disclaimer below
19217365Sjkim *    ("Disclaimer") and any redistribution must be conditioned upon
20217365Sjkim *    including a substantially similar Disclaimer requirement for further
21217365Sjkim *    binary redistribution.
22217365Sjkim * 3. Neither the names of the above-listed copyright holders nor the names
23217365Sjkim *    of any contributors may be used to endorse or promote products derived
24217365Sjkim *    from this software without specific prior written permission.
2567754Smsmith *
26217365Sjkim * Alternatively, this software may be distributed under the terms of the
27217365Sjkim * GNU General Public License ("GPL") version 2 as published by the Free
28217365Sjkim * Software Foundation.
2967754Smsmith *
30217365Sjkim * NO WARRANTY
31217365Sjkim * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32217365Sjkim * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
33217365Sjkim * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
34217365Sjkim * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35217365Sjkim * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36217365Sjkim * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37217365Sjkim * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38217365Sjkim * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39217365Sjkim * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40217365Sjkim * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41217365Sjkim * POSSIBILITY OF SUCH DAMAGES.
42217365Sjkim */
4367754Smsmith
4477424Smsmith#define __EXRESOLV_C__
4567754Smsmith
46193341Sjkim#include <contrib/dev/acpica/include/acpi.h>
47193341Sjkim#include <contrib/dev/acpica/include/accommon.h>
48193341Sjkim#include <contrib/dev/acpica/include/amlcode.h>
49193341Sjkim#include <contrib/dev/acpica/include/acdispat.h>
50193341Sjkim#include <contrib/dev/acpica/include/acinterp.h>
51193341Sjkim#include <contrib/dev/acpica/include/acnamesp.h>
5267754Smsmith
5367754Smsmith
5477424Smsmith#define _COMPONENT          ACPI_EXECUTER
5591116Smsmith        ACPI_MODULE_NAME    ("exresolv")
5667754Smsmith
57151937Sjkim/* Local prototypes */
5867754Smsmith
59151937Sjkimstatic ACPI_STATUS
60151937SjkimAcpiExResolveObjectToValue (
61151937Sjkim    ACPI_OPERAND_OBJECT     **StackPtr,
62151937Sjkim    ACPI_WALK_STATE         *WalkState);
63151937Sjkim
64151937Sjkim
6567754Smsmith/*******************************************************************************
6667754Smsmith *
6777424Smsmith * FUNCTION:    AcpiExResolveToValue
6867754Smsmith *
6967754Smsmith * PARAMETERS:  **StackPtr          - Points to entry on ObjStack, which can
7077424Smsmith *                                    be either an (ACPI_OPERAND_OBJECT *)
7167754Smsmith *                                    or an ACPI_HANDLE.
7277424Smsmith *              WalkState           - Current method state
7367754Smsmith *
7467754Smsmith * RETURN:      Status
7567754Smsmith *
7671867Smsmith * DESCRIPTION: Convert Reference objects to values
7767754Smsmith *
7867754Smsmith ******************************************************************************/
7967754Smsmith
8067754SmsmithACPI_STATUS
8177424SmsmithAcpiExResolveToValue (
8267754Smsmith    ACPI_OPERAND_OBJECT     **StackPtr,
8367754Smsmith    ACPI_WALK_STATE         *WalkState)
8467754Smsmith{
8577424Smsmith    ACPI_STATUS             Status;
8667754Smsmith
8767754Smsmith
88167802Sjkim    ACPI_FUNCTION_TRACE_PTR (ExResolveToValue, StackPtr);
8967754Smsmith
9067754Smsmith
9167754Smsmith    if (!StackPtr || !*StackPtr)
9267754Smsmith    {
93167802Sjkim        ACPI_ERROR ((AE_INFO, "Internal - null pointer"));
9467754Smsmith        return_ACPI_STATUS (AE_AML_NO_OPERAND);
9567754Smsmith    }
9667754Smsmith
9767754Smsmith    /*
9867754Smsmith     * The entity pointed to by the StackPtr can be either
9967754Smsmith     * 1) A valid ACPI_OPERAND_OBJECT, or
10067754Smsmith     * 2) A ACPI_NAMESPACE_NODE (NamedObj)
10167754Smsmith     */
10299679Siwasaki    if (ACPI_GET_DESCRIPTOR_TYPE (*StackPtr) == ACPI_DESC_TYPE_OPERAND)
10367754Smsmith    {
10477424Smsmith        Status = AcpiExResolveObjectToValue (StackPtr, WalkState);
10567754Smsmith        if (ACPI_FAILURE (Status))
10667754Smsmith        {
10767754Smsmith            return_ACPI_STATUS (Status);
10867754Smsmith        }
109151937Sjkim
110151937Sjkim        if (!*StackPtr)
111151937Sjkim        {
112167802Sjkim            ACPI_ERROR ((AE_INFO, "Internal - null pointer"));
113151937Sjkim            return_ACPI_STATUS (AE_AML_NO_OPERAND);
114151937Sjkim        }
11567754Smsmith    }
11667754Smsmith
11767754Smsmith    /*
11877424Smsmith     * Object on the stack may have changed if AcpiExResolveObjectToValue()
11967754Smsmith     * was called (i.e., we can't use an _else_ here.)
12067754Smsmith     */
12191116Smsmith    if (ACPI_GET_DESCRIPTOR_TYPE (*StackPtr) == ACPI_DESC_TYPE_NAMED)
12267754Smsmith    {
12399679Siwasaki        Status = AcpiExResolveNodeToValue (
12499679Siwasaki                        ACPI_CAST_INDIRECT_PTR (ACPI_NAMESPACE_NODE, StackPtr),
12577424Smsmith                        WalkState);
12677424Smsmith        if (ACPI_FAILURE (Status))
12777424Smsmith        {
12877424Smsmith            return_ACPI_STATUS (Status);
12977424Smsmith        }
13067754Smsmith    }
13167754Smsmith
13299146Siwasaki    ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Resolved object %p\n", *StackPtr));
13377424Smsmith    return_ACPI_STATUS (AE_OK);
13467754Smsmith}
13567754Smsmith
13667754Smsmith
13767754Smsmith/*******************************************************************************
13867754Smsmith *
13977424Smsmith * FUNCTION:    AcpiExResolveObjectToValue
14067754Smsmith *
141151937Sjkim * PARAMETERS:  StackPtr        - Pointer to an internal object
14277424Smsmith *              WalkState       - Current method state
14367754Smsmith *
14467754Smsmith * RETURN:      Status
14567754Smsmith *
146151937Sjkim * DESCRIPTION: Retrieve the value from an internal object. The Reference type
14767754Smsmith *              uses the associated AML opcode to determine the value.
14867754Smsmith *
14967754Smsmith ******************************************************************************/
15067754Smsmith
151151937Sjkimstatic ACPI_STATUS
15277424SmsmithAcpiExResolveObjectToValue (
15367754Smsmith    ACPI_OPERAND_OBJECT     **StackPtr,
15467754Smsmith    ACPI_WALK_STATE         *WalkState)
15567754Smsmith{
15677424Smsmith    ACPI_STATUS             Status = AE_OK;
15767754Smsmith    ACPI_OPERAND_OBJECT     *StackDesc;
158167802Sjkim    ACPI_OPERAND_OBJECT     *ObjDesc = NULL;
159193267Sjkim    UINT8                   RefType;
16067754Smsmith
16167754Smsmith
162167802Sjkim    ACPI_FUNCTION_TRACE (ExResolveObjectToValue);
16367754Smsmith
16467754Smsmith
16567754Smsmith    StackDesc = *StackPtr;
16667754Smsmith
167238381Sjkim    /* This is an object of type ACPI_OPERAND_OBJECT */
16867754Smsmith
169193267Sjkim    switch (StackDesc->Common.Type)
17067754Smsmith    {
171107325Siwasaki    case ACPI_TYPE_LOCAL_REFERENCE:
17267754Smsmith
173193267Sjkim        RefType = StackDesc->Reference.Class;
17467754Smsmith
175193267Sjkim        switch (RefType)
17667754Smsmith        {
177193267Sjkim        case ACPI_REFCLASS_LOCAL:
178193267Sjkim        case ACPI_REFCLASS_ARG:
17967754Smsmith
18067754Smsmith            /*
18167754Smsmith             * Get the local from the method's state info
18267754Smsmith             * Note: this increments the local's object reference count
18367754Smsmith             */
184193267Sjkim            Status = AcpiDsMethodDataGetValue (RefType,
185193267Sjkim                            StackDesc->Reference.Value, WalkState, &ObjDesc);
18667754Smsmith            if (ACPI_FAILURE (Status))
18767754Smsmith            {
18867754Smsmith                return_ACPI_STATUS (Status);
18967754Smsmith            }
19067754Smsmith
191129684Snjl            ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "[Arg/Local %X] ValueObj is %p\n",
192193267Sjkim                StackDesc->Reference.Value, ObjDesc));
193129684Snjl
19467754Smsmith            /*
19567754Smsmith             * Now we can delete the original Reference Object and
196129684Snjl             * replace it with the resolved value
19767754Smsmith             */
19877424Smsmith            AcpiUtRemoveReference (StackDesc);
19967754Smsmith            *StackPtr = ObjDesc;
20067754Smsmith            break;
20167754Smsmith
20267754Smsmith
203193267Sjkim        case ACPI_REFCLASS_INDEX:
20467754Smsmith
20567754Smsmith            switch (StackDesc->Reference.TargetType)
20667754Smsmith            {
20767754Smsmith            case ACPI_TYPE_BUFFER_FIELD:
20867754Smsmith
209193267Sjkim                /* Just return - do not dereference */
21067754Smsmith                break;
21167754Smsmith
21267754Smsmith
21367754Smsmith            case ACPI_TYPE_PACKAGE:
21499679Siwasaki
215193267Sjkim                /* If method call or CopyObject - do not dereference */
216193267Sjkim
217193267Sjkim                if ((WalkState->Opcode == AML_INT_METHODCALL_OP) ||
218193267Sjkim                    (WalkState->Opcode == AML_COPY_OP))
219193267Sjkim                {
220193267Sjkim                    break;
221193267Sjkim                }
222193267Sjkim
223193267Sjkim                /* Otherwise, dereference the PackageIndex to a package element */
224193267Sjkim
22567754Smsmith                ObjDesc = *StackDesc->Reference.Where;
22667754Smsmith                if (ObjDesc)
22767754Smsmith                {
22867754Smsmith                    /*
229193267Sjkim                     * Valid object descriptor, copy pointer to return value
23067754Smsmith                     * (i.e., dereference the package index)
23167754Smsmith                     * Delete the ref object, increment the returned object
23267754Smsmith                     */
23377424Smsmith                    AcpiUtRemoveReference (StackDesc);
23477424Smsmith                    AcpiUtAddReference (ObjDesc);
23567754Smsmith                    *StackPtr = ObjDesc;
23667754Smsmith                }
23767754Smsmith                else
23867754Smsmith                {
23967754Smsmith                    /*
240193267Sjkim                     * A NULL object descriptor means an uninitialized element of
24177424Smsmith                     * the package, can't dereference it
24267754Smsmith                     */
243167802Sjkim                    ACPI_ERROR ((AE_INFO,
244193267Sjkim                        "Attempt to dereference an Index to NULL package element Idx=%p",
24577424Smsmith                        StackDesc));
24667754Smsmith                    Status = AE_AML_UNINITIALIZED_ELEMENT;
24767754Smsmith                }
24867754Smsmith                break;
24967754Smsmith
25099679Siwasaki
25167754Smsmith            default:
25299679Siwasaki
25377424Smsmith                /* Invalid reference object */
25467754Smsmith
255167802Sjkim                ACPI_ERROR ((AE_INFO,
256204773Sjkim                    "Unknown TargetType 0x%X in Index/Reference object %p",
25767754Smsmith                    StackDesc->Reference.TargetType, StackDesc));
25867754Smsmith                Status = AE_AML_INTERNAL;
25967754Smsmith                break;
26067754Smsmith            }
26167754Smsmith            break;
26267754Smsmith
26367754Smsmith
264193267Sjkim        case ACPI_REFCLASS_REFOF:
265193267Sjkim        case ACPI_REFCLASS_DEBUG:
266193267Sjkim        case ACPI_REFCLASS_TABLE:
26767754Smsmith
268193267Sjkim            /* Just leave the object as-is, do not dereference */
269100966Siwasaki
27067754Smsmith            break;
27167754Smsmith
272193267Sjkim        case ACPI_REFCLASS_NAME:   /* Reference to a named object */
27367754Smsmith
274167802Sjkim            /* Dereference the name */
275151937Sjkim
276167802Sjkim            if ((StackDesc->Reference.Node->Type == ACPI_TYPE_DEVICE) ||
277167802Sjkim                (StackDesc->Reference.Node->Type == ACPI_TYPE_THERMAL))
278167802Sjkim            {
279167802Sjkim                /* These node types do not have 'real' subobjects */
280167802Sjkim
281167802Sjkim                *StackPtr = (void *) StackDesc->Reference.Node;
282167802Sjkim            }
283167802Sjkim            else
284167802Sjkim            {
285167802Sjkim                /* Get the object pointed to by the namespace node */
286167802Sjkim
287167802Sjkim                *StackPtr = (StackDesc->Reference.Node)->Object;
288167802Sjkim                AcpiUtAddReference (*StackPtr);
289167802Sjkim            }
290167802Sjkim
291151937Sjkim            AcpiUtRemoveReference (StackDesc);
292151937Sjkim            break;
293151937Sjkim
29467754Smsmith        default:
29567754Smsmith
296167802Sjkim            ACPI_ERROR ((AE_INFO,
297204773Sjkim                "Unknown Reference type 0x%X in %p", RefType, StackDesc));
29867754Smsmith            Status = AE_AML_INTERNAL;
29977424Smsmith            break;
30099679Siwasaki        }
30199679Siwasaki        break;
30267754Smsmith
30367754Smsmith
30499146Siwasaki    case ACPI_TYPE_BUFFER:
30599146Siwasaki
30699146Siwasaki        Status = AcpiDsGetBufferArguments (StackDesc);
30799146Siwasaki        break;
30899146Siwasaki
30999146Siwasaki
31099146Siwasaki    case ACPI_TYPE_PACKAGE:
31199146Siwasaki
31299146Siwasaki        Status = AcpiDsGetPackageArguments (StackDesc);
31399146Siwasaki        break;
31499146Siwasaki
31599146Siwasaki
31677424Smsmith    case ACPI_TYPE_BUFFER_FIELD:
317107325Siwasaki    case ACPI_TYPE_LOCAL_REGION_FIELD:
318107325Siwasaki    case ACPI_TYPE_LOCAL_BANK_FIELD:
319107325Siwasaki    case ACPI_TYPE_LOCAL_INDEX_FIELD:
32067754Smsmith
32187031Smsmith        ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "FieldRead SourceDesc=%p Type=%X\n",
322193267Sjkim            StackDesc, StackDesc->Common.Type));
32367754Smsmith
32499146Siwasaki        Status = AcpiExReadDataFromField (WalkState, StackDesc, &ObjDesc);
325167802Sjkim
326167802Sjkim        /* Remove a reference to the original operand, then override */
327167802Sjkim
328167802Sjkim        AcpiUtRemoveReference (*StackPtr);
32967754Smsmith        *StackPtr = (void *) ObjDesc;
33067754Smsmith        break;
33167754Smsmith
33267754Smsmith    default:
33367754Smsmith        break;
33487031Smsmith    }
33567754Smsmith
33667754Smsmith    return_ACPI_STATUS (Status);
33767754Smsmith}
33867754Smsmith
33967754Smsmith
340104470Siwasaki/*******************************************************************************
341104470Siwasaki *
342104470Siwasaki * FUNCTION:    AcpiExResolveMultiple
343104470Siwasaki *
344104470Siwasaki * PARAMETERS:  WalkState           - Current state (contains AML opcode)
345104470Siwasaki *              Operand             - Starting point for resolution
346104470Siwasaki *              ReturnType          - Where the object type is returned
347104470Siwasaki *              ReturnDesc          - Where the resolved object is returned
348104470Siwasaki *
349104470Siwasaki * RETURN:      Status
350104470Siwasaki *
351241973Sjkim * DESCRIPTION: Return the base object and type. Traverse a reference list if
352104470Siwasaki *              necessary to get to the base object.
353104470Siwasaki *
354104470Siwasaki ******************************************************************************/
355104470Siwasaki
356104470SiwasakiACPI_STATUS
357104470SiwasakiAcpiExResolveMultiple (
358104470Siwasaki    ACPI_WALK_STATE         *WalkState,
359104470Siwasaki    ACPI_OPERAND_OBJECT     *Operand,
360104470Siwasaki    ACPI_OBJECT_TYPE        *ReturnType,
361104470Siwasaki    ACPI_OPERAND_OBJECT     **ReturnDesc)
362104470Siwasaki{
363104470Siwasaki    ACPI_OPERAND_OBJECT     *ObjDesc = (void *) Operand;
364104470Siwasaki    ACPI_NAMESPACE_NODE     *Node;
365104470Siwasaki    ACPI_OBJECT_TYPE        Type;
366138287Smarks    ACPI_STATUS             Status;
367104470Siwasaki
368104470Siwasaki
369167802Sjkim    ACPI_FUNCTION_TRACE (AcpiExResolveMultiple);
370104470Siwasaki
371104470Siwasaki
372151937Sjkim    /* Operand can be either a namespace node or an operand descriptor */
373138287Smarks
374138287Smarks    switch (ACPI_GET_DESCRIPTOR_TYPE (ObjDesc))
375138287Smarks    {
376138287Smarks    case ACPI_DESC_TYPE_OPERAND:
377138287Smarks        Type = ObjDesc->Common.Type;
378138287Smarks        break;
379138287Smarks
380138287Smarks    case ACPI_DESC_TYPE_NAMED:
381138287Smarks        Type = ((ACPI_NAMESPACE_NODE *) ObjDesc)->Type;
382138287Smarks        ObjDesc = AcpiNsGetAttachedObject ((ACPI_NAMESPACE_NODE *) ObjDesc);
383138287Smarks
384138287Smarks        /* If we had an Alias node, use the attached object for type info */
385138287Smarks
386138287Smarks        if (Type == ACPI_TYPE_LOCAL_ALIAS)
387138287Smarks        {
388138287Smarks            Type = ((ACPI_NAMESPACE_NODE *) ObjDesc)->Type;
389138287Smarks            ObjDesc = AcpiNsGetAttachedObject ((ACPI_NAMESPACE_NODE *) ObjDesc);
390138287Smarks        }
391138287Smarks        break;
392138287Smarks
393138287Smarks    default:
394138287Smarks        return_ACPI_STATUS (AE_AML_OPERAND_TYPE);
395138287Smarks    }
396138287Smarks
397151937Sjkim    /* If type is anything other than a reference, we are done */
398138287Smarks
399138287Smarks    if (Type != ACPI_TYPE_LOCAL_REFERENCE)
400138287Smarks    {
401138287Smarks        goto Exit;
402138287Smarks    }
403138287Smarks
404138287Smarks    /*
405193267Sjkim     * For reference objects created via the RefOf, Index, or Load/LoadTable
406193267Sjkim     * operators, we need to get to the base object (as per the ACPI
407193267Sjkim     * specification of the ObjectType and SizeOf operators). This means
408193267Sjkim     * traversing the list of possibly many nested references.
409104470Siwasaki     */
410193267Sjkim    while (ObjDesc->Common.Type == ACPI_TYPE_LOCAL_REFERENCE)
411104470Siwasaki    {
412193267Sjkim        switch (ObjDesc->Reference.Class)
413104470Siwasaki        {
414193267Sjkim        case ACPI_REFCLASS_REFOF:
415193267Sjkim        case ACPI_REFCLASS_NAME:
416104470Siwasaki
417104470Siwasaki            /* Dereference the reference pointer */
418104470Siwasaki
419193267Sjkim            if (ObjDesc->Reference.Class == ACPI_REFCLASS_REFOF)
420167802Sjkim            {
421167802Sjkim                Node = ObjDesc->Reference.Object;
422167802Sjkim            }
423167802Sjkim            else /* AML_INT_NAMEPATH_OP */
424167802Sjkim            {
425167802Sjkim                Node = ObjDesc->Reference.Node;
426167802Sjkim            }
427104470Siwasaki
428104470Siwasaki            /* All "References" point to a NS node */
429104470Siwasaki
430104470Siwasaki            if (ACPI_GET_DESCRIPTOR_TYPE (Node) != ACPI_DESC_TYPE_NAMED)
431104470Siwasaki            {
432167802Sjkim                ACPI_ERROR ((AE_INFO,
433204773Sjkim                    "Not a namespace node %p [%s]",
434151937Sjkim                    Node, AcpiUtGetDescriptorName (Node)));
435104470Siwasaki                return_ACPI_STATUS (AE_AML_INTERNAL);
436104470Siwasaki            }
437104470Siwasaki
438104470Siwasaki            /* Get the attached object */
439104470Siwasaki
440104470Siwasaki            ObjDesc = AcpiNsGetAttachedObject (Node);
441104470Siwasaki            if (!ObjDesc)
442104470Siwasaki            {
443104470Siwasaki                /* No object, use the NS node type */
444104470Siwasaki
445104470Siwasaki                Type = AcpiNsGetType (Node);
446104470Siwasaki                goto Exit;
447104470Siwasaki            }
448104470Siwasaki
449104470Siwasaki            /* Check for circular references */
450104470Siwasaki
451104470Siwasaki            if (ObjDesc == Operand)
452104470Siwasaki            {
453104470Siwasaki                return_ACPI_STATUS (AE_AML_CIRCULAR_REFERENCE);
454104470Siwasaki            }
455104470Siwasaki            break;
456104470Siwasaki
457104470Siwasaki
458193267Sjkim        case ACPI_REFCLASS_INDEX:
459104470Siwasaki
460104470Siwasaki            /* Get the type of this reference (index into another object) */
461104470Siwasaki
462104470Siwasaki            Type = ObjDesc->Reference.TargetType;
463104470Siwasaki            if (Type != ACPI_TYPE_PACKAGE)
464104470Siwasaki            {
465104470Siwasaki                goto Exit;
466104470Siwasaki            }
467104470Siwasaki
468104470Siwasaki            /*
469104470Siwasaki             * The main object is a package, we want to get the type
470104470Siwasaki             * of the individual package element that is referenced by
471104470Siwasaki             * the index.
472104470Siwasaki             *
473104470Siwasaki             * This could of course in turn be another reference object.
474104470Siwasaki             */
475104470Siwasaki            ObjDesc = *(ObjDesc->Reference.Where);
476151937Sjkim            if (!ObjDesc)
477151937Sjkim            {
478151937Sjkim                /* NULL package elements are allowed */
479151937Sjkim
480151937Sjkim                Type = 0; /* Uninitialized */
481151937Sjkim                goto Exit;
482151937Sjkim            }
483104470Siwasaki            break;
484104470Siwasaki
485104470Siwasaki
486193267Sjkim        case ACPI_REFCLASS_TABLE:
487138287Smarks
488193267Sjkim            Type = ACPI_TYPE_DDB_HANDLE;
489193267Sjkim            goto Exit;
490193267Sjkim
491193267Sjkim
492193267Sjkim        case ACPI_REFCLASS_LOCAL:
493193267Sjkim        case ACPI_REFCLASS_ARG:
494193267Sjkim
495138287Smarks            if (ReturnDesc)
496138287Smarks            {
497193267Sjkim                Status = AcpiDsMethodDataGetValue (ObjDesc->Reference.Class,
498193267Sjkim                            ObjDesc->Reference.Value, WalkState, &ObjDesc);
499138287Smarks                if (ACPI_FAILURE (Status))
500138287Smarks                {
501138287Smarks                    return_ACPI_STATUS (Status);
502138287Smarks                }
503138287Smarks                AcpiUtRemoveReference (ObjDesc);
504138287Smarks            }
505138287Smarks            else
506138287Smarks            {
507193267Sjkim                Status = AcpiDsMethodDataGetNode (ObjDesc->Reference.Class,
508193267Sjkim                            ObjDesc->Reference.Value, WalkState, &Node);
509138287Smarks                if (ACPI_FAILURE (Status))
510138287Smarks                {
511138287Smarks                    return_ACPI_STATUS (Status);
512138287Smarks                }
513138287Smarks
514138287Smarks                ObjDesc = AcpiNsGetAttachedObject (Node);
515138287Smarks                if (!ObjDesc)
516138287Smarks                {
517138287Smarks                    Type = ACPI_TYPE_ANY;
518138287Smarks                    goto Exit;
519138287Smarks                }
520138287Smarks            }
521138287Smarks            break;
522138287Smarks
523138287Smarks
524193267Sjkim        case ACPI_REFCLASS_DEBUG:
525104470Siwasaki
526104470Siwasaki            /* The Debug Object is of type "DebugObject" */
527104470Siwasaki
528104470Siwasaki            Type = ACPI_TYPE_DEBUG_OBJECT;
529104470Siwasaki            goto Exit;
530104470Siwasaki
531104470Siwasaki
532104470Siwasaki        default:
533104470Siwasaki
534167802Sjkim            ACPI_ERROR ((AE_INFO,
535204773Sjkim                "Unknown Reference Class 0x%2.2X", ObjDesc->Reference.Class));
536104470Siwasaki            return_ACPI_STATUS (AE_AML_INTERNAL);
537104470Siwasaki        }
538104470Siwasaki    }
539104470Siwasaki
540104470Siwasaki    /*
541104470Siwasaki     * Now we are guaranteed to have an object that has not been created
542104470Siwasaki     * via the RefOf or Index operators.
543104470Siwasaki     */
544193267Sjkim    Type = ObjDesc->Common.Type;
545104470Siwasaki
546104470Siwasaki
547104470SiwasakiExit:
548104470Siwasaki    /* Convert internal types to external types */
549104470Siwasaki
550104470Siwasaki    switch (Type)
551104470Siwasaki    {
552107325Siwasaki    case ACPI_TYPE_LOCAL_REGION_FIELD:
553107325Siwasaki    case ACPI_TYPE_LOCAL_BANK_FIELD:
554107325Siwasaki    case ACPI_TYPE_LOCAL_INDEX_FIELD:
555104470Siwasaki
556104470Siwasaki        Type = ACPI_TYPE_FIELD_UNIT;
557104470Siwasaki        break;
558104470Siwasaki
559107325Siwasaki    case ACPI_TYPE_LOCAL_SCOPE:
560107325Siwasaki
561107325Siwasaki        /* Per ACPI Specification, Scope is untyped */
562107325Siwasaki
563107325Siwasaki        Type = ACPI_TYPE_ANY;
564107325Siwasaki        break;
565107325Siwasaki
566104470Siwasaki    default:
567104470Siwasaki        /* No change to Type required */
568104470Siwasaki        break;
569104470Siwasaki    }
570104470Siwasaki
571104470Siwasaki    *ReturnType = Type;
572104470Siwasaki    if (ReturnDesc)
573104470Siwasaki    {
574104470Siwasaki        *ReturnDesc = ObjDesc;
575104470Siwasaki    }
576104470Siwasaki    return_ACPI_STATUS (AE_OK);
577104470Siwasaki}
578