AnsweredAssumed Answered

RT1064: How to solve gcc linker error (.ARM.exidx+0x0): relocation truncated to fit: R_ARM_PREL31

Question asked by Udo Eberhardt on Dec 14, 2019
Latest reply on Dec 18, 2019 by Hui_Ma



According to my understanding this linker error occurs because of the following requirements from the ARM ABI standard:

- There is a separate .ARM.exidx section created by the compiler which contains entries that refer to addresses in the code.

- Each entry in .ARM.exidx contains a 31 bit signed integer to express the offset where the code resides. One bit is used for other purposes (to indicate the type of the entry). So the maximum offset that can be stored in an entry is 0x3FFF_FFFF.

- There is exactly one .ARM.exidx section in an image.

- The .ARM.exidx section is used for C++ exception handling but also for C code. Using compiler option -fno-exceptions does not solve the problem. In my specific case the entries in .ARM.exidx are created by assembler code in irq_cm4f.o (CMSIS RTOS) and C code in libgcc.a(_udivmoddi4.o).


If parts of the code are placed in ITCM (which is the whole purpose of ITCM) then the following problem occurs:

ITCM address: 0x0000_0000

FLASH address: 0x7000_0000  Offset: 0x7000_0000

The linker produces the above error message.


For RT1052 I was able to work around this by placing .ARM.exidx in OCRAM:

ITCM address: 0x0000_0000

OCRAM address: 0x2020_0000  Offset: 0x2020_0000

FLASH address: 0x6000_0000  Offset: 0x3FE_00000


For RT1064 this approach does not work because the internal FLASH resides at 0x7000_0000:

ITCM address: 0x0000_0000

OCRAM address: 0x2020_0000  Offset: 0x2020_0000

FLASH address: 0x7000_0000  Offset: 0x4FE_00000

The linker produces the above error message.


My questions:

1. Is there a solution to this problem at the linker level? For example, is it safe to simply discard the .ARM.exidx section?

2. Is it possible to map the FLASH to a lower address? It occurs to me that choosing such high addresses for the FLASH is a bit unfortunate.