dbnames.c revision 252279
1214501Srpaulo/*******************************************************************************
2214501Srpaulo *
3252726Srpaulo * Module Name: dbnames - Debugger commands for the acpi namespace
4214501Srpaulo *
5252726Srpaulo ******************************************************************************/
6252726Srpaulo
7214501Srpaulo/*
8214501Srpaulo * Copyright (C) 2000 - 2013, Intel Corp.
9214501Srpaulo * All rights reserved.
10214501Srpaulo *
11214501Srpaulo * Redistribution and use in source and binary forms, with or without
12252726Srpaulo * modification, are permitted provided that the following conditions
13214501Srpaulo * are met:
14214501Srpaulo * 1. Redistributions of source code must retain the above copyright
15214501Srpaulo *    notice, this list of conditions, and the following disclaimer,
16214501Srpaulo *    without modification.
17214501Srpaulo * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18214501Srpaulo *    substantially similar to the "NO WARRANTY" disclaimer below
19214501Srpaulo *    ("Disclaimer") and any redistribution must be conditioned upon
20214501Srpaulo *    including a substantially similar Disclaimer requirement for further
21214501Srpaulo *    binary redistribution.
22214501Srpaulo * 3. Neither the names of the above-listed copyright holders nor the names
23214501Srpaulo *    of any contributors may be used to endorse or promote products derived
24214501Srpaulo *    from this software without specific prior written permission.
25214501Srpaulo *
26214501Srpaulo * Alternatively, this software may be distributed under the terms of the
27214501Srpaulo * GNU General Public License ("GPL") version 2 as published by the Free
28214501Srpaulo * Software Foundation.
29214501Srpaulo *
30214501Srpaulo * NO WARRANTY
31214501Srpaulo * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32214501Srpaulo * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
33214501Srpaulo * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
34214501Srpaulo * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35214501Srpaulo * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36214501Srpaulo * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37214501Srpaulo * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38214501Srpaulo * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39214501Srpaulo * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40214501Srpaulo * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41214501Srpaulo * POSSIBILITY OF SUCH DAMAGES.
42214501Srpaulo */
43214501Srpaulo
44214501Srpaulo
45214501Srpaulo#include <contrib/dev/acpica/include/acpi.h>
46214501Srpaulo#include <contrib/dev/acpica/include/accommon.h>
47214501Srpaulo#include <contrib/dev/acpica/include/acnamesp.h>
48214501Srpaulo#include <contrib/dev/acpica/include/acdebug.h>
49214501Srpaulo#include <contrib/dev/acpica/include/acpredef.h>
50252726Srpaulo
51214501Srpaulo
52214501Srpaulo#ifdef ACPI_DEBUGGER
53214501Srpaulo
54214501Srpaulo#define _COMPONENT          ACPI_CA_DEBUGGER
55214501Srpaulo        ACPI_MODULE_NAME    ("dbnames")
56214501Srpaulo
57214501Srpaulo
58214501Srpaulo/* Local prototypes */
59214501Srpaulo
60214501Srpaulostatic ACPI_STATUS
61214501SrpauloAcpiDbWalkAndMatchName (
62214501Srpaulo    ACPI_HANDLE             ObjHandle,
63214501Srpaulo    UINT32                  NestingLevel,
64214501Srpaulo    void                    *Context,
65214501Srpaulo    void                    **ReturnValue);
66214501Srpaulo
67214501Srpaulostatic ACPI_STATUS
68214501SrpauloAcpiDbWalkForPredefinedNames (
69214501Srpaulo    ACPI_HANDLE             ObjHandle,
70214501Srpaulo    UINT32                  NestingLevel,
71214501Srpaulo    void                    *Context,
72214501Srpaulo    void                    **ReturnValue);
73214501Srpaulo
74214501Srpaulostatic ACPI_STATUS
75214501SrpauloAcpiDbWalkForSpecificObjects (
76214501Srpaulo    ACPI_HANDLE             ObjHandle,
77214501Srpaulo    UINT32                  NestingLevel,
78214501Srpaulo    void                    *Context,
79214501Srpaulo    void                    **ReturnValue);
80214501Srpaulo
81214501Srpaulostatic ACPI_STATUS
82214501SrpauloAcpiDbIntegrityWalk (
83214501Srpaulo    ACPI_HANDLE             ObjHandle,
84214501Srpaulo    UINT32                  NestingLevel,
85214501Srpaulo    void                    *Context,
86214501Srpaulo    void                    **ReturnValue);
87214501Srpaulo
88214501Srpaulostatic ACPI_STATUS
89214501SrpauloAcpiDbWalkForReferences (
90214501Srpaulo    ACPI_HANDLE             ObjHandle,
91214501Srpaulo    UINT32                  NestingLevel,
92214501Srpaulo    void                    *Context,
93214501Srpaulo    void                    **ReturnValue);
94214501Srpaulo
95214501Srpaulostatic ACPI_STATUS
96214501SrpauloAcpiDbBusWalk (
97214501Srpaulo    ACPI_HANDLE             ObjHandle,
98214501Srpaulo    UINT32                  NestingLevel,
99214501Srpaulo    void                    *Context,
100214501Srpaulo    void                    **ReturnValue);
101214501Srpaulo
102214501Srpaulo/*
103214501Srpaulo * Arguments for the Objects command
104214501Srpaulo * These object types map directly to the ACPI_TYPES
105214501Srpaulo */
106214501Srpaulostatic ACPI_DB_ARGUMENT_INFO    AcpiDbObjectTypes [] =
107214501Srpaulo{
108214501Srpaulo    {"ANY"},
109214501Srpaulo    {"INTEGERS"},
110214501Srpaulo    {"STRINGS"},
111214501Srpaulo    {"BUFFERS"},
112214501Srpaulo    {"PACKAGES"},
113214501Srpaulo    {"FIELDS"},
114214501Srpaulo    {"DEVICES"},
115214501Srpaulo    {"EVENTS"},
116214501Srpaulo    {"METHODS"},
117214501Srpaulo    {"MUTEXES"},
118214501Srpaulo    {"REGIONS"},
119214501Srpaulo    {"POWERRESOURCES"},
120214501Srpaulo    {"PROCESSORS"},
121214501Srpaulo    {"THERMALZONES"},
122252726Srpaulo    {"BUFFERFIELDS"},
123252726Srpaulo    {"DDBHANDLES"},
124252726Srpaulo    {"DEBUG"},
125252726Srpaulo    {"REGIONFIELDS"},
126252726Srpaulo    {"BANKFIELDS"},
127252726Srpaulo    {"INDEXFIELDS"},
128214501Srpaulo    {"REFERENCES"},
129214501Srpaulo    {"ALIAS"},
130214501Srpaulo    {NULL}           /* Must be null terminated */
131214501Srpaulo};
132214501Srpaulo
133214501Srpaulo
134214501Srpaulo/*******************************************************************************
135214501Srpaulo *
136214501Srpaulo * FUNCTION:    AcpiDbSetScope
137214501Srpaulo *
138214501Srpaulo * PARAMETERS:  Name                - New scope path
139214501Srpaulo *
140214501Srpaulo * RETURN:      Status
141214501Srpaulo *
142214501Srpaulo * DESCRIPTION: Set the "current scope" as maintained by this utility.
143214501Srpaulo *              The scope is used as a prefix to ACPI paths.
144214501Srpaulo *
145214501Srpaulo ******************************************************************************/
146214501Srpaulo
147214501Srpaulovoid
148214501SrpauloAcpiDbSetScope (
149214501Srpaulo    char                    *Name)
150214501Srpaulo{
151214501Srpaulo    ACPI_STATUS             Status;
152214501Srpaulo    ACPI_NAMESPACE_NODE     *Node;
153214501Srpaulo
154214501Srpaulo
155214501Srpaulo    if (!Name || Name[0] == 0)
156214501Srpaulo    {
157214501Srpaulo        AcpiOsPrintf ("Current scope: %s\n", AcpiGbl_DbScopeBuf);
158214501Srpaulo        return;
159214501Srpaulo    }
160214501Srpaulo
161214501Srpaulo    AcpiDbPrepNamestring (Name);
162214501Srpaulo
163214501Srpaulo    if (ACPI_IS_ROOT_PREFIX (Name[0]))
164214501Srpaulo    {
165214501Srpaulo        /* Validate new scope from the root */
166214501Srpaulo
167214501Srpaulo        Status = AcpiNsGetNode (AcpiGbl_RootNode, Name, ACPI_NS_NO_UPSEARCH,
168214501Srpaulo                    &Node);
169214501Srpaulo        if (ACPI_FAILURE (Status))
170214501Srpaulo        {
171214501Srpaulo            goto ErrorExit;
172214501Srpaulo        }
173214501Srpaulo
174214501Srpaulo        ACPI_STRCPY (AcpiGbl_DbScopeBuf, Name);
175214501Srpaulo        ACPI_STRCAT (AcpiGbl_DbScopeBuf, "\\");
176    }
177    else
178    {
179        /* Validate new scope relative to old scope */
180
181        Status = AcpiNsGetNode (AcpiGbl_DbScopeNode, Name, ACPI_NS_NO_UPSEARCH,
182                    &Node);
183        if (ACPI_FAILURE (Status))
184        {
185            goto ErrorExit;
186        }
187
188        ACPI_STRCAT (AcpiGbl_DbScopeBuf, Name);
189        ACPI_STRCAT (AcpiGbl_DbScopeBuf, "\\");
190    }
191
192    AcpiGbl_DbScopeNode = Node;
193    AcpiOsPrintf ("New scope: %s\n", AcpiGbl_DbScopeBuf);
194    return;
195
196ErrorExit:
197
198    AcpiOsPrintf ("Could not attach scope: %s, %s\n",
199        Name, AcpiFormatException (Status));
200}
201
202
203/*******************************************************************************
204 *
205 * FUNCTION:    AcpiDbDumpNamespace
206 *
207 * PARAMETERS:  StartArg        - Node to begin namespace dump
208 *              DepthArg        - Maximum tree depth to be dumped
209 *
210 * RETURN:      None
211 *
212 * DESCRIPTION: Dump entire namespace or a subtree. Each node is displayed
213 *              with type and other information.
214 *
215 ******************************************************************************/
216
217void
218AcpiDbDumpNamespace (
219    char                    *StartArg,
220    char                    *DepthArg)
221{
222    ACPI_HANDLE             SubtreeEntry = AcpiGbl_RootNode;
223    UINT32                  MaxDepth = ACPI_UINT32_MAX;
224
225
226    /* No argument given, just start at the root and dump entire namespace */
227
228    if (StartArg)
229    {
230        SubtreeEntry = AcpiDbConvertToNode (StartArg);
231        if (!SubtreeEntry)
232        {
233            return;
234        }
235
236        /* Now we can check for the depth argument */
237
238        if (DepthArg)
239        {
240            MaxDepth = ACPI_STRTOUL (DepthArg, NULL, 0);
241        }
242    }
243
244    AcpiDbSetOutputDestination (ACPI_DB_DUPLICATE_OUTPUT);
245    AcpiOsPrintf ("ACPI Namespace (from %4.4s (%p) subtree):\n",
246        ((ACPI_NAMESPACE_NODE *) SubtreeEntry)->Name.Ascii, SubtreeEntry);
247
248    /* Display the subtree */
249
250    AcpiDbSetOutputDestination (ACPI_DB_REDIRECTABLE_OUTPUT);
251    AcpiNsDumpObjects (ACPI_TYPE_ANY, ACPI_DISPLAY_SUMMARY, MaxDepth,
252        ACPI_OWNER_ID_MAX, SubtreeEntry);
253    AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
254}
255
256
257/*******************************************************************************
258 *
259 * FUNCTION:    AcpiDbDumpNamespaceByOwner
260 *
261 * PARAMETERS:  OwnerArg        - Owner ID whose nodes will be displayed
262 *              DepthArg        - Maximum tree depth to be dumped
263 *
264 * RETURN:      None
265 *
266 * DESCRIPTION: Dump elements of the namespace that are owned by the OwnerId.
267 *
268 ******************************************************************************/
269
270void
271AcpiDbDumpNamespaceByOwner (
272    char                    *OwnerArg,
273    char                    *DepthArg)
274{
275    ACPI_HANDLE             SubtreeEntry = AcpiGbl_RootNode;
276    UINT32                  MaxDepth = ACPI_UINT32_MAX;
277    ACPI_OWNER_ID           OwnerId;
278
279
280    OwnerId = (ACPI_OWNER_ID) ACPI_STRTOUL (OwnerArg, NULL, 0);
281
282    /* Now we can check for the depth argument */
283
284    if (DepthArg)
285    {
286        MaxDepth = ACPI_STRTOUL (DepthArg, NULL, 0);
287    }
288
289    AcpiDbSetOutputDestination (ACPI_DB_DUPLICATE_OUTPUT);
290    AcpiOsPrintf ("ACPI Namespace by owner %X:\n", OwnerId);
291
292    /* Display the subtree */
293
294    AcpiDbSetOutputDestination (ACPI_DB_REDIRECTABLE_OUTPUT);
295    AcpiNsDumpObjects (ACPI_TYPE_ANY, ACPI_DISPLAY_SUMMARY, MaxDepth, OwnerId,
296        SubtreeEntry);
297    AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
298}
299
300
301/*******************************************************************************
302 *
303 * FUNCTION:    AcpiDbWalkAndMatchName
304 *
305 * PARAMETERS:  Callback from WalkNamespace
306 *
307 * RETURN:      Status
308 *
309 * DESCRIPTION: Find a particular name/names within the namespace. Wildcards
310 *              are supported -- '?' matches any character.
311 *
312 ******************************************************************************/
313
314static ACPI_STATUS
315AcpiDbWalkAndMatchName (
316    ACPI_HANDLE             ObjHandle,
317    UINT32                  NestingLevel,
318    void                    *Context,
319    void                    **ReturnValue)
320{
321    ACPI_STATUS             Status;
322    char                    *RequestedName = (char *) Context;
323    UINT32                  i;
324    ACPI_BUFFER             Buffer;
325    ACPI_WALK_INFO          Info;
326
327
328    /* Check for a name match */
329
330    for (i = 0; i < 4; i++)
331    {
332        /* Wildcard support */
333
334        if ((RequestedName[i] != '?') &&
335            (RequestedName[i] != ((ACPI_NAMESPACE_NODE *) ObjHandle)->Name.Ascii[i]))
336        {
337            /* No match, just exit */
338
339            return (AE_OK);
340        }
341    }
342
343    /* Get the full pathname to this object */
344
345    Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
346    Status = AcpiNsHandleToPathname (ObjHandle, &Buffer);
347    if (ACPI_FAILURE (Status))
348    {
349        AcpiOsPrintf ("Could Not get pathname for object %p\n", ObjHandle);
350    }
351    else
352    {
353        Info.OwnerId = ACPI_OWNER_ID_MAX;
354        Info.DebugLevel = ACPI_UINT32_MAX;
355        Info.DisplayType = ACPI_DISPLAY_SUMMARY | ACPI_DISPLAY_SHORT;
356
357        AcpiOsPrintf ("%32s", (char *) Buffer.Pointer);
358        (void) AcpiNsDumpOneObject (ObjHandle, NestingLevel, &Info, NULL);
359        ACPI_FREE (Buffer.Pointer);
360    }
361
362    return (AE_OK);
363}
364
365
366/*******************************************************************************
367 *
368 * FUNCTION:    AcpiDbFindNameInNamespace
369 *
370 * PARAMETERS:  NameArg         - The 4-character ACPI name to find.
371 *                                wildcards are supported.
372 *
373 * RETURN:      None
374 *
375 * DESCRIPTION: Search the namespace for a given name (with wildcards)
376 *
377 ******************************************************************************/
378
379ACPI_STATUS
380AcpiDbFindNameInNamespace (
381    char                    *NameArg)
382{
383    char                    AcpiName[5] = "____";
384    char                    *AcpiNamePtr = AcpiName;
385
386
387    if (ACPI_STRLEN (NameArg) > 4)
388    {
389        AcpiOsPrintf ("Name must be no longer than 4 characters\n");
390        return (AE_OK);
391    }
392
393    /* Pad out name with underscores as necessary to create a 4-char name */
394
395    AcpiUtStrupr (NameArg);
396    while (*NameArg)
397    {
398        *AcpiNamePtr = *NameArg;
399        AcpiNamePtr++;
400        NameArg++;
401    }
402
403    /* Walk the namespace from the root */
404
405    (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
406                        AcpiDbWalkAndMatchName, NULL, AcpiName, NULL);
407
408    AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
409    return (AE_OK);
410}
411
412
413/*******************************************************************************
414 *
415 * FUNCTION:    AcpiDbWalkForPredefinedNames
416 *
417 * PARAMETERS:  Callback from WalkNamespace
418 *
419 * RETURN:      Status
420 *
421 * DESCRIPTION: Detect and display predefined ACPI names (names that start with
422 *              an underscore)
423 *
424 ******************************************************************************/
425
426static ACPI_STATUS
427AcpiDbWalkForPredefinedNames (
428    ACPI_HANDLE             ObjHandle,
429    UINT32                  NestingLevel,
430    void                    *Context,
431    void                    **ReturnValue)
432{
433    ACPI_NAMESPACE_NODE         *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
434    UINT32                      *Count = (UINT32 *) Context;
435    const ACPI_PREDEFINED_INFO  *Predefined;
436    const ACPI_PREDEFINED_INFO  *Package = NULL;
437    char                        *Pathname;
438    char                        StringBuffer[48];
439
440
441    Predefined = AcpiUtMatchPredefinedMethod (Node->Name.Ascii);
442    if (!Predefined)
443    {
444        return (AE_OK);
445    }
446
447    Pathname = AcpiNsGetExternalPathname (Node);
448    if (!Pathname)
449    {
450        return (AE_OK);
451    }
452
453    /* If method returns a package, the info is in the next table entry */
454
455    if (Predefined->Info.ExpectedBtypes & ACPI_RTYPE_PACKAGE)
456    {
457        Package = Predefined + 1;
458    }
459
460    AcpiUtGetExpectedReturnTypes (StringBuffer,
461        Predefined->Info.ExpectedBtypes);
462
463    AcpiOsPrintf ("%-32s Arguments %X, Return Types: %s", Pathname,
464        METHOD_GET_ARG_COUNT (Predefined->Info.ArgumentList),
465        StringBuffer);
466
467    if (Package)
468    {
469        AcpiOsPrintf (" (PkgType %2.2X, ObjType %2.2X, Count %2.2X)",
470            Package->RetInfo.Type, Package->RetInfo.ObjectType1,
471            Package->RetInfo.Count1);
472    }
473
474    AcpiOsPrintf("\n");
475
476    /* Check that the declared argument count matches the ACPI spec */
477
478    AcpiNsCheckAcpiCompliance (Pathname, Node, Predefined);
479
480    ACPI_FREE (Pathname);
481    (*Count)++;
482    return (AE_OK);
483}
484
485
486/*******************************************************************************
487 *
488 * FUNCTION:    AcpiDbCheckPredefinedNames
489 *
490 * PARAMETERS:  None
491 *
492 * RETURN:      None
493 *
494 * DESCRIPTION: Validate all predefined names in the namespace
495 *
496 ******************************************************************************/
497
498void
499AcpiDbCheckPredefinedNames (
500    void)
501{
502    UINT32                  Count = 0;
503
504
505    /* Search all nodes in namespace */
506
507    (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
508                AcpiDbWalkForPredefinedNames, NULL, (void *) &Count, NULL);
509
510    AcpiOsPrintf ("Found %u predefined names in the namespace\n", Count);
511}
512
513
514/*******************************************************************************
515 *
516 * FUNCTION:    AcpiDbWalkForSpecificObjects
517 *
518 * PARAMETERS:  Callback from WalkNamespace
519 *
520 * RETURN:      Status
521 *
522 * DESCRIPTION: Display short info about objects in the namespace
523 *
524 ******************************************************************************/
525
526static ACPI_STATUS
527AcpiDbWalkForSpecificObjects (
528    ACPI_HANDLE             ObjHandle,
529    UINT32                  NestingLevel,
530    void                    *Context,
531    void                    **ReturnValue)
532{
533    ACPI_WALK_INFO          *Info = (ACPI_WALK_INFO *) Context;
534    ACPI_BUFFER             Buffer;
535    ACPI_STATUS             Status;
536
537
538    Info->Count++;
539
540    /* Get and display the full pathname to this object */
541
542    Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
543    Status = AcpiNsHandleToPathname (ObjHandle, &Buffer);
544    if (ACPI_FAILURE (Status))
545    {
546        AcpiOsPrintf ("Could Not get pathname for object %p\n", ObjHandle);
547        return (AE_OK);
548    }
549
550    AcpiOsPrintf ("%32s", (char *) Buffer.Pointer);
551    ACPI_FREE (Buffer.Pointer);
552
553    /* Dump short info about the object */
554
555    (void) AcpiNsDumpOneObject (ObjHandle, NestingLevel, Info, NULL);
556    return (AE_OK);
557}
558
559
560/*******************************************************************************
561 *
562 * FUNCTION:    AcpiDbDisplayObjects
563 *
564 * PARAMETERS:  ObjTypeArg          - Type of object to display
565 *              DisplayCountArg     - Max depth to display
566 *
567 * RETURN:      None
568 *
569 * DESCRIPTION: Display objects in the namespace of the requested type
570 *
571 ******************************************************************************/
572
573ACPI_STATUS
574AcpiDbDisplayObjects (
575    char                    *ObjTypeArg,
576    char                    *DisplayCountArg)
577{
578    ACPI_WALK_INFO          Info;
579    ACPI_OBJECT_TYPE        Type;
580
581
582    /* Get the object type */
583
584    Type = AcpiDbMatchArgument (ObjTypeArg, AcpiDbObjectTypes);
585    if (Type == ACPI_TYPE_NOT_FOUND)
586    {
587        AcpiOsPrintf ("Invalid or unsupported argument\n");
588        return (AE_OK);
589    }
590
591    AcpiDbSetOutputDestination (ACPI_DB_DUPLICATE_OUTPUT);
592    AcpiOsPrintf (
593        "Objects of type [%s] defined in the current ACPI Namespace:\n",
594        AcpiUtGetTypeName (Type));
595
596    AcpiDbSetOutputDestination (ACPI_DB_REDIRECTABLE_OUTPUT);
597
598    Info.Count = 0;
599    Info.OwnerId = ACPI_OWNER_ID_MAX;
600    Info.DebugLevel = ACPI_UINT32_MAX;
601    Info.DisplayType = ACPI_DISPLAY_SUMMARY | ACPI_DISPLAY_SHORT;
602
603    /* Walk the namespace from the root */
604
605    (void) AcpiWalkNamespace (Type, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
606                AcpiDbWalkForSpecificObjects, NULL, (void *) &Info, NULL);
607
608    AcpiOsPrintf (
609        "\nFound %u objects of type [%s] in the current ACPI Namespace\n",
610        Info.Count, AcpiUtGetTypeName (Type));
611
612    AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
613    return (AE_OK);
614}
615
616
617/*******************************************************************************
618 *
619 * FUNCTION:    AcpiDbIntegrityWalk
620 *
621 * PARAMETERS:  Callback from WalkNamespace
622 *
623 * RETURN:      Status
624 *
625 * DESCRIPTION: Examine one NS node for valid values.
626 *
627 ******************************************************************************/
628
629static ACPI_STATUS
630AcpiDbIntegrityWalk (
631    ACPI_HANDLE             ObjHandle,
632    UINT32                  NestingLevel,
633    void                    *Context,
634    void                    **ReturnValue)
635{
636    ACPI_INTEGRITY_INFO     *Info = (ACPI_INTEGRITY_INFO *) Context;
637    ACPI_NAMESPACE_NODE     *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
638    ACPI_OPERAND_OBJECT     *Object;
639    BOOLEAN                 Alias = TRUE;
640
641
642    Info->Nodes++;
643
644    /* Verify the NS node, and dereference aliases */
645
646    while (Alias)
647    {
648        if (ACPI_GET_DESCRIPTOR_TYPE (Node) != ACPI_DESC_TYPE_NAMED)
649        {
650            AcpiOsPrintf ("Invalid Descriptor Type for Node %p [%s] - is %2.2X should be %2.2X\n",
651                Node, AcpiUtGetDescriptorName (Node), ACPI_GET_DESCRIPTOR_TYPE (Node),
652                ACPI_DESC_TYPE_NAMED);
653            return (AE_OK);
654        }
655
656        if ((Node->Type == ACPI_TYPE_LOCAL_ALIAS)  ||
657            (Node->Type == ACPI_TYPE_LOCAL_METHOD_ALIAS))
658        {
659            Node = (ACPI_NAMESPACE_NODE *) Node->Object;
660        }
661        else
662        {
663            Alias = FALSE;
664        }
665    }
666
667    if (Node->Type > ACPI_TYPE_LOCAL_MAX)
668    {
669        AcpiOsPrintf ("Invalid Object Type for Node %p, Type = %X\n",
670            Node, Node->Type);
671        return (AE_OK);
672    }
673
674    if (!AcpiUtValidAcpiName (Node->Name.Ascii))
675    {
676        AcpiOsPrintf ("Invalid AcpiName for Node %p\n", Node);
677        return (AE_OK);
678    }
679
680    Object = AcpiNsGetAttachedObject (Node);
681    if (Object)
682    {
683        Info->Objects++;
684        if (ACPI_GET_DESCRIPTOR_TYPE (Object) != ACPI_DESC_TYPE_OPERAND)
685        {
686            AcpiOsPrintf ("Invalid Descriptor Type for Object %p [%s]\n",
687                Object, AcpiUtGetDescriptorName (Object));
688        }
689    }
690
691    return (AE_OK);
692}
693
694
695/*******************************************************************************
696 *
697 * FUNCTION:    AcpiDbCheckIntegrity
698 *
699 * PARAMETERS:  None
700 *
701 * RETURN:      None
702 *
703 * DESCRIPTION: Check entire namespace for data structure integrity
704 *
705 ******************************************************************************/
706
707void
708AcpiDbCheckIntegrity (
709    void)
710{
711    ACPI_INTEGRITY_INFO     Info = {0,0};
712
713    /* Search all nodes in namespace */
714
715    (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
716                    AcpiDbIntegrityWalk, NULL, (void *) &Info, NULL);
717
718    AcpiOsPrintf ("Verified %u namespace nodes with %u Objects\n",
719        Info.Nodes, Info.Objects);
720}
721
722
723/*******************************************************************************
724 *
725 * FUNCTION:    AcpiDbWalkForReferences
726 *
727 * PARAMETERS:  Callback from WalkNamespace
728 *
729 * RETURN:      Status
730 *
731 * DESCRIPTION: Check if this namespace object refers to the target object
732 *              that is passed in as the context value.
733 *
734 * Note: Currently doesn't check subobjects within the Node's object
735 *
736 ******************************************************************************/
737
738static ACPI_STATUS
739AcpiDbWalkForReferences (
740    ACPI_HANDLE             ObjHandle,
741    UINT32                  NestingLevel,
742    void                    *Context,
743    void                    **ReturnValue)
744{
745    ACPI_OPERAND_OBJECT     *ObjDesc = (ACPI_OPERAND_OBJECT  *) Context;
746    ACPI_NAMESPACE_NODE     *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
747
748
749    /* Check for match against the namespace node itself */
750
751    if (Node == (void *) ObjDesc)
752    {
753        AcpiOsPrintf ("Object is a Node [%4.4s]\n",
754            AcpiUtGetNodeName (Node));
755    }
756
757    /* Check for match against the object attached to the node */
758
759    if (AcpiNsGetAttachedObject (Node) == ObjDesc)
760    {
761        AcpiOsPrintf ("Reference at Node->Object %p [%4.4s]\n",
762            Node, AcpiUtGetNodeName (Node));
763    }
764
765    return (AE_OK);
766}
767
768
769/*******************************************************************************
770 *
771 * FUNCTION:    AcpiDbFindReferences
772 *
773 * PARAMETERS:  ObjectArg       - String with hex value of the object
774 *
775 * RETURN:      None
776 *
777 * DESCRIPTION: Search namespace for all references to the input object
778 *
779 ******************************************************************************/
780
781void
782AcpiDbFindReferences (
783    char                    *ObjectArg)
784{
785    ACPI_OPERAND_OBJECT     *ObjDesc;
786    ACPI_SIZE               Address;
787
788
789    /* Convert string to object pointer */
790
791    Address = ACPI_STRTOUL (ObjectArg, NULL, 16);
792    ObjDesc = ACPI_TO_POINTER (Address);
793
794    /* Search all nodes in namespace */
795
796    (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
797                    AcpiDbWalkForReferences, NULL, (void *) ObjDesc, NULL);
798}
799
800
801/*******************************************************************************
802 *
803 * FUNCTION:    AcpiDbBusWalk
804 *
805 * PARAMETERS:  Callback from WalkNamespace
806 *
807 * RETURN:      Status
808 *
809 * DESCRIPTION: Display info about device objects that have a corresponding
810 *              _PRT method.
811 *
812 ******************************************************************************/
813
814static ACPI_STATUS
815AcpiDbBusWalk (
816    ACPI_HANDLE             ObjHandle,
817    UINT32                  NestingLevel,
818    void                    *Context,
819    void                    **ReturnValue)
820{
821    ACPI_NAMESPACE_NODE     *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
822    ACPI_STATUS             Status;
823    ACPI_BUFFER             Buffer;
824    ACPI_NAMESPACE_NODE     *TempNode;
825    ACPI_DEVICE_INFO        *Info;
826    UINT32                  i;
827
828
829    if ((Node->Type != ACPI_TYPE_DEVICE) &&
830        (Node->Type != ACPI_TYPE_PROCESSOR))
831    {
832        return (AE_OK);
833    }
834
835    /* Exit if there is no _PRT under this device */
836
837    Status = AcpiGetHandle (Node, METHOD_NAME__PRT,
838                ACPI_CAST_PTR (ACPI_HANDLE, &TempNode));
839    if (ACPI_FAILURE (Status))
840    {
841        return (AE_OK);
842    }
843
844    /* Get the full path to this device object */
845
846    Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
847    Status = AcpiNsHandleToPathname (ObjHandle, &Buffer);
848    if (ACPI_FAILURE (Status))
849    {
850        AcpiOsPrintf ("Could Not get pathname for object %p\n", ObjHandle);
851        return (AE_OK);
852    }
853
854    Status = AcpiGetObjectInfo (ObjHandle, &Info);
855    if (ACPI_FAILURE (Status))
856    {
857        return (AE_OK);
858    }
859
860    /* Display the full path */
861
862    AcpiOsPrintf ("%-32s Type %X", (char *) Buffer.Pointer, Node->Type);
863    ACPI_FREE (Buffer.Pointer);
864
865    if (Info->Flags & ACPI_PCI_ROOT_BRIDGE)
866    {
867        AcpiOsPrintf ("  - Is PCI Root Bridge");
868    }
869    AcpiOsPrintf ("\n");
870
871    /* _PRT info */
872
873    AcpiOsPrintf ("_PRT: %p\n", TempNode);
874
875    /* Dump _ADR, _HID, _UID, _CID */
876
877    if (Info->Valid & ACPI_VALID_ADR)
878    {
879        AcpiOsPrintf ("_ADR: %8.8X%8.8X\n", ACPI_FORMAT_UINT64 (Info->Address));
880    }
881    else
882    {
883        AcpiOsPrintf ("_ADR: <Not Present>\n");
884    }
885
886    if (Info->Valid & ACPI_VALID_HID)
887    {
888        AcpiOsPrintf ("_HID: %s\n", Info->HardwareId.String);
889    }
890    else
891    {
892        AcpiOsPrintf ("_HID: <Not Present>\n");
893    }
894
895    if (Info->Valid & ACPI_VALID_UID)
896    {
897        AcpiOsPrintf ("_UID: %s\n", Info->UniqueId.String);
898    }
899    else
900    {
901        AcpiOsPrintf ("_UID: <Not Present>\n");
902    }
903
904    if (Info->Valid & ACPI_VALID_CID)
905    {
906        for (i = 0; i < Info->CompatibleIdList.Count; i++)
907        {
908            AcpiOsPrintf ("_CID: %s\n",
909                Info->CompatibleIdList.Ids[i].String);
910        }
911    }
912    else
913    {
914        AcpiOsPrintf ("_CID: <Not Present>\n");
915    }
916
917    ACPI_FREE (Info);
918    return (AE_OK);
919}
920
921
922/*******************************************************************************
923 *
924 * FUNCTION:    AcpiDbGetBusInfo
925 *
926 * PARAMETERS:  None
927 *
928 * RETURN:      None
929 *
930 * DESCRIPTION: Display info about system busses.
931 *
932 ******************************************************************************/
933
934void
935AcpiDbGetBusInfo (
936    void)
937{
938    /* Search all nodes in namespace */
939
940    (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
941                    AcpiDbBusWalk, NULL, NULL, NULL);
942}
943
944#endif /* ACPI_DEBUGGER */
945