Commit 873392ca authored by Rusty Russell's avatar Rusty Russell Committed by Jesse Barnes

PCI: work_on_cpu: use in drivers/pci/pci-driver.c

This uses work_on_cpu(), rather than altering the cpumask of the
thread which we happen to be.

Note the cleanups:

1) I've removed the CONFIG_NUMA test, since dev_to_node() returns -1
   for !CONFIG_NUMA anyway and the compiler will eliminate it.

2) No need to reset mempolicy to default (a bad idea anyway) since
   work_on_cpu is run from a workqueue.
Signed-off-by: default avatarRusty Russell <rusty@rustcorp.com.au>
Signed-off-by: default avatarJesse Barnes <jbarnes@virtuousgeek.org>
parent a79d682f
...@@ -16,6 +16,7 @@ ...@@ -16,6 +16,7 @@
#include <linux/string.h> #include <linux/string.h>
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/sched.h> #include <linux/sched.h>
#include <linux/cpu.h>
#include "pci.h" #include "pci.h"
/* /*
...@@ -185,32 +186,43 @@ static const struct pci_device_id *pci_match_device(struct pci_driver *drv, ...@@ -185,32 +186,43 @@ static const struct pci_device_id *pci_match_device(struct pci_driver *drv,
return pci_match_id(drv->id_table, dev); return pci_match_id(drv->id_table, dev);
} }
struct drv_dev_and_id {
struct pci_driver *drv;
struct pci_dev *dev;
const struct pci_device_id *id;
};
static long local_pci_probe(void *_ddi)
{
struct drv_dev_and_id *ddi = _ddi;
return ddi->drv->probe(ddi->dev, ddi->id);
}
static int pci_call_probe(struct pci_driver *drv, struct pci_dev *dev, static int pci_call_probe(struct pci_driver *drv, struct pci_dev *dev,
const struct pci_device_id *id) const struct pci_device_id *id)
{ {
int error; int error, node;
#ifdef CONFIG_NUMA 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. */
struct mempolicy *oldpol;
cpumask_t oldmask = current->cpus_allowed;
int node = dev_to_node(&dev->dev);
/* 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. */
node = dev_to_node(&dev->dev);
if (node >= 0) { if (node >= 0) {
int cpu;
node_to_cpumask_ptr(nodecpumask, node); node_to_cpumask_ptr(nodecpumask, node);
set_cpus_allowed_ptr(current, nodecpumask);
} get_online_cpus();
/* And set default memory allocation policy */ cpu = cpumask_any_and(nodecpumask, cpu_online_mask);
oldpol = current->mempolicy; if (cpu < nr_cpu_ids)
current->mempolicy = NULL; /* fall back to system default policy */ error = work_on_cpu(cpu, local_pci_probe, &ddi);
#endif else
error = drv->probe(dev, id); error = local_pci_probe(&ddi);
#ifdef CONFIG_NUMA put_online_cpus();
set_cpus_allowed_ptr(current, &oldmask); } else
current->mempolicy = oldpol; error = local_pci_probe(&ddi);
#endif
return error; return error;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment