> For the complete documentation index, see [llms.txt](https://docs.nexus.xyz/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.nexus.xyz/math-engine/oracle.md).

# Oracle

Every perpetual market on the Exchange marks positions against a price that must be resistant to both fat-finger errors and deliberate manipulation. The oracle validator accepts a new print only if it stays within a per-step deviation bound of the current anchor $$P\_{oracle}$$ and, once ten prints have accumulated, within a wider path bound of the oldest print in the window. When the anchor is stale, a large move is never trusted on a single print: it must be confirmed by $$k$$ consecutive mutually-consistent prints, with a per-step bound that widens only after an escalation trigger fires.

The mark price $$P\_{mark}$$ that drives margin and liquidation is not the raw oracle price: it blends the trusted oracle anchor with a robust trade reference — the volume-weighted median of the last five trades — so that neither a single anomalous oracle tick nor a lone wash trade can move the mark across a liquidation threshold.

![Every print must clear both deviation bounds (a conjunctive fan-in on the anchor), while staleness opens a widening re-anchor loop whose confirmation threshold relaxes under escalation.](/files/6MYF6gqEszokSeBqgtBj)

*Every print must clear both deviation bounds (a conjunctive fan-in on the anchor), while staleness opens a widening re-anchor loop whose confirmation threshold relaxes under escalation.*

## Setting

| Symbol          | Name                       | Description                                                                                                                                                                                                                                                                                     | Units                  | Domain    |
| --------------- | -------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------------- | --------- |
| $$P\_{oracle}$$ | oracle\_price              | The current trusted oracle anchor price for the market. Strictly positive whenever the market has bootstrapped; a zero value denotes a brand-new market with no prior print.                                                                                                                    | USDX per unit of asset | (0, ∞)    |
| $$P\_{new}$$    | new\_price                 | The incoming oracle print being validated.                                                                                                                                                                                                                                                      | USDX per unit of asset | (0, ∞)    |
| $$P\_{old}$$    | oldest\_price              | The oldest accepted print in the rolling ten-entry update history, used by the path-manipulation check.                                                                                                                                                                                         | USDX per unit of asset | (0, ∞)    |
| $$\theta$$      | deviation\_threshold       | Per-market single-step deviation threshold (oracle\_deviation\_threshold); a print deviating from the anchor by strictly more than this is rejected.                                                                                                                                            | dimensionless fraction | (0, 1]    |
| $$N\_h$$        | history\_size              | Fixed size of the rolling price-update window used for path-manipulation detection (HISTORY\_SIZE = 10). The path check is armed only when the window is full.                                                                                                                                  | prints                 | \[10, 10] |
| $$P\_{trade}$$  | trade\_ref                 | Robust trade reference for the mark blend: the volume-weighted median price of the last five recorded trades, falling back to the last trade price when the window is empty. Weighting by traded size means moving the reference requires washing a majority of traded volume, not trade count. | USDX per unit of asset | (0, ∞)    |
| $$w$$           | oracle\_weight             | Per-market oracle weight in the mark blend (MarketParams.oracle\_mark\_weight), a unit-interval value defaulting to 0.95 (oracle-dominant).                                                                                                                                                     | dimensionless fraction | \[0, 1]   |
| $$P\_{mark}$$   | mark\_price                | The Exchange's mark price for the market: the oracle-weighted blend of the trusted anchor and the trade reference. Equals the oracle price when no trade has ever been recorded.                                                                                                                | USDX per unit of asset | (0, ∞)    |
| $$t\_{now}$$    | current\_time              | Timestamp of the incoming print or the staleness evaluation, in Unix milliseconds.                                                                                                                                                                                                              | milliseconds           | \[0, ∞)   |
| $$t\_{last}$$   | last\_update\_time         | Timestamp of the last trusted oracle update, in Unix milliseconds. Not advanced by pending (un-trusted) re-anchor prints.                                                                                                                                                                       | milliseconds           | \[0, ∞)   |
| $$\tau\_s$$     | staleness\_seconds         | Per-market staleness threshold (oracle\_staleness\_seconds); the anchor is stale when strictly more than this many seconds have elapsed since the last trusted update.                                                                                                                          | seconds                | (0, ∞)    |
| $$P\_{cand}$$   | candidate\_price           | The provisional re-anchor candidate: the running price level being confirmed while the anchor is stale. Not trusted and never used as the mark while pending.                                                                                                                                   | USDX per unit of asset | (0, ∞)    |
| $$\theta\_r$$   | reanchor\_max\_deviation   | Per-step consistency bound for re-anchor confirmations (oracle\_reanchor\_max\_deviation): a confirming print must land within this fraction of the running candidate or the confirmation counter restarts.                                                                                     | dimensionless fraction | (0, 1]    |
| $$\theta\_e$$   | escalation\_max\_deviation | Widened per-step bound (oracle\_reanchor\_escalation\_max\_deviation) applied once the escalation trigger has fired, letting a sustained-but-volatile legitimate correction accumulate confirmations. Finite: a step beyond it still restarts the counter.                                      | dimensionless fraction | (0, 1]    |
| $$k$$           | required\_confirmations    | Number of consecutive mutually-consistent prints required to trust a large move off a stale anchor (oracle\_reanchor\_confirmations). Floored at 2 in code so a misconfigured value of 1 cannot re-open the single-print bypass.                                                                | prints                 | \[2, ∞)   |
| $$n\_p$$        | pending\_prints            | Total prints observed during the current pending re-anchor sequence. Unlike the confirmation counter it never resets on an inconsistent step; it measures how long the market has been wedged.                                                                                                  | prints                 | \[0, ∞)   |
| $$N\_e$$        | escalation\_prints         | Print-count arm of the escalation trigger (oracle\_reanchor\_escalation\_prints).                                                                                                                                                                                                               | prints                 | \[1, ∞)   |
| $$t\_0$$        | pending\_since             | Timestamp (Unix milliseconds) of the print that opened the current pending re-anchor sequence; zero when not pending.                                                                                                                                                                           | milliseconds           | \[0, ∞)   |
| $$\tau\_e$$     | escalation\_seconds        | Wall-clock arm of the escalation trigger (oracle\_reanchor\_escalation\_seconds), measured against the feed-supplied update time.                                                                                                                                                               | seconds                | (0, ∞)    |

## The mechanism

### Deviation Guards

When the stored anchor is usable — positive and not stale — every incoming print is first measured against it as a relative deviation. The print is rejected when this deviation strictly exceeds the per-market threshold $$\theta$$ (the comparison is strict, so a move of exactly $$\theta$$ is accepted). This is the workhorse guard: a fat-finger print or a single-tick spike from the price producer is rejected here and never moves the anchor.

$$
\Delta\_{step} = \frac{\lvert P\_{new} - P\_{oracle} \rvert}{P\_{oracle}}, \qquad \text{accept only if } \Delta\_{step} \le \theta \tag{O.1}
$$

A manipulator who keeps each step under $$\theta$$ could still walk the price far over many prints. Once the rolling update history holds $$N\_h = 10$$ accepted prints, the validator also measures the incoming print against the oldest print in the window. This cumulative move is compared against the path threshold (O.3): a random walk over $$N$$ steps has expected deviation proportional to $$\sqrt{N}$$, while a directed walk grows proportionally to $$N$$, so scaling the threshold by $$\sqrt{N\_h}$$ separates the two regimes. The check is inactive while the window is refilling — after a re-anchor or on a brand-new market — a documented, accepted residual exposure.

$$
\Delta\_{path} = \frac{\lvert P\_{new} - P\_{old} \rvert}{P\_{old}} \tag{O.2}
$$

The path bound applied to (O.2) is the single-step threshold scaled by $$\sqrt{N\_h}$$. With the default $$\theta = 0.10$$ and $$N\_h = 10$$, the bound is $$0.10 \times \sqrt{10} \approx 0.3162$$: a cumulative move of more than about $$31.6%$$ across the window is rejected even though every individual step passed the single-step guard. The implementation uses the fixed decimal constant $$\sqrt{10} = 3.16227766016838$$.

$$
\theta\_{path} = \theta \cdot \sqrt{N\_h} \tag{O.3}
$$

### Staleness and Re-anchoring

The anchor is stale when strictly more than $$\tau\_s$$ seconds have elapsed since the last trusted update. Timestamps are Unix milliseconds, so the threshold is converted by multiplying by 1000 (with saturating integer arithmetic in the implementation). A stale anchor may hold an arbitrarily wrong value, so the deviation guards (O.1) and (O.2) cannot be trusted against it — staleness routes the print into the re-anchor path instead.

$$
\mathrm{stale} = \mathbb{1}\left\[, t\_{now} - t\_{last} > 1000,\tau\_s ,\right] \tag{O.4}
$$

A large move off a stale anchor — one whose deviation from the last-known-good price exceeds $$\theta$$ — is never trusted on a single print. It only seeds a candidate $$P\_{cand}$$; the mark does not move and the market stays fail-closed. Each subsequent print is measured against the running candidate: if the step stays within the active per-step bound (base $$\theta\_r$$, or the widened $$\theta\_e$$ once (O.6) fires) the confirmation counter advances; a larger step makes the print the fresh candidate with the counter restarted at 1. Only after $$k$$ consecutive consistent prints (with $$k$$ floored at 2) is the level trusted, the anchor moved, and the bookkeeping cleared. A benign recovery — a post-staleness print within $$\theta$$ of the old anchor — skips confirmation entirely and is trusted immediately.

$$
\Delta\_{cand} = \frac{\lvert P\_{new} - P\_{cand} \rvert}{P\_{cand}}, \qquad \text{confirm if } \Delta\_{cand} \le \theta\_{r}\ (\text{or } \theta\_{e} \text{ when escalated}) \tag{O.5}
$$

A legitimate correction whose true price moves more than $$\theta\_r$$ per print would reset the confirmation counter on every step and wedge the market fail-closed forever. The escalation trigger fires once the pending sequence has accumulated $$N\_e$$ prints or once $$\tau\_e$$ seconds have elapsed since it opened, whichever crosses first — the print counter $$n\_p$$ never resets on an inconsistent step, so it measures how long the market has been wedged. When active, the per-step bound in (O.5) widens from $$\theta\_r$$ to $$\theta\_e$$; no single print is ever trusted, and the widened bound remains finite.

$$
\mathrm{escalated} = \mathbb{1}\left\[, n\_p \ge N\_e ;\lor; t\_{now} - t\_0 \ge 1000,\tau\_e ,\right] \tag{O.6}
$$

### Mark Price

The mark price used for margin and liquidation blends the trusted oracle anchor with a robust trade reference. Because $$w \in \[0,1]$$, the mark always lies between the oracle price and the trade reference — an anomalous-but-accepted oracle tick is damped by trades, and vice versa. The trade reference $$P\_{trade}$$ is the volume-weighted median of the last five recorded trades: sorting the window by price and walking cumulative traded size, the reference is the first price at which cumulative size strictly exceeds half the total (when a sample's cumulative size lands exactly on half, the straddling price and the next positive-size price are averaged). Moving this reference therefore requires washing a majority of traded volume, not merely a majority of trade count. When the window is empty the reference falls back to the last trade price, and when no trade has ever been recorded the mark is simply the oracle price. A confirmed re-anchor over a large jump clears the trade window so pre-gap trades cannot pull the fresh mark back toward the stale level.

$$
P\_{mark} = w \cdot P\_{oracle} + (1 - w) \cdot P\_{trade} \tag{O.7}
$$

## Invariants

* The trusted anchor is strictly positive after bootstrap: $$P\_{oracle} > 0$$, and validation divides only by positive prices.
* On the fresh-anchor path, every accepted print satisfies $$\Delta\_{step} \le \theta$$ ((O.1)); the comparison is strict, so a move of exactly $$\theta$$ is accepted.
* When the ten-print history is full, every accepted print also satisfies $$\Delta\_{path} \le \theta \sqrt{10}$$ ((O.2), (O.3)).
* Because $$w \in \[0,1]$$, the mark is always bounded: $$\min(P\_{oracle}, P\_{trade}) \le P\_{mark} \le \max(P\_{oracle}, P\_{trade})$$ ((O.7)).
* A pending re-anchor never moves the anchor or advances the trusted timestamp: $$P\_{oracle}$$ and $$t\_{last}$$ are unchanged until $$k$$ consecutive consistent confirmations accumulate ((O.5)).
* The required confirmation count is floored at 2 in code, so a single print can never promote a large move off a stale anchor.
* A single trade with a minority of the window's traded volume cannot move the volume-weighted median trade reference, and hence cannot move the mark by more than the blend permits.
* Escalation widens the per-step bound to $$\theta\_e$$ but never removes it: a step beyond $$\theta\_e$$ still restarts the confirmation counter ((O.6)).

## Worked example

Consider a market with anchor $$P\_{oracle} = 100{,}000$$ USDX, deviation threshold $$\theta = 0.10$$, staleness window $$\tau\_s = 30$$ s, and oracle weight $$w = 0.95$$. A print of $$P\_{new} = 105{,}000$$ arrives one second after the last update. The anchor is fresh, so (O.1) gives $$\Delta\_{step} = |105{,}000 - 100{,}000| / 100{,}000 = 0.05 \le 0.10$$: the print is trusted and becomes the new anchor. Had the print been $$115{,}000$$, the deviation of $$0.15$$ would strictly exceed $$\theta$$ and the print would be rejected outright. Even a sequence of near-threshold steps is bounded: once ten prints fill the history, (O.2) is checked against (O.3) $$= 0.10 \times \sqrt{10} \approx 0.3162$$, so a compounding $$9%$$-per-print walk is cut off at the eleventh print.

Now suppose four trades of size 1 execute at $$99{,}000$$, $$100{,}000$$, $$101{,}000$$, and $$102{,}000$$. The equal-size volume-weighted median lands exactly on half the total volume between the two central prices, so the trade reference averages them: $$P\_{trade} = 100{,}500$$. By (O.7), $$P\_{mark} = 0.95 \times 100{,}000 + 0.05 \times 100{,}500 = 100{,}025$$ USDX. A lone wash trade at $$50{,}000$$ appended to a window of genuine $$100{,}000$$ trades leaves the median — and therefore the mark — unmoved, whereas the old single-last-trade blend would have dropped the mark to $$97{,}500$$.

Finally, suppose the feed goes silent for two minutes, so (O.4) fires ($$120{,}000 - 0 > 30 \times 1000$$), and the next print is $$42{,}000$$ against a stale anchor of $$160.165$$. The move is far beyond $$\theta$$, so it only seeds a candidate: the anchor and mark stay at the old level and the market remains fail-closed. Each subsequent print within $$\theta\_r = 0.10$$ of the running candidate ((O.5)) advances the confirmation counter; after $$k = 3$$ consecutive consistent prints the level is trusted, the anchor moves, and the stale pre-gap trade window is cleared so the fresh mark is the pure re-anchored oracle price.

## Analysis

### Sensitivity

Elasticities ε = (∂y/∂x)·(x/y), computed numerically from the verified expressions at each worked-example point. |ε| > 1 means the output moves more than proportionally with that input.

| Expression                | Input                | Elasticity ε |
| ------------------------- | -------------------- | ------------ |
| `single_step_deviation`   | new\_price           | 21           |
| `single_step_deviation`   | oracle\_price        | -21          |
| `path_deviation`          | new\_price           | 4.165        |
| `path_deviation`          | oldest\_price        | -4.165       |
| `path_threshold`          | deviation\_threshold | 1            |
| `is_stale`                | current\_time        | 0            |
| `is_stale`                | last\_update\_time   | 0            |
| `is_stale`                | staleness\_seconds   | 0            |
| `reanchor_step_deviation` | new\_price           | 1.111        |
| `reanchor_step_deviation` | candidate\_price     | -1.111       |
| `escalation_trigger`      | pending\_prints      | 5e+05        |
| `escalation_trigger`      | escalation\_prints   | -5e+05       |
| `escalation_trigger`      | current\_time        | 0            |
| `escalation_trigger`      | pending\_since       | 0            |
| `escalation_trigger`      | escalation\_seconds  | 0            |
| `mark_price`              | oracle\_price        | 0.9505       |
| `mark_price`              | trade\_ref           | 0.04952      |
| `mark_price`              | oracle\_weight       | 0.009505     |

![Sensitivity tornado — Single-step deviation](/files/xmZ0ew7yxv3TNmlSLImB)

![Sensitivity tornado — Mark price blend](/files/mTcGvoIiy4gM7IwADEtx)

### Response curves

![Relative deviation of an incoming print from a fixed 100,000 anchor; prints outside the ±10% band are rejected by the single-step guard.](/files/kZdFuKQS8BUOZCoT6Azf)

*Relative deviation of an incoming print from a fixed 100,000 anchor; prints outside the ±10% band are rejected by the single-step guard.*

![The mark blend as the trade reference varies, with the oracle anchor held at 100,000; higher oracle weights flatten the mark's sensitivity to trades.](/files/cjWCbRbEIsZ9dvzfP0JV)

*The mark blend as the trade reference varies, with the oracle anchor held at 100,000; higher oracle weights flatten the mark's sensitivity to trades.*

![The cumulative path bound is the single-step threshold scaled by √10 ≈ 3.162, holding the ten-print window size fixed.](/files/0097XQhRU1Wrhz0kHqWy)

*The cumulative path bound is the single-step threshold scaled by √10 ≈ 3.162, holding the ten-print window size fixed.*

### Parameter space

Joint parameter effects evaluated from the verified expressions over 2-D grids.

![The fresh/stale boundary is the line elapsed\_ms = 1000 × threshold, showing directly how tightening the staleness parameter shrinks the fresh region; last update time held at 0.](/files/0gWFhHLr6RHSJEk4KtQC)

*The fresh/stale boundary is the line elapsed\_ms = 1000 × threshold, showing directly how tightening the staleness parameter shrinks the fresh region; last update time held at 0.*

![Level sets fan out from the anchor point where trade\_ref equals the oracle price, showing that manipulation of the trade reference moves the mark by only (1 − weight) of the displacement; oracle price held at 100,000.](/files/YFHgNSsgri7x9p9hL8Rg)

*Level sets fan out from the anchor point where trade\_ref equals the oracle price, showing that manipulation of the trade reference moves the mark by only (1 − weight) of the displacement; oracle price held at 100,000.*

## References

* Derived from and adversarially verified against the Exchange's Rust implementation and its test suite.
* Sibling model: [funding-rate](/math-engine/funding-rate.md)
* Sibling model: [insurance-fund](/math-engine/insurance-fund.md)
* Sibling model: [liquidation-engine](/math-engine/liquidation-engine.md)
* Sibling model: [margin-math](/math-engine/margin-math.md)
* Sibling model: [order-book](/math-engine/order-book.md)
* Sibling model: [position-tracker](/math-engine/position-tracker.md)
* Sibling model: [settlement](/math-engine/settlement.md)


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.nexus.xyz/math-engine/oracle.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
