This patch optimizes the global variable access sequence when R_PPC64_TOC16_HA evaluates to 0.
The addis that the R_PPC64_TOC16_HA relocation operates on is overwritten with a nop and the related instruction that uses either a *_LO or *_LO_DS form is update to use the toc pointer a base register.
Details
Diff Detail
Event Timeline
Overall I think the patch looks good, but we should expand the ppc64-toc-addis-nop.s test to cover all the different sequences this will affect (like loading bytes/half-word/word signed and unsigned etc).
lld/ELF/Arch/PPC64.cpp | ||
---|---|---|
473 | Should the mask for ds-form instructions be 0xFFE00003 instead? I think this will turn something like lwa 3,b@toc@l(4) into ld 3, b@toc@l(2) |
lld/ELF/Arch/PPC64.cpp | ||
---|---|---|
390–391 | return Type == R_PPC64_TOC16_HA || Type == R_PPC64_TOC16_LO_DS || Type == R_PPC64_TOC16_LO; is better. | |
399 | I don't think you have to call this function ahead of time. Instead, I'd replace IsTocRelType with isTocRelType(Type). I believe compiler can optimize it so that it is as fast as this code. |
- Error when optimizing an updated form load or store.
- Add an option that can disable the toc optimization.
- Expand the testing.
ELF/Arch/PPC64.cpp | ||
---|---|---|
132 ↗ | (On Diff #162427) | This variable is used only once. You can eliminate it. |
560 ↗ | (On Diff #162427) | Just return the result of the boolean expression instead of if (e) return true; return false; |
633 ↗ | (On Diff #162427) | Can't -> can't |
634 ↗ | (On Diff #162427) | We have llvm::utohexstr, so I believe you can omit Twine::. |
ELF/Driver.cpp | ||
287–288 ↗ | (On Diff #162427) | It is indeed true that --no-toc-optimize is PPC64 only, but in other test patterns we don't care about that kind of negative flags. I'd check if Config->TocOptimize is true. |
ELF/Options.td | ||
319–320 ↗ | (On Diff #162427) | Indentation. Shouldn't TOC be all-caps? |
Moved checking of OPT_toc_optimise until after the machine has been decided and made it default to on only for PowerPC64.
ELF/Driver.cpp | ||
---|---|---|
287–288 ↗ | (On Diff #162427) | Forgot to update that in the diff, its fixed now. |
is better.