alder_lake_bios/Intel/AlderLake/AlderLakeChipsetPkg/Library/PlatformBdsLib/BootDevicesDisplay.c

614 lines
17 KiB
C

/** @file
PlatformBdsLib
;******************************************************************************
;* Copyright (c) 2014 - 2021, Insyde Software Corp. All Rights Reserved.
;*
;* You may not reproduce, distribute, publish, display, perform, modify, adapt,
;* transmit, broadcast, present, recite, release, license or otherwise exploit
;* any part of this publication in any form, by any means, without the prior
;* written permission of Insyde Software Corporation.
;*
;******************************************************************************
*/
#include "BootDevicesDisplay.h"
#include <PortNumberMap.h>
#include <Library/DxeInsydeChipsetLib.h>
#include <SetupVariable.h>
/**
Check this SATA port number is whther support
@param PortNum SATA port number
@retval EFI_SUCCESS platform supports this SATA port number
@retval EFI_UNSUPPORTED platform unsupports this SATA port number
**/
STATIC
EFI_STATUS
CheckSataPort (
IN UINTN PortNum
)
{
UINTN Index;
PORT_NUMBER_MAP *PortMappingTable; //retrieved from Pcd
PORT_NUMBER_MAP EndEntry;
UINTN NoPorts;
PortMappingTable = NULL;
ZeroMem (&EndEntry, sizeof (PORT_NUMBER_MAP));
PortMappingTable = (PORT_NUMBER_MAP *)PcdGetPtr (PcdPortNumberMapTable);
NoPorts = 0;
while (CompareMem (&EndEntry, &PortMappingTable[NoPorts], sizeof (PORT_NUMBER_MAP)) != 0) {
NoPorts++;
}
if (NoPorts == 0) {
return EFI_UNSUPPORTED;
}
for (Index = 0; Index < NoPorts; Index++) {
if (PortMappingTable[Index].PortNum == PortNum) {
return EFI_SUCCESS;
}
}
return EFI_UNSUPPORTED;
}
/**
According Port number and Bbs table to channel number, device number, and
Bbs Table Index.
@param LocalBbsTable Pointer to BbsTable.
@param PortNum SATA port number
@param Channel Pointer to channel number
@param Device Pointer to device number
@param BbsTableIndex Pointer to Bbs Table index
@retval EFI_SUCCESS Get Channel, Device and Bbs table index successful
@retval EFI_INVALID_PARAMETER Input parameter is invalid
@retval EFI_NOT_FOUND Cannot found associate Channel, device and Bbs table index
**/
STATIC
EFI_STATUS
GetChannelDevice (
IN BBS_TABLE *LocalBbsTable,
IN UINTN PortNum,
OUT UINT8 *Channel,
OUT UINT8 *Device,
OUT UINTN *BbsTableIndex
)
{
PORT_NUMBER_MAP *PortMappingTable;
PORT_NUMBER_MAP EndEntry;
UINTN TotalPortCnt;
UINTN Index;
UINTN PortCnt;
EFI_STATUS Status;
UINT8 SlaveMaster;
UINT8 PrimarySecondary;
PortMappingTable = NULL;
ZeroMem (&EndEntry, sizeof (PORT_NUMBER_MAP));
if (BbsTableIndex == NULL || Channel == NULL || Device == NULL) {
return EFI_INVALID_PARAMETER;
}
//
// Get Port maping table to check this port is supported
//
PortMappingTable = (PORT_NUMBER_MAP *)PcdGetPtr (PcdPortNumberMapTable);
TotalPortCnt = 0;
while (CompareMem (&EndEntry, &PortMappingTable[TotalPortCnt], sizeof (PORT_NUMBER_MAP)) != 0) {
TotalPortCnt++;
}
if (TotalPortCnt == 0) {
return EFI_UNSUPPORTED;
}
for (PortCnt = 0; PortCnt < TotalPortCnt; PortCnt++) {
if (PortMappingTable[PortCnt].PortNum == PortNum) {
break;
}
}
if (PortCnt == TotalPortCnt) {
return EFI_NOT_FOUND;
}
//
// Get channel number and device number from Bbs table
//
Status = EFI_NOT_FOUND;
for (Index = 1; Index < 9; Index++) {
if (LocalBbsTable[Index].BootPriority == BBS_IGNORE_ENTRY) {
continue;
}
//
// Caculate SlaveMaster and PrimarySecondary from BbsTableIndex
//
SlaveMaster = (UINT8) ((Index - 1) % 2);
PrimarySecondary = (UINT8) ((Index - 1) / 2 % 2);
if ((LocalBbsTable[Index].Bus == PortMappingTable[PortCnt].Bus) &&
(LocalBbsTable[Index].Device == PortMappingTable[PortCnt].Device) &&
(LocalBbsTable[Index].Function == PortMappingTable[PortCnt].Function) &&
(SlaveMaster == PortMappingTable[PortCnt].SlaveMaster) &&
(PrimarySecondary == PortMappingTable[PortCnt].PrimarySecondary)) {
*Channel = (UINT8) ((Index - 1) / 2);
*Device = (UINT8) ((Index - 1) % 2);
*BbsTableIndex = Index;
Status = EFI_SUCCESS;
break;
}
}
return Status;
}
/**
Check the specific BBS Table entry is SATA device
@param LocalBbsTable Pointer to BBS table start address
@param BbsTableIndex The specific Bbs table index
@retval TRUE It is SATA device
@retval FALSE It isn't SATA device
**/
BOOLEAN
IsSataDevice (
IN BBS_TABLE *LocalBbsTable,
IN UINTN BbsTableIndex
)
{
PORT_NUMBER_MAP *PortMappingTable;
PORT_NUMBER_MAP EndEntry;
UINTN TotalPortCnt;
UINTN Index;
PortMappingTable = NULL;
ZeroMem (&EndEntry, sizeof (PORT_NUMBER_MAP));
//
// Bbs table index 1~8 is used for SATA device
//
if ((BbsTableIndex > 0) && (BbsTableIndex < 9)){
return TRUE;
}
//
// check the PCI bus device function is matched for SATA controller
//
PortMappingTable = (PORT_NUMBER_MAP *)PcdGetPtr (PcdPortNumberMapTable);
TotalPortCnt = 0;
while (CompareMem (&EndEntry, &PortMappingTable[TotalPortCnt], sizeof (PORT_NUMBER_MAP)) != 0) {
TotalPortCnt++;
}
if (TotalPortCnt == 0) {
return FALSE;
}
for (Index = 0; Index < TotalPortCnt; Index++) {
if ((LocalBbsTable[BbsTableIndex].Bus == PortMappingTable[Index].Bus) &&
(LocalBbsTable[BbsTableIndex].Device == PortMappingTable[Index].Device) &&
(LocalBbsTable[BbsTableIndex].Function == PortMappingTable[Index].Function)) {
return TRUE;
}
}
return FALSE;
}
/**
Check the specific BBS Table entry is USB device
@param LocalBbsTable Pointer to BBS table start address
@param BbsTableIndex The specific Bbs table index
@retval TRUE It is USB device
@retval FALSE It isn't USB device
**/
BOOLEAN
IsUsbDevice (
IN BBS_TABLE *LocalBbsTable,
IN UINTN BbsTableIndex
)
{
if ((LocalBbsTable[BbsTableIndex].Class == PCI_CLASS_SERIAL) &&
(LocalBbsTable[BbsTableIndex].SubClass == PCI_CLASS_SERIAL_USB)) {
return TRUE;
}
return FALSE;
}
/**
Show all of sata devices' information on summary screen
@param LocalBbsTable Pointer to BBS table start address
@param LocalHddInfo Pointer to Hdd info statt address
@param HddCount Hdd count in Hdd info array
@param SetupNVRam Pointer to CHIPSET_CONFIGURATION variable
@param ShowedDeviceNum IN : Showed device number on summary screen before show SATA device
OUT : Showed device number on summary screen after show SATA device
@retval EFI_SUCCESS show SATA device successful
@retval EFI_ABORTED skip showing device
@retval EFI_INVALID_PARAMETER input parameter is invalid
**/
EFI_STATUS
ShowSataDevice (
IN BBS_TABLE *LocalBbsTable,
IN HDD_INFO *LocalHddInfo,
IN UINT16 HddCount,
IN CHIPSET_CONFIGURATION *SetupNVRam,
IN PCH_SETUP *PchSetup,
IN OUT UINTN *ShowedDeviceNum
)
{
UINT8 Channel;
UINT8 Device;
CHAR16 *SataPortStr;
CHAR16 ModelNametring[100];
CHAR16 PortNoStr[10];
UINTN PortNum;
UINTN DeviceCnt;
UINTN BbsTableIndex;
EFI_STATUS Status;
//
// check parameter is valid
//
if ((LocalBbsTable == NULL) || (LocalHddInfo == NULL) ||
(SetupNVRam == NULL) || (ShowedDeviceNum == NULL)) {
return EFI_INVALID_PARAMETER;
}
//
// check showed device number is lareger than MAX_DISPLAY_DEVICE_COUNT
//
if (*ShowedDeviceNum >= MAX_DISPLAY_DEVICE_COUNT) {
return EFI_ABORTED;
}
BbsTableIndex = 1;
DeviceCnt = *ShowedDeviceNum;
SataPortStr = PlatformBdsGetStringById (STRING_TOKEN (STR_SERIAL_ATA_PORT));
gST->ConOut->SetAttribute (gST->ConOut, EFI_WHITE);
//
// SATA Configuration
//
for (PortNum = 0; PortNum < 8; PortNum++) {
//
// IDE mode or AHCI mode without option Rom
//
if (((PchSetup->SataInterfaceMode == SATA_MODE_AHCI) && (SetupNVRam->AhciOptionRomSupport == 0))) {
//
// Check this port is whether support
//
Status = CheckSataPort (PortNum);
if (EFI_ERROR (Status)) {
continue;
}
//
// According port number to get channel, device and BbsTableIndex
//
Status = GetChannelDevice (LocalBbsTable, PortNum, &Channel, &Device, &BbsTableIndex);
if (EFI_ERROR (Status)) {
continue;
}
//
// AHIC mode with option ROM or RAID mode
//
} else {
Channel = (UINT8) (PortNum / 2);
Device = (UINT8) (PortNum % 2);
BbsTableIndex = PortNum + 1;
}
//
// Show SATA device
//
if (HddCount > (Channel * 2 + Device)) {
//
// only can show MAX_DISPLAY_DEVICE_COUNT devices to prevent covering other information
//
if (DeviceCnt > MAX_DISPLAY_DEVICE_COUNT) {
BdsLibOutputStrings (gST->ConOut, L"\n\r", L"...", NULL);
break;
}
BdsBuildLegacyDevNameString (
&LocalBbsTable[BbsTableIndex],
LocalHddInfo,
BbsTableIndex,
sizeof (ModelNametring),
ModelNametring
);
if (StrLen (ModelNametring) == 0) {
continue;
}
UnicodeValueToStringS (PortNoStr, 10 * sizeof(CHAR16), 0, PortNum, 0);
BdsLibOutputStrings (gST->ConOut, L"\n\r", SataPortStr, PortNoStr, L" : ", ModelNametring, NULL);
DeviceCnt++;
}
}
//
// Set showed Device number
//
*ShowedDeviceNum = DeviceCnt;
gBS->FreePool (SataPortStr);
return EFI_SUCCESS;
}
/**
show all of un-SATA device information on summary screen
@param LocalBbsTable Pointer to BBS table start address
@param BbsTotalCount Total BBS count in BBS table
@param LocalHddInfo Pointer to Hdd info statt address
@param ShowedDeviceNum IN : Showed device number on summary screen before show SATA device
OUT : Showed device number on summary screen after show SATA device
@retval EFI_SUCCESS show all of other device successful
@retval EFI_ABORTED skip showing device
@retval EFI_INVALID_PARAMETER input parameter is invalid
**/
EFI_STATUS
ShowUnSataDevice (
IN BBS_TABLE *LocalBbsTable,
IN UINT16 BbsTotalCount,
IN HDD_INFO *LocalHddInfo,
IN OUT UINTN *ShowedDeviceNum
)
{
CHAR16 *UsbDeviceStr;
CHAR16 *OtherDeviceStr;
CHAR16 ModelNametring[100];
CHAR16 DeviceNoStr[10];
UINTN BbsTableIndex;
UINTN UsbDeviceNum;
UINTN OtherDeviceNum;
UINTN TotalDeviceNum;
//
// check parameter is valid
//
if ((LocalBbsTable == NULL) || (LocalHddInfo == NULL)) {
return EFI_INVALID_PARAMETER;
}
//
// check showed device number is lareger than MAX_DISPLAY_DEVICE_COUNT
//
if (*ShowedDeviceNum >= MAX_DISPLAY_DEVICE_COUNT) {
return EFI_ABORTED;
}
//
// Initial local variable
//
UsbDeviceStr = PlatformBdsGetStringById (STRING_TOKEN (STR_BOOT_USB_DEVICE));
UsbDeviceNum = 0;
TotalDeviceNum = *ShowedDeviceNum;
gST->ConOut->SetAttribute (gST->ConOut, EFI_WHITE);
//
// Show USB device
//
for (BbsTableIndex = 0; BbsTableIndex < BbsTotalCount; BbsTableIndex++) {
if ((LocalBbsTable[BbsTableIndex].BootPriority == BBS_IGNORE_ENTRY) ||
(LocalBbsTable[BbsTableIndex].BootPriority == BBS_DO_NOT_BOOT_FROM)) {
continue;
}
//
// skip SATA device
//
if (IsSataDevice (LocalBbsTable, BbsTableIndex)) {
continue;
}
//
// Show USB device
//
if (IsUsbDevice (LocalBbsTable, BbsTableIndex)) {
//
// only can show MAX_DISPLAY_DEVICE_COUNT devices to prevent cover other information
//
if (TotalDeviceNum >= MAX_DISPLAY_DEVICE_COUNT) {
BdsLibOutputStrings (gST->ConOut, L"\n\r", L"...", NULL);
break;
}
UsbDeviceNum++;
TotalDeviceNum++;
BdsBuildLegacyDevNameString (
&LocalBbsTable[BbsTableIndex],
LocalHddInfo, BbsTableIndex,
sizeof (ModelNametring),
ModelNametring
);
UnicodeValueToStringS (DeviceNoStr, 10 * sizeof (CHAR16), 0, UsbDeviceNum, 0);
BdsLibOutputStrings (gST->ConOut, L"\n\r", UsbDeviceStr, DeviceNoStr, L" : ", ModelNametring, NULL);
}
}
gBS->FreePool (UsbDeviceStr);
//
// check showed device number is lareger than MAX_DISPLAY_DEVICE_COUNT
//
if (TotalDeviceNum >= MAX_DISPLAY_DEVICE_COUNT) {
*ShowedDeviceNum = TotalDeviceNum;
return EFI_ABORTED;
}
//
// Initial local variable for other device use
//
OtherDeviceNum = 0;
OtherDeviceStr = PlatformBdsGetStringById (STRING_TOKEN (STR_BOOT_OTHER_DEVICE));
//
// Show other device
//
for (BbsTableIndex = 0; BbsTableIndex < BbsTotalCount; BbsTableIndex++) {
if ((LocalBbsTable[BbsTableIndex].BootPriority == BBS_IGNORE_ENTRY) ||
(LocalBbsTable[BbsTableIndex].BootPriority == BBS_DO_NOT_BOOT_FROM)) {
continue;
}
//
// skip SATA device
//
if (IsSataDevice (LocalBbsTable, BbsTableIndex)) {
continue;
}
//
// Show other device
//
if (!IsUsbDevice (LocalBbsTable, BbsTableIndex)) {
//
// only can show MAX_DISPLAY_DEVICE_COUNT devices to prevent cover other information
//
if (TotalDeviceNum >= MAX_DISPLAY_DEVICE_COUNT) {
BdsLibOutputStrings (gST->ConOut, L"\n\r", L"...", NULL);
break;
}
OtherDeviceNum++;
TotalDeviceNum++;
BdsBuildLegacyDevNameString (
&LocalBbsTable[BbsTableIndex],
LocalHddInfo, BbsTableIndex,
sizeof (ModelNametring),
ModelNametring
);
UnicodeValueToStringS (DeviceNoStr, 10 * sizeof (CHAR16), 0, OtherDeviceNum, 0);
BdsLibOutputStrings (gST->ConOut, L"\n\r", OtherDeviceStr, DeviceNoStr, L" : ", ModelNametring, NULL);
}
}
//
// Set showed Device number
//
*ShowedDeviceNum = TotalDeviceNum;
gBS->FreePool (OtherDeviceStr);
return EFI_SUCCESS;
}
/**
Show all of attached devices information on summary screen
@retval EFI_SUCCESS Show all devices on summary screen successful.
**/
EFI_STATUS
ShowAllDevice (
VOID
)
{
EFI_STATUS Status;
UINT16 BbsTotalCount;
BBS_TABLE *LocalBbsTable;
HDD_INFO *LocalHddInfo;
UINT16 HddCount;
UINTN ShowedDeviceNum;
EFI_LEGACY_BIOS_PROTOCOL *LegacyBios;
CHIPSET_CONFIGURATION *SetupNVRam;
PCH_SETUP *PchSetup;
UINTN PchSetupSize;
SetupNVRam = NULL;
PchSetup = NULL;
Status = gBS->LocateProtocol (
&gEfiLegacyBiosProtocolGuid,
NULL,
(VOID **)&LegacyBios);
if (EFI_ERROR (Status)) {
return Status;
}
Status = LegacyBios->GetBbsInfo (
LegacyBios,
&HddCount,
&LocalHddInfo,
&BbsTotalCount,
&LocalBbsTable
);
if (EFI_ERROR (Status)) {
return Status;
}
//
// Locate gEfiSetupUtilityProtocolGuid to get SetupNvData
//
SetupNVRam = AllocateZeroPool (sizeof (CHIPSET_CONFIGURATION));
if (SetupNVRam == NULL) {
return EFI_OUT_OF_RESOURCES;
}
Status = GetChipsetSetupVariableDxe (SetupNVRam, sizeof (CHIPSET_CONFIGURATION));
if (EFI_ERROR (Status)) {
FreePool (SetupNVRam);
ASSERT_EFI_ERROR (Status);
return Status;
}
PchSetupSize = sizeof (PCH_SETUP);
PchSetup = AllocateZeroPool (PchSetupSize);
if (PchSetup == NULL) {
return EFI_OUT_OF_RESOURCES;
}
Status = gRT->GetVariable (
PCH_SETUP_VARIABLE_NAME,
&gPchSetupVariableGuid,
NULL,
&PchSetupSize,
PchSetup
);
if (EFI_ERROR (Status)) {
FreePool (PchSetup);
return Status;
}
BdsLibOutputStrings (gST->ConOut, L"\n\r", NULL);
ShowedDeviceNum = 0;
//
// Show SATA devices
//
ShowSataDevice (LocalBbsTable, LocalHddInfo, HddCount, SetupNVRam, PchSetup, &ShowedDeviceNum);
//
// Show other devices
//
ShowUnSataDevice (LocalBbsTable, BbsTotalCount, LocalHddInfo, &ShowedDeviceNum);
if (SetupNVRam != NULL) {
FreePool (SetupNVRam);
}
if (PchSetup != NULL) {
FreePool (PchSetup);
}
return EFI_SUCCESS;
}