The goal of this challenge is to leverage format strings to modify arbitrary memory locations to print the winning statement.
**printf(string);**
: This is the vulnerable function in this code. The printf()
will not check whether the supplied inputs expected format strings or not since it is coded to accept any string values. So what we can do is simply to verify if we can leak memory addresses and also write arbitrary code onto the stack ([READ] %p
→ [WRITE] %n
).**if(target) {**
: The target
variable is what we need to find. Then, by leveraging a Format String vulnerability, we will write the address onto the stack to print out the winning statement by specifying the right offset value.Let’s disassemble the binary to see what is doing at the ASM-level:
$ gdb -q format1
Reading symbols from /opt/protostar/bin/format1...done.
(gdb) set disassembly-flavor intel
(gdb) disassemble vuln
The program is pretty simple. One interesting thing is that mov eax,ds:0x8049638
moves the following address from the .bss
(part of the .data
segment) into EAX
register.
Below is to dump the binary’s headers using objdump
:
$ objdump -h /opt/protostar/bin/format1
...(snip)...
23 .data 00000008 08049628 08049628 00000628 2**2
CONTENTS, ALLOC, LOAD, DATA
24 .bss 0000000c 08049630 08049630 00000630 2**2
ALLOC
...(snip)...
Then, the test eax,eax
creates a conditional jump by setting eflags
value to ZF
(=Zero Flag) if the EAX
is equal to “0.” If “0,” it jumps; otherwise, it continues its execution flow.
As discussed, the vulnerable function is the printf(string)
. When we supply a random string, it just echoes back:
However, if we supply some format string parameters, we get interesting outputs 😮:
What this is doing is basically printing out some random addresses in stack memory. But more interesting thing is if we enter enough format string parameters, we can actually find the strings that we enter on the stack.
$ ./format1 $(python -c 'print "AAAA" + "%p|" * 156') && echo
To abuse this: (1) Find an offset where we can control → (2) Write an arbitrary code we wish to execute. In this case, we will just supply an address for target
variable to print the winning statement.
#format-string-attack #string-format #protostar-format1 #exploit-exercise-format1 #protostar-walkthrough