Monday, March 10, 2014

RuCTF 2014 Quals - TLS (Crypto 300)


The task consisted of a 19kB pcap file with a single complete TLS conversation between a client and an HTTPS server (using DHE_RSA), and a rather laconic description - "just break TLS". Well, since you asked…

Poking around

Shortly after opening the file in Wireshark intersting details surface. While the server looks absolutely valid, the client seems to have a rather unusal random number generator. The 0x20 byte long random nonce sent in the Client Hello message is:

0000000: 4469 4865 2031 3333 3720 3133 3337 2031  DiHe 1337 1337 1
0000010: 3333 3720 3133 3337 2031 3333 3720 3133  337 1337 1337 13

Since that looks very non-random, perhaps the client exponent is easy to figure out?
We can get the Diffie-Hellman parameters p and g from the Server Key Exchange mesage, we also have gx from the Client Key Exchange:
The first attempt - assuming the exponent to be " 1337", repeated to fill 32 bytes and shifted - was unsuccessful. The second - trying the number 1337 - worked just fine.

So now that the client's private exponent has been recovered, it's time to decrypt the session…


Wireshark comes with a built-in SSL decryption facility. What it needs is a Session ID and a Master Secret. The Session ID is (as this is a new session) sent in the Server Hello message, so we have that. We also have the client secret (1337), the generator (2), the prime and the server public key (gy). This allows us to compute gxy, the Pre-Master Secret, by simply raising the server public key to the 1337-th power, mod p.

The Master Secret is computed - according to TLS specs - as PRF(premaster_secret, "master secret", Client Random + Server Random)[0..47], the "+" being string concatenation, and PRF defined someplace else in the same RFC.

Luckily we have all of those, and there is a compliant implementation of the PRF function in the tlslite python library. Plugging in the appropriate values, the master secret is obtained:
After creating a master key logfile for Wireshark to consume, the data can be successfully decrypted:

Since RUCTF_ILoveToHackTLS was indeed the correct flag, this concludes the write-up.


  1. Hi,

    Could you please to upload the challenge file ?


  2. ← here you go. Additionally a message from the organizers: “we will publish all our tasks on Github ( after Quals Afterparty.”

  3. Hi! Nice review!

    Here is my solution:

    Alexander Bersenev, author of this task