[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-Id: <1452691267-32240-14-git-send-email-tn@semihalf.com>
Date: Wed, 13 Jan 2016 14:20:59 +0100
From: Tomasz Nowicki <tn@...ihalf.com>
To: bhelgaas@...gle.com, arnd@...db.de, will.deacon@....com,
catalin.marinas@....com, rjw@...ysocki.net, hanjun.guo@...aro.org,
Lorenzo.Pieralisi@....com, okaya@...eaurora.org,
jiang.liu@...ux.intel.com, Stefano.Stabellini@...citrix.com
Cc: robert.richter@...iumnetworks.com, mw@...ihalf.com,
Liviu.Dudau@....com, ddaney@...iumnetworks.com, tglx@...utronix.de,
wangyijing@...wei.com, Suravee.Suthikulpanit@....com,
msalter@...hat.com, linux-pci@...r.kernel.org,
linux-arm-kernel@...ts.infradead.org, linux-acpi@...r.kernel.org,
linux-kernel@...r.kernel.org, linaro-acpi@...ts.linaro.org,
jchandra@...adcom.com, jcm@...hat.com,
Tomasz Nowicki <tn@...ihalf.com>
Subject: [PATCH V3 13/21] pci, acpi: Provide generic way to assign bus domain number.
As we now have valid PCI host bridge device reference we can
introduce code that is going to find its bus domain number using
ACPI _SEG method.
Note that _SEG method is optional, therefore _SEG absence means
that all PCI buses belong to domain 0.
Signed-off-by: Tomasz Nowicki <tn@...ihalf.com>
Reviewed-by: Liviu Dudau <Liviu.Dudau@....com>
Tested-by: Suravee Suthikulpanit <Suravee.Suthikulpanit@....com>
Tested-by: Jeremy Linton <jeremy.linton@....com>
---
drivers/pci/pci.c | 29 +++++++++++++++++++++++++----
1 file changed, 25 insertions(+), 4 deletions(-)
diff --git a/drivers/pci/pci.c b/drivers/pci/pci.c
index 7274006..39a985b 100644
--- a/drivers/pci/pci.c
+++ b/drivers/pci/pci.c
@@ -25,6 +25,7 @@
#include <linux/device.h>
#include <linux/pm_runtime.h>
#include <linux/pci_hotplug.h>
+#include <linux/acpi.h>
#include <asm-generic/pci-bridge.h>
#include <asm/setup.h>
#include <linux/aer.h>
@@ -4796,14 +4797,34 @@ void pci_bus_assign_domain_nr(struct pci_bus *bus, struct device *parent)
* API and update the use_dt_domains value to keep track of method we
* are using to assign domain numbers (use_dt_domains = 0).
*
+ * IF ACPI, we expect non-DT method (use_dt_domains == -1)
+ * and call _SEG method for corresponding host bridge device.
+ * If _SEG method does not exist, following ACPI spec (6.5.6)
+ * all PCI buses belong to domain 0.
+ *
* All other combinations imply we have a platform that is trying
- * to mix domain numbers obtained from DT and pci_get_new_domain_nr(),
- * which is a recipe for domain mishandling and it is prevented by
- * invalidating the domain value (domain = -1) and printing a
- * corresponding error.
+ * to mix domain numbers obtained from DT, ACPI and
+ * pci_get_new_domain_nr(), which is a recipe for domain mishandling and
+ * it is prevented by invalidating the domain value (domain = -1) and
+ * printing a corresponding error.
*/
+
if (domain >= 0 && use_dt_domains) {
use_dt_domains = 1;
+#ifdef CONFIG_ACPI
+ } else if (!acpi_disabled && use_dt_domains == -1) {
+ struct acpi_device *acpi_dev = to_acpi_device(parent);
+ unsigned long long segment = 0;
+ acpi_status status;
+
+ status = acpi_evaluate_integer(acpi_dev->handle,
+ METHOD_NAME__SEG, NULL,
+ &segment);
+ if (ACPI_FAILURE(status) && status != AE_NOT_FOUND)
+ dev_err(&acpi_dev->dev, "can't evaluate _SEG\n");
+
+ domain = segment;
+#endif
} else if (domain < 0 && use_dt_domains != 1) {
use_dt_domains = 0;
domain = pci_get_new_domain_nr();
--
1.9.1
Powered by blists - more mailing lists