linux 2 6 核心模組程式設計探索

2021-05-23 03:25:01 字數 4841 閱讀 5178

乙個linux 核心模組程式設計的手記, 未寫完不斷更新中…

一 相關命令

0 檢視系統裝載了哪些 核心模組

lsmod modulename

1 載入核心模組

insmod modulename

2 解除安裝核心模組

rmmod modulename

3 建立裝置檔案

mknod filename dev_type major_number minor_number

說明: 引數 filename 建立的裝置檔名稱

dev_type 裝置檔案的型別,

c character device (字元裝置)

b block device (塊裝置)

兩種檔案型別的主要區別, block device 有 buffer

major_number 主要號碼 用於標記那個驅動可以使用此裝置(每乙個驅動只有唯一的 )

minor_number 映象號碼 the driver to distinguish between the various hardware it controls(不能準確翻譯)

———————————————

例:ls -l /dev/hda[1-3]

brw-rw—- 1 root disk 3, 1 jul 5 2000 /dev/hda1

brw-rw—- 1 root disk 3, 2 jul 5 2000 /dev/hda2

brw-rw—- 1 root disk 3, 3 jul 5 2000 /dev/hda3

b 表示裝置型別

3 表示 major number

1,2,3 表示 minor number

———————————————-

5 自動載入模組(除錯好了再用, 要不系統容易掛)

depmod -a (檢查核心 依賴關係是否正確) 生成 /lib/modules/version/modules.dep 檔案

modprobe 在 insmod之前掛載 (核心模組也有依賴性~~) 可以編輯 /etc/modules.conf 讓系統啟動時載入 重要的,比如驅動

modprobe -a msdos (載入 於msdos有依賴關係的所有模組)

二 相關檔案

1 /proc/modules.

存放載入核心的資訊。 lsmod 就是讀的這個檔案

2/etc/modules.conf

讓系統啟動時載入 重要的,比如驅動

3/lib/modules/version/modules.dep

核心依賴關係 ( 猜的, 沒看)

4/var/log/message

我是用turbo 10 桌面版本 作的測試 所以 printk() 函式 輸出時不能顯示在我的kde的終端上

這個問題曾經鬱悶 我 20 分鐘, 後來 情急之下 檢視 message檔案 才發現都printk輸出資訊都記錄在 這裡了, 我也夠笨的:(

當知道怎麼建立使用 "字元裝置檔案" 之後 就能寫自己的 printx函式了。也知道為什麼不能顯示在 kede的終端上了 :)

5 /proc/devices

已經使用的裝置檔案 裡面資料的結構是 major number device name

三 使用者空間 vs 核心空間 | 系統呼叫 (有趣)

核心可以訪問所有的資源,使用者程式也是如此, 只不過,要借助驅動來訪問。

核心要管理所有的資源,他是使用者程式於硬體的乙個橋梁。乙個使用者程式執行過程當中, 他把通過系統呼叫,把資料傳送給核心空間, 然後核心處理這個請求, 之後又把結果返回給使用者空間。核心可以捕獲到所有的這些資訊, 你可以替換到原來的系統呼叫, 你可一

讓open打不開檔案, 你可以讓mkdir建立不了目錄!!

三 該死的makefile!!!

一開始看的所有相關的文章,幾乎都是基於2.4版本的,照著2。4版本的makefile寫,但是我的核心是2.6的, 所以我百試不爽,編譯完了不能載入,鬱悶了好久,差一點沒換掉核心,後來找到了2。6 的手冊才知道問題所在。

2.6 版本核心模組的makefile 編譯成.ko檔案

————————————————————

ifneq ($(kernelrelease),)

obj-m:= test.o #模組名稱

else

kdir:= /lib/modules/$(shell uname -r)/build  #核心路徑

pwd:= $(shell pwd)

default:

$(make) -c $(kdir) subdirs=$(pwd) modules

endif

————————————————————

2.4 版本核心模組的makefile 編譯成.o檔案

————————————————————

arget =test

warn =-w -wall -wstrict-prototypes -wmissing-prototypes

include=-isystem /lib/modules/2.6.0-1/build/include  #核心路徑

cflag =-o2 -dmodule -d__kernel__ $ $

cc =gcc

$.o: $.c

$ $ -c $.c

.phony: clean

clean:

rm -rf $.o

————————————————————

