Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
128 changes: 124 additions & 4 deletions pal/baremetal/base/src/pal_peripherals.c
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,111 @@ extern const PCIE_INFO_TABLE platform_pcie_cfg;

uint32_t spcr_baudrate_id[] = {0, 0, 0, 9600, 19200, 0, 57600, 115200};

static uint32_t
pal_peripheral_is_duplicate(PERIPHERAL_INFO_BLOCK *start,
PERIPHERAL_INFO_BLOCK *current,
uint32_t bdf)
{
PERIPHERAL_INFO_BLOCK *iter = start;

while (iter < current) {
if ((iter->bdf == bdf) && (bdf != 0))
return 1;
iter++;
}

return 0;
}

static void
pal_peripheral_add_all_pci(PERIPHERAL_INFO_TABLE *peripheralInfoTable,
PERIPHERAL_INFO_BLOCK **per_info)
{
uint32_t ecam_index;
uint32_t bus;
uint32_t dev;
uint32_t func;
uint32_t seg;
uint32_t start_bus;
uint32_t end_bus;
uint32_t bdf;
uint32_t vendor_id;
uint32_t header_value;
uint32_t class_code;
uint32_t bar_count;
uint32_t bar_index;
uint32_t bar_reg_value;
uint64_t bar_value;
PERIPHERAL_INFO_BLOCK *info = *per_info;
PERIPHERAL_INFO_BLOCK *start = peripheralInfoTable->info;

for (ecam_index = 0; ecam_index < platform_pcie_cfg.num_entries; ecam_index++) {
seg = platform_pcie_cfg.block[ecam_index].segment_num;
start_bus = platform_pcie_cfg.block[ecam_index].start_bus_num;
end_bus = platform_pcie_cfg.block[ecam_index].end_bus_num;

for (bus = start_bus; bus <= end_bus; bus++) {
for (dev = 0; dev < PCIE_MAX_DEV; dev++) {
for (func = 0; func < PCIE_MAX_FUNC; func++) {
pal_pci_cfg_read(seg, bus, dev, func, 0, &vendor_id);
if ((vendor_id == 0x0) || (vendor_id == 0xFFFFFFFF))
continue;

bdf = PCIE_CREATE_BDF(seg, bus, dev, func);
if (pal_peripheral_is_duplicate(start, info, bdf))
continue;

pal_pci_cfg_read(seg, bus, dev, func, HEADER_OFFSET, &header_value);
pal_pci_cfg_read(seg, bus, dev, func, TYPE01_RIDR, &class_code);

if (PCIE_HEADER_TYPE(header_value) != TYPE0_HEADER)
continue;

bar_count = TYPE0_MAX_BARS;

info->type = PERIPHERAL_TYPE_OTHER;
info->bdf = bdf;
info->base0 = 0;
info->base1 = 0;
info->width = 0;
info->irq = 0;
info->flags = 0;
info->msi = 0;
info->msix = 0;
info->max_pasids = 0;
info->baud_rate = 0;
info->interface_type = 0;
info->platform_type = 0;

for (bar_index = 0; bar_index < bar_count; bar_index++) {
pal_pci_cfg_read(seg, bus, dev, func, BAR0_OFFSET + (4 * bar_index), &bar_reg_value);
bar_value = pal_pcie_get_base(bdf, bar_index);
if (bar_value != 0) {
if (info->base0 == 0)
info->base0 = bar_value;
else if (info->base1 == 0)
info->base1 = bar_value;
}

if (BAR_REG(bar_reg_value) == BAR_64_BIT)
bar_index++;
}

pal_print_msg(ACS_PRINT_DEBUG, "\n BDF is 0x%x", info->bdf);
pal_print_msg(ACS_PRINT_DEBUG, "\n Class code is 0x%x", class_code);
pal_print_msg(ACS_PRINT_DEBUG, "\n PCI peripheral BAR0 0x%llx BAR1 0x%llx",
info->base0, info->base1);

peripheralInfoTable->header.num_all++;
info++;
}
}
}
}

*per_info = info;
}

