VirtualBox

source: vbox/trunk/src/VBox/Devices/EFI/FirmwareNew/ShellPkg/Library/UefiShellAcpiViewCommandLib/AcpiView.c@ 85718

Last change on this file since 85718 was 85718, checked in by vboxsync, 5 years ago

Devices/EFI: Merge edk-stable202005 and make it build, bugref:4643

  • Property svn:eol-style set to native
File size: 18.4 KB
Line 
1/** @file
2
3 Copyright (c) 2016 - 2020, ARM Limited. All rights reserved.
4 SPDX-License-Identifier: BSD-2-Clause-Patent
5
6 @par Glossary:
7 - Sbbr or SBBR - Server Base Boot Requirements
8
9 @par Reference(s):
10 - Arm Server Base Boot Requirements 1.2, September 2019
11**/
12
13#include <Library/PrintLib.h>
14#include <Library/UefiLib.h>
15#include <Library/ShellLib.h>
16#include <Library/UefiBootServicesTableLib.h>
17#include <Library/BaseMemoryLib.h>
18#include <Library/DebugLib.h>
19#include <Library/MemoryAllocationLib.h>
20#include "AcpiParser.h"
21#include "AcpiTableParser.h"
22#include "AcpiView.h"
23#include "UefiShellAcpiViewCommandLib.h"
24
25#if defined(MDE_CPU_ARM) || defined (MDE_CPU_AARCH64)
26#include "Arm/SbbrValidator.h"
27#endif
28
29EFI_HII_HANDLE gShellAcpiViewHiiHandle = NULL;
30
31// Report variables
32STATIC UINT32 mSelectedAcpiTable;
33STATIC CONST CHAR16* mSelectedAcpiTableName;
34STATIC BOOLEAN mSelectedAcpiTableFound;
35STATIC EREPORT_OPTION mReportType;
36STATIC UINT32 mTableCount;
37STATIC UINT32 mBinTableCount;
38STATIC BOOLEAN mConsistencyCheck;
39STATIC BOOLEAN mColourHighlighting;
40STATIC BOOLEAN mMandatoryTableValidate;
41STATIC UINTN mMandatoryTableSpec;
42
43/**
44 An array of acpiview command line parameters.
45**/
46STATIC CONST SHELL_PARAM_ITEM ParamList[] = {
47 {L"-q", TypeFlag},
48 {L"-d", TypeFlag},
49 {L"-h", TypeFlag},
50 {L"-l", TypeFlag},
51 {L"-s", TypeValue},
52 {L"-r", TypeValue},
53 {NULL, TypeMax}
54};
55
56/**
57 This function returns the colour highlighting status.
58
59 @retval TRUE if colour highlighting is enabled.
60**/
61BOOLEAN
62GetColourHighlighting (
63 VOID
64 )
65{
66 return mColourHighlighting;
67}
68
69/**
70 This function sets the colour highlighting status.
71
72 @param Highlight The Highlight status.
73
74**/
75VOID
76SetColourHighlighting (
77 BOOLEAN Highlight
78 )
79{
80 mColourHighlighting = Highlight;
81}
82
83/**
84 This function returns the consistency checking status.
85
86 @retval TRUE if consistency checking is enabled.
87**/
88BOOLEAN
89GetConsistencyChecking (
90 VOID
91 )
92{
93 return mConsistencyCheck;
94}
95
96/**
97 This function sets the consistency checking status.
98
99 @param ConsistencyChecking The consistency checking status.
100
101**/
102VOID
103SetConsistencyChecking (
104 BOOLEAN ConsistencyChecking
105 )
106{
107 mConsistencyCheck = ConsistencyChecking;
108}
109
110/**
111 This function returns the ACPI table requirements validation flag.
112
113 @retval TRUE if check for mandatory table presence should be performed.
114**/
115BOOLEAN
116GetMandatoryTableValidate (
117 VOID
118 )
119{
120 return mMandatoryTableValidate;
121}
122
123/**
124 This function sets the ACPI table requirements validation flag.
125
126 @param Validate Enable/Disable ACPI table requirements validation.
127**/
128VOID
129SetMandatoryTableValidate (
130 BOOLEAN Validate
131 )
132{
133 mMandatoryTableValidate = Validate;
134}
135
136/**
137 This function returns the identifier of specification to validate ACPI table
138 requirements against.
139
140 @return ID of specification listing mandatory tables.
141**/
142UINTN
143GetMandatoryTableSpec (
144 VOID
145 )
146{
147 return mMandatoryTableSpec;
148}
149
150/**
151 This function sets the identifier of specification to validate ACPI table
152 requirements against.
153
154 @param Spec ID of specification listing mandatory tables.
155**/
156VOID
157SetMandatoryTableSpec (
158 UINTN Spec
159 )
160{
161 mMandatoryTableSpec = Spec;
162}
163
164/**
165 This function returns the report options.
166
167 @retval Returns the report option.
168**/
169STATIC
170EREPORT_OPTION
171GetReportOption (
172 VOID
173 )
174{
175 return mReportType;
176}
177
178/**
179 This function returns the selected ACPI table.
180
181 @retval Returns signature of the selected ACPI table.
182**/
183STATIC
184UINT32
185GetSelectedAcpiTable (
186 VOID
187 )
188{
189 return mSelectedAcpiTable;
190}
191
192/**
193 This function dumps the ACPI table to a file.
194
195 @param [in] Ptr Pointer to the ACPI table data.
196 @param [in] Length The length of the ACPI table.
197
198 @retval TRUE Success.
199 @retval FALSE Failure.
200**/
201STATIC
202BOOLEAN
203DumpAcpiTableToFile (
204 IN CONST UINT8* Ptr,
205 IN CONST UINTN Length
206 )
207{
208 EFI_STATUS Status;
209 CHAR16 FileNameBuffer[MAX_FILE_NAME_LEN];
210 SHELL_FILE_HANDLE DumpFileHandle;
211 UINTN TransferBytes;
212
213 DumpFileHandle = NULL;
214 TransferBytes = Length;
215
216 UnicodeSPrint (
217 FileNameBuffer,
218 sizeof (FileNameBuffer),
219 L".\\%s%04d.bin",
220 mSelectedAcpiTableName,
221 mBinTableCount++
222 );
223
224 Status = ShellOpenFileByName (
225 FileNameBuffer,
226 &DumpFileHandle,
227 EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE,
228 0
229 );
230 if (EFI_ERROR (Status)) {
231 ShellPrintHiiEx (
232 -1,
233 -1,
234 NULL,
235 STRING_TOKEN (STR_GEN_READONLY_MEDIA),
236 gShellAcpiViewHiiHandle,
237 L"acpiview"
238 );
239 return FALSE;
240 }
241
242 Print (L"Dumping ACPI table to : %s ... ", FileNameBuffer);
243
244 Status = ShellWriteFile (
245 DumpFileHandle,
246 &TransferBytes,
247 (VOID*)Ptr
248 );
249 if (EFI_ERROR (Status)) {
250 Print (L"ERROR: Failed to dump table to binary file.\n");
251 TransferBytes = 0;
252 } else {
253 Print (L"DONE.\n");
254 }
255
256 ShellCloseFile (&DumpFileHandle);
257 return (Length == TransferBytes);
258}
259
260/**
261 This function processes the table reporting options for the ACPI table.
262
263 @param [in] Signature The ACPI table Signature.
264 @param [in] TablePtr Pointer to the ACPI table data.
265 @param [in] Length The length fo the ACPI table.
266
267 @retval Returns TRUE if the ACPI table should be traced.
268**/
269BOOLEAN
270ProcessTableReportOptions (
271 IN CONST UINT32 Signature,
272 IN CONST UINT8* TablePtr,
273 IN CONST UINT32 Length
274 )
275{
276 UINTN OriginalAttribute;
277 UINT8* SignaturePtr;
278 BOOLEAN Log;
279 BOOLEAN HighLight;
280
281 //
282 // set local variables to suppress incorrect compiler/analyzer warnings
283 //
284 OriginalAttribute = 0;
285 SignaturePtr = (UINT8*)(UINTN)&Signature;
286 Log = FALSE;
287 HighLight = GetColourHighlighting ();
288
289 switch (GetReportOption ()) {
290 case ReportAll:
291 Log = TRUE;
292 break;
293 case ReportSelected:
294 if (Signature == GetSelectedAcpiTable ()) {
295 Log = TRUE;
296 mSelectedAcpiTableFound = TRUE;
297 }
298 break;
299 case ReportTableList:
300 if (mTableCount == 0) {
301 if (HighLight) {
302 OriginalAttribute = gST->ConOut->Mode->Attribute;
303 gST->ConOut->SetAttribute (
304 gST->ConOut,
305 EFI_TEXT_ATTR(EFI_CYAN,
306 ((OriginalAttribute&(BIT4|BIT5|BIT6))>>4))
307 );
308 }
309 Print (L"\nInstalled Table(s):\n");
310 if (HighLight) {
311 gST->ConOut->SetAttribute (gST->ConOut, OriginalAttribute);
312 }
313 }
314 Print (
315 L"\t%4d. %c%c%c%c\n",
316 ++mTableCount,
317 SignaturePtr[0],
318 SignaturePtr[1],
319 SignaturePtr[2],
320 SignaturePtr[3]
321 );
322 break;
323 case ReportDumpBinFile:
324 if (Signature == GetSelectedAcpiTable ()) {
325 mSelectedAcpiTableFound = TRUE;
326 DumpAcpiTableToFile (TablePtr, Length);
327 }
328 break;
329 case ReportMax:
330 // We should never be here.
331 // This case is only present to prevent compiler warning.
332 break;
333 } // switch
334
335 if (Log) {
336 if (HighLight) {
337 OriginalAttribute = gST->ConOut->Mode->Attribute;
338 gST->ConOut->SetAttribute (
339 gST->ConOut,
340 EFI_TEXT_ATTR(EFI_LIGHTBLUE,
341 ((OriginalAttribute&(BIT4|BIT5|BIT6))>>4))
342 );
343 }
344 Print (
345 L"\n\n --------------- %c%c%c%c Table --------------- \n\n",
346 SignaturePtr[0],
347 SignaturePtr[1],
348 SignaturePtr[2],
349 SignaturePtr[3]
350 );
351 if (HighLight) {
352 gST->ConOut->SetAttribute (gST->ConOut, OriginalAttribute);
353 }
354 }
355
356 return Log;
357}
358
359/**
360 This function converts a string to ACPI table signature.
361
362 @param [in] Str Pointer to the string to be converted to the
363 ACPI table signature.
364
365 @retval The ACPI table signature.
366**/
367STATIC
368UINT32
369ConvertStrToAcpiSignature (
370 IN CONST CHAR16* Str
371 )
372{
373 UINT8 Index;
374 CHAR8 Ptr[4];
375
376 ZeroMem (Ptr, sizeof (Ptr));
377 Index = 0;
378
379 // Convert to Upper case and convert to ASCII
380 while ((Index < 4) && (Str[Index] != 0)) {
381 if (Str[Index] >= L'a' && Str[Index] <= L'z') {
382 Ptr[Index] = (CHAR8)(Str[Index] - (L'a' - L'A'));
383 } else {
384 Ptr[Index] = (CHAR8)Str[Index];
385 }
386 Index++;
387 }
388 return *(UINT32*)Ptr;
389}
390
391/**
392 This function iterates the configuration table entries in the
393 system table, retrieves the RSDP pointer and starts parsing the ACPI tables.
394
395 @param [in] SystemTable Pointer to the EFI system table.
396
397 @retval Returns EFI_NOT_FOUND if the RSDP pointer is not found.
398 Returns EFI_UNSUPPORTED if the RSDP version is less than 2.
399 Returns EFI_SUCCESS if successful.
400**/
401STATIC
402EFI_STATUS
403EFIAPI
404AcpiView (
405 IN EFI_SYSTEM_TABLE* SystemTable
406 )
407{
408 EFI_STATUS Status;
409 UINTN Index;
410 EFI_CONFIGURATION_TABLE* EfiConfigurationTable;
411 BOOLEAN FoundAcpiTable;
412 UINTN OriginalAttribute;
413 UINTN PrintAttribute;
414 EREPORT_OPTION ReportOption;
415 UINT8* RsdpPtr;
416 UINT32 RsdpLength;
417 UINT8 RsdpRevision;
418 PARSE_ACPI_TABLE_PROC RsdpParserProc;
419 BOOLEAN Trace;
420
421 //
422 // set local variables to suppress incorrect compiler/analyzer warnings
423 //
424 EfiConfigurationTable = NULL;
425 OriginalAttribute = 0;
426
427 // Search the table for an entry that matches the ACPI Table Guid
428 FoundAcpiTable = FALSE;
429 for (Index = 0; Index < SystemTable->NumberOfTableEntries; Index++) {
430 if (CompareGuid (&gEfiAcpiTableGuid,
431 &(SystemTable->ConfigurationTable[Index].VendorGuid))) {
432 EfiConfigurationTable = &SystemTable->ConfigurationTable[Index];
433 FoundAcpiTable = TRUE;
434 break;
435 }
436 }
437
438 if (FoundAcpiTable) {
439 RsdpPtr = (UINT8*)EfiConfigurationTable->VendorTable;
440
441 // The RSDP revision is 1 byte starting at offset 15
442 RsdpRevision = *(RsdpPtr + RSDP_REVISION_OFFSET);
443
444 if (RsdpRevision < 2) {
445 Print (
446 L"ERROR: RSDP version less than 2 is not supported.\n"
447 );
448 return EFI_UNSUPPORTED;
449 }
450
451#if defined(MDE_CPU_ARM) || defined (MDE_CPU_AARCH64)
452 if (GetMandatoryTableValidate ()) {
453 ArmSbbrResetTableCounts ();
454 }
455#endif
456
457 // The RSDP length is 4 bytes starting at offset 20
458 RsdpLength = *(UINT32*)(RsdpPtr + RSDP_LENGTH_OFFSET);
459
460 Trace = ProcessTableReportOptions (RSDP_TABLE_INFO, RsdpPtr, RsdpLength);
461
462 Status = GetParser (RSDP_TABLE_INFO, &RsdpParserProc);
463 if (EFI_ERROR (Status)) {
464 Print (
465 L"ERROR: No registered parser found for RSDP.\n"
466 );
467 return Status;
468 }
469
470 RsdpParserProc (
471 Trace,
472 RsdpPtr,
473 RsdpLength,
474 RsdpRevision
475 );
476
477 } else {
478 IncrementErrorCount ();
479 Print (
480 L"ERROR: Failed to find ACPI Table Guid in System Configuration Table.\n"
481 );
482 return EFI_NOT_FOUND;
483 }
484
485#if defined(MDE_CPU_ARM) || defined (MDE_CPU_AARCH64)
486 if (GetMandatoryTableValidate ()) {
487 ArmSbbrReqsValidate ((ARM_SBBR_VERSION)GetMandatoryTableSpec ());
488 }
489#endif
490
491 ReportOption = GetReportOption ();
492 if (ReportTableList != ReportOption) {
493 if (((ReportSelected == ReportOption) ||
494 (ReportDumpBinFile == ReportOption)) &&
495 (!mSelectedAcpiTableFound)) {
496 Print (L"\nRequested ACPI Table not found.\n");
497 } else if (GetConsistencyChecking () &&
498 (ReportDumpBinFile != ReportOption)) {
499 OriginalAttribute = gST->ConOut->Mode->Attribute;
500
501 Print (L"\nTable Statistics:\n");
502
503 if (GetColourHighlighting ()) {
504 PrintAttribute = (GetErrorCount () > 0) ?
505 EFI_TEXT_ATTR (
506 EFI_RED,
507 ((OriginalAttribute&(BIT4|BIT5|BIT6))>>4)
508 ) :
509 OriginalAttribute;
510 gST->ConOut->SetAttribute (gST->ConOut, PrintAttribute);
511 }
512 Print (L"\t%d Error(s)\n", GetErrorCount ());
513
514 if (GetColourHighlighting ()) {
515 PrintAttribute = (GetWarningCount () > 0) ?
516 EFI_TEXT_ATTR (
517 EFI_RED,
518 ((OriginalAttribute&(BIT4|BIT5|BIT6))>>4)
519 ) :
520 OriginalAttribute;
521
522 gST->ConOut->SetAttribute (gST->ConOut, PrintAttribute);
523 }
524 Print (L"\t%d Warning(s)\n", GetWarningCount ());
525
526 if (GetColourHighlighting ()) {
527 gST->ConOut->SetAttribute (gST->ConOut, OriginalAttribute);
528 }
529 }
530 }
531 return EFI_SUCCESS;
532}
533
534/**
535 Function for 'acpiview' command.
536
537 @param[in] ImageHandle Handle to the Image (NULL if Internal).
538 @param[in] SystemTable Pointer to the System Table (NULL if Internal).
539**/
540SHELL_STATUS
541EFIAPI
542ShellCommandRunAcpiView (
543 IN EFI_HANDLE ImageHandle,
544 IN EFI_SYSTEM_TABLE* SystemTable
545 )
546{
547 EFI_STATUS Status;
548 SHELL_STATUS ShellStatus;
549 LIST_ENTRY* Package;
550 CHAR16* ProblemParam;
551 SHELL_FILE_HANDLE TmpDumpFileHandle;
552 CONST CHAR16* MandatoryTableSpecStr;
553
554 // Set Defaults
555 mReportType = ReportAll;
556 mTableCount = 0;
557 mBinTableCount = 0;
558 mSelectedAcpiTable = 0;
559 mSelectedAcpiTableName = NULL;
560 mSelectedAcpiTableFound = FALSE;
561 mConsistencyCheck = TRUE;
562 mMandatoryTableValidate = FALSE;
563 mMandatoryTableSpec = 0;
564
565 ShellStatus = SHELL_SUCCESS;
566 Package = NULL;
567 TmpDumpFileHandle = NULL;
568
569 // Reset The error/warning counters
570 ResetErrorCount ();
571 ResetWarningCount ();
572
573 Status = ShellCommandLineParse (ParamList, &Package, &ProblemParam, TRUE);
574 if (EFI_ERROR (Status)) {
575 if (Status == EFI_VOLUME_CORRUPTED && ProblemParam != NULL) {
576 ShellPrintHiiEx (
577 -1,
578 -1,
579 NULL,
580 STRING_TOKEN (STR_GEN_PROBLEM),
581 gShellAcpiViewHiiHandle,
582 L"acpiview",
583 ProblemParam
584 );
585 FreePool (ProblemParam);
586 } else {
587 Print (L"acpiview: Error processing input parameter(s)\n");
588 }
589 ShellStatus = SHELL_INVALID_PARAMETER;
590 } else {
591 if (ShellCommandLineGetCount (Package) > 1) {
592 ShellPrintHiiEx (
593 -1,
594 -1,
595 NULL,
596 STRING_TOKEN (STR_GEN_TOO_MANY),
597 gShellAcpiViewHiiHandle,
598 L"acpiview"
599 );
600 ShellStatus = SHELL_INVALID_PARAMETER;
601 } else if (ShellCommandLineGetFlag (Package, L"-?")) {
602 ShellPrintHiiEx (
603 -1,
604 -1,
605 NULL,
606 STRING_TOKEN (STR_GET_HELP_ACPIVIEW),
607 gShellAcpiViewHiiHandle,
608 L"acpiview"
609 );
610 } else if (ShellCommandLineGetFlag (Package, L"-s") &&
611 ShellCommandLineGetValue (Package, L"-s") == NULL) {
612 ShellPrintHiiEx (
613 -1,
614 -1,
615 NULL,
616 STRING_TOKEN (STR_GEN_NO_VALUE),
617 gShellAcpiViewHiiHandle,
618 L"acpiview",
619 L"-s"
620 );
621 ShellStatus = SHELL_INVALID_PARAMETER;
622 } else if (ShellCommandLineGetFlag (Package, L"-r") &&
623 ShellCommandLineGetValue (Package, L"-r") == NULL) {
624 ShellPrintHiiEx (
625 -1,
626 -1,
627 NULL,
628 STRING_TOKEN (STR_GEN_NO_VALUE),
629 gShellAcpiViewHiiHandle,
630 L"acpiview",
631 L"-r"
632 );
633 ShellStatus = SHELL_INVALID_PARAMETER;
634 } else if ((ShellCommandLineGetFlag (Package, L"-s") &&
635 ShellCommandLineGetFlag (Package, L"-l"))) {
636 ShellPrintHiiEx (
637 -1,
638 -1,
639 NULL,
640 STRING_TOKEN (STR_GEN_TOO_MANY),
641 gShellAcpiViewHiiHandle,
642 L"acpiview"
643 );
644 ShellStatus = SHELL_INVALID_PARAMETER;
645 } else if (ShellCommandLineGetFlag (Package, L"-d") &&
646 !ShellCommandLineGetFlag (Package, L"-s")) {
647 ShellPrintHiiEx (
648 -1,
649 -1,
650 NULL,
651 STRING_TOKEN (STR_GEN_MISSING_OPTION),
652 gShellAcpiViewHiiHandle,
653 L"acpiview",
654 L"-s",
655 L"-d"
656 );
657 ShellStatus = SHELL_INVALID_PARAMETER;
658 } else {
659 // Turn on colour highlighting if requested
660 SetColourHighlighting (ShellCommandLineGetFlag (Package, L"-h"));
661
662 // Surpress consistency checking if requested
663 SetConsistencyChecking (!ShellCommandLineGetFlag (Package, L"-q"));
664
665 // Evaluate the parameters for mandatory ACPI table presence checks
666 SetMandatoryTableValidate (ShellCommandLineGetFlag (Package, L"-r"));
667 MandatoryTableSpecStr = ShellCommandLineGetValue (Package, L"-r");
668
669 if (MandatoryTableSpecStr != NULL) {
670 SetMandatoryTableSpec (ShellHexStrToUintn (MandatoryTableSpecStr));
671 }
672
673 if (ShellCommandLineGetFlag (Package, L"-l")) {
674 mReportType = ReportTableList;
675 } else {
676 mSelectedAcpiTableName = ShellCommandLineGetValue (Package, L"-s");
677 if (mSelectedAcpiTableName != NULL) {
678 mSelectedAcpiTable = (UINT32)ConvertStrToAcpiSignature (
679 mSelectedAcpiTableName
680 );
681 mReportType = ReportSelected;
682
683 if (ShellCommandLineGetFlag (Package, L"-d")) {
684 // Create a temporary file to check if the media is writable.
685 CHAR16 FileNameBuffer[MAX_FILE_NAME_LEN];
686 mReportType = ReportDumpBinFile;
687
688 UnicodeSPrint (
689 FileNameBuffer,
690 sizeof (FileNameBuffer),
691 L".\\%s%04d.tmp",
692 mSelectedAcpiTableName,
693 mBinTableCount
694 );
695
696 Status = ShellOpenFileByName (
697 FileNameBuffer,
698 &TmpDumpFileHandle,
699 EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE |
700 EFI_FILE_MODE_CREATE,
701 0
702 );
703
704 if (EFI_ERROR (Status)) {
705 ShellStatus = SHELL_INVALID_PARAMETER;
706 TmpDumpFileHandle = NULL;
707 ShellPrintHiiEx (
708 -1,
709 -1,
710 NULL,
711 STRING_TOKEN (STR_GEN_READONLY_MEDIA),
712 gShellAcpiViewHiiHandle,
713 L"acpiview"
714 );
715 goto Done;
716 }
717 // Delete Temporary file.
718 ShellDeleteFile (&TmpDumpFileHandle);
719 } // -d
720 } // -s
721 }
722
723 // Parse ACPI Table information
724 Status = AcpiView (SystemTable);
725 if (EFI_ERROR (Status)) {
726 ShellStatus = SHELL_NOT_FOUND;
727 }
728 }
729 }
730
731Done:
732 if (Package != NULL) {
733 ShellCommandLineFreeVarList (Package);
734 }
735 return ShellStatus;
736}
Note: See TracBrowser for help on using the repository browser.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette