Sunday, June 2, 2013

EBCTF Teaser 2013 - Crypto 100 - [Team xbios]

We suspect an employee of one of the embassies has leaked confidential information to a foreign intelligence agency. We've managed to capture an individual whom we assume to be the recipient of the info. Our forensics department has managed to recover two messages from his outbox, which appear to be encrypted using some crypto tool. Along with each email our suspect also received an SMS message containing a password, however we were only able to recover one - "SieR1mephad7oose". Could you help us decrypt both messages?

We had access to the cypto algorithm ( and two messages sent (msg001.enc and msg002.enc). The password for 1st message is given in the README file. First lets decrypt the message
[ctf@renorobert cry100_espionage]$ python 
Usage: encrypt <password> <infile> <outfile> decrypt <password> <infile> <outfile>

[ctf@renorobert cry100_espionage]$ python decrypt SieR1mephad7oose msg001.enc msg001.dec 
[ctf@renorobert cry100_espionage]$ cat msg001.dec 
From: Vlugge Japie <>
To: Baron van Neemweggen <>
Subj: Weekly update


Sorry, I failed to get my hands on the information you
requested. Please don't tell the bureau - I'll have it
next week, promise! 

Vlugge Japie
Ok, there is nothing interesting in this message. We have to figure out a way to read the msg002.enc file. This is what the crypto algorithm does

Key Generation routine
[*] Generate raw bytes by hashing the password with sha256 algorithm, this gives 32 bytes
[*] XOR first half of hash with the second to generate 16 bytes key. Repeat this again for 20000 rounds

[*] Once key is generated, the message is split into blocks of 16 bytes
[*] First 16 bytes of message is XOR'ed with 16 bytes key to get cipher text
[*] The key is then updated using the same key generation routine, after appending the len(msg) to the current key
[*] Thus every 16 bytes of plain text is encrypted with updated key

Since both messages are sent by same person, we assumed that mail headers are same in both messages. To decrypt the msg002.enc file
[*] XOR first 16 bytes of decrypted msg001.enc file and first 16 bytes of decoded msg002.enc file
[*] We found the key that comes after 20000 rounds, now pass this key to the encryption routine mentioned above

We used the given to write the solution. Here it is
#!/usr/bin/env python

import hashlib

msg_one = open("msg001.dec").read().strip()
msg_two = open("msg002.enc").read().decode("base64")
hash_key = ''
blk = 16

# find key
for i in range(blk):
    hash_key += chr( ord(msg_one[i]) ^ ord(msg_two[i]) )
print repr(hash_key)

def xor(a, b):
    l = min(len(a), len(b))
    return ''.join([chr(ord(x) ^ ord(y)) for x, y in zip(a[:l], b[:l])])

def h(x):
    x = hashlib.sha256(x).digest()
    x = xor(x[:16], x[16:])
    return x

def crypt(msg, hash_key):

    k = hash_key
    out = ''

    for i in xrange(0, len(msg), 16):
        out += xor(msg[i:i+16], k)
        k = h(k + str(len(msg)))
    return out

print crypt(msg_two, hash_key)
[ctf@renorobert cry100_espionage]$ python
From: Vlugge Japie <>
To: Baron van Neemweggen <>
Subj: Found it!


I found some strange code on one of the documents.
Is this what you're looking for?


Vlugge Japie
The flag for the challenge is ebCTF{21bbc4f404fa2057cde2adbf864b5481}

No comments :

Post a Comment