Merge tag 'phy-fixes-5.13' of git://git.kernel.org/pub/scm/linux/kernel/git/phy/linux...
[linux-2.6-microblaze.git] / drivers / acpi / acpica / dbstats.c
1 // SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
2 /*******************************************************************************
3  *
4  * Module Name: dbstats - Generation and display of ACPI table statistics
5  *
6  ******************************************************************************/
7
8 #include <acpi/acpi.h>
9 #include "accommon.h"
10 #include "acdebug.h"
11 #include "acnamesp.h"
12
13 #define _COMPONENT          ACPI_CA_DEBUGGER
14 ACPI_MODULE_NAME("dbstats")
15
16 /* Local prototypes */
17 static void acpi_db_count_namespace_objects(void);
18
19 static void acpi_db_enumerate_object(union acpi_operand_object *obj_desc);
20
21 static acpi_status
22 acpi_db_classify_one_object(acpi_handle obj_handle,
23                             u32 nesting_level,
24                             void *context, void **return_value);
25
26 #if defined ACPI_DBG_TRACK_ALLOCATIONS || defined ACPI_USE_LOCAL_CACHE
27 static void acpi_db_list_info(struct acpi_memory_list *list);
28 #endif
29
30 /*
31  * Statistics subcommands
32  */
33 static struct acpi_db_argument_info acpi_db_stat_types[] = {
34         {"ALLOCATIONS"},
35         {"OBJECTS"},
36         {"MEMORY"},
37         {"MISC"},
38         {"TABLES"},
39         {"SIZES"},
40         {"STACK"},
41         {NULL}                  /* Must be null terminated */
42 };
43
44 #define CMD_STAT_ALLOCATIONS     0
45 #define CMD_STAT_OBJECTS         1
46 #define CMD_STAT_MEMORY          2
47 #define CMD_STAT_MISC            3
48 #define CMD_STAT_TABLES          4
49 #define CMD_STAT_SIZES           5
50 #define CMD_STAT_STACK           6
51
52 #if defined ACPI_DBG_TRACK_ALLOCATIONS || defined ACPI_USE_LOCAL_CACHE
53 /*******************************************************************************
54  *
55  * FUNCTION:    acpi_db_list_info
56  *
57  * PARAMETERS:  list            - Memory list/cache to be displayed
58  *
59  * RETURN:      None
60  *
61  * DESCRIPTION: Display information about the input memory list or cache.
62  *
63  ******************************************************************************/
64
65 static void acpi_db_list_info(struct acpi_memory_list *list)
66 {
67 #ifdef ACPI_DBG_TRACK_ALLOCATIONS
68         u32 outstanding;
69 #endif
70
71         acpi_os_printf("\n%s\n", list->list_name);
72
73         /* max_depth > 0 indicates a cache object */
74
75         if (list->max_depth > 0) {
76                 acpi_os_printf
77                     ("    Cache: [Depth    MaxD Avail  Size]                "
78                      "%8.2X %8.2X %8.2X %8.2X\n", list->current_depth,
79                      list->max_depth, list->max_depth - list->current_depth,
80                      (list->current_depth * list->object_size));
81         }
82 #ifdef ACPI_DBG_TRACK_ALLOCATIONS
83         if (list->max_depth > 0) {
84                 acpi_os_printf
85                     ("    Cache: [Requests Hits Misses ObjSize]             "
86                      "%8.2X %8.2X %8.2X %8.2X\n", list->requests, list->hits,
87                      list->requests - list->hits, list->object_size);
88         }
89
90         outstanding = acpi_db_get_cache_info(list);
91
92         if (list->object_size) {
93                 acpi_os_printf
94                     ("    Mem:   [Alloc    Free Max    CurSize Outstanding] "
95                      "%8.2X %8.2X %8.2X %8.2X %8.2X\n", list->total_allocated,
96                      list->total_freed, list->max_occupied,
97                      outstanding * list->object_size, outstanding);
98         } else {
99                 acpi_os_printf
100                     ("    Mem:   [Alloc Free Max CurSize Outstanding Total] "
101                      "%8.2X %8.2X %8.2X %8.2X %8.2X %8.2X\n",
102                      list->total_allocated, list->total_freed,
103                      list->max_occupied, list->current_total_size, outstanding,
104                      list->total_size);
105         }
106 #endif
107 }
108 #endif
109
110 /*******************************************************************************
111  *
112  * FUNCTION:    acpi_db_enumerate_object
113  *
114  * PARAMETERS:  obj_desc            - Object to be counted
115  *
116  * RETURN:      None
117  *
118  * DESCRIPTION: Add this object to the global counts, by object type.
119  *              Limited recursion handles subobjects and packages, and this
120  *              is probably acceptable within the AML debugger only.
121  *
122  ******************************************************************************/
123
124 static void acpi_db_enumerate_object(union acpi_operand_object *obj_desc)
125 {
126         u32 i;
127
128         if (!obj_desc) {
129                 return;
130         }
131
132         /* Enumerate this object first */
133
134         acpi_gbl_num_objects++;
135
136         if (obj_desc->common.type > ACPI_TYPE_NS_NODE_MAX) {
137                 acpi_gbl_obj_type_count_misc++;
138         } else {
139                 acpi_gbl_obj_type_count[obj_desc->common.type]++;
140         }
141
142         /* Count the sub-objects */
143
144         switch (obj_desc->common.type) {
145         case ACPI_TYPE_PACKAGE:
146
147                 for (i = 0; i < obj_desc->package.count; i++) {
148                         acpi_db_enumerate_object(obj_desc->package.elements[i]);
149                 }
150                 break;
151
152         case ACPI_TYPE_DEVICE:
153
154                 acpi_db_enumerate_object(obj_desc->device.notify_list[0]);
155                 acpi_db_enumerate_object(obj_desc->device.notify_list[1]);
156                 acpi_db_enumerate_object(obj_desc->device.handler);
157                 break;
158
159         case ACPI_TYPE_BUFFER_FIELD:
160
161                 if (acpi_ns_get_secondary_object(obj_desc)) {
162                         acpi_gbl_obj_type_count[ACPI_TYPE_BUFFER_FIELD]++;
163                 }
164                 break;
165
166         case ACPI_TYPE_REGION:
167
168                 acpi_gbl_obj_type_count[ACPI_TYPE_LOCAL_REGION_FIELD]++;
169                 acpi_db_enumerate_object(obj_desc->region.handler);
170                 break;
171
172         case ACPI_TYPE_POWER:
173
174                 acpi_db_enumerate_object(obj_desc->power_resource.
175                                          notify_list[0]);
176                 acpi_db_enumerate_object(obj_desc->power_resource.
177                                          notify_list[1]);
178                 break;
179
180         case ACPI_TYPE_PROCESSOR:
181
182                 acpi_db_enumerate_object(obj_desc->processor.notify_list[0]);
183                 acpi_db_enumerate_object(obj_desc->processor.notify_list[1]);
184                 acpi_db_enumerate_object(obj_desc->processor.handler);
185                 break;
186
187         case ACPI_TYPE_THERMAL:
188
189                 acpi_db_enumerate_object(obj_desc->thermal_zone.notify_list[0]);
190                 acpi_db_enumerate_object(obj_desc->thermal_zone.notify_list[1]);
191                 acpi_db_enumerate_object(obj_desc->thermal_zone.handler);
192                 break;
193
194         default:
195
196                 break;
197         }
198 }
199
200 /*******************************************************************************
201  *
202  * FUNCTION:    acpi_db_classify_one_object
203  *
204  * PARAMETERS:  Callback for walk_namespace
205  *
206  * RETURN:      Status
207  *
208  * DESCRIPTION: Enumerate both the object descriptor (including subobjects) and
209  *              the parent namespace node.
210  *
211  ******************************************************************************/
212
213 static acpi_status
214 acpi_db_classify_one_object(acpi_handle obj_handle,
215                             u32 nesting_level,
216                             void *context, void **return_value)
217 {
218         struct acpi_namespace_node *node;
219         union acpi_operand_object *obj_desc;
220         u32 type;
221
222         acpi_gbl_num_nodes++;
223
224         node = (struct acpi_namespace_node *)obj_handle;
225         obj_desc = acpi_ns_get_attached_object(node);
226
227         acpi_db_enumerate_object(obj_desc);
228
229         type = node->type;
230         if (type > ACPI_TYPE_NS_NODE_MAX) {
231                 acpi_gbl_node_type_count_misc++;
232         } else {
233                 acpi_gbl_node_type_count[type]++;
234         }
235
236         return (AE_OK);
237
238 #ifdef ACPI_FUTURE_IMPLEMENTATION
239
240         /* TBD: These need to be counted during the initial parsing phase */
241
242         if (acpi_ps_is_named_op(op->opcode)) {
243                 num_nodes++;
244         }
245
246         if (is_method) {
247                 num_method_elements++;
248         }
249
250         num_grammar_elements++;
251         op = acpi_ps_get_depth_next(root, op);
252
253         size_of_parse_tree = (num_grammar_elements - num_method_elements) *
254             (u32)sizeof(union acpi_parse_object);
255         size_of_method_trees =
256             num_method_elements * (u32)sizeof(union acpi_parse_object);
257         size_of_node_entries =
258             num_nodes * (u32)sizeof(struct acpi_namespace_node);
259         size_of_acpi_objects =
260             num_nodes * (u32)sizeof(union acpi_operand_object);
261 #endif
262 }
263
264 /*******************************************************************************
265  *
266  * FUNCTION:    acpi_db_count_namespace_objects
267  *
268  * PARAMETERS:  None
269  *
270  * RETURN:      None
271  *
272  * DESCRIPTION: Count and classify the entire namespace, including all
273  *              namespace nodes and attached objects.
274  *
275  ******************************************************************************/
276
277 static void acpi_db_count_namespace_objects(void)
278 {
279         u32 i;
280
281         acpi_gbl_num_nodes = 0;
282         acpi_gbl_num_objects = 0;
283
284         acpi_gbl_obj_type_count_misc = 0;
285         for (i = 0; i < (ACPI_TYPE_NS_NODE_MAX - 1); i++) {
286                 acpi_gbl_obj_type_count[i] = 0;
287                 acpi_gbl_node_type_count[i] = 0;
288         }
289
290         (void)acpi_ns_walk_namespace(ACPI_TYPE_ANY, ACPI_ROOT_OBJECT,
291                                      ACPI_UINT32_MAX, FALSE,
292                                      acpi_db_classify_one_object, NULL, NULL,
293                                      NULL);
294 }
295
296 /*******************************************************************************
297  *
298  * FUNCTION:    acpi_db_display_statistics
299  *
300  * PARAMETERS:  type_arg        - Subcommand
301  *
302  * RETURN:      Status
303  *
304  * DESCRIPTION: Display various statistics
305  *
306  ******************************************************************************/
307
308 acpi_status acpi_db_display_statistics(char *type_arg)
309 {
310         u32 i;
311         u32 temp;
312
313         acpi_ut_strupr(type_arg);
314         temp = acpi_db_match_argument(type_arg, acpi_db_stat_types);
315         if (temp == ACPI_TYPE_NOT_FOUND) {
316                 acpi_os_printf("Invalid or unsupported argument\n");
317                 return (AE_OK);
318         }
319
320         switch (temp) {
321         case CMD_STAT_ALLOCATIONS:
322
323 #ifdef ACPI_DBG_TRACK_ALLOCATIONS
324                 acpi_ut_dump_allocation_info();
325 #endif
326                 break;
327
328         case CMD_STAT_TABLES:
329
330                 acpi_os_printf("ACPI Table Information (not implemented):\n\n");
331                 break;
332
333         case CMD_STAT_OBJECTS:
334
335                 acpi_db_count_namespace_objects();
336
337                 acpi_os_printf
338                     ("\nObjects defined in the current namespace:\n\n");
339
340                 acpi_os_printf("%16.16s %10.10s %10.10s\n",
341                                "ACPI_TYPE", "NODES", "OBJECTS");
342
343                 for (i = 0; i < ACPI_TYPE_NS_NODE_MAX; i++) {
344                         acpi_os_printf("%16.16s %10u %10u\n",
345                                        acpi_ut_get_type_name(i),
346                                        acpi_gbl_node_type_count[i],
347                                        acpi_gbl_obj_type_count[i]);
348                 }
349
350                 acpi_os_printf("%16.16s %10u %10u\n", "Misc/Unknown",
351                                acpi_gbl_node_type_count_misc,
352                                acpi_gbl_obj_type_count_misc);
353
354                 acpi_os_printf("%16.16s %10u %10u\n", "TOTALS:",
355                                acpi_gbl_num_nodes, acpi_gbl_num_objects);
356                 break;
357
358         case CMD_STAT_MEMORY:
359
360 #ifdef ACPI_DBG_TRACK_ALLOCATIONS
361                 acpi_os_printf
362                     ("\n----Object Statistics (all in hex)---------\n");
363
364                 acpi_db_list_info(acpi_gbl_global_list);
365                 acpi_db_list_info(acpi_gbl_ns_node_list);
366 #endif
367
368 #ifdef ACPI_USE_LOCAL_CACHE
369                 acpi_os_printf
370                     ("\n----Cache Statistics (all in hex)---------\n");
371                 acpi_db_list_info(acpi_gbl_operand_cache);
372                 acpi_db_list_info(acpi_gbl_ps_node_cache);
373                 acpi_db_list_info(acpi_gbl_ps_node_ext_cache);
374                 acpi_db_list_info(acpi_gbl_state_cache);
375 #endif
376
377                 break;
378
379         case CMD_STAT_MISC:
380
381                 acpi_os_printf("\nMiscellaneous Statistics:\n\n");
382                 acpi_os_printf("%-28s:     %7u\n", "Calls to AcpiPsFind",
383                                acpi_gbl_ps_find_count);
384                 acpi_os_printf("%-28s:     %7u\n", "Calls to AcpiNsLookup",
385                                acpi_gbl_ns_lookup_count);
386
387                 acpi_os_printf("\nMutex usage:\n\n");
388                 for (i = 0; i < ACPI_NUM_MUTEX; i++) {
389                         acpi_os_printf("%-28s:     %7u\n",
390                                        acpi_ut_get_mutex_name(i),
391                                        acpi_gbl_mutex_info[i].use_count);
392                 }
393                 break;
394
395         case CMD_STAT_SIZES:
396
397                 acpi_os_printf("\nInternal object sizes:\n\n");
398
399                 acpi_os_printf("Common         %3d\n",
400                                (u32)sizeof(struct acpi_object_common));
401                 acpi_os_printf("Number         %3d\n",
402                                (u32)sizeof(struct acpi_object_integer));
403                 acpi_os_printf("String         %3d\n",
404                                (u32)sizeof(struct acpi_object_string));
405                 acpi_os_printf("Buffer         %3d\n",
406                                (u32)sizeof(struct acpi_object_buffer));
407                 acpi_os_printf("Package        %3d\n",
408                                (u32)sizeof(struct acpi_object_package));
409                 acpi_os_printf("BufferField    %3d\n",
410                                (u32)sizeof(struct acpi_object_buffer_field));
411                 acpi_os_printf("Device         %3d\n",
412                                (u32)sizeof(struct acpi_object_device));
413                 acpi_os_printf("Event          %3d\n",
414                                (u32)sizeof(struct acpi_object_event));
415                 acpi_os_printf("Method         %3d\n",
416                                (u32)sizeof(struct acpi_object_method));
417                 acpi_os_printf("Mutex          %3d\n",
418                                (u32)sizeof(struct acpi_object_mutex));
419                 acpi_os_printf("Region         %3d\n",
420                                (u32)sizeof(struct acpi_object_region));
421                 acpi_os_printf("PowerResource  %3d\n",
422                                (u32)sizeof(struct acpi_object_power_resource));
423                 acpi_os_printf("Processor      %3d\n",
424                                (u32)sizeof(struct acpi_object_processor));
425                 acpi_os_printf("ThermalZone    %3d\n",
426                                (u32)sizeof(struct acpi_object_thermal_zone));
427                 acpi_os_printf("RegionField    %3d\n",
428                                (u32)sizeof(struct acpi_object_region_field));
429                 acpi_os_printf("BankField      %3d\n",
430                                (u32)sizeof(struct acpi_object_bank_field));
431                 acpi_os_printf("IndexField     %3d\n",
432                                (u32)sizeof(struct acpi_object_index_field));
433                 acpi_os_printf("Reference      %3d\n",
434                                (u32)sizeof(struct acpi_object_reference));
435                 acpi_os_printf("Notify         %3d\n",
436                                (u32)sizeof(struct acpi_object_notify_handler));
437                 acpi_os_printf("AddressSpace   %3d\n",
438                                (u32)sizeof(struct acpi_object_addr_handler));
439                 acpi_os_printf("Extra          %3d\n",
440                                (u32)sizeof(struct acpi_object_extra));
441                 acpi_os_printf("Data           %3d\n",
442                                (u32)sizeof(struct acpi_object_data));
443
444                 acpi_os_printf("\n");
445
446                 acpi_os_printf("ParseObject    %3d\n",
447                                (u32)sizeof(struct acpi_parse_obj_common));
448                 acpi_os_printf("ParseObjectNamed %3d\n",
449                                (u32)sizeof(struct acpi_parse_obj_named));
450                 acpi_os_printf("ParseObjectAsl %3d\n",
451                                (u32)sizeof(struct acpi_parse_obj_asl));
452                 acpi_os_printf("OperandObject  %3d\n",
453                                (u32)sizeof(union acpi_operand_object));
454                 acpi_os_printf("NamespaceNode  %3d\n",
455                                (u32)sizeof(struct acpi_namespace_node));
456                 acpi_os_printf("AcpiObject     %3d\n",
457                                (u32)sizeof(union acpi_object));
458
459                 acpi_os_printf("\n");
460
461                 acpi_os_printf("Generic State  %3d\n",
462                                (u32)sizeof(union acpi_generic_state));
463                 acpi_os_printf("Common State   %3d\n",
464                                (u32)sizeof(struct acpi_common_state));
465                 acpi_os_printf("Control State  %3d\n",
466                                (u32)sizeof(struct acpi_control_state));
467                 acpi_os_printf("Update State   %3d\n",
468                                (u32)sizeof(struct acpi_update_state));
469                 acpi_os_printf("Scope State    %3d\n",
470                                (u32)sizeof(struct acpi_scope_state));
471                 acpi_os_printf("Parse Scope    %3d\n",
472                                (u32)sizeof(struct acpi_pscope_state));
473                 acpi_os_printf("Package State  %3d\n",
474                                (u32)sizeof(struct acpi_pkg_state));
475                 acpi_os_printf("Thread State   %3d\n",
476                                (u32)sizeof(struct acpi_thread_state));
477                 acpi_os_printf("Result Values  %3d\n",
478                                (u32)sizeof(struct acpi_result_values));
479                 acpi_os_printf("Notify Info    %3d\n",
480                                (u32)sizeof(struct acpi_notify_info));
481                 break;
482
483         case CMD_STAT_STACK:
484 #if defined(ACPI_DEBUG_OUTPUT)
485
486                 temp =
487                     (u32)ACPI_PTR_DIFF(acpi_gbl_entry_stack_pointer,
488                                        acpi_gbl_lowest_stack_pointer);
489
490                 acpi_os_printf("\nSubsystem Stack Usage:\n\n");
491                 acpi_os_printf("Entry Stack Pointer        %p\n",
492                                acpi_gbl_entry_stack_pointer);
493                 acpi_os_printf("Lowest Stack Pointer       %p\n",
494                                acpi_gbl_lowest_stack_pointer);
495                 acpi_os_printf("Stack Use                  %X (%u)\n", temp,
496                                temp);
497                 acpi_os_printf("Deepest Procedure Nesting  %u\n",
498                                acpi_gbl_deepest_nesting);
499 #endif
500                 break;
501
502         default:
503
504                 break;
505         }
506
507         acpi_os_printf("\n");
508         return (AE_OK);
509 }