s3c2410多通道adc驱动及测试程序(使用write控制多通道)

2024-02-10 03:18

本文主要是介绍s3c2410多通道adc驱动及测试程序(使用write控制多通道),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

免责声明:

本文所涉及的驱动是在SeonKon Choi于2003年编写的适合2.4版本内核的ADC驱动基础上结合网络能找得到的代码片段经过自己的修改并实践通过的。测试过程中的ADC并不涉及其它驱动(比如与ADC有很密切关系的触摸屏驱动)。本文作者本着GNU共享精神发表此文并附录源代码——其实公布源代码是必须的,因为代码使用GPL(而如何行文则是作者的自由)。至于如何使用文中知识点及代码,无论正确与否,概与文章作者无关,风险自担。不过,趁文章作者还有激情研究驱动之时,欢迎一起讨论,大家共同学习,天天向上。

 

杂项:

本文上接《s3c2410多通道adc驱动及测试程序》,里面承诺了用write来传递数据到内核中。那篇文章使用ioctl来控制通道,而本文使用write控制通道。而两者的驱动,在本质上是一致的——除了针对内核版本不同而有所修改外。

 

收获:

在修改人家驱动代码过程中,对于一些不确定的函数(比如位于哪个头文件,每个函数参数的含义),逐一google之,并查看内核源代码。个人认为,学习代码、驱动这种事情,最好在实践中学习,看书与实践结合起来。话虽如此,真正做到的人却不多。如果不去动手写,看再多的LDD3、ELDD、ULK、APUE、CSAPP也收获不丰,印象不深。说来惭愧,正是这个观点,让我一直不去看书,至今连LDD3也没看完,APUE也刚开了个头。

 

未尽及将来可能会做的事:

1、与TS共享中断,使用信号量进行互斥访问。

2、其它的。

 

正文:

如想直接抄代码,可忽略行文,直接到文章后面下载附录的工程压缩包或源代码。

1、对于头文件,不必说太多,2.4版本的内核有些头文件已经删除或修改或合并等等,比如像<linux/config.h>已经不在了。

2、使用ioremap,这使得代码整洁、易看。举一例:

网上使用如下代码片段(示意性代码)设置通道,读取ADC数据:

writel((1<<14) | PRSCVL(adcdev.prescale) | ADC_INPUT(adcdev.channel) | 0x01 | 0x01, S3C2410_ADCCON);

ret = readl(S3C2410_ADCDAT0);

 

使用宏后:

 START_ADC_AIN(adcdev.channel, adcdev.prescale);

 ret = ADCDAT0;

 

其中START_ADC_AIN将设置通道、启动ADC等合在一起,ADCDAT0是经过ioremap后加上一偏移得到的“寄存器”。

如此一来,是不是觉得后面的代码很直观很容易看?不过这也有一点不好,封闭得太多了,对于想知道其中原理的人来说可不是件好事。比如声明一个信号量,使用DECLARE_MUTEX(ADC_LOCK)或DEFINE_SEMAPHORE(ADC_LOCK),这很好懂,但是这个宏到底做了些什么呢?这就要深入到这个宏定义所在文件中研究了(在<linux/semaphore.h>文件中)。

 

对于这两宏,想说几句,因为最近一次移植新版本的内核(2.6.37.3),就是因为DECLARE_MUTEX不再使用而导致我浪费了几天的时间。据本人考查,最早说要将DECLARE_MUTEX改为DEFINE_SEMAPHORE是在08年10月底,参见地址http://lwn.net/Articles/304725/。而在Linux Cross Reference(网站如http://lxr.free-electrons.com/等等)中发现,直到2.6.36才出现DEFINE_SEMAPHORE,而且这个版本中两个宏同时存在。但是到了2.6.37,DECLARE_MUTEX这个宏却不存在了。

不由得想到某个论坛的签名,原文是英文的,原文及出处一时不知道去哪找了。大意是说UNIX最好的地方是什么?答曰:有社区,再问UNIX不好的地方是什么?答曰:有太多的社区。像Linux内核这东西,版本更新太快了,各种结构体名称变化、成员变化及新增函数、删除函数,让人目不暇接。虽说一味追求新版本不好,但是心理作用,还是选择新的版本来移植。新的东西当然有它的好,像买台android的手机,就得不停的刷机,不断折腾,这跟搞Linux在某种程度上是一样的。

 

3、硬件寄存器

ADC驱动涉及的寄存器不多,都可以在datasheet中找到说明的。如:

#define PRSCVL(x)              ((x) << 6)
#define ADC_INPUT(x)        ((x) << 3)
#define ADC_START            (1 << 0)

 

第一个是设置AD转换器预定频率(注:该术语可能不标准),左移6位,是因为ADCCON寄存器的6~13位就是这个值。而ADC_INPUT是选择通道的,位于ADCCON寄存器的3~5位。最后一行是使能ADC(启动ADC),位于ADCCON第0位,1表示开始转换(注:根据datasheet英文理解)。

其实这些不难理解的,看多代码了,自然也知道了。自从当年学AVR后,我对这种方式的移位特别有好感,甚至一度上瘾,常常跟别人说,不过没多少人理解,后来就算了,自己独自享受这种便捷了。

 

4、与原来代码的改动:

1)、去掉MOD_INC_USE_COUNT和MOD_DEC_USE_COUNT,这个据说在2.6中不再使用了。

2)、对于request_irq函数,将IRQ_ADC_DONE改为IRQ_ADC,最后一个参数改为&adcdev。

3)、将adcdone_int_handler函数返回类型由原来的void改为irqreturn_t。

