Nanomites was a Reverse engineering challenge of 300 point in SharifCTF7. The specification of this problem was the following:

Analyze the given file. Find the C&C IP address and the data sent to it in plain text.
Flag = SharifCTF{md5(strcat(IP, Data))}_

For the ones that coud not attend the competition, You can download the challenge from here.

After running the command file against the binary, I got the following output:

Nanomites.exe: PE32 executable (GUI) Intel 80386, for MS Windows

My next steps after knowing this was to analyze it with IDA in order to find out any evidence of the binary connecting to a remote host.

Once the file is in IDA, we can see that the binary is some what obfuscated.

relative call int3

Looking for strings XREFs, I found myself with the IP address of the C&C:


After knowing the IP address of the C&C, I then opened wireshark to see if I could intercept any communications. I indeed intercepted a stream. This stream looked like this:

Message intercpeted

Clearly there is an encrypted message that our host is sending to Note the size of the encryped payload is of 24 bytes

After knowing this information, then I proceeded to look where the application sent the buffer with the encrypted payload. Looking at the imported functions. We can see that send is at address 0x401564

send XREF

Based on the arguments that sends has. we can see the buffer that is supposed to hold the encrypted payload. If we look above the call to send we can see that this buffer is passed to two more functions. these are at 0x402C97 and 0x401260

0x402c97 0x401260

For sake of simplicity we are not really going to explain the purpose of function 0x402c97 since I think this function is merely used for confusion purposes. Depending how well we do debugging it, this function will return a value of 34, 22, 0 or instead redirect execution into an end_point of execution. Moreover, this function even though retrieves a different return value in eax depending which path is executed, this return value is never actually used outside the context of itself. However it really doesnt matter what this function returns. The actual purpose of this function is to copy the contents of its 3rd argument to its 1st argument. Wheter this copy will be successfull will be determined by the value of the second argument. The following is a decompilation of this function:

signed int __cdecl copy_cond(char *copy, int centinel, char *payload) {
  int v3; 
  _DWORD *v4; 
  signed int v5; 
  char v7; 
  signed int v8; 

  v3 = centinel;
  if ( !centinel )
    goto LABEL_4;
  if ( !payload )
    *copy = 0;
    v4 = junk();
    v8 = 22;
    goto LABEL_5;
  v7 = *payload;
  *copy = *payload;
  if ( v7 )
    v3 = centinel - 1;
  if ( v3 )
    return 0;
  *copy = 0;
  v4 = junk();
  v8 = 34;
  v5 = v8;
  *v4 = v8;
  return v5;

Furthermore, something more interesting happens when we analyze the function at 0x401260. In this function, the function discussed above (copy_cond) is called. Interesting enough, one of its arguments results some what familiar:

payload payload_dump

That is the encrypted payload we intercepted previously with wireshark. Assuming that the contents of the payload are copied to the first argument of that call, seeing the following will be enlighten:


The previous routine is xoring each byte of the buffer-copy of the encrypted payload against 70 (0x46). Knowing this, I run the following python script:

#!usr/bin/env python

payload = [ 0x12, 0x2e, 0x2f, 0x35, 0x19, 0x0f, 0x35, 0x19, \
            0x12, 0x2e, 0x23, 0x19, 0x15, 0x23, 0x25, 0x34, \
            0x23, 0x32, 0x19, 0x02, 0x27, 0x32, 0x27, 0x46 ]

print ''.join([chr(i ^ 70) for i in payload])

The output of this script is: This_Is_The_Secret_Data.

Having found the secret message, and knowing the IP address of the C&C server we can find the md5 for our flag, which happens to be: