cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

rsdump.c (14102B)


      1// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
      2/*******************************************************************************
      3 *
      4 * Module Name: rsdump - AML debugger support for resource structures.
      5 *
      6 ******************************************************************************/
      7
      8#include <acpi/acpi.h>
      9#include "accommon.h"
     10#include "acresrc.h"
     11
     12#define _COMPONENT          ACPI_RESOURCES
     13ACPI_MODULE_NAME("rsdump")
     14
     15/*
     16 * All functions in this module are used by the AML Debugger only
     17 */
     18/* Local prototypes */
     19static void acpi_rs_out_string(const char *title, const char *value);
     20
     21static void acpi_rs_out_integer8(const char *title, u8 value);
     22
     23static void acpi_rs_out_integer16(const char *title, u16 value);
     24
     25static void acpi_rs_out_integer32(const char *title, u32 value);
     26
     27static void acpi_rs_out_integer64(const char *title, u64 value);
     28
     29static void acpi_rs_out_title(const char *title);
     30
     31static void acpi_rs_dump_byte_list(u16 length, u8 *data);
     32
     33static void acpi_rs_dump_word_list(u16 length, u16 *data);
     34
     35static void acpi_rs_dump_dword_list(u8 length, u32 *data);
     36
     37static void acpi_rs_dump_short_byte_list(u8 length, u8 *data);
     38
     39static void
     40acpi_rs_dump_resource_source(struct acpi_resource_source *resource_source);
     41
     42static void
     43acpi_rs_dump_resource_label(char *title,
     44			    struct acpi_resource_label *resource_label);
     45
     46static void acpi_rs_dump_address_common(union acpi_resource_data *resource);
     47
     48static void
     49acpi_rs_dump_descriptor(void *resource, struct acpi_rsdump_info *table);
     50
     51/*******************************************************************************
     52 *
     53 * FUNCTION:    acpi_rs_dump_resource_list
     54 *
     55 * PARAMETERS:  resource_list       - Pointer to a resource descriptor list
     56 *
     57 * RETURN:      None
     58 *
     59 * DESCRIPTION: Dispatches the structure to the correct dump routine.
     60 *
     61 ******************************************************************************/
     62
     63void acpi_rs_dump_resource_list(struct acpi_resource *resource_list)
     64{
     65	u32 count = 0;
     66	u32 type;
     67
     68	ACPI_FUNCTION_ENTRY();
     69
     70	/* Check if debug output enabled */
     71
     72	if (!ACPI_IS_DEBUG_ENABLED(ACPI_LV_RESOURCES, _COMPONENT)) {
     73		return;
     74	}
     75
     76	/* Walk list and dump all resource descriptors (END_TAG terminates) */
     77
     78	do {
     79		acpi_os_printf("\n[%02X] ", count);
     80		count++;
     81
     82		/* Validate Type before dispatch */
     83
     84		type = resource_list->type;
     85		if (type > ACPI_RESOURCE_TYPE_MAX) {
     86			acpi_os_printf
     87			    ("Invalid descriptor type (%X) in resource list\n",
     88			     resource_list->type);
     89			return;
     90		} else if (!resource_list->type) {
     91			ACPI_ERROR((AE_INFO, "Invalid Zero Resource Type"));
     92			return;
     93		}
     94
     95		/* Sanity check the length. It must not be zero, or we loop forever */
     96
     97		if (!resource_list->length) {
     98			acpi_os_printf
     99			    ("Invalid zero length descriptor in resource list\n");
    100			return;
    101		}
    102
    103		/* Dump the resource descriptor */
    104
    105		if (type == ACPI_RESOURCE_TYPE_SERIAL_BUS) {
    106			acpi_rs_dump_descriptor(&resource_list->data,
    107						acpi_gbl_dump_serial_bus_dispatch
    108						[resource_list->data.
    109						 common_serial_bus.type]);
    110		} else {
    111			acpi_rs_dump_descriptor(&resource_list->data,
    112						acpi_gbl_dump_resource_dispatch
    113						[type]);
    114		}
    115
    116		/* Point to the next resource structure */
    117
    118		resource_list = ACPI_NEXT_RESOURCE(resource_list);
    119
    120		/* Exit when END_TAG descriptor is reached */
    121
    122	} while (type != ACPI_RESOURCE_TYPE_END_TAG);
    123}
    124
    125/*******************************************************************************
    126 *
    127 * FUNCTION:    acpi_rs_dump_irq_list
    128 *
    129 * PARAMETERS:  route_table     - Pointer to the routing table to dump.
    130 *
    131 * RETURN:      None
    132 *
    133 * DESCRIPTION: Print IRQ routing table
    134 *
    135 ******************************************************************************/
    136
    137void acpi_rs_dump_irq_list(u8 *route_table)
    138{
    139	struct acpi_pci_routing_table *prt_element;
    140	u8 count;
    141
    142	ACPI_FUNCTION_ENTRY();
    143
    144	/* Check if debug output enabled */
    145
    146	if (!ACPI_IS_DEBUG_ENABLED(ACPI_LV_RESOURCES, _COMPONENT)) {
    147		return;
    148	}
    149
    150	prt_element = ACPI_CAST_PTR(struct acpi_pci_routing_table, route_table);
    151
    152	/* Dump all table elements, Exit on zero length element */
    153
    154	for (count = 0; prt_element->length; count++) {
    155		acpi_os_printf("\n[%02X] PCI IRQ Routing Table Package\n",
    156			       count);
    157		acpi_rs_dump_descriptor(prt_element, acpi_rs_dump_prt);
    158
    159		prt_element = ACPI_ADD_PTR(struct acpi_pci_routing_table,
    160					   prt_element, prt_element->length);
    161	}
    162}
    163
    164/*******************************************************************************
    165 *
    166 * FUNCTION:    acpi_rs_dump_descriptor
    167 *
    168 * PARAMETERS:  resource            - Buffer containing the resource
    169 *              table               - Table entry to decode the resource
    170 *
    171 * RETURN:      None
    172 *
    173 * DESCRIPTION: Dump a resource descriptor based on a dump table entry.
    174 *
    175 ******************************************************************************/
    176
    177static void
    178acpi_rs_dump_descriptor(void *resource, struct acpi_rsdump_info *table)
    179{
    180	u8 *target = NULL;
    181	u8 *previous_target;
    182	const char *name;
    183	u8 count;
    184
    185	/* First table entry must contain the table length (# of table entries) */
    186
    187	count = table->offset;
    188
    189	while (count) {
    190		previous_target = target;
    191		target = ACPI_ADD_PTR(u8, resource, table->offset);
    192		name = table->name;
    193
    194		switch (table->opcode) {
    195		case ACPI_RSD_TITLE:
    196			/*
    197			 * Optional resource title
    198			 */
    199			if (table->name) {
    200				acpi_os_printf("%s Resource\n", name);
    201			}
    202			break;
    203
    204			/* Strings */
    205
    206		case ACPI_RSD_LITERAL:
    207
    208			acpi_rs_out_string(name,
    209					   ACPI_CAST_PTR(char, table->pointer));
    210			break;
    211
    212		case ACPI_RSD_STRING:
    213
    214			acpi_rs_out_string(name, ACPI_CAST_PTR(char, target));
    215			break;
    216
    217			/* Data items, 8/16/32/64 bit */
    218
    219		case ACPI_RSD_UINT8:
    220
    221			if (table->pointer) {
    222				acpi_rs_out_string(name,
    223						   table->pointer[*target]);
    224			} else {
    225				acpi_rs_out_integer8(name, ACPI_GET8(target));
    226			}
    227			break;
    228
    229		case ACPI_RSD_UINT16:
    230
    231			acpi_rs_out_integer16(name, ACPI_GET16(target));
    232			break;
    233
    234		case ACPI_RSD_UINT32:
    235
    236			acpi_rs_out_integer32(name, ACPI_GET32(target));
    237			break;
    238
    239		case ACPI_RSD_UINT64:
    240
    241			acpi_rs_out_integer64(name, ACPI_GET64(target));
    242			break;
    243
    244			/* Flags: 1-bit and 2-bit flags supported */
    245
    246		case ACPI_RSD_1BITFLAG:
    247
    248			acpi_rs_out_string(name,
    249					   table->pointer[*target & 0x01]);
    250			break;
    251
    252		case ACPI_RSD_2BITFLAG:
    253
    254			acpi_rs_out_string(name,
    255					   table->pointer[*target & 0x03]);
    256			break;
    257
    258		case ACPI_RSD_3BITFLAG:
    259
    260			acpi_rs_out_string(name,
    261					   table->pointer[*target & 0x07]);
    262			break;
    263
    264		case ACPI_RSD_6BITFLAG:
    265
    266			acpi_rs_out_integer8(name, (ACPI_GET8(target) & 0x3F));
    267			break;
    268
    269		case ACPI_RSD_SHORTLIST:
    270			/*
    271			 * Short byte list (single line output) for DMA and IRQ resources
    272			 * Note: The list length is obtained from the previous table entry
    273			 */
    274			if (previous_target) {
    275				acpi_rs_out_title(name);
    276				acpi_rs_dump_short_byte_list(*previous_target,
    277							     target);
    278			}
    279			break;
    280
    281		case ACPI_RSD_SHORTLISTX:
    282			/*
    283			 * Short byte list (single line output) for GPIO vendor data
    284			 * Note: The list length is obtained from the previous table entry
    285			 */
    286			if (previous_target) {
    287				acpi_rs_out_title(name);
    288				acpi_rs_dump_short_byte_list(*previous_target,
    289							     *
    290							     (ACPI_CAST_INDIRECT_PTR
    291							      (u8, target)));
    292			}
    293			break;
    294
    295		case ACPI_RSD_LONGLIST:
    296			/*
    297			 * Long byte list for Vendor resource data
    298			 * Note: The list length is obtained from the previous table entry
    299			 */
    300			if (previous_target) {
    301				acpi_rs_dump_byte_list(ACPI_GET16
    302						       (previous_target),
    303						       target);
    304			}
    305			break;
    306
    307		case ACPI_RSD_DWORDLIST:
    308			/*
    309			 * Dword list for Extended Interrupt resources
    310			 * Note: The list length is obtained from the previous table entry
    311			 */
    312			if (previous_target) {
    313				acpi_rs_dump_dword_list(*previous_target,
    314							ACPI_CAST_PTR(u32,
    315								      target));
    316			}
    317			break;
    318
    319		case ACPI_RSD_WORDLIST:
    320			/*
    321			 * Word list for GPIO Pin Table
    322			 * Note: The list length is obtained from the previous table entry
    323			 */
    324			if (previous_target) {
    325				acpi_rs_dump_word_list(*previous_target,
    326						       *(ACPI_CAST_INDIRECT_PTR
    327							 (u16, target)));
    328			}
    329			break;
    330
    331		case ACPI_RSD_ADDRESS:
    332			/*
    333			 * Common flags for all Address resources
    334			 */
    335			acpi_rs_dump_address_common(ACPI_CAST_PTR
    336						    (union acpi_resource_data,
    337						     target));
    338			break;
    339
    340		case ACPI_RSD_SOURCE:
    341			/*
    342			 * Optional resource_source for Address resources
    343			 */
    344			acpi_rs_dump_resource_source(ACPI_CAST_PTR
    345						     (struct
    346								   acpi_resource_source,
    347								   target));
    348			break;
    349
    350		case ACPI_RSD_LABEL:
    351			/*
    352			 * resource_label
    353			 */
    354			acpi_rs_dump_resource_label("Resource Label",
    355						    ACPI_CAST_PTR(struct
    356								  acpi_resource_label,
    357								  target));
    358			break;
    359
    360		case ACPI_RSD_SOURCE_LABEL:
    361			/*
    362			 * resource_source_label
    363			 */
    364			acpi_rs_dump_resource_label("Resource Source Label",
    365						    ACPI_CAST_PTR(struct
    366								  acpi_resource_label,
    367								  target));
    368			break;
    369
    370		default:
    371
    372			acpi_os_printf("**** Invalid table opcode [%X] ****\n",
    373				       table->opcode);
    374			return;
    375		}
    376
    377		table++;
    378		count--;
    379	}
    380}
    381
    382/*******************************************************************************
    383 *
    384 * FUNCTION:    acpi_rs_dump_resource_source
    385 *
    386 * PARAMETERS:  resource_source     - Pointer to a Resource Source struct
    387 *
    388 * RETURN:      None
    389 *
    390 * DESCRIPTION: Common routine for dumping the optional resource_source and the
    391 *              corresponding resource_source_index.
    392 *
    393 ******************************************************************************/
    394
    395static void
    396acpi_rs_dump_resource_source(struct acpi_resource_source *resource_source)
    397{
    398	ACPI_FUNCTION_ENTRY();
    399
    400	if (resource_source->index == 0xFF) {
    401		return;
    402	}
    403
    404	acpi_rs_out_integer8("Resource Source Index", resource_source->index);
    405
    406	acpi_rs_out_string("Resource Source",
    407			   resource_source->string_ptr ?
    408			   resource_source->string_ptr : "[Not Specified]");
    409}
    410
    411/*******************************************************************************
    412 *
    413 * FUNCTION:    acpi_rs_dump_resource_label
    414 *
    415 * PARAMETERS:  title              - Title of the dumped resource field
    416 *              resource_label     - Pointer to a Resource Label struct
    417 *
    418 * RETURN:      None
    419 *
    420 * DESCRIPTION: Common routine for dumping the resource_label
    421 *
    422 ******************************************************************************/
    423
    424static void
    425acpi_rs_dump_resource_label(char *title,
    426			    struct acpi_resource_label *resource_label)
    427{
    428	ACPI_FUNCTION_ENTRY();
    429
    430	acpi_rs_out_string(title,
    431			   resource_label->string_ptr ?
    432			   resource_label->string_ptr : "[Not Specified]");
    433}
    434
    435/*******************************************************************************
    436 *
    437 * FUNCTION:    acpi_rs_dump_address_common
    438 *
    439 * PARAMETERS:  resource        - Pointer to an internal resource descriptor
    440 *
    441 * RETURN:      None
    442 *
    443 * DESCRIPTION: Dump the fields that are common to all Address resource
    444 *              descriptors
    445 *
    446 ******************************************************************************/
    447
    448static void acpi_rs_dump_address_common(union acpi_resource_data *resource)
    449{
    450	ACPI_FUNCTION_ENTRY();
    451
    452	/* Decode the type-specific flags */
    453
    454	switch (resource->address.resource_type) {
    455	case ACPI_MEMORY_RANGE:
    456
    457		acpi_rs_dump_descriptor(resource, acpi_rs_dump_memory_flags);
    458		break;
    459
    460	case ACPI_IO_RANGE:
    461
    462		acpi_rs_dump_descriptor(resource, acpi_rs_dump_io_flags);
    463		break;
    464
    465	case ACPI_BUS_NUMBER_RANGE:
    466
    467		acpi_rs_out_string("Resource Type", "Bus Number Range");
    468		break;
    469
    470	default:
    471
    472		acpi_rs_out_integer8("Resource Type",
    473				     (u8) resource->address.resource_type);
    474		break;
    475	}
    476
    477	/* Decode the general flags */
    478
    479	acpi_rs_dump_descriptor(resource, acpi_rs_dump_general_flags);
    480}
    481
    482/*******************************************************************************
    483 *
    484 * FUNCTION:    acpi_rs_out*
    485 *
    486 * PARAMETERS:  title       - Name of the resource field
    487 *              value       - Value of the resource field
    488 *
    489 * RETURN:      None
    490 *
    491 * DESCRIPTION: Miscellaneous helper functions to consistently format the
    492 *              output of the resource dump routines
    493 *
    494 ******************************************************************************/
    495
    496static void acpi_rs_out_string(const char *title, const char *value)
    497{
    498
    499	acpi_os_printf("%27s : %s", title, value);
    500	if (!*value) {
    501		acpi_os_printf("[NULL NAMESTRING]");
    502	}
    503	acpi_os_printf("\n");
    504}
    505
    506static void acpi_rs_out_integer8(const char *title, u8 value)
    507{
    508	acpi_os_printf("%27s : %2.2X\n", title, value);
    509}
    510
    511static void acpi_rs_out_integer16(const char *title, u16 value)
    512{
    513
    514	acpi_os_printf("%27s : %4.4X\n", title, value);
    515}
    516
    517static void acpi_rs_out_integer32(const char *title, u32 value)
    518{
    519
    520	acpi_os_printf("%27s : %8.8X\n", title, value);
    521}
    522
    523static void acpi_rs_out_integer64(const char *title, u64 value)
    524{
    525
    526	acpi_os_printf("%27s : %8.8X%8.8X\n", title, ACPI_FORMAT_UINT64(value));
    527}
    528
    529static void acpi_rs_out_title(const char *title)
    530{
    531
    532	acpi_os_printf("%27s : ", title);
    533}
    534
    535/*******************************************************************************
    536 *
    537 * FUNCTION:    acpi_rs_dump*List
    538 *
    539 * PARAMETERS:  length      - Number of elements in the list
    540 *              data        - Start of the list
    541 *
    542 * RETURN:      None
    543 *
    544 * DESCRIPTION: Miscellaneous functions to dump lists of raw data
    545 *
    546 ******************************************************************************/
    547
    548static void acpi_rs_dump_byte_list(u16 length, u8 * data)
    549{
    550	u16 i;
    551
    552	for (i = 0; i < length; i++) {
    553		acpi_os_printf("%25s%2.2X : %2.2X\n", "Byte", i, data[i]);
    554	}
    555}
    556
    557static void acpi_rs_dump_short_byte_list(u8 length, u8 * data)
    558{
    559	u8 i;
    560
    561	for (i = 0; i < length; i++) {
    562		acpi_os_printf("%X ", data[i]);
    563	}
    564
    565	acpi_os_printf("\n");
    566}
    567
    568static void acpi_rs_dump_dword_list(u8 length, u32 * data)
    569{
    570	u8 i;
    571
    572	for (i = 0; i < length; i++) {
    573		acpi_os_printf("%25s%2.2X : %8.8X\n", "Dword", i, data[i]);
    574	}
    575}
    576
    577static void acpi_rs_dump_word_list(u16 length, u16 *data)
    578{
    579	u16 i;
    580
    581	for (i = 0; i < length; i++) {
    582		acpi_os_printf("%25s%2.2X : %4.4X\n", "Word", i, data[i]);
    583	}
    584}