GreeksEngine and HedgeSuggester are the SDK’s read-only analytics surface for a
market maker that has written (or is about to write) the LP’s capped IL claim. The claim
is long-gamma, long-vega convexity — the LP is long it, the MM is short it. Both
classes surface on the SDK as sdk.greeks and sdk.hedge.
The single most important property of this surface, repeated everywhere because it is
load-bearing: every number here is derived from the protocol’s OWN
deployed math — there is no parallel pricing model. Price greeks
finite-difference the deployed ILMath.computeIL; vol greeks
finite-difference the on-chain FairValueOracle.fairRate
Φ-sum. Nothing here reimplements the Φ-sum, and nothing here ever sends a transaction.
This surface carries no LP or depositor claim. It is pure analytics. The hedge it
suggests is the MM’s own residual-risk choice and is not relied upon for pool
solvency — see the caveat and
invariant I1.
How to get the surface
Both classes are wired by the factory onto the SDK; for tests or an alternate deployment you can also construct them directly with an injectedPublicClient and an optional address override.
(client: PublicClient, addrs?: Partial<HedgeAddresses>). The two
addresses default to the on-chain registry — ilMath = core.ilMath (price greeks +
strip) and fairValueOracle = stylus.fairValueOracle (vol greeks) — and are injectable
only for tests. See Addresses & units
and /reference/deployments for the live values.
Address
Deployed
ILMath — computeIL backs delta/gamma and the replication strip. Defaults to
core.ilMath.Address
Stylus
FairValueOracle — fairRate backs vega/theta. Defaults to
stylus.fairValueOracle.GreeksEngine
Three public methods.greeks is the per-position primitive; bookGreeks aggregates over
a book; priceGreeks/volGreeks are the private finite-difference engines (documented
below for the basis). Every method that needs an on-chain read returns a typed degraded
result on failure — nothing throws on a missing read.
Greeks — the output
All four greeks are plain number (the FD boundary converts bigint → float). They are
reported in decimals-independent conventions; read the basis notes before consuming.
GreeksOptions — the finite-difference tunables
number
default:"64"
Interior grid points across
[Pa, Pb] for the strip (the price-greeks FD uses a single
central difference, so this mainly drives the strip resolution). DEFAULT_POINTS = 64.number
default:"0.01"
Relative price bump for the central-difference delta/gamma — the FD steps to
.
DEFAULT_PRICE_BUMP_REL = 0.01 (1%).bigint
default:"1e16"
Absolute σ bump (WAD) for vega.
DEFAULT_SIGMA_BUMP_WAD = 10_000_000_000_000_000n =
0.01 in WAD = 1 vol point.number
default:"0.01"
Relative T bump for theta — the FD steps the duration by
±durationBumpRel, then scales
the result to per-year. DEFAULT_DURATION_BUMP_REL = 0.01.PositionGeometry — the input shape
greeks/bookGreeks consume the same PositionGeometry the MM client produces from
getPositionGeometry. It is decimals-aware: aWad/bWad/maxIL are
WAD/raw bigints, sqrt prices are Q64.96.
The finite-difference / fairRate basis
This is the part you must get exactly right in a technical conversation. The greeks split into two families with two different on-chain sources.Price greeks (delta, gamma) — central-difference ILMath.computeIL
priceGreeks finite-differences the deployed reference settlement
math directly. It evaluates the capped payoff
at three price ratios — — by calling
computeIL(sqrtP_T, sqrtPa, sqrtPb, L, amount0Entry, amount1Entry) and clamping the
result at MaxIL in float. Because computeIL is the same
function settlement uses, delta and gamma are exact with respect to the reference math
— the only approximation is the grid spacing, never the payoff.
With normalised to ratio , the relative bump is the absolute step in ratio
space, so:
where = priceBumpRel. Greeks are reported per unit
price-RATIO — dimensionless, decimals-independent — which is the natural
convention given the geometry is L-scaled but ratio-anchored.
The price step is computed through
sqrtPForRatio(sqrtP0X96, ratioWad):
. The sqrt(ratio) is taken
in float, but it only sets where on the curve computeIL is sampled — computeIL
itself is exact at whatever sqrtP it is fed.Vol greeks (vega, theta) — central-difference FairValueOracle.fairRate
volGreeks finite-differences the on-chain fairRate — the
pure, closed-form Φ-sum — never a reimplemented model. It
builds the fair premium from the rate:
calling fairRate(aWad, bWad, σ, T) for each bumped argument. The
cap is harmless in-range because holds there.
Vega — central difference in σ, reported per 1.0 vol:
The down-bump is floored at zero when sigmaRefWad < sigmaBump.
Theta — central difference in T (in seconds), then scaled to per year:
with SECONDS_PER_YEAR = 365·24·60·60. The sign convention is
— positive means value rises with more time, as a
long-gamma claim does. The duration step is at least 1 second.
Degradation
greeks wraps both FD families in a try/catch and returns
{ priceable: false, reason: 'oracle-degraded', detail } if any on-chain read fails — it
never throws. bookGreeks calls greeks per position and skips
any degraded one, counting it in skipped, so one bad position cannot poison a book sum.
See the degradation contract and
Priceable<T> in /sdk-reference/types.
Worked example — per-position and book greeks
HedgeSuggester
Turns the greeks into a concrete, approximate three-leg static hedge. Two suggest methods (a convenience form and aPriceable-envelope form) plus the empty-inverse
helper, and the free-function executeOnPanoptic.
HedgeInput is a single position or an array (a book) —
{ position, durationSeconds, sigmaRefWad } or a readonly array of them.
SuggestHedgeOptions (extends GreeksOptions)
'panoptic' | 'gammaswap'
default:"'panoptic'"
On-chain inverse venue to suggest for leg 2.
'perp' | 'spot'
default:"'perp'"
Residual delta-overlay instrument for leg 3.
number
default:"8"
Number of strikes in the replication strip — floored at 3.
points, priceBumpRel, sigmaBumpWad, durationBumpRel.
HedgeSuggestion — the output
- HedgeLeg (strip)
- OnChainInverse (leg 2)
- DeltaOverlay (leg 3)
The three legs (the “why”)
The MM is short the LP’s in-range convexity, so the hedge is a long-gamma stack that offsets it:1
Vanilla long-gamma replication strip (Carr-Madan / Breeden-Litzenberger)
The convex capped payoff is replicated by a strike
ladder. Breeden-Litzenberger says the option density at strike is the second
derivative ; the suggester discretises over a shared price-ratio grid in
(summing each position’s
computeIL), then reads off the
second differences as per-strike notionals: .
Below the down-move wing → puts; above → calls.
Flat/capped/OTM regions () are skipped.
Lipton-Lucic-Sepp static replication is the theory anchor only; see theory anchors.2
On-chain inverse long-gamma range
A long-gamma range over the book-aggregate — e.g. a Panoptic long strangle or
a GammaSwap borrowed-LP position — with
sizeL = Σ liquidity as a size proxy the MM
right-sizes against funding.3
Residual delta overlay
After legs 1 + 2, the residual book delta is flattened with a perp/spot. The MM book delta
is (it is short the claim), so the overlay trades of the underlying:
side = sign(delta), size = |delta|.suggestHedge vs suggestHedgeChecked
Both never throw. The difference is how degradation surfaces:
suggestHedgealways returns aHedgeSuggestion. On a degraded read it returns a structurally-valid but empty hedge — emptystrip, zero-size inverse, zero overlay — with the caveat still attached, so a caller never crashes. An emptyinputarray yields the same empty-but-valid suggestion.suggestHedgeCheckedreturnsPriceable<{ suggestion }>so you can branch:{ priceable:false, reason:'oracle-degraded', detail }on a failed read.
executeOnPanoptic — analytics only, never a tx
A free function (not a method) that produces a read-only PanopticPlan from a
suggestion. Its executed field is always false by design — the SDK does not execute
on-chain hedges; it only describes the inverse long-gamma range the MM may choose to open.
PanopticPlan: { executed: false, venue: 'panoptic', direction: 'long-gamma', rangeLow, rangeHigh, sizeL, caveat, note }.
Worked example — suggest a hedge for a book
The HEDGE_CAVEAT — why the hedge is NOT load-bearing
The caveat is attached verbatim to every suggestion and is exported as a constant so
the UI reproduces it word-for-word. It is the single most
important framing on this page.
A perpetual-option / on-chain inverse hedge is APPROXIMATE relative to the fixed-maturity IL claim (mismatched expiry, funding, discretisation). It is the MM’s own residual-risk choice and is NOT relied upon for pool solvency — invariant I1 (no bad debt, FULL) is structural and oracle-independent, fully collateralised at MaxIL regardless of whether the MM hedges.This is distinct from the LP and depositor claims, which live on other surfaces and are never merged with the hedge disclaimer: The MM keeps its own hedge book; the protocol’s no-bad-debt guarantee stands on full collateralisation at MaxIL, not on the MM’s hedge.
See also
MM client
Geometry, pricing, the pool-load-to-beat, quoting and fills — the surface that feeds
PositionGeometry into the greeks.The Φ-sum
The on-chain
fairRate closed form that vega/theta finite-difference.The IL formula
The
computeIL reference math that delta/gamma and the strip finite-difference.Invariant I1
Why no-bad-debt is structural and independent of whether the MM hedges.