Linux字元裝置驅動 經典標準字元模型

2021-09-24 21:03:59 字數 4880 閱讀 1573

經典標準字元模型,即為linux2.6之前的早期經典標準字元模型。

沒有使用乙個核心的結構體,把需要的資訊進行封裝

安裝驅動後,不會在/dev/目錄下建立裝置節點,需要使用mknod建立。

乙個主裝置號只能被註冊一次,一次註冊0~255的次裝置號就被占用了。

雜項裝置,每次註冊,只占用了乙個次裝置號,(主裝置號固定為10)

#include

註冊乙個標準字元裝置

int register_chrdev(unsigned int major,const char *name, const struct file_operations *fops)

引數:

major:	主裝置號

mane: 裝置名,不需要和/dev 下對應節點名相同

fops: 檔案操作集合

返回值(1)、當major為0時,表示動態分配

成功:返回分配的主裝置號

失敗:返回負數

(2)、當major>0時,表示靜態註冊,使用使用者定義的主裝置號

成功:返回0

失敗:返回負數

void unregister_chrdev(unsigned int major, const char *name)

引數

major:主裝置號

name:裝置名,使用register_chrdev 註冊的裝置名。

返回值:無

主裝置號:0~255,10為雜項裝置號

次裝置號:0~255

注意:早期經典字元裝置不會在dev目錄下建立裝置驅動節點,需要使用者手動建立,並且註冊後占用乙個主裝置號,因此次裝置號被全部占用。

註冊字元裝置後,都會在/proc/decices目錄下出現主裝置號。

建立主裝置號250,次裝置號100的裝置節點

mknod /dev/abc c 250 100

列印等級,數字越小,等級越高

檢視開發板等級

cat /proc/sys/kernel/prink

早期模型,註冊了主裝置號,就會占用其下的次裝置號。

#include //驅動模組標頭檔案 

#include #include #include //開發板引腳支援標頭檔案

#include //copy_from_user ,copy_to_user

#include// gpio標頭檔案

#define dev_name "zx_chrdev_led"

#define led_num (4)

static unsigned int led_pin[led_num] = ;

static unsigned int major = 0; //動態配置設定0,否則設定正數1~255 (自己保證可用)

static char * pchrdev_name = dev_name;

static ssize_t chrdev_read (struct file *pfile, char __user *buff, size_t size, loff_t *off)

static ssize_t chrdev_write(struct file *filp,

const char __user *user_buf,

size_t count,

loff_t *off)

; int i = 0;

printk(kern_emerg "line:%d,%s is call\n", __line__, __function__);

if(count == 0)

if(count > led_num)

ret = copy_from_user(buf, user_buf, count); //使用者空間傳資料到核心空間

if(ret)

for(i = 0; i < count; i++)

else if(buf[i] == 0)

}return count;

}static int chrdev_open(struct inode *pinode, struct file *pfile)

static int chrdev_release(struct inode *pinode, struct file *pfile)

static const struct file_operations chrdev_fops = ;

static int __init zx_chrdev_led_init(void)

gpio_direction_output(led_pin[i],1); //四盞燈設定為輸出功能,並且輸出高電平

} if(major)else

} printk(kern_emerg "major:%d\n",major);

printk(kern_emerg "%s is ok!!!\n",__function__);

return 0;

register_chrdev_err:

gpio_request_err:

for(--i; i >= 0; i--)

return ret ;

}static void __exit zx_chrdev_led_exit(void)

unregister_chrdev(major, pchrdev_name);

printk(kern_emerg "goodbye,zx_chrdev_led\n");

}module_init(zx_chrdev_led_init);

module_exit(zx_chrdev_led_exit);

module_license("gpl");

#include #include #include #include #include #include #include #define dev_name  "/dev/zx_chrdev_led"

#define led_num (4)

int main(void)

; //1£¬áᣬ0±íê¾ãð£¬

int i = 0;

int fd;

fd = open(dev_name, o_rdwr);

if(fd < 0)

while(1)

return 0;

}

對應的makefile只需修改雜項裝置對應的makefile,修改驅動的名字就可以。

[root@zx20150811 /home]# ls

[root@zx20150811 /home]# insmod zx_chrdev_led.ko

[ 3643.345000] major:249

[ 3643.345000] zx_chrdev_led_init is ok!!!

[root@zx20150811 /home]# mknod /dev/zx_chrdev_led c 249 1

[ 3740.410000] line:61,chrdev_open is call

[ 3740.410000] line:36,chrdev_write is call

[ 3741.410000] line:36,chrdev_write is call

[ 3742.410000] line:36,chrdev_write is call

[ 3743.410000] line:36,chrdev_write is call

[ 3744.410000] line:36,chrdev_write is call

[ 3745.410000] line:36,chrdev_write is call

[ 3746.410000] line:36,chrdev_write is call

^c[ 3746.990000] line:68,chrdev_release is call

[root@zx20150811 /home]#

這裡的次裝置號為1,因為經典標準字元模型一旦註冊了主裝置號,這個主裝置號下的次裝置號都被占用。下面測試其它的次裝置號。

[root@zx20150811 /home]# rmmod zx_chrdev_led.ko 

[ 3879.105000] goodbye,zx_chrdev_led

[root@zx20150811 /home]# rm -f /dev/zx_chrdev_led

[root@zx20150811 /home]# ls

[root@zx20150811 /home]# insmod zx_chrdev_led.ko

[ 3913.425000] major:249

[ 3913.425000] zx_chrdev_led_init is ok!!!

[root@zx20150811 /home]# mknod /dev/zx_chrdev_led c 249 23

[ 3950.420000] line:61,chrdev_open is call

[ 3950.420000] line:36,chrdev_write is call

[ 3951.420000] line:36,chrdev_write is call

[ 3952.420000] line:36,chrdev_write is call

[ 3953.420000] line:36,chrdev_write is call

[ 3954.420000] line:36,chrdev_write is call

^c[ 3954.925000] line:68,chrdev_release is call

[root@zx20150811 /home]#

結果可以知道,換個次裝置號應用程式依然能夠識別並使用。

驅動 linux裝置驅動 字元裝置驅動開發

preface 前面對linux裝置驅動的相應知識點進行了總結,現在進入實踐階段!linux 裝置驅動入門篇 linux 裝置驅動掃盲篇 fedora下的字元裝置驅動開發 開發乙個基本的字元裝置驅動 在linux核心驅動中,字元裝置是最基本的裝置驅動。字元裝置包括了裝置最基本的操作,如開啟裝置 關閉...

Linux裝置驅動之《字元裝置驅動》

linux裝置中最大的特點就是裝置操作猶如檔案操作一般,在應用層看來,硬體裝置只是乙個裝置檔案。應用程式可以像操作檔案一樣對硬體裝置進行操作,如open close read write 等。下面是乙個字元裝置驅動程式的簡單實現test.c 模組分析 1.初始化裝置驅動的結構體 struct fil...

Linux裝置驅動之字元裝置驅動

一 linux裝置的分類 linux系統將裝置分成三種基本型別,每個模組通常實現為其中某一類 字元模組 塊模組或網路模組。這三種型別有 字元裝置 字元裝置是個能夠像位元組流 類似檔案 一樣被訪問的裝置,由字元裝置驅動程式來實現這種特性。字元裝置可以通過檔案系統節點來訪問,比如 dev tty1等。這...