Trading and the venue
Every fill on the desk, from a user buy to a forced sale, settles through one Router against a venue that is open continuously, floored at the oracle mark on a buy and at the sale reference on a sell.
Always open
The venue is a set of on-chain pools, so it runs every hour of every day. There is no opening bell, no close, no holiday and no session the desk has to mirror: a buy, a sell, a swap, the daily charge and a forced sale all execute at 3am on a Sunday exactly as they do at noon on a Tuesday. Nothing in these pages is conditional on a market being open, because the market this desk trades on never closes.
One path for every fill
Buys, sells and swaps execute from inside your margin account: MarginAccounts holds custody, the Router takes the assets only for the duration of the fill transaction, and everything settles back into the same account atomically. A buy spends account USDG first and draws buying power for the remainder; a sell pays the debit first and credits any surplus as account USDG; a swap runs a sell then a buy in one transaction, with the margin test applied once to the post-swap basket. If any leg fails, the whole transaction reverts. Nothing partial ever settles, and nothing passes through your wallet mid-trade.
The minimum fill and your tolerance
The Router does not trust the venue's price. Before every buy it reads the mark from the oracle hub and computes the fair quantity; before every sell it reads the sale reference, which is the mark while the feed is fresh and the pool TWAP itself while the feed is stale, and computes the fair value; then it applies the caller's slippage budget, the tolerance you set on the ticket, to produce a floor:
The floor rides into the venue as the swap's minimum output. A fill that would land below it reverts in full; there is no partial execution and no fallback price. The mark itself is not always the Chainlink print: under a stale feed it is the pool TWAP capped one class deviation band above the feed's last print, which is crypto's normal state under the 5 minute crypto window and every weekend's for equities, and under divergence beyond the band it is the lower of feed and TWAP. The order ticket starts the tolerance at 1.00% and lets you move it, and the protocol enforces a hard ceiling of 2.00% on every caller, protocol flows included. All budgets are listed on the Parameters page.
What a trade costs
The desk charges a fee on every trade you make: 0.20% of the USDG notional, on a buy, a sell and a swap, once each. It is taken inside the settlement, because during a buy your USDG never passes through your wallet: MarginAccounts pays the Router out of the collateral it holds for you. On a buy the fee comes off the notional before the venue is paid, so you receive that much less of the asset and your debit carries the whole notional; on a sell it comes off the proceeds before they pay your debit down; on a swap it is charged once, on the sale leg. The order ticket shows the fee as a line of its own before you confirm, and the buying power figure on every screen is already net of it, so a buy of your whole buying power lands at your initial margin, up to a few millionths of rounding on an odd book, which can refuse the exact figure; a cent under it always settles. A forced sale and the daily charge carry no fee. The fee is protocol revenue: it lands in the vault's protocol balance beside the interest skim and sweeps with it to the foundation treasury. The rate moves only between 0 and 50 bps, a ceiling written into the contract.
The venue: every Uniswap pool through a route, the pinned pool as the fallback
An order runs a route. When you quote, the desk asks the Uniswap Trading API for the best route across every Uniswap pool on the chain (v2, v3 and v4, hooked or not, split across several when that fills better) for exactly your order and tolerance, and sends it with the order. The desk executes the route itself against the Universal Router, under rules that make the route's content irrelevant to custody: exactly the order's input is allowed for that one call and the allowance expires in the same block, the input must be wholly consumed, and the fill is what the desk itself received, measured against its own floor at the mark less your tolerance. A route that delivers less than that floor, or fails for any reason, is refused, and the order fills on the asset's pinned pool instead, inside the same tolerance, in the same transaction; the confirmation says which happened. A buy's route is sized at the notional less the desk fee, because that is what the Router is sent. The daily charge never routes: its batches are sized on chain, so no route can be fetched for them, and they run the pinned pool.
The pinned pool is the fallback and the daily charge's whole venue. The Router fills through ConcentratedVenueAdapter, which holds one venue per listed asset: the Uniswap v3 pool or hookless v4 pool key that the desk's depth measurement (shared/src/depthSizing.ts) found bears the largest clip at 125 bps of impact with the pool fee included. The pools are the chain's own: nobody rests them at a premium and no keeper re-centres them, so a fill pays that pool's fee tier plus impact, against wherever spot sits relative to the mark, on the buy side and the sell side alike.
What the ticket shows. The preview carries one venue figure and names its basis. When the api has served a route whose expected fill clears the desk's floor, the figure is the route's expected output, labelled Expected, with the pinned pool's own gap to the mark beside it as the fallback the chain runs if the route is refused at the moment of the fill, and the routing line says how many pools the route crosses and whether one of them is hooked. When no route is served (the api names the reason in one of three words: rate limited, no key, or no route) the figure is the pinned pool's, labelled Exact when the api has simulated the swap the pool would deliver now and Estimate while the quote loads or only the pool's at-the-price figure is available. A swap's figures are the ledger arithmetic at the mark: its sale leg may route, its buy leg fills on the pinned pool by construction. Whichever basis is shown, the floor the chain enforces is the same one, the mark less your tolerance, on either path. The demo chain and the testnet are mock deployments and fill through Uniswap v2 pools the desk seeded, with no routed path.
The desk marks your basket at the oracle mark, not the fill price. The venue gap on a buy, the pool fee, the gap between the mark and the pool's spot, and impact, comes out of equity at the moment of the fill: you paid slightly more than the value the risk engine credits you with. The ticket states this before you confirm.
Protocol flows ride the same path
The daily charge's batched, netted sells and the forced sales of the call process execute through the same Router and the same pinned pools as user trades, each under its own slippage limit:
| Flow | Limit | On breach |
|---|---|---|
| User trade | User set, at most 2.00% | Revert |
| Batch sale, treasury tokens (no member listed at launch) | 10 bps | Capitalise the charge and retry at the next daily charge; a fill under the limit halts nothing, and only a venue that cannot fill at all halts the asset for user trades |
| Batch sale, crypto and majors (1 listed at launch) | 30 bps | Capitalise the charge and retry at the next daily charge; a fill under the limit halts nothing, and only a venue that cannot fill at all halts the asset for user trades |
| Batch sale, stock and ETF tokens (25 listed at launch) | 150 bps | Capitalise the charge and retry at the next daily charge; a fill under the limit halts nothing, and only a venue that cannot fill at all halts the asset for user trades |
| Forced sale | 150 bps | Skip the leg for that call and move to the next asset; the next sweep retries it |
Every one of these limits sits below the user ceiling, so the ceiling check never blocks a protocol flow. A batch fill the Router refuses reverts inside the charge, and the whole of that asset's charge capitalises to the next day. The Router tells two refusals apart: a fill that completed under the class limit is the desk's own size against the pool's spread, and it halts nothing; a venue that could not fill at all is reported and raises the automatic halt described below. The stock limit is measured against the pools the deploy wires, because a class limit set under a venue's fee tier would capitalise every asset of that class at every charge. A forced sale takes at most one clip of each asset per call, each clip atomic under the same floor, and moves on to the account's next asset rather than back into a pool the same call has just moved, with the next clip left to the next sweep; a forced sale leg may carry a route the keeper fetched for it, tried first and falling back to the pinned pool exactly as a user order does. See Interest and the daily charge and Calls and forced sales for how those flows are sized.
Halts and the venue seam
The Router carries two halt flags per asset. The guardian's routerHalted is deliberate: while it is set, no buy and no sell of the asset can settle, the daily charge capitalises that asset's share, and forced sales skip it. The automatic venueHalted is raised by the desk itself when the venue cannot fill a batch sale or a forced sale at all, with no decision and no expiry: it refuses user buys and sells of the asset while the desk's own batches and forced sales keep trying, and it clears on the next desk fill that succeeds or when anyone clears it with a quote probe. A fill that completed under the desk's own floor does not raise it: that batch or leg is skipped and retried on its own cadence, because the desk's own price impact is not the venue failing. Two other things close an asset: a listing set to buys blocked or delisted refuses buys, and the Risk Council's clearVenue on the adapter stops every fill in the asset at once. Each applies to one asset at a time, and none is scheduled. A guardian pause does not expire on its own: after 72 hours the recorded unpause becomes executable by anyone.
The venue itself sits behind a single adapter pointer on the Router. Swapping the adapter is a wholesale governance action on the slowest timelock class: deploy a new adapter, point the Router at it, and every flow moves at once. The adapter carries a venue book of its own, one pool or pool key per asset, and the three calls that move it (setV3Venue, setV4Venue, clearVenue) sit on the Risk Council's fast path with no delay, so where a single asset fills can be re-pointed in minutes when a pool starts reverting; the adapter holds no funds between transactions and captures no fee. The routed path has a lever of its own: the guardian can pause it desk-wide (setRoutingPaused), after which every order fills on its pinned pool until the pause is lifted, so a bad day on the Universal Router or the Trading API needs no re-pointing. See Governance for the delay classes.