Browse Source

Merge tag 'pci-v4.10-fixes-3' of git://git.kernel.org/pub/scm/linux/kernel/git/helgaas/pci

Pull PCI fixes from Bjorn Helgaas:

 - check MSI affinity vs. number of vectors to avoid memory corruption

 - drop runtime power management for PCIe hotplug ports for now to avoid
   regressing hotplug via sysfs

* tag 'pci-v4.10-fixes-3' of git://git.kernel.org/pub/scm/linux/kernel/git/helgaas/pci:
  Revert "PCI: pciehp: Add runtime PM support for PCIe hotplug ports"
  PCI/MSI: Don't apply affinity if there aren't enough vectors left
Linus Torvalds 8 years ago
parent
commit
be11f436a8
3 changed files with 16 additions and 12 deletions
  1. 0 6
      drivers/pci/hotplug/pciehp_ctrl.c
  2. 10 0
      drivers/pci/msi.c
  3. 6 6
      drivers/pci/pci.c

+ 0 - 6
drivers/pci/hotplug/pciehp_ctrl.c

@@ -31,7 +31,6 @@
 #include <linux/kernel.h>
 #include <linux/kernel.h>
 #include <linux/types.h>
 #include <linux/types.h>
 #include <linux/slab.h>
 #include <linux/slab.h>
-#include <linux/pm_runtime.h>
 #include <linux/pci.h>
 #include <linux/pci.h>
 #include "../pci.h"
 #include "../pci.h"
 #include "pciehp.h"
 #include "pciehp.h"
@@ -99,7 +98,6 @@ static int board_added(struct slot *p_slot)
 	pciehp_green_led_blink(p_slot);
 	pciehp_green_led_blink(p_slot);
 
 
 	/* Check link training status */
 	/* Check link training status */
-	pm_runtime_get_sync(&ctrl->pcie->port->dev);
 	retval = pciehp_check_link_status(ctrl);
 	retval = pciehp_check_link_status(ctrl);
 	if (retval) {
 	if (retval) {
 		ctrl_err(ctrl, "Failed to check link status\n");
 		ctrl_err(ctrl, "Failed to check link status\n");
@@ -120,14 +118,12 @@ static int board_added(struct slot *p_slot)
 		if (retval != -EEXIST)
 		if (retval != -EEXIST)
 			goto err_exit;
 			goto err_exit;
 	}
 	}
-	pm_runtime_put(&ctrl->pcie->port->dev);
 
 
 	pciehp_green_led_on(p_slot);
 	pciehp_green_led_on(p_slot);
 	pciehp_set_attention_status(p_slot, 0);
 	pciehp_set_attention_status(p_slot, 0);
 	return 0;
 	return 0;
 
 
 err_exit:
 err_exit:
-	pm_runtime_put(&ctrl->pcie->port->dev);
 	set_slot_off(ctrl, p_slot);
 	set_slot_off(ctrl, p_slot);
 	return retval;
 	return retval;
 }
 }
@@ -141,9 +137,7 @@ static int remove_board(struct slot *p_slot)
 	int retval;
 	int retval;
 	struct controller *ctrl = p_slot->ctrl;
 	struct controller *ctrl = p_slot->ctrl;
 
 
-	pm_runtime_get_sync(&ctrl->pcie->port->dev);
 	retval = pciehp_unconfigure_device(p_slot);
 	retval = pciehp_unconfigure_device(p_slot);
-	pm_runtime_put(&ctrl->pcie->port->dev);
 	if (retval)
 	if (retval)
 		return retval;
 		return retval;
 
 

+ 10 - 0
drivers/pci/msi.c

@@ -1206,6 +1206,16 @@ int pci_alloc_irq_vectors_affinity(struct pci_dev *dev, unsigned int min_vecs,
 	if (flags & PCI_IRQ_AFFINITY) {
 	if (flags & PCI_IRQ_AFFINITY) {
 		if (!affd)
 		if (!affd)
 			affd = &msi_default_affd;
 			affd = &msi_default_affd;
+
+		if (affd->pre_vectors + affd->post_vectors > min_vecs)
+			return -EINVAL;
+
+		/*
+		 * If there aren't any vectors left after applying the pre/post
+		 * vectors don't bother with assigning affinity.
+		 */
+		if (affd->pre_vectors + affd->post_vectors == min_vecs)
+			affd = NULL;
 	} else {
 	} else {
 		if (WARN_ON(affd))
 		if (WARN_ON(affd))
 			affd = NULL;
 			affd = NULL;

+ 6 - 6
drivers/pci/pci.c

@@ -2241,10 +2241,13 @@ bool pci_bridge_d3_possible(struct pci_dev *bridge)
 			return false;
 			return false;
 
 
 		/*
 		/*
-		 * Hotplug ports handled by firmware in System Management Mode
+		 * Hotplug interrupts cannot be delivered if the link is down,
+		 * so parents of a hotplug port must stay awake. In addition,
+		 * hotplug ports handled by firmware in System Management Mode
 		 * may not be put into D3 by the OS (Thunderbolt on non-Macs).
 		 * may not be put into D3 by the OS (Thunderbolt on non-Macs).
+		 * For simplicity, disallow in general for now.
 		 */
 		 */
-		if (bridge->is_hotplug_bridge && !pciehp_is_native(bridge))
+		if (bridge->is_hotplug_bridge)
 			return false;
 			return false;
 
 
 		if (pci_bridge_d3_force)
 		if (pci_bridge_d3_force)
@@ -2276,10 +2279,7 @@ static int pci_dev_check_d3cold(struct pci_dev *dev, void *data)
 	     !pci_pme_capable(dev, PCI_D3cold)) ||
 	     !pci_pme_capable(dev, PCI_D3cold)) ||
 
 
 	    /* If it is a bridge it must be allowed to go to D3. */
 	    /* If it is a bridge it must be allowed to go to D3. */
-	    !pci_power_manageable(dev) ||
-
-	    /* Hotplug interrupts cannot be delivered if the link is down. */
-	    dev->is_hotplug_bridge)
+	    !pci_power_manageable(dev))
 
 
 		*d3cold_ok = false;
 		*d3cold_ok = false;