Atlas
C++23 engine for map-based strategy games with a deterministic lockstep simulation and sandboxed WebAssembly mods.

Live demo
Lab app, compiled with Emscripten
Atlas's own lab app (C++23 sim, view and ImGui UI) compiled with Emscripten; its SDL_GPU layer is replaced by a WebGPU backend written for this demo, the shaders were translated from HLSL with glslang and Tint, and it runs single-threaded.
Overview
Atlas is an engine, not a game: it has no countries, wars, diplomacy or rules, and is not meant to. I built it alone in gated milestones, M0 through M31, each ending with a clean configure, build, test run and a runnable demonstration.
By the numbers
- 1,000+ tests
- 1M-cell tick in 694 us
- 32 milestones, 25 ADRs
Highlights
- 01
Solo C++23 engine for map-based strategy games, built in 32 gated milestones: SDL_GPU renderer, asset pipeline with hot reload, versioned scene serialization, audio, animation, and 25 architecture decision records.
- 02
Deterministic fixed-tick simulation with canonical state hashing, replay, save and load, and lockstep play over ENet sockets proved hash for hash between two processes; a million-cell tick runs in 694 us on four workers.
- 03
Mods run as untrusted WebAssembly with no clock, filesystem or random generator; over 1,000 tests, and CI on macOS, Linux and Windows with ASan and TSan lanes, clang-tidy, a software-GPU lane and benchmarks gated at 1.25x of a recorded baseline.
The story
Every decision that is expensive to reverse is an ADR, 25 so far, and recent milestones each end with a report of what changed, what was run and what is still risky.
Atlas is an engine, not a game: it has no countries, wars, diplomacy or rules, and is not meant to. I built it alone in gated milestones, M0 through M31, each ending with a clean configure, build, test run and a runnable demonstration. Every decision that is expensive to reverse is an ADR, 25 so far, and recent milestones each end with a report of what changed, what was run and what is still risky.
The simulation advances in whole integer ticks and hashes its state, so a replay, a save or a second machine in lockstep can be checked bit for bit. Lockstep runs over the command queue: M14 proved it with several simulations in one process agreeing hash for hash, M17 with two processes over a real ENet socket at a 22.4 us median round trip. A million-cell tick takes 694 us on four workers against 1.650 ms without the pool; what remains is serial, and the hash is 0.38 ms of it. Mods are WebAssembly modules that reach simulation state only by submitting commands, with no clock, no filesystem and no random generator of their own.
Two applications live in the engine. atlas_sandbox demonstrates the lifecycle and scene layer. atlas_lab is a synthetic million-cell grid with map modes, picking, time controls and replay, there to test the architecture rather than to be a game. The first game is chess, written inside the engine’s tree from M18 to M26 as a probe: every rule including the draws, perft-verified, with the Opera Game as a golden hash, playable by two people at one screen or over a socket, and since M26 against an opponent that is a C mod compiled to WebAssembly. M27 made the engine installable as a package and moved chess to its own repository, atlas-chess, built against the installed engine and nothing else. That is the charter’s test for v1.0: a game links the engine and runs a deterministic simulation without patching engine internals.
Not done: the renderer is verified on one Apple GPU and one software rasteriser, so Direct3D 12 and non-Apple hardware are untested. Networking is direct address only, with no encryption, NAT traversal or lobby. No large mod has been written, so what loading a real one costs is unmeasured. Everything deferred is listed with its reason in docs/DEFERRED.md.