linux 5.17.12内核nvme驱动中,这么怎么修改pci_alloc_irq_vectors_affinity函数的参数,能将所有的io队列的亲和性绑定到同一个cpu核心上?代码展示
时间: 2024-03-17 15:39:57 浏览: 15
在 Linux 5.17.12 内核版本中,可以通过修改 `pci_alloc_irq_vectors_affinity()` 函数的 `affinity_hint` 参数来绑定 NVMe 驱动的所有 I/O 队列到同一 CPU 核心上。
以下是示例代码:
```c
static int nvme_setup_io_queues(struct nvme_dev *dev)
{
int err, qid;
cpumask_var_t mask;
// 分配 CPU 核心亲和性掩码
mask = alloc_cpumask_var(GFP_KERNEL);
if (!mask)
return -ENOMEM;
// 将所有 CPU 核心添加到掩码中
cpumask_setall(mask);
// 为每个 I/O 队列分配中断向量
for (qid = 0; qid < dev->ctrl.queue_count; qid++) {
struct nvme_queue *nvmeq = &dev->queues[qid];
struct nvme_q_vector *q = &dev->q_vectors[qid];
struct pci_dev *pdev = to_pci_dev(dev->dev);
irqreturn_t (*irq_fn)(int, void *);
// 设置中断处理函数
irq_fn = nvme_irq;
// 分配中断向量
err = pci_alloc_irq_vectors_affinity(pdev, 1, 1, PCI_IRQ_MSIX,
q->num_vecs, mask,
&q->affinity_hint);
if (err < 0) {
dev_err(dev->ctrl.device, "Failed to allocate IRQ vectors\n");
goto err_irq_vectors;
}
// 绑定 I/O 队列和中断向量
nvmeq->cq_vector = q->cq_vector = q->affinity_hint;
nvmeq->sq_vector = q->sq_vector = q->affinity_hint;
err = request_irq(pci_irq_vector(pdev, q->affinity_hint), irq_fn,
IRQF_SHARED, dev_name(dev->dev), nvmeq);
if (err < 0) {
dev_err(dev->ctrl.device, "Failed to request IRQ %d\n",
pci_irq_vector(pdev, q->affinity_hint));
goto err_request_irq;
}
}
free_cpumask_var(mask);
return 0;
err_request_irq:
for (; qid >= 0; qid--) {
struct nvme_q_vector *q = &dev->q_vectors[qid];
struct pci_dev *pdev = to_pci_dev(dev->dev);
free_irq(pci_irq_vector(pdev, q->affinity_hint), &dev->queues[qid]);
}
err_irq_vectors:
for (; qid >= 0; qid--) {
struct nvme_q_vector *q = &dev->q_vectors[qid];
struct pci_dev *pdev = to_pci_dev(dev->dev);
if (q->affinity_hint >= 0)
pci_free_irq_vectors(pdev);
}
free_cpumask_var(mask);
return err;
}
```
在此示例代码中,我们使用 `alloc_cpumask_var()` 函数来分配一个 CPU 核心亲和性掩码,然后使用 `cpumask_setall()` 函数将所有 CPU 核心添加到掩码中。接下来,我们使用 `pci_alloc_irq_vectors_affinity()` 函数为每个 I/O 队列分配中断向量,并将 `affinity_hint` 参数设置为掩码,以绑定所有 I/O 队列到同一 CPU 核心。最后,我们使用 `request_irq()` 函数将每个 I/O 队列和中断向量绑定在一起,以便在中断处理程序中处理 I/O 完成事件。
请注意,NVMe 驱动的代码可能因版本而异,因此请根据您使用的内核版本和驱动版本进行适当的修改。