成人在线你懂的-成人在线免费小视频-成人在线免费网站-成人在线免费视频观看-日韩精品国产一区二区-日韩精品国产一区

掃一掃
關注微信公眾號

深入淺出 Linux字符設備驅動程序解析
2007-04-30   網絡

llseek()函數 該函數用來修改文件的當前讀寫位置,并將新位置作為(正的)返回值返回,原型為:

loff_t (*llseek) (struct file *, loff_t, int);

poll()函數 poll 方法是poll 和select 這兩個系統調用的后端實現,用來查詢設備是否可讀或可寫,或是否處于某種特殊狀態,原型為:

unsigned int (*poll) (struct file *, struct poll_table_struct *);

我們將在"設備的阻塞與非阻塞操作"一節對該函數進行更深入的介紹。

 設備"gobalvar"的驅動程序的這些函數應分別命名為gobalvar_open、 gobalvar_ release、gobalvar_read、gobalvar_write、gobalvar_ioctl,因此設備"gobalvar"的基本入口點結構變量gobalvar_fops 賦值如下:

struct file_operations gobalvar_fops = {

 read: gobalvar_read,

 write: gobalvar_write,

};

  上述代碼中對gobalvar_fops的初始化方法并不是標準C所支持的,屬于GNU擴展語法。

  完整的globalvar.c文件源代碼如下:

#include <linux/module.h>

#include <linux/init.h>

#include <linux/fs.h>

#include <asm/uaccess.h> 

MODULE_LICENSE("GPL");

#define MAJOR_NUM 254 //主設備號

static ssize_t globalvar_read(struct file *, char *, size_t, loff_t*);

static ssize_t globalvar_write(struct file *, const char *, size_t, loff_t*);

//初始化字符設備驅動的file_operations結構體

struct file_operations globalvar_fops =

{

 read: globalvar_read, write: globalvar_write,

};

static int global_var = 0; //"globalvar"設備的全局變量

static int __init globalvar_init(void)

{

 int ret;

 //注冊設備驅動

 ret = register_chrdev(MAJOR_NUM, "globalvar", &globalvar_fops);

 if (ret)

 {

  printk("globalvar register failure");

 }

 else

 {

  printk("globalvar register success");

 }

 return ret;

}

static void __exit globalvar_exit(void)

{

 int ret;

 //注銷設備驅動

 ret = unregister_chrdev(MAJOR_NUM, "globalvar");

 if (ret)

 {

  printk("globalvar unregister failure");

 }

 else

 {

  printk("globalvar unregister success");

 }

}

static ssize_t globalvar_read(struct file *filp, char *buf, size_t len, loff_t *off)

{

 //將global_var從內核空間復制到用戶空間

 if (copy_to_user(buf, &global_var, sizeof(int)))

 {

  return - EFAULT;

 } 

 return sizeof(int);

}

static ssize_t globalvar_write(struct file *filp, const char *buf, size_t len, loff_t *off)

{

 //將用戶空間的數據復制到內核空間的global_var

 if (copy_from_user(&global_var, buf, sizeof(int)))

 {

  return - EFAULT;

 } 

 return sizeof(int);

}

module_init(globalvar_init);

module_exit(globalvar_exit); 

  運行:

gcc -D__KERNEL__ -DMODULE -DLINUX -I /usr/local/src/linux2.4/include -c -o globalvar.o globalvar.c 

  編譯代碼,運行:

inmod globalvar.o 

  加載globalvar模塊,再運行:

cat /proc/devices 

  發現其中多出了"254 globalvar"一行,如下圖:

 

  接著我們可以運行:

mknod /dev/globalvar c 254 0 

  創建設備節點,用戶進程通過/dev/globalvar這個路徑就可以訪問到這個全局變量虛擬設備了。

我們寫一個用戶態的程序globalvartest.c來驗證上述設備:

#include <sys/types.h>

#include <sys/stat.h>

#include <stdio.h>

#include <fcntl.h>

main()

{

 int fd, num;

 //打開"/dev/globalvar"

 fd = open("/dev/globalvar", O_RDWR, S_IRUSR | S_IWUSR);

 if (fd != -1 )

 {

  //初次讀globalvar

  read(fd, &num, sizeof(int));

  printf("The globalvar is %d\n", num);

  //寫globalvar

  printf("Please input the num written to globalvar\n");

  scanf("%d", &num);

  write(fd, &num, sizeof(int));

  //再次讀globalvar

  read(fd, &num, sizeof(int));

  printf("The globalvar is %d\n", num);

  //關閉"/dev/globalvar"

  close(fd);

 }

 else

 {

  printf("Device open failure\n");

 }

} 

  編譯上述文件:

gcc -o globalvartest.o globalvartest.c 

  運行

./globalvartest.o 

  可以發現"globalvar"設備可以正確的讀寫。

熱詞搜索:

上一篇:深入淺出 Linux字符設備驅動程序解析 一
下一篇:在Linux操作系統下如何開啟硬盤DMA 一

分享到: 收藏
主站蜘蛛池模板: 二年级100个词语| 山口小夜子| 加入民盟的好处和坏处| 黄海冰主演电视剧大全| 男按摩师给女性做私密按摩| 长安长安朗诵报名入口| 青春之歌电影演员表名单| charlie sheen| 神犬小七2| 高天妮| 情欲视频| 2014春节联欢晚会| 兔子电影| 思想认识不到位,重视程度不够| 少年班演员表| 日记100字简单| 美女xxx69爽爽免费观妞| 江苏卫视节目预告| 违规吃喝研讨发言材料| 美女在线| 甲种公牛1976| 郭碧婷个人简历资料| 变形记开头结尾优美段落| 美少女战士奥特曼| 胭脂似火电视剧免费观看完整版全集| 林安| 飞艇全天精准计划软件| 林正英演的全部电影| | 女孩们电影| 肮脏| 邵雨薇电影| 地铁电影| 地下道的美人鱼| 日本电影小小的家| 吻胸捏胸揉视频大全| bbbbbbbbb免费毛片视频| 伊利亚伍德| 康熙微服私访记1| 中国偷窥视频| 韩国电影《爱欲》|