我有2个驱动程序文件。
dr1.c
dr2.c
dr1.c执行EXPORT_SYMBOL(func1)。
dr2.c通过dr1.h
中的定义使用它编译dr1和dr2并创建目标文件。 但是,在内核编译的最后阶段,我收到一个错误 dr2中func1的未定义引用,但是创建了dr2目标文件。
我不明白为什么链接没有发生。
答案 0 :(得分:1)
基本上没有发生链接,因为func1()
中定义的dr1.c
地址dr2.c
是未知的。
这个问题有两种解决方案:
<强> 1。手动将地址公布到第二个文件:
在这种情况下,让我们假设模块dr1.c
和dr2.c
存在于不同的目录中并且拥有自己的Makefile
。首先,编译dr1
模块。完成后,将Modules.symvers
文件复制到包含dr2.c
的目录,然后构建dr2
模块。 Modules.symvers
基本上包含“导出符号”的地址,通过将其复制到另一个模块的目标,您将其“已知”,从而最终发生链接。
<强> 2。对两个模块使用通用的Makefile:
将dr1.c
和dr2.c
放在同一目录中,并为其创建一个公共内核Makefile
。在Makefile中输入以下条目:
obj-m := dr1.o dr2.o
完成此操作后,两个文件都将被编译,生成一个共同的Modules.symvers
文件,并相应地进行链接。
希望这会有所帮助。
答案 1 :(得分:0)
dr1正在编译为模块 dr2正被编译到内核中。
因此,链接不会发生,因为dr1不是vmlinux的一部分,即使dr1编译成模块没有任何错误。我也把dr2变成了一个模块。
另外,我必须确保在配置中启用了内核模块选项。