EVM Dual-Layer Integration
Hyperliquid-style dual-layer architecture enabling EVM smart contracts to read aggregate market data and submit trading intents
EVM Dual-Layer Integration
Olympus runs a Hyperliquid-style dual-layer architecture where an embedded reth Ethereum node operates alongside the core matching engine. Smart contracts on the EVM layer can:
- Read aggregate market data (BBO, depth, mid price, last trade, instrument config) via custom REVM precompiles
- Write trading intents (place order, cancel, lock/unlock assets) via the CoreWriter system contract
Architecture
+------------------------------------------------------------------+
| Olympus Validator Process |
| |
| +-------------------------+ +-------------------------------+ |
| | Core Engine | | EVM Layer (reth) | |
| | (Private, Deterministic | | (Public, Ethereum-compat) | |
| | | | | |
| | Matching Engine | | Smart Contracts | |
| | Order Books | | (user-deployed) | |
| | Ledger | | | |
| | | | | Read | | Write | |
| | ArcSwap<Snapshot> | | | | | |
| | | |<---|--Precompile CoreWriter-------| |
| | | | | (0x0800+) (.sol) | |
| | v | | | | |
| | Process Intent <------|----|--------------------| | |
| | (next tick) | | Event logs | |
| | | | | | |
| | +----------------|----|--> System Events injected | |
| | Results (fills, etc) | | (next block, 0x0900) | |
| +--------------------------+ +--------------------------------+ |
+------------------------------------------------------------------+Privacy Boundary
The core engine handles regulated securities. Individual orders, positions, and account balances never enter the EVM state. Only aggregate market data crosses from core to EVM:
| Exposed (aggregate) | Excluded (account-level) |
|---|---|
| Best bid/ask | Individual order details |
| Depth snapshot | Account positions |
| Mid price | Account balances |
| Last trade | Margin state |
| OHLCV | Order history |
| Instrument config | |
| Active instruments |
Block Production Sequence
- Core engine processes tick N -- state is finalized
- Engine publishes snapshot via
ArcSwap::swap() - reth builds EVM block M -- read precompiles access the finalized snapshot
- CoreWriter contract calls emit event logs
- After EVM block M is sealed, event processor extracts CoreWriter logs
- CoreWriter logs injected as transactions into core tick N+1
- Core processes them, results injected as system events in EVM block M+1
The 1-block/tick delay on the write path is inherent -- it protects the core engine from EVM execution timing.
Key Addresses
| Address | Purpose |
|---|---|
0x0800--0x0807 | Read precompiles (BBO, depth, mid price, etc.) |
0x0A00 | CoreWriter system contract (write path) |
0x0B00 | OlympusSettlement contract (state commitment roots) |
0x0900 | System event emitter (result callbacks) |
0x0C00 | OlympusReader contract (typed Solidity wrappers for read precompiles) |
0x0D00 | OlympusTokenFactory contract (CREATE2 factory for per-asset ERC-20 tokens) |
| Deterministic (CREATE2) | Per-asset OlympusToken ERC-20 contracts (see Asset Tokens) |
ERC-20 Asset Token Contracts
Each asset (e.g. AAPL, USD, BTC) has a dedicated OlympusToken ERC-20 contract deployed via the OlympusTokenFactory at 0x0D00. Tokens are per-asset, not per-instrument -- multiple instruments that share the same base asset share the same token. For example, "AAPL-USD" and "AAPL-BTC" both use the same AAPLo token for their base asset. These are standard ERC-20 tokens with operator-controlled mint and burnFrom functions.
- Naming convention: Token name =
"Olympus {ticker}", symbol ="{ticker}o"(e.g. name = "Olympus AAPL", symbol = "AAPLo"). - Deployment: Tokens are deployed via CREATE2 through the factory (
salt = keccak256(symbol), e.g.keccak256("AAPLo")) when instruments introduce new assets. Addresses are deterministic: same symbol always produces the same token address regardless of when it's deployed. - On-chain registry: Token addresses are queryable on-chain via
OlympusTokenFactory(0x0D00).getToken("AAPLo"). - Minting: When a user locks assets on the core layer, the bridge calls
factory.mint(token, recipient, amount)which proxies to the child token. - Burning: When a user unlocks assets via
CoreWriter.unlockAsset(), the bridge callsfactory.burnFrom(token, user, amount)(no allowance required — factory is the token operator). - Standard ERC-20: Users can
transfer()andapprove()tokens freely between EVM accounts. - Persistent addresses: Set
OLYMPUS_BRIDGE_SIGNER_KEYfor restart-stable EVM state. Token addresses are logged at startup (look for "token deployed via factory" log entries).
See Asset Tokens for the full asset vs. instrument distinction, the o suffix convention, and constructor args for Blockscout verification.
Data Encoding
All monetary values use 18-decimal fixed-point on the EVM side (matching the wei convention). The core engine uses native i64 fixed-point with per-instrument scales (e.g., price_scale=2 for equities). The precompiles and CoreWriter decoder handle the conversion transparently.