Random_key
Crypto challenge from ECW 2023
Random_key
The problem
We are given a c file :
unsigned char key[32] = { 0 };
void md5(unsigned char *in, unsigned char *out)
{
MD5_CTX ctx;
MD5_Init(&ctx);
MD5_Update(&ctx, in, strlen(in));
MD5_Final(out, &ctx);
}
unsigned char *generate_256bits_encryption_key(unsigned char *recipient_name)
{
int i = 0;
FILE *f = NULL;
time_t now1 = 0L;
time_t now2 = 0L;
time_t delta = 0L;
now1 = time(NULL);
f = fopen("/dev/urandom", "rb");
fread(&key, 1, 32, f);
fclose(f);
md5(recipient_name, key);
now2 = time(NULL);
delta = now2 - now1;
key[8] = delta;
return key;
}
And the python file using it :
from ctypes import *
from Crypto.Cipher import AES
SO_FILE = './generate_key.so'
FLAG_FILE = '../../flag.txt'
with open(FLAG_FILE, 'r') as f:
FLAG = f.read().encode()
def encrypt(plaintext, key):
return AES.new(key, AES.MODE_CBC, b'FEDCBA9876543210').encrypt(plaintext)
if __name__ == '__main__':
# long print
generate_256bits_encryption_key = CDLL(SO_FILE).generate_256bits_encryption_key
generate_256bits_encryption_key.restype = c_char_p
key = generate_256bits_encryption_key(b'Control_center').hex().encode()
enc = encrypt(FLAG, key)
print('Enc:', enc.hex())
The last thing we are given is the output of the python script :
Enc: 21952f9ced6c9109f8ce7c41cd3e0e6981c97a84745d5fdc75b2584e9a5a05e0
So the script creates an aes key by taking the md5 hash of a known parameter “recipient_name” in a buffer filled with 32 random bytes ( it hence overwrites 16 our of the 32 bytes), then setting the 8th byte to some time delta.
The solution
We can see after some test that the time delta is always 0, so the 8th bytes of the hash will always be 0. This means that the key returned is only of length 8 and only composed of the hash of the parameter.
Hash first 8 bytes | Hash last 8 bytes | 16 random bytes from urandom |
---|---|---|
Returned | Not returned | Not returned |
To extend the 8 bytes into the 16 bytes needed for the key, the python program just takes the hex representation and encode it, so we’ll just do the same.
Solve script :
from Crypto.Cipher import AES
import hashlib
flag = bytes.fromhex("21952f9ced6c9109f8ce7c41cd3e0e6981c97a84745d5fdc75b2584e9a5a05e0")
recipient_name = b'Control_center'
key = hashlib.md5(recipient_name).hexdigest()[:16].encode()
print(AES.new(key, AES.MODE_CBC, b'FEDCBA9876543210').decrypt(flag))
Flag : ECW{random_key_7AgmwlBXo1tDhyqR}