CTF,

Efiens CTF – mediumRE

sshot-3

Hi folks. This post is about a Efiens challenge, easy-medium RE that my colleague Cothan publish on twitter as a part of a set of them included on Efiens CTF.

Number of challenges solved by brucel33t

As described on his tweet, is an easy ctf that try to catch some talent people. I have spare time to participate as brucel33t kamikaze ninja. Three challenges per category that implies an easy,medium and hard levels. Let’s see our binary and it’s behaviour.

Original mediumRE task panel

mediumRE: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux.so.2, for GNU/Linux 2.6.32, BuildID[sha1]=274cf5b891f49bf138e9d60a08dce32daf80b3ab, not stripped

Binary ask for a password. We can remote GDB with IDA and start analysis. Has «main» and «check» interesting functions. If we focuse on «check» function binary do a strlen check for a 30 characters password lenght setting a counter to -1 if not.

Check function

The second red rectangle is indeed the check loop. Counter must be set to 30 to get the «Good» answer, so the if block need to enter 30 times on that compare. It Compares each element of an array «encoded» with our input multiply by first 30 Fibonacci sequence adding «i» value on each iteration.

What is this encoded array? Reader at this moment will have realized that if we use a simple equation we can solve the problem. We have:

  • encoded data: solution of input[i] * fibo[i] + i
  • fibo data: first 30 fibonacci sequence

Input is what we want to know. Let’s use a python script to solve this. On each iter we must calculate (enc[i] – i)/fibo[i]. This is char value of our input.

See encoded results on a breakpoint

30 values of enc array

And Fibonacci sequence

First 30 values of Fibonacci

Putting all together on Python.


#!/usr/bin/env python
"""
mediumRE from
compare algorithm
for ( i = 0; strlen(input) > i && i <= 29; ++i )
{
if ( enc[i] == input[i] * fibo[i] + i )
++cnt;
}
if ( cnt == 30 )
printf(yes);
else
printf(no);
"""
encoded = [0x43, 0x70, 0xDE, 0x138, 0x23E, 0x30D, 0x5EA, 0xA09, 0x46A, 0x12BA, 0x2327, 0x3CCB, 0x6258, 0x8BF4, 0xEE56, 0x1AC04, 0x2AE46, 0x3FB89, 0x21B07, 0x8ABD7, 0x115EE4, 0x1C605C, 0x324959, 0x33A637, 0x83A6BB, 0x81A97F, 0x143AFF2, 0x1D664AE, 0x32830EF, 0x1A2F745]
fibo = [0x01 ,0x01 , 0x02 , 0x03 , 0x05 , 0x08 , 0x0D , 0x15 , 0x22 , 0x37 , 0x59 , 0x90 , 0xE9 , 0x179 , 0x262 , 0x3DB , 0x63D , 0xA18 , 0x1055 , 0x1A6D , 0x2AC2 , 0x452F , 0x6FF1 , 0xB520 , 0x12511 , 0x1DA31 , 0x2FF42 , 0x4D973 , 0x7D8B5 , 0xCB228]
i=-1
flag =''
for enc in encoded:
i = i + 1
flag =''.join(chr((enc – i )/fibo[i]))
print flag

view raw

mediumRE.py

hosted with ❤ by GitHub

Final solution