Stochastic Order-driven Volatility Engine with Recursive Endogenous Instability, Generated Numerically
A C++20 multi-asset limit order book simulation engine that models endogenous flash crashes via rough volatility, multivariate Hawkes processes, and robust market making under Knightian ambiguity.
Version: 0.1.0 | Standard: C++20 | Author: keykyrios (Mitrajit Ghorui)
SOVEREIGN is a header-only simulation engine (22 .hpp files under include/sovereign/) compiled as a static library sovereign_lib. Entry point: apps/main.cpp.
Each tick (default Ξt = 10β»β΄) executes in strict causal order:
| Layer | Engine Class(es) | File(s) | Description |
|---|---|---|---|
| 1 | RoughVolEngine, CGMYEngine, RegimeEngine |
price/rough_vol.hpp, price/levy_jumps.hpp, price/regime.hpp |
12-factor Markovian fBm + CIR-subordinated CGMY jumps + 5-state HMM |
| 2 | HawkesEngine |
hawkes/multivariate.hpp |
10-component sum-of-exp Ogata thinning, 10βΆ event cap |
| 3 | LOBEngine (OrderBook) |
orderbook/lob.hpp |
Eigen::VectorXi book, iceberg orders, β-concave impact |
| 4 | MarketMakerEngine |
market_maker/robust_control.hpp |
5 ghost MM agents, HJB PDE on background thread |
| 5 | RuinEngine |
ruin/gerber_shiu.hpp |
CramΓ©r-Lundberg + Gerber-Shiu IDE (Picard, 200-pt grid) |
| 6 | CorrelationEngine, GraphEngine, SpectralEngine, ContagionEngine |
topology/*.hpp |
EWMA β MP cleaning β Higham β MST/PMFG β Fiedler + Brandes β Laplacian diffusion |
| 7 | PersistenceEngine, LandscapeEngine |
tda/*.hpp |
Native Zβ VR complex β TRI + Lβ landscape + Wasserstein-2 |
Threading: Layers 1β5 run on the main thread. Layers 6β7 run on a dedicated background thread via double-buffered SimulationState snapshots. HJB solving runs on a third thread. Synchronization via std::mutex + std::condition_variable.
RuinEngine (Ξ¨α΅’ > 0.5) β HawkesEngine baseline modulation (1.0 + 0.5Β·max(Ξ¨-0.5, 0))
RuinEngine (Ξ vector, contagion-blended) β HawkesEngine (not local actuarial ruin)
RuinEngine (Ξ vector) β ContagionEngine (implicit Euler Laplacian diffusion)
Topology results β HawkesEngine cross-excitation (Ξ±_ij *= exp(-0.5Β·d_graph))
TRI(t) β ΞΈ(t) = ΞΈβΒ·exp(Ξ±Β·TRI) [Layer 7 β Layer 4, ΞΈβ=0.5, Ξ±=0.1, clamped [0.1,10.0]]
| Library | Version | Purpose |
|---|---|---|
| Eigen3 | β₯ 3.4 | Linear algebra, vectorized matrix ops |
| nlohmann/json | any | Config deserialization (NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT) |
| Boost | β₯ 1.74 | boost::asio for TCP telemetry socket |
| OpenMP | optional | #pragma omp parallel for in price, LOB, impact loops |
| GUDHI | optional | Persistent homology (available via SOVEREIGN_USE_GUDHI=ON β see Building) |
Linux (apt):
sudo apt install libeigen3-dev nlohmann-json3-dev libboost-all-devWindows (MSYS2/UCRT64):
pacman -S mingw-w64-ucrt-x86_64-eigen3 mingw-w64-ucrt-x86_64-nlohmann-json mingw-w64-ucrt-x86_64-boostWindows (vcpkg):
vcpkg install eigen3 nlohmann-json boostmkdir build && cd build
cmake .. -DCMAKE_BUILD_TYPE=Release
cmake --build . --config Release -j$(nproc)CMake Options:
| Option | Default | Description |
|---|---|---|
SOVEREIGN_USE_OPENMP |
ON | Enable OpenMP parallelism |
SOVEREIGN_USE_GUDHI |
OFF | Enable GUDHI persistent cohomology backend (requires GUDHI installed) |
SOVEREIGN_BUILD_TESTS |
OFF | Build unit tests |
./sovereign # Default: 50 assets, dt=1e-4, T=1.0
./sovereign --config default_config.json # Load params from JSON
./sovereign --assets 100 --dt 5e-5 # CLI overrides (applied AFTER config load)
./sovereign --seed 12345 # Reproducible RNG
./sovereign --save-config out.json # Dump effective config| Flag | Description |
|---|---|
--config <path> |
Load configuration from JSON file |
--assets <N> |
Number of assets (default: 50) |
--steps <N> |
Override number of timesteps |
--dt <val> |
Timestep size (default: 1e-4) |
--seed <val> |
RNG seed (default: 42) |
--save-config <path> |
Save effective config to JSON |
The engine streams state snapshots as length-prefixed JSON over TCP to 127.0.0.1:8080:
- Protocol:
[4-byte LE uint32 length][JSON payload] - Decimation: Every 10 ticks (
flush_interval_ = 10) - Serialization: Direct
std::ostringstreamβ NOT nlohmann/json AST - Transport:
boost::asioTCP client with async write viastd::async - Fault tolerance: Silent reconnect if dashboard is not running
The dashboard (sovereign_dashboard.py) is a Python TCP server rendering via pyqtgraph.opengl.
Per-asset: price, log_price, vol, variance, hurst, jump, lob_impact, regime, return1, cum_ret, hawkes_intensity[50], lob{bid_vol, ask_vol, bid_price, ask_price}[20], mm_spread, mm_inventory, surplus, ruin, gerber_shiu.
Global: correlation[NΓN], raw_correlation[NΓN], eigenvalues[N], fiedler, clustering, betweenness[N], degree[N], tri, wasserstein, l1, l2, ruin_vector[N], distance[NΓN].
- 12-factor Markovian approximation of Volterra kernel K(t) = β(2H)Β·t^(H-1/2)
- Decay rates Ξ»β log-spaced from 0.01 to 10,000
- Weights: c_k = β(2H)Β·Ξ»_k^(Ξ³-1)Β·Ξlog(Ξ»)/Ξ(Ξ³) where Ξ³ = 1/2 - H (Abi Jaber & El Euch 2019)
- Exact OU diffusion coefficient per factor (no Euler discretization error)
- Stochastic Hurst OU process with reflection at [0.01, 0.99]
- Systemic market factor: Ξ²=0.5 common factor injected before Cholesky
- Truncated compound Poisson (|x| β₯ 0.01) + Gaussian residual
- Alfonsi implicit CIR subordinator with dynamic Feller enforcement
- Full Laplace exponent compensator Ο(-1) for martingale property
- Systemic jump: C_systemic = 0.5C, each asset gets 0.5ΓJ_systemic
- NΓ5Γ10 dimensional intensity (5 event types Γ 10 depth levels)
- 10-component sum-of-exponentials with O(1) recursive update
- Power-law weights: Ξ±_m β Ξ²_m^{-Ξ΅} (Ξ΅=0.5, approximates Ο(t)=(1+t/Ξ²)^{-(1+Ξ΅)})
- Mark-weighted excitation: w = clamp(size/11, 0.1, 3.0)
- Dykstra spectral radius projection (Ο(R) β€ 0.95)
- Zipf power-law heterogeneity: cap_scale = 1/β(i+1)
Eigen::VectorXibid/ask volumes (M=500 levels per side)- Iceberg orders with latency-gated revelation (~5ΞΌs)
- OU mid-price drift with tick-snapping (ΞΊ=100.0, tight tracking during flash crashes)
- β-concave impact: β sign(imbalance)Β·β|imbalance|Β·1/(1+d) over top 20 levels
- 5 ghost agents per asset (no physical LOB orders)
- Closed-form spread: Ξ΄* = (Ξ³+ΞΈ(t))ΟΒ²|I|/2 + 2Ξ¨ + floor, ΞΈ(t)=ΞΈβΒ·exp(Ξ±Β·TRI) dynamic
- Background HJB on 30Γ30 grid, dp=0.01 unified (CFL-adaptive FTCS, dedicated thread)
- Avellaneda-Stoikov fill model: Ξ» = 100Β·exp(-kΞ΄ - Ξ·|I|)
- Self-Match Prevention (SMP)
- Premium = spread Γ 200 fills/time
- Claims on LOB stress (|impact|Γ10β΄ > 10.0) + Poisson background (0.05/yr)
- CramΓ©r-Lundberg ruin probability with exponential claims
- Gerber-Shiu IDE: Gauss-Seidel iteration, 200-point grid, every 200 steps
- Contagion blending via exponential decay (rate 5.0) to local ruin probability
- EWMA Ξ±=0.005 with adaptive warm-up (first 2N samples)
- MarΔenko-Pastur cleaning with effective N_eff = min(2/Ξ±, t), ΟΒ² from bottom-half spectrum
- Higham alternating projections (50 iterations) for nearest correlation matrix
- Prim's MST O(NΒ²) + PMFG with Euler planarity filter (Eβ€3V-6) + common-neighbor face check
- Fiedler eigenvalue, Brandes betweenness, local clustering
- Implicit Euler Laplacian contagion diffusion (D=0.1) with unified exp(-β(2(1-Ο))) weights
- Vietoris-Rips filtration up to tetrahedra, Ξ΅_max = 2.0
- Native Zβ boundary matrix reduction with O(1) hash map face lookup
- TRI = Ξ£ (d-b)^p / (1+b), p=2.0 β heuristic, NOT Lβ norm
- L^p landscape norms via trapezoidal quadrature
- Greedy O(nΒ²) Wasserstein-2 on Hβ pairs (upper bound)
- RNG: Xoshiro256** with Box-Muller (cached spare), alignas(64)
- Thread-local RNGs: Forked via Vigna's 2ΒΉΒ²βΈ jump polynomial
- Subnormal prevention: FTZ + DAZ on x86_64
- Eigen threading: Disabled (
setNbThreads(1)) to prevent OMP oversubscription - Event buffer: Pre-allocated 4096 entries, reused per tick
- 3-thread architecture: Main tick loop + topology worker + HJB solver
- Markovian kernel weights: Corrected exponent from Ξ»^Ξ³ to Ξ»^(Ξ³-1) per Abi Jaber & El Euch (2019).
- CIR Alfonsi scheme: Ito correction now uses
cfg_.cir_lambdaconsistently. - CGMY small-jump mean: Corrected to use
1-Yexponent for Yβ(1,2) regime. - RMT ΟΒ² estimation: Fixed to use bottom-half (noise) eigenvalues, not top-half (signal).
- Gerber-Shiu IDE signs: Corrected the IDE RHS β conv and Ο are positive contributions.
- Persistence face lookup: O(MΒ²) linear scan replaced with O(1) hash map.
- Hawkes lambda_bar floor: Lowered from 1.0 to 1e-6 to prevent wasted proposals.
- Zipf cap_scale preservation:
modulate_by_graph()now preserves power-law heterogeneity. - Contagion/Spectral Laplacian unification: Both now use exp(-β(2(1-Ο))) weighting.
- Ruin cwiseMax ratchet: Removed β exponential blend governs onset and recovery.
- Distance matrix initialization: Now arccos(identity) instead of all-zeros.
- Landscape quadrature: Trapezoidal rule (half-weight endpoints) instead of Riemann sum.
- MLMC variance estimator: Unbiased (/(n-1)) + Welford-style incremental update.
- GUDHI Build Bug: Fixed
CMakeLists.txtto correctly defineSOVEREIGN_HAS_GUDHI. - TRI β ΞΈ Feedback: Connected the topological risk index to the market maker's ambiguity aversion.
- PMFG Planarity: Added Euler-formula planarity filter and common-neighbor checks.
- Hawkes Weights: Corrected uniform Ξ±_m to true power-law weights Ξ±_m β Ξ²_m^{-Ξ΅}.
- Variance Bias: Added missing cross-factor covariances to the exact martingale compensator.
- Dead Code Cleanup: Removed unused
VolterraFBM,FBMGenerator,n_hybrid_steps, andkernels.hpp. - HJB Grid Consistency: Unified background worker and engine grid spacing to
dp=0.01. - Ruin Signal Path: Clarified that Hawkes feedback reads contagion-blended ruin, not local actuarial ruin.
- LOB Price Lag: Increased OU tracking speed from 1.0 to 100.0 for instant tracking during flash crashes.
- Ghost Market Makers: MMs evaluate spreads and simulate fills internally but never place physical limit orders into the LOB.
- Orphaned MLMC:
mc/mlmc.hppcontains a complete Giles (2008) multi-level Monte Carlo implementation but is never called by the engine. - No Native Calibration: All parameters come from
default_config.json. No MLE/GMM calibration pipeline exists. - Wasserstein Upper Bound: The greedy O(nΒ²) matching is an upper bound on optimal transport, not exact.
All parameters live in config.hpp as nested structs with NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT. Key defaults:
| Parameter | Default | Location |
|---|---|---|
n_assets |
50 | UniverseConfig |
T |
1.0 | SimulationConfig |
dt |
1e-4 | SimulationConfig |
seed |
42 | SimulationConfig |
hurst |
0.10 | RoughVolConfig |
eta |
0.35 | RoughVolConfig |
rho |
-0.90 | RoughVolConfig |
xi_0 |
0.04 | RoughVolConfig |
C, G, M, Y |
1.0, 5.0, 10.0, 1.5 | LevyConfig |
n_order_types |
5 | HawkesConfig |
n_depth_levels |
10 | HawkesConfig |
base_intensity |
10.0 | HawkesConfig |
max_spectral_radius |
0.95 | HawkesConfig |
n_levels |
500 | LOBConfig |
n_market_makers |
5 | MarketMakerConfig |
gamma |
2.0 | MarketMakerConfig |
theta |
0.5 | MarketMakerConfig (base; dynamic ΞΈ(t)=ΞΈβΒ·exp(Ξ±Β·TRI) at runtime) |
tri_alpha |
0.1 | MarketMakerConfig (TRIβΞΈ coupling strength) |
ewma_alpha |
0.005 | TopologyConfig |
max_dimension |
2 | TDAConfig |
max_filtration |
2.0 | TDAConfig |
tri_weight_power |
2.0 | TDAConfig |
SOVEREIGN/
βββ CMakeLists.txt # Build system (C++20, Eigen3, nlohmann/json, Boost)
βββ apps/
β βββ main.cpp # Entry point with CLI parsing
βββ src/
β βββ config.cpp # SimulationConfig::from_json/to_json
βββ include/sovereign/
β βββ config.hpp # All config structs (214 lines)
β βββ engine.hpp # Main orchestrator (376 lines)
β βββ core/
β β βββ clock.hpp # SimulationClock + Event priority queue
β β βββ random.hpp # Xoshiro256** (dead FBMGenerator/VolterraFBM removed)
β β βββ state.hpp # AssetState, SimulationState
β βββ price/
β β βββ rough_vol.hpp # MarkovianFBM + RoughVolEngine
β β βββ levy_jumps.hpp # CGMYEngine + CIR subordinator
β β βββ regime.hpp # RegimeEngine (5-state HMM)
β βββ hawkes/
β β βββ multivariate.hpp # HawkesEngine (NΓ5Γ10, power-law weights)
β β βββ kernels.hpp # Empty stub (dead code removed)
β β βββ stability.hpp # Dykstra spectral radius projector
β βββ orderbook/
β β βββ lob.hpp # OrderBook + LOBEngine
β βββ market_maker/
β β βββ robust_control.hpp # MarketMakerEngine + HJB PDE
β βββ ruin/
β β βββ gerber_shiu.hpp # RuinEngine + CramΓ©r-Lundberg + Picard IDE
β βββ topology/
β β βββ correlation.hpp # EWMA + RMT + Higham
β β βββ graphs.hpp # Prim MST + PMFG (Euler planarity filter)
β β βββ spectral.hpp # Fiedler + Brandes + clustering
β β βββ contagion.hpp # Implicit Euler Laplacian diffusion
β βββ tda/
β β βββ persistence.hpp # Zβ boundary matrix reduction (+ GUDHI path)
β β βββ landscapes.hpp # Landscapes + TRI + Wasserstein-2
β βββ mc/
β β βββ mlmc.hpp # MLMC (orphaned β not called by engine)
β βββ viz/
β βββ telemetry.hpp # TCP length-prefixed JSON telemetry
βββ default_config.json # Default simulation parameters
βββ sovereign_dashboard.py # Python PyQtGraph real-time dashboard
MIT