分类: LINUX
2010-12-07 14:42:58
open sys_open 和 test_open
我在一个测试驱动是否正确的测试代码里看到如下:
int main()
{
.....省略
fd = open( "/dev/fs ",O_RDWR);
if (fd <= 0)
{ perror( "open ");
exit(1);
}
else printf( "open success ");
.....省略
}
这里就是说fd > 0 时,设备打开成功 。
但对应的驱动代码如下:
static int test_open(struct inode *inode ,struct file *file)
{MOD_INC_USE_COUNT ;
printk( "this is open \n ");
return 0 ;
}
这里的test_open函数返回的是 0
问题:
1.如你所说的:main中调用open函数时 ,先会调用sys_open()函数。请问open和sys_open是怎么关联上的?也就是说明明调用的是函数A,结果去执行函数B。这是如何实现的?
2. 如果是通过函数指针 把 open和test_open 关联上的话,那结果明显矛盾。因为打开文件成功的话,test_open函数返回的是 0 。fd <= 0的话,文件打开失败啊。矛盾矛盾。
回复如下。
LZ对LINUX设备驱动与内核的知识了解太少了,应用层调用open函数,首先会发出open系统调用,然后进入
内核,调用sys_open函数,打开文件系统中的/dev/fs文件,这个文件要么你是用mknod建立的,要么就直接在内核中用devfs方式来建立
的,无论你用哪种方式建立,最终都会读取其文件属性,如果发现其是设备文件,就会调用LINUX内核中的设备管理部分,根据其属性的主设备号(在建立设备
节点时已经把主设备号写入文件属性当中,如果你仔细看过mknod的用法就明白了),查找内核中相关联的file_operations,最终找到你的
test_open函数.
所以说 "在LINUX中设备即是文件 ",设备驱动首先会走文件系统这一条路(比如最先的 "/dev/fs
"),然后根据设备文件的属性最终找到相关联的file_operations,从而调用你的设备驱动例程.假如发现这个文件不是设备文件而只是磁盘文
件,就继续走文件系统,高速缓冲与磁盘调度这一条路了
这个问题深究起来,不是一下两下能说清楚的,跟高速缓冲区管理,文件系统管理,磁盘调度,设备管理甚至是进程管理都
有关系,你继续跟进open_namei函数与dentry_open函数去看,不过以你现在的水平还是不要再跟进去了,越进去越复杂,你只要记住一点,
当你在应用程中调用open函数,最终就会调用到你的device_open驱动例程中去,当然,前提是你的驱动是正确的,你的open函数的参数是正确
的,你的设备节点是正确的,同理,当你应用层调用write,read时,就会进入你驱动例程中的相应函数中去,明白这个原理就够了,至于是如何调用进去
的,等你有了相应的基础之后再来看。
至于书嘛,大概就四个步骤:
1.找本学习使用、配置LINUX的书置,任意一本都可以
2.找本讲解SHELL编程的书,只要包含Bash shell的任何一本书都可以
3.找本LINUX应用编程的书,听别人说过有两本: <
4. <
如果从头学起,大概需要两年时间才会有所斩获,就看你自己的基础了。
问:
大侠,我一直追着这个问题问是有原因的。
我本人不是学计算机的。软件方面的知识肯定不及硬件的多。写驱动的话,软硬件都得懂。硬件的操作在程序中哪里体现?不就是前面说的
device_open()函数中。要是把这个问题彻底弄懂了,就是弄懂了内核中对设备文件的操作是怎么转化到 对硬件的操作上来的。
=========================================
回复:
对硬件的操作一般不是在open中,而是在read,write里面,驱动做的一般也就是通过一些内核态的数据结构得到硬
件寄存器的值,按照相关硬件的规则做相应设置,你可以尝试写一些简单的驱动程序来实践,写一个简单的驱动,其实并不需要了解硬件很深,只需要你对
datasheet足够了解。
另外,设备驱动领域最经典的书还是 Linux Device Driver 3rd,强烈推荐,中英文都有。
chinaunix网友2010-12-08 15:07:53
很好的, 收藏了 推荐一个博客,提供很多免费软件编程电子书下载: http://free-ebooks.appspot.com