1100966Siwasaki/*******************************************************************************
2100966Siwasaki *
3100966Siwasaki * Module Name: dmnames - AML disassembler, names, namestrings, pathnames
4100966Siwasaki *
5100966Siwasaki ******************************************************************************/
6100966Siwasaki
7217365Sjkim/*
8217365Sjkim * Copyright (C) 2000 - 2011, Intel Corp.
9100966Siwasaki * All rights reserved.
10100966Siwasaki *
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.
25100966Siwasaki *
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.
29100966Siwasaki *
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 */
43100966Siwasaki
44100966Siwasaki
45193341Sjkim#include <contrib/dev/acpica/include/acpi.h>
46193341Sjkim#include <contrib/dev/acpica/include/accommon.h>
47193341Sjkim#include <contrib/dev/acpica/include/acparser.h>
48193341Sjkim#include <contrib/dev/acpica/include/amlcode.h>
49193341Sjkim#include <contrib/dev/acpica/include/acnamesp.h>
50193341Sjkim#include <contrib/dev/acpica/include/acdisasm.h>
51100966Siwasaki
52100966Siwasaki
53100966Siwasaki#ifdef ACPI_DISASSEMBLER
54100966Siwasaki
55102550Siwasaki#define _COMPONENT          ACPI_CA_DEBUGGER
56100966Siwasaki        ACPI_MODULE_NAME    ("dmnames")
57100966Siwasaki
58151937Sjkim/* Local prototypes */
59100966Siwasaki
60151937Sjkim#ifdef ACPI_OBSOLETE_FUNCTIONS
61100966Siwasakivoid
62151937SjkimAcpiDmDisplayPath (
63151937Sjkim    ACPI_PARSE_OBJECT       *Op);
64100966Siwasaki#endif
65100966Siwasaki
66100966Siwasaki
67100966Siwasaki/*******************************************************************************
68100966Siwasaki *
69100966Siwasaki * FUNCTION:    AcpiDmDumpName
70100966Siwasaki *
71100966Siwasaki * PARAMETERS:  Name            - 4 character ACPI name
72100966Siwasaki *
73100966Siwasaki * RETURN:      Final length of name
74100966Siwasaki *
75100966Siwasaki * DESCRIPTION: Dump an ACPI name, minus any trailing underscores.
76100966Siwasaki *
77100966Siwasaki ******************************************************************************/
78100966Siwasaki
79100966SiwasakiUINT32
80100966SiwasakiAcpiDmDumpName (
81193267Sjkim    UINT32                  Name)
82100966Siwasaki{
83100966Siwasaki    UINT32                  i;
84100966Siwasaki    UINT32                  Length;
85167802Sjkim    char                    NewName[4];
86100966Siwasaki
87100966Siwasaki
88193267Sjkim    /* Copy name locally in case the original name is not writeable */
89193267Sjkim
90193267Sjkim    *ACPI_CAST_PTR (UINT32, &NewName[0]) = Name;
91193267Sjkim
92167802Sjkim    /* Ensure that the name is printable, even if we have to fix it */
93167802Sjkim
94193267Sjkim    AcpiUtRepairName (NewName);
95167802Sjkim
96167802Sjkim    /* Remove all trailing underscores from the name */
97167802Sjkim
98167802Sjkim    Length = ACPI_NAME_SIZE;
99167802Sjkim    for (i = (ACPI_NAME_SIZE - 1); i != 0; i--)
100100966Siwasaki    {
101167802Sjkim        if (NewName[i] == '_')
102100966Siwasaki        {
103167802Sjkim            Length--;
104100966Siwasaki        }
105167802Sjkim        else
106167802Sjkim        {
107167802Sjkim            break;
108167802Sjkim        }
109100966Siwasaki    }
110100966Siwasaki
111167802Sjkim    /* Dump the name, up to the start of the trailing underscores */
112167802Sjkim
113100966Siwasaki    for (i = 0; i < Length; i++)
114100966Siwasaki    {
115167802Sjkim        AcpiOsPrintf ("%c", NewName[i]);
116100966Siwasaki    }
117100966Siwasaki
118100966Siwasaki    return (Length);
119100966Siwasaki}
120100966Siwasaki
121100966Siwasaki
122100966Siwasaki/*******************************************************************************
123100966Siwasaki *
124100966Siwasaki * FUNCTION:    AcpiPsDisplayObjectPathname
125100966Siwasaki *
126100966Siwasaki * PARAMETERS:  WalkState       - Current walk state
127100966Siwasaki *              Op              - Object whose pathname is to be obtained
128100966Siwasaki *
129100966Siwasaki * RETURN:      Status
130100966Siwasaki *
131100966Siwasaki * DESCRIPTION: Diplay the pathname associated with a named object.  Two
132100966Siwasaki *              versions. One searches the parse tree (for parser-only
133100966Siwasaki *              applications suchas AcpiDump), and the other searches the
134100966Siwasaki *              ACPI namespace (the parse tree is probably deleted)
135100966Siwasaki *
136100966Siwasaki ******************************************************************************/
137100966Siwasaki
138100966SiwasakiACPI_STATUS
139100966SiwasakiAcpiPsDisplayObjectPathname (
140100966Siwasaki    ACPI_WALK_STATE         *WalkState,
141100966Siwasaki    ACPI_PARSE_OBJECT       *Op)
142100966Siwasaki{
143100966Siwasaki    ACPI_STATUS             Status;
144100966Siwasaki    ACPI_NAMESPACE_NODE     *Node;
145100966Siwasaki    ACPI_BUFFER             Buffer;
146100966Siwasaki    UINT32                  DebugLevel;
147100966Siwasaki
148100966Siwasaki
149100966Siwasaki    /* Save current debug level so we don't get extraneous debug output */
150100966Siwasaki
151100966Siwasaki    DebugLevel = AcpiDbgLevel;
152100966Siwasaki    AcpiDbgLevel = 0;
153100966Siwasaki
154100966Siwasaki    /* Just get the Node out of the Op object */
155100966Siwasaki
156100966Siwasaki    Node = Op->Common.Node;
157100966Siwasaki    if (!Node)
158100966Siwasaki    {
159100966Siwasaki        /* Node not defined in this scope, look it up */
160100966Siwasaki
161151937Sjkim        Status = AcpiNsLookup (WalkState->ScopeInfo, Op->Common.Value.String,
162151937Sjkim                    ACPI_TYPE_ANY, ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT,
163151937Sjkim                    WalkState, &(Node));
164100966Siwasaki
165100966Siwasaki        if (ACPI_FAILURE (Status))
166100966Siwasaki        {
167100966Siwasaki            /*
168100966Siwasaki             * We can't get the pathname since the object
169100966Siwasaki             * is not in the namespace.  This can happen during single
170100966Siwasaki             * stepping where a dynamic named object is *about* to be created.
171100966Siwasaki             */
172100966Siwasaki            AcpiOsPrintf ("  [Path not found]");
173100966Siwasaki            goto Exit;
174100966Siwasaki        }
175100966Siwasaki
176100966Siwasaki        /* Save it for next time. */
177100966Siwasaki
178100966Siwasaki        Op->Common.Node = Node;
179100966Siwasaki    }
180100966Siwasaki
181100966Siwasaki    /* Convert NamedDesc/handle to a full pathname */
182100966Siwasaki
183100966Siwasaki    Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
184100966Siwasaki    Status = AcpiNsHandleToPathname (Node, &Buffer);
185100966Siwasaki    if (ACPI_FAILURE (Status))
186100966Siwasaki    {
187100966Siwasaki        AcpiOsPrintf ("****Could not get pathname****)");
188100966Siwasaki        goto Exit;
189100966Siwasaki    }
190100966Siwasaki
191100966Siwasaki    AcpiOsPrintf ("  (Path %s)", (char *) Buffer.Pointer);
192167802Sjkim    ACPI_FREE (Buffer.Pointer);
193100966Siwasaki
194100966Siwasaki
195100966SiwasakiExit:
196100966Siwasaki    /* Restore the debug level */
197100966Siwasaki
198100966Siwasaki    AcpiDbgLevel = DebugLevel;
199100966Siwasaki    return (Status);
200100966Siwasaki}
201100966Siwasaki
202100966Siwasaki
203100966Siwasaki/*******************************************************************************
204100966Siwasaki *
205100966Siwasaki * FUNCTION:    AcpiDmNamestring
206100966Siwasaki *
207100966Siwasaki * PARAMETERS:  Name                - ACPI Name string to store
208100966Siwasaki *
209100966Siwasaki * RETURN:      None
210100966Siwasaki *
211151937Sjkim * DESCRIPTION: Decode and dump an ACPI namestring. Handles prefix characters
212100966Siwasaki *
213100966Siwasaki ******************************************************************************/
214100966Siwasaki
215100966Siwasakivoid
216100966SiwasakiAcpiDmNamestring (
217114237Snjl    char                    *Name)
218100966Siwasaki{
219100966Siwasaki    UINT32                  SegCount;
220100966Siwasaki
221100966Siwasaki
222100966Siwasaki    if (!Name)
223100966Siwasaki    {
224100966Siwasaki        return;
225100966Siwasaki    }
226100966Siwasaki
227100966Siwasaki    /* Handle all Scope Prefix operators */
228100966Siwasaki
229100966Siwasaki    while (AcpiPsIsPrefixChar (ACPI_GET8 (Name)))
230100966Siwasaki    {
231100966Siwasaki        /* Append prefix character */
232100966Siwasaki
233100966Siwasaki        AcpiOsPrintf ("%1c", ACPI_GET8 (Name));
234100966Siwasaki        Name++;
235100966Siwasaki    }
236100966Siwasaki
237100966Siwasaki    switch (ACPI_GET8 (Name))
238100966Siwasaki    {
239100966Siwasaki    case 0:
240100966Siwasaki        SegCount = 0;
241100966Siwasaki        break;
242100966Siwasaki
243100966Siwasaki    case AML_DUAL_NAME_PREFIX:
244100966Siwasaki        SegCount = 2;
245100966Siwasaki        Name++;
246100966Siwasaki        break;
247100966Siwasaki
248100966Siwasaki    case AML_MULTI_NAME_PREFIX_OP:
249100966Siwasaki        SegCount = (UINT32) ACPI_GET8 (Name + 1);
250100966Siwasaki        Name += 2;
251100966Siwasaki        break;
252100966Siwasaki
253100966Siwasaki    default:
254100966Siwasaki        SegCount = 1;
255100966Siwasaki        break;
256100966Siwasaki    }
257100966Siwasaki
258100966Siwasaki    while (SegCount)
259100966Siwasaki    {
260100966Siwasaki        /* Append Name segment */
261100966Siwasaki
262193267Sjkim        AcpiDmDumpName (*ACPI_CAST_PTR (UINT32, Name));
263100966Siwasaki
264100966Siwasaki        SegCount--;
265100966Siwasaki        if (SegCount)
266100966Siwasaki        {
267100966Siwasaki            /* Not last name, append dot separator */
268100966Siwasaki
269100966Siwasaki            AcpiOsPrintf (".");
270100966Siwasaki        }
271100966Siwasaki        Name += ACPI_NAME_SIZE;
272100966Siwasaki    }
273100966Siwasaki}
274100966Siwasaki
275100966Siwasaki
276151937Sjkim#ifdef ACPI_OBSOLETE_FUNCTIONS
277100966Siwasaki/*******************************************************************************
278100966Siwasaki *
279100966Siwasaki * FUNCTION:    AcpiDmDisplayPath
280100966Siwasaki *
281100966Siwasaki * PARAMETERS:  Op                  - Named Op whose path is to be constructed
282100966Siwasaki *
283100966Siwasaki * RETURN:      None
284100966Siwasaki *
285100966Siwasaki * DESCRIPTION: Walk backwards from current scope and display the name
286100966Siwasaki *              of each previous level of scope up to the root scope
287100966Siwasaki *              (like "pwd" does with file systems)
288100966Siwasaki *
289100966Siwasaki ******************************************************************************/
290100966Siwasaki
291100966Siwasakivoid
292100966SiwasakiAcpiDmDisplayPath (
293100966Siwasaki    ACPI_PARSE_OBJECT       *Op)
294100966Siwasaki{
295100966Siwasaki    ACPI_PARSE_OBJECT       *Prev;
296100966Siwasaki    ACPI_PARSE_OBJECT       *Search;
297100966Siwasaki    UINT32                  Name;
298100966Siwasaki    BOOLEAN                 DoDot = FALSE;
299100966Siwasaki    ACPI_PARSE_OBJECT       *NamePath;
300100966Siwasaki    const ACPI_OPCODE_INFO  *OpInfo;
301100966Siwasaki
302100966Siwasaki
303100966Siwasaki    /* We are only interested in named objects */
304100966Siwasaki
305100966Siwasaki    OpInfo = AcpiPsGetOpcodeInfo (Op->Common.AmlOpcode);
306100966Siwasaki    if (!(OpInfo->Flags & AML_NSNODE))
307100966Siwasaki    {
308100966Siwasaki        return;
309100966Siwasaki    }
310100966Siwasaki
311100966Siwasaki    if (OpInfo->Flags & AML_CREATE)
312100966Siwasaki    {
313100966Siwasaki        /* Field creation - check for a fully qualified namepath */
314100966Siwasaki
315100966Siwasaki        if (Op->Common.AmlOpcode == AML_CREATE_FIELD_OP)
316100966Siwasaki        {
317100966Siwasaki            NamePath = AcpiPsGetArg (Op, 3);
318100966Siwasaki        }
319100966Siwasaki        else
320100966Siwasaki        {
321100966Siwasaki            NamePath = AcpiPsGetArg (Op, 2);
322100966Siwasaki        }
323100966Siwasaki
324100966Siwasaki        if ((NamePath) &&
325100966Siwasaki            (NamePath->Common.Value.String) &&
326100966Siwasaki            (NamePath->Common.Value.String[0] == '\\'))
327100966Siwasaki        {
328100966Siwasaki            AcpiDmNamestring (NamePath->Common.Value.String);
329100966Siwasaki            return;
330100966Siwasaki        }
331100966Siwasaki    }
332100966Siwasaki
333100966Siwasaki    Prev = NULL;            /* Start with Root Node */
334100966Siwasaki
335100966Siwasaki    while (Prev != Op)
336100966Siwasaki    {
337100966Siwasaki        /* Search upwards in the tree to find scope with "prev" as its parent */
338100966Siwasaki
339100966Siwasaki        Search = Op;
340100966Siwasaki        for (; ;)
341100966Siwasaki        {
342100966Siwasaki            if (Search->Common.Parent == Prev)
343100966Siwasaki            {
344100966Siwasaki                break;
345100966Siwasaki            }
346100966Siwasaki
347100966Siwasaki            /* Go up one level */
348100966Siwasaki
349100966Siwasaki            Search = Search->Common.Parent;
350100966Siwasaki        }
351100966Siwasaki
352100966Siwasaki        if (Prev)
353100966Siwasaki        {
354100966Siwasaki            OpInfo = AcpiPsGetOpcodeInfo (Search->Common.AmlOpcode);
355100966Siwasaki            if (!(OpInfo->Flags & AML_FIELD))
356100966Siwasaki            {
357100966Siwasaki                /* Below root scope, append scope name */
358100966Siwasaki
359100966Siwasaki                if (DoDot)
360100966Siwasaki                {
361100966Siwasaki                    /* Append dot */
362100966Siwasaki
363100966Siwasaki                    AcpiOsPrintf (".");
364100966Siwasaki                }
365100966Siwasaki
366100966Siwasaki                if (OpInfo->Flags & AML_CREATE)
367100966Siwasaki                {
368100966Siwasaki                    if (Op->Common.AmlOpcode == AML_CREATE_FIELD_OP)
369100966Siwasaki                    {
370100966Siwasaki                        NamePath = AcpiPsGetArg (Op, 3);
371100966Siwasaki                    }
372100966Siwasaki                    else
373100966Siwasaki                    {
374100966Siwasaki                        NamePath = AcpiPsGetArg (Op, 2);
375100966Siwasaki                    }
376100966Siwasaki
377100966Siwasaki                    if ((NamePath) &&
378100966Siwasaki                        (NamePath->Common.Value.String))
379100966Siwasaki                    {
380100966Siwasaki                        AcpiDmDumpName (NamePath->Common.Value.String);
381100966Siwasaki                    }
382100966Siwasaki                }
383100966Siwasaki                else
384100966Siwasaki                {
385100966Siwasaki                    Name = AcpiPsGetName (Search);
386100966Siwasaki                    AcpiDmDumpName ((char *) &Name);
387100966Siwasaki                }
388100966Siwasaki
389100966Siwasaki                DoDot = TRUE;
390100966Siwasaki            }
391100966Siwasaki        }
392100966Siwasaki        Prev = Search;
393100966Siwasaki    }
394100966Siwasaki}
395100966Siwasaki
396151937Sjkim
397151937Sjkim/*******************************************************************************
398151937Sjkim *
399151937Sjkim * FUNCTION:    AcpiDmValidateName
400151937Sjkim *
401151937Sjkim * PARAMETERS:  Name            - 4 character ACPI name
402151937Sjkim *
403151937Sjkim * RETURN:      None
404151937Sjkim *
405151937Sjkim * DESCRIPTION: Lookup the name
406151937Sjkim *
407151937Sjkim ******************************************************************************/
408151937Sjkim
409151937Sjkimvoid
410151937SjkimAcpiDmValidateName (
411151937Sjkim    char                    *Name,
412151937Sjkim    ACPI_PARSE_OBJECT       *Op)
413151937Sjkim{
414151937Sjkim
415151937Sjkim    if ((!Name) ||
416151937Sjkim        (!Op->Common.Parent))
417151937Sjkim    {
418151937Sjkim        return;
419151937Sjkim    }
420151937Sjkim
421151937Sjkim    if (!Op->Common.Node)
422151937Sjkim    {
423151937Sjkim        AcpiOsPrintf (
424151937Sjkim            " /**** Name not found or not accessible from this scope ****/ ");
425151937Sjkim    }
426151937Sjkim
427151937Sjkim    ACPI_PARSE_OBJECT       *TargetOp;
428151937Sjkim
429151937Sjkim
430151937Sjkim    if ((!Name) ||
431151937Sjkim        (!Op->Common.Parent))
432151937Sjkim    {
433151937Sjkim        return;
434151937Sjkim    }
435151937Sjkim
436151937Sjkim    TargetOp = AcpiPsFind (Op, Name, 0, 0);
437151937Sjkim    if (!TargetOp)
438151937Sjkim    {
439151937Sjkim        /*
440151937Sjkim         * Didn't find the name in the parse tree.  This may be
441151937Sjkim         * a problem, or it may simply be one of the predefined names
442151937Sjkim         * (such as _OS_).  Rather than worry about looking up all
443151937Sjkim         * the predefined names, just display the name as given
444151937Sjkim         */
445151937Sjkim        AcpiOsPrintf (
446151937Sjkim            " /**** Name not found or not accessible from this scope ****/ ");
447151937Sjkim    }
448151937Sjkim}
449100966Siwasaki#endif
450100966Siwasaki
451151937Sjkim#endif
452100966Siwasaki
453151937Sjkim
454