一:驅動基本框架
1:建立入口函式demo_init()和出口函式demo_exit()並用module_init(),module_exit(),module_license("gpl")函式進行註冊
二:填充驅動框架
1:入口函式中註冊裝置register_chrdev(),建立類class_create()以及裝置節點class_device_create()
2:建立入口函式中「註冊裝置」時所需的file_operations結構體demo_fops
static struct file_operations demo_fops
3:出口函式中刪除裝置節點class_device_unregister(),類class_destroy(),登出裝置unregister_chrdev()
4:在file_operations中對應的介面函式中實現對硬體的操作
三:原始碼
1:drv.c
#include #include #include #include #include #include #include #include #include #include #include #include #include static struct class *demo_class;
static struct class_device *demo_class_dev;
// gpf0,2
volatile unsigned long *gpfcon;
volatile unsigned long *gpfdat;
// gpg3,11
volatile unsigned long *gpgcon;
volatile unsigned long *gpgdat;
static struct timer_list key_timer;
static declare_wait_queue_head(irq_waitq);
static volatile int ev_press = 0;
static struct fasync_struct *signal_fasync;
struct pin_desc;
struct pin_desc pins_desc[3] = ,,,
};static struct pin_desc *irq_pd;
#if 0 //定義原子操作
static atomic_t canopen = atomic_init(1);
#else //定義互斥鎖
static declare_mutex(key_lock);
#endif
static unsigned char key_val;
static irqreturn_t keys_irq(int irq, void *dev_id)
static int demo_open(struct inode *inode, struct file *file)
#else
if(file->f_flags & o_nonblock)// 非阻塞,獲取不到資源則立即返回
else
#endif
request_irq(irq_eint0, keys_irq, irqt_bothedge, "s2", &pins_desc[0]);
request_irq(irq_eint2, keys_irq, irqt_bothedge, "s3", &pins_desc[1]);
request_irq(irq_eint11, keys_irq, irqt_bothedge, "s4", &pins_desc[2]);
return 0;
}ssize_t demo_read(struct file *file, char __user *buf, size_t size, loff_t *ppos)
else
copy_to_user(buf, &key_val, 1);
ev_press = 0;
return 1;
}int demo_release(struct inode *inode, struct file *file)
static unsigned int demo_poll(struct file *file, struct poll_table_struct *wait)
static int demo_fasync(int fd, struct file *filp, int on)
static struct file_operations demo_fops =
;int major;
static void key_timer_fun(unsigned long time)
else
ev_press = 1;
wake_up_interruptible(&irq_waitq);
kill_fasync(&signal_fasync, sigio, poll_in);
}static int demo_init(void)
static void demo_exit(void)
module_init(demo_init);
module_exit(demo_exit);
module_license("gpl");
2:test.c
#include #include #include #include #include #include #include #include #include int fd;
void signal_fun(int signum)
int main(int argc, char **ar**)
fcntl(fd, f_setown, getpid()); //告訴核心
oflags = fcntl(fd, f_getfl);
fcntl(fd, f_setfl, oflags | fasync);//改變fasync,會呼叫驅動中的fasync函式指標對應的函式。
while (1)
return 0;
}
2 6字元裝置驅動
chardev.c include include for file f op include include for copy to user include for cdev cdev init,cdev add module license gpl module author helight ...
字元裝置驅動3 字元類裝置驅動框架分析
前面的博文循規蹈矩按照無驅動框架的步驟分析了乙個簡單的字元裝置驅動,但是現如今更多是使用核心開發者提供的驅動框架來完成驅動的註冊,這樣的做法即可減少 的錯誤率,也能避免錯誤例如記憶體申請忘記釋放的問題,更能簡化驅動的開發難度,這裡就以乙個簡答的led類裝置驅動架構為例,分析字元裝置驅動框架 驅動框架...
5 字元裝置驅動LEDS
static int first drv open struct inode inode,struct file file static int first drv read struct file filp,char user buff,size t count,loff t offp stati...