pci: dump pci bus, lspci format

pull/443/head
Marco Oliverio 2024-03-13 15:11:32 +01:00
parent 0e334386a6
commit 7ce14a242a
3 changed files with 80 additions and 0 deletions

View File

@ -125,6 +125,7 @@ uint32_t pci_enum_bus(uint8_t bus, struct pci_enum_info *info);
int pci_enum_do(void); int pci_enum_do(void);
int pci_pre_enum(void); int pci_pre_enum(void);
int pcie_retraining_link(uint8_t bus, uint8_t dev, uint8_t fun); int pcie_retraining_link(uint8_t bus, uint8_t dev, uint8_t fun);
void pci_dump_config_space(void);
#ifdef __cplusplus #ifdef __cplusplus
} }

View File

@ -449,6 +449,7 @@ static int fsp_silicon_init(struct fsp_info_header *fsp_info, uint8_t *fsp_s_bas
wolfBoot_printf("pcie retraining failed %x\n", status); wolfBoot_printf("pcie retraining failed %x\n", status);
pci_enum_do(); pci_enum_do();
pci_dump_config_space();
notifyPhase = (notify_phase_cb)(fsp_s_base + notifyPhase = (notify_phase_cb)(fsp_s_base +
fsp_info->NotifyPhaseEntryOffset); fsp_info->NotifyPhaseEntryOffset);
param.Phase = EnumInitPhaseAfterPciEnumeration; param.Phase = EnumInitPhaseAfterPciEnumeration;

View File

@ -871,6 +871,84 @@ int pci_pre_enum(void)
return 0; return 0;
} }
#if defined(DEBUG_PCI)
void pci_dump(uint8_t bus, uint8_t dev, uint8_t fun)
{
uint32_t reg[256/4];
uint8_t *ptr;
int i;
for (i = 0; i < 256 / 4; i++) {
reg[i] = pci_config_read32(bus, dev, fun, i * 4);
}
ptr = (uint8_t*)reg;
for (i = 0; i < 256; i++) {
if (i % 0x10 == 0x0) {
if (i < 0x10) {
wolfBoot_printf("0");
}
wolfBoot_printf("%x: ", (int)i);
}
wolfBoot_printf("%s%x%s", (ptr[i] < 0x10 ? "0" :""), (int)ptr[i],
(i % 0x10 == 0xf ? "\n":" "));
}
}
static void pci_dump_bus(uint8_t bus)
{
uint16_t vendor_id, device_id, header_type;
uint8_t dev, fun, sec_bus;
uint32_t vd_code, reg;
int ret;
for (dev = 0; dev < PCI_ENUM_MAX_DEV; dev++) {
vd_code = pci_config_read32(bus, dev, 0, PCI_VENDOR_ID_OFFSET);
if (vd_code == 0xFFFFFFFF) {
/* No device here. */
continue;
}
for (fun = 0; fun < PCI_ENUM_MAX_FUN; fun++) {
vd_code = pci_config_read32(bus, dev, fun, PCI_VENDOR_ID_OFFSET);
if (vd_code == 0xFFFFFFFF) {
/* No device here. */
continue;
}
if (bus < 0x10)
wolfBoot_printf("0");
wolfBoot_printf("%x:", bus);
if (dev < 0x10)
wolfBoot_printf("0");
wolfBoot_printf("%x.", dev);
wolfBoot_printf("%d \n", fun);
pci_dump(bus, dev, fun);
header_type = pci_config_read16(bus, dev, fun,
PCI_HEADER_TYPE_OFFSET);
if ((header_type & PCI_HEADER_TYPE_TYPE_MASK) == PCI_HEADER_TYPE_BRIDGE) {
sec_bus = pci_config_read8(bus, dev, fun, PCI_SECONDARY_BUS);
if (sec_bus != 0)
pci_dump_bus(sec_bus);
}
/* just one function */
if ((fun == 0) && !(header_type & PCI_HEADER_TYPE_MULTIFUNC_MASK)) {
break;
}
}
}
}
void pci_dump_config_space()
{
return pci_dump_bus(0);
}
#else
void pci_dump_config_space() {};
#endif
int pci_enum_do(void) int pci_enum_do(void)
{ {
struct pci_enum_info enum_info; struct pci_enum_info enum_info;