2

So I have a Linux x86-64 binary linked with libc dynamically running on patched Ubuntu 16.04 remotely.

The executable makes one call to libc read and exits, allowing simple stack overflow into ROP. That's the only code compiled into the binary.

-----------------------
gdb-peda$ checksec
CANARY    : disabled
FORTIFY   : disabled
NX        : ENABLED
PIE       : disabled
RELRO     : Partial
-----------------------

Full ASLR is enabled.

I do not have access to a syscall gadget at any known address, and after hearing that vsyscall might work, I learned that vsyscall is now emulated in newer kernel versions and can't be used for a syscall gadget.

I've done manual searches for int 0x80, syscall, and sysenter hoping to find them in known executable section to no avail.

Does anyone know of any way to exploit this binary without any known address except for 'read'?

I suppose the only way that I can imagine is by somehow reading a libc address from the GOT and ROPing into dereferencing that address into a new function at a new offset... but I can't even find a gadget that will let me dereference.

I can't use partial address overwrite bruteforcing because x86-64 has too much entropy.

Is there some technique that I don't know of?

I'm banging my head against a wall on this one!

  • @SYS_V It's a challenge, so I don't have those things. I am by no means trying to have the problem solved for me, just trying to find any sort of information I can about techniques for bypassing ASLR/NX on extremely small binaries. I am aware that there are typically not syscall opcodes in text sections, but I thought I might get lucky and be able to ROP to the middle of an instruction. – Gbps Apr 9 '17 at 3:48
  • 1
    @SYS_V dropbox.com/s/yqc4waaa1xt78t8/SO_binary?dl=0 – Gbps Apr 9 '17 at 4:01
  • @SYS_V How would I open an fd to maps without a way to call 'open'? – Gbps Apr 9 '17 at 4:55
  • It's a remote exploit. – Gbps Apr 9 '17 at 5:04
4

It ends up that the solution was using a partial address overwrite after all.

Using the address to read in the GOT, a two-byte partial address overwrite can be done to jump within a guarantee of 8192 bytes from read into libc, with a 1/16th brute-force chance to jump within 65535 bytes (due to 4 byte entropy of ASLR).

Within the two-byte overwrite, there is a magic gadget located 0x6109 bytes away from the address of read, which is within the two-byte distance.

From one_gadget, the magic gadget near read can be found:

0xf0567 execve("/bin/sh", rsp+0x70, environ)
constraints:
  [rsp+0x70] == NULL

Where in this version of libc (2.6.32), the call to read is found at:

0xF6670 read            proc near

Using a call to read, we can overwrite the GOT entry of read and ROP back to main to call our magic gadget.

Also, another solution was found by doing that same partial address overwrite to ROP into setting up a syscall then overwriting the last byte of read to jump 0x0E bytes forward and hit the natural syscall gadget found within read. This way you don't have to bruteforce ASLR and have a stable exploit!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.