summary refs log tree commit diff
path: root/drivers/of/irq.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2016-01-14 11:13:28 -0800
committerLinus Torvalds <torvalds@linux-foundation.org>2016-01-14 11:13:28 -0800
commit5339f9d4c2ceccab00b28d65bd5c2b2cd6a3de05 (patch)
tree765564f61fc270c415de903b0dfb1e040c02944a /drivers/of/irq.c
parentcf8d7e3850ee44dc2f0a69405d731af62528a948 (diff)
parent183223770ae8625df8966ed15811d1b3ee8720aa (diff)
downloadlinux-5339f9d4c2ceccab00b28d65bd5c2b2cd6a3de05.tar.gz
Merge tag 'devicetree-for-4.5' of git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux
Pull DeviceTree updates from Rob Herring:

 - Rework and export the changeset API to make it available to users
   other than DT overlays

 - ARM secure devices binding

 - OCTEON USB binding

 - Clean-up of various SRAM binding docs

 - Various other binding doc updates

* tag 'devicetree-for-4.5' of git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux: (21 commits)
  drivers/of: Export OF changeset functions
  Fix documentation for adp1653 DT
  ARM: psci: Fix indentation in DT bindings
  of/platform: export of_default_bus_match_table
  of/unittest: Show broken behaviour in the platform bus
  of: fix declaration of of_io_request_and_map
  of/address: replace printk(KERN_ERR ...) with pr_err(...)
  of/irq: optimize device node matching loop in of_irq_init()
  dt-bindings: tda998x: Document the required 'port' node.
  net/macb: bindings doc: Merge cdns-emac to macb
  dt-bindings: Misc fix for the ATH79 DDR controllers
  dt-bindings: Misc fix for the ATH79 MISC interrupt controllers
  Documentation: dt: Add bindings for Secure-only devices
  dt-bindings: ARM: add arm,cortex-a72 compatible string
  ASoC: Atmel: ClassD: add GCK's parent clock in DT binding
  DT: add Olimex to vendor prefixes
  Documentation: fsl-quadspi: Add fsl,ls1021-qspi compatible string
  Documentation/devicetree: document OCTEON USB bindings
  usb: misc: usb3503: Describe better how to bind clock to the hub
  dt-bindings: Consolidate SRAM bindings from all vendors
  ...
Diffstat (limited to 'drivers/of/irq.c')
-rw-r--r--drivers/of/irq.c27
1 files changed, 13 insertions, 14 deletions
diff --git a/drivers/of/irq.c b/drivers/of/irq.c
index 4fa916dffc91..706e3ff67f8b 100644
--- a/drivers/of/irq.c
+++ b/drivers/of/irq.c
@@ -473,6 +473,7 @@ EXPORT_SYMBOL_GPL(of_irq_to_resource_table);
 
 struct of_intc_desc {
 	struct list_head	list;
+	of_irq_init_cb_t	irq_init_cb;
 	struct device_node	*dev;
 	struct device_node	*interrupt_parent;
 };
@@ -486,6 +487,7 @@ struct of_intc_desc {
  */
 void __init of_irq_init(const struct of_device_id *matches)
 {
+	const struct of_device_id *match;
 	struct device_node *np, *parent = NULL;
 	struct of_intc_desc *desc, *temp_desc;
 	struct list_head intc_desc_list, intc_parent_list;
@@ -493,10 +495,15 @@ void __init of_irq_init(const struct of_device_id *matches)
 	INIT_LIST_HEAD(&intc_desc_list);
 	INIT_LIST_HEAD(&intc_parent_list);
 
-	for_each_matching_node(np, matches) {
+	for_each_matching_node_and_match(np, matches, &match) {
 		if (!of_find_property(np, "interrupt-controller", NULL) ||
 				!of_device_is_available(np))
 			continue;
+
+		if (WARN(!match->data, "of_irq_init: no init function for %s\n",
+			 match->compatible))
+			continue;
+
 		/*
 		 * Here, we allocate and populate an of_intc_desc with the node
 		 * pointer, interrupt-parent device_node etc.
@@ -507,6 +514,7 @@ void __init of_irq_init(const struct of_device_id *matches)
 			goto err;
 		}
 
+		desc->irq_init_cb = match->data;
 		desc->dev = of_node_get(np);
 		desc->interrupt_parent = of_irq_find_parent(np);
 		if (desc->interrupt_parent == np)
@@ -526,27 +534,18 @@ void __init of_irq_init(const struct of_device_id *matches)
 		 * The assumption is that NULL parent means a root controller.
 		 */
 		list_for_each_entry_safe(desc, temp_desc, &intc_desc_list, list) {
-			const struct of_device_id *match;
 			int ret;
-			of_irq_init_cb_t irq_init_cb;
 
 			if (desc->interrupt_parent != parent)
 				continue;
 
 			list_del(&desc->list);
-			match = of_match_node(matches, desc->dev);
-			if (WARN(!match->data,
-			    "of_irq_init: no init function for %s\n",
-			    match->compatible)) {
-				kfree(desc);
-				continue;
-			}
 
-			pr_debug("of_irq_init: init %s @ %p, parent %p\n",
-				 match->compatible,
+			pr_debug("of_irq_init: init %s (%p), parent %p\n",
+				 desc->dev->full_name,
 				 desc->dev, desc->interrupt_parent);
-			irq_init_cb = (of_irq_init_cb_t)match->data;
-			ret = irq_init_cb(desc->dev, desc->interrupt_parent);
+			ret = desc->irq_init_cb(desc->dev,
+						desc->interrupt_parent);
 			if (ret) {
 				kfree(desc);
 				continue;