liunx sys属性节点的使用(一个简单小例子)

来源:互联网 发布:淘宝关键字 编辑:程序博客网 时间:2024/06/03 19:53

这个内核驱动代码:

#include <linux/module.h>#include <linux/platform_device.h>#include <linux/slab.h>#include <linux/input.h>#include <linux/kthread.h>#include <linux/semaphore.h>struct v_dev{struct platform_device *p_dev;struct input_dev *input;int x;int y;struct task_struct *run_thread;struct semaphore sem;};struct v_dev *vmouse_dev = NULL;static ssize_t write_pos(struct device *dev, struct device_attribute *attr,             const char *buf, size_t count){int x,y;sscanf(buf,"%d%d",&x,&y);vmouse_dev->x = x;vmouse_dev->y =y;//post 信号量up(&vmouse_dev->sem);return count;}static ssize_t show_pos(struct device *dev, struct device_attribute *attr,            char *buf){return sprintf(buf,"(%d,%d)\n",vmouse_dev->x,vmouse_dev->y);}DEVICE_ATTR(pos,0644,show_pos,write_pos);static int vmouse_thread(void *data){int x,y;struct v_dev *vmouse_dev = (struct v_dev*)data;struct semaphore *sema = &(vmouse_dev->sem);printk(KERN_INFO "vmouse thread running\n");while(1){//等待信号量while((down_interruptible(sema)) == -EINTR){} ;x = vmouse_dev->x;y = vmouse_dev->y;input_report_abs(vmouse_dev->input,ABS_X,x);input_report_abs(vmouse_dev->input,ABS_Y,y);input_sync(vmouse_dev->input);printk("vmouse thread report\n");}return 0;}static int vmouse_probe(struct platform_device *pdev){int ret = -1;printk("%s debug \n",__func__);if(vmouse_dev->p_dev == pdev){printk("platform device is same\n");}vmouse_dev->input = input_allocate_device();if(!(vmouse_dev->input)){printk("%s request input deivce error\n",__func__);goto alloc_input;}vmouse_dev->input->name = "vmouse";set_bit(EV_ABS,vmouse_dev->input->evbit);input_set_abs_params(vmouse_dev->input, ABS_X, -1024, 1024, 0, 0);input_set_abs_params(vmouse_dev->input, ABS_Y, -1024, 1024, 0, 0);ret = input_register_device(vmouse_dev->input);if(ret < 0){printk("%s register input device error\n",__func__);goto input_register;}device_create_file(&pdev->dev,&dev_attr_pos);//初始化信号量,在线程中要用到sema_init(&(vmouse_dev->sem),0);vmouse_dev->run_thread = kthread_run(vmouse_thread,vmouse_dev,"vmouse_thread");return 0;input_register:input_free_device(vmouse_dev->input);alloc_input:kfree(vmouse_dev);return ret;}static struct platform_driver vmouse_driver = {.probe = vmouse_probe,.driver = {.owner = THIS_MODULE,.name = "v_mouse",},};static int __init vmouse_init(void){int ret =-1;printk("%s\n", __func__);vmouse_dev = kzalloc(sizeof(struct v_dev),GFP_KERNEL);if(vmouse_dev == NULL){printk("%s alloc memory  error\n",__func__);return -ENOMEM;}vmouse_dev->p_dev= platform_device_register_simple("v_mouse",-1,NULL,0);if(!(vmouse_dev->p_dev)){printk("%s register platform device error\n",__func__);return ret;}ret = platform_driver_register(&vmouse_driver);if(ret < 0){printk("%s register driver error\n",__func__);return ret;}return 0;}static void __exit vmouse_exit(void){printk("%s\n", __func__);if(vmouse_dev->input != NULL){input_unregister_device(vmouse_dev->input);}printk("%s debug__1\n",__func__);if(vmouse_dev != NULL){platform_device_unregister(vmouse_dev->p_dev);}printk("%s debug__2\n",__func__);platform_driver_unregister(&vmouse_driver);printk("%s debug__3\n",__func__);kfree(vmouse_dev);printk("%s debug__4\n",__func__);}module_init(vmouse_init);module_exit(vmouse_exit);MODULE_LICENSE("GPL");MODULE_AUTHOR("WEED<weed_hz@126.com>");
应用层测试代码:

#include <fcntl.h>#include <linux/input.h>#include <stdio.h>//要看自己的节点了#define EVENT_DEV "/dev/input/event5"int main(void){struct input_event ev;int count,x,y;int fd = open(EVENT_DEV, O_RDWR);if(fd < 0){printf("open %s failed\n",EVENT_DEV);return 0;}while(1){count = read(fd, &ev,sizeof(struct input_event));if(EV_ABS == ev.type){if(ev.code == ABS_X){x = ev.value;}else if(ev.code == ABS_Y){y = ev.value;}printf("position: x=%d, y=%d\n",x,y);}else if(EV_SYN == ev.type){puts("sync!");}}return 0;}
先运行应用程序:./test_sys  
在另一个终端执行:echo "90 90" >/sys/devices/platform/v_mouse/pos

你就会看到你input设备上报的坐标,打印信息如下:

position: x=90, y=0
position: x=90, y=90
sync!

原创粉丝点击