下面是S3C2440A数据手册上的一段截图,展示了4个DMA通道和每个通道对应的DMA源:
对这些DMA通道和其对应DMA源的管理在文件linux/arch/arm/mach-s3c2440/dma.c中实现。
在文件dma.c中定义了一个结构体数组static struct s3c24xx_dma_map __initdata s3c2440_dma_mappings[],
这个结构体将所有DMA源和每个DMA源所能请求的DMA通道联系了起来。
这个管理结构体原型如下:
struct s3c24xx_dma_map {
const char *name; //DMA源的名
struct s3c24xx_dma_addr hw_addr; //源的物理地址。
unsigned long channels[S3C2410_DMA_CHANNELS]; //在S3C2440中S3C2410_DMA_CHANNELS为4,。
unsigned long channels_rx[S3C2410_DMA_CHANNELS];
};
static struct s3c24xx_dma_map __initdata s3c2440_dma_mappings[] = {
[DMACH_XD0] = {
.name = "xdreq0",
.channels[0] = S3C2410_DCON_CH0_XDREQ0 | DMA_CH_VALID,
},
[DMACH_XD1] = {
.name = "xdreq1",
.channels[1] = S3C2410_DCON_CH1_XDREQ1 | DMA_CH_VALID,
},
[DMACH_SDI] = {
.name = "sdi", //DMA源为SD卡 ,该源可以对四个DMA通道发出DMA请求。
.channels[0] = S3C2410_DCON_CH0_SDI | DMA_CH_VALID, // DMA_CH_VALID表明将该通道初始化为可用。
.channels[1] = S3C2440_DCON_CH1_SDI | DMA_CH_VALID,
//S3C2440_DCON_CH2_SDI将被写入DMA控制寄存器,用于DMA通道请求源选择。
.channels[2] = S3C2410_DCON_CH2_SDI | DMA_CH_VALID,
.channels[3] = S3C2410_DCON_CH3_SDI | DMA_CH_VALID,
.hw_addr.to = S3C2410_PA_IIS + S3C2410_IISFIFO,
.hw_addr.from = S3C2410_PA_IIS + S3C2410_IISFIFO,
},
[DMACH_SPI0] = {
.name = "spi0",
.channels[1] = S3C2410_DCON_CH1_SPI | DMA_CH_VALID,
.hw_addr.to = S3C2410_PA_SPI + S3C2410_SPTDAT,
.hw_addr.from = S3C2410_PA_SPI + S3C2410_SPRDAT,
},
[DMACH_SPI1] = {
.name = "spi1",
.channels[3] = S3C2410_DCON_CH3_SPI | DMA_CH_VALID,
.hw_addr.to = S3C2410_PA_SPI + 0x20 + S3C2410_SPTDAT,
.hw_addr.from = S3C2410_PA_SPI + 0x20 + S3C2410_SPRDAT,
},
[DMACH_UART0] = {
.name = "uart0",
.channels[0] = S3C2410_DCON_CH0_UART0 | DMA_CH_VALID,
.hw_addr.to = S3C2410_PA_UART0 + S3C2410_UTXH,
.hw_addr.from = S3C2410_PA_UART0 + S3C2410_URXH,
},
[DMACH_UART1] = {
.name = "uart1",
.channels[1]