From 34436106af3d00b9cf94dbf7200b8162937f9943 Mon Sep 17 00:00:00 2001 From: Frank Li Date: Fri, 21 Feb 2025 17:21:53 -0500 Subject: [PATCH 01/16] dt-bindings: dma: fsl,edma: Add i.MX94 support Add support for the i.MX94 DMA controllers. The SoC includes two DMA controllers: one compatible with i.MX93 eDMA3 and another compatible with i.MX95 eDMA5. Add compatible string "fsl,imx94-edma3" with fallback to "fsl,imx93-edma3". Add compatible string "fsl,imx94-edma5" with fallback to "fsl,imx95-edma5". Signed-off-by: Frank Li Acked-by: Rob Herring (Arm) Link: https://lore.kernel.org/r/20250221222153.405285-1-Frank.Li@nxp.com Signed-off-by: Vinod Koul --- Documentation/devicetree/bindings/dma/fsl,edma.yaml | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/Documentation/devicetree/bindings/dma/fsl,edma.yaml b/Documentation/devicetree/bindings/dma/fsl,edma.yaml index 4f925469533e..950e8fa4f4ab 100644 --- a/Documentation/devicetree/bindings/dma/fsl,edma.yaml +++ b/Documentation/devicetree/bindings/dma/fsl,edma.yaml @@ -27,6 +27,14 @@ properties: - fsl,imx93-edma4 - fsl,imx95-edma5 - nxp,s32g2-edma + - items: + - enum: + - fsl,imx94-edma3 + - const: fsl,imx93-edma3 + - items: + - enum: + - fsl,imx94-edma5 + - const: fsl,imx95-edma5 - items: - const: fsl,ls1028a-edma - const: fsl,vf610-edma -- 2.51.0 From 95032938c7c9b2e5ebb69f0ee10ebe340fa3af53 Mon Sep 17 00:00:00 2001 From: Stefan Wahren Date: Sat, 22 Feb 2025 10:50:28 +0100 Subject: [PATCH 02/16] dmaengine: bcm2835-dma: fix warning when CONFIG_PM=n The old SET_LATE_SYSTEM_SLEEP_PM_OPS macro cause a build warning when CONFIG_PM is disabled: warning: 'bcm2835_dma_suspend_late' defined but not used [-Wunused-function] Change this to the modern replacement. Reported-by: kernel test robot Closes: https://lore.kernel.org/oe-kbuild-all/202501071533.yrFb156H-lkp@intel.com/ Signed-off-by: Stefan Wahren Reviewed-by: Florian Fainelli Link: https://lore.kernel.org/r/20250222095028.48818-1-wahrenst@gmx.net Signed-off-by: Vinod Koul --- drivers/dma/bcm2835-dma.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/dma/bcm2835-dma.c b/drivers/dma/bcm2835-dma.c index 20b10c15c696..0117bb2e8591 100644 --- a/drivers/dma/bcm2835-dma.c +++ b/drivers/dma/bcm2835-dma.c @@ -893,7 +893,7 @@ static int bcm2835_dma_suspend_late(struct device *dev) } static const struct dev_pm_ops bcm2835_dma_pm_ops = { - SET_LATE_SYSTEM_SLEEP_PM_OPS(bcm2835_dma_suspend_late, NULL) + LATE_SYSTEM_SLEEP_PM_OPS(bcm2835_dma_suspend_late, NULL) }; static int bcm2835_dma_probe(struct platform_device *pdev) -- 2.51.0 From 0da30874729baeb01889b0eca16cfda122687503 Mon Sep 17 00:00:00 2001 From: Roger Quadros Date: Mon, 24 Feb 2025 16:04:17 +0200 Subject: [PATCH 03/16] dmaengine: ti: k3-udma-glue: Drop skip_fdq argument from k3_udma_glue_reset_rx_chn The user of k3_udma_glue_reset_rx_chn() e.g. ti_am65_cpsw_nuss can run on multiple platforms having different DMA architectures. On some platforms there can be one FDQ for all flows in the RX channel while for others there is a separate FDQ for each flow in the RX channel. So far we have been relying on the skip_fdq argument of k3_udma_glue_reset_rx_chn(). Instead of relying on the user to provide this information, infer it based on DMA architecture during k3_udma_glue_request_rx_chn() and save it in an internal flag 'single_fdq'. Use that flag at k3_udma_glue_reset_rx_chn() to deicide if the FDQ needs to be cleared for every flow or just for flow 0. Fixes the below issue on ti_am65_cpsw_nuss driver on AM62-SK. > ip link set eth1 down > ip link set eth0 down > ethtool -L eth0 rx 8 > ip link set eth0 up > modprobe -r ti_am65_cpsw_nuss [ 103.045726] ------------[ cut here ]------------ [ 103.050505] k3_knav_desc_pool size 512000 != avail 64000 [ 103.050703] WARNING: CPU: 1 PID: 450 at drivers/net/ethernet/ti/k3-cppi-desc-pool.c:33 k3_cppi_desc_pool_destroy+0xa0/0xa8 [k3_cppi_desc_pool] [ 103.068810] Modules linked in: ti_am65_cpsw_nuss(-) k3_cppi_desc_pool snd_soc_hdmi_codec crct10dif_ce snd_soc_simple_card snd_soc_simple_card_utils display_connector rtc_ti_k3 k3_j72xx_bandgap tidss drm_client_lib snd_soc_davinci_mcas p drm_dma_helper tps6598x phylink snd_soc_ti_udma rti_wdt drm_display_helper snd_soc_tlv320aic3x_i2c typec at24 phy_gmii_sel snd_soc_ti_edma snd_soc_tlv320aic3x sii902x snd_soc_ti_sdma sa2ul omap_mailbox drm_kms_helper authenc cfg80211 r fkill fuse drm drm_panel_orientation_quirks backlight ip_tables x_tables ipv6 [last unloaded: k3_cppi_desc_pool] [ 103.119950] CPU: 1 UID: 0 PID: 450 Comm: modprobe Not tainted 6.13.0-rc7-00001-g9c5e3435fa66 #1011 [ 103.119968] Hardware name: Texas Instruments AM625 SK (DT) [ 103.119974] pstate: 80000005 (Nzcv daif -PAN -UAO -TCO -DIT -SSBS BTYPE=--) [ 103.119983] pc : k3_cppi_desc_pool_destroy+0xa0/0xa8 [k3_cppi_desc_pool] [ 103.148007] lr : k3_cppi_desc_pool_destroy+0xa0/0xa8 [k3_cppi_desc_pool] [ 103.154709] sp : ffff8000826ebbc0 [ 103.158015] x29: ffff8000826ebbc0 x28: ffff0000090b6300 x27: 0000000000000000 [ 103.165145] x26: 0000000000000000 x25: 0000000000000000 x24: ffff0000019df6b0 [ 103.172271] x23: ffff0000019df6b8 x22: ffff0000019df410 x21: ffff8000826ebc88 [ 103.179397] x20: 000000000007d000 x19: ffff00000a3b3000 x18: 0000000000000000 [ 103.186522] x17: 0000000000000000 x16: 0000000000000000 x15: 000001e8c35e1cde [ 103.193647] x14: 0000000000000396 x13: 000000000000035c x12: 0000000000000000 [ 103.200772] x11: 000000000000003a x10: 00000000000009c0 x9 : ffff8000826eba20 [ 103.207897] x8 : ffff0000090b6d20 x7 : ffff00007728c180 x6 : ffff00007728c100 [ 103.215022] x5 : 0000000000000001 x4 : ffff000000508a50 x3 : ffff7ffff6146000 [ 103.222147] x2 : 0000000000000000 x1 : e300b4173ee6b200 x0 : 0000000000000000 [ 103.229274] Call trace: [ 103.231714] k3_cppi_desc_pool_destroy+0xa0/0xa8 [k3_cppi_desc_pool] (P) [ 103.238408] am65_cpsw_nuss_free_rx_chns+0x28/0x4c [ti_am65_cpsw_nuss] [ 103.244942] devm_action_release+0x14/0x20 [ 103.249040] release_nodes+0x3c/0x68 [ 103.252610] devres_release_all+0x8c/0xdc [ 103.256614] device_unbind_cleanup+0x18/0x60 [ 103.260876] device_release_driver_internal+0xf8/0x178 [ 103.266004] driver_detach+0x50/0x9c [ 103.269571] bus_remove_driver+0x6c/0xbc [ 103.273485] driver_unregister+0x30/0x60 [ 103.277401] platform_driver_unregister+0x14/0x20 [ 103.282096] am65_cpsw_nuss_driver_exit+0x18/0xff4 [ti_am65_cpsw_nuss] [ 103.288620] __arm64_sys_delete_module+0x17c/0x25c [ 103.293404] invoke_syscall+0x44/0x100 [ 103.297149] el0_svc_common.constprop.0+0xc0/0xe0 [ 103.301845] do_el0_svc+0x1c/0x28 [ 103.305155] el0_svc+0x28/0x98 [ 103.308207] el0t_64_sync_handler+0xc8/0xcc [ 103.312384] el0t_64_sync+0x198/0x19c [ 103.316040] ---[ end trace 0000000000000000 ]--- Signed-off-by: Roger Quadros Acked-by: Jakub Kicinski Acked-by: Peter Ujfalusi Link: https://lore.kernel.org/r/20250224-k3-udma-glue-single-fdq-v2-1-cbe7621f2507@kernel.org Signed-off-by: Vinod Koul --- drivers/dma/ti/k3-udma-glue.c | 15 +++++++++++---- drivers/net/ethernet/ti/am65-cpsw-nuss.c | 4 ++-- drivers/net/ethernet/ti/icssg/icssg_common.c | 2 +- include/linux/dma/k3-udma-glue.h | 3 +-- 4 files changed, 15 insertions(+), 9 deletions(-) diff --git a/drivers/dma/ti/k3-udma-glue.c b/drivers/dma/ti/k3-udma-glue.c index 7c224c3ab7a0..f87d244cc2d6 100644 --- a/drivers/dma/ti/k3-udma-glue.c +++ b/drivers/dma/ti/k3-udma-glue.c @@ -84,6 +84,7 @@ struct k3_udma_glue_rx_channel { struct k3_udma_glue_rx_flow *flows; u32 flow_num; u32 flows_ready; + bool single_fdq; /* one FDQ for all flows */ }; static void k3_udma_chan_dev_release(struct device *dev) @@ -970,10 +971,13 @@ k3_udma_glue_request_rx_chn_priv(struct device *dev, const char *name, ep_cfg = rx_chn->common.ep_config; - if (xudma_is_pktdma(rx_chn->common.udmax)) + if (xudma_is_pktdma(rx_chn->common.udmax)) { rx_chn->udma_rchan_id = ep_cfg->mapped_channel_id; - else + rx_chn->single_fdq = false; + } else { rx_chn->udma_rchan_id = -1; + rx_chn->single_fdq = true; + } /* request and cfg UDMAP RX channel */ rx_chn->udma_rchanx = xudma_rchan_get(rx_chn->common.udmax, @@ -1103,6 +1107,9 @@ k3_udma_glue_request_remote_rx_chn_common(struct k3_udma_glue_rx_channel *rx_chn rx_chn->common.chan_dev.dma_coherent = true; dma_coerce_mask_and_coherent(&rx_chn->common.chan_dev, DMA_BIT_MASK(48)); + rx_chn->single_fdq = false; + } else { + rx_chn->single_fdq = true; } ret = k3_udma_glue_allocate_rx_flows(rx_chn, cfg); @@ -1453,7 +1460,7 @@ EXPORT_SYMBOL_GPL(k3_udma_glue_tdown_rx_chn); void k3_udma_glue_reset_rx_chn(struct k3_udma_glue_rx_channel *rx_chn, u32 flow_num, void *data, - void (*cleanup)(void *data, dma_addr_t desc_dma), bool skip_fdq) + void (*cleanup)(void *data, dma_addr_t desc_dma)) { struct k3_udma_glue_rx_flow *flow = &rx_chn->flows[flow_num]; struct device *dev = rx_chn->common.dev; @@ -1465,7 +1472,7 @@ void k3_udma_glue_reset_rx_chn(struct k3_udma_glue_rx_channel *rx_chn, dev_dbg(dev, "RX reset flow %u occ_rx %u\n", flow_num, occ_rx); /* Skip RX FDQ in case one FDQ is used for the set of flows */ - if (skip_fdq) + if (rx_chn->single_fdq && flow_num) goto do_reset; /* diff --git a/drivers/net/ethernet/ti/am65-cpsw-nuss.c b/drivers/net/ethernet/ti/am65-cpsw-nuss.c index b663271e79f7..a1a482ca955f 100644 --- a/drivers/net/ethernet/ti/am65-cpsw-nuss.c +++ b/drivers/net/ethernet/ti/am65-cpsw-nuss.c @@ -515,7 +515,7 @@ static void am65_cpsw_destroy_rxq(struct am65_cpsw_common *common, int id) napi_disable(&flow->napi_rx); hrtimer_cancel(&flow->rx_hrtimer); k3_udma_glue_reset_rx_chn(rx_chn->rx_chn, id, rx_chn, - am65_cpsw_nuss_rx_cleanup, !!id); + am65_cpsw_nuss_rx_cleanup); for (port = 0; port < common->port_num; port++) { if (!common->ports[port].ndev) @@ -3406,7 +3406,7 @@ static int am65_cpsw_nuss_register_ndevs(struct am65_cpsw_common *common) for (i = 0; i < common->rx_ch_num_flows; i++) k3_udma_glue_reset_rx_chn(rx_chan->rx_chn, i, rx_chan, - am65_cpsw_nuss_rx_cleanup, !!i); + am65_cpsw_nuss_rx_cleanup); k3_udma_glue_disable_rx_chn(rx_chan->rx_chn); diff --git a/drivers/net/ethernet/ti/icssg/icssg_common.c b/drivers/net/ethernet/ti/icssg/icssg_common.c index 74f0f200a89d..62065416e886 100644 --- a/drivers/net/ethernet/ti/icssg/icssg_common.c +++ b/drivers/net/ethernet/ti/icssg/icssg_common.c @@ -955,7 +955,7 @@ void prueth_reset_rx_chan(struct prueth_rx_chn *chn, for (i = 0; i < num_flows; i++) k3_udma_glue_reset_rx_chn(chn->rx_chn, i, chn, - prueth_rx_cleanup, !!i); + prueth_rx_cleanup); if (disable) k3_udma_glue_disable_rx_chn(chn->rx_chn); } diff --git a/include/linux/dma/k3-udma-glue.h b/include/linux/dma/k3-udma-glue.h index 2dea217629d0..5d43881e6fb7 100644 --- a/include/linux/dma/k3-udma-glue.h +++ b/include/linux/dma/k3-udma-glue.h @@ -138,8 +138,7 @@ int k3_udma_glue_rx_get_irq(struct k3_udma_glue_rx_channel *rx_chn, u32 flow_num); void k3_udma_glue_reset_rx_chn(struct k3_udma_glue_rx_channel *rx_chn, u32 flow_num, void *data, - void (*cleanup)(void *data, dma_addr_t desc_dma), - bool skip_fdq); + void (*cleanup)(void *data, dma_addr_t desc_dma)); int k3_udma_glue_rx_flow_enable(struct k3_udma_glue_rx_channel *rx_chn, u32 flow_idx); int k3_udma_glue_rx_flow_disable(struct k3_udma_glue_rx_channel *rx_chn, -- 2.51.0 From 6f9669f3634b4e85374676dfdff9181bee14567d Mon Sep 17 00:00:00 2001 From: Thorsten Blum Date: Wed, 19 Feb 2025 11:54:17 +0100 Subject: [PATCH 04/16] dmaengine: Fix typo in comment s/consumer/consume/ Signed-off-by: Thorsten Blum Link: https://lore.kernel.org/r/20250219105419.2025-2-thorsten.blum@linux.dev Signed-off-by: Vinod Koul --- drivers/dma/sh/shdma-base.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/dma/sh/shdma-base.c b/drivers/dma/sh/shdma-base.c index fdd41e1c2263..6b4fce453c85 100644 --- a/drivers/dma/sh/shdma-base.c +++ b/drivers/dma/sh/shdma-base.c @@ -725,7 +725,7 @@ static struct dma_async_tx_descriptor *shdma_prep_dma_cyclic( slave_addr = ops->slave_addr(schan); /* - * Allocate the sg list dynamically as it would consumer too much stack + * Allocate the sg list dynamically as it would consume too much stack * space. */ sgl = kmalloc_array(sg_len, sizeof(*sgl), GFP_KERNEL); -- 2.51.0 From 964c032d1d5d1d896746b361416b84cef078dba5 Mon Sep 17 00:00:00 2001 From: Frank Li Date: Fri, 7 Mar 2025 16:50:59 -0500 Subject: [PATCH 05/16] dt-bindings: dma: fsl-mxs-dma: Add compatible string for i.MX8 chips Add compatible string for all i.MX8 chips, which is backward compatible with i.MX28. Set it to fall back to "fsl,imx28-dma-apbh". Signed-off-by: Frank Li Acked-by: Conor Dooley Link: https://lore.kernel.org/r/20250307215100.3257649-1-Frank.Li@nxp.com Signed-off-by: Vinod Koul --- Documentation/devicetree/bindings/dma/fsl,mxs-dma.yaml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/Documentation/devicetree/bindings/dma/fsl,mxs-dma.yaml b/Documentation/devicetree/bindings/dma/fsl,mxs-dma.yaml index a17cf2360dd4..75a7d9556699 100644 --- a/Documentation/devicetree/bindings/dma/fsl,mxs-dma.yaml +++ b/Documentation/devicetree/bindings/dma/fsl,mxs-dma.yaml @@ -31,6 +31,12 @@ properties: - fsl,imx6q-dma-apbh - fsl,imx6sx-dma-apbh - fsl,imx7d-dma-apbh + - fsl,imx8dxl-dma-apbh + - fsl,imx8mm-dma-apbh + - fsl,imx8mn-dma-apbh + - fsl,imx8mp-dma-apbh + - fsl,imx8mq-dma-apbh + - fsl,imx8qm-dma-apbh - fsl,imx8qxp-dma-apbh - const: fsl,imx28-dma-apbh - enum: -- 2.51.0 From 1fe283e850d6659dc3ccc295c6a0b470dd461047 Mon Sep 17 00:00:00 2001 From: =?utf8?q?J=2E=20Neusch=C3=A4fer?= Date: Sat, 8 Mar 2025 19:33:39 +0100 Subject: [PATCH 06/16] dt-bindings: dma: Convert fsl,elo*-dma to YAML MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit The devicetree bindings for Freescale DMA engines have so far existed as a text file. This patch converts them to YAML, and specifies all the compatible strings currently in use in arch/powerpc/boot/dts. Signed-off-by: J. Neuschäfer Reviewed-by: Rob Herring (Arm) Link: https://lore.kernel.org/r/20250308-ppcyaml-dma-v4-1-20392ea81ec6@posteo.net Signed-off-by: Vinod Koul --- .../devicetree/bindings/dma/fsl,elo-dma.yaml | 137 ++++++++++++ .../devicetree/bindings/dma/fsl,elo3-dma.yaml | 125 +++++++++++ .../bindings/dma/fsl,eloplus-dma.yaml | 132 ++++++++++++ .../devicetree/bindings/powerpc/fsl/dma.txt | 204 ------------------ 4 files changed, 394 insertions(+), 204 deletions(-) create mode 100644 Documentation/devicetree/bindings/dma/fsl,elo-dma.yaml create mode 100644 Documentation/devicetree/bindings/dma/fsl,elo3-dma.yaml create mode 100644 Documentation/devicetree/bindings/dma/fsl,eloplus-dma.yaml delete mode 100644 Documentation/devicetree/bindings/powerpc/fsl/dma.txt diff --git a/Documentation/devicetree/bindings/dma/fsl,elo-dma.yaml b/Documentation/devicetree/bindings/dma/fsl,elo-dma.yaml new file mode 100644 index 000000000000..92288d76d51b --- /dev/null +++ b/Documentation/devicetree/bindings/dma/fsl,elo-dma.yaml @@ -0,0 +1,137 @@ +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/dma/fsl,elo-dma.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Freescale Elo DMA Controller + +maintainers: + - J. Neuschäfer + +description: + This is a little-endian 4-channel DMA controller, used in Freescale mpc83xx + series chips such as mpc8315, mpc8349, mpc8379 etc. + +properties: + compatible: + items: + - enum: + - fsl,mpc8313-dma + - fsl,mpc8315-dma + - fsl,mpc8323-dma + - fsl,mpc8347-dma + - fsl,mpc8349-dma + - fsl,mpc8360-dma + - fsl,mpc8377-dma + - fsl,mpc8378-dma + - fsl,mpc8379-dma + - const: fsl,elo-dma + + reg: + items: + - description: + DMA General Status Register, i.e. DGSR which contains status for + all the 4 DMA channels. + + cell-index: + $ref: /schemas/types.yaml#/definitions/uint32 + description: Controller index. 0 for controller @ 0x8100. + + ranges: true + + "#address-cells": + const: 1 + + "#size-cells": + const: 1 + + interrupts: + maxItems: 1 + description: Controller interrupt. + +required: + - compatible + - reg + +patternProperties: + "^dma-channel@[0-9a-f]+$": + type: object + additionalProperties: false + + properties: + compatible: + oneOf: + # native DMA channel + - items: + - enum: + - fsl,mpc8315-dma-channel + - fsl,mpc8323-dma-channel + - fsl,mpc8347-dma-channel + - fsl,mpc8349-dma-channel + - fsl,mpc8360-dma-channel + - fsl,mpc8377-dma-channel + - fsl,mpc8378-dma-channel + - fsl,mpc8379-dma-channel + - const: fsl,elo-dma-channel + + # audio DMA channel, see fsl,ssi.yaml + - const: fsl,ssi-dma-channel + + reg: + maxItems: 1 + + cell-index: + description: DMA channel index starts at 0. + + interrupts: + maxItems: 1 + description: + Per-channel interrupt. Only necessary if no controller interrupt has + been provided. + +additionalProperties: false + +examples: + - | + #include + + dma@82a8 { + compatible = "fsl,mpc8349-dma", "fsl,elo-dma"; + reg = <0x82a8 4>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x8100 0x1a4>; + interrupts = <71 IRQ_TYPE_LEVEL_LOW>; + cell-index = <0>; + + dma-channel@0 { + compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; + reg = <0 0x80>; + cell-index = <0>; + interrupts = <71 IRQ_TYPE_LEVEL_LOW>; + }; + + dma-channel@80 { + compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; + reg = <0x80 0x80>; + cell-index = <1>; + interrupts = <71 IRQ_TYPE_LEVEL_LOW>; + }; + + dma-channel@100 { + compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; + reg = <0x100 0x80>; + cell-index = <2>; + interrupts = <71 IRQ_TYPE_LEVEL_LOW>; + }; + + dma-channel@180 { + compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; + reg = <0x180 0x80>; + cell-index = <3>; + interrupts = <71 IRQ_TYPE_LEVEL_LOW>; + }; + }; + +... diff --git a/Documentation/devicetree/bindings/dma/fsl,elo3-dma.yaml b/Documentation/devicetree/bindings/dma/fsl,elo3-dma.yaml new file mode 100644 index 000000000000..0f5e475657a7 --- /dev/null +++ b/Documentation/devicetree/bindings/dma/fsl,elo3-dma.yaml @@ -0,0 +1,125 @@ +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/dma/fsl,elo3-dma.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Freescale Elo3 DMA Controller + +maintainers: + - J. Neuschäfer + +description: + DMA controller which has same function as EloPlus except that Elo3 has 8 + channels while EloPlus has only 4, it is used in Freescale Txxx and Bxxx + series chips, such as t1040, t4240, b4860. + +properties: + compatible: + const: fsl,elo3-dma + + reg: + items: + - description: + DMA General Status Registers starting from DGSR0, for channel 1~4 + - description: + DMA General Status Registers starting from DGSR1, for channel 5~8 + + ranges: true + + "#address-cells": + const: 1 + + "#size-cells": + const: 1 + + interrupts: + maxItems: 1 + +patternProperties: + "^dma-channel@[0-9a-f]+$": + type: object + additionalProperties: false + + properties: + compatible: + enum: + # native DMA channel + - fsl,eloplus-dma-channel + + # audio DMA channel, see fsl,ssi.yaml + - fsl,ssi-dma-channel + + reg: + maxItems: 1 + + interrupts: + maxItems: 1 + description: + Per-channel interrupt. Only necessary if no controller interrupt has + been provided. + +additionalProperties: false + +examples: + - | + #include + + dma@100300 { + compatible = "fsl,elo3-dma"; + reg = <0x100300 0x4>, + <0x100600 0x4>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0x0 0x100100 0x500>; + + dma-channel@0 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x0 0x80>; + interrupts = <28 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + + dma-channel@80 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x80 0x80>; + interrupts = <29 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + + dma-channel@100 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x100 0x80>; + interrupts = <30 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + + dma-channel@180 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x180 0x80>; + interrupts = <31 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + + dma-channel@300 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x300 0x80>; + interrupts = <76 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + + dma-channel@380 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x380 0x80>; + interrupts = <77 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + + dma-channel@400 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x400 0x80>; + interrupts = <78 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + + dma-channel@480 { + compatible = "fsl,eloplus-dma-channel"; + reg = <0x480 0x80>; + interrupts = <79 IRQ_TYPE_EDGE_FALLING 0 0>; + }; + }; + +... diff --git a/Documentation/devicetree/bindings/dma/fsl,eloplus-dma.yaml b/Documentation/devicetree/bindings/dma/fsl,eloplus-dma.yaml new file mode 100644 index 000000000000..8992f244c4db --- /dev/null +++ b/Documentation/devicetree/bindings/dma/fsl,eloplus-dma.yaml @@ -0,0 +1,132 @@ +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/dma/fsl,eloplus-dma.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Freescale EloPlus DMA Controller + +maintainers: + - J. Neuschäfer + +description: + This is a 4-channel DMA controller with extended addresses and chaining, + mainly used in Freescale mpc85xx/86xx, Pxxx and BSC series chips, such as + mpc8540, mpc8641 p4080, bsc9131 etc. + +properties: + compatible: + oneOf: + - items: + - enum: + - fsl,mpc8540-dma + - fsl,mpc8541-dma + - fsl,mpc8548-dma + - fsl,mpc8555-dma + - fsl,mpc8560-dma + - fsl,mpc8572-dma + - fsl,mpc8641-dma + - const: fsl,eloplus-dma + - const: fsl,eloplus-dma + + reg: + items: + - description: + DMA General Status Register, i.e. DGSR which contains + status for all the 4 DMA channels + + cell-index: + $ref: /schemas/types.yaml#/definitions/uint32 + description: + controller index. 0 for controller @ 0x21000, 1 for controller @ 0xc000 + + ranges: true + + "#address-cells": + const: 1 + + "#size-cells": + const: 1 + + interrupts: + maxItems: 1 + description: Controller interrupt. + +patternProperties: + "^dma-channel@[0-9a-f]+$": + type: object + additionalProperties: false + + properties: + compatible: + oneOf: + # native DMA channel + - items: + - enum: + - fsl,mpc8540-dma-channel + - fsl,mpc8541-dma-channel + - fsl,mpc8548-dma-channel + - fsl,mpc8555-dma-channel + - fsl,mpc8560-dma-channel + - fsl,mpc8572-dma-channel + - const: fsl,eloplus-dma-channel + + # audio DMA channel, see fsl,ssi.yaml + - const: fsl,ssi-dma-channel + + reg: + maxItems: 1 + + cell-index: + description: DMA channel index starts at 0. + + interrupts: + maxItems: 1 + description: + Per-channel interrupt. Only necessary if no controller interrupt has + been provided. + +additionalProperties: false + +examples: + - | + #include + + dma@21300 { + compatible = "fsl,mpc8540-dma", "fsl,eloplus-dma"; + reg = <0x21300 4>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x21100 0x200>; + cell-index = <0>; + + dma-channel@0 { + compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; + reg = <0 0x80>; + cell-index = <0>; + interrupts = <20 IRQ_TYPE_EDGE_FALLING>; + }; + + dma-channel@80 { + compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; + reg = <0x80 0x80>; + cell-index = <1>; + interrupts = <21 IRQ_TYPE_EDGE_FALLING>; + }; + + dma-channel@100 { + compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; + reg = <0x100 0x80>; + cell-index = <2>; + interrupts = <22 IRQ_TYPE_EDGE_FALLING>; + }; + + dma-channel@180 { + compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; + reg = <0x180 0x80>; + cell-index = <3>; + interrupts = <23 IRQ_TYPE_EDGE_FALLING>; + }; + }; + +... diff --git a/Documentation/devicetree/bindings/powerpc/fsl/dma.txt b/Documentation/devicetree/bindings/powerpc/fsl/dma.txt deleted file mode 100644 index c11ad5c6db21..000000000000 --- a/Documentation/devicetree/bindings/powerpc/fsl/dma.txt +++ /dev/null @@ -1,204 +0,0 @@ -* Freescale DMA Controllers - -** Freescale Elo DMA Controller - This is a little-endian 4-channel DMA controller, used in Freescale mpc83xx - series chips such as mpc8315, mpc8349, mpc8379 etc. - -Required properties: - -- compatible : must include "fsl,elo-dma" -- reg : DMA General Status Register, i.e. DGSR which contains - status for all the 4 DMA channels -- ranges : describes the mapping between the address space of the - DMA channels and the address space of the DMA controller -- cell-index : controller index. 0 for controller @ 0x8100 -- interrupts : interrupt specifier for DMA IRQ - -- DMA channel nodes: - - compatible : must include "fsl,elo-dma-channel" - However, see note below. - - reg : DMA channel specific registers - - cell-index : DMA channel index starts at 0. - -Optional properties: - - interrupts : interrupt specifier for DMA channel IRQ - (on 83xx this is expected to be identical to - the interrupts property of the parent node) - -Example: - dma@82a8 { - #address-cells = <1>; - #size-cells = <1>; - compatible = "fsl,mpc8349-dma", "fsl,elo-dma"; - reg = <0x82a8 4>; - ranges = <0 0x8100 0x1a4>; - interrupt-parent = <&ipic>; - interrupts = <71 8>; - cell-index = <0>; - dma-channel@0 { - compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; - cell-index = <0>; - reg = <0 0x80>; - interrupt-parent = <&ipic>; - interrupts = <71 8>; - }; - dma-channel@80 { - compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; - cell-index = <1>; - reg = <0x80 0x80>; - interrupt-parent = <&ipic>; - interrupts = <71 8>; - }; - dma-channel@100 { - compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; - cell-index = <2>; - reg = <0x100 0x80>; - interrupt-parent = <&ipic>; - interrupts = <71 8>; - }; - dma-channel@180 { - compatible = "fsl,mpc8349-dma-channel", "fsl,elo-dma-channel"; - cell-index = <3>; - reg = <0x180 0x80>; - interrupt-parent = <&ipic>; - interrupts = <71 8>; - }; - }; - -** Freescale EloPlus DMA Controller - This is a 4-channel DMA controller with extended addresses and chaining, - mainly used in Freescale mpc85xx/86xx, Pxxx and BSC series chips, such as - mpc8540, mpc8641 p4080, bsc9131 etc. - -Required properties: - -- compatible : must include "fsl,eloplus-dma" -- reg : DMA General Status Register, i.e. DGSR which contains - status for all the 4 DMA channels -- cell-index : controller index. 0 for controller @ 0x21000, - 1 for controller @ 0xc000 -- ranges : describes the mapping between the address space of the - DMA channels and the address space of the DMA controller - -- DMA channel nodes: - - compatible : must include "fsl,eloplus-dma-channel" - However, see note below. - - cell-index : DMA channel index starts at 0. - - reg : DMA channel specific registers - - interrupts : interrupt specifier for DMA channel IRQ - -Example: - dma@21300 { - #address-cells = <1>; - #size-cells = <1>; - compatible = "fsl,mpc8540-dma", "fsl,eloplus-dma"; - reg = <0x21300 4>; - ranges = <0 0x21100 0x200>; - cell-index = <0>; - dma-channel@0 { - compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; - reg = <0 0x80>; - cell-index = <0>; - interrupt-parent = <&mpic>; - interrupts = <20 2>; - }; - dma-channel@80 { - compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; - reg = <0x80 0x80>; - cell-index = <1>; - interrupt-parent = <&mpic>; - interrupts = <21 2>; - }; - dma-channel@100 { - compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; - reg = <0x100 0x80>; - cell-index = <2>; - interrupt-parent = <&mpic>; - interrupts = <22 2>; - }; - dma-channel@180 { - compatible = "fsl,mpc8540-dma-channel", "fsl,eloplus-dma-channel"; - reg = <0x180 0x80>; - cell-index = <3>; - interrupt-parent = <&mpic>; - interrupts = <23 2>; - }; - }; - -** Freescale Elo3 DMA Controller - DMA controller which has same function as EloPlus except that Elo3 has 8 - channels while EloPlus has only 4, it is used in Freescale Txxx and Bxxx - series chips, such as t1040, t4240, b4860. - -Required properties: - -- compatible : must include "fsl,elo3-dma" -- reg : contains two entries for DMA General Status Registers, - i.e. DGSR0 which includes status for channel 1~4, and - DGSR1 for channel 5~8 -- ranges : describes the mapping between the address space of the - DMA channels and the address space of the DMA controller - -- DMA channel nodes: - - compatible : must include "fsl,eloplus-dma-channel" - - reg : DMA channel specific registers - - interrupts : interrupt specifier for DMA channel IRQ - -Example: -dma@100300 { - #address-cells = <1>; - #size-cells = <1>; - compatible = "fsl,elo3-dma"; - reg = <0x100300 0x4>, - <0x100600 0x4>; - ranges = <0x0 0x100100 0x500>; - dma-channel@0 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x0 0x80>; - interrupts = <28 2 0 0>; - }; - dma-channel@80 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x80 0x80>; - interrupts = <29 2 0 0>; - }; - dma-channel@100 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x100 0x80>; - interrupts = <30 2 0 0>; - }; - dma-channel@180 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x180 0x80>; - interrupts = <31 2 0 0>; - }; - dma-channel@300 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x300 0x80>; - interrupts = <76 2 0 0>; - }; - dma-channel@380 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x380 0x80>; - interrupts = <77 2 0 0>; - }; - dma-channel@400 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x400 0x80>; - interrupts = <78 2 0 0>; - }; - dma-channel@480 { - compatible = "fsl,eloplus-dma-channel"; - reg = <0x480 0x80>; - interrupts = <79 2 0 0>; - }; -}; - -Note on DMA channel compatible properties: The compatible property must say -"fsl,elo-dma-channel" or "fsl,eloplus-dma-channel" to be used by the Elo DMA -driver (fsldma). Any DMA channel used by fsldma cannot be used by another -DMA driver, such as the SSI sound drivers for the MPC8610. Therefore, any DMA -channel that should be used for another driver should not use -"fsl,elo-dma-channel" or "fsl,eloplus-dma-channel". For the SSI drivers, for -example, the compatible property should be "fsl,ssi-dma-channel". See ssi.txt -for more information. -- 2.51.0 From e87ca16e99118ab4e130a41bdf12abbf6a87656c Mon Sep 17 00:00:00 2001 From: Vinicius Costa Gomes Date: Wed, 5 Mar 2025 15:00:06 -0800 Subject: [PATCH 07/16] dmaengine: dmatest: Fix dmatest waiting less when interrupted Change the "wait for operation finish" logic to take interrupts into account. When using dmatest with idxd DMA engine, it's possible that during longer tests, the interrupt notifying the finish of an operation happens during wait_event_freezable_timeout(), which causes dmatest to cleanup all the resources, some of which might still be in use. This fix ensures that the wait logic correctly handles interrupts, preventing premature cleanup of resources. Reported-by: kernel test robot Closes: https://lore.kernel.org/oe-lkp/202502171134.8c403348-lkp@intel.com Signed-off-by: Vinicius Costa Gomes Reviewed-by: Dave Jiang Link: https://lore.kernel.org/r/20250305230007.590178-1-vinicius.gomes@intel.com Signed-off-by: Vinod Koul --- drivers/dma/dmatest.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/dma/dmatest.c b/drivers/dma/dmatest.c index 91b2fbc0b864..d891dfca358e 100644 --- a/drivers/dma/dmatest.c +++ b/drivers/dma/dmatest.c @@ -841,9 +841,9 @@ static int dmatest_func(void *data) } else { dma_async_issue_pending(chan); - wait_event_freezable_timeout(thread->done_wait, - done->done, - msecs_to_jiffies(params->timeout)); + wait_event_timeout(thread->done_wait, + done->done, + msecs_to_jiffies(params->timeout)); status = dma_async_is_tx_complete(chan, cookie, NULL, NULL); -- 2.51.0 From 6ec29d4086ed8b951fa794ac6c0e7cd7ae3762d9 Mon Sep 17 00:00:00 2001 From: Inochi Amaoto Date: Mon, 3 Mar 2025 14:56:48 +0800 Subject: [PATCH 08/16] dt-bindings: dma: snps,dw-axi-dmac: Allow devices to be marked as noncoherent A RISC-V platform can have both DMA coherent/noncoherent devices. Since the RISC-V architecture is marked coherent, devices should be marked as noncoherent when coherent devices exist. Add dma-noncoherent property for snps,dw-axi-dmac device. It will be used on SG2044, and it has other coherent devices. Signed-off-by: Inochi Amaoto Acked-by: Conor Dooley Link: https://lore.kernel.org/r/20250303065649.937233-1-inochiama@gmail.com Signed-off-by: Vinod Koul --- Documentation/devicetree/bindings/dma/snps,dw-axi-dmac.yaml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Documentation/devicetree/bindings/dma/snps,dw-axi-dmac.yaml b/Documentation/devicetree/bindings/dma/snps,dw-axi-dmac.yaml index 525f5f3932f5..935735a59afd 100644 --- a/Documentation/devicetree/bindings/dma/snps,dw-axi-dmac.yaml +++ b/Documentation/devicetree/bindings/dma/snps,dw-axi-dmac.yaml @@ -59,6 +59,8 @@ properties: minimum: 1 maximum: 8 + dma-noncoherent: true + resets: minItems: 1 maxItems: 2 -- 2.51.0 From c9c59da76ce9cb3f215b66eb3708cda1134a5206 Mon Sep 17 00:00:00 2001 From: Peng Fan Date: Fri, 28 Feb 2025 15:17:19 +0800 Subject: [PATCH 09/16] dmaengine: fsl-edma: cleanup chan after dma_async_device_unregister There is kernel dump when do module test: sysfs: cannot create duplicate filename /devices/platform/soc@0/44000000.bus/44000000.dma-controller/dma/dma0chan0 __dma_async_device_channel_register+0x128/0x19c dma_async_device_register+0x150/0x454 fsl_edma_probe+0x6cc/0x8a0 platform_probe+0x68/0xc8 fsl_edma_cleanup_vchan will unlink vchan.chan.device_node, while dma_async_device_unregister needs the link to do __dma_async_device_channel_unregister. So need move fsl_edma_cleanup_vchan after dma_async_device_unregister to make sure channel could be freed. So clean up chan after dma_async_device_unregister to address this. Fixes: 6f93b93b2a1b ("dmaengine: fsl-edma: kill the tasklets upon exit") Reviewed-by: Frank Li Signed-off-by: Peng Fan Link: https://lore.kernel.org/r/20250228071720.3780479-1-peng.fan@oss.nxp.com Signed-off-by: Vinod Koul --- drivers/dma/fsl-edma-main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/dma/fsl-edma-main.c b/drivers/dma/fsl-edma-main.c index 760c9e3e374c..7eb4d898434b 100644 --- a/drivers/dma/fsl-edma-main.c +++ b/drivers/dma/fsl-edma-main.c @@ -802,9 +802,9 @@ static void fsl_edma_remove(struct platform_device *pdev) struct fsl_edma_engine *fsl_edma = platform_get_drvdata(pdev); fsl_edma_irq_exit(pdev, fsl_edma); - fsl_edma_cleanup_vchan(&fsl_edma->dma_dev); of_dma_controller_free(np); dma_async_device_unregister(&fsl_edma->dma_dev); + fsl_edma_cleanup_vchan(&fsl_edma->dma_dev); fsl_disable_clocks(fsl_edma, fsl_edma->drvdata->dmamuxs); } -- 2.51.0 From fa70c4c3c580c239a0f9e83a14770ab026e8d820 Mon Sep 17 00:00:00 2001 From: Peng Fan Date: Fri, 28 Feb 2025 15:17:20 +0800 Subject: [PATCH 10/16] dmaengine: fsl-edma: free irq correctly in remove path Add fsl_edma->txirq/errirq check to avoid below warning because no errirq at i.MX9 platform. Otherwise there will be kernel dump: WARNING: CPU: 0 PID: 11 at kernel/irq/devres.c:144 devm_free_irq+0x74/0x80 Modules linked in: CPU: 0 UID: 0 PID: 11 Comm: kworker/u8:0 Not tainted 6.12.0-rc7#18 Hardware name: NXP i.MX93 11X11 EVK board (DT) Workqueue: events_unbound deferred_probe_work_func pstate: 60400009 (nZCv daif +PAN -UAO -TCO -DIT -SSBS BTYPE=--) pc : devm_free_irq+0x74/0x80 lr : devm_free_irq+0x48/0x80 Call trace: devm_free_irq+0x74/0x80 (P) devm_free_irq+0x48/0x80 (L) fsl_edma_remove+0xc4/0xc8 platform_remove+0x28/0x44 device_remove+0x4c/0x80 Fixes: 44eb827264de ("dmaengine: fsl-edma: request per-channel IRQ only when channel is allocated") Reviewed-by: Frank Li Signed-off-by: Peng Fan Link: https://lore.kernel.org/r/20250228071720.3780479-2-peng.fan@oss.nxp.com Signed-off-by: Vinod Koul --- drivers/dma/fsl-edma-main.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/drivers/dma/fsl-edma-main.c b/drivers/dma/fsl-edma-main.c index 7eb4d898434b..756d67325db5 100644 --- a/drivers/dma/fsl-edma-main.c +++ b/drivers/dma/fsl-edma-main.c @@ -401,6 +401,7 @@ fsl_edma2_irq_init(struct platform_device *pdev, /* The last IRQ is for eDMA err */ if (i == count - 1) { + fsl_edma->errirq = irq; ret = devm_request_irq(&pdev->dev, irq, fsl_edma_err_handler, 0, "eDMA2-ERR", fsl_edma); @@ -420,10 +421,13 @@ static void fsl_edma_irq_exit( struct platform_device *pdev, struct fsl_edma_engine *fsl_edma) { if (fsl_edma->txirq == fsl_edma->errirq) { - devm_free_irq(&pdev->dev, fsl_edma->txirq, fsl_edma); + if (fsl_edma->txirq >= 0) + devm_free_irq(&pdev->dev, fsl_edma->txirq, fsl_edma); } else { - devm_free_irq(&pdev->dev, fsl_edma->txirq, fsl_edma); - devm_free_irq(&pdev->dev, fsl_edma->errirq, fsl_edma); + if (fsl_edma->txirq >= 0) + devm_free_irq(&pdev->dev, fsl_edma->txirq, fsl_edma); + if (fsl_edma->errirq >= 0) + devm_free_irq(&pdev->dev, fsl_edma->errirq, fsl_edma); } } @@ -620,6 +624,8 @@ static int fsl_edma_probe(struct platform_device *pdev) if (!fsl_edma) return -ENOMEM; + fsl_edma->errirq = -EINVAL; + fsl_edma->txirq = -EINVAL; fsl_edma->drvdata = drvdata; fsl_edma->n_chans = chans; mutex_init(&fsl_edma->fsl_edma_mutex); -- 2.51.0 From 566beb347eded7a860511164a7a163bc882dc4d0 Mon Sep 17 00:00:00 2001 From: Siddharth Vadapalli Date: Wed, 5 Feb 2025 17:48:01 +0530 Subject: [PATCH 11/16] dmaengine: ti: k3-udma: Enable second resource range for BCDMA and PKTDMA The SoC DMA resources for UDMA, BCDMA and PKTDMA can be described via a combination of up to two resource ranges. The first resource range handles the default partitioning wherein all resources belonging to that range are allocated to a single entity and form a continuous range. For use-cases where the resources are shared across multiple entities and require to be described via discontinuous ranges, a second resource range is required. Currently, udma_setup_resources() supports handling resources that belong to the second range. Extend bcdma_setup_resources() and pktdma_setup_resources() to support the same. Signed-off-by: Siddharth Vadapalli Acked-by: Peter Ujfalusi Link: https://lore.kernel.org/r/20250205121805.316792-1-s-vadapalli@ti.com Signed-off-by: Vinod Koul --- drivers/dma/ti/k3-udma.c | 36 ++++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/drivers/dma/ti/k3-udma.c b/drivers/dma/ti/k3-udma.c index 7ed1956b4642..b223a7aacb0c 100644 --- a/drivers/dma/ti/k3-udma.c +++ b/drivers/dma/ti/k3-udma.c @@ -4886,6 +4886,12 @@ static int bcdma_setup_resources(struct udma_dev *ud) irq_res.desc[i].start = rm_res->desc[i].start + oes->bcdma_bchan_ring; irq_res.desc[i].num = rm_res->desc[i].num; + + if (rm_res->desc[i].num_sec) { + irq_res.desc[i].start_sec = rm_res->desc[i].start_sec + + oes->bcdma_bchan_ring; + irq_res.desc[i].num_sec = rm_res->desc[i].num_sec; + } } } } else { @@ -4909,6 +4915,15 @@ static int bcdma_setup_resources(struct udma_dev *ud) irq_res.desc[i + 1].start = rm_res->desc[j].start + oes->bcdma_tchan_ring; irq_res.desc[i + 1].num = rm_res->desc[j].num; + + if (rm_res->desc[j].num_sec) { + irq_res.desc[i].start_sec = rm_res->desc[j].start_sec + + oes->bcdma_tchan_data; + irq_res.desc[i].num_sec = rm_res->desc[j].num_sec; + irq_res.desc[i + 1].start_sec = rm_res->desc[j].start_sec + + oes->bcdma_tchan_ring; + irq_res.desc[i + 1].num_sec = rm_res->desc[j].num_sec; + } } } } @@ -4929,6 +4944,15 @@ static int bcdma_setup_resources(struct udma_dev *ud) irq_res.desc[i + 1].start = rm_res->desc[j].start + oes->bcdma_rchan_ring; irq_res.desc[i + 1].num = rm_res->desc[j].num; + + if (rm_res->desc[j].num_sec) { + irq_res.desc[i].start_sec = rm_res->desc[j].start_sec + + oes->bcdma_rchan_data; + irq_res.desc[i].num_sec = rm_res->desc[j].num_sec; + irq_res.desc[i + 1].start_sec = rm_res->desc[j].start_sec + + oes->bcdma_rchan_ring; + irq_res.desc[i + 1].num_sec = rm_res->desc[j].num_sec; + } } } } @@ -5063,6 +5087,12 @@ static int pktdma_setup_resources(struct udma_dev *ud) irq_res.desc[i].start = rm_res->desc[i].start + oes->pktdma_tchan_flow; irq_res.desc[i].num = rm_res->desc[i].num; + + if (rm_res->desc[i].num_sec) { + irq_res.desc[i].start_sec = rm_res->desc[i].start_sec + + oes->pktdma_tchan_flow; + irq_res.desc[i].num_sec = rm_res->desc[i].num_sec; + } } } rm_res = tisci_rm->rm_ranges[RM_RANGE_RFLOW]; @@ -5074,6 +5104,12 @@ static int pktdma_setup_resources(struct udma_dev *ud) irq_res.desc[i].start = rm_res->desc[j].start + oes->pktdma_rchan_flow; irq_res.desc[i].num = rm_res->desc[j].num; + + if (rm_res->desc[j].num_sec) { + irq_res.desc[i].start_sec = rm_res->desc[j].start_sec + + oes->pktdma_rchan_flow; + irq_res.desc[i].num_sec = rm_res->desc[j].num_sec; + } } } ret = ti_sci_inta_msi_domain_alloc_irqs(ud->dev, &irq_res); -- 2.51.0 From e7240aba2053d437a661d946b3d413f310138a45 Mon Sep 17 00:00:00 2001 From: Matthew Majewski Date: Sun, 16 Feb 2025 16:47:41 -0500 Subject: [PATCH 12/16] dmaengine: ti: edma: support sw triggered chans in of_edma_xlate() The .of_edma_xlate() function always sets the hw_triggered flag to true. This causes sw triggered channels consumed via the device-tree to not function properly, as the driver incorrectly assumes they are hw triggered. Modify the xlate() function to correctly set the hw_triggered flag to false for channels reserved for memcpy operation (ie, sw triggered). Signed-off-by: Matthew Majewski Acked-by: Peter Ujfalusi Link: https://lore.kernel.org/r/20250216214741.207538-1-mattwmajewski@gmail.com Signed-off-by: Vinod Koul --- drivers/dma/ti/edma.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/drivers/dma/ti/edma.c b/drivers/dma/ti/edma.c index b1a54655e6ce..3ed406f08c44 100644 --- a/drivers/dma/ti/edma.c +++ b/drivers/dma/ti/edma.c @@ -2259,8 +2259,12 @@ static struct dma_chan *of_edma_xlate(struct of_phandle_args *dma_spec, return NULL; out: - /* The channel is going to be used as HW synchronized */ - echan->hw_triggered = true; + /* + * The channel is going to be HW synchronized, unless it was + * reserved as a memcpy channel + */ + echan->hw_triggered = + !edma_is_memcpy_channel(i, ecc->info->memcpy_channels); return dma_get_slave_channel(chan); } #else -- 2.51.0 From b9014a10bdb8e967d85819f5ef61e6f80d0b46c9 Mon Sep 17 00:00:00 2001 From: Nathan Lynch Date: Mon, 10 Feb 2025 17:29:11 -0600 Subject: [PATCH 13/16] dmaengine: Remove device_prep_dma_imm_data from struct dma_device The device_prep_dma_imm_data() method isn't implemented or invoked by any code since commit 80ade22c06ca ("misc: mic: remove the MIC drivers"). Remove it, shrinking struct dma_device by a few bytes. Signed-off-by: Nathan Lynch Link: https://lore.kernel.org/r/20250210-dmaengine-drop-imm-data-v1-1-e017766da2fa@amd.com Signed-off-by: Vinod Koul --- include/linux/dmaengine.h | 4 ---- 1 file changed, 4 deletions(-) diff --git a/include/linux/dmaengine.h b/include/linux/dmaengine.h index a360e0330436..bb146c5ac3e4 100644 --- a/include/linux/dmaengine.h +++ b/include/linux/dmaengine.h @@ -839,7 +839,6 @@ struct dma_filter { * The function takes a buffer of size buf_len. The callback function will * be called after period_len bytes have been transferred. * @device_prep_interleaved_dma: Transfer expression in a generic way. - * @device_prep_dma_imm_data: DMA's 8 byte immediate data to the dst address * @device_caps: May be used to override the generic DMA slave capabilities * with per-channel specific ones * @device_config: Pushes a new configuration to a channel, return 0 or an error @@ -942,9 +941,6 @@ struct dma_device { struct dma_async_tx_descriptor *(*device_prep_interleaved_dma)( struct dma_chan *chan, struct dma_interleaved_template *xt, unsigned long flags); - struct dma_async_tx_descriptor *(*device_prep_dma_imm_data)( - struct dma_chan *chan, dma_addr_t dst, u64 data, - unsigned long flags); void (*device_caps)(struct dma_chan *chan, struct dma_slave_caps *caps); int (*device_config)(struct dma_chan *chan, struct dma_slave_config *config); -- 2.51.0 From b87c29c007e80f4737a056b3c5c21b5b5106b7f7 Mon Sep 17 00:00:00 2001 From: Basavaraj Natikar Date: Mon, 3 Feb 2025 21:55:09 +0530 Subject: [PATCH 14/16] dmaengine: ae4dma: Remove deprecated PCI IDs Two previously used PCI IDs are deprecated and should not be used for AE4DMA. Hence, remove as they are unsupported for AE4DMA. Fixes: 90a30e268d9b ("dmaengine: ae4dma: Add AMD ae4dma controller driver") Signed-off-by: Basavaraj Natikar Link: https://lore.kernel.org/r/20250203162511.911946-2-Basavaraj.Natikar@amd.com Signed-off-by: Vinod Koul --- drivers/dma/amd/ae4dma/ae4dma-pci.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/drivers/dma/amd/ae4dma/ae4dma-pci.c b/drivers/dma/amd/ae4dma/ae4dma-pci.c index aad0dc4294a3..7f96843f5215 100644 --- a/drivers/dma/amd/ae4dma/ae4dma-pci.c +++ b/drivers/dma/amd/ae4dma/ae4dma-pci.c @@ -137,8 +137,6 @@ static void ae4_pci_remove(struct pci_dev *pdev) } static const struct pci_device_id ae4_pci_table[] = { - { PCI_VDEVICE(AMD, 0x14C8), }, - { PCI_VDEVICE(AMD, 0x14DC), }, { PCI_VDEVICE(AMD, 0x149B), }, /* Last entry must be zero */ { 0, } -- 2.51.0 From feba04e6fdf4daccc83fc09d499a3e32c178edb4 Mon Sep 17 00:00:00 2001 From: Basavaraj Natikar Date: Mon, 3 Feb 2025 21:55:10 +0530 Subject: [PATCH 15/16] dmaengine: ae4dma: Use the MSI count and its corresponding IRQ number Instead of using the defined maximum hardware queue, which can lead to incorrect values if the counts mismatch, use the exact supported MSI count and its corresponding IRQ number. Fixes: 90a30e268d9b ("dmaengine: ae4dma: Add AMD ae4dma controller driver") Signed-off-by: Basavaraj Natikar Link: https://lore.kernel.org/r/20250203162511.911946-3-Basavaraj.Natikar@amd.com Signed-off-by: Vinod Koul --- drivers/dma/amd/ae4dma/ae4dma-pci.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/dma/amd/ae4dma/ae4dma-pci.c b/drivers/dma/amd/ae4dma/ae4dma-pci.c index 7f96843f5215..2c63907db228 100644 --- a/drivers/dma/amd/ae4dma/ae4dma-pci.c +++ b/drivers/dma/amd/ae4dma/ae4dma-pci.c @@ -46,8 +46,8 @@ static int ae4_get_irqs(struct ae4_device *ae4) } else { ae4_msix->msix_count = ret; - for (i = 0; i < MAX_AE4_HW_QUEUES; i++) - ae4->ae4_irq[i] = ae4_msix->msix_entry[i].vector; + for (i = 0; i < ae4_msix->msix_count; i++) + ae4->ae4_irq[i] = pci_irq_vector(pdev, i); } return ret; -- 2.51.0 From 6565439894570a07b00dba0b739729fe6b56fba4 Mon Sep 17 00:00:00 2001 From: Basavaraj Natikar Date: Mon, 3 Feb 2025 21:55:11 +0530 Subject: [PATCH 16/16] dmaengine: ptdma: Utilize the AE4DMA engine's multi-queue functionality MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit As AE4DMA offers multi-channel functionality compared to PTDMA’s single queue, utilize multi-queue, which supports higher speeds than PTDMA, to achieve higher performance using the AE4DMA workqueue based mechanism. Fixes: 69a47b16a51b ("dmaengine: ptdma: Extend ptdma to support multi-channel and version") Signed-off-by: Basavaraj Natikar Link: https://lore.kernel.org/r/20250203162511.911946-4-Basavaraj.Natikar@amd.com Signed-off-by: Vinod Koul --- drivers/dma/amd/ae4dma/ae4dma.h | 2 + drivers/dma/amd/ptdma/ptdma-dmaengine.c | 90 ++++++++++++++++++++++++- 2 files changed, 89 insertions(+), 3 deletions(-) diff --git a/drivers/dma/amd/ae4dma/ae4dma.h b/drivers/dma/amd/ae4dma/ae4dma.h index 265c5d436008..57f6048726bb 100644 --- a/drivers/dma/amd/ae4dma/ae4dma.h +++ b/drivers/dma/amd/ae4dma/ae4dma.h @@ -37,6 +37,8 @@ #define AE4_DMA_VERSION 4 #define CMD_AE4_DESC_DW0_VAL 2 +#define AE4_TIME_OUT 5000 + struct ae4_msix { int msix_count; struct msix_entry msix_entry[MAX_AE4_HW_QUEUES]; diff --git a/drivers/dma/amd/ptdma/ptdma-dmaengine.c b/drivers/dma/amd/ptdma/ptdma-dmaengine.c index 35c84ec9608b..715ac3ae067b 100644 --- a/drivers/dma/amd/ptdma/ptdma-dmaengine.c +++ b/drivers/dma/amd/ptdma/ptdma-dmaengine.c @@ -198,8 +198,10 @@ static struct pt_dma_desc *pt_handle_active_desc(struct pt_dma_chan *chan, { struct dma_async_tx_descriptor *tx_desc; struct virt_dma_desc *vd; + struct pt_device *pt; unsigned long flags; + pt = chan->pt; /* Loop over descriptors until one is found with commands */ do { if (desc) { @@ -217,7 +219,7 @@ static struct pt_dma_desc *pt_handle_active_desc(struct pt_dma_chan *chan, spin_lock_irqsave(&chan->vc.lock, flags); - if (desc) { + if (pt->ver != AE4_DMA_VERSION && desc) { if (desc->status != DMA_COMPLETE) { if (desc->status != DMA_ERROR) desc->status = DMA_COMPLETE; @@ -235,7 +237,7 @@ static struct pt_dma_desc *pt_handle_active_desc(struct pt_dma_chan *chan, spin_unlock_irqrestore(&chan->vc.lock, flags); - if (tx_desc) { + if (pt->ver != AE4_DMA_VERSION && tx_desc) { dmaengine_desc_get_callback_invoke(tx_desc, NULL); dma_run_dependencies(tx_desc); vchan_vdesc_fini(vd); @@ -245,11 +247,25 @@ static struct pt_dma_desc *pt_handle_active_desc(struct pt_dma_chan *chan, return NULL; } +static inline bool ae4_core_queue_full(struct pt_cmd_queue *cmd_q) +{ + u32 front_wi = readl(cmd_q->reg_control + AE4_WR_IDX_OFF); + u32 rear_ri = readl(cmd_q->reg_control + AE4_RD_IDX_OFF); + + if (((MAX_CMD_QLEN + front_wi - rear_ri) % MAX_CMD_QLEN) >= (MAX_CMD_QLEN - 1)) + return true; + + return false; +} + static void pt_cmd_callback(void *data, int err) { struct pt_dma_desc *desc = data; + struct ae4_cmd_queue *ae4cmd_q; struct dma_chan *dma_chan; struct pt_dma_chan *chan; + struct ae4_device *ae4; + struct pt_device *pt; int ret; if (err == -EINPROGRESS) @@ -257,11 +273,32 @@ static void pt_cmd_callback(void *data, int err) dma_chan = desc->vd.tx.chan; chan = to_pt_chan(dma_chan); + pt = chan->pt; if (err) desc->status = DMA_ERROR; while (true) { + if (pt->ver == AE4_DMA_VERSION) { + ae4 = container_of(pt, struct ae4_device, pt); + ae4cmd_q = &ae4->ae4cmd_q[chan->id]; + + if (ae4cmd_q->q_cmd_count >= (CMD_Q_LEN - 1) || + ae4_core_queue_full(&ae4cmd_q->cmd_q)) { + wake_up(&ae4cmd_q->q_w); + + if (wait_for_completion_timeout(&ae4cmd_q->cmp, + msecs_to_jiffies(AE4_TIME_OUT)) + == 0) { + dev_err(pt->dev, "TIMEOUT %d:\n", ae4cmd_q->id); + break; + } + + reinit_completion(&ae4cmd_q->cmp); + continue; + } + } + /* Check for DMA descriptor completion */ desc = pt_handle_active_desc(chan, desc); @@ -296,6 +333,49 @@ static struct pt_dma_desc *pt_alloc_dma_desc(struct pt_dma_chan *chan, return desc; } +static void pt_cmd_callback_work(void *data, int err) +{ + struct dma_async_tx_descriptor *tx_desc; + struct pt_dma_desc *desc = data; + struct dma_chan *dma_chan; + struct virt_dma_desc *vd; + struct pt_dma_chan *chan; + unsigned long flags; + + dma_chan = desc->vd.tx.chan; + chan = to_pt_chan(dma_chan); + + if (err == -EINPROGRESS) + return; + + tx_desc = &desc->vd.tx; + vd = &desc->vd; + + if (err) + desc->status = DMA_ERROR; + + spin_lock_irqsave(&chan->vc.lock, flags); + if (desc) { + if (desc->status != DMA_COMPLETE) { + if (desc->status != DMA_ERROR) + desc->status = DMA_COMPLETE; + + dma_cookie_complete(tx_desc); + dma_descriptor_unmap(tx_desc); + } else { + tx_desc = NULL; + } + } + spin_unlock_irqrestore(&chan->vc.lock, flags); + + if (tx_desc) { + dmaengine_desc_get_callback_invoke(tx_desc, NULL); + dma_run_dependencies(tx_desc); + list_del(&desc->vd.node); + vchan_vdesc_fini(vd); + } +} + static struct pt_dma_desc *pt_create_desc(struct dma_chan *dma_chan, dma_addr_t dst, dma_addr_t src, @@ -327,6 +407,7 @@ static struct pt_dma_desc *pt_create_desc(struct dma_chan *dma_chan, desc->len = len; if (pt->ver == AE4_DMA_VERSION) { + pt_cmd->pt_cmd_callback = pt_cmd_callback_work; ae4 = container_of(pt, struct ae4_device, pt); ae4cmd_q = &ae4->ae4cmd_q[chan->id]; mutex_lock(&ae4cmd_q->cmd_lock); @@ -367,13 +448,16 @@ static void pt_issue_pending(struct dma_chan *dma_chan) { struct pt_dma_chan *chan = to_pt_chan(dma_chan); struct pt_dma_desc *desc; + struct pt_device *pt; unsigned long flags; bool engine_is_idle = true; + pt = chan->pt; + spin_lock_irqsave(&chan->vc.lock, flags); desc = pt_next_dma_desc(chan); - if (desc) + if (desc && pt->ver != AE4_DMA_VERSION) engine_is_idle = false; vchan_issue_pending(&chan->vc); -- 2.51.0