Monday, July 13, 2015

PoliCTF RE200 - REVERSEMEPLZ

This is a 32 bit binary which validates a key. Removing the dead codes, this is what the algorithm looks like:
    for (size_t i = 0; i < 0xF; i++) {
        if (key[i] < 'a') key[i] = transform(key[1] & 1);
        if (key[i] > 'z') key[i] = transform(key[1] & 2);
        dec[i] = transform(key[i]);
        if (dec[i] != 0xCF && dec[i] > 0xCC) flag = true; 
    }    

    if (flag) return 0;

    for (size_t i = 1; i < 0xF; i++) {
        if (dec[i] - dec[i-1] != diff_array[i]) return 0;
    }

    return transform(key[0]) == 'b';
So the key length is 15 bytes. The first byte of key is transformed to 'b'. The function at 0x08048519 takes single byte as input and gives a single byte output. Considering all ascii small letters as input, one can create transformation table. If that doesn't work, assume key[1] value and build table for ascii printables under transform(0), transform(1) or transform(2)

Below is the solution:

int8_t flag[16] = {0};
int8_t table[256][1] = {0};

int main(int argc, char **argv)
{
    for (size_t c = 97; c <= 122; c++)
        table[transform(c)][0] = c;

    flag[0] = table['b'][0];

    for (size_t i = 0; i < 14; i++)
        flag[i+1] = table[table[flag[i]][0] + diff_array[i]][0];

    printf("%s\n", flag);
    return 0;
}
Flag for the challenge is flag{onetwotheflagyo}. Full source is found here

No comments :

Post a Comment