news 2026/4/1 18:33:32

28.驱动程序,生成ko文件,需要放到特定文件夹去编译吗?

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
28.驱动程序,生成ko文件,需要放到特定文件夹去编译吗?

编写Linux内核驱动生成.ko(内核模块)文件,不一定需要把代码放到内核源码目录编译,但核心取决于你的编译方式——有两种主流方式,对应不同的文件存放逻辑,推荐第二种(更灵活):

一、两种编译方式的文件存放规则

方式1:内核源码树内编译(传统方式,需放特定目录)
  • 要求:必须把驱动代码放到Linux内核源码的指定目录(如drivers/i2c/devices/drivers/misc/);
  • 原因依赖内核源码的Makefile体系,需要修改目录下的KconfigMakefile,让内核编译系统识别你的驱动
  • 步骤示例(以AHT20驱动为例):
  • aht20.c放到linux-src/drivers/i2c/devices/
  • 修改该目录下的Makefile,添加:obj-$(CONFIG_AHT20) += aht20.o
  • 修改该目录下的Kconfig,添加驱动配置项;
  • 回到内核根目录,执行make modules编译出.ko
  • 缺点:侵入内核源码,不灵活,多驱动开发时易混乱;
  • 适用场景:驱动需要合入内核主线、或依赖内核深层接口。
方式2:内核源码树外编译(推荐,无需放特定目录)
  • 核心:通过自定义Makefile指定内核源码路径,驱动代码可放在任意目录(如/home/yourname/drivers/aht20/);
  • 原理:自定义Makefile通过KERNELDIR指向内核源码目录,借助内核的scripts/Makefile.modpost工具完成编译,无需修改内核源码;
  • 优势:驱动代码独立,编译不影响内核源码,灵活易管理;
  • 新手必用:99%的嵌入式驱动开发场景(如AHT20/PCF8574驱动)都用这种方式。

二、独立目录编译.ko(无需内核源码目录)

以编译AHT20驱动为例,全程无需把代码放进内核目录:

步骤1:任意目录创建驱动代码和Makefile

比如在/home/root/drivers/aht20/下创建两个文件:

  • aht20.c(驱动源码,略);
  • Makefile(核心,指定内核路径和编译规则):
# 1. 指定你的内核源码目录(开发板对应的内核源码,不是系统内核) KERNELDIR ?= /home/root/linux-4.19.35-imx6ul # 替换为你的内核源码路径 # 2. 指定编译后的模块存放目录(可选,默认当前目录) PWD ?= $(shell pwd) # 3. 内核模块编译规则 obj-m += aht20.o # 要编译的驱动文件:aht20.c → aht20.ko # 4. 编译目标 all: make -C $(KERNELDIR) M=$(PWD) modules # -C进入内核目录,M指定驱动目录 clean: make -C $(KERNELDIR) M=$(PWD) clean
步骤2:编译生成.ko

在驱动目录执行编译命令:

make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- # 交叉编译(根据你的编译器调整)
  • ARCH=arm:指定CPU架构(ARM);
  • CROSS_COMPILE:指定交叉编译器前缀(和你的开发板匹配);
  • 编译完成后,当前目录会生成aht20.ko(还有.o/.mod.c等中间文件)。
关键注意事项
  • 内核源码必须匹配
    • 编译.ko的内核源码,必须和开发板运行的内核“版本+配置+编译选项”完全一致(否则insmod时会报version magic mismatch);
    • 比如开发板内核是4.19.35,就必须用同版本的内核源码编译,不能用Ubuntu系统的内核源码。
  • 无需修改内核源码
    • 这种方式完全独立,不用动内核目录的任何文件,驱动代码放在任意目录都能编译;
    • 若驱动依赖内核头文件(如linux/i2c-dev.h),内核源码会自动提供,无需额外拷贝。
  • 编译工具链匹配
    • 必须用和内核编译相同的交叉编译器(比如内核用arm-linux-gnueabihf-gcc 7.5,驱动也得用这个版本)。

三、常见误区澄清

  1. “必须放内核目录”是错的:只有要把驱动合入内核主线时才需要,普通开发完全不用;
  2. “任意目录编译”的前提:内核源码必须提前配置(make defconfig/make menuconfig)并编译过(至少编译出vmlinux),否则会缺少头文件和编译依赖;
  3. .ko的安装:编译好的.ko无需放到内核目录,直接拷贝到开发板任意目录(如/lib/modules/$(uname -r)/extra/),执行insmod aht20.ko即可加载。

总结

  • 无需把驱动代码放到内核特定目录编译,独立目录+自定义Makefile是嵌入式驱动开发的标准做法;
  • 核心是Makefile中指定正确的内核源码路径,保证内核版本、工具链和开发板匹配;
  • 对你的AHT20/PCF8574驱动开发,直接在自己的工作目录(如~/drivers/)创建代码和Makefile,编译即可,完全不用动内核源码目录。
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/3/30 1:05:42

27.MPSOC FPGA 驱动PCF8574

上一篇记录了AHT20,本篇记录下PCF8574&#xff0c;原理类似&#xff1a;#include <stdio.h> #include <stdlib.h> #include <fcntl.h> #include <unistd.h> #include <sys/ioctl.h> #include <linux/i2c-dev.h> #include <errno.h> …

作者头像 李华
网站建设 2026/4/1 3:13:09

通信系统仿真:数字调制与解调技术_(28).Simulink通信系统仿真

Simulink通信系统仿真 1. Simulink概述 1.1 Simulink简介 Simulink是MATLAB的一个附加产品&#xff0c;主要用于动态系统建模、仿真和分析。Simulink提供了一个图形用户界面&#xff08;GUI&#xff09;&#xff0c;使用户可以通过拖放操作来构建复杂的系统模型。在通信系统仿真…

作者头像 李华
网站建设 2026/3/25 23:11:29

论文AIGC率太高?5个超实用降AI工具分享,AI率降低80%以上

最近身边好多同学都在为论文的AI率头疼。明明自己认真改过好几遍了&#xff0c;查重系统还是显示AIGC率爆表&#xff0c;导师那关根本过不去。现在用AI工具辅助确实提升了效率&#xff0c;但怎么让内容更“人性化”&#xff0c;避免被系统标红&#xff0c;这才是关键。 我自己试…

作者头像 李华
网站建设 2026/3/30 13:42:00

团队合并与拆分的判断标准

团队合并与拆分的判断标准&#xff0c;核心是服务于组织的战略目标、效率和敏捷性。合并的判断标准主要基于“协同增效”和“规模效益”&#xff0c;当多个团队目标高度一致、资源重叠或需要集中力量办大事&#xff08;如攻坚核心项目&#xff09;时&#xff0c;应考虑合并。 而…

作者头像 李华
网站建设 2026/3/28 8:28:50

C#字典操作与类对象全解析

《字典》字典&#xff1a;包含了key&#xff08;键&#xff09;和value&#xff08;值&#xff09;&#xff0c;简称键值对&#xff0c;键是唯一的&#xff0c;值可以是任意类型的&#xff0c;字典是没有顺序的&#xff0c;只能通过键取值。 创建字典的方法 // Dictionary<…

作者头像 李华