From 4728e3fe2ff1b02b84ddab876d8af5eeb74eee18 Mon Sep 17 00:00:00 2001 From: Daniel Scally Date: Thu, 18 Jan 2024 11:29:59 +0000 Subject: dmaengine: pl330: Clear callback_result for re-used descs The pl330 driver re-uses DMA descriptors rather than reallocating them each time. At present, upon re-use the .callback member is cleared, but .callback result is not. This causes problems where a consuming driver sets the .callback_result for some submissions but not for others, as eventually the function is invoked erronously. Clear .callback_result along with .callback Signed-off-by: Daniel Scally Link: https://lore.kernel.org/r/20240118112959.1027471-1-dan.scally@ideasonboard.com Signed-off-by: Vinod Koul --- drivers/dma/pl330.c | 1 + 1 file changed, 1 insertion(+) (limited to 'drivers') diff --git a/drivers/dma/pl330.c b/drivers/dma/pl330.c index c29744bfdf2c..5f6d7f1e095f 100644 --- a/drivers/dma/pl330.c +++ b/drivers/dma/pl330.c @@ -2588,6 +2588,7 @@ static struct dma_pl330_desc *pluck_desc(struct list_head *pool, desc->status = PREP; desc->txd.callback = NULL; + desc->txd.callback_result = NULL; } spin_unlock_irqrestore(lock, flags); -- cgit v1.2.3 From 33b7db45533af240fe44e809f9dc4d604cf82d07 Mon Sep 17 00:00:00 2001 From: Peter Robinson Date: Fri, 12 Jan 2024 09:32:56 +0000 Subject: dmaengine: tegra210-adma: Update dependency to ARCH_TEGRA Update the architecture dependency to be the generic Tegra because the driver works on the four latest Tegra generations not just T210, if you build a kernel with a specific ARCH_TEGRA_xxx_SOC option that excludes 210 you don't get this driver. Fixes: 433de642a76c9 ("dmaengine: tegra210-adma: add support for Tegra186/Tegra194") Signed-off-by: Peter Robinson Cc: Jon Hunter Cc: Thierry Reding Cc: Sameer Pujar Cc: Laxman Dewangan Reviewed-by: Jon Hunter Link: https://lore.kernel.org/r/20240112093310.329642-2-pbrobinson@gmail.com Signed-off-by: Vinod Koul --- drivers/dma/Kconfig | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/Kconfig b/drivers/dma/Kconfig index e928f2ca0f1e..002a5ec80620 100644 --- a/drivers/dma/Kconfig +++ b/drivers/dma/Kconfig @@ -643,16 +643,16 @@ config TEGRA20_APB_DMA config TEGRA210_ADMA tristate "NVIDIA Tegra210 ADMA support" - depends on (ARCH_TEGRA_210_SOC || COMPILE_TEST) + depends on (ARCH_TEGRA || COMPILE_TEST) select DMA_ENGINE select DMA_VIRTUAL_CHANNELS help - Support for the NVIDIA Tegra210 ADMA controller driver. The - DMA controller has multiple DMA channels and is used to service - various audio clients in the Tegra210 audio processing engine - (APE). This DMA controller transfers data from memory to - peripheral and vice versa. It does not support memory to - memory data transfer. + Support for the NVIDIA Tegra210/Tegra186/Tegra194/Tegra234 ADMA + controller driver. The DMA controller has multiple DMA channels + and is used to service various audio clients in the Tegra210 + audio processing engine (APE). This DMA controller transfers + data from memory to peripheral and vice versa. It does not + support memory to memory data transfer. config TIMB_DMA tristate "Timberdale FPGA DMA support" -- cgit v1.2.3 From 8fcc3f7dbdaeff3c3be47a15d1acd7863dfee92d Mon Sep 17 00:00:00 2001 From: Peter Korsgaard Date: Fri, 5 Jan 2024 11:59:56 +0100 Subject: dmaengine: xilinx_dma: check for invalid vdma interleaved parameters The VDMA HSIZE register (corresponding to sgl[0].size) is only 16bit wide / the VSIZE register (corresponding to numf) is only 13bit wide, so reject requests not fitting within that rather than silently transferring too little data. Signed-off-by: Peter Korsgaard Reviewed-by: Radhey Shyam Pandey Link: https://lore.kernel.org/r/20240105105956.1370220-1-peter@korsgaard.com Signed-off-by: Vinod Koul --- drivers/dma/xilinx/xilinx_dma.c | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'drivers') diff --git a/drivers/dma/xilinx/xilinx_dma.c b/drivers/dma/xilinx/xilinx_dma.c index e40696f6f864..5eb51ae93e89 100644 --- a/drivers/dma/xilinx/xilinx_dma.c +++ b/drivers/dma/xilinx/xilinx_dma.c @@ -112,7 +112,9 @@ /* Register Direct Mode Registers */ #define XILINX_DMA_REG_VSIZE 0x0000 +#define XILINX_DMA_VSIZE_MASK GENMASK(12, 0) #define XILINX_DMA_REG_HSIZE 0x0004 +#define XILINX_DMA_HSIZE_MASK GENMASK(15, 0) #define XILINX_DMA_REG_FRMDLY_STRIDE 0x0008 #define XILINX_DMA_FRMDLY_STRIDE_FRMDLY_SHIFT 24 @@ -2050,6 +2052,10 @@ xilinx_vdma_dma_prep_interleaved(struct dma_chan *dchan, if (!xt->numf || !xt->sgl[0].size) return NULL; + if (xt->numf & ~XILINX_DMA_VSIZE_MASK || + xt->sgl[0].size & ~XILINX_DMA_HSIZE_MASK) + return NULL; + if (xt->frame_size != 1) return NULL; -- cgit v1.2.3 From 7510bf84c4e318bff63b13183929a4272e1d2b5d Mon Sep 17 00:00:00 2001 From: Kunwu Chan Date: Wed, 24 Jan 2024 17:55:02 +0800 Subject: dmaengine: bestcomm: Code cleanup for bcom_sram_init This part was commented from commit 2f9ea1bde0d1 ("[POWERPC] bestcomm: core bestcomm support for Freescale MPC5200") in about 16 years before. If there are no plans to enable this part code in the future, we can remove this dead code. Signed-off-by: Kunwu Chan Link: https://lore.kernel.org/r/20240124095502.480506-1-chentao@kylinos.cn Signed-off-by: Vinod Koul --- drivers/dma/bestcomm/sram.c | 5 ----- 1 file changed, 5 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/bestcomm/sram.c b/drivers/dma/bestcomm/sram.c index 0553956f7456..ad74d57cc3ab 100644 --- a/drivers/dma/bestcomm/sram.c +++ b/drivers/dma/bestcomm/sram.c @@ -90,13 +90,8 @@ int bcom_sram_init(struct device_node *sram_node, char *owner) bcom_sram->rh = rh_create(4); /* Attach the free zones */ -#if 0 - /* Currently disabled ... for future use only */ - reg_addr_p = of_get_property(sram_node, "available", &psize); -#else regaddr_p = NULL; psize = 0; -#endif if (!regaddr_p || !psize) { /* Attach the whole zone */ -- cgit v1.2.3 From 81a1f90f20af71728f900f245aa69e9425fdef84 Mon Sep 17 00:00:00 2001 From: Siddharth Vadapalli Date: Wed, 24 Jan 2024 18:13:16 +0530 Subject: dmaengine: ti: k3-udma-glue: Add function to parse channel by ID The existing helper function of_k3_udma_glue_parse() fetches the DMA Channel thread ID from the device-tree node. This makes it necessary to have a device-tree node with the Channel thread IDs populated. However, in the case where the thread ID is known by alternate methods (an example being that of Firmware running on remote core sharing details of the thread IDs), there is no equivalent function to implement the functionality of the existing of_k3_udma_glue_parse() function. In such cases, the driver utilizing the DMA APIs might not even have a device-tree node to begin with, since it could be probed with other methods (RPMsg-Bus for example). Add the of_k3_udma_glue_parse_chn_by_id() helper function which accepts the thread ID as an argument, thereby making it unnecessary to have a device-tree node for obtaining the thread ID. Since of_k3_udma_glue_parse() and of_k3_udma_glue_parse_chn_by_id() share a lot of code in common, create a new function to handle the common code which is named as of_k3_udma_glue_parse_chn_common(). Signed-off-by: Siddharth Vadapalli Acked-by: Peter Ujfalusi Link: https://lore.kernel.org/r/20240124124319.820002-2-s-vadapalli@ti.com Signed-off-by: Vinod Koul --- drivers/dma/ti/k3-udma-glue.c | 73 ++++++++++++++++++++++++++++--------------- 1 file changed, 48 insertions(+), 25 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/ti/k3-udma-glue.c b/drivers/dma/ti/k3-udma-glue.c index c278d5facf7d..d8781625034b 100644 --- a/drivers/dma/ti/k3-udma-glue.c +++ b/drivers/dma/ti/k3-udma-glue.c @@ -111,6 +111,35 @@ static int of_k3_udma_glue_parse(struct device_node *udmax_np, return 0; } +static int of_k3_udma_glue_parse_chn_common(struct k3_udma_glue_common *common, u32 thread_id, + bool tx_chn) +{ + if (tx_chn && !(thread_id & K3_PSIL_DST_THREAD_ID_OFFSET)) + return -EINVAL; + + if (!tx_chn && (thread_id & K3_PSIL_DST_THREAD_ID_OFFSET)) + return -EINVAL; + + /* get psil endpoint config */ + common->ep_config = psil_get_ep_config(thread_id); + if (IS_ERR(common->ep_config)) { + dev_err(common->dev, + "No configuration for psi-l thread 0x%04x\n", + thread_id); + return PTR_ERR(common->ep_config); + } + + common->epib = common->ep_config->needs_epib; + common->psdata_size = common->ep_config->psd_size; + + if (tx_chn) + common->dst_thread = thread_id; + else + common->src_thread = thread_id; + + return 0; +} + static int of_k3_udma_glue_parse_chn(struct device_node *chn_np, const char *name, struct k3_udma_glue_common *common, bool tx_chn) @@ -153,38 +182,32 @@ static int of_k3_udma_glue_parse_chn(struct device_node *chn_np, common->atype_asel = dma_spec.args[1]; } - if (tx_chn && !(thread_id & K3_PSIL_DST_THREAD_ID_OFFSET)) { - ret = -EINVAL; - goto out_put_spec; - } + ret = of_k3_udma_glue_parse_chn_common(common, thread_id, tx_chn); - if (!tx_chn && (thread_id & K3_PSIL_DST_THREAD_ID_OFFSET)) { - ret = -EINVAL; - goto out_put_spec; - } +out_put_spec: + of_node_put(dma_spec.np); + return ret; +} - /* get psil endpoint config */ - common->ep_config = psil_get_ep_config(thread_id); - if (IS_ERR(common->ep_config)) { - dev_err(common->dev, - "No configuration for psi-l thread 0x%04x\n", - thread_id); - ret = PTR_ERR(common->ep_config); - goto out_put_spec; - } +static int +of_k3_udma_glue_parse_chn_by_id(struct device_node *udmax_np, struct k3_udma_glue_common *common, + bool tx_chn, u32 thread_id) +{ + int ret = 0; - common->epib = common->ep_config->needs_epib; - common->psdata_size = common->ep_config->psd_size; + if (unlikely(!udmax_np)) + return -EINVAL; - if (tx_chn) - common->dst_thread = thread_id; - else - common->src_thread = thread_id; + ret = of_k3_udma_glue_parse(udmax_np, common); + if (ret) + goto out_put_spec; + + ret = of_k3_udma_glue_parse_chn_common(common, thread_id, tx_chn); out_put_spec: - of_node_put(dma_spec.np); + of_node_put(udmax_np); return ret; -}; +} static void k3_udma_glue_dump_tx_chn(struct k3_udma_glue_tx_channel *tx_chn) { -- cgit v1.2.3 From 7edd7a2fd345b10e80ee854aaacc6452d6f46a7e Mon Sep 17 00:00:00 2001 From: Siddharth Vadapalli Date: Wed, 24 Jan 2024 18:13:17 +0530 Subject: dmaengine: ti: k3-udma-glue: Update name for remote RX channel device A single RX Channel can have multiple flows. It is possible that a single device requests multiple flows on the same RX Channel. In such cases, the existing implementation of naming the device on the basis of the RX Channel can result in duplicate names. The existing implementation only uses the RX Channel source thread when naming, which implies duplicate names when different flows are being requested on the same RX Channel. In order to avoid duplicate names, include the RX flow as well in the name. Signed-off-by: Siddharth Vadapalli Acked-by: Peter Ujfalusi Link: https://lore.kernel.org/r/20240124124319.820002-3-s-vadapalli@ti.com Signed-off-by: Vinod Koul --- drivers/dma/ti/k3-udma-glue.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/ti/k3-udma-glue.c b/drivers/dma/ti/k3-udma-glue.c index d8781625034b..eff1ae3d3efe 100644 --- a/drivers/dma/ti/k3-udma-glue.c +++ b/drivers/dma/ti/k3-udma-glue.c @@ -1072,8 +1072,8 @@ k3_udma_glue_request_remote_rx_chn(struct device *dev, const char *name, rx_chn->common.chan_dev.class = &k3_udma_glue_devclass; rx_chn->common.chan_dev.parent = xudma_get_device(rx_chn->common.udmax); - dev_set_name(&rx_chn->common.chan_dev, "rchan_remote-0x%04x", - rx_chn->common.src_thread); + dev_set_name(&rx_chn->common.chan_dev, "rchan_remote-0x%04x-0x%02x", + rx_chn->common.src_thread, rx_chn->flow_id_base); ret = device_register(&rx_chn->common.chan_dev); if (ret) { dev_err(dev, "Channel Device registration failed %d\n", ret); -- cgit v1.2.3 From 7cbf7f4bf71a054d687c8860380c655a36d0f369 Mon Sep 17 00:00:00 2001 From: Siddharth Vadapalli Date: Wed, 24 Jan 2024 18:13:18 +0530 Subject: dmaengine: ti: k3-udma-glue: Add function to request TX chan for thread ID The existing function k3_udma_glue_request_tx_chn() supports requesting a TX DMA channel by its name. Add a new function to request TX DMA channel for a given thread ID, named k3_udma_glue_request_tx_chn_for_thread_id(). Also, export it for use by drivers which are probed by alternate methods (non device-tree) but still wish to make use of the existing DMA APIs. Such drivers could be informed about the thread ID corresponding to the TX DMA channel by RPMsg for example. Since the new function k3_udma_glue_request_tx_chn_for_thread_id() reuses most of the code in k3_udma_glue_request_tx_chn(), create a new function for the common code, named k3_udma_glue_request_tx_chn_common(). Signed-off-by: Siddharth Vadapalli Acked-by: Peter Ujfalusi Link: https://lore.kernel.org/r/20240124124319.820002-4-s-vadapalli@ti.com Signed-off-by: Vinod Koul --- drivers/dma/ti/k3-udma-glue.c | 102 +++++++++++++++++++++++++++++---------- include/linux/dma/k3-udma-glue.h | 5 ++ 2 files changed, 81 insertions(+), 26 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/ti/k3-udma-glue.c b/drivers/dma/ti/k3-udma-glue.c index eff1ae3d3efe..a475bbea35ee 100644 --- a/drivers/dma/ti/k3-udma-glue.c +++ b/drivers/dma/ti/k3-udma-glue.c @@ -274,29 +274,13 @@ static int k3_udma_glue_cfg_tx_chn(struct k3_udma_glue_tx_channel *tx_chn) return tisci_rm->tisci_udmap_ops->tx_ch_cfg(tisci_rm->tisci, &req); } -struct k3_udma_glue_tx_channel *k3_udma_glue_request_tx_chn(struct device *dev, - const char *name, struct k3_udma_glue_tx_channel_cfg *cfg) +static int +k3_udma_glue_request_tx_chn_common(struct device *dev, + struct k3_udma_glue_tx_channel *tx_chn, + struct k3_udma_glue_tx_channel_cfg *cfg) { - struct k3_udma_glue_tx_channel *tx_chn; int ret; - tx_chn = devm_kzalloc(dev, sizeof(*tx_chn), GFP_KERNEL); - if (!tx_chn) - return ERR_PTR(-ENOMEM); - - tx_chn->common.dev = dev; - tx_chn->common.swdata_size = cfg->swdata_size; - tx_chn->tx_pause_on_err = cfg->tx_pause_on_err; - tx_chn->tx_filt_einfo = cfg->tx_filt_einfo; - tx_chn->tx_filt_pswords = cfg->tx_filt_pswords; - tx_chn->tx_supr_tdpkt = cfg->tx_supr_tdpkt; - - /* parse of udmap channel */ - ret = of_k3_udma_glue_parse_chn(dev->of_node, name, - &tx_chn->common, true); - if (ret) - goto err; - tx_chn->common.hdesc_size = cppi5_hdesc_calc_size(tx_chn->common.epib, tx_chn->common.psdata_size, tx_chn->common.swdata_size); @@ -312,7 +296,7 @@ struct k3_udma_glue_tx_channel *k3_udma_glue_request_tx_chn(struct device *dev, if (IS_ERR(tx_chn->udma_tchanx)) { ret = PTR_ERR(tx_chn->udma_tchanx); dev_err(dev, "UDMAX tchanx get err %d\n", ret); - goto err; + return ret; } tx_chn->udma_tchan_id = xudma_tchan_get_id(tx_chn->udma_tchanx); @@ -325,7 +309,7 @@ struct k3_udma_glue_tx_channel *k3_udma_glue_request_tx_chn(struct device *dev, dev_err(dev, "Channel Device registration failed %d\n", ret); put_device(&tx_chn->common.chan_dev); tx_chn->common.chan_dev.parent = NULL; - goto err; + return ret; } if (xudma_is_pktdma(tx_chn->common.udmax)) { @@ -349,7 +333,7 @@ struct k3_udma_glue_tx_channel *k3_udma_glue_request_tx_chn(struct device *dev, &tx_chn->ringtxcq); if (ret) { dev_err(dev, "Failed to get TX/TXCQ rings %d\n", ret); - goto err; + return ret; } /* Set the dma_dev for the rings to be configured */ @@ -365,13 +349,13 @@ struct k3_udma_glue_tx_channel *k3_udma_glue_request_tx_chn(struct device *dev, ret = k3_ringacc_ring_cfg(tx_chn->ringtx, &cfg->tx_cfg); if (ret) { dev_err(dev, "Failed to cfg ringtx %d\n", ret); - goto err; + return ret; } ret = k3_ringacc_ring_cfg(tx_chn->ringtxcq, &cfg->txcq_cfg); if (ret) { dev_err(dev, "Failed to cfg ringtx %d\n", ret); - goto err; + return ret; } /* request and cfg psi-l */ @@ -382,11 +366,42 @@ struct k3_udma_glue_tx_channel *k3_udma_glue_request_tx_chn(struct device *dev, ret = k3_udma_glue_cfg_tx_chn(tx_chn); if (ret) { dev_err(dev, "Failed to cfg tchan %d\n", ret); - goto err; + return ret; } k3_udma_glue_dump_tx_chn(tx_chn); + return 0; +} + +struct k3_udma_glue_tx_channel * +k3_udma_glue_request_tx_chn(struct device *dev, const char *name, + struct k3_udma_glue_tx_channel_cfg *cfg) +{ + struct k3_udma_glue_tx_channel *tx_chn; + int ret; + + tx_chn = devm_kzalloc(dev, sizeof(*tx_chn), GFP_KERNEL); + if (!tx_chn) + return ERR_PTR(-ENOMEM); + + tx_chn->common.dev = dev; + tx_chn->common.swdata_size = cfg->swdata_size; + tx_chn->tx_pause_on_err = cfg->tx_pause_on_err; + tx_chn->tx_filt_einfo = cfg->tx_filt_einfo; + tx_chn->tx_filt_pswords = cfg->tx_filt_pswords; + tx_chn->tx_supr_tdpkt = cfg->tx_supr_tdpkt; + + /* parse of udmap channel */ + ret = of_k3_udma_glue_parse_chn(dev->of_node, name, + &tx_chn->common, true); + if (ret) + goto err; + + ret = k3_udma_glue_request_tx_chn_common(dev, tx_chn, cfg); + if (ret) + goto err; + return tx_chn; err: @@ -395,6 +410,41 @@ err: } EXPORT_SYMBOL_GPL(k3_udma_glue_request_tx_chn); +struct k3_udma_glue_tx_channel * +k3_udma_glue_request_tx_chn_for_thread_id(struct device *dev, + struct k3_udma_glue_tx_channel_cfg *cfg, + struct device_node *udmax_np, u32 thread_id) +{ + struct k3_udma_glue_tx_channel *tx_chn; + int ret; + + tx_chn = devm_kzalloc(dev, sizeof(*tx_chn), GFP_KERNEL); + if (!tx_chn) + return ERR_PTR(-ENOMEM); + + tx_chn->common.dev = dev; + tx_chn->common.swdata_size = cfg->swdata_size; + tx_chn->tx_pause_on_err = cfg->tx_pause_on_err; + tx_chn->tx_filt_einfo = cfg->tx_filt_einfo; + tx_chn->tx_filt_pswords = cfg->tx_filt_pswords; + tx_chn->tx_supr_tdpkt = cfg->tx_supr_tdpkt; + + ret = of_k3_udma_glue_parse_chn_by_id(udmax_np, &tx_chn->common, true, thread_id); + if (ret) + goto err; + + ret = k3_udma_glue_request_tx_chn_common(dev, tx_chn, cfg); + if (ret) + goto err; + + return tx_chn; + +err: + k3_udma_glue_release_tx_chn(tx_chn); + return ERR_PTR(ret); +} +EXPORT_SYMBOL_GPL(k3_udma_glue_request_tx_chn_for_thread_id); + void k3_udma_glue_release_tx_chn(struct k3_udma_glue_tx_channel *tx_chn) { if (tx_chn->psil_paired) { diff --git a/include/linux/dma/k3-udma-glue.h b/include/linux/dma/k3-udma-glue.h index e443be4d3b4b..c81386ceb1c1 100644 --- a/include/linux/dma/k3-udma-glue.h +++ b/include/linux/dma/k3-udma-glue.h @@ -26,6 +26,11 @@ struct k3_udma_glue_tx_channel; struct k3_udma_glue_tx_channel *k3_udma_glue_request_tx_chn(struct device *dev, const char *name, struct k3_udma_glue_tx_channel_cfg *cfg); +struct k3_udma_glue_tx_channel * +k3_udma_glue_request_tx_chn_for_thread_id(struct device *dev, + struct k3_udma_glue_tx_channel_cfg *cfg, + struct device_node *udmax_np, u32 thread_id); + void k3_udma_glue_release_tx_chn(struct k3_udma_glue_tx_channel *tx_chn); int k3_udma_glue_push_tx_chn(struct k3_udma_glue_tx_channel *tx_chn, struct cppi5_host_desc_t *desc_tx, -- cgit v1.2.3 From e54df52312fed462a005706d5d7ed6250da91d1e Mon Sep 17 00:00:00 2001 From: Siddharth Vadapalli Date: Wed, 24 Jan 2024 18:13:19 +0530 Subject: dmaengine: ti: k3-udma-glue: Add function to request RX chan for thread ID The existing function k3_udma_glue_request_remote_rx_chn() supports requesting an RX DMA channel and flow by the name of the RX DMA channel. Add support to request RX DMA channel for a given thread ID in the form of a new function named k3_udma_glue_request_remote_rx_chn_for_thread_id(). Also, export it for use by drivers which are probed by alternate methods (non device-tree) but still wish to make use of the existing DMA APIs. Such drivers could be informed about the thread ID corresponding to the RX DMA channel by RPMsg for example. Since the new function k3_udma_glue_request_remote_rx_chn_for_thread_id() reuses most of the code in k3_udma_glue_request_remote_rx_chn(), create a new function named k3_udma_glue_request_remote_rx_chn_common() for the common code. Signed-off-by: Siddharth Vadapalli Acked-by: Peter Ujfalusi Link: https://lore.kernel.org/r/20240124124319.820002-5-s-vadapalli@ti.com Signed-off-by: Vinod Koul --- drivers/dma/ti/k3-udma-glue.c | 123 +++++++++++++++++++++++++++++---------- include/linux/dma/k3-udma-glue.h | 5 ++ 2 files changed, 96 insertions(+), 32 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/ti/k3-udma-glue.c b/drivers/dma/ti/k3-udma-glue.c index a475bbea35ee..c9b93055dc9d 100644 --- a/drivers/dma/ti/k3-udma-glue.c +++ b/drivers/dma/ti/k3-udma-glue.c @@ -1073,12 +1073,59 @@ err: return ERR_PTR(ret); } +static int +k3_udma_glue_request_remote_rx_chn_common(struct k3_udma_glue_rx_channel *rx_chn, + struct k3_udma_glue_rx_channel_cfg *cfg, + struct device *dev) +{ + int ret, i; + + rx_chn->common.hdesc_size = cppi5_hdesc_calc_size(rx_chn->common.epib, + rx_chn->common.psdata_size, + rx_chn->common.swdata_size); + + rx_chn->flows = devm_kcalloc(dev, rx_chn->flow_num, + sizeof(*rx_chn->flows), GFP_KERNEL); + if (!rx_chn->flows) + return -ENOMEM; + + rx_chn->common.chan_dev.class = &k3_udma_glue_devclass; + rx_chn->common.chan_dev.parent = xudma_get_device(rx_chn->common.udmax); + dev_set_name(&rx_chn->common.chan_dev, "rchan_remote-0x%04x-0x%02x", + rx_chn->common.src_thread, rx_chn->flow_id_base); + ret = device_register(&rx_chn->common.chan_dev); + if (ret) { + dev_err(dev, "Channel Device registration failed %d\n", ret); + put_device(&rx_chn->common.chan_dev); + rx_chn->common.chan_dev.parent = NULL; + return ret; + } + + if (xudma_is_pktdma(rx_chn->common.udmax)) { + /* prepare the channel device as coherent */ + rx_chn->common.chan_dev.dma_coherent = true; + dma_coerce_mask_and_coherent(&rx_chn->common.chan_dev, + DMA_BIT_MASK(48)); + } + + ret = k3_udma_glue_allocate_rx_flows(rx_chn, cfg); + if (ret) + return ret; + + for (i = 0; i < rx_chn->flow_num; i++) + rx_chn->flows[i].udma_rflow_id = rx_chn->flow_id_base + i; + + k3_udma_glue_dump_rx_chn(rx_chn); + + return 0; +} + static struct k3_udma_glue_rx_channel * k3_udma_glue_request_remote_rx_chn(struct device *dev, const char *name, struct k3_udma_glue_rx_channel_cfg *cfg) { struct k3_udma_glue_rx_channel *rx_chn; - int ret, i; + int ret; if (cfg->flow_id_num <= 0 || cfg->flow_id_use_rxchan_id || @@ -1109,44 +1156,55 @@ k3_udma_glue_request_remote_rx_chn(struct device *dev, const char *name, if (ret) goto err; - rx_chn->common.hdesc_size = cppi5_hdesc_calc_size(rx_chn->common.epib, - rx_chn->common.psdata_size, - rx_chn->common.swdata_size); - - rx_chn->flows = devm_kcalloc(dev, rx_chn->flow_num, - sizeof(*rx_chn->flows), GFP_KERNEL); - if (!rx_chn->flows) { - ret = -ENOMEM; + ret = k3_udma_glue_request_remote_rx_chn_common(rx_chn, cfg, dev); + if (ret) goto err; - } - rx_chn->common.chan_dev.class = &k3_udma_glue_devclass; - rx_chn->common.chan_dev.parent = xudma_get_device(rx_chn->common.udmax); - dev_set_name(&rx_chn->common.chan_dev, "rchan_remote-0x%04x-0x%02x", - rx_chn->common.src_thread, rx_chn->flow_id_base); - ret = device_register(&rx_chn->common.chan_dev); - if (ret) { - dev_err(dev, "Channel Device registration failed %d\n", ret); - put_device(&rx_chn->common.chan_dev); - rx_chn->common.chan_dev.parent = NULL; - goto err; - } + return rx_chn; - if (xudma_is_pktdma(rx_chn->common.udmax)) { - /* prepare the channel device as coherent */ - rx_chn->common.chan_dev.dma_coherent = true; - dma_coerce_mask_and_coherent(&rx_chn->common.chan_dev, - DMA_BIT_MASK(48)); - } +err: + k3_udma_glue_release_rx_chn(rx_chn); + return ERR_PTR(ret); +} - ret = k3_udma_glue_allocate_rx_flows(rx_chn, cfg); +struct k3_udma_glue_rx_channel * +k3_udma_glue_request_remote_rx_chn_for_thread_id(struct device *dev, + struct k3_udma_glue_rx_channel_cfg *cfg, + struct device_node *udmax_np, u32 thread_id) +{ + struct k3_udma_glue_rx_channel *rx_chn; + int ret; + + if (cfg->flow_id_num <= 0 || + cfg->flow_id_use_rxchan_id || + cfg->def_flow_cfg || + cfg->flow_id_base < 0) + return ERR_PTR(-EINVAL); + + /* + * Remote RX channel is under control of Remote CPU core, so + * Linux can only request and manipulate by dedicated RX flows + */ + + rx_chn = devm_kzalloc(dev, sizeof(*rx_chn), GFP_KERNEL); + if (!rx_chn) + return ERR_PTR(-ENOMEM); + + rx_chn->common.dev = dev; + rx_chn->common.swdata_size = cfg->swdata_size; + rx_chn->remote = true; + rx_chn->udma_rchan_id = -1; + rx_chn->flow_num = cfg->flow_id_num; + rx_chn->flow_id_base = cfg->flow_id_base; + rx_chn->psil_paired = false; + + ret = of_k3_udma_glue_parse_chn_by_id(udmax_np, &rx_chn->common, false, thread_id); if (ret) goto err; - for (i = 0; i < rx_chn->flow_num; i++) - rx_chn->flows[i].udma_rflow_id = rx_chn->flow_id_base + i; - - k3_udma_glue_dump_rx_chn(rx_chn); + ret = k3_udma_glue_request_remote_rx_chn_common(rx_chn, cfg, dev); + if (ret) + goto err; return rx_chn; @@ -1154,6 +1212,7 @@ err: k3_udma_glue_release_rx_chn(rx_chn); return ERR_PTR(ret); } +EXPORT_SYMBOL_GPL(k3_udma_glue_request_remote_rx_chn_for_thread_id); struct k3_udma_glue_rx_channel * k3_udma_glue_request_rx_chn(struct device *dev, const char *name, diff --git a/include/linux/dma/k3-udma-glue.h b/include/linux/dma/k3-udma-glue.h index c81386ceb1c1..1e491c5dcac2 100644 --- a/include/linux/dma/k3-udma-glue.h +++ b/include/linux/dma/k3-udma-glue.h @@ -114,6 +114,11 @@ struct k3_udma_glue_rx_channel *k3_udma_glue_request_rx_chn( const char *name, struct k3_udma_glue_rx_channel_cfg *cfg); +struct k3_udma_glue_rx_channel * +k3_udma_glue_request_remote_rx_chn_for_thread_id(struct device *dev, + struct k3_udma_glue_rx_channel_cfg *cfg, + struct device_node *udmax_np, u32 thread_id); + void k3_udma_glue_release_rx_chn(struct k3_udma_glue_rx_channel *rx_chn); int k3_udma_glue_enable_rx_chn(struct k3_udma_glue_rx_channel *rx_chn); void k3_udma_glue_disable_rx_chn(struct k3_udma_glue_rx_channel *rx_chn); -- cgit v1.2.3 From 93bdff7bb83a9ea79f41d4e48e1711fd5f4ec4ed Mon Sep 17 00:00:00 2001 From: Vaishnav Achath Date: Thu, 25 Jan 2024 16:44:49 +0530 Subject: dmaengine: ti: k3-psil-j721s2: Add entry for CSI2RX The CSI2RX subsystem uses PSI-L DMA to transfer frames to memory. It can have up to 32 threads per instance. J721S2 has two instances of the subsystem, so there are 64 threads total, Add them to the endpoint map. Signed-off-by: Vaishnav Achath Reviewed-by: Udit Kumar Link: https://lore.kernel.org/r/20240125111449.855876-1-vaishnav.a@ti.com Signed-off-by: Vinod Koul --- drivers/dma/ti/k3-psil-j721s2.c | 73 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 73 insertions(+) (limited to 'drivers') diff --git a/drivers/dma/ti/k3-psil-j721s2.c b/drivers/dma/ti/k3-psil-j721s2.c index 1d5430fc5724..ba08bdcdcd2b 100644 --- a/drivers/dma/ti/k3-psil-j721s2.c +++ b/drivers/dma/ti/k3-psil-j721s2.c @@ -57,6 +57,14 @@ }, \ } +#define PSIL_CSI2RX(x) \ + { \ + .thread_id = x, \ + .ep_config = { \ + .ep_type = PSIL_EP_NATIVE, \ + }, \ + } + /* PSI-L source thread IDs, used for RX (DMA_DEV_TO_MEM) */ static struct psil_ep j721s2_src_ep_map[] = { /* PDMA_MCASP - McASP0-4 */ @@ -114,6 +122,71 @@ static struct psil_ep j721s2_src_ep_map[] = { PSIL_PDMA_XY_PKT(0x4707), PSIL_PDMA_XY_PKT(0x4708), PSIL_PDMA_XY_PKT(0x4709), + /* CSI2RX */ + PSIL_CSI2RX(0x4940), + PSIL_CSI2RX(0x4941), + PSIL_CSI2RX(0x4942), + PSIL_CSI2RX(0x4943), + PSIL_CSI2RX(0x4944), + PSIL_CSI2RX(0x4945), + PSIL_CSI2RX(0x4946), + PSIL_CSI2RX(0x4947), + PSIL_CSI2RX(0x4948), + PSIL_CSI2RX(0x4949), + PSIL_CSI2RX(0x494a), + PSIL_CSI2RX(0x494b), + PSIL_CSI2RX(0x494c), + PSIL_CSI2RX(0x494d), + PSIL_CSI2RX(0x494e), + PSIL_CSI2RX(0x494f), + PSIL_CSI2RX(0x4950), + PSIL_CSI2RX(0x4951), + PSIL_CSI2RX(0x4952), + PSIL_CSI2RX(0x4953), + PSIL_CSI2RX(0x4954), + PSIL_CSI2RX(0x4955), + PSIL_CSI2RX(0x4956), + PSIL_CSI2RX(0x4957), + PSIL_CSI2RX(0x4958), + PSIL_CSI2RX(0x4959), + PSIL_CSI2RX(0x495a), + PSIL_CSI2RX(0x495b), + PSIL_CSI2RX(0x495c), + PSIL_CSI2RX(0x495d), + PSIL_CSI2RX(0x495e), + PSIL_CSI2RX(0x495f), + PSIL_CSI2RX(0x4960), + PSIL_CSI2RX(0x4961), + PSIL_CSI2RX(0x4962), + PSIL_CSI2RX(0x4963), + PSIL_CSI2RX(0x4964), + PSIL_CSI2RX(0x4965), + PSIL_CSI2RX(0x4966), + PSIL_CSI2RX(0x4967), + PSIL_CSI2RX(0x4968), + PSIL_CSI2RX(0x4969), + PSIL_CSI2RX(0x496a), + PSIL_CSI2RX(0x496b), + PSIL_CSI2RX(0x496c), + PSIL_CSI2RX(0x496d), + PSIL_CSI2RX(0x496e), + PSIL_CSI2RX(0x496f), + PSIL_CSI2RX(0x4970), + PSIL_CSI2RX(0x4971), + PSIL_CSI2RX(0x4972), + PSIL_CSI2RX(0x4973), + PSIL_CSI2RX(0x4974), + PSIL_CSI2RX(0x4975), + PSIL_CSI2RX(0x4976), + PSIL_CSI2RX(0x4977), + PSIL_CSI2RX(0x4978), + PSIL_CSI2RX(0x4979), + PSIL_CSI2RX(0x497a), + PSIL_CSI2RX(0x497b), + PSIL_CSI2RX(0x497c), + PSIL_CSI2RX(0x497d), + PSIL_CSI2RX(0x497e), + PSIL_CSI2RX(0x497f), /* MAIN SA2UL */ PSIL_SA2UL(0x4a40, 0), PSIL_SA2UL(0x4a41, 0), -- cgit v1.2.3 From 5dc604455dcf20bdca639bf6b8ea2ea60d39c022 Mon Sep 17 00:00:00 2001 From: Frank Li Date: Thu, 21 Dec 2023 10:35:23 -0500 Subject: dmaengine: fsl-edma: involve help macro fsl_edma_set(get)_tcd() Using help macro fsl_edma_set(get)_tcd() and edma_cp_tcd_to_reg() to handle difference field size. This is not function change and prepare for 64bit tcd in imx95. Signed-off-by: Frank Li Link: https://lore.kernel.org/r/20231221153528.1588049-2-Frank.Li@nxp.com Signed-off-by: Vinod Koul --- drivers/dma/fsl-edma-common.c | 61 ++++++++++++++++++++++--------------------- drivers/dma/fsl-edma-common.h | 23 ++++++++++++++++ 2 files changed, 54 insertions(+), 30 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/fsl-edma-common.c b/drivers/dma/fsl-edma-common.c index b53f46245c37..50f55d7566a3 100644 --- a/drivers/dma/fsl-edma-common.c +++ b/drivers/dma/fsl-edma-common.c @@ -358,10 +358,10 @@ static size_t fsl_edma_desc_residue(struct fsl_edma_chan *fsl_chan, /* calculate the total size in this desc */ for (len = i = 0; i < fsl_chan->edesc->n_tcds; i++) { - nbytes = le32_to_cpu(edesc->tcd[i].vtcd->nbytes); + nbytes = fsl_edma_get_tcd_to_cpu(fsl_chan, edesc->tcd[i].vtcd, nbytes); if (nbytes & (EDMA_V3_TCD_NBYTES_DMLOE | EDMA_V3_TCD_NBYTES_SMLOE)) nbytes = EDMA_V3_TCD_NBYTES_MLOFF_NBYTES(nbytes); - len += nbytes * le16_to_cpu(edesc->tcd[i].vtcd->biter); + len += nbytes * fsl_edma_get_tcd_to_cpu(fsl_chan, edesc->tcd[i].vtcd, biter); } if (!in_progress) @@ -374,16 +374,16 @@ static size_t fsl_edma_desc_residue(struct fsl_edma_chan *fsl_chan, /* figure out the finished and calculate the residue */ for (i = 0; i < fsl_chan->edesc->n_tcds; i++) { - nbytes = le32_to_cpu(edesc->tcd[i].vtcd->nbytes); + nbytes = fsl_edma_get_tcd_to_cpu(fsl_chan, edesc->tcd[i].vtcd, nbytes); if (nbytes & (EDMA_V3_TCD_NBYTES_DMLOE | EDMA_V3_TCD_NBYTES_SMLOE)) nbytes = EDMA_V3_TCD_NBYTES_MLOFF_NBYTES(nbytes); - size = nbytes * le16_to_cpu(edesc->tcd[i].vtcd->biter); + size = nbytes * fsl_edma_get_tcd_to_cpu(fsl_chan, edesc->tcd[i].vtcd, biter); if (dir == DMA_MEM_TO_DEV) - dma_addr = le32_to_cpu(edesc->tcd[i].vtcd->saddr); + dma_addr = fsl_edma_get_tcd_to_cpu(fsl_chan, edesc->tcd[i].vtcd, saddr); else - dma_addr = le32_to_cpu(edesc->tcd[i].vtcd->daddr); + dma_addr = fsl_edma_get_tcd_to_cpu(fsl_chan, edesc->tcd[i].vtcd, daddr); len -= size; if (cur_addr >= dma_addr && cur_addr < dma_addr + size) { @@ -439,26 +439,26 @@ static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan, */ edma_write_tcdreg(fsl_chan, 0, csr); - edma_write_tcdreg(fsl_chan, tcd->saddr, saddr); - edma_write_tcdreg(fsl_chan, tcd->daddr, daddr); + edma_cp_tcd_to_reg(fsl_chan, tcd, saddr); + edma_cp_tcd_to_reg(fsl_chan, tcd, daddr); - edma_write_tcdreg(fsl_chan, tcd->attr, attr); - edma_write_tcdreg(fsl_chan, tcd->soff, soff); + edma_cp_tcd_to_reg(fsl_chan, tcd, attr); + edma_cp_tcd_to_reg(fsl_chan, tcd, soff); - edma_write_tcdreg(fsl_chan, tcd->nbytes, nbytes); - edma_write_tcdreg(fsl_chan, tcd->slast, slast); + edma_cp_tcd_to_reg(fsl_chan, tcd, nbytes); + edma_cp_tcd_to_reg(fsl_chan, tcd, slast); - edma_write_tcdreg(fsl_chan, tcd->citer, citer); - edma_write_tcdreg(fsl_chan, tcd->biter, biter); - edma_write_tcdreg(fsl_chan, tcd->doff, doff); + edma_cp_tcd_to_reg(fsl_chan, tcd, citer); + edma_cp_tcd_to_reg(fsl_chan, tcd, biter); + edma_cp_tcd_to_reg(fsl_chan, tcd, doff); - edma_write_tcdreg(fsl_chan, tcd->dlast_sga, dlast_sga); + edma_cp_tcd_to_reg(fsl_chan, tcd, dlast_sga); - csr = le16_to_cpu(tcd->csr); + csr = fsl_edma_get_tcd_to_cpu(fsl_chan, tcd, csr); if (fsl_chan->is_sw) { csr |= EDMA_TCD_CSR_START; - tcd->csr = cpu_to_le16(csr); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, csr, csr); } /* @@ -473,7 +473,7 @@ static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan, edma_writel_chreg(fsl_chan, edma_readl_chreg(fsl_chan, ch_csr), ch_csr); - edma_write_tcdreg(fsl_chan, tcd->csr, csr); + edma_cp_tcd_to_reg(fsl_chan, tcd, csr); } static inline @@ -493,12 +493,12 @@ void fsl_edma_fill_tcd(struct fsl_edma_chan *fsl_chan, * So we put the value in little endian in memory, waiting * for fsl_edma_set_tcd_regs doing the swap. */ - tcd->saddr = cpu_to_le32(src); - tcd->daddr = cpu_to_le32(dst); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, src, saddr); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, dst, daddr); - tcd->attr = cpu_to_le16(attr); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, attr, attr); - tcd->soff = cpu_to_le16(soff); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, soff, soff); if (fsl_chan->is_multi_fifo) { /* set mloff to support multiple fifo */ @@ -515,15 +515,16 @@ void fsl_edma_fill_tcd(struct fsl_edma_chan *fsl_chan, } } - tcd->nbytes = cpu_to_le32(nbytes); - tcd->slast = cpu_to_le32(slast); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, nbytes, nbytes); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, slast, slast); - tcd->citer = cpu_to_le16(EDMA_TCD_CITER_CITER(citer)); - tcd->doff = cpu_to_le16(doff); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, EDMA_TCD_CITER_CITER(citer), citer); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, doff, doff); - tcd->dlast_sga = cpu_to_le32(dlast_sga); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, dlast_sga, dlast_sga); + + fsl_edma_set_tcd_to_le(fsl_chan, tcd, EDMA_TCD_BITER_BITER(biter), biter); - tcd->biter = cpu_to_le16(EDMA_TCD_BITER_BITER(biter)); if (major_int) csr |= EDMA_TCD_CSR_INT_MAJOR; @@ -539,7 +540,7 @@ void fsl_edma_fill_tcd(struct fsl_edma_chan *fsl_chan, if (fsl_chan->is_sw) csr |= EDMA_TCD_CSR_START; - tcd->csr = cpu_to_le16(csr); + fsl_edma_set_tcd_to_le(fsl_chan, tcd, csr, csr); } static struct fsl_edma_desc *fsl_edma_alloc_desc(struct fsl_edma_chan *fsl_chan, diff --git a/drivers/dma/fsl-edma-common.h b/drivers/dma/fsl-edma-common.h index bb5221158a77..ce779274d81e 100644 --- a/drivers/dma/fsl-edma-common.h +++ b/drivers/dma/fsl-edma-common.h @@ -238,6 +238,9 @@ struct fsl_edma_engine { edma_writel(chan->edma, (u32 __force)val, &chan->tcd->__name) : \ edma_writew(chan->edma, (u16 __force)val, &chan->tcd->__name)) +#define edma_cp_tcd_to_reg(chan, __tcd, __name) \ + edma_write_tcdreg(chan, __tcd->__name, __name) + #define edma_readl_chreg(chan, __name) \ edma_readl(chan->edma, \ (void __iomem *)&(container_of(chan->tcd, struct fsl_edma3_ch_reg, tcd)->__name)) @@ -246,6 +249,26 @@ struct fsl_edma_engine { edma_writel(chan->edma, val, \ (void __iomem *)&(container_of(chan->tcd, struct fsl_edma3_ch_reg, tcd)->__name)) +#define fsl_edma_get_tcd(_chan, _tcd, _field) ((_tcd)->_field) + +#define fsl_edma_le_to_cpu(x) \ +(sizeof(x) == sizeof(u32) ? le32_to_cpu((__force __le32)(x)) : le16_to_cpu((__force __le16)(x))) + +#define fsl_edma_get_tcd_to_cpu(_chan, _tcd, _field) \ +fsl_edma_le_to_cpu(fsl_edma_get_tcd(_chan, _tcd, _field)) + +#define fsl_edma_set_tcd_to_le(_fsl_chan, _tcd, _val, _field) \ +do { \ + switch (sizeof((_tcd)->_field)) { \ + case sizeof(u32): \ + *(__force __le32 *)(&((_tcd)->_field)) = cpu_to_le32(_val); \ + break; \ + case sizeof(u16): \ + *(__force __le16 *)(&((_tcd)->_field)) = cpu_to_le16(_val); \ + break; \ + } \ +} while (0) + /* * R/W functions for big- or little-endian registers: * The eDMA controller's endian is independent of the CPU core's endian. -- cgit v1.2.3 From 537df9ab2d72bb782926a7d263a9f0a101e60b2e Mon Sep 17 00:00:00 2001 From: Frank Li Date: Thu, 21 Dec 2023 10:35:24 -0500 Subject: dmaengine: fsl-edma: fix spare build warning ../drivers/dma/fsl-edma-common.c:93:9: sparse: warning: cast removes address space '__iomem' of expression ../drivers/dma/fsl-edma-common.c:101:25: sparse: warning: cast removes address space '__iomem' of expression ... ../drivers/dma/fsl-edma-main.c:557:17: sparse: got restricted __le32 [usertype] Signed-off-by: Frank Li Link: https://lore.kernel.org/r/20231221153528.1588049-3-Frank.Li@nxp.com Signed-off-by: Vinod Koul --- drivers/dma/fsl-edma-common.h | 6 ++++-- drivers/dma/fsl-edma-main.c | 2 +- 2 files changed, 5 insertions(+), 3 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/fsl-edma-common.h b/drivers/dma/fsl-edma-common.h index ce779274d81e..fb45c7d4c1f4 100644 --- a/drivers/dma/fsl-edma-common.h +++ b/drivers/dma/fsl-edma-common.h @@ -243,11 +243,13 @@ struct fsl_edma_engine { #define edma_readl_chreg(chan, __name) \ edma_readl(chan->edma, \ - (void __iomem *)&(container_of(chan->tcd, struct fsl_edma3_ch_reg, tcd)->__name)) + (void __iomem *)&(container_of(((__force void *)chan->tcd),\ + struct fsl_edma3_ch_reg, tcd)->__name)) #define edma_writel_chreg(chan, val, __name) \ edma_writel(chan->edma, val, \ - (void __iomem *)&(container_of(chan->tcd, struct fsl_edma3_ch_reg, tcd)->__name)) + (void __iomem *)&(container_of(((__force void *)chan->tcd),\ + struct fsl_edma3_ch_reg, tcd)->__name)) #define fsl_edma_get_tcd(_chan, _tcd, _field) ((_tcd)->_field) diff --git a/drivers/dma/fsl-edma-main.c b/drivers/dma/fsl-edma-main.c index 45cc419b1b4a..df3af5762adc 100644 --- a/drivers/dma/fsl-edma-main.c +++ b/drivers/dma/fsl-edma-main.c @@ -536,7 +536,7 @@ static int fsl_edma_probe(struct platform_device *pdev) fsl_chan->pdev = pdev; vchan_init(&fsl_chan->vchan, &fsl_edma->dma_dev); - edma_write_tcdreg(fsl_chan, 0, csr); + edma_write_tcdreg(fsl_chan, cpu_to_le32(0), csr); fsl_edma_chan_mux(fsl_chan, 0, false); } -- cgit v1.2.3 From e0a08ed25492b6437e366b347113db484037b9b9 Mon Sep 17 00:00:00 2001 From: Frank Li Date: Thu, 21 Dec 2023 10:35:25 -0500 Subject: dmaengine: fsl-edma: add address for channel mux register in fsl_edma_chan iMX95 move channel mux register to management page address space. This prepare to support iMX95. Add mux_addr in struct fsl_edma_chan. No function change. Signed-off-by: Frank Li Link: https://lore.kernel.org/r/20231221153528.1588049-4-Frank.Li@nxp.com Signed-off-by: Vinod Koul --- drivers/dma/fsl-edma-common.c | 6 +++--- drivers/dma/fsl-edma-common.h | 3 +++ drivers/dma/fsl-edma-main.c | 3 +++ 3 files changed, 9 insertions(+), 3 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/fsl-edma-common.c b/drivers/dma/fsl-edma-common.c index 50f55d7566a3..65f466ab9d4d 100644 --- a/drivers/dma/fsl-edma-common.c +++ b/drivers/dma/fsl-edma-common.c @@ -97,8 +97,8 @@ static void fsl_edma3_enable_request(struct fsl_edma_chan *fsl_chan) * ch_mux: With the exception of 0, attempts to write a value * already in use will be forced to 0. */ - if (!edma_readl_chreg(fsl_chan, ch_mux)) - edma_writel_chreg(fsl_chan, fsl_chan->srcid, ch_mux); + if (!edma_readl(fsl_chan->edma, fsl_chan->mux_addr)) + edma_writel(fsl_chan->edma, fsl_chan->srcid, fsl_chan->mux_addr); } val = edma_readl_chreg(fsl_chan, ch_csr); @@ -134,7 +134,7 @@ static void fsl_edma3_disable_request(struct fsl_edma_chan *fsl_chan) flags = fsl_edma_drvflags(fsl_chan); if (flags & FSL_EDMA_DRV_HAS_CHMUX) - edma_writel_chreg(fsl_chan, 0, ch_mux); + edma_writel(fsl_chan->edma, 0, fsl_chan->mux_addr); val &= ~EDMA_V3_CH_CSR_ERQ; edma_writel_chreg(fsl_chan, val, ch_csr); diff --git a/drivers/dma/fsl-edma-common.h b/drivers/dma/fsl-edma-common.h index fb45c7d4c1f4..4f39a548547a 100644 --- a/drivers/dma/fsl-edma-common.h +++ b/drivers/dma/fsl-edma-common.h @@ -145,6 +145,7 @@ struct fsl_edma_chan { enum dma_data_direction dma_dir; char chan_name[32]; struct fsl_edma_hw_tcd __iomem *tcd; + void __iomem *mux_addr; u32 real_count; struct work_struct issue_worker; struct platform_device *pdev; @@ -206,6 +207,8 @@ struct fsl_edma_drvdata { u32 chreg_off; u32 chreg_space_sz; u32 flags; + u32 mux_off; /* channel mux register offset */ + u32 mux_skip; /* how much skip for each channel */ int (*setup_irq)(struct platform_device *pdev, struct fsl_edma_engine *fsl_edma); }; diff --git a/drivers/dma/fsl-edma-main.c b/drivers/dma/fsl-edma-main.c index df3af5762adc..bbdf8ff72f65 100644 --- a/drivers/dma/fsl-edma-main.c +++ b/drivers/dma/fsl-edma-main.c @@ -359,6 +359,8 @@ static struct fsl_edma_drvdata imx93_data4 = { .flags = FSL_EDMA_DRV_HAS_CHMUX | FSL_EDMA_DRV_HAS_DMACLK | FSL_EDMA_DRV_EDMA4, .chreg_space_sz = 0x8000, .chreg_off = 0x10000, + .mux_off = 0x10000 + offsetof(struct fsl_edma3_ch_reg, ch_mux), + .mux_skip = 0x8000, .setup_irq = fsl_edma3_irq_init, }; @@ -532,6 +534,7 @@ static int fsl_edma_probe(struct platform_device *pdev) offsetof(struct fsl_edma3_ch_reg, tcd) : 0; fsl_chan->tcd = fsl_edma->membase + i * drvdata->chreg_space_sz + drvdata->chreg_off + len; + fsl_chan->mux_addr = fsl_edma->membase + drvdata->mux_off + i * drvdata->mux_skip; fsl_chan->pdev = pdev; vchan_init(&fsl_chan->vchan, &fsl_edma->dma_dev); -- cgit v1.2.3 From b51dd7c8aac292396d038d0a9fb9c1589addb515 Mon Sep 17 00:00:00 2001 From: Frank Li Date: Thu, 21 Dec 2023 10:35:26 -0500 Subject: dmaengine: mcf-edma: utilize edma_write_tcdreg() macro for TCD Access The TCD structure has undergone modifications, incorporating fields extended to 64 bits. When TCD64 is enabled, the TCD type shifts to 'void *'. Use of the edma_write_tcdreg() macro to facilitate TCD register access. Add cpu_to_le32(0) to ensure little-endian compatibility with TCD registers and avoid a build warning. Signed-off-by: Frank Li Link: https://lore.kernel.org/r/20231221153528.1588049-5-Frank.Li@nxp.com Signed-off-by: Vinod Koul --- drivers/dma/mcf-edma-main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/dma/mcf-edma-main.c b/drivers/dma/mcf-edma-main.c index ab21455d9c3a..dba631783876 100644 --- a/drivers/dma/mcf-edma-main.c +++ b/drivers/dma/mcf-edma-main.c @@ -202,7 +202,7 @@ static int mcf_edma_probe(struct platform_device *pdev) vchan_init(&mcf_chan->vchan, &mcf_edma->dma_dev); mcf_chan->tcd = mcf_edma->membase + EDMA_TCD + i * sizeof(struct fsl_edma_hw_tcd); - iowrite32(0x0, &mcf_chan->tcd->csr); + edma_write_tcdreg(mcf_chan, cpu_to_le32(0), csr); } iowrite32(~0, regs->inth); -- cgit v1.2.3 From de7d9cb3b064fdfb2e0e7706d14ffee20b762ad2 Mon Sep 17 00:00:00 2001 From: Frank Li Date: Thu, 21 Dec 2023 10:35:28 -0500 Subject: dmaengine: fsl-edma: integrate TCD64 support for i.MX95 In i.MX95's edma version 5, the TCD structure is extended to support 64-bit addresses for fields like saddr and daddr. To prevent code duplication, employ help macros to handle the fields, as the field names remain the same between TCD and TCD64. Change local variables related to TCD addresses from 'u32' to 'dma_addr_t' to accept 64-bit DMA addresses. Change 'vtcd' type to 'void *' to avoid direct use. Use helper macros to access the TCD fields correctly. Call 'dma_set_mask_and_coherent(64)' when TCD64 is supported. Signed-off-by: Frank Li Link: https://lore.kernel.org/r/20231221153528.1588049-7-Frank.Li@nxp.com Signed-off-by: Vinod Koul --- drivers/dma/fsl-edma-common.c | 34 +++++---- drivers/dma/fsl-edma-common.h | 165 ++++++++++++++++++++++++++++++++++-------- drivers/dma/fsl-edma-main.c | 14 ++++ 3 files changed, 170 insertions(+), 43 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/fsl-edma-common.c b/drivers/dma/fsl-edma-common.c index 65f466ab9d4d..c8acff09308f 100644 --- a/drivers/dma/fsl-edma-common.c +++ b/drivers/dma/fsl-edma-common.c @@ -351,7 +351,7 @@ static size_t fsl_edma_desc_residue(struct fsl_edma_chan *fsl_chan, { struct fsl_edma_desc *edesc = fsl_chan->edesc; enum dma_transfer_direction dir = edesc->dirn; - dma_addr_t cur_addr, dma_addr; + dma_addr_t cur_addr, dma_addr, old_addr; size_t len, size; u32 nbytes = 0; int i; @@ -367,10 +367,16 @@ static size_t fsl_edma_desc_residue(struct fsl_edma_chan *fsl_chan, if (!in_progress) return len; - if (dir == DMA_MEM_TO_DEV) - cur_addr = edma_read_tcdreg(fsl_chan, saddr); - else - cur_addr = edma_read_tcdreg(fsl_chan, daddr); + /* 64bit read is not atomic, need read retry when high 32bit changed */ + do { + if (dir == DMA_MEM_TO_DEV) { + old_addr = edma_read_tcdreg(fsl_chan, saddr); + cur_addr = edma_read_tcdreg(fsl_chan, saddr); + } else { + old_addr = edma_read_tcdreg(fsl_chan, daddr); + cur_addr = edma_read_tcdreg(fsl_chan, daddr); + } + } while (upper_32_bits(cur_addr) != upper_32_bits(old_addr)); /* figure out the finished and calculate the residue */ for (i = 0; i < fsl_chan->edesc->n_tcds; i++) { @@ -426,8 +432,7 @@ enum dma_status fsl_edma_tx_status(struct dma_chan *chan, return fsl_chan->status; } -static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan, - struct fsl_edma_hw_tcd *tcd) +static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan, void *tcd) { u16 csr = 0; @@ -478,9 +483,9 @@ static void fsl_edma_set_tcd_regs(struct fsl_edma_chan *fsl_chan, static inline void fsl_edma_fill_tcd(struct fsl_edma_chan *fsl_chan, - struct fsl_edma_hw_tcd *tcd, u32 src, u32 dst, - u16 attr, u16 soff, u32 nbytes, u32 slast, u16 citer, - u16 biter, u16 doff, u32 dlast_sga, bool major_int, + struct fsl_edma_hw_tcd *tcd, dma_addr_t src, dma_addr_t dst, + u16 attr, u16 soff, u32 nbytes, dma_addr_t slast, u16 citer, + u16 biter, u16 doff, dma_addr_t dlast_sga, bool major_int, bool disable_req, bool enable_sg) { struct dma_slave_config *cfg = &fsl_chan->cfg; @@ -581,8 +586,9 @@ struct dma_async_tx_descriptor *fsl_edma_prep_dma_cyclic( dma_addr_t dma_buf_next; bool major_int = true; int sg_len, i; - u32 src_addr, dst_addr, last_sg, nbytes; + dma_addr_t src_addr, dst_addr, last_sg; u16 soff, doff, iter; + u32 nbytes; if (!is_slave_direction(direction)) return NULL; @@ -654,8 +660,9 @@ struct dma_async_tx_descriptor *fsl_edma_prep_slave_sg( struct fsl_edma_chan *fsl_chan = to_fsl_edma_chan(chan); struct fsl_edma_desc *fsl_desc; struct scatterlist *sg; - u32 src_addr, dst_addr, last_sg, nbytes; + dma_addr_t src_addr, dst_addr, last_sg; u16 soff, doff, iter; + u32 nbytes; int i; if (!is_slave_direction(direction)) @@ -804,7 +811,8 @@ int fsl_edma_alloc_chan_resources(struct dma_chan *chan) struct fsl_edma_chan *fsl_chan = to_fsl_edma_chan(chan); fsl_chan->tcd_pool = dma_pool_create("tcd_pool", chan->device->dev, - sizeof(struct fsl_edma_hw_tcd), + fsl_edma_drvflags(fsl_chan) & FSL_EDMA_DRV_TCD64 ? + sizeof(struct fsl_edma_hw_tcd64) : sizeof(struct fsl_edma_hw_tcd), 32, 0); return 0; } diff --git a/drivers/dma/fsl-edma-common.h b/drivers/dma/fsl-edma-common.h index 4f39a548547a..a05a1f283ece 100644 --- a/drivers/dma/fsl-edma-common.h +++ b/drivers/dma/fsl-edma-common.h @@ -87,6 +87,20 @@ struct fsl_edma_hw_tcd { __le16 biter; }; +struct fsl_edma_hw_tcd64 { + __le64 saddr; + __le16 soff; + __le16 attr; + __le32 nbytes; + __le64 slast; + __le64 daddr; + __le64 dlast_sga; + __le16 doff; + __le16 citer; + __le16 csr; + __le16 biter; +} __packed; + struct fsl_edma3_ch_reg { __le32 ch_csr; __le32 ch_es; @@ -96,7 +110,10 @@ struct fsl_edma3_ch_reg { __le32 ch_mux; __le32 ch_mattr; /* edma4, reserved for edma3 */ __le32 ch_reserved; - struct fsl_edma_hw_tcd tcd; + union { + struct fsl_edma_hw_tcd tcd; + struct fsl_edma_hw_tcd64 tcd64; + }; } __packed; /* @@ -125,7 +142,7 @@ struct edma_regs { struct fsl_edma_sw_tcd { dma_addr_t ptcd; - struct fsl_edma_hw_tcd *vtcd; + void *vtcd; }; struct fsl_edma_chan { @@ -144,7 +161,7 @@ struct fsl_edma_chan { u32 dma_dev_size; enum dma_data_direction dma_dir; char chan_name[32]; - struct fsl_edma_hw_tcd __iomem *tcd; + void __iomem *tcd; void __iomem *mux_addr; u32 real_count; struct work_struct issue_worker; @@ -188,6 +205,7 @@ struct fsl_edma_desc { #define FSL_EDMA_DRV_CLEAR_DONE_E_SG BIT(13) /* Need clean CHn_CSR DONE before enable TCD's MAJORELINK */ #define FSL_EDMA_DRV_CLEAR_DONE_E_LINK BIT(14) +#define FSL_EDMA_DRV_TCD64 BIT(15) #define FSL_EDMA_DRV_EDMA3 (FSL_EDMA_DRV_SPLIT_REG | \ FSL_EDMA_DRV_BUS_8BYTE | \ @@ -231,18 +249,61 @@ struct fsl_edma_engine { struct fsl_edma_chan chans[] __counted_by(n_chans); }; -#define edma_read_tcdreg(chan, __name) \ -(sizeof(chan->tcd->__name) == sizeof(u32) ? \ - edma_readl(chan->edma, &chan->tcd->__name) : \ - edma_readw(chan->edma, &chan->tcd->__name)) +#define edma_read_tcdreg_c(chan, _tcd, __name) \ +(sizeof((_tcd)->__name) == sizeof(u64) ? \ + edma_readq(chan->edma, &(_tcd)->__name) : \ + ((sizeof((_tcd)->__name) == sizeof(u32)) ? \ + edma_readl(chan->edma, &(_tcd)->__name) : \ + edma_readw(chan->edma, &(_tcd)->__name) \ + )) + +#define edma_read_tcdreg(chan, __name) \ +((fsl_edma_drvflags(chan) & FSL_EDMA_DRV_TCD64) ? \ + edma_read_tcdreg_c(chan, ((struct fsl_edma_hw_tcd64 __iomem *)chan->tcd), __name) : \ + edma_read_tcdreg_c(chan, ((struct fsl_edma_hw_tcd __iomem *)chan->tcd), __name) \ +) + +#define edma_write_tcdreg_c(chan, _tcd, _val, __name) \ +do { \ + switch (sizeof(_tcd->__name)) { \ + case sizeof(u64): \ + edma_writeq(chan->edma, (u64 __force)_val, &_tcd->__name); \ + break; \ + case sizeof(u32): \ + edma_writel(chan->edma, (u32 __force)_val, &_tcd->__name); \ + break; \ + case sizeof(u16): \ + edma_writew(chan->edma, (u16 __force)_val, &_tcd->__name); \ + break; \ + case sizeof(u8): \ + edma_writeb(chan->edma, (u8 __force)_val, &_tcd->__name); \ + break; \ + } \ +} while (0) -#define edma_write_tcdreg(chan, val, __name) \ -(sizeof(chan->tcd->__name) == sizeof(u32) ? \ - edma_writel(chan->edma, (u32 __force)val, &chan->tcd->__name) : \ - edma_writew(chan->edma, (u16 __force)val, &chan->tcd->__name)) +#define edma_write_tcdreg(chan, val, __name) \ +do { \ + struct fsl_edma_hw_tcd64 __iomem *tcd64_r = (struct fsl_edma_hw_tcd64 __iomem *)chan->tcd; \ + struct fsl_edma_hw_tcd __iomem *tcd_r = (struct fsl_edma_hw_tcd __iomem *)chan->tcd; \ + \ + if (fsl_edma_drvflags(chan) & FSL_EDMA_DRV_TCD64) \ + edma_write_tcdreg_c(chan, tcd64_r, val, __name); \ + else \ + edma_write_tcdreg_c(chan, tcd_r, val, __name); \ +} while (0) -#define edma_cp_tcd_to_reg(chan, __tcd, __name) \ - edma_write_tcdreg(chan, __tcd->__name, __name) +#define edma_cp_tcd_to_reg(chan, __tcd, __name) \ +do { \ + struct fsl_edma_hw_tcd64 __iomem *tcd64_r = (struct fsl_edma_hw_tcd64 __iomem *)chan->tcd; \ + struct fsl_edma_hw_tcd __iomem *tcd_r = (struct fsl_edma_hw_tcd __iomem *)chan->tcd; \ + struct fsl_edma_hw_tcd64 *tcd64_m = (struct fsl_edma_hw_tcd64 *)__tcd; \ + struct fsl_edma_hw_tcd *tcd_m = (struct fsl_edma_hw_tcd *)__tcd; \ + \ + if (fsl_edma_drvflags(chan) & FSL_EDMA_DRV_TCD64) \ + edma_write_tcdreg_c(chan, tcd64_r, tcd64_m->__name, __name); \ + else \ + edma_write_tcdreg_c(chan, tcd_r, tcd_m->__name, __name); \ +} while (0) #define edma_readl_chreg(chan, __name) \ edma_readl(chan->edma, \ @@ -254,24 +315,41 @@ struct fsl_edma_engine { (void __iomem *)&(container_of(((__force void *)chan->tcd),\ struct fsl_edma3_ch_reg, tcd)->__name)) -#define fsl_edma_get_tcd(_chan, _tcd, _field) ((_tcd)->_field) - -#define fsl_edma_le_to_cpu(x) \ -(sizeof(x) == sizeof(u32) ? le32_to_cpu((__force __le32)(x)) : le16_to_cpu((__force __le16)(x))) - -#define fsl_edma_get_tcd_to_cpu(_chan, _tcd, _field) \ -fsl_edma_le_to_cpu(fsl_edma_get_tcd(_chan, _tcd, _field)) +#define fsl_edma_get_tcd(_chan, _tcd, _field) \ +(fsl_edma_drvflags(_chan) & FSL_EDMA_DRV_TCD64 ? (((struct fsl_edma_hw_tcd64 *)_tcd)->_field) : \ + (((struct fsl_edma_hw_tcd *)_tcd)->_field)) + +#define fsl_edma_le_to_cpu(x) \ +(sizeof(x) == sizeof(u64) ? le64_to_cpu((__force __le64)(x)) : \ + (sizeof(x) == sizeof(u32) ? le32_to_cpu((__force __le32)(x)) : \ + le16_to_cpu((__force __le16)(x)))) + +#define fsl_edma_get_tcd_to_cpu(_chan, _tcd, _field) \ +(fsl_edma_drvflags(_chan) & FSL_EDMA_DRV_TCD64 ? \ + fsl_edma_le_to_cpu(((struct fsl_edma_hw_tcd64 *)_tcd)->_field) : \ + fsl_edma_le_to_cpu(((struct fsl_edma_hw_tcd *)_tcd)->_field)) + +#define fsl_edma_set_tcd_to_le_c(_tcd, _val, _field) \ +do { \ + switch (sizeof((_tcd)->_field)) { \ + case sizeof(u64): \ + *(__force __le64 *)(&((_tcd)->_field)) = cpu_to_le64(_val); \ + break; \ + case sizeof(u32): \ + *(__force __le32 *)(&((_tcd)->_field)) = cpu_to_le32(_val); \ + break; \ + case sizeof(u16): \ + *(__force __le16 *)(&((_tcd)->_field)) = cpu_to_le16(_val); \ + break; \ + } \ +} while (0) -#define fsl_edma_set_tcd_to_le(_fsl_chan, _tcd, _val, _field) \ -do { \ - switch (sizeof((_tcd)->_field)) { \ - case sizeof(u32): \ - *(__force __le32 *)(&((_tcd)->_field)) = cpu_to_le32(_val); \ - break; \ - case sizeof(u16): \ - *(__force __le16 *)(&((_tcd)->_field)) = cpu_to_le16(_val); \ - break; \ - } \ +#define fsl_edma_set_tcd_to_le(_chan, _tcd, _val, _field) \ +do { \ + if (fsl_edma_drvflags(_chan) & FSL_EDMA_DRV_TCD64) \ + fsl_edma_set_tcd_to_le_c((struct fsl_edma_hw_tcd64 *)_tcd, _val, _field); \ + else \ + fsl_edma_set_tcd_to_le_c((struct fsl_edma_hw_tcd *)_tcd, _val, _field); \ } while (0) /* @@ -280,6 +358,21 @@ do { \ * For the big-endian IP module, the offset for 8-bit or 16-bit registers * should also be swapped opposite to that in little-endian IP. */ +static inline u64 edma_readq(struct fsl_edma_engine *edma, void __iomem *addr) +{ + u64 l, h; + + if (edma->big_endian) { + l = ioread32be(addr); + h = ioread32be(addr + 4); + } else { + l = ioread32(addr); + h = ioread32(addr + 4); + } + + return (h << 32) | l; +} + static inline u32 edma_readl(struct fsl_edma_engine *edma, void __iomem *addr) { if (edma->big_endian) @@ -325,6 +418,18 @@ static inline void edma_writel(struct fsl_edma_engine *edma, iowrite32(val, addr); } +static inline void edma_writeq(struct fsl_edma_engine *edma, + u64 val, void __iomem *addr) +{ + if (edma->big_endian) { + iowrite32be(val & 0xFFFFFFFF, addr); + iowrite32be(val >> 32, addr + 4); + } else { + iowrite32(val & 0xFFFFFFFF, addr); + iowrite32(val >> 32, addr + 4); + } +} + static inline struct fsl_edma_chan *to_fsl_edma_chan(struct dma_chan *chan) { return container_of(chan, struct fsl_edma_chan, vchan.chan); diff --git a/drivers/dma/fsl-edma-main.c b/drivers/dma/fsl-edma-main.c index bbdf8ff72f65..8fff86c16614 100644 --- a/drivers/dma/fsl-edma-main.c +++ b/drivers/dma/fsl-edma-main.c @@ -364,6 +364,16 @@ static struct fsl_edma_drvdata imx93_data4 = { .setup_irq = fsl_edma3_irq_init, }; +static struct fsl_edma_drvdata imx95_data5 = { + .flags = FSL_EDMA_DRV_HAS_CHMUX | FSL_EDMA_DRV_HAS_DMACLK | FSL_EDMA_DRV_EDMA4 | + FSL_EDMA_DRV_TCD64, + .chreg_space_sz = 0x8000, + .chreg_off = 0x10000, + .mux_off = 0x200, + .mux_skip = sizeof(u32), + .setup_irq = fsl_edma3_irq_init, +}; + static const struct of_device_id fsl_edma_dt_ids[] = { { .compatible = "fsl,vf610-edma", .data = &vf610_data}, { .compatible = "fsl,ls1028a-edma", .data = &ls1028a_data}, @@ -372,6 +382,7 @@ static const struct of_device_id fsl_edma_dt_ids[] = { { .compatible = "fsl,imx8qm-adma", .data = &imx8qm_audio_data}, { .compatible = "fsl,imx93-edma3", .data = &imx93_data3}, { .compatible = "fsl,imx93-edma4", .data = &imx93_data4}, + { .compatible = "fsl,imx95-edma5", .data = &imx95_data5}, { /* sentinel */ } }; MODULE_DEVICE_TABLE(of, fsl_edma_dt_ids); @@ -512,6 +523,9 @@ static int fsl_edma_probe(struct platform_device *pdev) return ret; } + if (drvdata->flags & FSL_EDMA_DRV_TCD64) + dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(64)); + INIT_LIST_HEAD(&fsl_edma->dma_dev.channels); for (i = 0; i < fsl_edma->n_chans; i++) { struct fsl_edma_chan *fsl_chan = &fsl_edma->chans[i]; -- cgit v1.2.3 From cf497f3585f944ff42cc2c84453569f37a1bd6b9 Mon Sep 17 00:00:00 2001 From: "Ricardo B. Marliere" Date: Tue, 13 Feb 2024 11:43:15 -0300 Subject: dmaengine: idxd: make dsa_bus_type const Since commit d492cc2573a0 ("driver core: device.h: make struct bus_type a const *"), the driver core can properly handle constant struct bus_type, move the dsa_bus_type variable to be a constant structure as well, placing it into read-only memory which can not be modified at runtime. Cc: Greg Kroah-Hartman Suggested-by: Greg Kroah-Hartman Signed-off-by: "Ricardo B. Marliere" Reviewed-by: Dave Jiang Reviewed-by: Fenghua Yu Reviewed-by: Greg Kroah-Hartman Link: https://lore.kernel.org/r/20240213-bus_cleanup-idxd-v1-1-c3e703675387@marliere.net Signed-off-by: Vinod Koul --- drivers/dma/idxd/bus.c | 2 +- drivers/dma/idxd/idxd.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/idxd/bus.c b/drivers/dma/idxd/bus.c index 0c9e689a2e77..b83b27e04f2a 100644 --- a/drivers/dma/idxd/bus.c +++ b/drivers/dma/idxd/bus.c @@ -72,7 +72,7 @@ static int idxd_bus_uevent(const struct device *dev, struct kobj_uevent_env *env return add_uevent_var(env, "MODALIAS=" IDXD_DEVICES_MODALIAS_FMT, 0); } -struct bus_type dsa_bus_type = { +const struct bus_type dsa_bus_type = { .name = "dsa", .match = idxd_config_bus_match, .probe = idxd_config_bus_probe, diff --git a/drivers/dma/idxd/idxd.h b/drivers/dma/idxd/idxd.h index 47de3f93ff1e..f14a660a2a34 100644 --- a/drivers/dma/idxd/idxd.h +++ b/drivers/dma/idxd/idxd.h @@ -516,7 +516,7 @@ static inline void idxd_set_user_intr(struct idxd_device *idxd, bool enable) iowrite32(reg.bits, idxd->reg_base + IDXD_GENCFG_OFFSET); } -extern struct bus_type dsa_bus_type; +extern const struct bus_type dsa_bus_type; extern bool support_enqcmd; extern struct ida idxd_ida; -- cgit v1.2.3 From 1e0a2852a134833f6827de15cd62ea0ed19f1b60 Mon Sep 17 00:00:00 2001 From: "Ricardo B. Marliere" Date: Mon, 19 Feb 2024 08:46:56 -0300 Subject: dmaengine: idxd: constify the struct device_type usage Since commit aed65af1cc2f ("drivers: make device_type const"), the driver core can properly handle constant struct device_type. Move the dsa_device_type, iax_device_type, idxd_wq_device_type, idxd_cdev_file_type, idxd_cdev_device_type and idxd_group_device_type variables to be constant structures as well, placing it into read-only memory which can not be modified at runtime. Cc: Greg Kroah-Hartman Signed-off-by: "Ricardo B. Marliere" Reviewed-by: Fenghua Yu Link: https://lore.kernel.org/r/20240219-device_cleanup-dmaengine-v1-1-9f72f3cf3587@marliere.net Signed-off-by: Vinod Koul --- drivers/dma/idxd/cdev.c | 4 ++-- drivers/dma/idxd/idxd.h | 12 ++++++------ drivers/dma/idxd/sysfs.c | 10 +++++----- 3 files changed, 13 insertions(+), 13 deletions(-) (limited to 'drivers') diff --git a/drivers/dma/idxd/cdev.c b/drivers/dma/idxd/cdev.c index 77f8885cf407..72bb982d7af7 100644 --- a/drivers/dma/idxd/cdev.c +++ b/drivers/dma/idxd/cdev.c @@ -152,7 +152,7 @@ static void idxd_file_dev_release(struct device *dev) mutex_unlock(&wq->wq_lock); } -static struct device_type idxd_cdev_file_type = { +static const struct device_type idxd_cdev_file_type = { .name = "idxd_file", .release = idxd_file_dev_release, .groups = cdev_file_attribute_groups, @@ -169,7 +169,7 @@ static void idxd_cdev_dev_release(struct device *dev) kfree(idxd_cdev); } -static struct device_type idxd_cdev_device_type = { +static const struct device_type idxd_cdev_device_type = { .name = "idxd_cdev", .release = idxd_cdev_dev_release, }; diff --git a/drivers/dma/idxd/idxd.h b/drivers/dma/idxd/idxd.h index f14a660a2a34..d8d3611bf79a 100644 --- a/drivers/dma/idxd/idxd.h +++ b/drivers/dma/idxd/idxd.h @@ -282,7 +282,7 @@ typedef int (*load_device_defaults_fn_t) (struct idxd_device *idxd); struct idxd_driver_data { const char *name_prefix; enum idxd_type type; - struct device_type *dev_type; + const struct device_type *dev_type; int compl_size; int align; int evl_cr_off; @@ -520,11 +520,11 @@ extern const struct bus_type dsa_bus_type; extern bool support_enqcmd; extern struct ida idxd_ida; -extern struct device_type dsa_device_type; -extern struct device_type iax_device_type; -extern struct device_type idxd_wq_device_type; -extern struct device_type idxd_engine_device_type; -extern struct device_type idxd_group_device_type; +extern const struct device_type dsa_device_type; +extern const struct device_type iax_device_type; +extern const struct device_type idxd_wq_device_type; +extern const struct device_type idxd_engine_device_type; +extern const struct device_type idxd_group_device_type; static inline bool is_dsa_dev(struct idxd_dev *idxd_dev) { diff --git a/drivers/dma/idxd/sysfs.c b/drivers/dma/idxd/sysfs.c index 523ae0dff7d4..7f28f01be672 100644 --- a/drivers/dma/idxd/sysfs.c +++ b/drivers/dma/idxd/sysfs.c @@ -91,7 +91,7 @@ static void idxd_conf_engine_release(struct device *dev) kfree(engine); } -struct device_type idxd_engine_device_type = { +const struct device_type idxd_engine_device_type = { .name = "engine", .release = idxd_conf_engine_release, .groups = idxd_engine_attribute_groups, @@ -577,7 +577,7 @@ static void idxd_conf_group_release(struct device *dev) kfree(group); } -struct device_type idxd_group_device_type = { +const struct device_type idxd_group_device_type = { .name = "group", .release = idxd_conf_group_release, .groups = idxd_group_attribute_groups, @@ -1369,7 +1369,7 @@ static void idxd_conf_wq_release(struct device *dev) kfree(wq); } -struct device_type idxd_wq_device_type = { +const struct device_type idxd_wq_device_type = { .name = "wq", .release = idxd_conf_wq_release, .groups = idxd_wq_attribute_groups, @@ -1798,13 +1798,13 @@ static void idxd_conf_device_release(struct device *dev) kfree(idxd); } -struct device_type dsa_device_type = { +const struct device_type dsa_device_type = { .name = "dsa", .release = idxd_conf_device_release, .groups = idxd_attribute_groups, }; -struct device_type iax_device_type = { +const struct device_type iax_device_type = { .name = "iax", .release = idxd_conf_device_release, .groups = idxd_attribute_groups, -- cgit v1.2.3 From 16374aba824971d73916f005e79207370c9c31dd Mon Sep 17 00:00:00 2001 From: Krzysztof Kozlowski Date: Thu, 8 Feb 2024 21:27:41 +0100 Subject: dmaengine: pl08x: constify pointer to char in filter function The opaque argument chan_id passed to filter function is actually pointer to const memory, so make that obvious in the filter for code readability and safety. Signed-off-by: Krzysztof Kozlowski Link: https://lore.kernel.org/r/20240208202742.631307-1-krzysztof.kozlowski@linaro.org Signed-off-by: Vinod Koul --- drivers/dma/amba-pl08x.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/dma/amba-pl08x.c b/drivers/dma/amba-pl08x.c index eea8bd33b4b7..fbf048f432bf 100644 --- a/drivers/dma/amba-pl08x.c +++ b/drivers/dma/amba-pl08x.c @@ -2239,7 +2239,7 @@ static int pl08x_resume(struct dma_chan *chan) bool pl08x_filter_id(struct dma_chan *chan, void *chan_id) { struct pl08x_dma_chan *plchan; - char *name = chan_id; + const char *name = chan_id; /* Reject channels for devices not bound to this driver */ if (chan->device->dev->driver != &pl08x_amba_driver.drv) -- cgit v1.2.3 From 716141d366f45d62ffe4dd53a045867b26e29d19 Mon Sep 17 00:00:00 2001 From: Krzysztof Kozlowski Date: Thu, 8 Feb 2024 21:27:42 +0100 Subject: dmaengine: of: constify of_phandle_args in of_dma_find_controller() of_dma_find_controller() does not modify passed of_phandle_args so the argument can be made pointer to const for code safety. Signed-off-by: Krzysztof Kozlowski Link: https://lore.kernel.org/r/20240208202742.631307-2-krzysztof.kozlowski@linaro.org Signed-off-by: Vinod Koul --- drivers/dma/of-dma.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/dma/of-dma.c b/drivers/dma/of-dma.c index 775a7f408b9a..e588fff9f21d 100644 --- a/drivers/dma/of-dma.c +++ b/drivers/dma/of-dma.c @@ -29,7 +29,7 @@ static DEFINE_MUTEX(of_dma_lock); * to the DMA data stored is retuned. A NULL pointer is returned if no match is * found. */ -static struct of_dma *of_dma_find_controller(struct of_phandle_args *dma_spec) +static struct of_dma *of_dma_find_controller(const struct of_phandle_args *dma_spec) { struct of_dma *ofdma; -- cgit v1.2.3