/* Set DMA address
*
* Copy address to the structure, and set the invalid bit
*/
void __set_dma_addr (unsigned int chan, void *addr)
{
dma_t *dma = dma_channel(chan); if (dma->active)
printk(KERN_ERR "dma%d: altering DMA address while "
"DMA active\n", chan);
dma->sg = NULL;
dma->addr = addr;
dma->invalid = 1;
}
---------------------------------------------------------------------
/* Set the DMA byte count for this channel
*
* This should not be called if a DMA channel is enabled,
* especially since some DMA architectures don't update the
* DMA count immediately, but defer it to the enable_dma().
*/
extern void set_dma_count(unsigned int chan, unsigned long count);
该函数对传输的字节赋值,count表示16位通道的字节数
----------------------------------------------------------------------
/* Set the transfer direction for this channel
*
* This should not be called if a DMA channel is enabled,
* especially since some DMA architectures don't update the
* DMA transfer direction immediately, but defer it to the
* enable_dma().
*/
extern void set_dma_mode(unsigned int chan, unsigned int mode);
指出通道从设备读(DMA_MODE_WRITE)或写(DMA_MODE_READ),注意这里的
write或read都是对cpu而言的,向cpu写--当然就是从设备读取数据了。
当mode设置为DMA_MODE_CASCADE时,表示释放对总线的控制。
void set_dma_mode (unsigned int chan, unsigned int mode)
{
dma_t *dma = dma_channel(chan);
if (dma->active)
printk(KERN_ERR "dma%d: altering DMA mode while "
"DMA active\n", chan);
dma->dma_mode = mode;
dma->invalid = 1;
}
------------------------------------------------------------
/* Set the transfer speed for this channel
*/
extern void set_dma_speed(unsigned int chan, int cycle_ns);
--------------------------------------------------------------------
/* Get DMA residue count. After a DMA transfer, this
* should return zero. Reading this while a DMA transfer is
* still in progress will return unpredictable results.
* If called before the channel has been used, it may return 1.
* Otherwise, it returns the number of _bytes_ left to transfer.
*/
extern int get_dma_residue(unsigned int chan);
该函数查询一个DMA传输还有多少字节没有传输完,
函数返回剩余的字节数,当传输成功时,该函数返回0.
-------------------------------------------------------------
/* enable/disable a specific DMA channel */
static inline void enable_dma(unsigned int dmanr)
{
if (dmanr <= 3)
dma_outb(dmanr, DMA1_MASK_REG);
else
dma_outb(dmanr & 3, DMA2_MASK_REG);
}
在DMA通道中包含了合法的数据时,该函数激活DMA控制器
----------------------------------------------------
static inline void disable_dma(unsigned int dmanr)
{
if (dmanr <= 3)
dma_outb(dmanr | 4, DMA1_MASK_REG);
else
dma_outb((dmanr & 3) | 4, DMA2_MASK_REG);
}
该函数禁止DMA通道,对它的设置应该在配置DMA之前