input_open_file()浅析
来源:互联网 发布:淘宝客服晚上几点下班 编辑:程序博客网 时间:2024/06/05 17:10
/* 当用户空间调用open()的时候,这个函数最终会被调用。 这个函数主要: 将打开文件的f_op替换成了input_handler中定义的fops 如果以后用户层调用read、write、ioctl....系统调用, 那么input_handler中fops中定义的对应方法会被调用到 vfs_read: ssize_t vfs_read(struct file *file, char __user *buf, size_t count, loff_t *pos) { .... if (file->f_op->read){ ret = file->f_op->read(file, buf, count, pos); } ....}如: evdev中这些方法会被调用到。 static const struct file_operationsevdev_fops = { .owner = THIS_MODULE, .read = evdev_read, .write = evdev_write, .poll = evdev_poll, .open = evdev_open, .release = evdev_release, .unlocked_ioctl = evdev_ioctl, }; 这个函数和v4l2、framebuffer子系统中的open函数有点类似 . v4l2、framebuffer的一些函数以前博文中有分析过。这里就简单的列举一下。 比如 : v4l2: 当用户层调用open()的时候,v4l2_open()也会被调用 static int v4l2_open(struct inode *inode, struct file *filp) { struct video_device *vdev; ... vdev = video_devdata(filp); 也是从一个数组中取出对应的video_device if (vdev->fops->open) { ret = vdev->fops->open(filp); //也是调用具体设备提供的操作方法 } } 不一样的是,在open函数中没有替换file->f_op,它使用的是另外一种策略 在看fb fb_open(struct inode *inode, struct file *file) { int fbidx = iminor(inode); struct fb_info *info; int res = 0; info = get_fb_info(fbidx); //也是从一个数组中获取对应的fb_info file->private_data = info; //也是调用了具体设备提供的操作函数 if (info->fbops->fb_open) { res = info->fbops->fb_open(info,1); } }*/static int input_open_file(struct inode * inode,struct file *file){ struct input_handler * handler; const struct file_operations *old_fops,*new_fops = NULL; int err; /** 获取互斥锁----访问临界区----释放互斥锁 */ //获取互斥锁,可以被信号打断,在等待锁的过程中 //如果有信号的到来,该函数返回-EINTR err = mutex_lock_interruptible(&input_mutex); if (err) { return err; } /** minor(ionde) :获取次设备号 从input_table[]中获取对应的input_handler 好,看看input_table[] 一指针数组 static struct input_handler *input_table[8]; 在什么时候被填充? 在时间处理层 向核心层 注册input_handler的时候 int input_register_handler(struct input_handler *handler) { //如果这个被注册的input_handler提供了file_operations if (handler->fops != NULL) { if (input_table[handler->minor >> 5]) { retval = -EBUSY; goto out; } //将这个被注册的input_handler依据次设备号位索引值放入到input_table[]中 //这个minor = input_table[]中空缺项的索引值 input_table[handler->minor >> 5] = handler; } } 在void input_unregister_handler(struct input_handler *handler) { .... //从input_table[]中删除 if (handler->fops != NULL){ input_table[handler->minor >> 5] = NULL; } } */ handler = input_table[minor(inode)>>5]; if (handler) { /** 将取出来的input_handler的fops赋值给new_fops 例如:evdev input_handler: static struct input_handler evdev_handler = { .event = evdev_event, .connect = evdev_connect, .disconnect = evdev_disconnect, .fops = &evdev_fops, .minor = EVDEV_MINOR_BASE, .name = "evdev", .id_table = evdev_ids, }; fops: static const struct file_operations evdev_fops = { .owner = THIS_MODULE, .read = evdev_read, .write = evdev_write, .poll = evdev_poll, .open = evdev_open, .release = evdev_release, .unlocked_ioctl = evdev_ioctl, #ifdef CONFIG_COMPAT .compat_ioctl = evdev_ioctl_compat, #endif .fasync = evdev_fasync, .flush = evdev_flush, .llseek = no_llseek, }; */ //比如 现在的new_fops 等价于 evdev_fops new_fops = fops_get(handler->fops); } mutex_unlock(&input_mutex);//释放互斥体 /** 如果取出来的input_handler中没有定义fops 或者定义了fops,但是fops中没有定义open函数,那么会失败返回 */ if (!new_fops || !new_fops->open) { fops_put(new_fops); err = -ENODEV; goto out; } old_fops = file->f_op; /** 将取出来的input_handler的fops赋给 打开文件的f_op 如果是evdev :这样,以后使用到文件的f_op就变成了 evdev_fops */ file->f_op = new_fops; /** 调用这个input_handler中定义的fops中的open函数 如果input_handler是evdev的话,evdev_open函数就会被调用 */ err = new_fops->open(inode, file); if (err) { fops_put(file->f_op); file->f_op = fops_get(old_fops); } fops_put(old_fops);}
0 0
- input_open_file()浅析
- 浅析
- 浅析
- 电子邮件浅析
- 浅析GLib
- 浅析激光打印机
- NPetsShop浅析
- 嵌入式 浅析
- 浅析GLib
- 浅析ArcIMS
- 浅析ArcIMS
- enum 浅析
- 浅析WebGIS
- fstream 浅析
- ClassLoader浅析
- 浅析ArcIMS
- AOP浅析
- HashMap浅析
- 欢迎使用CSDN-markdown编辑器
- Bundle类 android基础一
- swift开发中No such module 'Cocoa' 错误
- hibernate 使用jdbc批量插入数据
- 1877: [SDOI2009]晨跑
- input_open_file()浅析
- Virtualbox正在运行虚拟机,被强制中断导致虚拟机无法启动(start按钮为灰色)解决方案
- Struts2 Convention Plugin ( struts2 零配置 )
- 向上转型的理解
- Android之如何解决popupWindow(pw.setFocusable(true))按返回键和menu键退出
- List,set,Map 的用法和区别
- iOS自定义TabBar
- 关于SearchView设置字体颜色,提示字体及背景的解决方法
- php composer