💾 Archived View for bbs.geminispace.org › s › Linux › 5066 captured on 2024-03-21 at 15:28:32. Gemini links have been rewritten to link to archived content

View Raw

More Information

⬅️ Previous capture (2024-02-05)

➡️ Next capture (2024-05-10)

🚧 View Differences

-=-=-=-=-=-=-

Address Randomization Tribulations

So, I have a tiny 32-bit application (a Forth) taking up about 4K, written in fasm. Pure minimalism, including an iffy elf header that fasm creates, with a fixed load address. More on that later.

It's been unstable, and I tracked the instability down to the initial memory allocation. Right at the start I add my desired memory size to the code base (the top label in asm code), and invoke `brk` system call. This worked as long as I allocated a largish amount, but failed on anything smaller than 16MB or so. Furthermore, it failed intermittently.

After much painful debugging I realized that even though the system is always loaded at the address in the header (0x08048000), due to address randomization, Linux thinks it is elsewhere. Asking brk for say 64K (0x0805800) will often be below the current break, and often entirely below the randomized space it thinks the program is in, causing a SEGFAULT shortly thereafter.

This seems like a bug - the loader should either abide by the forced address requested, or not allow a fixed load -- not load at requested address but pretend it is elsewhere in the memory space.

Has anyone encountered such nonsense? I kind of doubt it because most people use gcc and a proper linker, not barely-supported 32-bit architecture with a really bizzare assembler. But worth asking.

Posted in: s/Linux

🚀 stack

2023-09-02 · 7 months ago

1 Comment

🚀 stack [OP] · 2023-09-03 at 20:23:

I was completery right.

Tried with gdb (yuck), after `set disable-randomization off`, to turn randomization on, because gdb turns randomization off by default (wasting a bunch of my time, but kind of almost doesn't make no sense, pun intended).

(gdb) info proc mappings
process 144876
Mapped address spaces:

        Start Addr   End Addr       Size     Offset  Perms   objfile
         0x8048000  0x804a000     0x2000        0x0  rwxp   /home/stack/src/nForth/nforth
         0x87df000  0xa049000  0x186a000        0x0  rwxp   [heap]
        0xf7f75000 0xf7f79000     0x4000        0x0  r--p   [vvar]
        0xf7f79000 0xf7f7b000     0x2000        0x0  r-xp   [vdso]
        0xffc4e000 0xffc6f000    0x21000        0x0  rwxp   [stack]
(gdb)

So, nforth loads at 0x0804800-0x0804A00, but when heap is expanded up, it starts at 0x087DF000 and goes to 0x0A04900. So the memory space is not contiguous, and the entire idea of sysbreak is bullshit, in this particular case.