代码学习inux内核驱动(六)
字符驱动设备
#include <linux/device.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/string.h>
#include <linux/uaccess.h>
#include <linux/fs.h>
#include <linux/cdev.h>
#include <linux/delay.h>
MODULE_AUTHOR("xyzeng");
MODULE_LICENSE("Dual BSD/GPL");
int hello_open (struct inode * node, struct file * pfile)
{
return 0;
}
ssize_t hello_read (struct file * pfile, char __user * pchar, size_t size, loff_t * off)
{
char * pstr = "hello fdfdf hell dfdfdffdfdf\n";
copy_to_user(pchar,pstr,strlen(pstr));
*off += strlen(pstr);
static long temp = 1024*2;
temp -= *off;
if((temp -64) > 0)
return temp;
else{
temp = 1024*2;
*off =0;
return 0 ;
}
}
ssize_t hello_write (struct file * pfile , const char __user * pchar, size_t size , loff_t * off)
{
char hello[64] ={0};
copy_from_user(hello,pchar,size);
printk("hello_write off:%d,size:%d,pchar:%s\n",*off,size,hello);
return size;
}
long hello_unlocked_ioctl (struct file * pfile, unsigned int cmd , unsigned long arg)
{
printk("hello_read :pfile:%p\n",pfile);
msleep(10*10000);
return 0;
}
struct file_operations hello_fop = {
.read = hello_read,
.write = hello_write,
.unlocked_ioctl = hello_unlocked_ioctl,
};
static struct cdev hello_cdev ={
.owner = THIS_MODULE,
.ops = &hello_fop,
};
static struct class *cls;
dev_t devid;
static int code_case_cdev_init( void )
{
#if 0
major = register_chrdev(0, "hello", &fop);
printk("register_chrdev :major :%d\n",major);
#else
devid = MKDEV(0,0);
cdev_init(&hello_cdev,&hello_fop);
int ret = alloc_chrdev_region(&devid,0,1,"hello_hello");
ret = cdev_add(&hello_cdev,devid,1);
printk("ret=%d,devid:%x\n",ret,devid);
cls = class_create(THIS_MODULE, "hello_ko");
if(cls != NULL){
device_create(cls, NULL,devid, NULL, "hello0");
} else {
printk("class_create: NULL\n");
}
return 0;
#endif
}
static void code_case_cdev_exit( void )
{
device_destroy(cls, devid);
class_destroy(cls);
cdev_del(&hello_cdev);
unregister_chrdev_region(devid, 1);
}
module_init(code_case_cdev_init);
module_exit(code_case_cdev_exit);