From 6e9c5c8ef2820d18492d07172ac52f23ea8a54d9 Mon Sep 17 00:00:00 2001 From: Wolfram Sang Date: Mon, 7 Oct 2024 13:02:01 +0200 Subject: [PATCH] dmaengine: sh: rz-dmac: handle configs where one address is zero Configs like the ones coming from the MMC subsystem will have either 'src' or 'dst' zeroed, resulting in an unknown bus width. This will bail out on the RZ DMA driver because of the sanity check for a valid bus width. Reorder the code, so that the check will only be applied when the corresponding address is non-zero. Fixes: 5000d37042a6 ("dmaengine: sh: Add DMAC driver for RZ/G2L SoC") Signed-off-by: Wolfram Sang Reviewed-by: Biju Das Reviewed-by: Geert Uytterhoeven Tested-by: Biju Das Tested-by: Claudiu Beznea Link: https://lore.kernel.org/r/20241007110200.43166-6-wsa+renesas@sang-engineering.com Signed-off-by: Vinod Koul --- drivers/dma/sh/rz-dmac.c | 25 ++++++++++++++----------- 1 file changed, 14 insertions(+), 11 deletions(-) diff --git a/drivers/dma/sh/rz-dmac.c b/drivers/dma/sh/rz-dmac.c index 65a27c5a7bce..811389fc9cb8 100644 --- a/drivers/dma/sh/rz-dmac.c +++ b/drivers/dma/sh/rz-dmac.c @@ -601,22 +601,25 @@ static int rz_dmac_config(struct dma_chan *chan, struct rz_dmac_chan *channel = to_rz_dmac_chan(chan); u32 val; - channel->src_per_address = config->src_addr; channel->dst_per_address = config->dst_addr; - - val = rz_dmac_ds_to_val_mapping(config->dst_addr_width); - if (val == CHCFG_DS_INVALID) - return -EINVAL; - channel->chcfg &= ~CHCFG_FILL_DDS_MASK; - channel->chcfg |= FIELD_PREP(CHCFG_FILL_DDS_MASK, val); + if (channel->dst_per_address) { + val = rz_dmac_ds_to_val_mapping(config->dst_addr_width); + if (val == CHCFG_DS_INVALID) + return -EINVAL; - val = rz_dmac_ds_to_val_mapping(config->src_addr_width); - if (val == CHCFG_DS_INVALID) - return -EINVAL; + channel->chcfg |= FIELD_PREP(CHCFG_FILL_DDS_MASK, val); + } + channel->src_per_address = config->src_addr; channel->chcfg &= ~CHCFG_FILL_SDS_MASK; - channel->chcfg |= FIELD_PREP(CHCFG_FILL_SDS_MASK, val); + if (channel->src_per_address) { + val = rz_dmac_ds_to_val_mapping(config->src_addr_width); + if (val == CHCFG_DS_INVALID) + return -EINVAL; + + channel->chcfg |= FIELD_PREP(CHCFG_FILL_SDS_MASK, val); + } return 0; }