Crypto Schola
What's inside

125 challenges across the TLS attack surface.

Ten families cover client configuration and verification, protocol downgrades, RSA, DH/ECDH, ECDSA, RNG failures, KEMs, oracles and key leakage. Most labs ship in both TLS 1.2 and TLS 1.3 variants, plus multi-round gauntlets that mix vulnerabilities.

Client trusts the wrong thing

No chain check · SAN-only match · leaked Superfish CA key

Real client verification bugs

Apple "goto fail" · CVE-2020-0601 forged base point

Protocol downgrade

NULL cipher · FREAK export RSA · Logjam DHE

Broken RSA keys

Fermat · Wiener · Boneh-Durfee · Pollard p±1 · RSA-CRT faults

Weak Diffie-Hellman parameters

Tiny modulus · smooth p-1 · bad generator · invalid curve · MOV

Signing-nonce leakage

Nonce reuse · biased nonce · lattice attack

Post-quantum KEM attacks

ML-KEM/Kyber (lattice) & HQC (code-based) · KAT-exact primitives · genuine KEMTLS handshakes

Post-quantum signatures

ML-DSA/Dilithium (FIPS 204) & SLH-DSA/SPHINCS+ (FIPS 205) · nonce reuse · weak key generation

Weak or backdoored entropy

Predictable ServerHello.random · weak X25519 keys

Padding & compression oracles

Bleichenbacher · Manger · BREACH / CRIME

Key leakage & side channels

FTP · SSH · HTTP · Redis · Postgres · Heartbleed

Proof, not theory

Examples of real attacks reproduced.

Each family above isn't hypothetical — these are named CVEs and historical incidents the lab rebuilds at the protocol level.

CVE-2014-0160 Heartbleed
CVE-2014-1266 Apple "goto fail"
CVE-2020-0601 CurveBall
CVE-2015-4000 Logjam
FREAK RSA_EXPORT downgrade
BREACH / CRIME compression oracles
Superfish / Komodia 2015 CA key leak
Dual_EC_DRBG backdoored RNG
Bellcore / Lenstra RSA-CRT fault
Bleichenbacher / Manger padding oracles
FAQ

Frequently asked questions

Is this real TLS, or a simplified simulation?

Real. Where a supported library (rustls) has no config knob for the historical misconfiguration being taught — finite-field DHE, RSA_EXPORT, explicit-curve ECDHE, static-key KEMTLS — the platform hand-rolls a genuine TLS 1.2/1.3 engine instead: real record layer, real key schedule, real Finished messages. There is no vendored X.509/ASN.1 crate anywhere in the project either. And the cryptography is the genuine article: every algorithm in the lab passes its official Known-Answer Tests, not just the post-quantum ones. A single audit (audit_kat.sh) validates each primitive bit-for-bit against the standard's own vectors — ML-KEM-768 (FIPS 203), ML-DSA-65 (FIPS 204), HQC and SLH-DSA-SHAKE-128f (FIPS 205) against the NIST ACVP / KAT vectors, and the classical primitives (SHA-2/SHA-3, SHAKE, HMAC, HKDF, AES-GCM, PBKDF2, RSA PKCS#1 v1.5 & PSS, DSA, ECDSA P-256) against their FIPS / RFC test vectors. Keys and signatures therefore interoperate with any standard library — the weakness is always in how a primitive is used, never a toy look-alike.

Do I need to already know the underlying cryptography?

You should be comfortable with TLS fundamentals, a terminal, and modular arithmetic. Levels 1-2 explain enough as you go; Levels 3-4 assume you can follow a lattice-reduction or index-calculus argument.

What do I actually submit to solve a challenge?

A 32-byte secret, as 64 hex characters, that the TLS client sent the server inside the (broken) TLS session. It's checked against an independent validator process, not against a static answer file.

Is the platform's own source code included?

No — deliberately. The student archive ships pre-built Docker images and a launcher script only, so nothing on disk hands you the answer by accident. That's separate from the challenge solutions themselves, which are included in full.

Are solutions really included?

Yes. Every one of the 125 challenges ships with a complete, working exploit script and a written explanation of the technique. Try first — the solution is there the moment you want it.

Does this run on macOS or Windows?

The core attack model needs a genuinely rootful Linux Docker daemon with direct host access to the lab's bridge network for ARP spoofing — something a rootless daemon (and most non-Linux Docker setups) cannot provide. The optional attacker-toolbox container works around this for challenges that don't strictly need a host-level MITM position, but a native Linux host is what this was built and tested against.

What's the resource footprint when it's running?

Small either way. The three core containers (server, client, validator) are FROM scratch, UPX-packed Rust binaries. The free 12-challenge sample measures about 2.2 MB combined on disk; the full 125-challenge build compiles in more challenge code per binary, so it's larger — roughly 5 MB combined, based on this project's own measured light-vs-full size delta (~50-65% smaller per binary when only 12 of 125 challenges are compiled in). RAM stays around 10 MB total either way — only one challenge runs at a time regardless of how many are compiled in, so RAM tracks the active challenge, not the build size. CPU usage is negligible outside brief bursts during key generation at startup. Docker Compose caps each container at 2 GB RAM / 2 CPU cores as a safety ceiling, not a requirement — real usage is a small fraction of that. One documented exception: server_rsa_hundreds_servers_tls12 spawns 501 parallel RSA-2048 key generations at startup and needs --cpus=8 to finish in reasonable time. The optional attacker toolbox (nmap, hydra, etc. — only built if you ask for it) adds roughly 70 MB and isn't required for most challenges.

What if I get stuck?

Every challenge's write-up in the manual explains the vulnerability class and the technique that solves it, and the included solution script is there if you'd rather see it worked end to end. For anything beyond that, reach out — contact details will be provided with the release materials.

Ready to see it running?

Try 12 of the 125 challenges free, or get the full lab.