SIP-303: Markets (V3)
Author | |
---|---|
Status | Implemented |
Type | Governance |
Network | Ethereum & Optimism |
Implementor | Daniel Beal (@dbeal-eth), Leonardo Massazza (@leomassazza), Alejandro Santander (@ajsantander) |
Release | TBD |
Proposal | Loading status... |
Created | 2022-05-03 |
Simple Summary
This SIP proposes the creation of markets in Version 3 of the Synthetix protocol. Markets are expected to accept snxUSD, generate derivatives, rely on liquidity provided by pools to back any debt they have issued, and return snxUSD to the pools backing it as an incentive.
Abstract
Markets are a generic abstraction that allow products (such as spot markets and futures markets) to be built on the protocol. Market contracts interact with the market manager to mint snxUSD, burn snxUSD, and coordinate liquidity from pools. Markets can be designed and deployed by anyone.
Motivation
By creating a generic market interface, we are able to cleanly separate concerns in the codebase and allow for greater composability with the protocol. Though we anticipate starting with implementations of futures and spot market contracts, it should be possible to design new types of markets backed by the protocol as well.
Specification
Overview
Markets interact with the market manager to read the amount of liquidity available to them and report the balance (net debt or credit) they’ve generated. The market manager tracks the share of the balance apportioned to each of the pools that are providing liquidity to a given market.
Rationale
By facilitating all of the logic pertaining to minting and burning snxUSD within the market manager, we’re able to allow the permissionless creation of markets in the protocol. The intention of this design is ensure that only the pools which back a given market are exposed to risk generated from this market, while keeping snxUSD fungible and shielded from this risk.
In the worst case scenario, a malicious actor could generate a market, persuade pools to provide it with liquidity, and then set the balance
value to a large negative number (suggesting large debt inflation). This would subject the pools involved to liquidation, but no other risk should be assumed by the protocol.
Technical Specification
The market manager will implement something similar to the following interface:
interface IMarketManager {
function registerMarket(address market) returns (uint);
function liquidity(uint marketId) returns (uint);
function marketUsdDebt(uint marketId) returns (int);
function marketTotalDebt(uint marketId) returns (int);
function deposit(uint marketId, uint amount);
function withdraw(uint marketId, uint amount, address recipient);
}
Markets can be registered with the market manager using the registerMarket()
function. This validates the presence of a debt()
function in the specified contract and stores the market’s address. This function may also emit an event (for protocol analytics) or include various restrictions around market creation.
A market’s total debt has two components: snxUSD debt and reported debt. The snxUSD debt is increased when the market withdraws snxUSD and decreased when it deposits snxUSD. It may also report additional debt (with a reportedDebt
function) which is typically incurred from price fluctations among the synthetic assets it backs. Each vault is responsible for a share of a market's total debt proportional to the amount of collateral it has delegated. A market cannot withdraw snxUSD if its debt exceeds a maximum calculated from a weighted average of the maximum debt share values among its backing pools.
The only function that a market must implement is reportedDebt()
.
interface IMarket {
function reportedDebt(uint marketId) view returns uint;
}
As an example, a basic synth spot market for sBTC could be implemented as follows:
- An ERC-20 contract would be deployed, with a mint and burn function only callable by the market contract and a
symbol()
function that returnssBTC
. - The sBTC market contract would be deployed with the following functionality:
reportedDebt()
- Returns the total supply of the sBTC token multiplied by the current price of BTC.
buy(uint amount)
- Transfers the specified amount of snxUSD from
msg.sender
to the market manager with thedeposit()
function. - Determines the exchange rate based on a price oracle and applies any fees.
- Mints the appropriate amount of sBTC to
msg.sender
.
- Transfers the specified amount of snxUSD from
sell(uint amount)
- Burns the specified amount of sBTC from
msg.sender
. - Determines the exchange rate based on a price oracle and applies any fees.
- Transfers the appropriate amount of snxUSD from the market manager the
withdraw()
function tomsg.sender
.
- Burns the specified amount of sBTC from
Note that if fees are simply deducted during exchange, they are effectively distributed among vaults pro-rata based on the amount of liquidity they’re providing. This would be similar to stakers having their snxUSD fees instantaneously burned in the current version of the protocol. Stakers could then mint snxUSD to retrieve them.
Test Cases
Relevant tests will be developed during implementation.
Configurable Values (Via SCCP)
- Approved Markets (address[]) - This is a list of market contract addresses owned (or otherwise approved) by the Spartan Council and will be listed in the official UI.
Copyright
Copyright and related rights waived via CC0.