前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >详解linux dma驱动编写

详解linux dma驱动编写

作者头像
砸漏
发布2020-10-19 17:50:45
3.6K0
发布2020-10-19 17:50:45
举报
文章被收录于专栏:恩蓝脚本

linux下面的驱动虽然什么样的情形都有,但是dma驱动却并不少见。dma可以有很多的好处,其中最重要的功能就是能够帮助我们将数据搬来搬去,这个时候cpu就由时间去做别的事情了,提高了设备效率。

1、dma驱动在什么地方

代码语言:javascript
复制
drivers/dma 

2、如何看s3c的dma驱动,先看Kconfig

代码语言:javascript
复制
config S3C24XX_DMAC 
  bool "Samsung S3C24XX DMA support" 
  depends on ARCH_S3C24XX || COMPILE_TEST 
  select DMA_ENGINE 
  select DMA_VIRTUAL_CHANNELS 
  help 
   Support for the Samsung S3C24XX DMA controller driver. The 
   DMA controller is having multiple DMA channels which can be 
   configured for different peripherals like audio, UART, SPI. 
   The DMA controller can transfer data from memory to peripheral, 
   periphal to memory, periphal to periphal and memory to memory. 

3、发现s3c只依赖于S3C24XX_DMAC,这样可以接着看Makefile

代码语言:javascript
复制
obj-$(CONFIG_S3C24XX_DMAC) += s3c24xx-dma.o 

4、确认驱动文件为s3c24xx-dma.c,了解基本结构

代码语言:javascript
复制
static struct platform_driver s3c24xx_dma_driver = { 
  .driver   = { 
    .name  = "s3c24xx-dma", 
  }, 
  .id_table  = s3c24xx_dma_driver_ids, 
  .probe   = s3c24xx_dma_probe, 
  .remove   = s3c24xx_dma_remove, 
}; 
 
module_platform_driver(s3c24xx_dma_driver); 

5、驱动为基本的platform driver,接着就可以了解probe函数了

代码语言:javascript
复制
/* Initialize memcpy engine */ 
dma_cap_set(DMA_MEMCPY, s3cdma->memcpy.cap_mask); 
dma_cap_set(DMA_PRIVATE, s3cdma->memcpy.cap_mask); 
s3cdma->memcpy.dev = &pdev->dev; 
s3cdma->memcpy.device_free_chan_resources = 
        s3c24xx_dma_free_chan_resources; 
s3cdma->memcpy.device_prep_dma_memcpy = s3c24xx_dma_prep_memcpy; 
s3cdma->memcpy.device_tx_status = s3c24xx_dma_tx_status; 
s3cdma->memcpy.device_issue_pending = s3c24xx_dma_issue_pending; 
s3cdma->memcpy.device_config = s3c24xx_dma_set_runtime_config; 
s3cdma->memcpy.device_terminate_all = s3c24xx_dma_terminate_all; 
s3cdma->memcpy.device_synchronize = s3c24xx_dma_synchronize; 
 
/* Initialize slave engine for SoC internal dedicated peripherals */ 
dma_cap_set(DMA_SLAVE, s3cdma->slave.cap_mask); 
dma_cap_set(DMA_CYCLIC, s3cdma->slave.cap_mask); 
dma_cap_set(DMA_PRIVATE, s3cdma->slave.cap_mask); 
s3cdma->slave.dev = &pdev->dev; 
s3cdma->slave.device_free_chan_resources = 
        s3c24xx_dma_free_chan_resources; 
s3cdma->slave.device_tx_status = s3c24xx_dma_tx_status; 
s3cdma->slave.device_issue_pending = s3c24xx_dma_issue_pending; 
s3cdma->slave.device_prep_slave_sg = s3c24xx_dma_prep_slave_sg; 
s3cdma->slave.device_prep_dma_cyclic = s3c24xx_dma_prep_dma_cyclic; 
s3cdma->slave.device_config = s3c24xx_dma_set_runtime_config; 
s3cdma->slave.device_terminate_all = s3c24xx_dma_terminate_all; 
s3cdma->slave.device_synchronize = s3c24xx_dma_synchronize; 
s3cdma->slave.filter.map = pdata->slave_map; 
s3cdma->slave.filter.mapcnt = pdata->slavecnt; 
s3cdma->slave.filter.fn = s3c24xx_dma_filter; 

6、通过code获悉,s3cdma有master和slave两个engine,且部分接口共享。

只要完成dma接口的适配,dma就可以正常使用了。当然,前提是,两个engine要进行注册使用。

代码语言:javascript
复制
ret = dma_async_device_register(&s3cdma->memcpy); 
if (ret) { 
  dev_warn(&pdev->dev, 
    "%s failed to register memcpy as an async device - %d\n", 
    __func__, ret); 
  goto err_memcpy_reg; 
} 
 
ret = dma_async_device_register(&s3cdma->slave); 
if (ret) { 
  dev_warn(&pdev->dev, 
    "%s failed to register slave as an async device - %d\n", 
    __func__, ret); 
  goto err_slave_reg; 
} 

以上就是本文的全部内容,希望对大家的学习有所帮助。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2020-09-11 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档