mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-10-29 23:53:32 +00:00
soc: ti: k3-ringacc: Use correct device for allocation in RING mode
In RING mode the ringacc does not access the ring memory. In this access mode the ringacc coherency does not have meaning. If the ring is configured in RING mode, then the ringacc itself will not access to the ring memory. Only the requester (user) of the ring is going to read/write to the memory. Extend the ring configuration parameters with a device pointer to be used for DMA API when the ring is configured in RING mode. Extending the ring configuration struct will allow per ring selection of device to be used for allocation, thus allowing per ring coherency. To avoid regression, fall back to use the ringacc dev in case the alloc_dev is not provided. Signed-off-by: Peter Ujfalusi <peter.ujfalusi@ti.com> Reviewed-by: Grygorii Strashko <grygorii.strashko@ti.com> Signed-off-by: Santosh Shilimkar <santosh.shilimkar@oracle.com>
This commit is contained in:
parent
fed7552f1e
commit
8c42379e40
2 changed files with 18 additions and 5 deletions
|
@ -141,6 +141,7 @@ struct k3_ring_state {
|
||||||
* @parent: Pointer on struct @k3_ringacc
|
* @parent: Pointer on struct @k3_ringacc
|
||||||
* @use_count: Use count for shared rings
|
* @use_count: Use count for shared rings
|
||||||
* @proxy_id: RA Ring Proxy Id (only if @K3_RINGACC_RING_USE_PROXY)
|
* @proxy_id: RA Ring Proxy Id (only if @K3_RINGACC_RING_USE_PROXY)
|
||||||
|
* @dma_dev: device to be used for DMA API (allocation, mapping)
|
||||||
*/
|
*/
|
||||||
struct k3_ring {
|
struct k3_ring {
|
||||||
struct k3_ring_rt_regs __iomem *rt;
|
struct k3_ring_rt_regs __iomem *rt;
|
||||||
|
@ -160,6 +161,7 @@ struct k3_ring {
|
||||||
struct k3_ringacc *parent;
|
struct k3_ringacc *parent;
|
||||||
u32 use_count;
|
u32 use_count;
|
||||||
int proxy_id;
|
int proxy_id;
|
||||||
|
struct device *dma_dev;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct k3_ringacc_ops {
|
struct k3_ringacc_ops {
|
||||||
|
@ -508,11 +510,12 @@ int k3_ringacc_ring_free(struct k3_ring *ring)
|
||||||
|
|
||||||
k3_ringacc_ring_free_sci(ring);
|
k3_ringacc_ring_free_sci(ring);
|
||||||
|
|
||||||
dma_free_coherent(ringacc->dev,
|
dma_free_coherent(ring->dma_dev,
|
||||||
ring->size * (4 << ring->elm_size),
|
ring->size * (4 << ring->elm_size),
|
||||||
ring->ring_mem_virt, ring->ring_mem_dma);
|
ring->ring_mem_virt, ring->ring_mem_dma);
|
||||||
ring->flags = 0;
|
ring->flags = 0;
|
||||||
ring->ops = NULL;
|
ring->ops = NULL;
|
||||||
|
ring->dma_dev = NULL;
|
||||||
if (ring->proxy_id != K3_RINGACC_PROXY_NOT_USED) {
|
if (ring->proxy_id != K3_RINGACC_PROXY_NOT_USED) {
|
||||||
clear_bit(ring->proxy_id, ringacc->proxy_inuse);
|
clear_bit(ring->proxy_id, ringacc->proxy_inuse);
|
||||||
ring->proxy = NULL;
|
ring->proxy = NULL;
|
||||||
|
@ -633,8 +636,12 @@ int k3_ringacc_ring_cfg(struct k3_ring *ring, struct k3_ring_cfg *cfg)
|
||||||
switch (ring->mode) {
|
switch (ring->mode) {
|
||||||
case K3_RINGACC_RING_MODE_RING:
|
case K3_RINGACC_RING_MODE_RING:
|
||||||
ring->ops = &k3_ring_mode_ring_ops;
|
ring->ops = &k3_ring_mode_ring_ops;
|
||||||
|
ring->dma_dev = cfg->dma_dev;
|
||||||
|
if (!ring->dma_dev)
|
||||||
|
ring->dma_dev = ringacc->dev;
|
||||||
break;
|
break;
|
||||||
case K3_RINGACC_RING_MODE_MESSAGE:
|
case K3_RINGACC_RING_MODE_MESSAGE:
|
||||||
|
ring->dma_dev = ringacc->dev;
|
||||||
if (ring->proxy)
|
if (ring->proxy)
|
||||||
ring->ops = &k3_ring_mode_proxy_ops;
|
ring->ops = &k3_ring_mode_proxy_ops;
|
||||||
else
|
else
|
||||||
|
@ -646,9 +653,9 @@ int k3_ringacc_ring_cfg(struct k3_ring *ring, struct k3_ring_cfg *cfg)
|
||||||
goto err_free_proxy;
|
goto err_free_proxy;
|
||||||
}
|
}
|
||||||
|
|
||||||
ring->ring_mem_virt = dma_alloc_coherent(ringacc->dev,
|
ring->ring_mem_virt = dma_alloc_coherent(ring->dma_dev,
|
||||||
ring->size * (4 << ring->elm_size),
|
ring->size * (4 << ring->elm_size),
|
||||||
&ring->ring_mem_dma, GFP_KERNEL);
|
&ring->ring_mem_dma, GFP_KERNEL);
|
||||||
if (!ring->ring_mem_virt) {
|
if (!ring->ring_mem_virt) {
|
||||||
dev_err(ringacc->dev, "Failed to alloc ring mem\n");
|
dev_err(ringacc->dev, "Failed to alloc ring mem\n");
|
||||||
ret = -ENOMEM;
|
ret = -ENOMEM;
|
||||||
|
@ -669,12 +676,13 @@ int k3_ringacc_ring_cfg(struct k3_ring *ring, struct k3_ring_cfg *cfg)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
err_free_mem:
|
err_free_mem:
|
||||||
dma_free_coherent(ringacc->dev,
|
dma_free_coherent(ring->dma_dev,
|
||||||
ring->size * (4 << ring->elm_size),
|
ring->size * (4 << ring->elm_size),
|
||||||
ring->ring_mem_virt,
|
ring->ring_mem_virt,
|
||||||
ring->ring_mem_dma);
|
ring->ring_mem_dma);
|
||||||
err_free_ops:
|
err_free_ops:
|
||||||
ring->ops = NULL;
|
ring->ops = NULL;
|
||||||
|
ring->dma_dev = NULL;
|
||||||
err_free_proxy:
|
err_free_proxy:
|
||||||
ring->proxy = NULL;
|
ring->proxy = NULL;
|
||||||
return ret;
|
return ret;
|
||||||
|
|
|
@ -67,6 +67,9 @@ struct k3_ring;
|
||||||
* few times. It's usable when the same ring is used as Free Host PD ring
|
* few times. It's usable when the same ring is used as Free Host PD ring
|
||||||
* for different flows, for example.
|
* for different flows, for example.
|
||||||
* Note: Locking should be done by consumer if required
|
* Note: Locking should be done by consumer if required
|
||||||
|
* @dma_dev: Master device which is using and accessing to the ring
|
||||||
|
* memory when the mode is K3_RINGACC_RING_MODE_RING. Memory allocations
|
||||||
|
* should be done using this device.
|
||||||
*/
|
*/
|
||||||
struct k3_ring_cfg {
|
struct k3_ring_cfg {
|
||||||
u32 size;
|
u32 size;
|
||||||
|
@ -74,6 +77,8 @@ struct k3_ring_cfg {
|
||||||
enum k3_ring_mode mode;
|
enum k3_ring_mode mode;
|
||||||
#define K3_RINGACC_RING_SHARED BIT(1)
|
#define K3_RINGACC_RING_SHARED BIT(1)
|
||||||
u32 flags;
|
u32 flags;
|
||||||
|
|
||||||
|
struct device *dma_dev;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define K3_RINGACC_RING_ID_ANY (-1)
|
#define K3_RINGACC_RING_ID_ANY (-1)
|
||||||
|
|
Loading…
Reference in a new issue