[lld] [lld][ELF] Fix a corner case of elf::getLoongArchPageDelta (PR #71907)
Fangrui Song via llvm-commits
llvm-commits at lists.llvm.org
Wed Nov 22 11:21:07 PST 2023
MaskRay wrote:
> I made a brute force algorithm:
>
> ```python
> def uintptr_t(x):
> return x & ((1 << 64) - 1)
>
> def ptrdiff_t(x):
> x = uintptr_t(x)
> if x & (1 << 63):
> x = (1 << 64) - x
> return x
>
> def pcalau12i(pc, imm):
> assert(imm in range(-0x80000, 0x80000))
> return uintptr_t(pc + (imm << 12)) & ~0xfff
>
> def simm(width, bits):
> assert(bits >= 0 and bits < (1 << width))
> return bits - ((1 << width) if bits & (1 << (width - 1)) else 0)
>
> def reloc(dest, pc):
> lo12 = dest & 0xfff
> a1_first_val = uintptr_t(simm(12, lo12))
>
> for hi20 in range(-0x80000, 0x80000):
> a0 = pcalau12i(pc, hi20)
> # We need to insert something into a1[32..] to make a0 + a1 = dest,
> # i. e. a1 = dest - a0.
> want_a1 = uintptr_t(dest - a0)
> if (want_a1 & 0xffffffff) != (a1_first_val & 0xffffffff):
> continue
>
> lo20 = (want_a1 >> 32) & 0xfffff
> hi12 = (want_a1 >> 52) & 0xfff
> return (lo12, hi20 & 0xfffff, lo20, hi12)
>
> raise Exception("should not be reachable")
>
> def test(dest, pc):
> reloc(dest, pc)
> lo12, hi20, lo20, hi12 = reloc(dest, pc)
> a0 = pcalau12i(pc, simm(20, hi20))
> a1 = uintptr_t(simm(12, lo12))
> a1 &= ~(0xffffffff << 32)
> a1 |= lo20 << 32
> a1 |= hi12 << 52
> assert(uintptr_t(a1 + a0) == dest)
>
> test(0xfffffffffffff8ee, 0x8ee)
> test(0, 0x80000ffc)
> test(0, 0x80001000)
> ```
>
> Now I need to optimize `for hi20 in range(-0x80000, 0x80000):` line, limiting hi20 into one or two possible values.
I like using a program to enumerate all the interesting bits. We should figure out a concise program to compute the offset and avoid the special cases (like in the current patch):
```
if (result == 0xfff'fffff'fffff'000 && negativeA) // special case
return 0xfff'fffff'00000'000;
```
We should have a description how the new code does its job and a concise proof as the comment.
https://github.com/llvm/llvm-project/pull/71907
More information about the llvm-commits
mailing list