Use Example
The following code block provides a DMA use case.
/* Request a callback function for transmission complete */ static void dma_complete_func(void *arg) { struct completion *done = (struct completion *)arg; complete(done); } struct dma_chan *chan; dma_cap_mask_t mask; dma_cookie_t cookie; struct dma_slave_config config; struct dma_tx_state state; struct dma_async_tx_descriptor *tx = NULL; void *src_buf; dma_addr_t src_dma; dma_cap_zero(mask); dma_cap_set(DMA_SLAVE, mask); dma_cap_set(DMA_CYCLIC, mask); /* Request an available channel */ chan = dma_request_channel(dt->mask, NULL, NULL); if (!chan){ return -EINVAL; } src_buf = kmalloc(1024*4, GFP_KERNEL); if (!src_buf) { dma_release_channel(chan); return -EINVAL; } /* Use DMA to visit the mapping address */ src_dma = dma_map_single(NULL, src_buf, 1024*4, DMA_TO_DEVICE); config.direction = DMA_MEM_TO_DEV; config.src_addr = src_dma; config.dst_addr = 0x01c; config.src_addr_width = DMA_SLAVE_BUSWIDTH_2_BYTES; config.dst_addr_width = DMA_SLAVE_BUSWIDTH_2_BYTES; config.src_maxburst = 1; config.dst_maxburst = 1; dmaengine_slave_config(chan, &config); tx = dmaengine_pre_dma_cyclic(chan, scr_dma, 1024*4, 1024, DMA_MEM_TO_DEV, DMA_PREP_INTERRUPT | DMA_CTRL_ACK); /* Set the callback function for transmission complete */ tx->callback = dma_complete_func; /* submit and start the transmission */ cookie = dmaengine_submit(tx); dma_async_issue_pending(chan);