Linux设备驱动程序:HelloWorld

    技术2022-05-20  39

    内核模块是Linux内核向外部提供的一个插口,其全称为动态可加载内核模块(Loadable Kernel Module,LKM),我们简称为模块。Linux内核之所以提供模块机制,是因为它本身是一个单内核(monolithic kernel)。单内核的最大优点是效率高,因为所有的内容都集成在一起,但其缺点是可扩展性和可维护性相对较差,模块机制就是为了弥补这一缺陷。

    (一) 什么是模块

    模块是具有独立功能的程序,它可以被单独编译,但不能独立运行。它在运行时被链接到内核作为内核的一部分在内核空间运行,这与运行在用户空间的进程是不同的。模块通常由一组函数和数据结构组成,用来实现一种文件系统、一个驱动程序或其他内核上层的功能。

    (二)编写一个简单的模块

    模块和内核都在内核空间运行,模块编程在一定意义上说就是内核编程。因为内核版本的每次变化,其中的某些函数名也会相应地发生变化,因此模块编程与内核版本密切相关。

    /* hello world driver for kernel 2.6 */ #include <linux/module.h> #include <linux/kernel.h> #include <linux/init.h> /* * 这是模块的初始化函数,它必需包含诸如要编译的代码、初始化数据结构等内容。 */ static int __init hello_init(void) { printk(KERN_DEBUG "Hello,World! from the kernel space…/n"); return 0; } /* * 这是模块的退出和清理函数。此处可以做所有终止该驱动程序时相关的清理工作。 */ static void __exit hello_exit(void) { printk(KERN_DEBUG "Goodbye, World! leaving kernel space…/n"); } /* * 这是驱动程序初始化的入口点。对于内置模块,内核在引导时调用该入口点; * 对于可加载模块则在该模块插入内核时才调用。 */ module_init(hello_init); /* * 对于可加载模块,内核在此处调用hello_exit函数,而对于内置的模块, * 它什么都不做。 */ module_exit(hello_exit); MODULE_LICENSE("GPL");

    (三)编译模块

    # Makefile obj-m += hello.o all: make -C /lib/modules/$(shell uname -r)/build M=$(PWD) modules clean: make -C /lib/modules/$(shell uname -r)/build M=$(PWD) clean

    (四)加载与卸载模块

     

    dipper@jiangkun:~/ldd/hello$ sudo insmod hello.ko dipper@jiangkun:~/ldd/hello$ sudo rmmod hello 

     


    最新回复(0)