/**
@brief This API fills in the PERIPHERAL_INFO_TABLE with information about peripherals
in the system.
Expand All @@ -50,6 +155,7 @@ pal_peripheral_create_info_table(PERIPHERAL_INFO_TABLE *peripheralInfoTable)
uint32_t DeviceBdf = 0;
uint32_t StartBdf = 0;
uint32_t bar_index = 0;
uint32_t class_code = 0;
uint32_t i = 0;
uint64_t uart;
PERIPHERAL_INFO_BLOCK *per_info = NULL;
Expand Down Expand Up @@ -88,9 +194,14 @@ pal_peripheral_create_info_table(PERIPHERAL_INFO_TABLE *peripheralInfoTable)
}
per_info->bdf = DeviceBdf;
per_info->platform_type = 0;

pal_print_msg(ACS_PRINT_INFO,
"\n Found a USB controller %4x",
pal_pci_cfg_read(PCIE_EXTRACT_BDF_SEG(DeviceBdf),
PCIE_EXTRACT_BDF_BUS(DeviceBdf),
PCIE_EXTRACT_BDF_DEV(DeviceBdf),
PCIE_EXTRACT_BDF_FUNC(DeviceBdf),
TYPE01_RIDR, &class_code);
pal_print_msg(ACS_PRINT_INFO, "\n BDF is 0x%x", per_info->bdf);
pal_print_msg(ACS_PRINT_INFO, "\n Class code is 0x%x", class_code);
pal_print_msg(ACS_PRINT_INFO, "\n Found a USB controller %4x",
per_info->base0);
peripheralInfoTable->header.num_usb++;
peripheralInfoTable->header.num_all++;
Expand Down Expand Up @@ -119,7 +230,13 @@ pal_peripheral_create_info_table(PERIPHERAL_INFO_TABLE *peripheralInfoTable)
}
per_info->platform_type = 0;
per_info->bdf = DeviceBdf;

pal_pci_cfg_read(PCIE_EXTRACT_BDF_SEG(DeviceBdf),
PCIE_EXTRACT_BDF_BUS(DeviceBdf),
PCIE_EXTRACT_BDF_DEV(DeviceBdf),
PCIE_EXTRACT_BDF_FUNC(DeviceBdf),
TYPE01_RIDR, &class_code);
pal_print_msg(ACS_PRINT_INFO, "\n BDF is 0x%x", per_info->bdf);
pal_print_msg(ACS_PRINT_INFO, "\n Class code is 0x%x", class_code);
pal_print_msg(ACS_PRINT_INFO,
"\n Found a SATA controller %4x",
per_info->base0);
Expand Down Expand Up @@ -164,6 +281,9 @@ pal_peripheral_create_info_table(PERIPHERAL_INFO_TABLE *peripheralInfoTable)
per_info++;
}

if (platform_pcie_cfg.num_entries != 0)
pal_peripheral_add_all_pci(peripheralInfoTable, &per_info);

per_info->type = 0xFF; //indicate end of table
}

Expand Down
2 changes: 1 addition & 1 deletion pal/baremetal/target/RDN2/include/platform_override_fvp.h
Original file line number Diff line number Diff line change
Expand Up @@ -604,7 +604,7 @@
#define VDM_RSP_MASK 7

/* PERIPHERAL platform config parameters */
#define PLATFORM_OVERRIDE_PERIPHERAL_COUNT 3 //UART + USB + SATA
#define PLATFORM_OVERRIDE_PERIPHERAL_COUNT 64 //PCI peripherals + UART/USB/SATA

#define UART_ADDRESS 0xF98DFE18
#define BASE_ADDRESS_ADDRESS_SPACE_ID 0x0
Expand Down
2 changes: 1 addition & 1 deletion pal/baremetal/target/RDV3/include/platform_override_fvp.h
Original file line number Diff line number Diff line change
Expand Up @@ -634,7 +634,7 @@
#define PLATFORM_OVERRIDE_CXL0_WINDOW_RESTRICTIONS 0x0 /* CFMWS Window restrictions*/

/* ----------------------------- Peripheral info ----------------------------- */
#define PLATFORM_OVERRIDE_PERIPHERAL_COUNT 2 //UART + USB + SATA
#define PLATFORM_OVERRIDE_PERIPHERAL_COUNT 64 //PCI peripherals + UART/USB/SATA

#define UART_ADDRESS 0xF98DFE18 /* Non-zero if UART is present */
#define BASE_ADDRESS_ADDRESS 0x2A400000 /* UART MMIO base */
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -583,7 +583,7 @@
#define PLATFORM_OVERRIDE_CXL0_WINDOW_RESTRICTIONS 0x0 /* CFMWS Window restrictions*/

/* ----------------------------- Peripheral info ----------------------------- */
#define PLATFORM_OVERRIDE_PERIPHERAL_COUNT 2 //UART + USB + SATA
#define PLATFORM_OVERRIDE_PERIPHERAL_COUNT 64 //PCI peripherals + UART/USB/SATA