4)、另外添加cdev类型的变量,因为注册字符设备需要使用到。

5)、判断copy_from_user、copy_to_user两个函数的返回值,正常返回0,出错则返回没有复制成功的字节数。出错时返回-EFAULT。如果不判断,会出现一个警告,比如:

warning: ignoring return value of 'copy_to_user', declared with attribute warn_unused_result

内核中很多地方都使用这两个函数,都作了判断。

 

其它的修改不一一道来了。

 

测试过程:

测试手段很多,由于本人的网络驱动一直不成功,不能使用方便快捷的NFS方式来测试。将编译好的驱动模块和交叉编译后的测试程序拷贝到U盘,再用U盘复制到开发板上,在这个过程中,文件丢失了可执行性,又得在开发板上用chmod恢复可执行性。很是麻烦。

 

原想将未修改的代码与修改后的代码作一个patch的,不过有10KB那么大,就不帖出来了(附件里有)。下面附上工程目录及源代码。如果网页显示与工程文件不一致,以工程目录中的文件为准。实际代码中没有中文注释,由此带来的各种质问及不解,本人不作解释。

 

整个工程下载(压缩文件名称为s3c2410-adc-latelee.org.tar.bz2,md5sum为0aa975c62eaefb8d05430bca8d7df088):

---

 

应用层的测试代码:

---

本人得到的原始的源代码如下:

---

经过修改后的源代码:

---

原文出处:www.latelee.org/embedded-linux/mutil-channel-adc-of-s3c2410-write.html

这篇关于s3c2410多通道adc驱动及测试程序(使用write控制多通道)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/695995

相关文章

一文详解如何使用Java获取PDF页面信息

《一文详解如何使用Java获取PDF页面信息》了解PDF页面属性是我们在处理文档、内容提取、打印设置或页面重组等任务时不可或缺的一环,下面我们就来看看如何使用Java语言获取这些信息吧... 目录引言一、安装和引入PDF处理库引入依赖二、获取 PDF 页数三、获取页面尺寸(宽高)四、获取页面旋转角度五、判断

C++中assign函数的使用

《C++中assign函数的使用》在C++标准模板库中,std::list等容器都提供了assign成员函数,它比操作符更灵活,支持多种初始化方式,下面就来介绍一下assign的用法,具有一定的参考价... 目录​1.assign的基本功能​​语法​2. 具体用法示例​​​(1) 填充n个相同值​​(2)

Spring StateMachine实现状态机使用示例详解

《SpringStateMachine实现状态机使用示例详解》本文介绍SpringStateMachine实现状态机的步骤,包括依赖导入、枚举定义、状态转移规则配置、上下文管理及服务调用示例,重点解... 目录什么是状态机使用示例什么是状态机状态机是计算机科学中的​​核心建模工具​​,用于描述对象在其生命

使用Python删除Excel中的行列和单元格示例详解

《使用Python删除Excel中的行列和单元格示例详解》在处理Excel数据时,删除不需要的行、列或单元格是一项常见且必要的操作,本文将使用Python脚本实现对Excel表格的高效自动化处理,感兴... 目录开发环境准备使用 python 删除 Excphpel 表格中的行删除特定行删除空白行删除含指定

深入理解Go语言中二维切片的使用

《深入理解Go语言中二维切片的使用》本文深入讲解了Go语言中二维切片的概念与应用,用于表示矩阵、表格等二维数据结构,文中通过示例代码介绍的非常详细,需要的朋友们下面随着小编来一起学习学习吧... 目录引言二维切片的基本概念定义创建二维切片二维切片的操作访问元素修改元素遍历二维切片二维切片的动态调整追加行动态

prometheus如何使用pushgateway监控网路丢包

《prometheus如何使用pushgateway监控网路丢包》:本文主要介绍prometheus如何使用pushgateway监控网路丢包问题,具有很好的参考价值,希望对大家有所帮助,如有错误... 目录监控网路丢包脚本数据图表总结监控网路丢包脚本[root@gtcq-gt-monitor-prome

Python通用唯一标识符模块uuid使用案例详解

《Python通用唯一标识符模块uuid使用案例详解》Pythonuuid模块用于生成128位全局唯一标识符,支持UUID1-5版本,适用于分布式系统、数据库主键等场景,需注意隐私、碰撞概率及存储优... 目录简介核心功能1. UUID版本2. UUID属性3. 命名空间使用场景1. 生成唯一标识符2. 数

浅析Spring如何控制Bean的加载顺序

《浅析Spring如何控制Bean的加载顺序》在大多数情况下,我们不需要手动控制Bean的加载顺序,因为Spring的IoC容器足够智能,但在某些特殊场景下,这种隐式的依赖关系可能不存在,下面我们就来... 目录核心原则:依赖驱动加载手动控制 Bean 加载顺序的方法方法 1:使用@DependsOn(最直

SpringBoot中如何使用Assert进行断言校验

《SpringBoot中如何使用Assert进行断言校验》Java提供了内置的assert机制,而Spring框架也提供了更强大的Assert工具类来帮助开发者进行参数校验和状态检查,下... 目录前言一、Java 原生assert简介1.1 使用方式1.2 示例代码1.3 优缺点分析二、Spring Fr

Android kotlin中 Channel 和 Flow 的区别和选择使用场景分析

《Androidkotlin中Channel和Flow的区别和选择使用场景分析》Kotlin协程中,Flow是冷数据流,按需触发,适合响应式数据处理;Channel是热数据流,持续发送,支持... 目录一、基本概念界定FlowChannel二、核心特性对比数据生产触发条件生产与消费的关系背压处理机制生命周期