2018-03-14 16:13:07 -07:00
// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
2015-10-19 10:25:20 +08:00
/*******************************************************************************
*
* Module Name : dbnames - Debugger commands for the acpi namespace
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
# include <acpi/acpi.h>
# include "accommon.h"
# include "acnamesp.h"
# include "acdebug.h"
# include "acpredef.h"
# define _COMPONENT ACPI_CA_DEBUGGER
ACPI_MODULE_NAME ( " dbnames " )
/* Local prototypes */
static acpi_status
acpi_db_walk_and_match_name ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value ) ;
static acpi_status
acpi_db_walk_for_predefined_names ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value ) ;
static acpi_status
acpi_db_walk_for_specific_objects ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value ) ;
static acpi_status
acpi_db_walk_for_object_counts ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value ) ;
static acpi_status
acpi_db_integrity_walk ( acpi_handle obj_handle ,
u32 nesting_level , void * context , void * * return_value ) ;
static acpi_status
acpi_db_walk_for_references ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value ) ;
static acpi_status
acpi_db_bus_walk ( acpi_handle obj_handle ,
u32 nesting_level , void * context , void * * return_value ) ;
/*
* Arguments for the Objects command
* These object types map directly to the ACPI_TYPES
*/
static struct acpi_db_argument_info acpi_db_object_types [ ] = {
{ " ANY " } ,
{ " INTEGERS " } ,
{ " STRINGS " } ,
{ " BUFFERS " } ,
{ " PACKAGES " } ,
{ " FIELDS " } ,
{ " DEVICES " } ,
{ " EVENTS " } ,
{ " METHODS " } ,
{ " MUTEXES " } ,
{ " REGIONS " } ,
{ " POWERRESOURCES " } ,
{ " PROCESSORS " } ,
{ " THERMALZONES " } ,
{ " BUFFERFIELDS " } ,
{ " DDBHANDLES " } ,
{ " DEBUG " } ,
{ " REGIONFIELDS " } ,
{ " BANKFIELDS " } ,
{ " INDEXFIELDS " } ,
{ " REFERENCES " } ,
{ " ALIASES " } ,
{ " METHODALIASES " } ,
{ " NOTIFY " } ,
{ " ADDRESSHANDLER " } ,
{ " RESOURCE " } ,
{ " RESOURCEFIELD " } ,
{ " SCOPES " } ,
{ NULL } /* Must be null terminated */
} ;
/*******************************************************************************
*
* FUNCTION : acpi_db_set_scope
*
* PARAMETERS : name - New scope path
*
* RETURN : Status
*
* DESCRIPTION : Set the " current scope " as maintained by this utility .
* The scope is used as a prefix to ACPI paths .
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_set_scope ( char * name )
{
acpi_status status ;
struct acpi_namespace_node * node ;
if ( ! name | | name [ 0 ] = = 0 ) {
acpi_os_printf ( " Current scope: %s \n " , acpi_gbl_db_scope_buf ) ;
return ;
}
acpi_db_prep_namestring ( name ) ;
if ( ACPI_IS_ROOT_PREFIX ( name [ 0 ] ) ) {
/* Validate new scope from the root */
status = acpi_ns_get_node ( acpi_gbl_root_node , name ,
ACPI_NS_NO_UPSEARCH , & node ) ;
if ( ACPI_FAILURE ( status ) ) {
goto error_exit ;
}
acpi_gbl_db_scope_buf [ 0 ] = 0 ;
} else {
/* Validate new scope relative to old scope */
status = acpi_ns_get_node ( acpi_gbl_db_scope_node , name ,
ACPI_NS_NO_UPSEARCH , & node ) ;
if ( ACPI_FAILURE ( status ) ) {
goto error_exit ;
}
}
/* Build the final pathname */
if ( acpi_ut_safe_strcat
( acpi_gbl_db_scope_buf , sizeof ( acpi_gbl_db_scope_buf ) , name ) ) {
status = AE_BUFFER_OVERFLOW ;
goto error_exit ;
}
if ( acpi_ut_safe_strcat
( acpi_gbl_db_scope_buf , sizeof ( acpi_gbl_db_scope_buf ) , " \\ " ) ) {
status = AE_BUFFER_OVERFLOW ;
goto error_exit ;
}
acpi_gbl_db_scope_node = node ;
acpi_os_printf ( " New scope: %s \n " , acpi_gbl_db_scope_buf ) ;
return ;
error_exit :
acpi_os_printf ( " Could not attach scope: %s, %s \n " ,
name , acpi_format_exception ( status ) ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_dump_namespace
*
* PARAMETERS : start_arg - Node to begin namespace dump
* depth_arg - Maximum tree depth to be dumped
*
* RETURN : None
*
* DESCRIPTION : Dump entire namespace or a subtree . Each node is displayed
* with type and other information .
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_dump_namespace ( char * start_arg , char * depth_arg )
{
acpi_handle subtree_entry = acpi_gbl_root_node ;
u32 max_depth = ACPI_UINT32_MAX ;
/* No argument given, just start at the root and dump entire namespace */
if ( start_arg ) {
subtree_entry = acpi_db_convert_to_node ( start_arg ) ;
if ( ! subtree_entry ) {
return ;
}
/* Now we can check for the depth argument */
if ( depth_arg ) {
max_depth = strtoul ( depth_arg , NULL , 0 ) ;
}
}
acpi_db_set_output_destination ( ACPI_DB_DUPLICATE_OUTPUT ) ;
2018-05-08 14:06:11 -07:00
if ( ( ( struct acpi_namespace_node * ) subtree_entry ) - > parent ) {
acpi_os_printf ( " ACPI Namespace (from %4.4s (%p) subtree): \n " ,
( ( struct acpi_namespace_node * ) subtree_entry ) - >
name . ascii , subtree_entry ) ;
} else {
acpi_os_printf ( " ACPI Namespace (from %s): \n " ,
ACPI_NAMESPACE_ROOT ) ;
}
2015-10-19 10:25:20 +08:00
/* Display the subtree */
acpi_db_set_output_destination ( ACPI_DB_REDIRECTABLE_OUTPUT ) ;
acpi_ns_dump_objects ( ACPI_TYPE_ANY , ACPI_DISPLAY_SUMMARY , max_depth ,
ACPI_OWNER_ID_MAX , subtree_entry ) ;
acpi_db_set_output_destination ( ACPI_DB_CONSOLE_OUTPUT ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_dump_namespace_paths
*
* PARAMETERS : None
*
* RETURN : None
*
* DESCRIPTION : Dump entire namespace with full object pathnames and object
* type information . Alternative to " namespace " command .
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_dump_namespace_paths ( void )
{
acpi_db_set_output_destination ( ACPI_DB_DUPLICATE_OUTPUT ) ;
acpi_os_printf ( " ACPI Namespace (from root): \n " ) ;
/* Display the entire namespace */
acpi_db_set_output_destination ( ACPI_DB_REDIRECTABLE_OUTPUT ) ;
acpi_ns_dump_object_paths ( ACPI_TYPE_ANY , ACPI_DISPLAY_SUMMARY ,
ACPI_UINT32_MAX , ACPI_OWNER_ID_MAX ,
acpi_gbl_root_node ) ;
acpi_db_set_output_destination ( ACPI_DB_CONSOLE_OUTPUT ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_dump_namespace_by_owner
*
* PARAMETERS : owner_arg - Owner ID whose nodes will be displayed
* depth_arg - Maximum tree depth to be dumped
*
* RETURN : None
*
* DESCRIPTION : Dump elements of the namespace that are owned by the owner_id .
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_dump_namespace_by_owner ( char * owner_arg , char * depth_arg )
{
acpi_handle subtree_entry = acpi_gbl_root_node ;
u32 max_depth = ACPI_UINT32_MAX ;
acpi_owner_id owner_id ;
2016-05-05 12:57:53 +08:00
owner_id = ( acpi_owner_id ) strtoul ( owner_arg , NULL , 0 ) ;
2015-10-19 10:25:20 +08:00
/* Now we can check for the depth argument */
if ( depth_arg ) {
max_depth = strtoul ( depth_arg , NULL , 0 ) ;
}
acpi_db_set_output_destination ( ACPI_DB_DUPLICATE_OUTPUT ) ;
acpi_os_printf ( " ACPI Namespace by owner %X: \n " , owner_id ) ;
/* Display the subtree */
acpi_db_set_output_destination ( ACPI_DB_REDIRECTABLE_OUTPUT ) ;
acpi_ns_dump_objects ( ACPI_TYPE_ANY , ACPI_DISPLAY_SUMMARY , max_depth ,
owner_id , subtree_entry ) ;
acpi_db_set_output_destination ( ACPI_DB_CONSOLE_OUTPUT ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_walk_and_match_name
*
* PARAMETERS : Callback from walk_namespace
*
* RETURN : Status
*
* DESCRIPTION : Find a particular name / names within the namespace . Wildcards
* are supported - - ' ? ' matches any character .
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static acpi_status
acpi_db_walk_and_match_name ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value )
{
acpi_status status ;
char * requested_name = ( char * ) context ;
u32 i ;
struct acpi_buffer buffer ;
struct acpi_walk_info info ;
/* Check for a name match */
for ( i = 0 ; i < 4 ; i + + ) {
/* Wildcard support */
if ( ( requested_name [ i ] ! = ' ? ' ) & &
( requested_name [ i ] ! = ( ( struct acpi_namespace_node * )
obj_handle ) - > name . ascii [ i ] ) ) {
/* No match, just exit */
return ( AE_OK ) ;
}
}
/* Get the full pathname to this object */
buffer . length = ACPI_ALLOCATE_LOCAL_BUFFER ;
status = acpi_ns_handle_to_pathname ( obj_handle , & buffer , TRUE ) ;
if ( ACPI_FAILURE ( status ) ) {
acpi_os_printf ( " Could Not get pathname for object %p \n " ,
obj_handle ) ;
} else {
2018-06-01 12:06:40 -07:00
info . count = 0 ;
2015-10-19 10:25:20 +08:00
info . owner_id = ACPI_OWNER_ID_MAX ;
info . debug_level = ACPI_UINT32_MAX ;
info . display_type = ACPI_DISPLAY_SUMMARY | ACPI_DISPLAY_SHORT ;
acpi_os_printf ( " %32s " , ( char * ) buffer . pointer ) ;
( void ) acpi_ns_dump_one_object ( obj_handle , nesting_level , & info ,
NULL ) ;
ACPI_FREE ( buffer . pointer ) ;
}
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_find_name_in_namespace
*
* PARAMETERS : name_arg - The 4 - character ACPI name to find .
* wildcards are supported .
*
* RETURN : None
*
* DESCRIPTION : Search the namespace for a given name ( with wildcards )
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
acpi_status acpi_db_find_name_in_namespace ( char * name_arg )
{
char acpi_name [ 5 ] = " ____ " ;
char * acpi_name_ptr = acpi_name ;
2019-04-08 13:42:25 -07:00
if ( strlen ( name_arg ) > ACPI_NAMESEG_SIZE ) {
2015-10-19 10:25:20 +08:00
acpi_os_printf ( " Name must be no longer than 4 characters \n " ) ;
return ( AE_OK ) ;
}
/* Pad out name with underscores as necessary to create a 4-char name */
acpi_ut_strupr ( name_arg ) ;
while ( * name_arg ) {
* acpi_name_ptr = * name_arg ;
acpi_name_ptr + + ;
name_arg + + ;
}
/* Walk the namespace from the root */
( void ) acpi_walk_namespace ( ACPI_TYPE_ANY , ACPI_ROOT_OBJECT ,
ACPI_UINT32_MAX , acpi_db_walk_and_match_name ,
NULL , acpi_name , NULL ) ;
acpi_db_set_output_destination ( ACPI_DB_CONSOLE_OUTPUT ) ;
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_walk_for_predefined_names
*
* PARAMETERS : Callback from walk_namespace
*
* RETURN : Status
*
* DESCRIPTION : Detect and display predefined ACPI names ( names that start with
* an underscore )
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static acpi_status
acpi_db_walk_for_predefined_names ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value )
{
struct acpi_namespace_node * node =
( struct acpi_namespace_node * ) obj_handle ;
u32 * count = ( u32 * ) context ;
const union acpi_predefined_info * predefined ;
const union acpi_predefined_info * package = NULL ;
char * pathname ;
char string_buffer [ 48 ] ;
predefined = acpi_ut_match_predefined_method ( node - > name . ascii ) ;
if ( ! predefined ) {
return ( AE_OK ) ;
}
2015-12-29 13:53:50 +08:00
pathname = acpi_ns_get_normalized_pathname ( node , TRUE ) ;
2015-10-19 10:25:20 +08:00
if ( ! pathname ) {
return ( AE_OK ) ;
}
/* If method returns a package, the info is in the next table entry */
if ( predefined - > info . expected_btypes & ACPI_RTYPE_PACKAGE ) {
package = predefined + 1 ;
}
acpi_ut_get_expected_return_types ( string_buffer ,
predefined - > info . expected_btypes ) ;
acpi_os_printf ( " %-32s Arguments %X, Return Types: %s " , pathname ,
METHOD_GET_ARG_COUNT ( predefined - > info . argument_list ) ,
string_buffer ) ;
if ( package ) {
acpi_os_printf ( " (PkgType %2.2X, ObjType %2.2X, Count %2.2X) " ,
package - > ret_info . type ,
package - > ret_info . object_type1 ,
package - > ret_info . count1 ) ;
}
acpi_os_printf ( " \n " ) ;
/* Check that the declared argument count matches the ACPI spec */
acpi_ns_check_acpi_compliance ( pathname , node , predefined ) ;
ACPI_FREE ( pathname ) ;
( * count ) + + ;
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_check_predefined_names
*
* PARAMETERS : None
*
* RETURN : None
*
* DESCRIPTION : Validate all predefined names in the namespace
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_check_predefined_names ( void )
{
u32 count = 0 ;
/* Search all nodes in namespace */
( void ) acpi_walk_namespace ( ACPI_TYPE_ANY , ACPI_ROOT_OBJECT ,
ACPI_UINT32_MAX ,
acpi_db_walk_for_predefined_names , NULL ,
( void * ) & count , NULL ) ;
acpi_os_printf ( " Found %u predefined names in the namespace \n " , count ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_walk_for_object_counts
*
* PARAMETERS : Callback from walk_namespace
*
* RETURN : Status
*
* DESCRIPTION : Display short info about objects in the namespace
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static acpi_status
acpi_db_walk_for_object_counts ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value )
{
struct acpi_object_info * info = ( struct acpi_object_info * ) context ;
struct acpi_namespace_node * node =
( struct acpi_namespace_node * ) obj_handle ;
if ( node - > type > ACPI_TYPE_NS_NODE_MAX ) {
acpi_os_printf ( " [%4.4s]: Unknown object type %X \n " ,
node - > name . ascii , node - > type ) ;
} else {
info - > types [ node - > type ] + + ;
}
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_walk_for_specific_objects
*
* PARAMETERS : Callback from walk_namespace
*
* RETURN : Status
*
* DESCRIPTION : Display short info about objects in the namespace
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static acpi_status
acpi_db_walk_for_specific_objects ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value )
{
struct acpi_walk_info * info = ( struct acpi_walk_info * ) context ;
struct acpi_buffer buffer ;
acpi_status status ;
info - > count + + ;
/* Get and display the full pathname to this object */
buffer . length = ACPI_ALLOCATE_LOCAL_BUFFER ;
status = acpi_ns_handle_to_pathname ( obj_handle , & buffer , TRUE ) ;
if ( ACPI_FAILURE ( status ) ) {
acpi_os_printf ( " Could Not get pathname for object %p \n " ,
obj_handle ) ;
return ( AE_OK ) ;
}
acpi_os_printf ( " %32s " , ( char * ) buffer . pointer ) ;
ACPI_FREE ( buffer . pointer ) ;
/* Dump short info about the object */
( void ) acpi_ns_dump_one_object ( obj_handle , nesting_level , info , NULL ) ;
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_display_objects
*
* PARAMETERS : obj_type_arg - Type of object to display
* display_count_arg - Max depth to display
*
* RETURN : None
*
* DESCRIPTION : Display objects in the namespace of the requested type
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
acpi_status acpi_db_display_objects ( char * obj_type_arg , char * display_count_arg )
{
struct acpi_walk_info info ;
acpi_object_type type ;
struct acpi_object_info * object_info ;
u32 i ;
u32 total_objects = 0 ;
/* No argument means display summary/count of all object types */
if ( ! obj_type_arg ) {
object_info =
ACPI_ALLOCATE_ZEROED ( sizeof ( struct acpi_object_info ) ) ;
/* Walk the namespace from the root */
( void ) acpi_walk_namespace ( ACPI_TYPE_ANY , ACPI_ROOT_OBJECT ,
ACPI_UINT32_MAX ,
acpi_db_walk_for_object_counts , NULL ,
( void * ) object_info , NULL ) ;
acpi_os_printf ( " \n Summary of namespace objects: \n \n " ) ;
for ( i = 0 ; i < ACPI_TOTAL_TYPES ; i + + ) {
acpi_os_printf ( " %8u %s \n " , object_info - > types [ i ] ,
acpi_ut_get_type_name ( i ) ) ;
total_objects + = object_info - > types [ i ] ;
}
acpi_os_printf ( " \n %8u Total namespace objects \n \n " ,
total_objects ) ;
ACPI_FREE ( object_info ) ;
return ( AE_OK ) ;
}
/* Get the object type */
type = acpi_db_match_argument ( obj_type_arg , acpi_db_object_types ) ;
if ( type = = ACPI_TYPE_NOT_FOUND ) {
acpi_os_printf ( " Invalid or unsupported argument \n " ) ;
return ( AE_OK ) ;
}
acpi_db_set_output_destination ( ACPI_DB_DUPLICATE_OUTPUT ) ;
acpi_os_printf
( " Objects of type [%s] defined in the current ACPI Namespace: \n " ,
acpi_ut_get_type_name ( type ) ) ;
acpi_db_set_output_destination ( ACPI_DB_REDIRECTABLE_OUTPUT ) ;
info . count = 0 ;
info . owner_id = ACPI_OWNER_ID_MAX ;
info . debug_level = ACPI_UINT32_MAX ;
info . display_type = ACPI_DISPLAY_SUMMARY | ACPI_DISPLAY_SHORT ;
/* Walk the namespace from the root */
( void ) acpi_walk_namespace ( type , ACPI_ROOT_OBJECT , ACPI_UINT32_MAX ,
acpi_db_walk_for_specific_objects , NULL ,
( void * ) & info , NULL ) ;
acpi_os_printf
( " \n Found %u objects of type [%s] in the current ACPI Namespace \n " ,
info . count , acpi_ut_get_type_name ( type ) ) ;
acpi_db_set_output_destination ( ACPI_DB_CONSOLE_OUTPUT ) ;
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_integrity_walk
*
* PARAMETERS : Callback from walk_namespace
*
* RETURN : Status
*
* DESCRIPTION : Examine one NS node for valid values .
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static acpi_status
acpi_db_integrity_walk ( acpi_handle obj_handle ,
u32 nesting_level , void * context , void * * return_value )
{
struct acpi_integrity_info * info =
( struct acpi_integrity_info * ) context ;
struct acpi_namespace_node * node =
( struct acpi_namespace_node * ) obj_handle ;
union acpi_operand_object * object ;
u8 alias = TRUE ;
info - > nodes + + ;
/* Verify the NS node, and dereference aliases */
while ( alias ) {
if ( ACPI_GET_DESCRIPTOR_TYPE ( node ) ! = ACPI_DESC_TYPE_NAMED ) {
acpi_os_printf
( " Invalid Descriptor Type for Node %p [%s] - "
" is %2.2X should be %2.2X \n " , node ,
acpi_ut_get_descriptor_name ( node ) ,
ACPI_GET_DESCRIPTOR_TYPE ( node ) ,
ACPI_DESC_TYPE_NAMED ) ;
return ( AE_OK ) ;
}
if ( ( node - > type = = ACPI_TYPE_LOCAL_ALIAS ) | |
( node - > type = = ACPI_TYPE_LOCAL_METHOD_ALIAS ) ) {
node = ( struct acpi_namespace_node * ) node - > object ;
} else {
alias = FALSE ;
}
}
if ( node - > type > ACPI_TYPE_LOCAL_MAX ) {
acpi_os_printf ( " Invalid Object Type for Node %p, Type = %X \n " ,
node , node - > type ) ;
return ( AE_OK ) ;
}
2016-05-05 13:00:36 +08:00
if ( ! acpi_ut_valid_nameseg ( node - > name . ascii ) ) {
2015-10-19 10:25:20 +08:00
acpi_os_printf ( " Invalid AcpiName for Node %p \n " , node ) ;
return ( AE_OK ) ;
}
object = acpi_ns_get_attached_object ( node ) ;
if ( object ) {
info - > objects + + ;
if ( ACPI_GET_DESCRIPTOR_TYPE ( object ) ! = ACPI_DESC_TYPE_OPERAND ) {
acpi_os_printf
( " Invalid Descriptor Type for Object %p [%s] \n " ,
object , acpi_ut_get_descriptor_name ( object ) ) ;
}
}
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_check_integrity
*
* PARAMETERS : None
*
* RETURN : None
*
* DESCRIPTION : Check entire namespace for data structure integrity
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_check_integrity ( void )
{
struct acpi_integrity_info info = { 0 , 0 } ;
/* Search all nodes in namespace */
( void ) acpi_walk_namespace ( ACPI_TYPE_ANY , ACPI_ROOT_OBJECT ,
ACPI_UINT32_MAX , acpi_db_integrity_walk , NULL ,
( void * ) & info , NULL ) ;
acpi_os_printf ( " Verified %u namespace nodes with %u Objects \n " ,
info . nodes , info . objects ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_walk_for_references
*
* PARAMETERS : Callback from walk_namespace
*
* RETURN : Status
*
* DESCRIPTION : Check if this namespace object refers to the target object
* that is passed in as the context value .
*
* Note : Currently doesn ' t check subobjects within the Node ' s object
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static acpi_status
acpi_db_walk_for_references ( acpi_handle obj_handle ,
u32 nesting_level ,
void * context , void * * return_value )
{
union acpi_operand_object * obj_desc =
( union acpi_operand_object * ) context ;
struct acpi_namespace_node * node =
( struct acpi_namespace_node * ) obj_handle ;
/* Check for match against the namespace node itself */
if ( node = = ( void * ) obj_desc ) {
acpi_os_printf ( " Object is a Node [%4.4s] \n " ,
acpi_ut_get_node_name ( node ) ) ;
}
/* Check for match against the object attached to the node */
if ( acpi_ns_get_attached_object ( node ) = = obj_desc ) {
acpi_os_printf ( " Reference at Node->Object %p [%4.4s] \n " ,
node , acpi_ut_get_node_name ( node ) ) ;
}
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_find_references
*
* PARAMETERS : object_arg - String with hex value of the object
*
* RETURN : None
*
* DESCRIPTION : Search namespace for all references to the input object
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_find_references ( char * object_arg )
{
union acpi_operand_object * obj_desc ;
acpi_size address ;
/* Convert string to object pointer */
address = strtoul ( object_arg , NULL , 16 ) ;
obj_desc = ACPI_TO_POINTER ( address ) ;
/* Search all nodes in namespace */
( void ) acpi_walk_namespace ( ACPI_TYPE_ANY , ACPI_ROOT_OBJECT ,
ACPI_UINT32_MAX , acpi_db_walk_for_references ,
NULL , ( void * ) obj_desc , NULL ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_bus_walk
*
* PARAMETERS : Callback from walk_namespace
*
* RETURN : Status
*
* DESCRIPTION : Display info about device objects that have a corresponding
* _PRT method .
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static acpi_status
acpi_db_bus_walk ( acpi_handle obj_handle ,
u32 nesting_level , void * context , void * * return_value )
{
struct acpi_namespace_node * node =
( struct acpi_namespace_node * ) obj_handle ;
acpi_status status ;
struct acpi_buffer buffer ;
struct acpi_namespace_node * temp_node ;
struct acpi_device_info * info ;
u32 i ;
if ( ( node - > type ! = ACPI_TYPE_DEVICE ) & &
( node - > type ! = ACPI_TYPE_PROCESSOR ) ) {
return ( AE_OK ) ;
}
/* Exit if there is no _PRT under this device */
status = acpi_get_handle ( node , METHOD_NAME__PRT ,
ACPI_CAST_PTR ( acpi_handle , & temp_node ) ) ;
if ( ACPI_FAILURE ( status ) ) {
return ( AE_OK ) ;
}
/* Get the full path to this device object */
buffer . length = ACPI_ALLOCATE_LOCAL_BUFFER ;
status = acpi_ns_handle_to_pathname ( obj_handle , & buffer , TRUE ) ;
if ( ACPI_FAILURE ( status ) ) {
acpi_os_printf ( " Could Not get pathname for object %p \n " ,
obj_handle ) ;
return ( AE_OK ) ;
}
status = acpi_get_object_info ( obj_handle , & info ) ;
if ( ACPI_FAILURE ( status ) ) {
return ( AE_OK ) ;
}
/* Display the full path */
acpi_os_printf ( " %-32s Type %X " , ( char * ) buffer . pointer , node - > type ) ;
ACPI_FREE ( buffer . pointer ) ;
if ( info - > flags & ACPI_PCI_ROOT_BRIDGE ) {
acpi_os_printf ( " - Is PCI Root Bridge " ) ;
}
acpi_os_printf ( " \n " ) ;
/* _PRT info */
acpi_os_printf ( " _PRT: %p \n " , temp_node ) ;
/* Dump _ADR, _HID, _UID, _CID */
if ( info - > valid & ACPI_VALID_ADR ) {
acpi_os_printf ( " _ADR: %8.8X%8.8X \n " ,
ACPI_FORMAT_UINT64 ( info - > address ) ) ;
} else {
acpi_os_printf ( " _ADR: <Not Present> \n " ) ;
}
if ( info - > valid & ACPI_VALID_HID ) {
acpi_os_printf ( " _HID: %s \n " , info - > hardware_id . string ) ;
} else {
acpi_os_printf ( " _HID: <Not Present> \n " ) ;
}
if ( info - > valid & ACPI_VALID_UID ) {
acpi_os_printf ( " _UID: %s \n " , info - > unique_id . string ) ;
} else {
acpi_os_printf ( " _UID: <Not Present> \n " ) ;
}
if ( info - > valid & ACPI_VALID_CID ) {
for ( i = 0 ; i < info - > compatible_id_list . count ; i + + ) {
acpi_os_printf ( " _CID: %s \n " ,
info - > compatible_id_list . ids [ i ] . string ) ;
}
} else {
acpi_os_printf ( " _CID: <Not Present> \n " ) ;
}
ACPI_FREE ( info ) ;
return ( AE_OK ) ;
}
/*******************************************************************************
*
* FUNCTION : acpi_db_get_bus_info
*
* PARAMETERS : None
*
* RETURN : None
*
2019-02-15 13:36:19 -08:00
* DESCRIPTION : Display info about system buses .
2015-10-19 10:25:20 +08:00
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void acpi_db_get_bus_info ( void )
{
/* Search all nodes in namespace */
( void ) acpi_walk_namespace ( ACPI_TYPE_ANY , ACPI_ROOT_OBJECT ,
ACPI_UINT32_MAX , acpi_db_bus_walk , NULL , NULL ,
NULL ) ;
}