Add Agilex5 AXI DMA support
Subsystems (3)
v4 cover Add Agilex5 AXI DMA support
This series introduces support for Agilex5 SoC in the Synopsys DesignWare AXI DMA binding and updates the device tree to use the platform-specific compatible string.
The Agilex5 only has 40-bit DMA addressable bit instead of 64-bit. Hence, this specific addition will enable driver to handle this limitation.
---
Notes:
This patch series is applied on socfpga maintainer's tree
https://git.kernel.org/pub/scm/linux/kernel/git/dinguyen/linux.git/log/?h=socfpga_dts_for_v6.20
Changes in v4:
- Use common code to get dma ranges.
- Simplify the code to only in hw_init that will set the bit mask.
Changes in v3:
- simplify dma-ranges addition without description as per input from Rob.
- Add simple-bus to with address-cells, size-cells, dma-ranges added under this bus-node.
- Move dma controller device node under simple-bus node.
- Rename "arm64: dts: intel: agilex5: Add dma-ranges, address and size cells to dma node" to #2
- Drop "dt-bindings: dma: snps,dw-axi-dmac: Add #address-cells and #size-cells"
- Refactor "dma: dw-axi-dmac: Add support for Agilex5 and dynamic bus width" to align with dma controller node now under simple-bus node.
Changes in v2:
- Add dma-ranges property.
- Add address-cells and size-cells due to warning when dma-ranges is define without address-cells and size-cells present. Also prevent kernel panic if address-cells and size-cells are not defined.
- Add driver support to handle defined properties and set the DMA BIT MASK according to value from DT.
- Rename "arm64: dts: agilex5: Use platform-specific compatible for AXI DMA" to "arm64: dts: intel: agilex5: Add dma-ranges and address cells to dma node"
This changes is validated on:
- intel/socfpga_agilex5_socdk.dtb
- snps,dw-axi-dmac.yaml
- snps,dw-axi-dmac.yaml intel/socfpga_agilex5_socdk.dtb
- Agilex5 devkit
---
Khairul Anuar Romli (3):
dt-bindings: dma: snps,dw-axi-dmac: Add compatible string for Agilex5
arm64: dts: intel: agilex5: Add simple-bus node on top of dma
controller node
dma: dw-axi-dmac: Add support for Agilex5 and dynamic bus width
.../bindings/dma/snps,dw-axi-dmac.yaml | 14 ++-- .../arm64/boot/dts/intel/socfpga_agilex5.dtsi | 78 ++++++++++--------- .../dma/dw-axi-dmac/dw-axi-dmac-platform.c | 16 +++- drivers/dma/dw-axi-dmac/dw-axi-dmac.h | 1 + 4 files changed, 68 insertions(+), 41 deletions(-)
Signature · 1 line
2.43.7
PATCH v4 1/3 dt-bindings: dma: snps,dw-axi-dmac: Add compatible string for Agilex5
The address bus on Agilex5 is limited to 40 bits. When SMMU is enable this will cause address truncation and translation faults. Hence introducing "altr,agilex5-axi-dma" to enable platform specific configuration to configure the dma addressable bit mask.
Add a fallback capability for the compatible property to allow driver to probe and initialize with a newly added compatible string without requiring additional entry in the driver.
---
Changes in v4:
- remove dma-ranges as it is no longer required
Changes in v3:
- Simple dma-ranges property with true and without description
Changes in v2:
- Add dma-ranges
--- .../devicetree/bindings/dma/snps,dw-axi-dmac.yaml | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-)
Documentation/devicetree/bindings/dma/snps,dw-axi-dmac.yaml +9 -5
@@ -17,11 +17,15 @@ allOf: properties: compatible: - enum: - - snps,axi-dma-1.01a - - intel,kmb-axi-dma - - starfive,jh7110-axi-dma - - starfive,jh8100-axi-dma + oneOf: + - enum: + - snps,axi-dma-1.01a + - intel,kmb-axi-dma + - starfive,jh7110-axi-dma + - starfive,jh8100-axi-dma + - items: + - const: altr,agilex5-axi-dma + - const: snps,axi-dma-1.01a reg: minItems: 1
Signature · 1 line
2.43.7
PATCH v4 2/3 arm64: dts: intel: agilex5: Add simple-bus node on top of dma controller node
In reply to Khairul Anuar RomliMove dma-controller node under simple-bus node to allow bus node specific property able to be properly defined. This is require to fulfill Agilex5 bus limitation that is limited to 40-addressable-bit.
Update the compatible string for the DMA controller nodes in the Agilex5 device tree from the generic "snps,axi-dma-1.01a" to the platform-specific "altr,agilex5-axi-dma". Add fallback capability to ensure driver is able to initialize properly.
This change enables the use of platform-specific features and constraints in the driver, such as setting a 40-bit DMA addressable mask through dma-ranges, which is required for Agilex5. It also aligns with the updated device tree bindings and driver support for this compatible string.
---
Changes in v4:
- No changes.
Changes in v3:
- Rename the patch "arm64: dts: intel: agilex5: Add dma-ranges, address and size cells to dma node"
- Add simple-bus and move dmac0 and dmac1 1 level down.
Changes in v2:
- Rename the from add platform specific to add dma-ranges, address and size cells.
- Define address-cells and size-cells for dmac0 and dmac1
- Add dma-ranges for agilex5 for 40-bit
--- .../arm64/boot/dts/intel/socfpga_agilex5.dtsi | 78 ++++++++++--------- 1 file changed, 43 insertions(+), 35 deletions(-)
arch/arm64/boot/dts/intel/socfpga_agilex5.dtsi +43 -35
@@ -324,42 +324,50 @@ ocram: sram@0 { #size-cells = <1>; }; - dmac0: dma-controller@10db0000 { - compatible = "snps,axi-dma-1.01a"; - reg = <0x10db0000 0x500>; - clocks = <&clkmgr AGILEX5_L4_MAIN_CLK>, - <&clkmgr AGILEX5_L4_MP_CLK>; - clock-names = "core-clk", "cfgr-clk"; - interrupt-parent = <&intc>; - interrupts = <GIC_SPI 86 IRQ_TYPE_LEVEL_HIGH>; - #dma-cells = <1>; - dma-channels = <4>; - snps,dma-masters = <1>; - snps,data-width = <2>; - snps,block-size = <32767 32767 32767 32767>; - snps,priority = <0 1 2 3>; - snps,axi-max-burst-len = <8>; - iommus = <&smmu 8>; - dma-coherent; - }; + dma: dma-bus@10db0000 { + compatible = "simple-bus"; + #address-cells = <1>; + #size-cells = <2>; + ranges = <0x00 0x10db0000 0x00 0x20000>; + dma-ranges = <0x00 0x00 0x100 0x00>; + + dmac0: dma-controller@0 { + compatible = "altr,agilex5-axi-dma", + "snps,axi-dma-1.01a"; + reg = <0x0 0x0 0x500>; + clocks = <&clkmgr AGILEX5_L4_MAIN_CLK>, + <&clkmgr AGILEX5_L4_MP_CLK>; + clock-names = "core-clk", "cfgr-clk"; + interrupt-parent = <&intc>; + interrupts = <GIC_SPI 86 IRQ_TYPE_LEVEL_HIGH>; + #dma-cells = <1>; + dma-channels = <4>; + snps,dma-masters = <1>; + snps,data-width = <2>; + snps,block-size = <32767 32767 32767 32767>; + snps,priority = <0 1 2 3>; + snps,axi-max-burst-len = <8>; + iommus = <&smmu 8>; + }; - dmac1: dma-controller@10dc0000 { - compatible = "snps,axi-dma-1.01a"; - reg = <0x10dc0000 0x500>; - clocks = <&clkmgr AGILEX5_L4_MAIN_CLK>, - <&clkmgr AGILEX5_L4_MP_CLK>; - clock-names = "core-clk", "cfgr-clk"; - interrupt-parent = <&intc>; - interrupts = <GIC_SPI 171 IRQ_TYPE_LEVEL_HIGH>; - #dma-cells = <1>; - dma-channels = <4>; - snps,dma-masters = <1>; - snps,data-width = <2>; - snps,block-size = <32767 32767 32767 32767>; - snps,priority = <0 1 2 3>; - snps,axi-max-burst-len = <8>; - iommus = <&smmu 9>; - dma-coherent; + dmac1: dma-controller@10000 { + compatible = "altr,agilex5-axi-dma", + "snps,axi-dma-1.01a"; + reg = <0x10000 0x0 0x500>; + clocks = <&clkmgr AGILEX5_L4_MAIN_CLK>, + <&clkmgr AGILEX5_L4_MP_CLK>; + clock-names = "core-clk", "cfgr-clk"; + interrupt-parent = <&intc>; + interrupts = <GIC_SPI 171 IRQ_TYPE_LEVEL_HIGH>; + #dma-cells = <1>; + dma-channels = <4>; + snps,dma-masters = <1>; + snps,data-width = <2>; + snps,block-size = <32767 32767 32767 32767>; + snps,priority = <0 1 2 3>; + snps,axi-max-burst-len = <8>; + iommus = <&smmu 9>; + }; }; rst: rstmgr@10d11000 {
Signature · 1 line
2.43.7
PATCH v4 3/3 dma: dw-axi-dmac: Add support for Agilex5 and dynamic bus width
In reply to Khairul Anuar RomliAdd device tree compatible string support for the Altera Agilex5 AXI DMA controller.
Use common get "dma-ranges" property and calculate the actual number of addressable bits (bus width) for the DMA engine. This calculated value is then used to set the coherent mask via 'dma_set_mask_and_coherent()', allowing the driver to correctly handle devices with bus widths less than 64 bits. Initialize the addressable bits default to 64 if 'dma-ranges' is not specified or cannot be parsed.
---
Changes in v4:
- Simplify the code to use common code to get dma ranges.
- Narrow the code changes on hw_init.
Changes in v3:
- Refactor the code to align with dma controller device node move to 1 level down.
Changes in v2:
- Add driver implementation to set the DMA BIT MAST to 40 based on dma-ranges defined in DT.
- Add glue for driver and DT.
--- drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c | 16 +++++++++++++++- drivers/dma/dw-axi-dmac/dw-axi-dmac.h | 1 + 2 files changed, 16 insertions(+), 1 deletion(-)
drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c +15 -1
@@ -12,6 +12,7 @@#include <linux/device.h> #include <linux/dmaengine.h> #include <linux/dmapool.h> +#include <linux/dma-direct.h> #include <linux/dma-mapping.h> #include <linux/err.h> #include <linux/interrupt.h>
@@ -264,14 +265,25 @@ static inline bool axi_chan_is_hw_enable(struct axi_dma_chan *chan)static void axi_dma_hw_init (struct axi_dma_chip *chip) { +const struct bus_dma_region *map =NULL ; +unsigned int addressable_bits =64 ;int ret; +u64 max_bus;u32 i;for (i =0 ; i < chip->dw->hdata->nr_channels; i++) {axi_chan_irq_disable (&chip->dw->chan[i],DWAXIDMAC_IRQ_ALL );axi_chan_disable (&chip->dw->chan[i]); } - ret =dma_set_mask_and_coherent (chip->dev,DMA_BIT_MASK (64 )); + + ret =of_dma_get_range (chip->dev->of_node, &map); +if (!ret) { + max_bus = map->dma_start + map->size -1 ; + addressable_bits =fls64 (max_bus); + } + +dev_dbg (chip->dev,"Addressable bus width: %u\n" , addressable_bits); + ret =dma_set_mask_and_coherent (chip->dev,DMA_BIT_MASK (addressable_bits));if (ret)dev_warn (chip->dev,"Unable to set coherent mask\n" ); }
@@ -1669,6 +1681,8 @@ static const struct of_device_id dw_dma_of_id_table[] = { }, { .compatible = "starfive,jh8100-axi-dma", .data = (void *)AXI_DMA_FLAG_HAS_RESETS, + }, { + .compatible = "altr,agilex5-axi-dma" }, {} };
drivers/dma/dw-axi-dmac/dw-axi-dmac.h +1 -0
@@ -143,6 +143,7 @@ static inline struct axi_dma_chan *dchan_to_axi_dma_chan(struct dma_chan *dchan)return vc_to_axi_dma_chan (to_virt_chan (dchan)); } +int of_dma_get_range (struct device_node *np,const struct bus_dma_region **map);#define COMMON_REG_LEN 0x100#define CHAN_REG_LEN 0x100
Signature · 1 line
2.43.7
Rob Herring
maintainerRe: [PATCH v4 3/3] dma: dw-axi-dmac: Add support for Agilex5 and dynamic bus width
Quoted 53 lines · Khairul Anuar Romli
Add device tree compatible string support for the Altera Agilex5 AXI DMA controller.
Use common get "dma-ranges" property and calculate the actual number of addressable bits (bus width) for the DMA engine. This calculated value is then used to set the coherent mask via '
dma_set_mask_and_coherent()', allowing the driver to correctly handle devices with bus widths less than 64 bits. Initialize the addressable bits default to 64 if 'dma-ranges' is not specified or cannot be parsed.Signed-off-by Khairul Anuar Romli <[email protected]>---
Changes in v4:
- Simplify the code to use common code to get dma ranges.
- Narrow the code changes onhw_init.
Changes in v3:
- Refactor the code to align with dma controller device node move to 1 level down.
Changes in v2:
- Add driver implementation to set the DMA BIT MAST to 40 based on dma-ranges defined in DT.
- Add glue for driver and DT.--- drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c | 16 +++++++++++++++- drivers/dma/dw-axi-dmac/dw-axi-dmac.h | 1 + 2 files changed, 16 insertions(+), 1 deletion(-)drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c +4
-0@@ -12,6 +12,7 @@#include <linux/device.h> #include <linux/dmaengine.h> #include <linux/dmapool.h> +#include <linux/dma-direct.h> #include <linux/dma-mapping.h> #include <linux/err.h> #include <linux/interrupt.h> @@ -264,14 +265,25 @@ static inline bool axi_chan_is_hw_enable(struct axi_dma_chan *chan)static void axi_dma_hw_init (struct axi_dma_chip *chip) { +const struct bus_dma_region *map =NULL ; +unsigned int addressable_bits =64 ;int ret; +u64 max_bus;u32 i;for (i =0 ; i < chip->dw->hdata->nr_channels; i++) {axi_chan_irq_disable (&chip->dw->chan[i],DWAXIDMAC_IRQ_ALL );axi_chan_disable (&chip->dw->chan[i]); }
drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c static inline bool axi_chan_is_hw_enable(struct axi_dma_chan *chan) · line 286
Quoted 10 lines
drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c +9
-1- ret =dma_set_mask_and_coherent (chip->dev,DMA_BIT_MASK (64 )); + + ret =of_dma_get_range (chip->dev->of_node, &map); +if (!ret) { + max_bus = map->dma_start + map->size -1 ; + addressable_bits =fls64 (max_bus); + } + +dev_dbg (chip->dev,"Addressable bus width: %u\n" , addressable_bits); + ret =dma_set_mask_and_coherent (chip->dev,DMA_BIT_MASK (addressable_bits));
I'm pretty sure you don't need to do any of this. The core will merge the device's mask with the bus ranges.
Rob
Re: [PATCH v4 3/3] dma: dw-axi-dmac: Add support for Agilex5 and dynamic bus width
Quoted 68 lines · Rob Herring
Quoted 53 lines · Khairul Anuar Romli
Add device tree compatible string support for the Altera Agilex5 AXI DMA controller.
Use common get "dma-ranges" property and calculate the actual number of addressable bits (bus width) for the DMA engine. This calculated value is then used to set the coherent mask via '
dma_set_mask_and_coherent()', allowing the driver to correctly handle devices with bus widths less than 64 bits. Initialize the addressable bits default to 64 if 'dma-ranges' is not specified or cannot be parsed.Signed-off-by Khairul Anuar Romli <[email protected]>---
Changes in v4:
- Simplify the code to use common code to get dma ranges.
- Narrow the code changes onhw_init.
Changes in v3:
- Refactor the code to align with dma controller device node move to 1 level down.
Changes in v2:
- Add driver implementation to set the DMA BIT MAST to 40 based on dma-ranges defined in DT.
- Add glue for driver and DT.--- drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c | 16 +++++++++++++++- drivers/dma/dw-axi-dmac/dw-axi-dmac.h | 1 + 2 files changed, 16 insertions(+), 1 deletion(-)drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c +4
-0@@ -12,6 +12,7 @@#include <linux/device.h> #include <linux/dmaengine.h> #include <linux/dmapool.h> +#include <linux/dma-direct.h> #include <linux/dma-mapping.h> #include <linux/err.h> #include <linux/interrupt.h> @@ -264,14 +265,25 @@ static inline bool axi_chan_is_hw_enable(struct axi_dma_chan *chan)static void axi_dma_hw_init (struct axi_dma_chip *chip) { +const struct bus_dma_region *map =NULL ; +unsigned int addressable_bits =64 ;int ret; +u64 max_bus;u32 i;for (i =0 ; i < chip->dw->hdata->nr_channels; i++) {axi_chan_irq_disable (&chip->dw->chan[i],DWAXIDMAC_IRQ_ALL );axi_chan_disable (&chip->dw->chan[i]); }drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c static inline bool axi_chan_is_hw_enable(struct axi_dma_chan *chan) · line 286
Quoted 10 lines
drivers/dma/dw-axi-dmac/dw-axi-dmac-platform.c +9
-1- ret =dma_set_mask_and_coherent (chip->dev,DMA_BIT_MASK (64 )); + + ret =of_dma_get_range (chip->dev->of_node, &map); +if (!ret) { + max_bus = map->dma_start + map->size -1 ; + addressable_bits =fls64 (max_bus); + } + +dev_dbg (chip->dev,"Addressable bus width: %u\n" , addressable_bits); + ret =dma_set_mask_and_coherent (chip->dev,DMA_BIT_MASK (addressable_bits));I'm pretty sure you don't need to do any of this. The core will merge the device's mask with the bus ranges.
Quoted 1 line
Rob
Shall we drop the entire patch series or only drop this patch and keep the binding and dts patches?
Thanks.
Regards,
Khairul