摘要:主要介绍了在进行linux驱动开发前,需要了解和掌握的一些基本知识。
MobaXterm窗口设置
为了解决在命令行中输入较长命令时,MobaXterm终端不能自动换行而导致命令首尾字符覆盖的问题,需要将MobaXterm终端大小设置成与linux终端一致,其步骤为:
- Linux终端窗口大小设置
- 查询终端窗口的行列数:
stty size
- 设置终端窗口列数:
stty cols num
- 设置终端窗口行数:
stty rows num
- MobaXterm终端大小设置
- 右击会话窗口,选择edit session
- 选择Terminal settings——>Terminal font settings——>Terminal size
- 输入与linux终端相同的行列值
编译内核模块前的环境准备
- 下载linux内核源码
- 安装必要的工具库
- 编译内核
内核模块头文件
-
<linux/module.h>
:包含内核模块信息声明的相关函数 -
<linux/init.h>
:包含module_init()和module_exit()函数 -
<linux/kernel.h>
:包含内核提供的各种函数,如printk等
内核模块打印函数
因为内核模块无法使用glibc库,所以它自身实现了一个类printf函数,但是需要指定打印等级,因为只有消息的打印等级高于(数字上小于)当前终端的显示等级,才会输出到终端。当然你也可以使用dmesg
命令查看所有等级的消息。
-
#define KERN_EMERG "<0>"
:系统即将崩溃 -
#define KERN_ALERT "<1>"
:需要马上处理 -
#define KERN_CRIT "<2>"
:情况严重 -
#define KERN_ERR "<3>"
:发生错误 -
#define KERN_WARNING "<4>"
:警告 -
#define KERN_NOTICE "<5>"
:需要注意 -
#define KERN_INFO "<6>"
:一般消息 -
#define KERN_DEBUG "<7>"
:调试信息
- 系统当前printk打印设置情况
- 当前控制台(终端)日志级别(printk消息的日志级别要小于该值方能在控制台打印)
- 默认消息日志级别(未指定日志级别的printk() 采用的默认级别,一般被定义为4)
- 最小的控制台级别(控制台日志级别可被设置的最小值)
- 默认控制台日志级别(控制台日志级别的缺省值)
其实这四个值是在kernel/printk.c
中被定义的:
所以,如果不想打印任何消息到控制台,就可以如下设置:
Makefile
$(MAKE):Makefile的默认变量,值为make
选项-C:让make工具跳转到linux内核目录下读取顶层Makefile
M:表示当前所编译的内核模块的源码目录
$(CURDIR):Makefile的默认变量,值为当前目录所在路径,也可以写成M=$(`pwd`)
make modules:执行linux顶层Makefile的伪目标modules,实现将内核模块源码的读取并编译成为ko文件
insmode xxx.ko:安装xxx模块
rmmod xxx:卸载xxx模块
lsmod :查看当前系统下的已安装模块
模块参数
- 作用:根据不同应用场合给内核模块传递不同的参数,提高内核模块灵活性。
- 步骤:
- 定义一个常见变量
- 使用
module_param
宏把传参数值赋给变量
-
module_param(name, type, perm)
- name: 参数名
- type:参数类型
- int对应int
- byte对应char类型的变量
- bool对应布尔变量
- charp对应字符串类型char*或“strings…”
- perm:读写权限(以0开头的八进制4位数字,不允许含执行权限)
- 其可在
/sys/module/模块名/parameters
目录下,生成该参数对应的文件名
符号共享
符号共享是指内核模块间可以共享导出的符号表,即变量或函数A在模块1中导出的话,那么在模块2中也可以引用了
- 变量共享:在另一个模块使用时需要用extern修饰;
- 函数共享:在另一个模块使用时,需要添加函数声明(也在头文件中声明);
- 查看当前内核中的符号表:
cat /proc/kallsyms | grep xxx
模块加卸载
- 手动加载
- 加载时必须先加载相关依赖模块
- 卸载时必须按相反顺序卸载
- 自动加载
- 将所有内核模块放到
/lib/modules/内核版本/
目录下;
- 内核版本获取方式:
uname -r
- 建立模块依赖关系:
depmod -a
- 查看模块依赖关系:
cat /lib/modules/内核版本/modules.dep
- 加载模块及其依赖模块:
modprobe xxx
- 卸载模块及其依赖模块:
modprobe -r xxx