summaryrefslogtreecommitdiff
path: root/arch/mips
diff options
context:
space:
mode:
authorJon Derrick <jonathan.derrick@intel.com>2020-07-21 14:26:09 -0600
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2020-08-19 08:16:27 +0200
commita3ec61c84d857ed170979839cfcbf85b3ca7af4f (patch)
tree2c85c38840a941018d979d9059d00d2f94eb7f41 /arch/mips
parent35e1338bddcd7dfe056cc4e492b9e1e878203eb9 (diff)
irqdomain/treewide: Free firmware node after domain removal
commit ec0160891e387f4771f953b888b1fe951398e5d9 upstream. Commit 711419e504eb ("irqdomain: Add the missing assignment of domain->fwnode for named fwnode") unintentionally caused a dangling pointer page fault issue on firmware nodes that were freed after IRQ domain allocation. Commit e3beca48a45b fixed that dangling pointer issue by only freeing the firmware node after an IRQ domain allocation failure. That fix no longer frees the firmware node immediately, but leaves the firmware node allocated after the domain is removed. The firmware node must be kept around through irq_domain_remove, but should be freed it afterwards. Add the missing free operations after domain removal where where appropriate. Fixes: e3beca48a45b ("irqdomain/treewide: Keep firmware node unconditionally allocated") Signed-off-by: Jon Derrick <jonathan.derrick@intel.com> Signed-off-by: Thomas Gleixner <tglx@linutronix.de> Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com> Acked-by: Bjorn Helgaas <bhelgaas@google.com> # drivers/pci Cc: stable@vger.kernel.org Link: https://lkml.kernel.org/r/1595363169-7157-1-git-send-email-jonathan.derrick@intel.com Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'arch/mips')
-rw-r--r--arch/mips/pci/pci-xtalk-bridge.c3
1 files changed, 3 insertions, 0 deletions
diff --git a/arch/mips/pci/pci-xtalk-bridge.c b/arch/mips/pci/pci-xtalk-bridge.c
index 6ce76b18186e..c4b1c6cf2660 100644
--- a/arch/mips/pci/pci-xtalk-bridge.c
+++ b/arch/mips/pci/pci-xtalk-bridge.c
@@ -539,6 +539,7 @@ err_free_resource:
pci_free_resource_list(&host->windows);
err_remove_domain:
irq_domain_remove(domain);
+ irq_domain_free_fwnode(fn);
return err;
}
@@ -546,8 +547,10 @@ static int bridge_remove(struct platform_device *pdev)
{
struct pci_bus *bus = platform_get_drvdata(pdev);
struct bridge_controller *bc = BRIDGE_CONTROLLER(bus);
+ struct fwnode_handle *fn = bc->domain->fwnode;
irq_domain_remove(bc->domain);
+ irq_domain_free_fwnode(fn);
pci_lock_rescan_remove();
pci_stop_root_bus(bus);
pci_remove_root_bus(bus);