soc/amd: move common pci_domain_fill_ssdt implementation to acpi/

Even though it has an 'amd_' prefix, the amd_pci_domain_fill_ssdt
implementation doesn't contain any AMD-specific code and can also be
used by other SoCs. So factor it out, move the implementation to
src/acpi/acpigen_pci_root_resource_producer.c, and rename it to
pci_domain_fill_ssdt. When a SoC now assigns pci_domain_fill_ssdt to its
domain operation's acpi_fill_ssdt function pointer, the PCI domain
resource producer information will be added to the SSDT.

Signed-off-by: Felix Held <felix-coreboot@felixheld.de>
Change-Id: I7bd8568cf0b7051c74adbedfe0e416a0938ccb99
Reviewed-on: https://review.coreboot.org/c/coreboot/+/80464
Reviewed-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Reviewed-by: Matt DeVillier <matt.devillier@amd.corp-partner.google.com>
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
diff --git a/src/acpi/Makefile.mk b/src/acpi/Makefile.mk
index 6bb34cb..e9d5cb0 100644
--- a/src/acpi/Makefile.mk
+++ b/src/acpi/Makefile.mk
@@ -7,6 +7,7 @@
 ramstage-y += acpi_apic.c
 ramstage-y += acpi_dmar.c
 ramstage-y += acpi_hpet.c
+ramstage-y += acpigen_pci_root_resource_producer.c
 endif
 ramstage-$(CONFIG_ACPI_PPTT) += acpi_pptt.c
 ramstage-y += acpigen.c
diff --git a/src/acpi/acpigen_pci_root_resource_producer.c b/src/acpi/acpigen_pci_root_resource_producer.c
new file mode 100644
index 0000000..c9efe0e
--- /dev/null
+++ b/src/acpi/acpigen_pci_root_resource_producer.c
@@ -0,0 +1,106 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+
+#include <acpi/acpigen.h>
+#include <acpi/acpigen_pci.h>
+#include <arch/pci_io_cfg.h>
+#include <arch/vga.h>
+#include <console/console.h>
+#include <device/device.h>
+#include <types.h>
+
+static void write_ssdt_domain_io_producer_range_helper(const char *domain_name,
+						       resource_t base, resource_t limit)
+{
+	printk(BIOS_DEBUG, "%s _CRS: adding IO range [%llx-%llx]\n", domain_name, base, limit);
+	acpigen_resource_producer_io(base, limit);
+}
+
+static void write_ssdt_domain_io_producer_range(const char *domain_name,
+						resource_t base, resource_t limit)
+{
+	/*
+	 * Split the IO region at the PCI config IO ports so that the IO resource producer
+	 * won't cover the same IO ports that the IO resource consumer for the PCI config IO
+	 * ports in the same ACPI device already covers.
+	 */
+	if (base < PCI_IO_CONFIG_INDEX) {
+		write_ssdt_domain_io_producer_range_helper(domain_name,
+					base,
+					MIN(limit, PCI_IO_CONFIG_INDEX - 1));
+	}
+	if (limit > PCI_IO_CONFIG_LAST_PORT) {
+		write_ssdt_domain_io_producer_range_helper(domain_name,
+					MAX(base, PCI_IO_CONFIG_LAST_PORT + 1),
+					limit);
+	}
+}
+
+static void write_ssdt_domain_mmio_producer_range(const char *domain_name,
+						  resource_t base, resource_t limit)
+{
+	printk(BIOS_DEBUG, "%s _CRS: adding MMIO range [%llx-%llx]\n",
+	       domain_name, base, limit);
+	acpigen_resource_producer_mmio(base, limit,
+		MEM_RSRC_FLAG_MEM_READ_WRITE | MEM_RSRC_FLAG_MEM_ATTR_NON_CACHE);
+}
+
+void pci_domain_fill_ssdt(const struct device *domain)
+{
+	const char *acpi_scope = acpi_device_path(domain);
+	printk(BIOS_DEBUG, "%s ACPI scope: '%s'\n", __func__, acpi_scope);
+	acpigen_write_scope(acpi_device_path(domain));
+
+	acpigen_write_name("_CRS");
+	acpigen_write_resourcetemplate_header();
+
+	/* PCI bus number range in domain */
+	printk(BIOS_DEBUG, "%s _CRS: adding busses [%x-%x] in segment group %x\n",
+	       acpi_device_name(domain), domain->downstream->secondary,
+	       domain->downstream->max_subordinate, domain->downstream->segment_group);
+	acpigen_resource_producer_bus_number(domain->downstream->secondary,
+					     domain->downstream->max_subordinate);
+
+	if (domain->path.domain.domain == 0) {
+		/* ACPI 6.4.2.5 I/O Port Descriptor */
+		acpigen_write_io16(PCI_IO_CONFIG_INDEX, PCI_IO_CONFIG_LAST_PORT, 1,
+				   PCI_IO_CONFIG_PORT_COUNT, 1);
+	}
+
+	struct resource *res;
+	for (res = domain->resource_list; res != NULL; res = res->next) {
+		if (!(res->flags & IORESOURCE_ASSIGNED))
+			continue;
+		/* Don't add MMIO producer ranges for reserved MMIO regions from non-PCI
+		   devices */
+		if (res->flags & IORESOURCE_RESERVE)
+			continue;
+		/* Don't add MMIO producer ranges for DRAM regions */
+		if (res->flags & IORESOURCE_STORED)
+			continue;
+		switch (res->flags & IORESOURCE_TYPE_MASK) {
+		case IORESOURCE_IO:
+			write_ssdt_domain_io_producer_range(acpi_device_name(domain),
+							    res->base, res->limit);
+			break;
+		case IORESOURCE_MEM:
+			write_ssdt_domain_mmio_producer_range(acpi_device_name(domain),
+							      res->base, res->limit);
+			break;
+		default:
+			break;
+		}
+	}
+
+	if (domain->downstream->bridge_ctrl & PCI_BRIDGE_CTL_VGA) {
+		printk(BIOS_DEBUG, "%s _CRS: adding VGA resource\n", acpi_device_name(domain));
+		acpigen_resource_producer_mmio(VGA_MMIO_BASE, VGA_MMIO_LIMIT,
+			MEM_RSRC_FLAG_MEM_READ_WRITE | MEM_RSRC_FLAG_MEM_ATTR_CACHE);
+	}
+
+	acpigen_write_resourcetemplate_footer();
+
+	acpigen_write_SEG(domain->downstream->segment_group);
+	acpigen_write_BBN(domain->downstream->secondary);
+	/* Scope */
+	acpigen_pop_len();
+}
diff --git a/src/include/acpi/acpigen_pci.h b/src/include/acpi/acpigen_pci.h
index 8a96eb3..69216ec 100644
--- a/src/include/acpi/acpigen_pci.h
+++ b/src/include/acpi/acpigen_pci.h
@@ -14,4 +14,6 @@
 void acpigen_write_PRT_source_entry(unsigned int pci_dev, unsigned int acpi_pin,
 				    const char *source_path, unsigned int index);
 