#define UART_ADDRESS 0xF98DFE18 /* Non-zero if UART is present */
#define BASE_ADDRESS_ADDRESS 0x2A400000 /* UART MMIO base */
Expand Down
13 changes: 5 additions & 8 deletions pal/uefi_acpi/src/pal_peripherals.c
Original file line number Diff line number Diff line change
Expand Up @@ -131,20 +131,12 @@ pal_peripheral_add_all_pci(PERIPHERAL_INFO_TABLE *peripheralInfoTable,
if ((PciHeader.Device.Hdr.HeaderType & HEADER_LAYOUT_CODE) != HEADER_TYPE_DEVICE)
continue;

/* Skip bridges and cardbus controllers, we only want endpoint functions */
if (IS_PCI_BRIDGE(&(PciHeader.Bridge)) || IS_CARDBUS_BRIDGE(&(PciHeader.Bridge)))
continue;

bars = PciHeader.Device.Device.Bar;
bar_count = TYPE0_MAX_BARS;
class_code = ((PciHeader.Device.Hdr.ClassCode[2] << 16) |
(PciHeader.Device.Hdr.ClassCode[1] << 8) |
PciHeader.Device.Hdr.ClassCode[0]);

/* Skip all bridge class devices (host bridge, PCI-PCI bridge, etc.) */
if ((class_code >> 16) == 0x06)
continue;

info->type = PERIPHERAL_TYPE_OTHER;
info->bdf = DeviceBdf;
info->platform_type = PLATFORM_TYPE_ACPI;
Expand Down Expand Up @@ -173,6 +165,11 @@ pal_peripheral_add_all_pci(PERIPHERAL_INFO_TABLE *peripheralInfoTable,
bar_index++;
}

pal_print_msg(ACS_PRINT_INFO, "\n BDF is 0x%x", info->bdf);
pal_print_msg(ACS_PRINT_INFO, "\n Class code is 0x%x", class_code);
pal_print_msg(ACS_PRINT_INFO, "\n PCI peripheral BAR0 0x%llx BAR1 0x%llx",
info->base0, info->base1);

peripheralInfoTable->header.num_all++;
info++;
}
Expand Down
17 changes: 13 additions & 4 deletions pal/uefi_dt/src/pal_peripherals.c
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,7 @@ pal_peripheral_add_all_pci(PERIPHERAL_INFO_TABLE *peripheralInfoTable,
UINT32 bar_count;
UINT32 DeviceBdf;
UINT32 *bars;
UINT32 class_code;
PCI_TYPE_GENERIC PciHeader;
PERIPHERAL_INFO_BLOCK *info = *per_info;
PERIPHERAL_INFO_BLOCK *start = peripheralInfoTable->info;
Expand Down Expand Up @@ -150,12 +151,15 @@ pal_peripheral_add_all_pci(PERIPHERAL_INFO_TABLE *peripheralInfoTable,
if (EFI_ERROR (Status))
continue;

class_code = ((PciHeader.Device.Hdr.ClassCode[2] << 16) |
(PciHeader.Device.Hdr.ClassCode[1] << 8) |
PciHeader.Device.Hdr.ClassCode[0]);

if ((PciHeader.Device.Hdr.HeaderType & HEADER_LAYOUT_CODE) != HEADER_TYPE_DEVICE)
continue;

bars = PciHeader.Device.Device.Bar;
bar_count = TYPE0_MAX_BARS;
if (IS_PCI_BRIDGE(&(PciHeader.Bridge)) || IS_CARDBUS_BRIDGE(&(PciHeader.Bridge))) {
bars = PciHeader.Bridge.Bridge.Bar;
bar_count = TYPE1_MAX_BARS;
}

info->type = PERIPHERAL_TYPE_OTHER;
info->bdf = DeviceBdf;
Expand Down Expand Up @@ -185,6 +189,11 @@ pal_peripheral_add_all_pci(PERIPHERAL_INFO_TABLE *peripheralInfoTable,
bar_index++;
}

pal_print_msg(ACS_PRINT_INFO, "\n BDF is 0x%x", info->bdf);
pal_print_msg(ACS_PRINT_INFO, "\n Class code is 0x%x", class_code);
pal_print_msg(ACS_PRINT_INFO, "\n PCI peripheral BAR0 0x%llx BAR1 0x%llx",
info->base0, info->base1);

peripheralInfoTable->header.num_all++;
info++;
}
Expand Down
1 change: 0 additions & 1 deletion tools/cmake/infra/bsa_test.txt
Original file line number Diff line number Diff line change
Expand Up @@ -174,4 +174,3 @@ e035.c
e036.c
e039.c
e046.c
p047.c
6 changes: 6 additions & 0 deletions tools/cmake/infra/pc_bsa_test.txt
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,12 @@ g004.c
g005.c
g012.c
g014.c
g015.c
g016.c
its003.c
its004.c
its005.c
its006.c
interface010.c
interface011.c
i001.c
Expand Down
Loading