From 91f1e792fe085cd14919803b55983b8c760effb0 Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Mon, 10 May 2021 20:06:02 +0530 Subject: firmware: ti_sci: Update ti_sci_cmd_rm_udmap_tx_ch_cfg() API to the latest Update struct ti_sci_msg_rm_udmap_tx_ch_cfg_req to latest ABI to support AM64x BCDMA Block copy channels. Signed-off-by: Vignesh Raghavendra --- include/linux/soc/ti/ti_sci_protocol.h | 14 ++++++++++++++ 1 file changed, 14 insertions(+) (limited to 'include/linux/soc') diff --git a/include/linux/soc/ti/ti_sci_protocol.h b/include/linux/soc/ti/ti_sci_protocol.h index eb916ba1019..794737923cf 100644 --- a/include/linux/soc/ti/ti_sci_protocol.h +++ b/include/linux/soc/ti/ti_sci_protocol.h @@ -379,6 +379,13 @@ struct ti_sci_rm_psil_ops { #define TI_SCI_RM_UDMAP_RX_FLOW_DESC_HOST 0 #define TI_SCI_RM_UDMAP_RX_FLOW_DESC_MONO 2 +#define TI_SCI_RM_UDMAP_CHAN_BURST_SIZE_64_BYTES 1 +#define TI_SCI_RM_UDMAP_CHAN_BURST_SIZE_128_BYTES 2 +#define TI_SCI_RM_UDMAP_CHAN_BURST_SIZE_256_BYTES 3 + +#define TI_SCI_RM_BCDMA_EXTENDED_CH_TYPE_TCHAN 0 +#define TI_SCI_RM_BCDMA_EXTENDED_CH_TYPE_BCHAN 1 + /* UDMAP TX/RX channel valid_params common declarations */ #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_PAUSE_ON_ERR_VALID BIT(0) #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_ATYPE_VALID BIT(1) @@ -389,6 +396,7 @@ struct ti_sci_rm_psil_ops { #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_QOS_VALID BIT(6) #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_ORDER_ID_VALID BIT(7) #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_SCHED_PRIORITY_VALID BIT(8) +#define TI_SCI_MSG_VALUE_RM_UDMAP_CH_BURST_SIZE_VALID BIT(14) /** * Configures a Navigator Subsystem UDMAP transmit channel @@ -403,6 +411,8 @@ struct ti_sci_msg_rm_udmap_tx_ch_cfg { #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_TX_SUPR_TDPKT_VALID BIT(11) #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_TX_CREDIT_COUNT_VALID BIT(12) #define TI_SCI_MSG_VALUE_RM_UDMAP_CH_TX_FDEPTH_VALID BIT(13) +#define TI_SCI_MSG_VALUE_RM_UDMAP_CH_TX_TDTYPE_VALID BIT(15) +#define TI_SCI_MSG_VALUE_RM_UDMAP_CH_EXTENDED_CH_TYPE_VALID BIT(16) u16 nav_id; u16 index; u8 tx_pause_on_err; @@ -419,6 +429,9 @@ struct ti_sci_msg_rm_udmap_tx_ch_cfg { u8 tx_orderid; u16 fdepth; u8 tx_sched_priority; + u8 tx_burst_size; + u8 tx_tdtype; + u8 extended_ch_type; }; /** @@ -448,6 +461,7 @@ struct ti_sci_msg_rm_udmap_rx_ch_cfg { u8 rx_chan_type; u8 rx_ignore_short; u8 rx_ignore_long; + u8 rx_burst_size; }; /** -- cgit v1.3.1 From c409b4932dba6403a706f9453d627abfb5d93e20 Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Mon, 10 May 2021 20:06:03 +0530 Subject: soc: ti: k3-navss-ringacc: Add AM64 ringacc support AM64 dual mode rings are modeled as pair of Rings objects which has common configuration and memory buffer, but separate real-time control register sets for each direction mem2dev (forward) and dev2mem (reverse). AM64 rings must be requested only using k3_ringacc_request_rings_pair(), and forward ring must always be initialized/configured. After this any other Ringacc APIs can be used without any callers changes. Signed-off-by: Vignesh Raghavendra --- drivers/soc/ti/k3-navss-ringacc.c | 273 +++++++++++++++++++++++++++++++- include/linux/soc/ti/k3-navss-ringacc.h | 15 ++ 2 files changed, 283 insertions(+), 5 deletions(-) (limited to 'include/linux/soc') diff --git a/drivers/soc/ti/k3-navss-ringacc.c b/drivers/soc/ti/k3-navss-ringacc.c index c5099ad084d..10ef6be7205 100644 --- a/drivers/soc/ti/k3-navss-ringacc.c +++ b/drivers/soc/ti/k3-navss-ringacc.c @@ -23,6 +23,7 @@ #include #include #include +#include #define set_bit(bit, bitmap) __set_bit(bit, bitmap) #define clear_bit(bit, bitmap) __clear_bit(bit, bitmap) @@ -56,6 +57,7 @@ static u32 ringacc_readl(void __iomem *reg) } #define KNAV_RINGACC_CFG_RING_SIZE_ELCNT_MASK GENMASK(19, 0) +#define K3_DMARING_RING_CFG_RING_SIZE_ELCNT_MASK GENMASK(15, 0) /** * struct k3_nav_ring_rt_regs - The RA Control/Status Registers region @@ -71,6 +73,13 @@ struct k3_nav_ring_rt_regs { }; #define KNAV_RINGACC_RT_REGS_STEP 0x1000 +#define K3_DMARING_RING_RT_REGS_STEP 0x2000 +#define K3_DMARING_RING_RT_REGS_REVERSE_OFS 0x1000 +#define KNAV_RINGACC_RT_OCC_MASK GENMASK(20, 0) +#define K3_DMARING_RING_RT_OCC_TDOWN_COMPLETE BIT(31) +#define K3_DMARING_RING_RT_DB_ENTRY_MASK GENMASK(7, 0) +#define K3_DMARING_RING_RT_DB_TDOWN_ACK BIT(31) + /** * struct k3_nav_ring_fifo_regs - The Ring Accelerator Queues Registers region @@ -173,6 +182,7 @@ struct k3_nav_ring { u32 flags; #define KNAV_RING_FLAG_BUSY BIT(1) #define K3_NAV_RING_FLAG_SHARED BIT(2) +#define K3_NAV_RING_FLAG_REVERSE BIT(3) struct k3_nav_ring_state state; u32 ring_id; struct k3_nav_ringacc *parent; @@ -200,6 +210,7 @@ struct k3_nav_ringacc_ops { * @tisci_ring_ops - ti-sci rings ops * @tisci_dev_id - ti-sci device id * @ops: SoC specific ringacc operation + * @dual_ring: indicate k3_dmaring dual ring support */ struct k3_nav_ringacc { struct udevice *dev; @@ -220,8 +231,24 @@ struct k3_nav_ringacc { u32 tisci_dev_id; const struct k3_nav_ringacc_ops *ops; + bool dual_ring; }; +static int k3_nav_ringacc_ring_read_occ(struct k3_nav_ring *ring) +{ + return readl(&ring->rt->occ) & KNAV_RINGACC_RT_OCC_MASK; +} + +static void k3_nav_ringacc_ring_update_occ(struct k3_nav_ring *ring) +{ + u32 val; + + val = readl(&ring->rt->occ); + + ring->state.occ = val & KNAV_RINGACC_RT_OCC_MASK; + ring->state.tdown_complete = !!(val & K3_DMARING_RING_RT_OCC_TDOWN_COMPLETE); +} + static long k3_nav_ringacc_ring_get_fifo_pos(struct k3_nav_ring *ring) { return KNAV_RINGACC_FIFO_WINDOW_SIZE_BYTES - @@ -235,12 +262,23 @@ static void *k3_nav_ringacc_get_elm_addr(struct k3_nav_ring *ring, u32 idx) static int k3_nav_ringacc_ring_push_mem(struct k3_nav_ring *ring, void *elem); static int k3_nav_ringacc_ring_pop_mem(struct k3_nav_ring *ring, void *elem); +static int k3_dmaring_ring_fwd_pop_mem(struct k3_nav_ring *ring, void *elem); +static int k3_dmaring_ring_reverse_pop_mem(struct k3_nav_ring *ring, void *elem); static struct k3_nav_ring_ops k3_nav_mode_ring_ops = { .push_tail = k3_nav_ringacc_ring_push_mem, .pop_head = k3_nav_ringacc_ring_pop_mem, }; +static struct k3_nav_ring_ops k3_dmaring_fwd_ring_ops = { + .push_tail = k3_nav_ringacc_ring_push_mem, + .pop_head = k3_dmaring_ring_fwd_pop_mem, +}; + +static struct k3_nav_ring_ops k3_dmaring_reverse_ring_ops = { + .pop_head = k3_dmaring_ring_reverse_pop_mem, +}; + static int k3_nav_ringacc_ring_push_io(struct k3_nav_ring *ring, void *elem); static int k3_nav_ringacc_ring_pop_io(struct k3_nav_ring *ring, void *elem); static int k3_nav_ringacc_ring_push_head_io(struct k3_nav_ring *ring, @@ -328,6 +366,27 @@ error: return NULL; } +static int k3_dmaring_ring_request_rings_pair(struct k3_nav_ringacc *ringacc, + int fwd_id, int compl_id, + struct k3_nav_ring **fwd_ring, + struct k3_nav_ring **compl_ring) +{ + /* k3_dmaring: fwd_id == compl_id, so we ignore compl_id */ + if (fwd_id < 0) + return -EINVAL; + + if (test_bit(fwd_id, ringacc->rings_inuse)) + return -EBUSY; + + *fwd_ring = &ringacc->rings[fwd_id]; + *compl_ring = &ringacc->rings[fwd_id + ringacc->num_rings]; + set_bit(fwd_id, ringacc->rings_inuse); + ringacc->rings[fwd_id].use_count++; + dev_dbg(ringacc->dev, "Giving ring#%d\n", fwd_id); + + return 0; +} + int k3_nav_ringacc_request_rings_pair(struct k3_nav_ringacc *ringacc, int fwd_id, int compl_id, struct k3_nav_ring **fwd_ring, @@ -338,6 +397,10 @@ int k3_nav_ringacc_request_rings_pair(struct k3_nav_ringacc *ringacc, if (!fwd_ring || !compl_ring) return -EINVAL; + if (ringacc->dual_ring) + return k3_dmaring_ring_request_rings_pair(ringacc, fwd_id, compl_id, + fwd_ring, compl_ring); + *fwd_ring = k3_nav_ringacc_request_ring(ringacc, fwd_id, 0); if (!(*fwd_ring)) return -ENODEV; @@ -493,6 +556,13 @@ int k3_nav_ringacc_ring_free(struct k3_nav_ring *ring) ringacc = ring->parent; + /* + * k3_dmaring: rings shared memory and configuration, only forward ring is + * configured and reverse ring considered as slave. + */ + if (ringacc->dual_ring && (ring->flags & K3_NAV_RING_FLAG_REVERSE)) + return 0; + pr_debug("%s flags: 0x%08x\n", __func__, ring->flags); if (!test_bit(ring->ring_id, ringacc->rings_inuse)) @@ -562,6 +632,76 @@ static int k3_nav_ringacc_ring_cfg_sci(struct k3_nav_ring *ring) return ret; } +static int k3_dmaring_ring_cfg(struct k3_nav_ring *ring, struct k3_nav_ring_cfg *cfg) +{ + struct k3_nav_ringacc *ringacc; + struct k3_nav_ring *reverse_ring; + int ret = 0; + + if (cfg->elm_size != K3_NAV_RINGACC_RING_ELSIZE_8 || + cfg->mode != K3_NAV_RINGACC_RING_MODE_RING || + cfg->size & ~K3_DMARING_RING_CFG_RING_SIZE_ELCNT_MASK) + return -EINVAL; + + ringacc = ring->parent; + + /* + * k3_dmaring: rings shared memory and configuration, only forward ring is + * configured and reverse ring considered as slave. + */ + if (ringacc->dual_ring && (ring->flags & K3_NAV_RING_FLAG_REVERSE)) + return 0; + + if (!test_bit(ring->ring_id, ringacc->rings_inuse)) + return -EINVAL; + + ring->size = cfg->size; + ring->elm_size = cfg->elm_size; + ring->mode = cfg->mode; + memset(&ring->state, 0, sizeof(ring->state)); + + ring->ops = &k3_dmaring_fwd_ring_ops; + + ring->ring_mem_virt = + dma_alloc_coherent(ring->size * (4 << ring->elm_size), + (unsigned long *)&ring->ring_mem_dma); + if (!ring->ring_mem_virt) { + dev_err(ringacc->dev, "Failed to alloc ring mem\n"); + ret = -ENOMEM; + goto err_free_ops; + } + + ret = k3_nav_ringacc_ring_cfg_sci(ring); + if (ret) + goto err_free_mem; + + ring->flags |= KNAV_RING_FLAG_BUSY; + + /* k3_dmaring: configure reverse ring */ + reverse_ring = &ringacc->rings[ring->ring_id + ringacc->num_rings]; + reverse_ring->size = cfg->size; + reverse_ring->elm_size = cfg->elm_size; + reverse_ring->mode = cfg->mode; + memset(&reverse_ring->state, 0, sizeof(reverse_ring->state)); + reverse_ring->ops = &k3_dmaring_reverse_ring_ops; + + reverse_ring->ring_mem_virt = ring->ring_mem_virt; + reverse_ring->ring_mem_dma = ring->ring_mem_dma; + reverse_ring->flags |= KNAV_RING_FLAG_BUSY; + + return 0; + +err_free_mem: + dma_free_coherent(ringacc->dev, + ring->size * (4 << ring->elm_size), + ring->ring_mem_virt, + ring->ring_mem_dma); +err_free_ops: + ring->ops = NULL; + ring->proxy = NULL; + return ret; +} + int k3_nav_ringacc_ring_cfg(struct k3_nav_ring *ring, struct k3_nav_ring_cfg *cfg) { @@ -570,6 +710,10 @@ int k3_nav_ringacc_ring_cfg(struct k3_nav_ring *ring, if (!ring || !cfg) return -EINVAL; + + if (ringacc->dual_ring) + return k3_dmaring_ring_cfg(ring, cfg); + if (cfg->elm_size > K3_NAV_RINGACC_RING_ELSIZE_256 || cfg->mode > K3_NAV_RINGACC_RING_MODE_QM || cfg->size & ~KNAV_RINGACC_CFG_RING_SIZE_ELCNT_MASK || @@ -839,6 +983,63 @@ static int k3_nav_ringacc_ring_pop_tail_io(struct k3_nav_ring *ring, void *elem) ring, elem, K3_RINGACC_ACCESS_MODE_POP_HEAD); } +static int k3_dmaring_ring_fwd_pop_mem(struct k3_nav_ring *ring, void *elem) +{ + void *elem_ptr; + u32 elem_idx; + + /* + * k3_dmaring: forward ring is always tied DMA channel and HW does not + * maintain any state data required for POP operation and its unknown + * how much elements were consumed by HW. So, to actually + * do POP, the read pointer has to be recalculated every time. + */ + ring->state.occ = k3_nav_ringacc_ring_read_occ(ring); + if (ring->state.windex >= ring->state.occ) + elem_idx = ring->state.windex - ring->state.occ; + else + elem_idx = ring->size - (ring->state.occ - ring->state.windex); + + elem_ptr = k3_nav_ringacc_get_elm_addr(ring, elem_idx); + invalidate_dcache_range((unsigned long)ring->ring_mem_virt, + ALIGN((unsigned long)ring->ring_mem_virt + + ring->size * (4 << ring->elm_size), + ARCH_DMA_MINALIGN)); + + memcpy(elem, elem_ptr, (4 << ring->elm_size)); + + ring->state.occ--; + writel(-1, &ring->rt->db); + + dev_dbg(ring->parent->dev, "%s: occ%d Windex%d Rindex%d pos_ptr%px\n", + __func__, ring->state.occ, ring->state.windex, elem_idx, + elem_ptr); + return 0; +} + +static int k3_dmaring_ring_reverse_pop_mem(struct k3_nav_ring *ring, void *elem) +{ + void *elem_ptr; + + elem_ptr = k3_nav_ringacc_get_elm_addr(ring, ring->state.rindex); + + if (ring->state.occ) { + invalidate_dcache_range((unsigned long)ring->ring_mem_virt, + ALIGN((unsigned long)ring->ring_mem_virt + + ring->size * (4 << ring->elm_size), + ARCH_DMA_MINALIGN)); + + memcpy(elem, elem_ptr, (4 << ring->elm_size)); + ring->state.rindex = (ring->state.rindex + 1) % ring->size; + ring->state.occ--; + writel(-1 & K3_DMARING_RING_RT_DB_ENTRY_MASK, &ring->rt->db); + } + + dev_dbg(ring->parent->dev, "%s: occ%d index%d pos_ptr%px\n", + __func__, ring->state.occ, ring->state.rindex, elem_ptr); + return 0; +} + static int k3_nav_ringacc_ring_push_mem(struct k3_nav_ring *ring, void *elem) { void *elem_ptr; @@ -930,7 +1131,7 @@ int k3_nav_ringacc_ring_pop(struct k3_nav_ring *ring, void *elem) return -EINVAL; if (!ring->state.occ) - ring->state.occ = k3_nav_ringacc_ring_get_occ(ring); + k3_nav_ringacc_ring_update_occ(ring); pr_debug("ring_pop%d: occ%d index%d\n", ring->ring_id, ring->state.occ, ring->state.rindex); @@ -952,7 +1153,7 @@ int k3_nav_ringacc_ring_pop_tail(struct k3_nav_ring *ring, void *elem) return -EINVAL; if (!ring->state.occ) - ring->state.occ = k3_nav_ringacc_ring_get_occ(ring); + k3_nav_ringacc_ring_update_occ(ring); pr_debug("ring_pop_tail: occ%d index%d\n", ring->state.occ, ring->state.rindex); @@ -969,6 +1170,7 @@ int k3_nav_ringacc_ring_pop_tail(struct k3_nav_ring *ring, void *elem) static int k3_nav_ringacc_probe_dt(struct k3_nav_ringacc *ringacc) { struct udevice *dev = ringacc->dev; + struct udevice *devp = dev; struct udevice *tisci_dev = NULL; int ret; @@ -981,7 +1183,7 @@ static int k3_nav_ringacc_probe_dt(struct k3_nav_ringacc *ringacc) ringacc->dma_ring_reset_quirk = dev_read_bool(dev, "ti,dma-ring-reset-quirk"); - ret = uclass_get_device_by_phandle(UCLASS_FIRMWARE, dev, + ret = uclass_get_device_by_phandle(UCLASS_FIRMWARE, devp, "ti,sci", &tisci_dev); if (ret) { pr_debug("TISCI RA RM get failed (%d)\n", ret); @@ -991,14 +1193,14 @@ static int k3_nav_ringacc_probe_dt(struct k3_nav_ringacc *ringacc) ringacc->tisci = (struct ti_sci_handle *) (ti_sci_get_handle_from_sysfw(tisci_dev)); - ret = dev_read_u32_default(dev, "ti,sci", 0); + ret = dev_read_u32_default(devp, "ti,sci", 0); if (!ret) { dev_err(dev, "TISCI RA RM disabled\n"); ringacc->tisci = NULL; return ret; } - ret = dev_read_u32(dev, "ti,sci-dev-id", &ringacc->tisci_dev_id); + ret = dev_read_u32(devp, "ti,sci-dev-id", &ringacc->tisci_dev_id); if (ret) { dev_err(dev, "ti,sci-dev-id read failure %d\n", ret); ringacc->tisci = NULL; @@ -1089,6 +1291,67 @@ static int k3_nav_ringacc_init(struct udevice *dev, struct k3_nav_ringacc *ringa return 0; } +struct k3_nav_ringacc *k3_ringacc_dmarings_init(struct udevice *dev, + struct k3_ringacc_init_data *data) +{ + struct k3_nav_ringacc *ringacc; + void __iomem *base_rt; + int i; + + ringacc = devm_kzalloc(dev, sizeof(*ringacc), GFP_KERNEL); + if (!ringacc) + return ERR_PTR(-ENOMEM); + + ringacc->dual_ring = true; + + ringacc->dev = dev; + ringacc->num_rings = data->num_rings; + ringacc->tisci = data->tisci; + ringacc->tisci_dev_id = data->tisci_dev_id; + + base_rt = (uint32_t *)devfdt_get_addr_name(dev, "ringrt"); + if (IS_ERR(base_rt)) + return base_rt; + + ringacc->rings = devm_kzalloc(dev, + sizeof(*ringacc->rings) * + ringacc->num_rings * 2, + GFP_KERNEL); + ringacc->rings_inuse = devm_kcalloc(dev, + BITS_TO_LONGS(ringacc->num_rings), + sizeof(unsigned long), GFP_KERNEL); + + if (!ringacc->rings || !ringacc->rings_inuse) + return ERR_PTR(-ENOMEM); + + for (i = 0; i < ringacc->num_rings; i++) { + struct k3_nav_ring *ring = &ringacc->rings[i]; + + ring->rt = base_rt + K3_DMARING_RING_RT_REGS_STEP * i; + ring->parent = ringacc; + ring->ring_id = i; + ring->proxy_id = K3_RINGACC_PROXY_NOT_USED; + + ring = &ringacc->rings[ringacc->num_rings + i]; + ring->rt = base_rt + K3_DMARING_RING_RT_REGS_STEP * i + + K3_DMARING_RING_RT_REGS_REVERSE_OFS; + ring->parent = ringacc; + ring->ring_id = i; + ring->proxy_id = K3_RINGACC_PROXY_NOT_USED; + ring->flags = K3_NAV_RING_FLAG_REVERSE; + } + + ringacc->tisci_ring_ops = &ringacc->tisci->ops.rm_ring_ops; + + dev_info(dev, "k3_dmaring Ring probed rings:%u, sci-dev-id:%u\n", + ringacc->num_rings, + ringacc->tisci_dev_id); + dev_info(dev, "dma-ring-reset-quirk: %s\n", + ringacc->dma_ring_reset_quirk ? "enabled" : "disabled"); + + return ringacc; +} + struct ringacc_match_data { struct k3_nav_ringacc_ops ops; }; diff --git a/include/linux/soc/ti/k3-navss-ringacc.h b/include/linux/soc/ti/k3-navss-ringacc.h index 9176277ff0b..1e9b7d91258 100644 --- a/include/linux/soc/ti/k3-navss-ringacc.h +++ b/include/linux/soc/ti/k3-navss-ringacc.h @@ -238,4 +238,19 @@ int k3_nav_ringacc_ring_push_head(struct k3_nav_ring *ring, void *elem); */ int k3_nav_ringacc_ring_pop_tail(struct k3_nav_ring *ring, void *elem); +/* DMA ring support */ +struct ti_sci_handle; + +/** + * struct struct k3_ringacc_init_data - Initialization data for DMA rings + */ +struct k3_ringacc_init_data { + const struct ti_sci_handle *tisci; + u32 tisci_dev_id; + u32 num_rings; +}; + +struct k3_nav_ringacc *k3_ringacc_dmarings_init(struct udevice *dev, + struct k3_ringacc_init_data *data); + #endif /* __SOC_TI_K3_NAVSS_RINGACC_API_H_ */ -- cgit v1.3.1 From f1e97c705803ab07141640238a9c3036daf03011 Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Mon, 10 May 2021 20:06:04 +0530 Subject: soc: ti: k3-navss-ringacc: Remove unused ring modes With AM64x supporting only K3_NAV_RINGACC_RING_MODE_RING or the exposed ring mode, all other K3 SoCs have also been moved to this common baseline. Therefore drop other modes such as K3_NAV_RINGACC_RING_MODE_MESSAGE (and proxy) to save on SPL footprint. There is a saving of ~800 bytes with this change for am65x_evm_r5_defconfig. Signed-off-by: Vignesh Raghavendra Reviewed-by: Grygorii Strashko --- drivers/soc/ti/k3-navss-ringacc.c | 311 +------------------------------- include/linux/soc/ti/k3-navss-ringacc.h | 7 +- 2 files changed, 8 insertions(+), 310 deletions(-) (limited to 'include/linux/soc') diff --git a/drivers/soc/ti/k3-navss-ringacc.c b/drivers/soc/ti/k3-navss-ringacc.c index 10ef6be7205..b5a5c9da98a 100644 --- a/drivers/soc/ti/k3-navss-ringacc.c +++ b/drivers/soc/ti/k3-navss-ringacc.c @@ -91,36 +91,6 @@ struct k3_nav_ring_fifo_regs { u32 peek_tail_data[128]; /* Ring Peek Tail Entry Data Regs */ }; -/** - * struct k3_ringacc_proxy_gcfg_regs - RA Proxy Global Config MMIO Region - */ -struct k3_ringacc_proxy_gcfg_regs { - u32 revision; /* Revision Register */ - u32 config; /* Config Register */ -}; - -#define K3_RINGACC_PROXY_CFG_THREADS_MASK GENMASK(15, 0) - -/** - * struct k3_ringacc_proxy_target_regs - RA Proxy Datapath MMIO Region - */ -struct k3_ringacc_proxy_target_regs { - u32 control; /* Proxy Control Register */ - u32 status; /* Proxy Status Register */ - u8 resv_512[504]; - u32 data[128]; /* Proxy Data Register */ -}; - -#define K3_RINGACC_PROXY_TARGET_STEP 0x1000 -#define K3_RINGACC_PROXY_NOT_USED (-1) - -enum k3_ringacc_proxy_access_mode { - PROXY_ACCESS_MODE_HEAD = 0, - PROXY_ACCESS_MODE_TAIL = 1, - PROXY_ACCESS_MODE_PEEK_HEAD = 2, - PROXY_ACCESS_MODE_PEEK_TAIL = 3, -}; - #define KNAV_RINGACC_FIFO_WINDOW_SIZE_BYTES (512U) #define KNAV_RINGACC_FIFO_REGS_STEP 0x1000 #define KNAV_RINGACC_MAX_DB_RING_CNT (127U) @@ -156,7 +126,6 @@ struct k3_nav_ring_state { * * @rt - Ring control/status registers * @fifos - Ring queues registers - * @proxy - Ring Proxy Datapath registers * @ring_mem_dma - Ring buffer dma address * @ring_mem_virt - Ring buffer virt address * @ops - Ring operations @@ -167,12 +136,10 @@ struct k3_nav_ring_state { * @ring_id - Ring Id * @parent - Pointer on struct @k3_nav_ringacc * @use_count - Use count for shared rings - * @proxy_id - RA Ring Proxy Id (only if @K3_NAV_RINGACC_RING_USE_PROXY) */ struct k3_nav_ring { struct k3_nav_ring_rt_regs __iomem *rt; struct k3_nav_ring_fifo_regs __iomem *fifos; - struct k3_ringacc_proxy_target_regs __iomem *proxy; dma_addr_t ring_mem_dma; void *ring_mem_virt; struct k3_nav_ring_ops *ops; @@ -187,7 +154,6 @@ struct k3_nav_ring { u32 ring_id; struct k3_nav_ringacc *parent; u32 use_count; - int proxy_id; }; struct k3_nav_ringacc_ops { @@ -198,8 +164,6 @@ struct k3_nav_ringacc_ops { * struct k3_nav_ringacc - Rings accelerator descriptor * * @dev - pointer on RA device - * @proxy_gcfg - RA proxy global config registers - * @proxy_target_base - RA proxy datapath region * @num_rings - number of ring in RA * @rm_gp_range - general purpose rings range from tisci * @dma_ring_reset_quirk - DMA reset w/a enable @@ -214,14 +178,11 @@ struct k3_nav_ringacc_ops { */ struct k3_nav_ringacc { struct udevice *dev; - struct k3_ringacc_proxy_gcfg_regs __iomem *proxy_gcfg; - void __iomem *proxy_target_base; u32 num_rings; /* number of rings in Ringacc module */ unsigned long *rings_inuse; struct ti_sci_resource *rm_gp_range; bool dma_ring_reset_quirk; u32 num_proxies; - unsigned long *proxy_inuse; struct k3_nav_ring *rings; struct list_head list; @@ -249,12 +210,6 @@ static void k3_nav_ringacc_ring_update_occ(struct k3_nav_ring *ring) ring->state.tdown_complete = !!(val & K3_DMARING_RING_RT_OCC_TDOWN_COMPLETE); } -static long k3_nav_ringacc_ring_get_fifo_pos(struct k3_nav_ring *ring) -{ - return KNAV_RINGACC_FIFO_WINDOW_SIZE_BYTES - - (4 << ring->elm_size); -} - static void *k3_nav_ringacc_get_elm_addr(struct k3_nav_ring *ring, u32 idx) { return (idx * (4 << ring->elm_size) + ring->ring_mem_virt); @@ -279,44 +234,14 @@ static struct k3_nav_ring_ops k3_dmaring_reverse_ring_ops = { .pop_head = k3_dmaring_ring_reverse_pop_mem, }; -static int k3_nav_ringacc_ring_push_io(struct k3_nav_ring *ring, void *elem); -static int k3_nav_ringacc_ring_pop_io(struct k3_nav_ring *ring, void *elem); -static int k3_nav_ringacc_ring_push_head_io(struct k3_nav_ring *ring, - void *elem); -static int k3_nav_ringacc_ring_pop_tail_io(struct k3_nav_ring *ring, - void *elem); - -static struct k3_nav_ring_ops k3_nav_mode_msg_ops = { - .push_tail = k3_nav_ringacc_ring_push_io, - .push_head = k3_nav_ringacc_ring_push_head_io, - .pop_tail = k3_nav_ringacc_ring_pop_tail_io, - .pop_head = k3_nav_ringacc_ring_pop_io, -}; - -static int k3_ringacc_ring_push_head_proxy(struct k3_nav_ring *ring, - void *elem); -static int k3_ringacc_ring_push_tail_proxy(struct k3_nav_ring *ring, - void *elem); -static int k3_ringacc_ring_pop_head_proxy(struct k3_nav_ring *ring, void *elem); -static int k3_ringacc_ring_pop_tail_proxy(struct k3_nav_ring *ring, void *elem); - -static struct k3_nav_ring_ops k3_nav_mode_proxy_ops = { - .push_tail = k3_ringacc_ring_push_tail_proxy, - .push_head = k3_ringacc_ring_push_head_proxy, - .pop_tail = k3_ringacc_ring_pop_tail_proxy, - .pop_head = k3_ringacc_ring_pop_head_proxy, -}; - struct udevice *k3_nav_ringacc_get_dev(struct k3_nav_ringacc *ringacc) { return ringacc->dev; } struct k3_nav_ring *k3_nav_ringacc_request_ring(struct k3_nav_ringacc *ringacc, - int id, u32 flags) + int id) { - int proxy_id = K3_RINGACC_PROXY_NOT_USED; - if (id == K3_NAV_RINGACC_RING_ID_ANY) { /* Request for any general purpose ring */ struct ti_sci_resource_desc *gp_rings = @@ -338,24 +263,10 @@ struct k3_nav_ring *k3_nav_ringacc_request_ring(struct k3_nav_ringacc *ringacc, else if (ringacc->rings[id].flags & K3_NAV_RING_FLAG_SHARED) goto out; - if (flags & K3_NAV_RINGACC_RING_USE_PROXY) { - proxy_id = find_next_zero_bit(ringacc->proxy_inuse, - ringacc->num_proxies, 0); - if (proxy_id == ringacc->num_proxies) - goto error; - } - if (!try_module_get(ringacc->dev->driver->owner)) goto error; - if (proxy_id != K3_RINGACC_PROXY_NOT_USED) { - set_bit(proxy_id, ringacc->proxy_inuse); - ringacc->rings[id].proxy_id = proxy_id; - pr_debug("Giving ring#%d proxy#%d\n", - id, proxy_id); - } else { - pr_debug("Giving ring#%d\n", id); - } + pr_debug("Giving ring#%d\n", id); set_bit(id, ringacc->rings_inuse); out: @@ -401,11 +312,11 @@ int k3_nav_ringacc_request_rings_pair(struct k3_nav_ringacc *ringacc, return k3_dmaring_ring_request_rings_pair(ringacc, fwd_id, compl_id, fwd_ring, compl_ring); - *fwd_ring = k3_nav_ringacc_request_ring(ringacc, fwd_id, 0); + *fwd_ring = k3_nav_ringacc_request_ring(ringacc, fwd_id); if (!(*fwd_ring)) return -ENODEV; - *compl_ring = k3_nav_ringacc_request_ring(ringacc, compl_id, 0); + *compl_ring = k3_nav_ringacc_request_ring(ringacc, compl_id); if (!(*compl_ring)) { k3_nav_ringacc_ring_free(*fwd_ring); ret = -ENODEV; @@ -581,11 +492,6 @@ int k3_nav_ringacc_ring_free(struct k3_nav_ring *ring) ring->ring_mem_virt, ring->ring_mem_dma); ring->flags &= ~KNAV_RING_FLAG_BUSY; ring->ops = NULL; - if (ring->proxy_id != K3_RINGACC_PROXY_NOT_USED) { - clear_bit(ring->proxy_id, ringacc->proxy_inuse); - ring->proxy = NULL; - ring->proxy_id = K3_RINGACC_PROXY_NOT_USED; - } no_init: clear_bit(ring->ring_id, ringacc->rings_inuse); @@ -698,7 +604,6 @@ err_free_mem: ring->ring_mem_dma); err_free_ops: ring->ops = NULL; - ring->proxy = NULL; return ret; } @@ -728,32 +633,14 @@ int k3_nav_ringacc_ring_cfg(struct k3_nav_ring *ring, ring->mode = cfg->mode; memset(&ring->state, 0, sizeof(ring->state)); - if (ring->proxy_id != K3_RINGACC_PROXY_NOT_USED) - ring->proxy = ringacc->proxy_target_base + - ring->proxy_id * K3_RINGACC_PROXY_TARGET_STEP; - switch (ring->mode) { case K3_NAV_RINGACC_RING_MODE_RING: ring->ops = &k3_nav_mode_ring_ops; break; - case K3_NAV_RINGACC_RING_MODE_QM: - /* - * In Queue mode elm_size can be 8 only and each operation - * uses 2 element slots - */ - if (cfg->elm_size != K3_NAV_RINGACC_RING_ELSIZE_8 || - cfg->size % 2) - goto err_free_proxy; - case K3_NAV_RINGACC_RING_MODE_MESSAGE: - if (ring->proxy) - ring->ops = &k3_nav_mode_proxy_ops; - else - ring->ops = &k3_nav_mode_msg_ops; - break; default: ring->ops = NULL; ret = -EINVAL; - goto err_free_proxy; + goto err_free_ops; }; ring->ring_mem_virt = @@ -784,8 +671,6 @@ err_free_mem: ring->ring_mem_dma); err_free_ops: ring->ops = NULL; -err_free_proxy: - ring->proxy = NULL; return ret; } @@ -830,159 +715,6 @@ enum k3_ringacc_access_mode { K3_RINGACC_ACCESS_MODE_PEEK_TAIL, }; -static int k3_ringacc_ring_cfg_proxy(struct k3_nav_ring *ring, - enum k3_ringacc_proxy_access_mode mode) -{ - u32 val; - - val = ring->ring_id; - val |= mode << 16; - val |= ring->elm_size << 24; - ringacc_writel(val, &ring->proxy->control); - return 0; -} - -static int k3_nav_ringacc_ring_access_proxy( - struct k3_nav_ring *ring, void *elem, - enum k3_ringacc_access_mode access_mode) -{ - void __iomem *ptr; - - ptr = (void __iomem *)&ring->proxy->data; - - switch (access_mode) { - case K3_RINGACC_ACCESS_MODE_PUSH_HEAD: - case K3_RINGACC_ACCESS_MODE_POP_HEAD: - k3_ringacc_ring_cfg_proxy(ring, PROXY_ACCESS_MODE_HEAD); - break; - case K3_RINGACC_ACCESS_MODE_PUSH_TAIL: - case K3_RINGACC_ACCESS_MODE_POP_TAIL: - k3_ringacc_ring_cfg_proxy(ring, PROXY_ACCESS_MODE_TAIL); - break; - default: - return -EINVAL; - } - - ptr += k3_nav_ringacc_ring_get_fifo_pos(ring); - - switch (access_mode) { - case K3_RINGACC_ACCESS_MODE_POP_HEAD: - case K3_RINGACC_ACCESS_MODE_POP_TAIL: - pr_debug("proxy:memcpy_fromio(x): --> ptr(%p), mode:%d\n", - ptr, access_mode); - memcpy_fromio(elem, ptr, (4 << ring->elm_size)); - ring->state.occ--; - break; - case K3_RINGACC_ACCESS_MODE_PUSH_TAIL: - case K3_RINGACC_ACCESS_MODE_PUSH_HEAD: - pr_debug("proxy:memcpy_toio(x): --> ptr(%p), mode:%d\n", - ptr, access_mode); - memcpy_toio(ptr, elem, (4 << ring->elm_size)); - ring->state.free--; - break; - default: - return -EINVAL; - } - - pr_debug("proxy: free%d occ%d\n", - ring->state.free, ring->state.occ); - return 0; -} - -static int k3_ringacc_ring_push_head_proxy(struct k3_nav_ring *ring, void *elem) -{ - return k3_nav_ringacc_ring_access_proxy( - ring, elem, K3_RINGACC_ACCESS_MODE_PUSH_HEAD); -} - -static int k3_ringacc_ring_push_tail_proxy(struct k3_nav_ring *ring, void *elem) -{ - return k3_nav_ringacc_ring_access_proxy( - ring, elem, K3_RINGACC_ACCESS_MODE_PUSH_TAIL); -} - -static int k3_ringacc_ring_pop_head_proxy(struct k3_nav_ring *ring, void *elem) -{ - return k3_nav_ringacc_ring_access_proxy( - ring, elem, K3_RINGACC_ACCESS_MODE_POP_HEAD); -} - -static int k3_ringacc_ring_pop_tail_proxy(struct k3_nav_ring *ring, void *elem) -{ - return k3_nav_ringacc_ring_access_proxy( - ring, elem, K3_RINGACC_ACCESS_MODE_POP_HEAD); -} - -static int k3_nav_ringacc_ring_access_io( - struct k3_nav_ring *ring, void *elem, - enum k3_ringacc_access_mode access_mode) -{ - void __iomem *ptr; - - switch (access_mode) { - case K3_RINGACC_ACCESS_MODE_PUSH_HEAD: - case K3_RINGACC_ACCESS_MODE_POP_HEAD: - ptr = (void __iomem *)&ring->fifos->head_data; - break; - case K3_RINGACC_ACCESS_MODE_PUSH_TAIL: - case K3_RINGACC_ACCESS_MODE_POP_TAIL: - ptr = (void __iomem *)&ring->fifos->tail_data; - break; - default: - return -EINVAL; - } - - ptr += k3_nav_ringacc_ring_get_fifo_pos(ring); - - switch (access_mode) { - case K3_RINGACC_ACCESS_MODE_POP_HEAD: - case K3_RINGACC_ACCESS_MODE_POP_TAIL: - pr_debug("memcpy_fromio(x): --> ptr(%p), mode:%d\n", - ptr, access_mode); - memcpy_fromio(elem, ptr, (4 << ring->elm_size)); - ring->state.occ--; - break; - case K3_RINGACC_ACCESS_MODE_PUSH_TAIL: - case K3_RINGACC_ACCESS_MODE_PUSH_HEAD: - pr_debug("memcpy_toio(x): --> ptr(%p), mode:%d\n", - ptr, access_mode); - memcpy_toio(ptr, elem, (4 << ring->elm_size)); - ring->state.free--; - break; - default: - return -EINVAL; - } - - pr_debug("free%d index%d occ%d index%d\n", - ring->state.free, ring->state.windex, ring->state.occ, ring->state.rindex); - return 0; -} - -static int k3_nav_ringacc_ring_push_head_io(struct k3_nav_ring *ring, - void *elem) -{ - return k3_nav_ringacc_ring_access_io( - ring, elem, K3_RINGACC_ACCESS_MODE_PUSH_HEAD); -} - -static int k3_nav_ringacc_ring_push_io(struct k3_nav_ring *ring, void *elem) -{ - return k3_nav_ringacc_ring_access_io( - ring, elem, K3_RINGACC_ACCESS_MODE_PUSH_TAIL); -} - -static int k3_nav_ringacc_ring_pop_io(struct k3_nav_ring *ring, void *elem) -{ - return k3_nav_ringacc_ring_access_io( - ring, elem, K3_RINGACC_ACCESS_MODE_POP_HEAD); -} - -static int k3_nav_ringacc_ring_pop_tail_io(struct k3_nav_ring *ring, void *elem) -{ - return k3_nav_ringacc_ring_access_io( - ring, elem, K3_RINGACC_ACCESS_MODE_POP_HEAD); -} - static int k3_dmaring_ring_fwd_pop_mem(struct k3_nav_ring *ring, void *elem) { void *elem_ptr; @@ -1219,7 +951,7 @@ static int k3_nav_ringacc_probe_dt(struct k3_nav_ringacc *ringacc) static int k3_nav_ringacc_init(struct udevice *dev, struct k3_nav_ringacc *ringacc) { - void __iomem *base_fifo, *base_rt; + void __iomem *base_rt; int ret, i; ret = k3_nav_ringacc_probe_dt(ringacc); @@ -1231,24 +963,6 @@ static int k3_nav_ringacc_init(struct udevice *dev, struct k3_nav_ringacc *ringa if (IS_ERR(base_rt)) return PTR_ERR(base_rt); - base_fifo = (uint32_t *)devfdt_get_addr_name(dev, "fifos"); - pr_debug("fifos %p\n", base_fifo); - if (IS_ERR(base_fifo)) - return PTR_ERR(base_fifo); - - ringacc->proxy_gcfg = (struct k3_ringacc_proxy_gcfg_regs __iomem *) - devfdt_get_addr_name(dev, "proxy_gcfg"); - if (IS_ERR(ringacc->proxy_gcfg)) - return PTR_ERR(ringacc->proxy_gcfg); - ringacc->proxy_target_base = - (struct k3_ringacc_proxy_gcfg_regs __iomem *) - devfdt_get_addr_name(dev, "proxy_target"); - if (IS_ERR(ringacc->proxy_target_base)) - return PTR_ERR(ringacc->proxy_target_base); - - ringacc->num_proxies = ringacc_readl(&ringacc->proxy_gcfg->config) & - K3_RINGACC_PROXY_CFG_THREADS_MASK; - ringacc->rings = devm_kzalloc(dev, sizeof(*ringacc->rings) * ringacc->num_rings, @@ -1256,21 +970,15 @@ static int k3_nav_ringacc_init(struct udevice *dev, struct k3_nav_ringacc *ringa ringacc->rings_inuse = devm_kcalloc(dev, BITS_TO_LONGS(ringacc->num_rings), sizeof(unsigned long), GFP_KERNEL); - ringacc->proxy_inuse = devm_kcalloc(dev, - BITS_TO_LONGS(ringacc->num_proxies), - sizeof(unsigned long), GFP_KERNEL); - if (!ringacc->rings || !ringacc->rings_inuse || !ringacc->proxy_inuse) + if (!ringacc->rings || !ringacc->rings_inuse) return -ENOMEM; for (i = 0; i < ringacc->num_rings; i++) { ringacc->rings[i].rt = base_rt + KNAV_RINGACC_RT_REGS_STEP * i; - ringacc->rings[i].fifos = base_fifo + - KNAV_RINGACC_FIFO_REGS_STEP * i; ringacc->rings[i].parent = ringacc; ringacc->rings[i].ring_id = i; - ringacc->rings[i].proxy_id = K3_RINGACC_PROXY_NOT_USED; } dev_set_drvdata(dev, ringacc); @@ -1285,9 +993,6 @@ static int k3_nav_ringacc_init(struct udevice *dev, struct k3_nav_ringacc *ringa ringacc->tisci_dev_id); dev_info(dev, "dma-ring-reset-quirk: %s\n", ringacc->dma_ring_reset_quirk ? "enabled" : "disabled"); - dev_info(dev, "RA Proxy rev. %08x, num_proxies:%u\n", - ringacc_readl(&ringacc->proxy_gcfg->revision), - ringacc->num_proxies); return 0; } @@ -1330,14 +1035,12 @@ struct k3_nav_ringacc *k3_ringacc_dmarings_init(struct udevice *dev, ring->rt = base_rt + K3_DMARING_RING_RT_REGS_STEP * i; ring->parent = ringacc; ring->ring_id = i; - ring->proxy_id = K3_RINGACC_PROXY_NOT_USED; ring = &ringacc->rings[ringacc->num_rings + i]; ring->rt = base_rt + K3_DMARING_RING_RT_REGS_STEP * i + K3_DMARING_RING_RT_REGS_REVERSE_OFS; ring->parent = ringacc; ring->ring_id = i; - ring->proxy_id = K3_RINGACC_PROXY_NOT_USED; ring->flags = K3_NAV_RING_FLAG_REVERSE; } diff --git a/include/linux/soc/ti/k3-navss-ringacc.h b/include/linux/soc/ti/k3-navss-ringacc.h index 1e9b7d91258..0ad8f203da1 100644 --- a/include/linux/soc/ti/k3-navss-ringacc.h +++ b/include/linux/soc/ti/k3-navss-ringacc.h @@ -83,22 +83,17 @@ struct k3_nav_ring_cfg { }; #define K3_NAV_RINGACC_RING_ID_ANY (-1) -#define K3_NAV_RINGACC_RING_USE_PROXY BIT(1) /** * k3_nav_ringacc_request_ring - request ring from ringacc * @ringacc: pointer on ringacc * @id: ring id or K3_NAV_RINGACC_RING_ID_ANY for any general purpose ring - * @flags: - * @K3_NAV_RINGACC_RING_USE_PROXY: if set - proxy will be allocated and - * used to access ring memory. Sopported only for rings in - * Message/Credentials/Queue mode. * * Returns pointer on the Ring - struct k3_nav_ring * or NULL in case of failure. */ struct k3_nav_ring *k3_nav_ringacc_request_ring(struct k3_nav_ringacc *ringacc, - int id, u32 flags); + int id); int k3_nav_ringacc_request_rings_pair(struct k3_nav_ringacc *ringacc, int fwd_id, int compl_id, -- cgit v1.3.1