+void pci_domain_fill_ssdt(const struct device *domain);
+
 #endif /* ACPIGEN_PCI_H */
diff --git a/src/soc/amd/cezanne/chip.c b/src/soc/amd/cezanne/chip.c
index 83fd5c6..7463352 100644
--- a/src/soc/amd/cezanne/chip.c
+++ b/src/soc/amd/cezanne/chip.c
@@ -1,5 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 
+#include <acpi/acpigen_pci.h>
 #include <amdblocks/acpi.h>
 #include <amdblocks/data_fabric.h>
 #include <amdblocks/fsp.h>
@@ -32,7 +33,7 @@
 	.scan_bus	= amd_pci_domain_scan_bus,
 	.init		= amd_pci_domain_init,
 	.acpi_name	= soc_acpi_name,
-	.acpi_fill_ssdt	= amd_pci_domain_fill_ssdt,
+	.acpi_fill_ssdt	= pci_domain_fill_ssdt,
 };
 
 static void soc_init(void *chip_info)
diff --git a/src/soc/amd/common/block/data_fabric/domain.c b/src/soc/amd/common/block/data_fabric/domain.c
index ab85e2b5..b056d60 100644
--- a/src/soc/amd/common/block/data_fabric/domain.c
+++ b/src/soc/amd/common/block/data_fabric/domain.c
@@ -1,10 +1,8 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 
-#include <acpi/acpigen.h>
 #include <amdblocks/data_fabric.h>
 #include <amdblocks/root_complex.h>
 #include <arch/ioapic.h>
-#include <arch/vga.h>
 #include <console/console.h>
 #include <cpu/amd/mtrr.h>
 #include <cpu/cpu.h>
@@ -214,100 +212,3 @@
 		read_soc_memmap_resources(domain, &idx);
 	}
 }
