Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
0002 /*******************************************************************************
0003  *
0004  * Module Name: dbutils - AML debugger utilities
0005  *
0006  ******************************************************************************/
0007 
0008 #include <acpi/acpi.h>
0009 #include "accommon.h"
0010 #include "acnamesp.h"
0011 #include "acdebug.h"
0012 
0013 #define _COMPONENT          ACPI_CA_DEBUGGER
0014 ACPI_MODULE_NAME("dbutils")
0015 
0016 /* Local prototypes */
0017 #ifdef ACPI_OBSOLETE_FUNCTIONS
0018 acpi_status acpi_db_second_pass_parse(union acpi_parse_object *root);
0019 
0020 void acpi_db_dump_buffer(u32 address);
0021 #endif
0022 
0023 /*******************************************************************************
0024  *
0025  * FUNCTION:    acpi_db_match_argument
0026  *
0027  * PARAMETERS:  user_argument           - User command line
0028  *              arguments               - Array of commands to match against
0029  *
0030  * RETURN:      Index into command array or ACPI_TYPE_NOT_FOUND if not found
0031  *
0032  * DESCRIPTION: Search command array for a command match
0033  *
0034  ******************************************************************************/
0035 
0036 acpi_object_type
0037 acpi_db_match_argument(char *user_argument,
0038                struct acpi_db_argument_info *arguments)
0039 {
0040     u32 i;
0041 
0042     if (!user_argument || user_argument[0] == 0) {
0043         return (ACPI_TYPE_NOT_FOUND);
0044     }
0045 
0046     for (i = 0; arguments[i].name; i++) {
0047         if (strstr(ACPI_CAST_PTR(char, arguments[i].name),
0048                ACPI_CAST_PTR(char,
0049                      user_argument)) == arguments[i].name) {
0050             return (i);
0051         }
0052     }
0053 
0054     /* Argument not recognized */
0055 
0056     return (ACPI_TYPE_NOT_FOUND);
0057 }
0058 
0059 /*******************************************************************************
0060  *
0061  * FUNCTION:    acpi_db_set_output_destination
0062  *
0063  * PARAMETERS:  output_flags        - Current flags word
0064  *
0065  * RETURN:      None
0066  *
0067  * DESCRIPTION: Set the current destination for debugger output. Also sets
0068  *              the debug output level accordingly.
0069  *
0070  ******************************************************************************/
0071 
0072 void acpi_db_set_output_destination(u32 output_flags)
0073 {
0074 
0075     acpi_gbl_db_output_flags = (u8)output_flags;
0076 
0077     if ((output_flags & ACPI_DB_REDIRECTABLE_OUTPUT) &&
0078         acpi_gbl_db_output_to_file) {
0079         acpi_dbg_level = acpi_gbl_db_debug_level;
0080     } else {
0081         acpi_dbg_level = acpi_gbl_db_console_debug_level;
0082     }
0083 }
0084 
0085 /*******************************************************************************
0086  *
0087  * FUNCTION:    acpi_db_dump_external_object
0088  *
0089  * PARAMETERS:  obj_desc        - External ACPI object to dump
0090  *              level           - Nesting level.
0091  *
0092  * RETURN:      None
0093  *
0094  * DESCRIPTION: Dump the contents of an ACPI external object
0095  *
0096  ******************************************************************************/
0097 
0098 void acpi_db_dump_external_object(union acpi_object *obj_desc, u32 level)
0099 {
0100     u32 i;
0101 
0102     if (!obj_desc) {
0103         acpi_os_printf("[Null Object]\n");
0104         return;
0105     }
0106 
0107     for (i = 0; i < level; i++) {
0108         acpi_os_printf(" ");
0109     }
0110 
0111     switch (obj_desc->type) {
0112     case ACPI_TYPE_ANY:
0113 
0114         acpi_os_printf("[Null Object] (Type=0)\n");
0115         break;
0116 
0117     case ACPI_TYPE_INTEGER:
0118 
0119         acpi_os_printf("[Integer] = %8.8X%8.8X\n",
0120                    ACPI_FORMAT_UINT64(obj_desc->integer.value));
0121         break;
0122 
0123     case ACPI_TYPE_STRING:
0124 
0125         acpi_os_printf("[String] Length %.2X = ",
0126                    obj_desc->string.length);
0127         acpi_ut_print_string(obj_desc->string.pointer, ACPI_UINT8_MAX);
0128         acpi_os_printf("\n");
0129         break;
0130 
0131     case ACPI_TYPE_BUFFER:
0132 
0133         acpi_os_printf("[Buffer] Length %.2X = ",
0134                    obj_desc->buffer.length);
0135         if (obj_desc->buffer.length) {
0136             if (obj_desc->buffer.length > 16) {
0137                 acpi_os_printf("\n");
0138             }
0139 
0140             acpi_ut_debug_dump_buffer(ACPI_CAST_PTR
0141                           (u8,
0142                            obj_desc->buffer.pointer),
0143                           obj_desc->buffer.length,
0144                           DB_BYTE_DISPLAY, _COMPONENT);
0145         } else {
0146             acpi_os_printf("\n");
0147         }
0148         break;
0149 
0150     case ACPI_TYPE_PACKAGE:
0151 
0152         acpi_os_printf("[Package] Contains %u Elements:\n",
0153                    obj_desc->package.count);
0154 
0155         for (i = 0; i < obj_desc->package.count; i++) {
0156             acpi_db_dump_external_object(&obj_desc->package.
0157                              elements[i], level + 1);
0158         }
0159         break;
0160 
0161     case ACPI_TYPE_LOCAL_REFERENCE:
0162 
0163         acpi_os_printf("[Object Reference] = ");
0164         acpi_db_display_internal_object(obj_desc->reference.handle,
0165                         NULL);
0166         break;
0167 
0168     case ACPI_TYPE_PROCESSOR:
0169 
0170         acpi_os_printf("[Processor]\n");
0171         break;
0172 
0173     case ACPI_TYPE_POWER:
0174 
0175         acpi_os_printf("[Power Resource]\n");
0176         break;
0177 
0178     default:
0179 
0180         acpi_os_printf("[Unknown Type] %X\n", obj_desc->type);
0181         break;
0182     }
0183 }
0184 
0185 /*******************************************************************************
0186  *
0187  * FUNCTION:    acpi_db_prep_namestring
0188  *
0189  * PARAMETERS:  name            - String to prepare
0190  *
0191  * RETURN:      None
0192  *
0193  * DESCRIPTION: Translate all forward slashes and dots to backslashes.
0194  *
0195  ******************************************************************************/
0196 
0197 void acpi_db_prep_namestring(char *name)
0198 {
0199 
0200     if (!name) {
0201         return;
0202     }
0203 
0204     acpi_ut_strupr(name);
0205 
0206     /* Convert a leading forward slash to a backslash */
0207 
0208     if (*name == '/') {
0209         *name = '\\';
0210     }
0211 
0212     /* Ignore a leading backslash, this is the root prefix */
0213 
0214     if (ACPI_IS_ROOT_PREFIX(*name)) {
0215         name++;
0216     }
0217 
0218     /* Convert all slash path separators to dots */
0219 
0220     while (*name) {
0221         if ((*name == '/') || (*name == '\\')) {
0222             *name = '.';
0223         }
0224 
0225         name++;
0226     }
0227 }
0228 
0229 /*******************************************************************************
0230  *
0231  * FUNCTION:    acpi_db_local_ns_lookup
0232  *
0233  * PARAMETERS:  name            - Name to lookup
0234  *
0235  * RETURN:      Pointer to a namespace node, null on failure
0236  *
0237  * DESCRIPTION: Lookup a name in the ACPI namespace
0238  *
0239  * Note: Currently begins search from the root. Could be enhanced to use
0240  * the current prefix (scope) node as the search beginning point.
0241  *
0242  ******************************************************************************/
0243 
0244 struct acpi_namespace_node *acpi_db_local_ns_lookup(char *name)
0245 {
0246     char *internal_path;
0247     acpi_status status;
0248     struct acpi_namespace_node *node = NULL;
0249 
0250     acpi_db_prep_namestring(name);
0251 
0252     /* Build an internal namestring */
0253 
0254     status = acpi_ns_internalize_name(name, &internal_path);
0255     if (ACPI_FAILURE(status)) {
0256         acpi_os_printf("Invalid namestring: %s\n", name);
0257         return (NULL);
0258     }
0259 
0260     /*
0261      * Lookup the name.
0262      * (Uses root node as the search starting point)
0263      */
0264     status = acpi_ns_lookup(NULL, internal_path, ACPI_TYPE_ANY,
0265                 ACPI_IMODE_EXECUTE,
0266                 ACPI_NS_NO_UPSEARCH | ACPI_NS_DONT_OPEN_SCOPE,
0267                 NULL, &node);
0268     if (ACPI_FAILURE(status)) {
0269         acpi_os_printf("Could not locate name: %s, %s\n",
0270                    name, acpi_format_exception(status));
0271     }
0272 
0273     ACPI_FREE(internal_path);
0274     return (node);
0275 }
0276 
0277 /*******************************************************************************
0278  *
0279  * FUNCTION:    acpi_db_uint32_to_hex_string
0280  *
0281  * PARAMETERS:  value           - The value to be converted to string
0282  *              buffer          - Buffer for result (not less than 11 bytes)
0283  *
0284  * RETURN:      None
0285  *
0286  * DESCRIPTION: Convert the unsigned 32-bit value to the hexadecimal image
0287  *
0288  * NOTE: It is the caller's responsibility to ensure that the length of buffer
0289  *       is sufficient.
0290  *
0291  ******************************************************************************/
0292 
0293 void acpi_db_uint32_to_hex_string(u32 value, char *buffer)
0294 {
0295     int i;
0296 
0297     if (value == 0) {
0298         strcpy(buffer, "0");
0299         return;
0300     }
0301 
0302     buffer[8] = '\0';
0303 
0304     for (i = 7; i >= 0; i--) {
0305         buffer[i] = acpi_gbl_upper_hex_digits[value & 0x0F];
0306         value = value >> 4;
0307     }
0308 }
0309 
0310 #ifdef ACPI_OBSOLETE_FUNCTIONS
0311 /*******************************************************************************
0312  *
0313  * FUNCTION:    acpi_db_second_pass_parse
0314  *
0315  * PARAMETERS:  root            - Root of the parse tree
0316  *
0317  * RETURN:      Status
0318  *
0319  * DESCRIPTION: Second pass parse of the ACPI tables. We need to wait until
0320  *              second pass to parse the control methods
0321  *
0322  ******************************************************************************/
0323 
0324 acpi_status acpi_db_second_pass_parse(union acpi_parse_object *root)
0325 {
0326     union acpi_parse_object *op = root;
0327     union acpi_parse_object *method;
0328     union acpi_parse_object *search_op;
0329     union acpi_parse_object *start_op;
0330     acpi_status status = AE_OK;
0331     u32 base_aml_offset;
0332     struct acpi_walk_state *walk_state;
0333 
0334     ACPI_FUNCTION_ENTRY();
0335 
0336     acpi_os_printf("Pass two parse ....\n");
0337 
0338     while (op) {
0339         if (op->common.aml_opcode == AML_METHOD_OP) {
0340             method = op;
0341 
0342             /* Create a new walk state for the parse */
0343 
0344             walk_state =
0345                 acpi_ds_create_walk_state(0, NULL, NULL, NULL);
0346             if (!walk_state) {
0347                 return (AE_NO_MEMORY);
0348             }
0349 
0350             /* Init the Walk State */
0351 
0352             walk_state->parser_state.aml =
0353                 walk_state->parser_state.aml_start =
0354                 method->named.data;
0355             walk_state->parser_state.aml_end =
0356                 walk_state->parser_state.pkg_end =
0357                 method->named.data + method->named.length;
0358             walk_state->parser_state.start_scope = op;
0359 
0360             walk_state->descending_callback =
0361                 acpi_ds_load1_begin_op;
0362             walk_state->ascending_callback = acpi_ds_load1_end_op;
0363 
0364             /* Perform the AML parse */
0365 
0366             status = acpi_ps_parse_aml(walk_state);
0367 
0368             base_aml_offset =
0369                 (method->common.value.arg)->common.aml_offset + 1;
0370             start_op = (method->common.value.arg)->common.next;
0371             search_op = start_op;
0372 
0373             while (search_op) {
0374                 search_op->common.aml_offset += base_aml_offset;
0375                 search_op =
0376                     acpi_ps_get_depth_next(start_op, search_op);
0377             }
0378         }
0379 
0380         if (op->common.aml_opcode == AML_REGION_OP) {
0381 
0382             /* TBD: [Investigate] this isn't quite the right thing to do! */
0383             /*
0384              *
0385              * Method = (ACPI_DEFERRED_OP *) Op;
0386              * Status = acpi_ps_parse_aml (Op, Method->Body, Method->body_length);
0387              */
0388         }
0389 
0390         if (ACPI_FAILURE(status)) {
0391             break;
0392         }
0393 
0394         op = acpi_ps_get_depth_next(root, op);
0395     }
0396 
0397     return (status);
0398 }
0399 
0400 /*******************************************************************************
0401  *
0402  * FUNCTION:    acpi_db_dump_buffer
0403  *
0404  * PARAMETERS:  address             - Pointer to the buffer
0405  *
0406  * RETURN:      None
0407  *
0408  * DESCRIPTION: Print a portion of a buffer
0409  *
0410  ******************************************************************************/
0411 
0412 void acpi_db_dump_buffer(u32 address)
0413 {
0414 
0415     acpi_os_printf("\nLocation %X:\n", address);
0416 
0417     acpi_dbg_level |= ACPI_LV_TABLES;
0418     acpi_ut_debug_dump_buffer(ACPI_TO_POINTER(address), 64, DB_BYTE_DISPLAY,
0419                   ACPI_UINT32_MAX);
0420 }
0421 #endif