diff options
Diffstat (limited to 'Lessons/Lesson_29/UefiLessonsPkg/AcpiInfo')
-rw-r--r-- | Lessons/Lesson_29/UefiLessonsPkg/AcpiInfo/AcpiInfo.c | 108 |
1 files changed, 78 insertions, 30 deletions
diff --git a/Lessons/Lesson_29/UefiLessonsPkg/AcpiInfo/AcpiInfo.c b/Lessons/Lesson_29/UefiLessonsPkg/AcpiInfo/AcpiInfo.c index 0511f59..9b3c866 100644 --- a/Lessons/Lesson_29/UefiLessonsPkg/AcpiInfo/AcpiInfo.c +++ b/Lessons/Lesson_29/UefiLessonsPkg/AcpiInfo/AcpiInfo.c @@ -4,6 +4,74 @@ #include <Library/BaseMemoryLib.h> #include <Protocol/Shell.h> +EFI_SHELL_PROTOCOL* ShellProtocol; + +EFI_STATUS SaveACPITable(UINT32 Signature, VOID* addr, UINTN size) { + CHAR16 TableName[5]; + TableName[0] = (CHAR16)((Signature>> 0)&0xFF); + TableName[1] = (CHAR16)((Signature>> 8)&0xFF); + TableName[2] = (CHAR16)((Signature>>16)&0xFF); + TableName[3] = (CHAR16)((Signature>>24)&0xFF); + TableName[4] = 0; + + CHAR16 FileName[9] = {0}; + StrCpyS(FileName, 9, TableName); + StrCatS(FileName, 9, L".aml"); + SHELL_FILE_HANDLE FileHandle; + EFI_STATUS Status = ShellProtocol->OpenFileByName(FileName, + &FileHandle, + EFI_FILE_MODE_CREATE | + EFI_FILE_MODE_WRITE | + EFI_FILE_MODE_READ); + if (!EFI_ERROR(Status)) { + Status = ShellProtocol->WriteFile(FileHandle, &size, addr); + if (EFI_ERROR(Status)) { + Print(L"Error in WriteFile: %r\n", Status); + } + Status = ShellProtocol->CloseFile(FileHandle); + if (EFI_ERROR(Status)) { + Print(L"Error in CloseFile: %r\n", Status); + } + } else { + Print(L"Error in OpenFileByName: %r\n", Status); + } + return Status; +} + + +VOID CheckSubtables(EFI_ACPI_6_3_COMMON_HEADER* table) +{ + if (((CHAR8)((table->Signature >> 0) & 0xFF) == 'F') && + ((CHAR8)((table->Signature >> 8) & 0xFF) == 'A') && + ((CHAR8)((table->Signature >> 16) & 0xFF) == 'C') && + ((CHAR8)((table->Signature >> 24) & 0xFF) == 'P')) { + EFI_ACPI_6_3_FIXED_ACPI_DESCRIPTION_TABLE* FADT = (EFI_ACPI_6_3_FIXED_ACPI_DESCRIPTION_TABLE*)table; + + EFI_ACPI_6_3_COMMON_HEADER* DSDT = (EFI_ACPI_6_3_COMMON_HEADER*)(UINT64)(FADT->Dsdt); + if (((CHAR8)((DSDT->Signature >> 0) & 0xFF) == 'D') && + ((CHAR8)((DSDT->Signature >> 8) & 0xFF) == 'S') && + ((CHAR8)((DSDT->Signature >> 16) & 0xFF) == 'D') && + ((CHAR8)((DSDT->Signature >> 24) & 0xFF) == 'T')) { + Print(L"\tDSDT table is placed at address %p with length 0x%x\n", DSDT, DSDT->Length); + SaveACPITable(DSDT->Signature, DSDT, DSDT->Length); + } else { + Print(L"\tError! DSDT signature is not valid!\n"); + } + + EFI_ACPI_6_3_COMMON_HEADER* FACS = (EFI_ACPI_6_3_COMMON_HEADER*)(UINT64)(FADT->FirmwareCtrl); + if (((CHAR8)((FACS->Signature >> 0) & 0xFF) == 'F') && + ((CHAR8)((FACS->Signature >> 8) & 0xFF) == 'A') && + ((CHAR8)((FACS->Signature >> 16) & 0xFF) == 'C') && + ((CHAR8)((FACS->Signature >> 24) & 0xFF) == 'S')) { + Print(L"\tFACS table is placed at address %p with length 0x%x\n", FACS, FACS->Length); + SaveACPITable(FACS->Signature, FACS, FACS->Length); + } else { + Print(L"\tError! FACS signature is not valid!\n"); + } + } +} + + EFI_STATUS EFIAPI UefiMain ( @@ -11,7 +79,6 @@ UefiMain ( IN EFI_SYSTEM_TABLE *SystemTable ) { - EFI_SHELL_PROTOCOL* ShellProtocol; EFI_STATUS Status = gBS->LocateProtocol( &gEfiShellProtocolGuid, NULL, @@ -68,37 +135,18 @@ UefiMain ( while (offset < XSDT->Length) { UINT64* table_address = (UINT64*)((UINT8*)XSDT + offset); EFI_ACPI_6_3_COMMON_HEADER* table = (EFI_ACPI_6_3_COMMON_HEADER*)(*table_address); - CHAR16 TableName[5]; - TableName[0] = (CHAR16)((table->Signature>> 0)&0xFF); - TableName[1] = (CHAR16)((table->Signature>> 8)&0xFF); - TableName[2] = (CHAR16)((table->Signature>>16)&0xFF); - TableName[3] = (CHAR16)((table->Signature>>24)&0xFF); - TableName[4] = 0; - - Print(L"\t%s table is placed at address %p with length 0x%x\n", - TableName, + Print(L"\t%c%c%c%c table is placed at address %p with length 0x%x\n", + (CHAR8)((table->Signature>> 0)&0xFF), + (CHAR8)((table->Signature>> 8)&0xFF), + (CHAR8)((table->Signature>>16)&0xFF), + (CHAR8)((table->Signature>>24)&0xFF), table, table->Length); - CHAR16 FileName[9] = {0}; - StrCpyS(FileName, 9, TableName); - StrCatS(FileName, 9, L".aml"); - SHELL_FILE_HANDLE FileHandle; - Status = ShellProtocol->OpenFileByName(FileName, - &FileHandle, - EFI_FILE_MODE_CREATE | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_READ); - if (!EFI_ERROR(Status)) { - UINTN size = table->Length; - Status = ShellProtocol->WriteFile(FileHandle, &size, (VOID*)table); - if (EFI_ERROR(Status)) { - Print(L"Error in WriteFile: %r\n", Status); - } - Status = ShellProtocol->CloseFile(FileHandle); - if (EFI_ERROR(Status)) { - Print(L"Error in CloseFile: %r\n", Status); - } - } else { - Print(L"Error in OpenFileByName: %r\n", Status); - } + + SaveACPITable(table->Signature, table, table->Length); + + CheckSubtables(table); + offset += sizeof(UINT64); } |