四 核心模組程式結構

————————————————-

/** hello-1.c - 簡單的hello the world 程式摘自手冊

*/#include /* 所有的核心模組都需要的 */

#include /* needed for kern_alert */

//初始化程式,載入模組時執行

int init_module(void)

//清除函式,解除安裝模組時執行

void cleanup_module(void)

——————————————————

2.6 版本有更多的書寫方法,比如加入載入引數, 加入核心說明等等,可以參考相關文件

五 應用字元裝置檔案

5.1 資料結構

1 file_operations 在中定義

說明: 這個結構體中包含對裝置操作的函式指標, 可以通過他的配置和實現操作函式來完成對裝置的操作

把你不使用的入口 設為null。

靠,這傢伙也太難記了,我曾經3次看到這,就去論壇灌水了,不想往下看了。 今兒耐著性子把他看完,才發現自己是個笨蛋!

在新的驅動程式中,你可能會看到一更簡單,更友好的給file_operations 賦值的方式,看下面的這個結構,手冊上說這玩意是

gcc extension gcc 擴充套件 (gnu c), 是這個意思吧, 反正我理解的就是,gcc在編譯它的時候 先把下面這個玩意翻譯正標準的c,然後再編譯。 哀,可憐的 c標準!不過話又說回來,這東西除了linux別的也沒什麼用處。

——————————————

struct file_operations fops = ;

——————————————

手冊上說 下面的這個是 c99 特性寫法!(這玩意bsd 也用不了吧? 為什麼還要這麼亂!) 注意:低版本的 gcc 可能會不正常編譯地!因為它超出了gnu c 標準 (http://www-900.ibm.com/developerworks/cn/linux/l-c99/index.shtml c99 標準參考)

——————————————

struct file_operations fops = ;

——————————————

俺選擇 的是第一種寫法!

2 *file* 結構 在 中定義

說明:* 它不同於file (glibc 中定義的)

* 它是核心級的結構體

* 它表示抽象的 'file'

* 它不是磁碟上的那個 file

* 驅動用結構體來給這個東西賦值,****** 完善理解 *******

* 指向它的指標型別 為 filp , 也可以直接寫成 struct file file

5.2 相關函式

1 註冊裝置函式

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

還記得之前寫的建立裝置檔案的命令吧,

引數說明: major: 它就是 major number 對應唯一的驅動,記住!

name: 它就是 filename 可以在 /proc/devices 裡面找到它(叫device name 更好點)

fops: file_operations 結構體, 這個可以理解為操作裝置的 核心入口,可以用上面說的兩種方法去填充它

函式返回: 1 major 為 0: 動態分配的 major number 值

2 major 為 指定值:

3 major 為特殊數值:

特殊說明: 因為乙個驅動只能有一 個 major值,所以有以下三種建立方法

1 先建立裝置檔案,你可以分配乙個固定的major值

2 動態分配 major值, 讀取 /proc/devices 檔案 找到major值, 用指令碼建立(在使用者空間建立裝置檔案)

3 動態分配 major值,使用系統呼叫函式,直接建立裝置檔案 (在核心空間執行)

第 1 種方法不可取, 因為你不可預知 是否將來要 用到這個major number

第 2 種方法,需要在使用者空間建立

第 3 種方法最好,可以動態的建立,銷毀裝置檔案,不過麻煩

linux 2 6 核心模組程式設計探索

乙個linux 核心模組程式設計的手記,未寫完不斷更新中 一 相關命令 0 檢視系統裝載了哪些 核心模組 lsmod modulename 1 載入核心模組 insmod modulename 2 解除安裝核心模組 rmmod modulename 3 建立裝置檔案 mknod filename d...

linux2 6核心模組的編譯

首先將下面的程式寫進乙個hello1.c的檔案裡 vim hello1.c include linux module.h include linux kernel.h include linux init.h static int init lkp init void static void exi...

Linux 2 6核心驅動之hello模組

終於開始在鍾愛的linux上學習寫驅動程式了。本來以為寫乙個hello模組是異常簡單的事情,結果折騰了幾天才編譯通過。首先為了測試安裝了虛擬機器 核心程式是很危險滴,我可不想讓自己的愛本頻繁崩潰 裝fedora17 fedora18的live版在虛擬機器上始終跑不起來 來回來去幾次也裝不上virtu...