-
-static void write_ssdt_domain_io_producer_range_helper(const char *domain_name,
-						       resource_t base, resource_t limit)
-{
-	printk(BIOS_DEBUG, "%s _CRS: adding IO range [%llx-%llx]\n", domain_name, base, limit);
-	acpigen_resource_producer_io(base, limit);
-}
-
-static void write_ssdt_domain_io_producer_range(const char *domain_name,
-						resource_t base, resource_t limit)
-{
-	/*
-	 * Split the IO region at the PCI config IO ports so that the IO resource producer
-	 * won't cover the same IO ports that the IO resource consumer for the PCI config IO
-	 * ports in the same ACPI device already covers.
-	 */
-	if (base < PCI_IO_CONFIG_INDEX) {
-		write_ssdt_domain_io_producer_range_helper(domain_name,
-					base,
-					MIN(limit, PCI_IO_CONFIG_INDEX - 1));
-	}
-	if (limit > PCI_IO_CONFIG_LAST_PORT) {
-		write_ssdt_domain_io_producer_range_helper(domain_name,
-					MAX(base, PCI_IO_CONFIG_LAST_PORT + 1),
-					limit);
-	}
-}
-
-static void write_ssdt_domain_mmio_producer_range(const char *domain_name,
-						  resource_t base, resource_t limit)
-{
-	printk(BIOS_DEBUG, "%s _CRS: adding MMIO range [%llx-%llx]\n",
-	       domain_name, base, limit);
-	acpigen_resource_producer_mmio(base, limit,
-		MEM_RSRC_FLAG_MEM_READ_WRITE | MEM_RSRC_FLAG_MEM_ATTR_NON_CACHE);
-}
-
-void amd_pci_domain_fill_ssdt(const struct device *domain)
-{
-	const char *acpi_scope = acpi_device_path(domain);
-	printk(BIOS_DEBUG, "%s ACPI scope: '%s'\n", __func__, acpi_scope);
-	acpigen_write_scope(acpi_device_path(domain));
-
-	acpigen_write_name("_CRS");
-	acpigen_write_resourcetemplate_header();
-
-	/* PCI bus number range in domain */
-	printk(BIOS_DEBUG, "%s _CRS: adding busses [%x-%x] in segment group %x\n",
-	       acpi_device_name(domain), domain->downstream->secondary,
-	       domain->downstream->max_subordinate, domain->downstream->segment_group);
-	acpigen_resource_producer_bus_number(domain->downstream->secondary,
-					     domain->downstream->max_subordinate);
-
-	if (domain->path.domain.domain == 0) {
-		/* ACPI 6.4.2.5 I/O Port Descriptor */
-		acpigen_write_io16(PCI_IO_CONFIG_INDEX, PCI_IO_CONFIG_LAST_PORT, 1,
-				   PCI_IO_CONFIG_PORT_COUNT, 1);
-	}
-
-	struct resource *res;
-	for (res = domain->resource_list; res != NULL; res = res->next) {
-		if (!(res->flags & IORESOURCE_ASSIGNED))
-			continue;
-		/* Don't add MMIO producer ranges for reserved MMIO regions from non-PCI
-		   devices */
-		if (res->flags & IORESOURCE_RESERVE)
-			continue;
-		/* Don't add MMIO producer ranges for DRAM regions */
-		if (res->flags & IORESOURCE_STORED)
-			continue;
-		switch (res->flags & IORESOURCE_TYPE_MASK) {
-		case IORESOURCE_IO:
-			write_ssdt_domain_io_producer_range(acpi_device_name(domain),
-							    res->base, res->limit);
-			break;
-		case IORESOURCE_MEM:
-			write_ssdt_domain_mmio_producer_range(acpi_device_name(domain),
-							      res->base, res->limit);
-			break;
-		default:
-			break;
-		}
-	}
-
-	if (domain->downstream->bridge_ctrl & PCI_BRIDGE_CTL_VGA) {
-		printk(BIOS_DEBUG, "%s _CRS: adding VGA resource\n", acpi_device_name(domain));
-		acpigen_resource_producer_mmio(VGA_MMIO_BASE, VGA_MMIO_LIMIT,
-			MEM_RSRC_FLAG_MEM_READ_WRITE | MEM_RSRC_FLAG_MEM_ATTR_CACHE);
-	}
-
-	acpigen_write_resourcetemplate_footer();
-
-	acpigen_write_SEG(domain->downstream->segment_group);
-	acpigen_write_BBN(domain->downstream->secondary);
-	/* Scope */
-	acpigen_pop_len();
-}
diff --git a/src/soc/amd/common/block/include/amdblocks/data_fabric.h b/src/soc/amd/common/block/include/amdblocks/data_fabric.h
index f0073df..fbed0b2 100644
--- a/src/soc/amd/common/block/include/amdblocks/data_fabric.h
+++ b/src/soc/amd/common/block/include/amdblocks/data_fabric.h
@@ -55,6 +55,4 @@
 void amd_pci_domain_read_resources(struct device *domain);
 void amd_pci_domain_scan_bus(struct device *domain);
 
