Mips 使用GNU ld,我如何在不获取“的情况下强制指定(外部)符号的地址;“重新安置”;错误?

Mips 使用GNU ld,我如何在不获取“的情况下强制指定(外部)符号的地址;“重新安置”;错误?,mips,linker-errors,ld,relocation,linker-scripts,Mips,Linker Errors,Ld,Relocation,Linker Scripts,我有两个函数,a()和b(),它们都有特定的固定加载/运行时地址。我自己编译a(),而b()已经提供(例如在ROM中) 文件a.c如下所示: extern void b(void); void a(void) { b(); } 这将生成以下汇编代码: 00000000 <a>: 0: 08000000 j 0 <a> 0: R_MIPS_26 b 4: 00000000

我有两个函数,
a()
b()
,它们都有特定的固定加载/运行时地址。我自己编译
a()
,而
b()
已经提供(例如在ROM中)

文件
a.c
如下所示:

extern void b(void);

void a(void) {
    b();
}
这将生成以下汇编代码:

00000000 <a>:
   0:   08000000       j 0 <a>
                       0: R_MIPS_26 b
   4:   00000000       nop
但是,使用此脚本链接
a.o
会产生以下错误:

a.o: In function 'a':
(.text+0x0): relocation truncated to fit: R_MIPS_26 against `b`

这可能是因为链接器正试图将完整的32位值(
0x80002000
)放入跳转目标的26位空间。我的链接器脚本有什么问题?

请尝试使用
long\u call
属性:

__attribute__((long_call))
extern void b(void);

所有MIPS属性的手册都是。

作为参考,这似乎是相关的:我无法帮助使用链接器脚本,但另一种解决方案是使用函数指针。对于几个不会太多工作的函数,您是否尝试过在脚本中使用
b=0x2000
?这是链接器需要插入到
J
指令中的值。
__attribute__((long_call))
extern void b(void);