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

dw_dmac: Allow src/dst msize & flow controller to be configured at runtime

Msize or Burst Size is peripheral dependent in case of prep_slave_sg and
cyclic_prep transfers, and in case of memcpy transfers it is platform dependent.
So msize configuration must come from platform data.

Also some peripherals (ex: JPEG), need to be flow controller for dma transfers,
so this information in case of slave_sg & cyclic_prep transfers must come from
platform data.

Signed-off-by: Viresh Kumar <viresh.kumar@st.com>
Signed-off-by: Vinod Koul <vinod.koul@intel.com>

authored by

Viresh KUMAR and committed by
Vinod Koul
ee66509d 59c22fc1

+39 -6
+8 -6
drivers/dma/dw_dmac.c
··· 36 36 struct dw_dma_slave *__slave = (private); \ 37 37 int dms = __slave ? __slave->dst_master : 0; \ 38 38 int sms = __slave ? __slave->src_master : 1; \ 39 + u8 smsize = __slave ? __slave->src_msize : 0; \ 40 + u8 dmsize = __slave ? __slave->dst_msize : 0; \ 39 41 \ 40 - (DWC_CTLL_DST_MSIZE(0) \ 41 - | DWC_CTLL_SRC_MSIZE(0) \ 42 + (DWC_CTLL_DST_MSIZE(dmsize) \ 43 + | DWC_CTLL_SRC_MSIZE(smsize) \ 42 44 | DWC_CTLL_LLP_D_EN \ 43 45 | DWC_CTLL_LLP_S_EN \ 44 46 | DWC_CTLL_DMS(dms) \ ··· 685 683 | DWC_CTLL_DST_WIDTH(reg_width) 686 684 | DWC_CTLL_DST_FIX 687 685 | DWC_CTLL_SRC_INC 688 - | DWC_CTLL_FC_M2P); 686 + | DWC_CTLL_FC(dws->fc)); 689 687 reg = dws->tx_reg; 690 688 for_each_sg(sgl, sg, sg_len, i) { 691 689 struct dw_desc *desc; ··· 730 728 | DWC_CTLL_SRC_WIDTH(reg_width) 731 729 | DWC_CTLL_DST_INC 732 730 | DWC_CTLL_SRC_FIX 733 - | DWC_CTLL_FC_P2M); 731 + | DWC_CTLL_FC(dws->fc)); 734 732 735 733 reg = dws->rx_reg; 736 734 for_each_sg(sgl, sg, sg_len, i) { ··· 1148 1146 | DWC_CTLL_SRC_WIDTH(reg_width) 1149 1147 | DWC_CTLL_DST_FIX 1150 1148 | DWC_CTLL_SRC_INC 1151 - | DWC_CTLL_FC_M2P 1149 + | DWC_CTLL_FC(dws->fc) 1152 1150 | DWC_CTLL_INT_EN); 1153 1151 break; 1154 1152 case DMA_FROM_DEVICE: ··· 1159 1157 | DWC_CTLL_DST_WIDTH(reg_width) 1160 1158 | DWC_CTLL_DST_INC 1161 1159 | DWC_CTLL_SRC_FIX 1162 - | DWC_CTLL_FC_P2M 1160 + | DWC_CTLL_FC(dws->fc) 1163 1161 | DWC_CTLL_INT_EN); 1164 1162 break; 1165 1163 default:
+1
drivers/dma/dw_dmac_regs.h
··· 86 86 #define DWC_CTLL_SRC_MSIZE(n) ((n)<<14) 87 87 #define DWC_CTLL_S_GATH_EN (1 << 17) /* src gather, !FIX */ 88 88 #define DWC_CTLL_D_SCAT_EN (1 << 18) /* dst scatter, !FIX */ 89 + #define DWC_CTLL_FC(n) ((n) << 20) 89 90 #define DWC_CTLL_FC_M2M (0 << 20) /* mem-to-mem */ 90 91 #define DWC_CTLL_FC_M2P (1 << 20) /* mem-to-periph */ 91 92 #define DWC_CTLL_FC_P2M (2 << 20) /* periph-to-mem */
+30
include/linux/dw_dmac.h
··· 42 42 DW_DMA_SLAVE_WIDTH_32BIT, 43 43 }; 44 44 45 + /* bursts size */ 46 + enum dw_dma_msize { 47 + DW_DMA_MSIZE_1, 48 + DW_DMA_MSIZE_4, 49 + DW_DMA_MSIZE_8, 50 + DW_DMA_MSIZE_16, 51 + DW_DMA_MSIZE_32, 52 + DW_DMA_MSIZE_64, 53 + DW_DMA_MSIZE_128, 54 + DW_DMA_MSIZE_256, 55 + }; 56 + 57 + /* flow controller */ 58 + enum dw_dma_fc { 59 + DW_DMA_FC_D_M2M, 60 + DW_DMA_FC_D_M2P, 61 + DW_DMA_FC_D_P2M, 62 + DW_DMA_FC_D_P2P, 63 + DW_DMA_FC_P_P2M, 64 + DW_DMA_FC_SP_P2P, 65 + DW_DMA_FC_P_M2P, 66 + DW_DMA_FC_DP_P2P, 67 + }; 68 + 45 69 /** 46 70 * struct dw_dma_slave - Controller-specific information about a slave 47 71 * ··· 79 55 * @cfg_lo: Platform-specific initializer for the CFG_LO register 80 56 * @src_master: src master for transfers on allocated channel. 81 57 * @dst_master: dest master for transfers on allocated channel. 58 + * @src_msize: src burst size. 59 + * @dst_msize: dest burst size. 60 + * @fc: flow controller for DMA transfer 82 61 */ 83 62 struct dw_dma_slave { 84 63 struct device *dma_dev; ··· 92 65 u32 cfg_lo; 93 66 u8 src_master; 94 67 u8 dst_master; 68 + u8 src_msize; 69 + u8 dst_msize; 70 + u8 fc; 95 71 }; 96 72 97 73 /* Platform-configurable bits in CFG_HI */