Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

mmc: atmel-mci: fix burst/chunk size modification

The use of DMA slave config operation requires that the burst size
(aka chunk size) is specified through this interface.
Modify atmel-mci slave driver to use this specification on its side.

Signed-off-by: Nicolas Ferre <nicolas.ferre@atmel.com>
Signed-off-by: Ludovic Desroches <ludovic.desroches@atmel.com>
Signed-off-by: Chris Ball <cjb@laptop.org>

authored by

Nicolas Ferre and committed by
Chris Ball
693e5e20 b87cc1b5

+19 -3
+14
drivers/mmc/host/atmel-mci-regs.h
··· 140 140 #define atmci_writel(port,reg,value) \ 141 141 __raw_writel((value), (port)->regs + reg) 142 142 143 + /* 144 + * Fix sconfig's burst size according to atmel MCI. We need to convert them as: 145 + * 1 -> 0, 4 -> 1, 8 -> 2, 16 -> 3. 146 + * 147 + * This can be done by finding most significant bit set. 148 + */ 149 + static inline unsigned int atmci_convert_chksize(unsigned int maxburst) 150 + { 151 + if (maxburst > 1) 152 + return fls(maxburst) - 2; 153 + else 154 + return 0; 155 + } 156 + 143 157 #endif /* __DRIVERS_MMC_ATMEL_MCI_H__ */
+5 -3
drivers/mmc/host/atmel-mci.c
··· 910 910 enum dma_data_direction direction; 911 911 enum dma_transfer_direction slave_dirn; 912 912 unsigned int sglen; 913 + u32 maxburst; 913 914 u32 iflags; 914 915 915 916 data->error = -EINPROGRESS; ··· 944 943 if (!chan) 945 944 return -ENODEV; 946 945 947 - if (host->caps.has_dma) 948 - atmci_writel(host, ATMCI_DMA, ATMCI_DMA_CHKSIZE(3) | ATMCI_DMAEN); 949 - 950 946 if (data->flags & MMC_DATA_READ) { 951 947 direction = DMA_FROM_DEVICE; 952 948 host->dma_conf.direction = slave_dirn = DMA_DEV_TO_MEM; 949 + maxburst = atmci_convert_chksize(host->dma_conf.src_maxburst); 953 950 } else { 954 951 direction = DMA_TO_DEVICE; 955 952 host->dma_conf.direction = slave_dirn = DMA_MEM_TO_DEV; 953 + maxburst = atmci_convert_chksize(host->dma_conf.dst_maxburst); 956 954 } 955 + 956 + atmci_writel(host, ATMCI_DMA, ATMCI_DMA_CHKSIZE(maxburst) | ATMCI_DMAEN); 957 957 958 958 sglen = dma_map_sg(chan->device->dev, data->sg, 959 959 data->sg_len, direction);