PCI updates for v3.13:
PCI device hotplug - Move device_del() from pci_stop_dev() to pci_destroy_dev() (Rafael J. Wysocki) Host bridge drivers - Update maintainers for DesignWare, i.MX6, Armada, R-Car (Bjorn Helgaas) - mvebu: Return 'unsupported' for Interrupt Line and Interrupt Pin (Jason Gunthorpe) Miscellaneous - Avoid unnecessary CPU switch when calling .probe() (Alexander Duyck) - Revert "workqueue: allow work_on_cpu() to be called recursively" (Bjorn Helgaas) - Disable Bus Master only on kexec reboot (Khalid Aziz) - Omit PCI ID macro strings to shorten quirk names for LTO (Michal Marek) MAINTAINERS | 33 +++++++++++++++++++++++++++++++++ drivers/pci/host/pci-mvebu.c | 5 +++++ drivers/pci/pci-driver.c | 38 ++++++++++++++++++++++++++++++-------- drivers/pci/remove.c | 4 +++- include/linux/kexec.h | 3 +++ include/linux/pci.h | 30 +++++++++++++++--------------- kernel/kexec.c | 4 ++++ kernel/workqueue.c | 32 ++++++++++---------------------- 8 files changed, 103 insertions(+), 46 deletions(-) -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.11 (GNU/Linux) iQIcBAABAgAGBQJSrLDLAAoJEFmIoMA60/r8JO4P/iakGDezwXcd9YTbdaq/NmEK 31JtBao9rJNSUXpFGaFKGm99A479QNb+Fo1o5NaysyGbcAA2W0HeCkaee13hpw2D l3wvzJRoEwqVySOzMwlGsxxhYuvGiZ2WVALNkwBzwyCiYtypNnUtGNCSp/3J6XKp 2ZUjoagyixdS4oYoR4irZucPBWwzW89Gx4oJ0rBttNVsXjiT1D2OzYDYTuxMyb2E ZjXJqTUYzfwiFxqKPrGOabUPD9GX3EWaFmu01FLlsSznPZkk9yJR3/eq6I6utp/E WSpP+7v3jnPHjZVky1FdHaP5wqurtNRsiWBQVyNYF+M5WofKA1hGA+niJDEB/pVL vE74fJfZzpET1jlZR+7Z5qHPxW2A8Q2ARn74A42DYLQGmJEh7VdARcayV1E4diRH DzEnhf33b9bwIC1Q0cESWZ5RH4r2Xbjg0a1qoVQYi5VEJEMWXID3Ofk64Bd9QOz4 oLZ27V7clurD+gNarch/zgpd9LVIHLFriR2YWPpA0Iwy9EjueH8GsiOS3NqDn2SQ sQg5utE4vdnix4VrCvvbufAr3kJngndtuj/s7I3lZqi7nCyS+jeFFvMUd9h3MUqZ rs1IN1/qeTBBNi2dtmcKDN2ItahCoBhTI37JRaijZwe+B5m6mTe049it+E0SZPI2 IqLOYWL4ggT0se/cMXld =Edvk -----END PGP SIGNATURE----- Merge tag 'pci-v3.13-fixes-2' of git://git.kernel.org/pub/scm/linux/kernel/git/helgaas/pci Pull PCI updates from Bjorn Helgaas: "PCI device hotplug - Move device_del() from pci_stop_dev() to pci_destroy_dev() (Rafael Wysocki) Host bridge drivers - Update maintainers for DesignWare, i.MX6, Armada, R-Car (Bjorn Helgaas) - mvebu: Return 'unsupported' for Interrupt Line and Interrupt Pin (Jason Gunthorpe) Miscellaneous - Avoid unnecessary CPU switch when calling .probe() (Alexander Duyck) - Revert "workqueue: allow work_on_cpu() to be called recursively" (Bjorn Helgaas) - Disable Bus Master only on kexec reboot (Khalid Aziz) - Omit PCI ID macro strings to shorten quirk names for LTO (Michal Marek)" * tag 'pci-v3.13-fixes-2' of git://git.kernel.org/pub/scm/linux/kernel/git/helgaas/pci: MAINTAINERS: Add DesignWare, i.MX6, Armada, R-Car PCI host maintainers PCI: Disable Bus Master only on kexec reboot PCI: mvebu: Return 'unsupported' for Interrupt Line and Interrupt Pin PCI: Omit PCI ID macro strings to shorten quirk names PCI: Move device_del() from pci_stop_dev() to pci_destroy_dev() Revert "workqueue: allow work_on_cpu() to be called recursively" PCI: Avoid unnecessary CPU switch when calling driver .probe() method
This commit is contained in:
commit
9199c4caa1
33
MAINTAINERS
33
MAINTAINERS
|
@ -6465,19 +6465,52 @@ F: drivers/pci/
|
|||
F: include/linux/pci*
|
||||
F: arch/x86/pci/
|
||||
|
||||
PCI DRIVER FOR IMX6
|
||||
M: Richard Zhu <r65037@freescale.com>
|
||||
M: Shawn Guo <shawn.guo@linaro.org>
|
||||
L: linux-pci@vger.kernel.org
|
||||
L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
|
||||
S: Maintained
|
||||
F: drivers/pci/host/*imx6*
|
||||
|
||||
PCI DRIVER FOR MVEBU (Marvell Armada 370 and Armada XP SOC support)
|
||||
M: Thomas Petazzoni <thomas.petazzoni@free-electrons.com>
|
||||
M: Jason Cooper <jason@lakedaemon.net>
|
||||
L: linux-pci@vger.kernel.org
|
||||
L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
|
||||
S: Maintained
|
||||
F: drivers/pci/host/*mvebu*
|
||||
|
||||
PCI DRIVER FOR NVIDIA TEGRA
|
||||
M: Thierry Reding <thierry.reding@gmail.com>
|
||||
L: linux-tegra@vger.kernel.org
|
||||
L: linux-pci@vger.kernel.org
|
||||
S: Supported
|
||||
F: Documentation/devicetree/bindings/pci/nvidia,tegra20-pcie.txt
|
||||
F: drivers/pci/host/pci-tegra.c
|
||||
|
||||
PCI DRIVER FOR RENESAS R-CAR
|
||||
M: Simon Horman <horms@verge.net.au>
|
||||
L: linux-pci@vger.kernel.org
|
||||
L: linux-sh@vger.kernel.org
|
||||
S: Maintained
|
||||
F: drivers/pci/host/*rcar*
|
||||
|
||||
PCI DRIVER FOR SAMSUNG EXYNOS
|
||||
M: Jingoo Han <jg1.han@samsung.com>
|
||||
L: linux-pci@vger.kernel.org
|
||||
L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
|
||||
L: linux-samsung-soc@vger.kernel.org (moderated for non-subscribers)
|
||||
S: Maintained
|
||||
F: drivers/pci/host/pci-exynos.c
|
||||
|
||||
PCI DRIVER FOR SYNOPSIS DESIGNWARE
|
||||
M: Mohit Kumar <mohit.kumar@st.com>
|
||||
M: Jingoo Han <jg1.han@samsung.com>
|
||||
L: linux-pci@vger.kernel.org
|
||||
S: Maintained
|
||||
F: drivers/pci/host/*designware*
|
||||
|
||||
PCMCIA SUBSYSTEM
|
||||
P: Linux PCMCIA Team
|
||||
L: linux-pcmcia@lists.infradead.org
|
||||
|
|
|
@ -447,6 +447,11 @@ static int mvebu_sw_pci_bridge_read(struct mvebu_pcie_port *port,
|
|||
*value = 0;
|
||||
break;
|
||||
|
||||
case PCI_INTERRUPT_LINE:
|
||||
/* LINE PIN MIN_GNT MAX_LAT */
|
||||
*value = 0;
|
||||
break;
|
||||
|
||||
default:
|
||||
*value = 0xffffffff;
|
||||
return PCIBIOS_BAD_REGISTER_NUMBER;
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
#include <linux/cpu.h>
|
||||
#include <linux/pm_runtime.h>
|
||||
#include <linux/suspend.h>
|
||||
#include <linux/kexec.h>
|
||||
#include "pci.h"
|
||||
|
||||
struct pci_dynid {
|
||||
|
@ -288,12 +289,27 @@ static int pci_call_probe(struct pci_driver *drv, struct pci_dev *dev,
|
|||
int error, node;
|
||||
struct drv_dev_and_id ddi = { drv, dev, id };
|
||||
|
||||
/* Execute driver initialization on node where the device's
|
||||
bus is attached to. This way the driver likely allocates
|
||||
its local memory on the right node without any need to
|
||||
change it. */
|
||||
/*
|
||||
* Execute driver initialization on node where the device is
|
||||
* attached. This way the driver likely allocates its local memory
|
||||
* on the right node.
|
||||
*/
|
||||
node = dev_to_node(&dev->dev);
|
||||
if (node >= 0) {
|
||||
|
||||
/*
|
||||
* On NUMA systems, we are likely to call a PF probe function using
|
||||
* work_on_cpu(). If that probe calls pci_enable_sriov() (which
|
||||
* adds the VF devices via pci_bus_add_device()), we may re-enter
|
||||
* this function to call the VF probe function. Calling
|
||||
* work_on_cpu() again will cause a lockdep warning. Since VFs are
|
||||
* always on the same node as the PF, we can work around this by
|
||||
* avoiding work_on_cpu() when we're already on the correct node.
|
||||
*
|
||||
* Preemption is enabled, so it's theoretically unsafe to use
|
||||
* numa_node_id(), but even if we run the probe function on the
|
||||
* wrong node, it should be functionally correct.
|
||||
*/
|
||||
if (node >= 0 && node != numa_node_id()) {
|
||||
int cpu;
|
||||
|
||||
get_online_cpus();
|
||||
|
@ -305,6 +321,7 @@ static int pci_call_probe(struct pci_driver *drv, struct pci_dev *dev,
|
|||
put_online_cpus();
|
||||
} else
|
||||
error = local_pci_probe(&ddi);
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
|
@ -399,12 +416,17 @@ static void pci_device_shutdown(struct device *dev)
|
|||
pci_msi_shutdown(pci_dev);
|
||||
pci_msix_shutdown(pci_dev);
|
||||
|
||||
#ifdef CONFIG_KEXEC
|
||||
/*
|
||||
* Turn off Bus Master bit on the device to tell it to not
|
||||
* continue to do DMA. Don't touch devices in D3cold or unknown states.
|
||||
* If this is a kexec reboot, turn off Bus Master bit on the
|
||||
* device to tell it to not continue to do DMA. Don't touch
|
||||
* devices in D3cold or unknown states.
|
||||
* If it is not a kexec reboot, firmware will hit the PCI
|
||||
* devices with big hammer and stop their DMA any way.
|
||||
*/
|
||||
if (pci_dev->current_state <= PCI_D3hot)
|
||||
if (kexec_in_progress && (pci_dev->current_state <= PCI_D3hot))
|
||||
pci_clear_master(pci_dev);
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef CONFIG_PM
|
||||
|
|
|
@ -24,7 +24,7 @@ static void pci_stop_dev(struct pci_dev *dev)
|
|||
if (dev->is_added) {
|
||||
pci_proc_detach_device(dev);
|
||||
pci_remove_sysfs_dev_files(dev);
|
||||
device_del(&dev->dev);
|
||||
device_release_driver(&dev->dev);
|
||||
dev->is_added = 0;
|
||||
}
|
||||
|
||||
|
@ -34,6 +34,8 @@ static void pci_stop_dev(struct pci_dev *dev)
|
|||
|
||||
static void pci_destroy_dev(struct pci_dev *dev)
|
||||
{
|
||||
device_del(&dev->dev);
|
||||
|
||||
down_write(&pci_bus_sem);
|
||||
list_del(&dev->bus_list);
|
||||
up_write(&pci_bus_sem);
|
||||
|
|
|
@ -198,6 +198,9 @@ extern u32 vmcoreinfo_note[VMCOREINFO_NOTE_SIZE/4];
|
|||
extern size_t vmcoreinfo_size;
|
||||
extern size_t vmcoreinfo_max_size;
|
||||
|
||||
/* flag to track if kexec reboot is in progress */
|
||||
extern bool kexec_in_progress;
|
||||
|
||||
int __init parse_crashkernel(char *cmdline, unsigned long long system_ram,
|
||||
unsigned long long *crash_size, unsigned long long *crash_base);
|
||||
int parse_crashkernel_high(char *cmdline, unsigned long long system_ram,
|
||||
|
|
|
@ -1567,65 +1567,65 @@ enum pci_fixup_pass {
|
|||
/* Anonymous variables would be nice... */
|
||||
#define DECLARE_PCI_FIXUP_SECTION(section, name, vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
static const struct pci_fixup __pci_fixup_##name __used \
|
||||
static const struct pci_fixup __PASTE(__pci_fixup_##name,__LINE__) __used \
|
||||
__attribute__((__section__(#section), aligned((sizeof(void *))))) \
|
||||
= { vendor, device, class, class_shift, hook };
|
||||
|
||||
#define DECLARE_PCI_FIXUP_CLASS_EARLY(vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_early, \
|
||||
vendor##device##hook, vendor, device, class, class_shift, hook)
|
||||
hook, vendor, device, class, class_shift, hook)
|
||||
#define DECLARE_PCI_FIXUP_CLASS_HEADER(vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_header, \
|
||||
vendor##device##hook, vendor, device, class, class_shift, hook)
|
||||
hook, vendor, device, class, class_shift, hook)
|
||||
#define DECLARE_PCI_FIXUP_CLASS_FINAL(vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_final, \
|
||||
vendor##device##hook, vendor, device, class, class_shift, hook)
|
||||
hook, vendor, device, class, class_shift, hook)
|
||||
#define DECLARE_PCI_FIXUP_CLASS_ENABLE(vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_enable, \
|
||||
vendor##device##hook, vendor, device, class, class_shift, hook)
|
||||
hook, vendor, device, class, class_shift, hook)
|
||||
#define DECLARE_PCI_FIXUP_CLASS_RESUME(vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_resume, \
|
||||
resume##vendor##device##hook, vendor, device, class, \
|
||||
resume##hook, vendor, device, class, \
|
||||
class_shift, hook)
|
||||
#define DECLARE_PCI_FIXUP_CLASS_RESUME_EARLY(vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_resume_early, \
|
||||
resume_early##vendor##device##hook, vendor, device, \
|
||||
resume_early##hook, vendor, device, \
|
||||
class, class_shift, hook)
|
||||
#define DECLARE_PCI_FIXUP_CLASS_SUSPEND(vendor, device, class, \
|
||||
class_shift, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_suspend, \
|
||||
suspend##vendor##device##hook, vendor, device, class, \
|
||||
suspend##hook, vendor, device, class, \
|
||||
class_shift, hook)
|
||||
|
||||
#define DECLARE_PCI_FIXUP_EARLY(vendor, device, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_early, \
|
||||
vendor##device##hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
#define DECLARE_PCI_FIXUP_HEADER(vendor, device, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_header, \
|
||||
vendor##device##hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
#define DECLARE_PCI_FIXUP_FINAL(vendor, device, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_final, \
|
||||
vendor##device##hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
#define DECLARE_PCI_FIXUP_ENABLE(vendor, device, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_enable, \
|
||||
vendor##device##hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
hook, vendor, device, PCI_ANY_ID, 0, hook)
|
||||
#define DECLARE_PCI_FIXUP_RESUME(vendor, device, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_resume, \
|
||||
resume##vendor##device##hook, vendor, device, \
|
||||
resume##hook, vendor, device, \
|
||||
PCI_ANY_ID, 0, hook)
|
||||
#define DECLARE_PCI_FIXUP_RESUME_EARLY(vendor, device, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_resume_early, \
|
||||
resume_early##vendor##device##hook, vendor, device, \
|
||||
resume_early##hook, vendor, device, \
|
||||
PCI_ANY_ID, 0, hook)
|
||||
#define DECLARE_PCI_FIXUP_SUSPEND(vendor, device, hook) \
|
||||
DECLARE_PCI_FIXUP_SECTION(.pci_fixup_suspend, \
|
||||
suspend##vendor##device##hook, vendor, device, \
|
||||
suspend##hook, vendor, device, \
|
||||
PCI_ANY_ID, 0, hook)
|
||||
|
||||
#ifdef CONFIG_PCI_QUIRKS
|
||||
|
|
|
@ -47,6 +47,9 @@ u32 vmcoreinfo_note[VMCOREINFO_NOTE_SIZE/4];
|
|||
size_t vmcoreinfo_size;
|
||||
size_t vmcoreinfo_max_size = sizeof(vmcoreinfo_data);
|
||||
|
||||
/* Flag to indicate we are going to kexec a new kernel */
|
||||
bool kexec_in_progress = false;
|
||||
|
||||
/* Location of the reserved area for the crash kernel */
|
||||
struct resource crashk_res = {
|
||||
.name = "Crash kernel",
|
||||
|
@ -1675,6 +1678,7 @@ int kernel_kexec(void)
|
|||
} else
|
||||
#endif
|
||||
{
|
||||
kexec_in_progress = true;
|
||||
kernel_restart_prepare(NULL);
|
||||
printk(KERN_EMERG "Starting new kernel\n");
|
||||
machine_shutdown();
|
||||
|
|
|
@ -2851,19 +2851,6 @@ already_gone:
|
|||
return false;
|
||||
}
|
||||
|
||||
static bool __flush_work(struct work_struct *work)
|
||||
{
|
||||
struct wq_barrier barr;
|
||||
|
||||
if (start_flush_work(work, &barr)) {
|
||||
wait_for_completion(&barr.done);
|
||||
destroy_work_on_stack(&barr.work);
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* flush_work - wait for a work to finish executing the last queueing instance
|
||||
* @work: the work to flush
|
||||
|
@ -2877,10 +2864,18 @@ static bool __flush_work(struct work_struct *work)
|
|||
*/
|
||||
bool flush_work(struct work_struct *work)
|
||||
{
|
||||
struct wq_barrier barr;
|
||||
|
||||
lock_map_acquire(&work->lockdep_map);
|
||||
lock_map_release(&work->lockdep_map);
|
||||
|
||||
return __flush_work(work);
|
||||
if (start_flush_work(work, &barr)) {
|
||||
wait_for_completion(&barr.done);
|
||||
destroy_work_on_stack(&barr.work);
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(flush_work);
|
||||
|
||||
|
@ -4832,14 +4827,7 @@ long work_on_cpu(int cpu, long (*fn)(void *), void *arg)
|
|||
|
||||
INIT_WORK_ONSTACK(&wfc.work, work_for_cpu_fn);
|
||||
schedule_work_on(cpu, &wfc.work);
|
||||
|
||||
/*
|
||||
* The work item is on-stack and can't lead to deadlock through
|
||||
* flushing. Use __flush_work() to avoid spurious lockdep warnings
|
||||
* when work_on_cpu()s are nested.
|
||||
*/
|
||||
__flush_work(&wfc.work);
|
||||
|
||||
flush_work(&wfc.work);
|
||||
return wfc.ret;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(work_on_cpu);
|
||||
|
|
Loading…
Reference in New Issue