How to find shellcode address

Penetration Testing Wiki

How to find shellcode address

Some notes on how to find the right address in your specific environment to exploit Apache

On my environment Debian Sarge with Apache 1.3.34 installed from apt-get, the address which I had to jump to execute the shellcode was 0x0834ae77. As this address it is not helpful at all in exactly the same conditions, here a little help to figure out this address in your environment.

To guess the address I thought different methods. Please, if you find another way would be nice to hear from you 🙂

Method #1: Debugger’s help

In an optimal environment or if we compile Apache with debug support, we can use gdb to debug Apache setting a breakpoint inside the function escape_absolute_uri and get the address of uri variable. But if we are trying to exploit in-the-wild or just our binary is stripped (table of symbols lacks) and does not have debug support, it is not so simple… Indeed, that was my case 😀

Method #2: Brute force until success

Here there are no tricks, just begin trying with the highest heap memory to the lowest one, incrementing one byte at a time.
In kernel 2.6.18-5-686 the starting address for the heap is 0x080495C4, then a proper range to try would be from 0x080495C0 to 0x085495C0 (5 MB range space).

Method #3: Get the address from apache’s child core file

This is quite tricky but worked at the first time to me, quite hard but accurate.

The first thing to do (obviously to exploit a machine which is yours and you have root access) is enable Core Dump support for apache. Once you got the core file from the server (trying with some trivial address like 0x01020304) establish a mapping between adresses of the core file and memory addresses.
To establish the mapping, I searched into the crashed process’ memory map (gdb /usr/sbin/apache core) what contains some random address, i.e. 0x0808bbc0, now you know some memory address and its content. Now searching for the contents into the core file you can get the offset (difference between memory addresses and core file addresses). In my case I was able to access 0x0808bbc0 in the core file using an offset of 0x8bc0, i.e. memory address 0x0808bbc0 was dumped to 0x8bc0 in the core file.
I wrote a naive program to ease the finding of the shellcode address:

#include <stdio.h>

int main() {
        FILE *f;
        char c, u, z;
        int addr= 0x0808bbc0;
        f= fopen("core", "r");
        fseek(f, 0x8bc0, SEEK_SET);
        fread(&z, 1, 1, f); addr++;
        fread(&u, 1, 1, f); addr++;
        while (!feof(f)){
                fread(&c, 1, 1, f); addr++;
                if (z == '\x90' && u == '\x89' && c == '\xe6') {
                        printf("addr: 0x%x\n", addr);
                }
                z= u; u= c;
        }
        return 0;
}

Where addr is the address where the heap begins, and \x90, \x89 and \xe6 is some shellcode’s OPcodes to find. Once we got some addresses, using gdb we can check whether it is the correct one or not.

Maybe knowing better the core files format (ELF) another approach could be reached to get this easily and faster, anyway as I had no time to find a method, I thought that and worked for me.

Note: I suppose that you already know that linux kernel uses Virtual Address space Randomization since version 2.6.11, so it is “impossible” to take advantage in those situations.