在達到能直接修改linux內核的程度之前,我們寫的代碼都需要以模塊的方式添加到內核中去運行。本節就介紹最簡單的模塊編寫和加載方法。
1、首先創建一個目錄modules,以存放以後編寫的模塊。再在其下創建一個子目錄hello,最為本節創建模塊的位置。
2、編寫源文件hello.c,代碼如下。
- #include <linux/init.h>
- #include <linux/module.h>
-
- MODULE_LICENSE("Dual BSD/GPL");
-
- static int hello_init(void)
- {
- printk(KERN_INFO "Hello, world!\n");
- return 0;
- }
-
- static void hello_exit()
- {
- printk(KERN_INFO "Hello, exit!\n");
- }
-
- module_init(hello_init);
- module_exit(hello_exit);
3、編寫Makefile文件,如下。
- KERNEL_DIR := /lib/modules/$(shell uname -r)/build
- PWD := $(shell pwd)
-
- module-objs := hello.o
-
- obj-m := module.o
-
- default:
- $(MAKE) -C $(KERNEL_DIR) M=$(PWD) modules
這裡先把hello.c編譯為hello.o,再把hello.o合並到module.o,最後生成可加載模塊module.ko。其實也可以不通過module.o,直接用hello.o生成可加載模塊。只是linux習慣的做法是先把所有的目標文件合並到一個目標文件,再進行其它操作。
4、編譯並加載模塊。
- $make
編譯生成module.ko
- $sudo insmod module.ko
將module.ko加入內核模塊
- $lsmod
查看已加載的模塊列表,包括module模塊
- $sudo rmmod module
卸載module模塊
- $dmesg | less
打印最近的5條記錄,會看到在hello_init和hello_exit中打印的信息。
現在我們已經完全了解了模塊編譯加載的流程,相當於打開了進入內核的大門。以後會接觸到越來越多的內核API,我們能做的事也會越來越多。