c - EXPORT_SYMBOL 在一个方向上导致未定义的引用,但在另一个方向上没有(重定位被截断)
问题描述
我正在使用 aarch64 机器上的 4.9 Linux 内核,特别是mm/memory.c和自定义平台设备驱动程序。我的目标是让我的设备驱动程序将一些信息传达给源自memory.c中的函数的硬件。
起初,我尝试了与(平台)设备驱动程序通信时使用的相同方法:
EXPORT_SYMBOL
对于驱动程序 A 中的相应功能- 在驱动程序 B中将符号定义为extern并访问
通常像魅力一样工作,但是这次我在使用平台驱动程序EXPORT和memory.c
使用extern进行链接时遇到了以下错误:
mm/memory.c:164:(.text+0x2a874): relocation truncated to fit: R_AARCH64_ADR_PREL_PG_HI21 against undefined symbol `my_func'
但是,如果我反其道而行之,那就是:
- 定义
EXPORT_SYMBOL
一个函数指针memory.c
- 将指向平台驱动程序函数的指针分配给导出的符号
... 有用!
具体来说...
平台驱动:
void my_func(args){ ... };
EXPORT_SYMBOL(my_func);
内存.c:
extern void my_func(args);
...导致上述链接器错误。
但 ...
平台驱动:
extern void (*funcptr)(args);
driver_probe() {
...
funcptr = &my_func;
....
}
内存.c:
void (*funcptr)(args) = NULL;
EXPORT_SYMBOL(funcptr);
...有效!
快速的谷歌搜索暗示链接器错误与 gcc 选项 PIC/PIE 有关,但我找不到明确的答案。
它现在可以工作了……但是为什么呢?:-)
解决方案
推荐阅读
- arm - ARM 处理器寄存器与字
- sql - SQL:从具有包含该列下一个值的附加列的表中选择一行
- angular - 存储在数据库中的标记中的 Angular 9 搜索和更新元素
- javascript - 下拉值应更改为选定选项而不是默认值 - 角度
- c++ - 具有虚拟类的 unique_ptr
- angular - NGXS如何在异步调用后触发Angular重新渲染?
- c++ - C++ 通用组件系统
- mysql - 在 MYSQL 的 ALTER TABLE 语句中使用变量或函数
- javascript - 选中的复选框在owl carousal html中自动取消选择
- python - 如何基于多列合并两个不相等的数据框?