Level 0: Euphrates (10 pts)
The function getbuf is called within bufbomb
by a function test having the following C code:
void test()
{
int val;
volatile int local = uniqueval();
val = getbuf();
/* Check for corrupted stack */
if (local != uniqueval()) {
printf("Sabotaged!: the stack has been corrupted\n");
}
else if (val == cookie) {
printf("Boom!: getbuf returned 0x%x\n", val);
validate(3);
}
else {
printf("Dud: getbuf returned 0x%x\n", val);
}
}
When getbuf executes its return statement (line 5 of
getbuf), the program ordinarily resumes execution within function
test (at line 5 of this function). Within the file bufbomb, there is a function
smoke having the following C code:
void smoke()
{
printf("Smoke!: You called smoke()\n");
validate(0);
exit(0);
}
Your task is to get bufbomb to execute the code for
smoke when getbuf executes its return
statement, rather than returning to test. You can
do this by supplying an exploit string that overwrites the stored
return pointer in the stack frame for getbuf with the
address of the first instruction in smoke. Note that
your exploit string may also corrupt other parts of the stack state,
but this will not cause a problem, since smoke causes the
program to exit directly.
Some Advice:
- All the information you need to devise your exploit
string for this level can be determined by examining a diassembled
version of
bufbomb. - Be careful about byte ordering.
- You might want to use
gdbto step the program through the last few instructions ofgetbufto make sure it is doing the right thing. -
The placement of
bufwithin the stack frame forgetbufdepends on which version ofgccwas used to compilebufbomb. You will need to pad the beginning of your exploit string with the proper number of bytes to overwrite the return pointer. The values of these bytes can be arbitrary.