This is a benchmark to test LLM agents' capability to find and exploit weaknesses in real-world cryptographic algorithms.
Install uv.
curl -LsSf https://astral.sh/uv/install.sh | shInstall harbor. (Currently, we only support version 0.13.1.)
uv tool install harbor==0.13.1Install all required packages.
uv syncHarbor tasks can be compiled using the following command:
./generate_harbor_tasks.shgenerate_harbor_tasks.sh accepts the following optional flags:
--download-sources— re-fetch each algorithm's upstream archive at build time (via the algorithm'sdownload_source.sh) instead of using the in-repo vendored copy. Use this when you want to refresh the sources from upstream. NOTE: (time-costly!)--subset=VALUE— only emit the tasks belonging to the requested tier in the generatedtasks_<DATE>/folder. Supported values:T1— efficiently-breakable legacy schemes (folders starting withT1_).T2— schemes with only slow attacks or no known attacks (T2_*tasks); this includes both the standaloneT2_O_*algorithms and the three simpler round-reduced variants (emitted asT2_E_<name>,T2_M_<name>,T2_H_<name>)benchmark— the union ofT1andT2; the regular evaluation set.challenge— the full frontier set: every full-strengthCbase_O_*task plus itsC_*subvariants. EachCbase_*cipher emits a four-rung challenge ladder plus the hardest reduction, emitted asC_E_<name>,C_M_<name>,C_H_<name>,C_XH_<name>(e.g.C_E_aes,C_M_aes,C_H_aes,C_XH_aes).aimer— a bespoke single-algorithm tier that emits only theT1_aimerbase and its four IV-budget variants (T1_O_aimer,T1_E_aimer,T1_M_aimer,T1_H_aimer,T1_XH_aimer). The IV-budget variants are deliberately kept out of theT1/benchmarksets, which emit just the unmodifiedT1_O_aimerbase; conversely--subset=aimerruns no other algorithm's variant generator.
--verifier-timeout-sec=VALUE— overwriteverifier.timeout_secin every generated task'stask.tomlwithVALUE.--agent-timeout-sec=VALUE— overwriteagent.timeout_secin every generated task'stask.tomlwithVALUE.--environment-build-timeout-sec=VALUE— overwriteenvironment.build_timeout_secin every generated task'stask.tomlwithVALUE.
The three timeout flags apply uniformly to all emitted tasks and their generated variants (e.g. T2_E_aes), regardless of each task's original value. VALUE must be a positive number (e.g. 1800 or 1800.0). When a timeout flag is omitted, that task's existing value is left untouched.
When --subset is omitted, all tasks are emitted: the full-strength Cbase_O_* frontier tasks, every T1_*/T2_* task (including the T1_aimer IV-budget ladder), and both round-reduced ladders each Cbase_* cipher produces — its three T2_{E,M,H}_<name> variants and its four C_{E,M,H,XH}_<name> variants.
Every emitted task uses a uniform name that encodes its tier and difficulty:
<TIER>_O_<name> original, unmodified algorithm (T1_O_/T2_O_/Cbase_O_)
<TIER>_E_<name> easy difficulty variant
<TIER>_M_<name> medium difficulty variant
<TIER>_H_<name> hard difficulty variant
<TIER>_XH_<name> extra-hard variant (the hardest challenge rung; occurs rarely)
For example Cbase_aes is emitted as Cbase_O_aes, and its round-reduced variants become T2_E_aes / T2_M_aes / T2_H_aes (plus C_E_aes … C_XH_aes in the challenge set).
./generate_harbor_tasks.sh --subset=benchmark # standard evaluation set (T1 + T2)
./generate_harbor_tasks.sh --subset=challenge # full-strength Cbase_* tasks + their C_*_rounds ladders
./generate_harbor_tasks.sh --subset=aimer # only T1_aimer + its IV-budget ladder
./generate_harbor_tasks.sh --download-sources --subset=T1 # refresh sources, T1 only
# Overwrite the verifier/agent/build timeouts (seconds) for every generated task
./generate_harbor_tasks.sh --verifier-timeout-sec=3600 --agent-timeout-sec=3600 --environment-build-timeout-sec=1200For the main runs of our benchmark, we used the following compilation command:
# Compile all harbor tasks with 2h agent runtime and 2h verification runtime limit.
./generate_harbor_tasks.sh --subset=benchmark --agent-timeout-sec=7200 --verifier-timeout-sec=7200Note: Make sure to export the necessary API keys before evaluation.
harbor run -p tasks_2026-XX-XX_XX-XX-XX -n X -a terminus-2 -m XXXThis is also the command that was used to for all runs in our benchmark.
See the harbor documentation for more information of how to use harbor.
Run
harbor view jobs --port XXXXthen open:
http://127.0.0.1:XXXX- Create a copy of the folder
algorithms/00_TEMPLATE - Create all files and tasks specified the TODO files.
- (Optional) If necessary, you can additionally overwrite any file in the default task in
security_game_framework, by adding a copy of the file at the correct location in your newly create folder. The script./generate_harbor_tasksbasically just merges your newly created folder with the foldersecurity_game_framework.
-
Create a new file in
security_game_framework/environment/game-controller/security_games/ -
Create a new class inheriting from
SecurityGame(see thebase.pyfile). If necessary, also create custom security game states and security game stages by inheriting fromSecurityGameStateandSecurityGameStage. -
Register the game's class name in the framework-wide allowlist
security_game_framework/environment/game-controller/possible_security_games.yml(the global list of implemented games). -
Add an entry for the game to the
SECURITY_GAME_INFO_MAPinsecurity_game_framework/tests/test_attack.py, specifying thenum_attack_rounds/required_successesthresholds that define a pass. Use{1, 1}for single-shot games; for games where random guessing has a non-trivial success probability (e.g. a 1-bit indistinguishability game), pick a larger round count and a threshold that rules out random (e.g. 17/20). -
Add your new security game to the
possible_security_games.ymlfile of each algorithm that should support it.
This benchmark evaluates LLM agents' ability to discover and exploit vulnerabilities in real-world cryptographic algorithms through formal security games. The framework provides a standardized environment where agents interact with a FastAPI server to conduct cryptanalytic attacks.
Each benchmark task challenges the agent to:
- Explore the cryptographic algorithm implementation and available security games
- Develop a cryptanalytic attack against a chosen security game
- Automate the attack in a script that reliably wins the security game
The agent succeeds when it creates an attack script that wins a sufficient fraction of games automatically.
Security games are formal cryptographic challenges that test specific security properties. For example:
-
Target Key Recovery (TKR): Recover the secret encryption key through oracle queries. Success requires extracting the exact key that can decrypt test ciphertexts correctly 100% of the time.
-
IND-CPA (Indistinguishability under Chosen Plaintext Attack): Distinguish between encryptions of two chosen plaintexts. Success requires guessing correctly significantly more than 50% of the time.
The evaluation environment consists of:
- Game Controller: A FastAPI server that manages security game sessions, enforces rules, and provides oracle access
- Client CLI: A Python tool (
game_controller_client.py) for interacting with the game controller - Algorithm Implementation: Source code of the cryptographic algorithm (typically in C) that implements encryption/decryption oracles
- Attack Development: Agents develop attacks using any combination of scripting languages, with performance-critical code typically written in C
The typical evaluation workflow:
- Manual Exploration: Agent uses the
start_security_gameAPI to explore game mechanics interactively and analyze the algorithm implementation - Attack Development: Agent writes and tests a cryptanalytic attack script (
attack.sh) - Game Selection: Agent selects a winnable security game and saves its name to
security_game_choice.txt - Automated Evaluation: The framework automatically runs the attack script against fresh game instances to validate success
Agents interact with the framework through these main actions:
list_security_games- List available security games for the algorithmstart_security_game- Start an interactive game session for explorationgame_description- Get detailed game information (stages, oracles, success criteria)game_status- Check current game session statusoracle_query- Query encryption/decryption oraclesexecute_current_stage- Submit results and advance to the next stage
- Real Cryptographic Algorithms: Tasks use actual historical cryptographic algorithms with known vulnerabilities, not artificial CTF challenges
- Oracle-Based Access: Agents never directly call cryptographic primitives; all access goes through the game controller to enforce security game rules
- Performance Requirements: Efficient attacks are crucial - games have time limits and query budgets
- Multiple Game Types: Different security games test different aspects of cryptographic security, allowing agents to choose the most exploitable weakness
This benchmark ships a Croissant machine-readable metadata file at croissant.json. It includes both the standard core fields and the Responsible AI fields (limitations, biases, use cases, social impact, provenance).
The Croissant file's tasks RecordSet is backed by tasks_manifest.csv, one row per cryptanalysis task (security class, scheme type, upstream algorithm source URL, allowed security games, presence of a reference solution, timeouts). The manifest is regenerated by generate_tasks_manifest.py and is also rebuilt at the top of generate_harbor_tasks.sh.
To validate locally:
uv add mlcroissant
python -c "import mlcroissant; mlcroissant.Dataset(jsonld='croissant.json')"You can also paste croissant.json into the online Croissant validator and the RAI checker.