-void amd_pci_domain_fill_ssdt(const struct device *domain);
-
 #endif /* AMD_BLOCK_DATA_FABRIC_H */
diff --git a/src/soc/amd/genoa_poc/domain.c b/src/soc/amd/genoa_poc/domain.c
index 14248cd..5672f65 100644
--- a/src/soc/amd/genoa_poc/domain.c
+++ b/src/soc/amd/genoa_poc/domain.c
@@ -1,5 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 
+#include <acpi/acpigen_pci.h>
 #include <amdblocks/ioapic.h>
 #include <amdblocks/data_fabric.h>
 #include <amdblocks/root_complex.h>
@@ -63,5 +64,5 @@
 	.scan_bus	= amd_pci_domain_scan_bus,
 	.init		= amd_pci_domain_init,
 	.acpi_name	= genoa_domain_acpi_name,
-	.acpi_fill_ssdt	= amd_pci_domain_fill_ssdt,
+	.acpi_fill_ssdt	= pci_domain_fill_ssdt,
 };
diff --git a/src/soc/amd/glinda/chip.c b/src/soc/amd/glinda/chip.c
index 515580d..e227f41 100644
--- a/src/soc/amd/glinda/chip.c
+++ b/src/soc/amd/glinda/chip.c
@@ -2,6 +2,7 @@
 
 /* TODO: Update for Glinda */
 
+#include <acpi/acpigen_pci.h>
 #include <amdblocks/acpi.h>
 #include <amdblocks/data_fabric.h>
 #include <amdblocks/fsp.h>
@@ -34,7 +35,7 @@
 	.scan_bus	= amd_pci_domain_scan_bus,
 	.init		= amd_pci_domain_init,
 	.acpi_name	= soc_acpi_name,
-	.acpi_fill_ssdt	= amd_pci_domain_fill_ssdt,
+	.acpi_fill_ssdt	= pci_domain_fill_ssdt,
 };
 
 static void soc_init(void *chip_info)
diff --git a/src/soc/amd/mendocino/chip.c b/src/soc/amd/mendocino/chip.c
index 729f97a..fb61f585 100644
--- a/src/soc/amd/mendocino/chip.c
+++ b/src/soc/amd/mendocino/chip.c
@@ -1,5 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 
+#include <acpi/acpigen_pci.h>
 #include <amdblocks/acpi.h>
 #include <amdblocks/data_fabric.h>
 #include <amdblocks/fsp.h>
@@ -32,7 +33,7 @@
 	.scan_bus	= amd_pci_domain_scan_bus,
 	.init		= amd_pci_domain_init,
 	.acpi_name	= soc_acpi_name,
-	.acpi_fill_ssdt	= amd_pci_domain_fill_ssdt,
+	.acpi_fill_ssdt	= pci_domain_fill_ssdt,
 };
 
 static void soc_init(void *chip_info)
diff --git a/src/soc/amd/phoenix/chip.c b/src/soc/amd/phoenix/chip.c
index f45e7b8..a88468b 100644
--- a/src/soc/amd/phoenix/chip.c
+++ b/src/soc/amd/phoenix/chip.c
@@ -2,6 +2,7 @@
 
 /* TODO: Update for Phoenix */
 
+#include <acpi/acpigen_pci.h>
 #include <amdblocks/acpi.h>
 #include <amdblocks/data_fabric.h>
 #include <amdblocks/fsp.h>
@@ -35,7 +36,7 @@
 	.scan_bus	= amd_pci_domain_scan_bus,
 	.init		= amd_pci_domain_init,
 	.acpi_name	= soc_acpi_name,
-	.acpi_fill_ssdt	= amd_pci_domain_fill_ssdt,
+	.acpi_fill_ssdt	= pci_domain_fill_ssdt,
 };
 
 static void soc_init(void *chip_info)
diff --git a/src/soc/amd/picasso/chip.c b/src/soc/amd/picasso/chip.c
index 7411948..e642060 100644
--- a/src/soc/amd/picasso/chip.c
+++ b/src/soc/amd/picasso/chip.c
@@ -1,5 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 
+#include <acpi/acpigen_pci.h>
 #include <amdblocks/acpi.h>
 #include <amdblocks/data_fabric.h>
 #include <amdblocks/fsp.h>
@@ -33,7 +34,7 @@
 	.scan_bus	= amd_pci_domain_scan_bus,
 	.init		= amd_pci_domain_init,
 	.acpi_name	= soc_acpi_name,
-	.acpi_fill_ssdt	= amd_pci_domain_fill_ssdt,
+	.acpi_fill_ssdt	= pci_domain_fill_ssdt,
 };
 
 static void soc_init(void *chip_info)