通过前面的学习,我们知道Linux内核是由大量而且复杂的代码组成的,而内核源码中又有很大一部分是各种驱动程序组成的。为了不使参与到Linux内核开发的“黑客”们不会被内核代码的复杂性淹没,设备驱动程序就是一个很好的进入Linux内核大门的入口。在接下来的一段时间里我们将要对Linux系统下的各个子系统进行归纳和学习,从而各个击破,以学习Linux下内核模块的设计和实现。
那我们就先从简单的驱动程序入手---字符设备驱动。
本节主要目标为使用字符设备,以了解字符驱动程序的工作机制。
提供好的字符驱动:memdev.c
编译:Makefile
相关理论知识:
对字符设备文件的访问:
由上图可知,应用程序是通过字符设备文件来找到对应的设备驱动程序进而控制字符设备。
字符设备文件通过主设备号与设备驱动程序一一对应。
创建字符设备文件的两种方法:1>使用mknod命令 ;2>使用函数在驱动程序中创建。
1>使用mknod命令创建设备文件
mknod /dev/文件名 c 主设备号 次设备号
查看开发板上的安装好的驱动的主设备号---252
次设备号选择范围(0-255)
在驱动代码中,我们是利用一个数组去模拟寄存器,进而操作数组==操作寄存器
则去操作驱动即是去操作寄存器。
2>实现写设备应用程序
注:在编译时使用静态编译该代码,因为开发板上没有函数库。
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
int main()
{
int fd;
fd = open("/dev/memdev0", O_RDWR);
if(-1 != fd)
{
write(fd, "hello", 6);
}
close(fd);
return 0;
}
3>实现读设备应用程序
#include <stdio.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>
int main()
{
int n;
int fd;
char buf[10];
fd = open("/dev/memdev0", O_RDWR);
if(-1 != fd)
{
if(n = read(fd, buf, 6))
{
printf("%s\n", buf);
}
}
return 0;
}
4>运行程序
先执行写设备用户程序,而后对字符设备文件进行读取。
读取结果为:
读出正确结果,说明设备驱动工作正常。即通过对 设备文件/dev/memdev0 .操作 设备驱动memdev 读写寄存器成功。
注:实验中遇到的错误
当在生成的可执行文件无法执行时,考虑是不是由于缺少该执行文件所需要的函数库导致的。。
如下:
使用readelf -d命令去查看该执行文件所需要的库
解决方法:使用静态链接的方式去编译。