Attention is currently required from: Arthur Heymans, Christian Walter, Jincheng Li, Johnny Lin, Jonathan Zhang, Lean Sheng Tan, Patrick Rudolph, Tim Chu.
Shuo Liu would like Jincheng Li to review this change.
soc/intel/xeon_sp: Add xeonsp_acpigen_write_PRT_pci_bridge
Add support of _PRT SSDT generation for PCI domain and root ports.
The routing info is based on PCI interrupt pin/line info configured
in pch_pirq_init() ahead of time.
Change-Id: I98497523d11fcdd3724bc6b09585a3fe17fec2a7
Signed-off-by: Shuo Liu <shuo.liu@intel.com>
Signed-off-by: Jincheng Li <jincheng.li@intel.com>
---
M src/soc/intel/xeon_sp/acpi.c
M src/soc/intel/xeon_sp/gnr/chip.c
M src/soc/intel/xeon_sp/gnr/soc_acpi.c
M src/soc/intel/xeon_sp/include/soc/acpi.h
4 files changed, 70 insertions(+), 0 deletions(-)
git pull ssh://review.coreboot.org:29418/coreboot refs/changes/69/81569/1
diff --git a/src/soc/intel/xeon_sp/acpi.c b/src/soc/intel/xeon_sp/acpi.c
index 9881138..1c2ef76 100644
--- a/src/soc/intel/xeon_sp/acpi.c
+++ b/src/soc/intel/xeon_sp/acpi.c
@@ -1,10 +1,14 @@
/* SPDX-License-Identifier: GPL-2.0-or-later */
+#include <acpi/acpigen.h>
+#include <acpi/acpigen_pci.h>
#include <assert.h>
+#include <device/pci_ops.h>
#include <intelblocks/acpi.h>
#include <soc/chip_common.h>
#include <soc/pci_devs.h>
#include <soc/util.h>
+#include <southbridge/intel/common/acpi_pirq_gen.h>
#include <stdint.h>
#include <stdlib.h>
@@ -206,3 +210,43 @@
return NULL;
}
+
+void xeonsp_acpigen_write_PRT_pci_bridge(const struct device *br)
+{
+ int dev_num = 0;
+ uint32_t routed_dev_bitmap = 0;
+ char *entry_count;
+
+ if ((!is_pci_bridge(br)) && (br->path.type != DEVICE_PATH_DOMAIN))
+ return;
+
+ const char *acpi_scope = acpi_device_path(br);
+ if (!acpi_scope)
+ return;
+
+ acpigen_write_scope(acpi_scope);
+ acpigen_write_name("_PRT");
+ entry_count = acpigen_write_package(0);
+
+ struct device *dev = NULL;
+ while ((dev = dev_bus_each_child(br->downstream, dev))) {
+ if (!is_pci(dev))
+ continue;
+ dev_num = PCI_SLOT(dev->path.pci.devfn);
+ if (routed_dev_bitmap & (1 << dev_num))
+ continue;
+
+ uint8_t int_line = pci_read_config8(dev, PCI_INTERRUPT_LINE);
+ uint8_t int_pin = pci_read_config8(dev, PCI_INTERRUPT_PIN);
+ if ((int_pin > PCI_INT_MAX) || (int_pin < PCI_INT_A))
+ continue;
+
+ acpigen_write_PRT_GSI_entry(dev_num, int_pin - PCI_INT_A, int_line);
+
+ (*entry_count)++;
+ routed_dev_bitmap |= (1 << dev_num);
+ }
+
+ acpigen_pop_len();
+ acpigen_pop_len();
+}
diff --git a/src/soc/intel/xeon_sp/gnr/chip.c b/src/soc/intel/xeon_sp/gnr/chip.c
index c918587..3be2d10 100644
--- a/src/soc/intel/xeon_sp/gnr/chip.c
+++ b/src/soc/intel/xeon_sp/gnr/chip.c
@@ -3,12 +3,14 @@
#include <arch/hpet.h>
#include <arch/ioapic.h>
#include <assert.h>
+#include <bootstate.h>
#include <console/console.h>
#include <console/debug.h>
#include <cpu/x86/lapic.h>
#include <device/pci.h>
#include <gpio.h>
#include <intelblocks/gpio.h>
+#include <intelblocks/itss.h>
#include <intelblocks/lpc_lib.h>
#include <intelblocks/pcr.h>
#include <intelblocks/pmclib.h>
@@ -18,6 +20,7 @@
#include <soc/chip_common.h>
#include <soc/cpu.h>
#include <soc/pch.h>
+#include <soc/pcr_ids.h>
#include <soc/ramstage.h>
#include <soc/soc_util.h>
#include <soc/util.h>
@@ -89,3 +92,15 @@
{
mainboard_silicon_init_params(silupd);
}
+
+static void pirq_init(void *unused)
+{
+ /* to program irq pin/line for pci devices */
+ pch_pirq_init();
+ /* set polarity low for PIRQA to PIRQH */
+ for (int i = 0; i < PIRQ_COUNT; i++) {
+ itss_set_irq_polarity(pcr_read8(PID_ITSS, PCR_ITSS_PIRQA_ROUT + i), 1);
+ }
+}
+
+BOOT_STATE_INIT_ENTRY(BS_DEV_INIT, BS_ON_EXIT, pirq_init, NULL);
diff --git a/src/soc/intel/xeon_sp/gnr/soc_acpi.c b/src/soc/intel/xeon_sp/gnr/soc_acpi.c
index d8160fc..d960b9e 100644
--- a/src/soc/intel/xeon_sp/gnr/soc_acpi.c
+++ b/src/soc/intel/xeon_sp/gnr/soc_acpi.c
@@ -109,6 +109,15 @@
acpigen_pop_len();
acpigen_pop_len();
+
+ /* _PRT */
+ xeonsp_acpigen_write_PRT_pci_bridge(domain);
+ struct device *dev = NULL;
+ while ((dev = dev_bus_each_child(domain->downstream, dev))) {
+ if (!is_pci_bridge(dev))
+ continue;
+ xeonsp_acpigen_write_PRT_pci_bridge(dev);
+ }
}
uint32_t soc_get_granted_pci_features(const struct device *domain)
diff --git a/src/soc/intel/xeon_sp/include/soc/acpi.h b/src/soc/intel/xeon_sp/include/soc/acpi.h
index 7ab681e..6d611db 100644
--- a/src/soc/intel/xeon_sp/include/soc/acpi.h
+++ b/src/soc/intel/xeon_sp/include/soc/acpi.h
@@ -26,4 +26,6 @@
void iio_domain_set_acpi_name(struct device *dev, const char *prefix);
void iio_domain_set_root_port_acpi_names(const struct device *domain);
+void xeonsp_acpigen_write_PRT_pci_bridge(const struct device *br);
+
#endif /* _SOC_ACPI_H_ */
To view, visit change 81569. To unsubscribe, or for help writing mail filters, visit settings.