]> CyberLeo.Net >> Repos - FreeBSD/releng/8.0.git/blob - sys/contrib/dev/acpica/debugger/dbcmds.c
Adjust to reflect 8.0-RELEASE.
[FreeBSD/releng/8.0.git] / sys / contrib / dev / acpica / debugger / dbcmds.c
1 /*******************************************************************************
2  *
3  * Module Name: dbcmds - debug commands and output routines
4  *
5  ******************************************************************************/
6
7 /******************************************************************************
8  *
9  * 1. Copyright Notice
10  *
11  * Some or all of this work - Copyright (c) 1999 - 2009, Intel Corp.
12  * All rights reserved.
13  *
14  * 2. License
15  *
16  * 2.1. This is your license from Intel Corp. under its intellectual property
17  * rights.  You may have additional license terms from the party that provided
18  * you this software, covering your right to use that party's intellectual
19  * property rights.
20  *
21  * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a
22  * copy of the source code appearing in this file ("Covered Code") an
23  * irrevocable, perpetual, worldwide license under Intel's copyrights in the
24  * base code distributed originally by Intel ("Original Intel Code") to copy,
25  * make derivatives, distribute, use and display any portion of the Covered
26  * Code in any form, with the right to sublicense such rights; and
27  *
28  * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent
29  * license (with the right to sublicense), under only those claims of Intel
30  * patents that are infringed by the Original Intel Code, to make, use, sell,
31  * offer to sell, and import the Covered Code and derivative works thereof
32  * solely to the minimum extent necessary to exercise the above copyright
33  * license, and in no event shall the patent license extend to any additions
34  * to or modifications of the Original Intel Code.  No other license or right
35  * is granted directly or by implication, estoppel or otherwise;
36  *
37  * The above copyright and patent license is granted only if the following
38  * conditions are met:
39  *
40  * 3. Conditions
41  *
42  * 3.1. Redistribution of Source with Rights to Further Distribute Source.
43  * Redistribution of source code of any substantial portion of the Covered
44  * Code or modification with rights to further distribute source must include
45  * the above Copyright Notice, the above License, this list of Conditions,
46  * and the following Disclaimer and Export Compliance provision.  In addition,
47  * Licensee must cause all Covered Code to which Licensee contributes to
48  * contain a file documenting the changes Licensee made to create that Covered
49  * Code and the date of any change.  Licensee must include in that file the
50  * documentation of any changes made by any predecessor Licensee.  Licensee
51  * must include a prominent statement that the modification is derived,
52  * directly or indirectly, from Original Intel Code.
53  *
54  * 3.2. Redistribution of Source with no Rights to Further Distribute Source.
55  * Redistribution of source code of any substantial portion of the Covered
56  * Code or modification without rights to further distribute source must
57  * include the following Disclaimer and Export Compliance provision in the
58  * documentation and/or other materials provided with distribution.  In
59  * addition, Licensee may not authorize further sublicense of source of any
60  * portion of the Covered Code, and must include terms to the effect that the
61  * license from Licensee to its licensee is limited to the intellectual
62  * property embodied in the software Licensee provides to its licensee, and
63  * not to intellectual property embodied in modifications its licensee may
64  * make.
65  *
66  * 3.3. Redistribution of Executable. Redistribution in executable form of any
67  * substantial portion of the Covered Code or modification must reproduce the
68  * above Copyright Notice, and the following Disclaimer and Export Compliance
69  * provision in the documentation and/or other materials provided with the
70  * distribution.
71  *
72  * 3.4. Intel retains all right, title, and interest in and to the Original
73  * Intel Code.
74  *
75  * 3.5. Neither the name Intel nor any other trademark owned or controlled by
76  * Intel shall be used in advertising or otherwise to promote the sale, use or
77  * other dealings in products derived from or relating to the Covered Code
78  * without prior written authorization from Intel.
79  *
80  * 4. Disclaimer and Export Compliance
81  *
82  * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED
83  * HERE.  ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE
84  * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT,  ASSISTANCE,
85  * INSTALLATION, TRAINING OR OTHER SERVICES.  INTEL WILL NOT PROVIDE ANY
86  * UPDATES, ENHANCEMENTS OR EXTENSIONS.  INTEL SPECIFICALLY DISCLAIMS ANY
87  * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A
88  * PARTICULAR PURPOSE.
89  *
90  * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES
91  * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR
92  * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT,
93  * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY
94  * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL
95  * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES.  THESE LIMITATIONS
96  * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY
97  * LIMITED REMEDY.
98  *
99  * 4.3. Licensee shall not export, either directly or indirectly, any of this
100  * software or system incorporating such software without first obtaining any
101  * required license or other approval from the U. S. Department of Commerce or
102  * any other agency or department of the United States Government.  In the
103  * event Licensee exports any such software from the United States or
104  * re-exports any such software from a foreign destination, Licensee shall
105  * ensure that the distribution and export/re-export of the software is in
106  * compliance with all laws, regulations, orders, or other restrictions of the
107  * U.S. Export Administration Regulations. Licensee agrees that neither it nor
108  * any of its subsidiaries will export/re-export any technical data, process,
109  * software, or service, directly or indirectly, to any country for which the
110  * United States government or any agency thereof requires an export license,
111  * other governmental approval, or letter of assurance, without first obtaining
112  * such license, approval or letter.
113  *
114  *****************************************************************************/
115
116
117 #include <contrib/dev/acpica/include/acpi.h>
118 #include <contrib/dev/acpica/include/accommon.h>
119 #include <contrib/dev/acpica/include/acdispat.h>
120 #include <contrib/dev/acpica/include/acnamesp.h>
121 #include <contrib/dev/acpica/include/acevents.h>
122 #include <contrib/dev/acpica/include/acdebug.h>
123 #include <contrib/dev/acpica/include/acresrc.h>
124 #include <contrib/dev/acpica/include/acdisasm.h>
125 #include <contrib/dev/acpica/include/actables.h>
126 #include <contrib/dev/acpica/include/acparser.h>
127
128 #ifdef ACPI_DEBUGGER
129
130 #define _COMPONENT          ACPI_CA_DEBUGGER
131         ACPI_MODULE_NAME    ("dbcmds")
132
133 /* Local prototypes */
134
135 static ACPI_STATUS
136 AcpiDbIntegrityWalk (
137     ACPI_HANDLE             ObjHandle,
138     UINT32                  NestingLevel,
139     void                    *Context,
140     void                    **ReturnValue);
141
142 static ACPI_STATUS
143 AcpiDbWalkAndMatchName (
144     ACPI_HANDLE             ObjHandle,
145     UINT32                  NestingLevel,
146     void                    *Context,
147     void                    **ReturnValue);
148
149 static ACPI_STATUS
150 AcpiDbWalkForReferences (
151     ACPI_HANDLE             ObjHandle,
152     UINT32                  NestingLevel,
153     void                    *Context,
154     void                    **ReturnValue);
155
156 static ACPI_STATUS
157 AcpiDbWalkForSpecificObjects (
158     ACPI_HANDLE             ObjHandle,
159     UINT32                  NestingLevel,
160     void                    *Context,
161     void                    **ReturnValue);
162
163 static ACPI_NAMESPACE_NODE *
164 AcpiDbConvertToNode (
165     char                    *InString);
166
167 static void
168 AcpiDmCompareAmlResources (
169     UINT8                   *Aml1Buffer,
170     ACPI_RSDESC_SIZE        Aml1BufferLength,
171     UINT8                   *Aml2Buffer,
172     ACPI_RSDESC_SIZE        Aml2BufferLength);
173
174 static ACPI_STATUS
175 AcpiDmTestResourceConversion (
176     ACPI_NAMESPACE_NODE     *Node,
177     char                    *Name);
178
179
180 /*
181  * Arguments for the Objects command
182  * These object types map directly to the ACPI_TYPES
183  */
184 static ARGUMENT_INFO        AcpiDbObjectTypes [] =
185 {
186     {"ANY"},
187     {"INTEGERS"},
188     {"STRINGS"},
189     {"BUFFERS"},
190     {"PACKAGES"},
191     {"FIELDS"},
192     {"DEVICES"},
193     {"EVENTS"},
194     {"METHODS"},
195     {"MUTEXES"},
196     {"REGIONS"},
197     {"POWERRESOURCES"},
198     {"PROCESSORS"},
199     {"THERMALZONES"},
200     {"BUFFERFIELDS"},
201     {"DDBHANDLES"},
202     {"DEBUG"},
203     {"REGIONFIELDS"},
204     {"BANKFIELDS"},
205     {"INDEXFIELDS"},
206     {"REFERENCES"},
207     {"ALIAS"},
208     {NULL}           /* Must be null terminated */
209 };
210
211
212 /*******************************************************************************
213  *
214  * FUNCTION:    AcpiDbConvertToNode
215  *
216  * PARAMETERS:  InString        - String to convert
217  *
218  * RETURN:      Pointer to a NS node
219  *
220  * DESCRIPTION: Convert a string to a valid NS pointer.  Handles numeric or
221  *              alpha strings.
222  *
223  ******************************************************************************/
224
225 static ACPI_NAMESPACE_NODE *
226 AcpiDbConvertToNode (
227     char                    *InString)
228 {
229     ACPI_NAMESPACE_NODE     *Node;
230
231
232     if ((*InString >= 0x30) && (*InString <= 0x39))
233     {
234         /* Numeric argument, convert */
235
236         Node = ACPI_TO_POINTER (ACPI_STRTOUL (InString, NULL, 16));
237         if (!AcpiOsReadable (Node, sizeof (ACPI_NAMESPACE_NODE)))
238         {
239             AcpiOsPrintf ("Address %p is invalid in this address space\n",
240                 Node);
241             return (NULL);
242         }
243
244         /* Make sure pointer is valid NS node */
245
246         if (ACPI_GET_DESCRIPTOR_TYPE (Node) != ACPI_DESC_TYPE_NAMED)
247         {
248             AcpiOsPrintf ("Address %p is not a valid NS node [%s]\n",
249                     Node, AcpiUtGetDescriptorName (Node));
250             return (NULL);
251         }
252     }
253     else
254     {
255         /* Alpha argument */
256         /* The parameter is a name string that must be resolved to a
257          * Named obj
258          */
259         Node = AcpiDbLocalNsLookup (InString);
260         if (!Node)
261         {
262             Node = AcpiGbl_RootNode;
263         }
264     }
265
266     return (Node);
267 }
268
269
270 /*******************************************************************************
271  *
272  * FUNCTION:    AcpiDbSleep
273  *
274  * PARAMETERS:  ObjectArg       - Desired sleep state (0-5)
275  *
276  * RETURN:      Status
277  *
278  * DESCRIPTION: Simulate a sleep/wake sequence
279  *
280  ******************************************************************************/
281
282 ACPI_STATUS
283 AcpiDbSleep (
284     char                    *ObjectArg)
285 {
286     ACPI_STATUS             Status;
287     UINT8                   SleepState;
288
289
290     SleepState = (UINT8) ACPI_STRTOUL (ObjectArg, NULL, 0);
291
292     AcpiOsPrintf ("**** Prepare to sleep ****\n");
293     Status = AcpiEnterSleepStatePrep (SleepState);
294     if (ACPI_FAILURE (Status))
295     {
296         return (Status);
297     }
298
299     AcpiOsPrintf ("**** Going to sleep ****\n");
300     Status = AcpiEnterSleepState (SleepState);
301     if (ACPI_FAILURE (Status))
302     {
303         return (Status);
304     }
305
306     AcpiOsPrintf ("**** returning from sleep ****\n");
307     Status = AcpiLeaveSleepState (SleepState);
308
309     return (Status);
310 }
311
312
313 /*******************************************************************************
314  *
315  * FUNCTION:    AcpiDbWalkForReferences
316  *
317  * PARAMETERS:  Callback from WalkNamespace
318  *
319  * RETURN:      Status
320  *
321  * DESCRIPTION: Check if this namespace object refers to the target object
322  *              that is passed in as the context value.
323  *
324  * Note: Currently doesn't check subobjects within the Node's object
325  *
326  ******************************************************************************/
327
328 static ACPI_STATUS
329 AcpiDbWalkForReferences (
330     ACPI_HANDLE             ObjHandle,
331     UINT32                  NestingLevel,
332     void                    *Context,
333     void                    **ReturnValue)
334 {
335     ACPI_OPERAND_OBJECT     *ObjDesc = (ACPI_OPERAND_OBJECT  *) Context;
336     ACPI_NAMESPACE_NODE     *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
337
338
339     /* Check for match against the namespace node itself */
340
341     if (Node == (void *) ObjDesc)
342     {
343         AcpiOsPrintf ("Object is a Node [%4.4s]\n",
344             AcpiUtGetNodeName (Node));
345     }
346
347     /* Check for match against the object attached to the node */
348
349     if (AcpiNsGetAttachedObject (Node) == ObjDesc)
350     {
351         AcpiOsPrintf ("Reference at Node->Object %p [%4.4s]\n",
352             Node, AcpiUtGetNodeName (Node));
353     }
354
355     return (AE_OK);
356 }
357
358
359 /*******************************************************************************
360  *
361  * FUNCTION:    AcpiDbFindReferences
362  *
363  * PARAMETERS:  ObjectArg       - String with hex value of the object
364  *
365  * RETURN:      None
366  *
367  * DESCRIPTION: Search namespace for all references to the input object
368  *
369  ******************************************************************************/
370
371 void
372 AcpiDbFindReferences (
373     char                    *ObjectArg)
374 {
375     ACPI_OPERAND_OBJECT     *ObjDesc;
376
377
378     /* Convert string to object pointer */
379
380     ObjDesc = ACPI_TO_POINTER (ACPI_STRTOUL (ObjectArg, NULL, 16));
381
382     /* Search all nodes in namespace */
383
384     (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
385                     AcpiDbWalkForReferences, (void *) ObjDesc, NULL);
386 }
387
388
389 /*******************************************************************************
390  *
391  * FUNCTION:    AcpiDbWalkForPredefinedNames
392  *
393  * PARAMETERS:  Callback from WalkNamespace
394  *
395  * RETURN:      Status
396  *
397  * DESCRIPTION: Detect and display predefined ACPI names (names that start with
398  *              an underscore)
399  *
400  ******************************************************************************/
401
402 static ACPI_STATUS
403 AcpiDbWalkForPredefinedNames (
404     ACPI_HANDLE             ObjHandle,
405     UINT32                  NestingLevel,
406     void                    *Context,
407     void                    **ReturnValue)
408 {
409     ACPI_NAMESPACE_NODE         *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
410     UINT32                      *Count = (UINT32 *) Context;
411     const ACPI_PREDEFINED_INFO  *Predefined;
412     const ACPI_PREDEFINED_INFO  *Package = NULL;
413     char                        *Pathname;
414
415
416     Predefined = AcpiNsCheckForPredefinedName (Node);
417     if (!Predefined)
418     {
419         return (AE_OK);
420     }
421
422     Pathname = AcpiNsGetExternalPathname (Node);
423     if (!Pathname)
424     {
425         return (AE_OK);
426     }
427
428     /* If method returns a package, the info is in the next table entry */
429
430     if (Predefined->Info.ExpectedBtypes & ACPI_BTYPE_PACKAGE)
431     {
432         Package = Predefined + 1;
433     }
434
435     AcpiOsPrintf ("%-32s arg %X ret %2.2X", Pathname,
436         Predefined->Info.ParamCount, Predefined->Info.ExpectedBtypes);
437
438     if (Package)
439     {
440         AcpiOsPrintf (" PkgType %2.2X ObjType %2.2X Count %2.2X",
441             Package->RetInfo.Type, Package->RetInfo.ObjectType1,
442             Package->RetInfo.Count1);
443     }
444
445     AcpiOsPrintf("\n");
446
447     AcpiNsCheckParameterCount (Pathname, Node, ACPI_UINT32_MAX, Predefined);
448     ACPI_FREE (Pathname);
449     (*Count)++;
450
451     return (AE_OK);
452 }
453
454
455 /*******************************************************************************
456  *
457  * FUNCTION:    AcpiDbCheckPredefinedNames
458  *
459  * PARAMETERS:  None
460  *
461  * RETURN:      None
462  *
463  * DESCRIPTION: Validate all predefined names in the namespace
464  *
465  ******************************************************************************/
466
467 void
468 AcpiDbCheckPredefinedNames (
469     void)
470 {
471     UINT32                  Count = 0;
472
473
474     /* Search all nodes in namespace */
475
476     (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
477                 AcpiDbWalkForPredefinedNames, (void *) &Count, NULL);
478
479     AcpiOsPrintf ("Found %d predefined names in the namespace\n", Count);
480 }
481
482
483 /*******************************************************************************
484  *
485  * FUNCTION:    AcpiDbWalkForExecute
486  *
487  * PARAMETERS:  Callback from WalkNamespace
488  *
489  * RETURN:      Status
490  *
491  * DESCRIPTION: Batch execution module. Currently only executes predefined
492  *              ACPI names.
493  *
494  ******************************************************************************/
495
496 static ACPI_STATUS
497 AcpiDbWalkForExecute (
498     ACPI_HANDLE             ObjHandle,
499     UINT32                  NestingLevel,
500     void                    *Context,
501     void                    **ReturnValue)
502 {
503     ACPI_NAMESPACE_NODE         *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
504     UINT32                      *Count = (UINT32 *) Context;
505     const ACPI_PREDEFINED_INFO  *Predefined;
506     ACPI_BUFFER                 ReturnObj;
507     ACPI_STATUS                 Status;
508     char                        *Pathname;
509     ACPI_BUFFER             Buffer;
510     UINT32                  i;
511     ACPI_DEVICE_INFO        *ObjInfo;
512     ACPI_OBJECT_LIST        ParamObjects;
513     ACPI_OBJECT             Params[ACPI_METHOD_NUM_ARGS];
514
515
516     Predefined = AcpiNsCheckForPredefinedName (Node);
517     if (!Predefined)
518     {
519         return (AE_OK);
520     }
521
522     if (Node->Type == ACPI_TYPE_LOCAL_SCOPE)
523     {
524         return (AE_OK);
525     }
526
527     Pathname = AcpiNsGetExternalPathname (Node);
528     if (!Pathname)
529     {
530         return (AE_OK);
531     }
532
533     /* Get the object info for number of method parameters */
534
535     Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
536     Status = AcpiGetObjectInfo (ObjHandle, &Buffer);
537     if (ACPI_FAILURE (Status))
538     {
539         return (Status);
540     }
541
542     ParamObjects.Pointer = NULL;
543     ParamObjects.Count   = 0;
544
545     ObjInfo = Buffer.Pointer;
546     if (ObjInfo->Type == ACPI_TYPE_METHOD)
547     {
548
549         /* Setup default parameters */
550
551         for (i = 0; i < ObjInfo->ParamCount; i++)
552         {
553             Params[i].Type           = ACPI_TYPE_INTEGER;
554             Params[i].Integer.Value  = 1;
555         }
556
557         ParamObjects.Pointer     = Params;
558         ParamObjects.Count       = ObjInfo->ParamCount;
559     }
560
561     ACPI_FREE (Buffer.Pointer);
562
563     ReturnObj.Pointer = NULL;
564     ReturnObj.Length = ACPI_ALLOCATE_BUFFER;
565
566
567     /* Do the actual method execution */
568
569     AcpiGbl_MethodExecuting = TRUE;
570
571     Status = AcpiEvaluateObject (Node, NULL, &ParamObjects, &ReturnObj);
572
573     AcpiOsPrintf ("%-32s returned %s\n", Pathname, AcpiFormatException (Status));
574     AcpiGbl_MethodExecuting = FALSE;
575
576     ACPI_FREE (Pathname);
577     (*Count)++;
578
579     return (AE_OK);
580 }
581
582
583 /*******************************************************************************
584  *
585  * FUNCTION:    AcpiDbBatchExecute
586  *
587  * PARAMETERS:  None
588  *
589  * RETURN:      None
590  *
591  * DESCRIPTION: Namespace batch execution.
592  *
593  ******************************************************************************/
594
595 void
596 AcpiDbBatchExecute (
597     void)
598 {
599     UINT32                  Count = 0;
600
601
602     /* Search all nodes in namespace */
603
604     (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
605                 AcpiDbWalkForExecute, (void *) &Count, NULL);
606
607     AcpiOsPrintf ("Executed %d predefined names in the namespace\n", Count);
608 }
609
610
611 /*******************************************************************************
612  *
613  * FUNCTION:    AcpiDbDisplayLocks
614  *
615  * PARAMETERS:  None
616  *
617  * RETURN:      None
618  *
619  * DESCRIPTION: Display information about internal mutexes.
620  *
621  ******************************************************************************/
622
623 void
624 AcpiDbDisplayLocks (
625     void)
626 {
627     UINT32                  i;
628
629
630     for (i = 0; i < ACPI_MAX_MUTEX; i++)
631     {
632         AcpiOsPrintf ("%26s : %s\n", AcpiUtGetMutexName (i),
633             AcpiGbl_MutexInfo[i].ThreadId == ACPI_MUTEX_NOT_ACQUIRED
634                 ? "Locked" : "Unlocked");
635     }
636 }
637
638
639 /*******************************************************************************
640  *
641  * FUNCTION:    AcpiDbDisplayTableInfo
642  *
643  * PARAMETERS:  TableArg        - String with name of table to be displayed
644  *
645  * RETURN:      None
646  *
647  * DESCRIPTION: Display information about loaded tables.  Current
648  *              implementation displays all loaded tables.
649  *
650  ******************************************************************************/
651
652 void
653 AcpiDbDisplayTableInfo (
654     char                    *TableArg)
655 {
656     UINT32                  i;
657     ACPI_TABLE_DESC         *TableDesc;
658     ACPI_STATUS             Status;
659
660
661     /* Walk the entire root table list */
662
663     for (i = 0; i < AcpiGbl_RootTableList.Count; i++)
664     {
665         TableDesc = &AcpiGbl_RootTableList.Tables[i];
666         AcpiOsPrintf ("%d ", i);
667
668         /* Make sure that the table is mapped */
669
670         Status = AcpiTbVerifyTable (TableDesc);
671         if (ACPI_FAILURE (Status))
672         {
673             return;
674         }
675
676         /* Dump the table header */
677
678         if (TableDesc->Pointer)
679         {
680             AcpiTbPrintTableHeader (TableDesc->Address, TableDesc->Pointer);
681         }
682         else
683         {
684             /* If the pointer is null, the table has been unloaded */
685
686             ACPI_INFO ((AE_INFO, "%4.4s - Table has been unloaded",
687                 TableDesc->Signature.Ascii));
688         }
689     }
690 }
691
692
693 /*******************************************************************************
694  *
695  * FUNCTION:    AcpiDbUnloadAcpiTable
696  *
697  * PARAMETERS:  TableArg        - Name of the table to be unloaded
698  *              InstanceArg     - Which instance of the table to unload (if
699  *                                there are multiple tables of the same type)
700  *
701  * RETURN:      Nonde
702  *
703  * DESCRIPTION: Unload an ACPI table.
704  *              Instance is not implemented
705  *
706  ******************************************************************************/
707
708 void
709 AcpiDbUnloadAcpiTable (
710     char                    *TableArg,
711     char                    *InstanceArg)
712 {
713 /* TBD: Need to reimplement for new data structures */
714
715 #if 0
716     UINT32                  i;
717     ACPI_STATUS             Status;
718
719
720     /* Search all tables for the target type */
721
722     for (i = 0; i < (ACPI_TABLE_ID_MAX+1); i++)
723     {
724         if (!ACPI_STRNCMP (TableArg, AcpiGbl_TableData[i].Signature,
725                 AcpiGbl_TableData[i].SigLength))
726         {
727             /* Found the table, unload it */
728
729             Status = AcpiUnloadTable (i);
730             if (ACPI_SUCCESS (Status))
731             {
732                 AcpiOsPrintf ("[%s] unloaded and uninstalled\n", TableArg);
733             }
734             else
735             {
736                 AcpiOsPrintf ("%s, while unloading [%s]\n",
737                     AcpiFormatException (Status), TableArg);
738             }
739
740             return;
741         }
742     }
743
744     AcpiOsPrintf ("Unknown table type [%s]\n", TableArg);
745 #endif
746 }
747
748
749 /*******************************************************************************
750  *
751  * FUNCTION:    AcpiDbSetMethodBreakpoint
752  *
753  * PARAMETERS:  Location            - AML offset of breakpoint
754  *              WalkState           - Current walk info
755  *              Op                  - Current Op (from parse walk)
756  *
757  * RETURN:      None
758  *
759  * DESCRIPTION: Set a breakpoint in a control method at the specified
760  *              AML offset
761  *
762  ******************************************************************************/
763
764 void
765 AcpiDbSetMethodBreakpoint (
766     char                    *Location,
767     ACPI_WALK_STATE         *WalkState,
768     ACPI_PARSE_OBJECT       *Op)
769 {
770     UINT32                  Address;
771
772
773     if (!Op)
774     {
775         AcpiOsPrintf ("There is no method currently executing\n");
776         return;
777     }
778
779     /* Get and verify the breakpoint address */
780
781     Address = ACPI_STRTOUL (Location, NULL, 16);
782     if (Address <= Op->Common.AmlOffset)
783     {
784         AcpiOsPrintf ("Breakpoint %X is beyond current address %X\n",
785             Address, Op->Common.AmlOffset);
786     }
787
788     /* Save breakpoint in current walk */
789
790     WalkState->UserBreakpoint = Address;
791     AcpiOsPrintf ("Breakpoint set at AML offset %X\n", Address);
792 }
793
794
795 /*******************************************************************************
796  *
797  * FUNCTION:    AcpiDbSetMethodCallBreakpoint
798  *
799  * PARAMETERS:  Op                  - Current Op (from parse walk)
800  *
801  * RETURN:      None
802  *
803  * DESCRIPTION: Set a breakpoint in a control method at the specified
804  *              AML offset
805  *
806  ******************************************************************************/
807
808 void
809 AcpiDbSetMethodCallBreakpoint (
810     ACPI_PARSE_OBJECT       *Op)
811 {
812
813
814     if (!Op)
815     {
816         AcpiOsPrintf ("There is no method currently executing\n");
817         return;
818     }
819
820     AcpiGbl_StepToNextCall = TRUE;
821 }
822
823
824 /*******************************************************************************
825  *
826  * FUNCTION:    AcpiDbDisassembleAml
827  *
828  * PARAMETERS:  Statements          - Number of statements to disassemble
829  *              Op                  - Current Op (from parse walk)
830  *
831  * RETURN:      None
832  *
833  * DESCRIPTION: Display disassembled AML (ASL) starting from Op for the number
834  *              of statements specified.
835  *
836  ******************************************************************************/
837
838 void
839 AcpiDbDisassembleAml (
840     char                    *Statements,
841     ACPI_PARSE_OBJECT       *Op)
842 {
843     UINT32                  NumStatements = 8;
844
845
846     if (!Op)
847     {
848         AcpiOsPrintf ("There is no method currently executing\n");
849         return;
850     }
851
852     if (Statements)
853     {
854         NumStatements = ACPI_STRTOUL (Statements, NULL, 0);
855     }
856
857 #ifdef ACPI_DISASSEMBLER
858     AcpiDmDisassemble (NULL, Op, NumStatements);
859 #endif
860 }
861
862
863 /*******************************************************************************
864  *
865  * FUNCTION:    AcpiDbDisassembleMethod
866  *
867  * PARAMETERS:  Name            - Name of control method
868  *
869  * RETURN:      None
870  *
871  * DESCRIPTION: Display disassembled AML (ASL) starting from Op for the number
872  *              of statements specified.
873  *
874  ******************************************************************************/
875
876 ACPI_STATUS
877 AcpiDbDisassembleMethod (
878     char                    *Name)
879 {
880     ACPI_STATUS             Status;
881     ACPI_PARSE_OBJECT       *Op;
882     ACPI_WALK_STATE         *WalkState;
883     ACPI_OPERAND_OBJECT     *ObjDesc;
884     ACPI_NAMESPACE_NODE     *Method;
885
886
887     Method = AcpiDbConvertToNode (Name);
888     if (!Method)
889     {
890         return (AE_BAD_PARAMETER);
891     }
892
893     ObjDesc = Method->Object;
894
895     Op = AcpiPsCreateScopeOp ();
896     if (!Op)
897     {
898         return (AE_NO_MEMORY);
899     }
900
901     /* Create and initialize a new walk state */
902
903     WalkState = AcpiDsCreateWalkState (0, Op, NULL, NULL);
904     if (!WalkState)
905     {
906         return (AE_NO_MEMORY);
907     }
908
909     Status = AcpiDsInitAmlWalk (WalkState, Op, NULL,
910                     ObjDesc->Method.AmlStart,
911                     ObjDesc->Method.AmlLength, NULL, ACPI_IMODE_LOAD_PASS1);
912     if (ACPI_FAILURE (Status))
913     {
914         return (Status);
915     }
916
917     /* Parse the AML */
918
919     WalkState->ParseFlags &= ~ACPI_PARSE_DELETE_TREE;
920     WalkState->ParseFlags |= ACPI_PARSE_DISASSEMBLE;
921     Status = AcpiPsParseAml (WalkState);
922
923 #ifdef ACPI_DISASSEMBLER
924     AcpiDmDisassemble (NULL, Op, 0);
925 #endif
926     AcpiPsDeleteParseTree (Op);
927     return (AE_OK);
928 }
929
930
931 /*******************************************************************************
932  *
933  * FUNCTION:    AcpiDbDumpNamespace
934  *
935  * PARAMETERS:  StartArg        - Node to begin namespace dump
936  *              DepthArg        - Maximum tree depth to be dumped
937  *
938  * RETURN:      None
939  *
940  * DESCRIPTION: Dump entire namespace or a subtree.  Each node is displayed
941  *              with type and other information.
942  *
943  ******************************************************************************/
944
945 void
946 AcpiDbDumpNamespace (
947     char                    *StartArg,
948     char                    *DepthArg)
949 {
950     ACPI_HANDLE             SubtreeEntry = AcpiGbl_RootNode;
951     UINT32                  MaxDepth = ACPI_UINT32_MAX;
952
953
954     /* No argument given, just start at the root and dump entire namespace */
955
956     if (StartArg)
957     {
958         SubtreeEntry = AcpiDbConvertToNode (StartArg);
959         if (!SubtreeEntry)
960         {
961             return;
962         }
963
964         /* Now we can check for the depth argument */
965
966         if (DepthArg)
967         {
968             MaxDepth = ACPI_STRTOUL (DepthArg, NULL, 0);
969         }
970     }
971
972     AcpiDbSetOutputDestination (ACPI_DB_DUPLICATE_OUTPUT);
973     AcpiOsPrintf ("ACPI Namespace (from %4.4s (%p) subtree):\n",
974         ((ACPI_NAMESPACE_NODE *) SubtreeEntry)->Name.Ascii, SubtreeEntry);
975
976     /* Display the subtree */
977
978     AcpiDbSetOutputDestination (ACPI_DB_REDIRECTABLE_OUTPUT);
979     AcpiNsDumpObjects (ACPI_TYPE_ANY, ACPI_DISPLAY_SUMMARY, MaxDepth,
980         ACPI_OWNER_ID_MAX, SubtreeEntry);
981     AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
982 }
983
984
985 /*******************************************************************************
986  *
987  * FUNCTION:    AcpiDbDumpNamespaceByOwner
988  *
989  * PARAMETERS:  OwnerArg        - Owner ID whose nodes will be displayed
990  *              DepthArg        - Maximum tree depth to be dumped
991  *
992  * RETURN:      None
993  *
994  * DESCRIPTION: Dump elements of the namespace that are owned by the OwnerId.
995  *
996  ******************************************************************************/
997
998 void
999 AcpiDbDumpNamespaceByOwner (
1000     char                    *OwnerArg,
1001     char                    *DepthArg)
1002 {
1003     ACPI_HANDLE             SubtreeEntry = AcpiGbl_RootNode;
1004     UINT32                  MaxDepth = ACPI_UINT32_MAX;
1005     ACPI_OWNER_ID           OwnerId;
1006
1007
1008     OwnerId = (ACPI_OWNER_ID) ACPI_STRTOUL (OwnerArg, NULL, 0);
1009
1010     /* Now we can check for the depth argument */
1011
1012     if (DepthArg)
1013     {
1014         MaxDepth = ACPI_STRTOUL (DepthArg, NULL, 0);
1015     }
1016
1017     AcpiDbSetOutputDestination (ACPI_DB_DUPLICATE_OUTPUT);
1018     AcpiOsPrintf ("ACPI Namespace by owner %X:\n", OwnerId);
1019
1020     /* Display the subtree */
1021
1022     AcpiDbSetOutputDestination (ACPI_DB_REDIRECTABLE_OUTPUT);
1023     AcpiNsDumpObjects (ACPI_TYPE_ANY, ACPI_DISPLAY_SUMMARY, MaxDepth, OwnerId,
1024         SubtreeEntry);
1025     AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
1026 }
1027
1028
1029 /*******************************************************************************
1030  *
1031  * FUNCTION:    AcpiDbSendNotify
1032  *
1033  * PARAMETERS:  Name            - Name of ACPI object to send the notify to
1034  *              Value           - Value of the notify to send.
1035  *
1036  * RETURN:      None
1037  *
1038  * DESCRIPTION: Send an ACPI notification.  The value specified is sent to the
1039  *              named object as an ACPI notify.
1040  *
1041  ******************************************************************************/
1042
1043 void
1044 AcpiDbSendNotify (
1045     char                    *Name,
1046     UINT32                  Value)
1047 {
1048     ACPI_NAMESPACE_NODE     *Node;
1049     ACPI_STATUS             Status;
1050
1051
1052     /* Translate name to an Named object */
1053
1054     Node = AcpiDbConvertToNode (Name);
1055     if (!Node)
1056     {
1057         return;
1058     }
1059
1060     /* Decode Named object type */
1061
1062     switch (Node->Type)
1063     {
1064     case ACPI_TYPE_DEVICE:
1065     case ACPI_TYPE_THERMAL:
1066
1067          /* Send the notify */
1068
1069         Status = AcpiEvQueueNotifyRequest (Node, Value);
1070         if (ACPI_FAILURE (Status))
1071         {
1072             AcpiOsPrintf ("Could not queue notify\n");
1073         }
1074         break;
1075
1076     default:
1077         AcpiOsPrintf ("Named object is not a device or a thermal object\n");
1078         break;
1079     }
1080 }
1081
1082
1083 /*******************************************************************************
1084  *
1085  * FUNCTION:    AcpiDbSetMethodData
1086  *
1087  * PARAMETERS:  TypeArg         - L for local, A for argument
1088  *              IndexArg        - which one
1089  *              ValueArg        - Value to set.
1090  *
1091  * RETURN:      None
1092  *
1093  * DESCRIPTION: Set a local or argument for the running control method.
1094  *              NOTE: only object supported is Number.
1095  *
1096  ******************************************************************************/
1097
1098 void
1099 AcpiDbSetMethodData (
1100     char                    *TypeArg,
1101     char                    *IndexArg,
1102     char                    *ValueArg)
1103 {
1104     char                    Type;
1105     UINT32                  Index;
1106     UINT32                  Value;
1107     ACPI_WALK_STATE         *WalkState;
1108     ACPI_OPERAND_OBJECT     *ObjDesc;
1109     ACPI_STATUS             Status;
1110     ACPI_NAMESPACE_NODE     *Node;
1111
1112
1113     /* Validate TypeArg */
1114
1115     AcpiUtStrupr (TypeArg);
1116     Type = TypeArg[0];
1117     if ((Type != 'L') &&
1118         (Type != 'A') &&
1119         (Type != 'N'))
1120     {
1121         AcpiOsPrintf ("Invalid SET operand: %s\n", TypeArg);
1122         return;
1123     }
1124
1125     Value = ACPI_STRTOUL (ValueArg, NULL, 16);
1126
1127     if (Type == 'N')
1128     {
1129         Node = AcpiDbConvertToNode (IndexArg);
1130         if (Node->Type != ACPI_TYPE_INTEGER)
1131         {
1132             AcpiOsPrintf ("Can only set Integer nodes\n");
1133             return;
1134         }
1135         ObjDesc = Node->Object;
1136         ObjDesc->Integer.Value = Value;
1137         return;
1138     }
1139
1140     /* Get the index and value */
1141
1142     Index = ACPI_STRTOUL (IndexArg, NULL, 16);
1143
1144     WalkState = AcpiDsGetCurrentWalkState (AcpiGbl_CurrentWalkList);
1145     if (!WalkState)
1146     {
1147         AcpiOsPrintf ("There is no method currently executing\n");
1148         return;
1149     }
1150
1151     /* Create and initialize the new object */
1152
1153     ObjDesc = AcpiUtCreateInternalObject (ACPI_TYPE_INTEGER);
1154     if (!ObjDesc)
1155     {
1156         AcpiOsPrintf ("Could not create an internal object\n");
1157         return;
1158     }
1159
1160     ObjDesc->Integer.Value = Value;
1161
1162     /* Store the new object into the target */
1163
1164     switch (Type)
1165     {
1166     case 'A':
1167
1168         /* Set a method argument */
1169
1170         if (Index > ACPI_METHOD_MAX_ARG)
1171         {
1172             AcpiOsPrintf ("Arg%d - Invalid argument name\n", Index);
1173             goto Cleanup;
1174         }
1175
1176         Status = AcpiDsStoreObjectToLocal (ACPI_REFCLASS_ARG, Index, ObjDesc,
1177                     WalkState);
1178         if (ACPI_FAILURE (Status))
1179         {
1180             goto Cleanup;
1181         }
1182
1183         ObjDesc = WalkState->Arguments[Index].Object;
1184
1185         AcpiOsPrintf ("Arg%d: ", Index);
1186         AcpiDmDisplayInternalObject (ObjDesc, WalkState);
1187         break;
1188
1189     case 'L':
1190
1191         /* Set a method local */
1192
1193         if (Index > ACPI_METHOD_MAX_LOCAL)
1194         {
1195             AcpiOsPrintf ("Local%d - Invalid local variable name\n", Index);
1196             goto Cleanup;
1197         }
1198
1199         Status = AcpiDsStoreObjectToLocal (ACPI_REFCLASS_LOCAL, Index, ObjDesc,
1200                     WalkState);
1201         if (ACPI_FAILURE (Status))
1202         {
1203             goto Cleanup;
1204         }
1205
1206         ObjDesc = WalkState->LocalVariables[Index].Object;
1207
1208         AcpiOsPrintf ("Local%d: ", Index);
1209         AcpiDmDisplayInternalObject (ObjDesc, WalkState);
1210         break;
1211
1212     default:
1213         break;
1214     }
1215
1216 Cleanup:
1217     AcpiUtRemoveReference (ObjDesc);
1218 }
1219
1220
1221 /*******************************************************************************
1222  *
1223  * FUNCTION:    AcpiDbWalkForSpecificObjects
1224  *
1225  * PARAMETERS:  Callback from WalkNamespace
1226  *
1227  * RETURN:      Status
1228  *
1229  * DESCRIPTION: Display short info about objects in the namespace
1230  *
1231  ******************************************************************************/
1232
1233 static ACPI_STATUS
1234 AcpiDbWalkForSpecificObjects (
1235     ACPI_HANDLE             ObjHandle,
1236     UINT32                  NestingLevel,
1237     void                    *Context,
1238     void                    **ReturnValue)
1239 {
1240     ACPI_WALK_INFO          *Info = (ACPI_WALK_INFO *) Context;
1241     ACPI_BUFFER             Buffer;
1242     ACPI_STATUS             Status;
1243
1244
1245     Info->Count++;
1246
1247     /* Get and display the full pathname to this object */
1248
1249     Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
1250     Status = AcpiNsHandleToPathname (ObjHandle, &Buffer);
1251     if (ACPI_FAILURE (Status))
1252     {
1253         AcpiOsPrintf ("Could Not get pathname for object %p\n", ObjHandle);
1254         return (AE_OK);
1255     }
1256
1257     AcpiOsPrintf ("%32s", (char *) Buffer.Pointer);
1258     ACPI_FREE (Buffer.Pointer);
1259
1260     /* Dump short info about the object */
1261
1262     (void) AcpiNsDumpOneObject (ObjHandle, NestingLevel, Info, NULL);
1263     return (AE_OK);
1264 }
1265
1266
1267 /*******************************************************************************
1268  *
1269  * FUNCTION:    AcpiDbDisplayObjects
1270  *
1271  * PARAMETERS:  ObjTypeArg          - Type of object to display
1272  *              DisplayCountArg     - Max depth to display
1273  *
1274  * RETURN:      None
1275  *
1276  * DESCRIPTION: Display objects in the namespace of the requested type
1277  *
1278  ******************************************************************************/
1279
1280 ACPI_STATUS
1281 AcpiDbDisplayObjects (
1282     char                    *ObjTypeArg,
1283     char                    *DisplayCountArg)
1284 {
1285     ACPI_WALK_INFO          Info;
1286     ACPI_OBJECT_TYPE        Type;
1287
1288
1289     /* Get the object type */
1290
1291     Type = AcpiDbMatchArgument (ObjTypeArg, AcpiDbObjectTypes);
1292     if (Type == ACPI_TYPE_NOT_FOUND)
1293     {
1294         AcpiOsPrintf ("Invalid or unsupported argument\n");
1295         return (AE_OK);
1296     }
1297
1298     AcpiDbSetOutputDestination (ACPI_DB_DUPLICATE_OUTPUT);
1299     AcpiOsPrintf (
1300         "Objects of type [%s] defined in the current ACPI Namespace:\n",
1301         AcpiUtGetTypeName (Type));
1302
1303     AcpiDbSetOutputDestination (ACPI_DB_REDIRECTABLE_OUTPUT);
1304
1305     Info.Count = 0;
1306     Info.OwnerId = ACPI_OWNER_ID_MAX;
1307     Info.DebugLevel = ACPI_UINT32_MAX;
1308     Info.DisplayType = ACPI_DISPLAY_SUMMARY | ACPI_DISPLAY_SHORT;
1309
1310     /* Walk the namespace from the root */
1311
1312     (void) AcpiWalkNamespace (Type, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
1313                 AcpiDbWalkForSpecificObjects, (void *) &Info, NULL);
1314
1315     AcpiOsPrintf (
1316         "\nFound %u objects of type [%s] in the current ACPI Namespace\n",
1317         Info.Count, AcpiUtGetTypeName (Type));
1318
1319     AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
1320     return (AE_OK);
1321 }
1322
1323
1324 /*******************************************************************************
1325  *
1326  * FUNCTION:    AcpiDbWalkAndMatchName
1327  *
1328  * PARAMETERS:  Callback from WalkNamespace
1329  *
1330  * RETURN:      Status
1331  *
1332  * DESCRIPTION: Find a particular name/names within the namespace.  Wildcards
1333  *              are supported -- '?' matches any character.
1334  *
1335  ******************************************************************************/
1336
1337 static ACPI_STATUS
1338 AcpiDbWalkAndMatchName (
1339     ACPI_HANDLE             ObjHandle,
1340     UINT32                  NestingLevel,
1341     void                    *Context,
1342     void                    **ReturnValue)
1343 {
1344     ACPI_STATUS             Status;
1345     char                    *RequestedName = (char *) Context;
1346     UINT32                  i;
1347     ACPI_BUFFER             Buffer;
1348     ACPI_WALK_INFO          Info;
1349
1350
1351     /* Check for a name match */
1352
1353     for (i = 0; i < 4; i++)
1354     {
1355         /* Wildcard support */
1356
1357         if ((RequestedName[i] != '?') &&
1358             (RequestedName[i] != ((ACPI_NAMESPACE_NODE *) ObjHandle)->Name.Ascii[i]))
1359         {
1360             /* No match, just exit */
1361
1362             return (AE_OK);
1363         }
1364     }
1365
1366     /* Get the full pathname to this object */
1367
1368     Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
1369     Status = AcpiNsHandleToPathname (ObjHandle, &Buffer);
1370     if (ACPI_FAILURE (Status))
1371     {
1372         AcpiOsPrintf ("Could Not get pathname for object %p\n", ObjHandle);
1373     }
1374     else
1375     {
1376         Info.OwnerId = ACPI_OWNER_ID_MAX;
1377         Info.DebugLevel = ACPI_UINT32_MAX;
1378         Info.DisplayType = ACPI_DISPLAY_SUMMARY | ACPI_DISPLAY_SHORT;
1379
1380         AcpiOsPrintf ("%32s", (char *) Buffer.Pointer);
1381         (void) AcpiNsDumpOneObject (ObjHandle, NestingLevel, &Info, NULL);
1382         ACPI_FREE (Buffer.Pointer);
1383     }
1384
1385     return (AE_OK);
1386 }
1387
1388
1389 /*******************************************************************************
1390  *
1391  * FUNCTION:    AcpiDbFindNameInNamespace
1392  *
1393  * PARAMETERS:  NameArg         - The 4-character ACPI name to find.
1394  *                                wildcards are supported.
1395  *
1396  * RETURN:      None
1397  *
1398  * DESCRIPTION: Search the namespace for a given name (with wildcards)
1399  *
1400  ******************************************************************************/
1401
1402 ACPI_STATUS
1403 AcpiDbFindNameInNamespace (
1404     char                    *NameArg)
1405 {
1406     char                    AcpiName[5] = "____";
1407     char                    *AcpiNamePtr = AcpiName;
1408
1409
1410     if (ACPI_STRLEN (NameArg) > 4)
1411     {
1412         AcpiOsPrintf ("Name must be no longer than 4 characters\n");
1413         return (AE_OK);
1414     }
1415
1416     /* Pad out name with underscores as necessary to create a 4-char name */
1417
1418     AcpiUtStrupr (NameArg);
1419     while (*NameArg)
1420     {
1421         *AcpiNamePtr = *NameArg;
1422         AcpiNamePtr++;
1423         NameArg++;
1424     }
1425
1426     /* Walk the namespace from the root */
1427
1428     (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
1429                         AcpiDbWalkAndMatchName, AcpiName, NULL);
1430
1431     AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
1432     return (AE_OK);
1433 }
1434
1435
1436 /*******************************************************************************
1437  *
1438  * FUNCTION:    AcpiDbSetScope
1439  *
1440  * PARAMETERS:  Name                - New scope path
1441  *
1442  * RETURN:      Status
1443  *
1444  * DESCRIPTION: Set the "current scope" as maintained by this utility.
1445  *              The scope is used as a prefix to ACPI paths.
1446  *
1447  ******************************************************************************/
1448
1449 void
1450 AcpiDbSetScope (
1451     char                    *Name)
1452 {
1453     ACPI_STATUS             Status;
1454     ACPI_NAMESPACE_NODE     *Node;
1455
1456
1457     if (!Name || Name[0] == 0)
1458     {
1459         AcpiOsPrintf ("Current scope: %s\n", AcpiGbl_DbScopeBuf);
1460         return;
1461     }
1462
1463     AcpiDbPrepNamestring (Name);
1464
1465     if (Name[0] == '\\')
1466     {
1467         /* Validate new scope from the root */
1468
1469         Status = AcpiNsGetNode (AcpiGbl_RootNode, Name, ACPI_NS_NO_UPSEARCH,
1470                     &Node);
1471         if (ACPI_FAILURE (Status))
1472         {
1473             goto ErrorExit;
1474         }
1475
1476         ACPI_STRCPY (AcpiGbl_DbScopeBuf, Name);
1477         ACPI_STRCAT (AcpiGbl_DbScopeBuf, "\\");
1478     }
1479     else
1480     {
1481         /* Validate new scope relative to old scope */
1482
1483         Status = AcpiNsGetNode (AcpiGbl_DbScopeNode, Name, ACPI_NS_NO_UPSEARCH,
1484                     &Node);
1485         if (ACPI_FAILURE (Status))
1486         {
1487             goto ErrorExit;
1488         }
1489
1490         ACPI_STRCAT (AcpiGbl_DbScopeBuf, Name);
1491         ACPI_STRCAT (AcpiGbl_DbScopeBuf, "\\");
1492     }
1493
1494     AcpiGbl_DbScopeNode = Node;
1495     AcpiOsPrintf ("New scope: %s\n", AcpiGbl_DbScopeBuf);
1496     return;
1497
1498 ErrorExit:
1499
1500     AcpiOsPrintf ("Could not attach scope: %s, %s\n",
1501         Name, AcpiFormatException (Status));
1502 }
1503
1504
1505 /*******************************************************************************
1506  *
1507  * FUNCTION:    AcpiDmCompareAmlResources
1508  *
1509  * PARAMETERS:  Aml1Buffer          - Contains first resource list
1510  *              Aml1BufferLength    - Length of first resource list
1511  *              Aml2Buffer          - Contains second resource list
1512  *              Aml2BufferLength    - Length of second resource list
1513  *
1514  * RETURN:      None
1515  *
1516  * DESCRIPTION: Compare two AML resource lists, descriptor by descriptor (in
1517  *              order to isolate a miscompare to an individual resource)
1518  *
1519  ******************************************************************************/
1520
1521 static void
1522 AcpiDmCompareAmlResources (
1523     UINT8                   *Aml1Buffer,
1524     ACPI_RSDESC_SIZE        Aml1BufferLength,
1525     UINT8                   *Aml2Buffer,
1526     ACPI_RSDESC_SIZE        Aml2BufferLength)
1527 {
1528     UINT8                   *Aml1;
1529     UINT8                   *Aml2;
1530     ACPI_RSDESC_SIZE        Aml1Length;
1531     ACPI_RSDESC_SIZE        Aml2Length;
1532     ACPI_RSDESC_SIZE        Offset = 0;
1533     UINT8                   ResourceType;
1534     UINT32                  Count = 0;
1535
1536
1537     /* Compare overall buffer sizes (may be different due to size rounding) */
1538
1539     if (Aml1BufferLength != Aml2BufferLength)
1540     {
1541         AcpiOsPrintf (
1542             "**** Buffer length mismatch in converted AML: original %X new %X ****\n",
1543             Aml1BufferLength, Aml2BufferLength);
1544     }
1545
1546     Aml1 = Aml1Buffer;
1547     Aml2 = Aml2Buffer;
1548
1549     /* Walk the descriptor lists, comparing each descriptor */
1550
1551     while (Aml1 < (Aml1Buffer + Aml1BufferLength))
1552     {
1553         /* Get the lengths of each descriptor */
1554
1555         Aml1Length = AcpiUtGetDescriptorLength (Aml1);
1556         Aml2Length = AcpiUtGetDescriptorLength (Aml2);
1557         ResourceType = AcpiUtGetResourceType (Aml1);
1558
1559         /* Check for descriptor length match */
1560
1561         if (Aml1Length != Aml2Length)
1562         {
1563             AcpiOsPrintf (
1564                 "**** Length mismatch in descriptor [%.2X] type %2.2X, Offset %8.8X L1 %X L2 %X ****\n",
1565                 Count, ResourceType, Offset, Aml1Length, Aml2Length);
1566         }
1567
1568         /* Check for descriptor byte match */
1569
1570         else if (ACPI_MEMCMP (Aml1, Aml2, Aml1Length))
1571         {
1572             AcpiOsPrintf (
1573                 "**** Data mismatch in descriptor [%.2X] type %2.2X, Offset %8.8X ****\n",
1574                 Count, ResourceType, Offset);
1575         }
1576
1577         /* Exit on EndTag descriptor */
1578
1579         if (ResourceType == ACPI_RESOURCE_NAME_END_TAG)
1580         {
1581             return;
1582         }
1583
1584         /* Point to next descriptor in each buffer */
1585
1586         Count++;
1587         Offset += Aml1Length;
1588         Aml1 += Aml1Length;
1589         Aml2 += Aml2Length;
1590     }
1591 }
1592
1593
1594 /*******************************************************************************
1595  *
1596  * FUNCTION:    AcpiDmTestResourceConversion
1597  *
1598  * PARAMETERS:  Node            - Parent device node
1599  *              Name            - resource method name (_CRS)
1600  *
1601  * RETURN:      Status
1602  *
1603  * DESCRIPTION: Compare the original AML with a conversion of the AML to
1604  *              internal resource list, then back to AML.
1605  *
1606  ******************************************************************************/
1607
1608 static ACPI_STATUS
1609 AcpiDmTestResourceConversion (
1610     ACPI_NAMESPACE_NODE     *Node,
1611     char                    *Name)
1612 {
1613     ACPI_STATUS             Status;
1614     ACPI_BUFFER             ReturnObj;
1615     ACPI_BUFFER             ResourceObj;
1616     ACPI_BUFFER             NewAml;
1617     ACPI_OBJECT             *OriginalAml;
1618
1619
1620     AcpiOsPrintf ("Resource Conversion Comparison:\n");
1621
1622     NewAml.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
1623     ReturnObj.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
1624     ResourceObj.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
1625
1626     /* Get the original _CRS AML resource template */
1627
1628     Status = AcpiEvaluateObject (Node, Name, NULL, &ReturnObj);
1629     if (ACPI_FAILURE (Status))
1630     {
1631         AcpiOsPrintf ("Could not obtain %s: %s\n",
1632             Name, AcpiFormatException (Status));
1633         return (Status);
1634     }
1635
1636     /* Get the AML resource template, converted to internal resource structs */
1637
1638     Status = AcpiGetCurrentResources (Node, &ResourceObj);
1639     if (ACPI_FAILURE (Status))
1640     {
1641         AcpiOsPrintf ("AcpiGetCurrentResources failed: %s\n",
1642             AcpiFormatException (Status));
1643         goto Exit1;
1644     }
1645
1646     /* Convert internal resource list to external AML resource template */
1647
1648     Status = AcpiRsCreateAmlResources (ResourceObj.Pointer, &NewAml);
1649     if (ACPI_FAILURE (Status))
1650     {
1651         AcpiOsPrintf ("AcpiRsCreateAmlResources failed: %s\n",
1652             AcpiFormatException (Status));
1653         goto Exit2;
1654     }
1655
1656     /* Compare original AML to the newly created AML resource list */
1657
1658     OriginalAml = ReturnObj.Pointer;
1659
1660     AcpiDmCompareAmlResources (
1661         OriginalAml->Buffer.Pointer, (ACPI_RSDESC_SIZE) OriginalAml->Buffer.Length,
1662         NewAml.Pointer, (ACPI_RSDESC_SIZE) NewAml.Length);
1663
1664     /* Cleanup and exit */
1665
1666     ACPI_FREE (NewAml.Pointer);
1667 Exit2:
1668     ACPI_FREE (ResourceObj.Pointer);
1669 Exit1:
1670     ACPI_FREE (ReturnObj.Pointer);
1671     return (Status);
1672 }
1673
1674
1675 /*******************************************************************************
1676  *
1677  * FUNCTION:    AcpiDbDisplayResources
1678  *
1679  * PARAMETERS:  ObjectArg       - String with hex value of the object
1680  *
1681  * RETURN:      None
1682  *
1683  * DESCRIPTION: Display the resource objects associated with a device.
1684  *
1685  ******************************************************************************/
1686
1687 void
1688 AcpiDbDisplayResources (
1689     char                    *ObjectArg)
1690 {
1691     ACPI_NAMESPACE_NODE     *Node;
1692     ACPI_STATUS             Status;
1693     ACPI_BUFFER             ReturnObj;
1694
1695
1696     AcpiDbSetOutputDestination (ACPI_DB_REDIRECTABLE_OUTPUT);
1697     AcpiDbgLevel |= ACPI_LV_RESOURCES;
1698
1699     /* Convert string to object pointer */
1700
1701     Node = AcpiDbConvertToNode (ObjectArg);
1702     if (!Node)
1703     {
1704         return;
1705     }
1706
1707     /* Prepare for a return object of arbitrary size */
1708
1709     ReturnObj.Pointer = AcpiGbl_DbBuffer;
1710     ReturnObj.Length  = ACPI_DEBUG_BUFFER_SIZE;
1711
1712     /* _PRT */
1713
1714     AcpiOsPrintf ("Evaluating _PRT\n");
1715
1716     /* Check if _PRT exists */
1717
1718     Status = AcpiEvaluateObject (Node, METHOD_NAME__PRT, NULL, &ReturnObj);
1719     if (ACPI_FAILURE (Status))
1720     {
1721         AcpiOsPrintf ("Could not obtain _PRT: %s\n",
1722             AcpiFormatException (Status));
1723         goto GetCrs;
1724     }
1725
1726     ReturnObj.Pointer = AcpiGbl_DbBuffer;
1727     ReturnObj.Length  = ACPI_DEBUG_BUFFER_SIZE;
1728
1729     Status = AcpiGetIrqRoutingTable (Node, &ReturnObj);
1730     if (ACPI_FAILURE (Status))
1731     {
1732         AcpiOsPrintf ("GetIrqRoutingTable failed: %s\n",
1733             AcpiFormatException (Status));
1734         goto GetCrs;
1735     }
1736
1737     AcpiRsDumpIrqList (ACPI_CAST_PTR (UINT8, AcpiGbl_DbBuffer));
1738
1739
1740     /* _CRS */
1741
1742 GetCrs:
1743     AcpiOsPrintf ("Evaluating _CRS\n");
1744
1745     ReturnObj.Pointer = AcpiGbl_DbBuffer;
1746     ReturnObj.Length  = ACPI_DEBUG_BUFFER_SIZE;
1747
1748     /* Check if _CRS exists */
1749
1750     Status = AcpiEvaluateObject (Node, METHOD_NAME__CRS, NULL, &ReturnObj);
1751     if (ACPI_FAILURE (Status))
1752     {
1753         AcpiOsPrintf ("Could not obtain _CRS: %s\n",
1754             AcpiFormatException (Status));
1755         goto GetPrs;
1756     }
1757
1758     /* Get the _CRS resource list */
1759
1760     ReturnObj.Pointer = AcpiGbl_DbBuffer;
1761     ReturnObj.Length  = ACPI_DEBUG_BUFFER_SIZE;
1762
1763     Status = AcpiGetCurrentResources (Node, &ReturnObj);
1764     if (ACPI_FAILURE (Status))
1765     {
1766         AcpiOsPrintf ("AcpiGetCurrentResources failed: %s\n",
1767             AcpiFormatException (Status));
1768         goto GetPrs;
1769     }
1770
1771     /* Dump the _CRS resource list */
1772
1773     AcpiRsDumpResourceList (ACPI_CAST_PTR (ACPI_RESOURCE,
1774         ReturnObj.Pointer));
1775
1776     /*
1777      * Perform comparison of original AML to newly created AML. This tests both
1778      * the AML->Resource conversion and the Resource->Aml conversion.
1779      */
1780     Status = AcpiDmTestResourceConversion (Node, METHOD_NAME__CRS);
1781
1782     /* Execute _SRS with the resource list */
1783
1784     Status = AcpiSetCurrentResources (Node, &ReturnObj);
1785     if (ACPI_FAILURE (Status))
1786     {
1787         AcpiOsPrintf ("AcpiSetCurrentResources failed: %s\n",
1788             AcpiFormatException (Status));
1789         goto GetPrs;
1790     }
1791
1792
1793     /* _PRS */
1794
1795 GetPrs:
1796     AcpiOsPrintf ("Evaluating _PRS\n");
1797
1798     ReturnObj.Pointer = AcpiGbl_DbBuffer;
1799     ReturnObj.Length  = ACPI_DEBUG_BUFFER_SIZE;
1800
1801     /* Check if _PRS exists */
1802
1803     Status = AcpiEvaluateObject (Node, METHOD_NAME__PRS, NULL, &ReturnObj);
1804     if (ACPI_FAILURE (Status))
1805     {
1806         AcpiOsPrintf ("Could not obtain _PRS: %s\n",
1807             AcpiFormatException (Status));
1808         goto Cleanup;
1809     }
1810
1811     ReturnObj.Pointer = AcpiGbl_DbBuffer;
1812     ReturnObj.Length  = ACPI_DEBUG_BUFFER_SIZE;
1813
1814     Status = AcpiGetPossibleResources (Node, &ReturnObj);
1815     if (ACPI_FAILURE (Status))
1816     {
1817         AcpiOsPrintf ("AcpiGetPossibleResources failed: %s\n",
1818             AcpiFormatException (Status));
1819         goto Cleanup;
1820     }
1821
1822     AcpiRsDumpResourceList (ACPI_CAST_PTR (ACPI_RESOURCE, AcpiGbl_DbBuffer));
1823
1824 Cleanup:
1825
1826     AcpiDbSetOutputDestination (ACPI_DB_CONSOLE_OUTPUT);
1827     return;
1828 }
1829
1830
1831 /*******************************************************************************
1832  *
1833  * FUNCTION:    AcpiDbIntegrityWalk
1834  *
1835  * PARAMETERS:  Callback from WalkNamespace
1836  *
1837  * RETURN:      Status
1838  *
1839  * DESCRIPTION: Examine one NS node for valid values.
1840  *
1841  ******************************************************************************/
1842
1843 static ACPI_STATUS
1844 AcpiDbIntegrityWalk (
1845     ACPI_HANDLE             ObjHandle,
1846     UINT32                  NestingLevel,
1847     void                    *Context,
1848     void                    **ReturnValue)
1849 {
1850     ACPI_INTEGRITY_INFO     *Info = (ACPI_INTEGRITY_INFO *) Context;
1851     ACPI_NAMESPACE_NODE     *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
1852     ACPI_OPERAND_OBJECT     *Object;
1853     BOOLEAN                 Alias = TRUE;
1854
1855
1856     Info->Nodes++;
1857
1858     /* Verify the NS node, and dereference aliases */
1859
1860     while (Alias)
1861     {
1862         if (ACPI_GET_DESCRIPTOR_TYPE (Node) != ACPI_DESC_TYPE_NAMED)
1863         {
1864             AcpiOsPrintf ("Invalid Descriptor Type for Node %p [%s] - is %2.2X should be %2.2X\n",
1865                 Node, AcpiUtGetDescriptorName (Node), ACPI_GET_DESCRIPTOR_TYPE (Node),
1866                 ACPI_DESC_TYPE_NAMED);
1867             return (AE_OK);
1868         }
1869
1870         if ((Node->Type == ACPI_TYPE_LOCAL_ALIAS)  ||
1871             (Node->Type == ACPI_TYPE_LOCAL_METHOD_ALIAS))
1872         {
1873             Node = (ACPI_NAMESPACE_NODE *) Node->Object;
1874         }
1875         else
1876         {
1877             Alias = FALSE;
1878         }
1879     }
1880
1881     if (Node->Type > ACPI_TYPE_LOCAL_MAX)
1882     {
1883         AcpiOsPrintf ("Invalid Object Type for Node %p, Type = %X\n",
1884             Node, Node->Type);
1885         return (AE_OK);
1886     }
1887
1888     if (!AcpiUtValidAcpiName (Node->Name.Integer))
1889     {
1890         AcpiOsPrintf ("Invalid AcpiName for Node %p\n", Node);
1891         return (AE_OK);
1892     }
1893
1894     Object = AcpiNsGetAttachedObject (Node);
1895     if (Object)
1896     {
1897         Info->Objects++;
1898         if (ACPI_GET_DESCRIPTOR_TYPE (Object) != ACPI_DESC_TYPE_OPERAND)
1899         {
1900             AcpiOsPrintf ("Invalid Descriptor Type for Object %p [%s]\n",
1901                 Object, AcpiUtGetDescriptorName (Object));
1902         }
1903     }
1904
1905     return (AE_OK);
1906 }
1907
1908
1909 /*******************************************************************************
1910  *
1911  * FUNCTION:    AcpiDbCheckIntegrity
1912  *
1913  * PARAMETERS:  None
1914  *
1915  * RETURN:      None
1916  *
1917  * DESCRIPTION: Check entire namespace for data structure integrity
1918  *
1919  ******************************************************************************/
1920
1921 void
1922 AcpiDbCheckIntegrity (
1923     void)
1924 {
1925     ACPI_INTEGRITY_INFO     Info = {0,0};
1926
1927     /* Search all nodes in namespace */
1928
1929     (void) AcpiWalkNamespace (ACPI_TYPE_ANY, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
1930                     AcpiDbIntegrityWalk, (void *) &Info, NULL);
1931
1932     AcpiOsPrintf ("Verified %d namespace nodes with %d Objects\n",
1933         Info.Nodes, Info.Objects);
1934 }
1935
1936
1937 /*******************************************************************************
1938  *
1939  * FUNCTION:    AcpiDbGenerateGpe
1940  *
1941  * PARAMETERS:  GpeArg          - Raw GPE number, ascii string
1942  *              BlockArg        - GPE block number, ascii string
1943  *                                0 or 1 for FADT GPE blocks
1944  *
1945  * RETURN:      None
1946  *
1947  * DESCRIPTION: Generate a GPE
1948  *
1949  ******************************************************************************/
1950
1951 void
1952 AcpiDbGenerateGpe (
1953     char                    *GpeArg,
1954     char                    *BlockArg)
1955 {
1956     UINT32                  BlockNumber;
1957     UINT32                  GpeNumber;
1958     ACPI_GPE_EVENT_INFO     *GpeEventInfo;
1959
1960
1961     GpeNumber   = ACPI_STRTOUL (GpeArg, NULL, 0);
1962     BlockNumber = ACPI_STRTOUL (BlockArg, NULL, 0);
1963
1964
1965     GpeEventInfo = AcpiEvGetGpeEventInfo (ACPI_TO_POINTER (BlockNumber),
1966         GpeNumber);
1967     if (!GpeEventInfo)
1968     {
1969         AcpiOsPrintf ("Invalid GPE\n");
1970         return;
1971     }
1972
1973     (void) AcpiEvGpeDispatch (GpeEventInfo, GpeNumber);
1974 }
1975
1976
1977 /*******************************************************************************
1978  *
1979  * FUNCTION:    AcpiDbBusWalk
1980  *
1981  * PARAMETERS:  Callback from WalkNamespace
1982  *
1983  * RETURN:      Status
1984  *
1985  * DESCRIPTION: Display info about device objects that have a corresponding
1986  *              _PRT method.
1987  *
1988  ******************************************************************************/
1989
1990 static ACPI_STATUS
1991 AcpiDbBusWalk (
1992     ACPI_HANDLE             ObjHandle,
1993     UINT32                  NestingLevel,
1994     void                    *Context,
1995     void                    **ReturnValue)
1996 {
1997     ACPI_NAMESPACE_NODE     *Node = (ACPI_NAMESPACE_NODE *) ObjHandle;
1998     ACPI_STATUS             Status;
1999     ACPI_BUFFER             Buffer;
2000     ACPI_INTEGER            ADR;
2001     ACPI_DEVICE_ID          Id;
2002     ACPI_COMPATIBLE_ID_LIST *Cid;
2003     ACPI_NAMESPACE_NODE     *TempNode;
2004
2005
2006     /* Exit if there is no _PRT under this device */
2007
2008     Status = AcpiGetHandle (Node, METHOD_NAME__PRT,
2009                 ACPI_CAST_PTR (ACPI_HANDLE, &TempNode));
2010     if (ACPI_FAILURE (Status))
2011     {
2012         return (AE_OK);
2013     }
2014
2015     /* Get the full path to this device object */
2016
2017     Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER;
2018     Status = AcpiNsHandleToPathname (ObjHandle, &Buffer);
2019     if (ACPI_FAILURE (Status))
2020     {
2021         AcpiOsPrintf ("Could Not get pathname for object %p\n", ObjHandle);
2022         return (AE_OK);
2023     }
2024
2025     /* Display the full path */
2026
2027     AcpiOsPrintf ("%-32s", (char *) Buffer.Pointer);
2028     ACPI_FREE (Buffer.Pointer);
2029
2030     /* _PRT info */
2031
2032     AcpiOsPrintf ("_PRT=%p", TempNode);
2033
2034     /* Get the _ADR value */
2035
2036     Status = AcpiUtEvaluateNumericObject (METHOD_NAME__ADR, Node, &ADR);
2037     if (ACPI_FAILURE (Status))
2038     {
2039         AcpiOsPrintf (" No _ADR      ");
2040     }
2041     else
2042     {
2043         AcpiOsPrintf (" _ADR=%8.8X", (UINT32) ADR);
2044     }
2045
2046     /* Get the _HID if present */
2047
2048     Status = AcpiUtExecute_HID (Node, &Id);
2049     if (ACPI_SUCCESS (Status))
2050     {
2051         AcpiOsPrintf (" _HID=%s", Id.Value);
2052     }
2053     else
2054     {
2055         AcpiOsPrintf ("             ");
2056     }
2057
2058     /* Get the _UID if present */
2059
2060     Status = AcpiUtExecute_UID (Node, &Id);
2061     if (ACPI_SUCCESS (Status))
2062     {
2063         AcpiOsPrintf (" _UID=%s", Id.Value);
2064     }
2065
2066     /* Get the _CID if present */
2067
2068     Status = AcpiUtExecute_CID (Node, &Cid);
2069     if (ACPI_SUCCESS (Status))
2070     {
2071         AcpiOsPrintf (" _CID=%s", Cid->Id[0].Value);
2072         ACPI_FREE (Cid);
2073     }
2074
2075     AcpiOsPrintf ("\n");
2076     return (AE_OK);
2077 }
2078
2079
2080 /*******************************************************************************
2081  *
2082  * FUNCTION:    AcpiDbGetBusInfo
2083  *
2084  * PARAMETERS:  None
2085  *
2086  * RETURN:      None
2087  *
2088  * DESCRIPTION: Display info about system busses.
2089  *
2090  ******************************************************************************/
2091
2092 void
2093 AcpiDbGetBusInfo (
2094     void)
2095 {
2096     /* Search all nodes in namespace */
2097
2098     (void) AcpiWalkNamespace (ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX,
2099                     AcpiDbBusWalk, NULL, NULL);
2100 }
2101
2102 #endif /* ACPI_DEBUGGER */