mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-12-04 01:24:12 +08:00
6daa90439e
New drivers/devices - Qualcomm ADM driver - Qualcomm GPI driver - Allwinner A100 DMA support - Microchip Sama7g5 support - Mediatek MT8516 apdma - Updates: - more updates to idxd driver and support for IAX config - runtime PM support for dw driver - TI keystone drivers for 5.11 included here due to dependency for TI drivers -----BEGIN PGP SIGNATURE----- iQIzBAABCAAdFiEE+vs47OPLdNbVcHzyfBQHDyUjg0cFAl/bkxEACgkQfBQHDyUj g0dxNA//WzpVy9QJnj6OgXIjM+9sBjqls0iPVfy1JeeMmVW8cgCwLyBNZcssKRye mJ9+VnTx4JQBj4KD2cFBdpr46GvBFbSbcWNSCdm179NtHI4G6tjtynOcWaI9Clu2 0KHoa/EHIj8/jD3Hsbm+WZ1zCoY4VKBXsEq6x1Sj2tpp0/ocDhH4XLAsWTHE9OAD sc+0OtHr1wU4EdV6TKNTT0jXsdtzxOPPsvRsoaKncnR+Mkrgv0FvMBfBLhOb3a+m wUHEkwrEP1pT4Xcew6ZkYs4RYwJI3pllu2gUTs5qtidc723ol/C4kJ27q55N4azb j5buA8AhEwqIDH8qNuV07qaIu2VTdTdbYid3xgAeFygwM1npecZvOf8k6rTjxR/6 XN8jaDuhc2uISY7Gt5c6tOe8rG3ffNhYrmEuGD5HI0hcglpALiE4NcgalaaQS9J1 suQ6AUtCslReD+6M/lfarn9Zd3UAKGbxU8vCNPq0EcSAGUz9u9VK2VwKiGnAZ8bb ED3QDUzZYjTDWpiVodsuJlONgaMLsRCQecZWMDRNpzmf1rCXnkY0eDGiSMz+IiXZ 87IdD66u3d/Mkm6jVdwp6+tKZ/ohj+dtIWKhMd8cKXv5zTzS+4IokxpkxdjBsHPx z+G73IMHjQo8xl/P0IhhwZw+7cBrkntLq8lRSbYxjSTP09QerNE= =uNBn -----END PGP SIGNATURE----- Merge tag 'dmaengine-5.11-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/dmaengine Pull dmaengine updates from Vinod Koul: "The last dmaengine updates for this year :) This contains couple of new drivers, new device support and updates to bunch of drivers. New drivers/devices: - Qualcomm ADM driver - Qualcomm GPI driver - Allwinner A100 DMA support - Microchip Sama7g5 support - Mediatek MT8516 apdma Updates: - more updates to idxd driver and support for IAX config - runtime PM support for dw driver - TI drivers" * tag 'dmaengine-5.11-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/dmaengine: (75 commits) soc: ti: k3-ringacc: Use correct error casting in k3_ringacc_dmarings_init dmaengine: ti: k3-udma-glue: Add support for K3 PKTDMA dmaengine: ti: k3-udma: Initial support for K3 PKTDMA dmaengine: ti: k3-udma: Add support for BCDMA channel TPL handling dmaengine: ti: k3-udma: Initial support for K3 BCDMA soc: ti: k3-ringacc: add AM64 DMA rings support. dmaengine: ti: Add support for k3 event routers dmaengine: ti: k3-psil: Add initial map for AM64 dmaengine: ti: k3-psil: Extend psil_endpoint_config for K3 PKTDMA dt-bindings: dma: ti: Add document for K3 PKTDMA dt-bindings: dma: ti: Add document for K3 BCDMA dmaengine: dmatest: Use dmaengine_get_dma_device dmaengine: doc: client: Update for dmaengine_get_dma_device() usage dmaengine: Add support for per channel coherency handling dmaengine: of-dma: Add support for optional router configuration callback dmaengine: ti: k3-udma-glue: Configure the dma_dev for rings dmaengine: ti: k3-udma-glue: Get the ringacc from udma_dev dmaengine: ti: k3-udma-glue: Add function to get device pointer for DMA API dmaengine: ti: k3-udma: Add support for second resource range from sysfw dmaengine: ti: k3-udma: Wait for peer teardown completion if supported ...
121 lines
2.8 KiB
C
121 lines
2.8 KiB
C
// SPDX-License-Identifier: GPL-2.0
|
|
/* Copyright(c) 2019 Intel Corporation. All rights rsvd. */
|
|
#include <linux/init.h>
|
|
#include <linux/kernel.h>
|
|
#include <linux/module.h>
|
|
#include <linux/pci.h>
|
|
#include <uapi/linux/idxd.h>
|
|
#include "idxd.h"
|
|
#include "registers.h"
|
|
|
|
static struct idxd_desc *__get_desc(struct idxd_wq *wq, int idx, int cpu)
|
|
{
|
|
struct idxd_desc *desc;
|
|
struct idxd_device *idxd = wq->idxd;
|
|
|
|
desc = wq->descs[idx];
|
|
memset(desc->hw, 0, sizeof(struct dsa_hw_desc));
|
|
memset(desc->completion, 0, idxd->compl_size);
|
|
desc->cpu = cpu;
|
|
|
|
if (device_pasid_enabled(idxd))
|
|
desc->hw->pasid = idxd->pasid;
|
|
|
|
/*
|
|
* Descriptor completion vectors are 1-8 for MSIX. We will round
|
|
* robin through the 8 vectors.
|
|
*/
|
|
wq->vec_ptr = (wq->vec_ptr % idxd->num_wq_irqs) + 1;
|
|
desc->hw->int_handle = wq->vec_ptr;
|
|
return desc;
|
|
}
|
|
|
|
struct idxd_desc *idxd_alloc_desc(struct idxd_wq *wq, enum idxd_op_type optype)
|
|
{
|
|
int cpu, idx;
|
|
struct idxd_device *idxd = wq->idxd;
|
|
DEFINE_SBQ_WAIT(wait);
|
|
struct sbq_wait_state *ws;
|
|
struct sbitmap_queue *sbq;
|
|
|
|
if (idxd->state != IDXD_DEV_ENABLED)
|
|
return ERR_PTR(-EIO);
|
|
|
|
sbq = &wq->sbq;
|
|
idx = sbitmap_queue_get(sbq, &cpu);
|
|
if (idx < 0) {
|
|
if (optype == IDXD_OP_NONBLOCK)
|
|
return ERR_PTR(-EAGAIN);
|
|
} else {
|
|
return __get_desc(wq, idx, cpu);
|
|
}
|
|
|
|
ws = &sbq->ws[0];
|
|
for (;;) {
|
|
sbitmap_prepare_to_wait(sbq, ws, &wait, TASK_INTERRUPTIBLE);
|
|
if (signal_pending_state(TASK_INTERRUPTIBLE, current))
|
|
break;
|
|
idx = sbitmap_queue_get(sbq, &cpu);
|
|
if (idx > 0)
|
|
break;
|
|
schedule();
|
|
}
|
|
|
|
sbitmap_finish_wait(sbq, ws, &wait);
|
|
if (idx < 0)
|
|
return ERR_PTR(-EAGAIN);
|
|
|
|
return __get_desc(wq, idx, cpu);
|
|
}
|
|
|
|
void idxd_free_desc(struct idxd_wq *wq, struct idxd_desc *desc)
|
|
{
|
|
int cpu = desc->cpu;
|
|
|
|
desc->cpu = -1;
|
|
sbitmap_queue_clear(&wq->sbq, desc->id, cpu);
|
|
}
|
|
|
|
int idxd_submit_desc(struct idxd_wq *wq, struct idxd_desc *desc)
|
|
{
|
|
struct idxd_device *idxd = wq->idxd;
|
|
int vec = desc->hw->int_handle;
|
|
void __iomem *portal;
|
|
int rc;
|
|
|
|
if (idxd->state != IDXD_DEV_ENABLED)
|
|
return -EIO;
|
|
|
|
portal = wq->portal;
|
|
|
|
/*
|
|
* The wmb() flushes writes to coherent DMA data before
|
|
* possibly triggering a DMA read. The wmb() is necessary
|
|
* even on UP because the recipient is a device.
|
|
*/
|
|
wmb();
|
|
if (wq_dedicated(wq)) {
|
|
iosubmit_cmds512(portal, desc->hw, 1);
|
|
} else {
|
|
/*
|
|
* It's not likely that we would receive queue full rejection
|
|
* since the descriptor allocation gates at wq size. If we
|
|
* receive a -EAGAIN, that means something went wrong such as the
|
|
* device is not accepting descriptor at all.
|
|
*/
|
|
rc = enqcmds(portal, desc->hw);
|
|
if (rc < 0)
|
|
return rc;
|
|
}
|
|
|
|
/*
|
|
* Pending the descriptor to the lockless list for the irq_entry
|
|
* that we designated the descriptor to.
|
|
*/
|
|
if (desc->hw->flags & IDXD_OP_FLAG_RCI)
|
|
llist_add(&desc->llnode,
|
|
&idxd->irq_entries[vec].pending_llist);
|
|
|
|
return 0;
|
|
}
|