For now, we use instructions to calculate the address for the element of the global array. If that offset is too large(i.e. larger than 16 bit), we have to add extra instructions to do the calculation. i.e.
double attribute((visibility("hidden"))) b[2000000000];
double foo() { return b[4096] ; }
This is the code sequence we get now:
addis 3, 2, b@toc@ha li 4, 0 addi 3, 3, b@toc@l ori 4, 4, 32768 lfdx 1, 4, 3
Because 32768 is not 16-bit constant, we have to use the X-form load to load the address of b[4096]. This patch is trying to leverage the addend in the relocation to do the address calculation. This is the new instruction sequence we want to produce:
addis 3, 2, b@toc@ha+32768 lfd 1, b@toc@l+32768(3) blr
Notice that, as this transformation will take up one extra TOC entry(b+32768), we only do this if the offset is larger than 16 bit and smaller than 32bit.
It is not clear to me how we ensure Offset fits into a signed 16-bit immediate.