Defcon CTF Quals 2014 – 100lines | zepvn
6/13/2014
Search MAY 18, 2014
Defcon CTF Quals 2014 – 100lines By admin
Challenge description:
It’s not broken, you just need more RAM. http://services.2014.shallweplayaga.me/100lines_53ac15fc7aa93da92629d37a669e106c 100lines_53ac15fc7aa93da92629d37a669e106c.2014.shallweplayaga.me:20689 This is the second 64-bit binary file that I deal with in this CTF. It has 4 main functions called calc , loop , getByte , and of course main . A quick pseudo-code to describe what main does: Generate 38 number (32-bit each) as OTP, store to (long long) OTP[38] Calculate (long long) seed variable based on a constant (named __randpad_len in the binary) Generate a (char*) static_buffer based on static buffer (named __randpad in the binary) Print all generated numbers to STDOUT. Read 8 chars from STDIN. set counter = 0 For each input char: Do a check with very long condition which involves a lot of calls to getByte() function. If the check returns True: counter += 1 if counter > 6: Read file 'flag' and store to (char*) flag. Loop i from 0 to 37: (char) c = getByte(OTP[i], seed, static_buffer) ^ flag[i] Princ c to STDOUT in hex format.
The condition that is used to check looks like this:
if ((input_string[i] == (LODWORD(LODWORD(LOBYTE(LODWORD(LODWORD(getByte(OTP[i], seed, static_buffer)) - LODWORD(LODWORD(LOBYTE(LODWORD(LOWORD(LODWORD(LODWORD(LODW
That looks pretty scary to me. However if we look at it closely, the check is basically a comparison between our input character and an expression of OTP , seed , and static_buffer which are all known. So by evaluating that expression with the first 8 numbers from OTP we could get the expected input characters. But it’s actually impossible to do so with the current code base as it always end up calling malloc with a very huge number in getByte function:
char getByte(unsigned long long index, unsigned long long seed, unsigned char* static_buffer) { int size = (seed – 0×20) * ((seed << 2) - 80); (char*) new_buffer = malloc(size); if (new_buffer == null) { exit(0); } else { loop(seed, static_buffer, new_buffer) free(new_buffer); return new_buffer[index]; } }
Notice that the value of seed is 0xf81000 that makes size equal to 1,057,159,935,887,872 , that means it's trying to malloc about 961 Terabytes here! So we definitely need to rewrite this function. We can see that: http://zepvn.com/blog/defcon-ctf-quals-2014-100lines.php
1/5