Comment on page
The below file contains a detailed log of the ABI changes that took place when upgrading from V1 to V2 https://docs.google.com/spreadsheets/d/1ptFFkhtyYYs7KMueqUbQ3AJ8gRT8smFqumDvmRxzkPE/edit?usp=sharing
One of the most fundamental changes in V2 compared to V1 is the introduction of a new smart contract architecture - Diamond Proxy. This structure changes the way communication is done between smart contracts, both internally and externally. In V1, each component was a somewhat independent agent with its interface and administration.
V2 introduces a router: a contract that acts as an abstraction layer between IPOR smart contracts and 3rd party, either a front-end application or another smart contract.
Each external method within the IPOR protocol must be called on the router to be delegated via a delegateCall to the corresponding smart contract. This helps remove complexity from the interface, save gas, and enable functionalities such as gas-efficient batching. The state that the router keeps is limited to the administration:
V2, thanks to overhauled architecture, requires approval only on the router level. Whereas before, each proxy contract required its approval, now only one approval suffices.
- Method to chain the functions of the IPOR protocol.
V2 introduces a way to execute many functions on behalf of another address. The following methods can be executed with
- Opening swap: ex.
openSwapPayFixed28daysUsdt. The beneficiary will be an owner of the swap
- Closing swap: ex.
closeSwapUsdc. The beneficiary will receive the liquidation deposit.
- Provide liquidity: ex.
provideLiquidityUsdt. Liquidity will be deposited with the beneficiary as an owner.
- Staking ipTokens: ex:
stakeLpTokensToLiquidityMining. Each user can stake their own tokens to an account of the beneficiary. The beneficiary becomes the owner of staked tokens.
- Stake IPOR token:
stakeGovernanceTokenToPowerToken.The beneficiary will become the owner of pwIPOR staked.
- Delegating pwIPOR to a pool can only be done on behalf of another user when combined with staking in one method:
Services are the contracts that change the state.
In the chart depicting the V2 overview, the above lenses are marked in green serve. They are similar to views in MVC.
AMM contract, formerly known as "Milton," has been divided into more manageable parts:
- Treasury (state; pause, unpause, admin) that holds balances of ERC20
- services with business logic
V2 introduces multiple tenors of swaps that can be opened. Each tenor has its own individual function to open, i.e.:
Tenor is the maximum time for which the derivative can stay open.
V2 changes the logic for closing swaps. Instead of allowing exit at any moment, V2 requires the user to open a swap on the opposite leg for a matching duration. That action is completed via the internal logic of the smart contract.
Unless the swap is within 6 hours of maturity or its PLN is close to +/- 100%, the user can unwind. Otherwise, the swap can be closed as in V1.
Unwinding PNL is calculated until the swap's maturity and immediately settled.
V1 had a functionality to charge fees on profits of closed swaps. This has been removed in V2.
V2 Introduces a function to claim from all the pools simultaneously. Thanks to the router-based architecture of diamond proxy, the claiming can be easily combined with re-delegation
A new addition to the IPOR smart contracts is the risk oracle. It's dedicated to keeping track of parameters necessary to offer a fair rate when opening swaps. Service monitoring activity on the blockchain has a right to print to this oracle.
- maxNotionalPayFixed - the maximum amount of notional that AMM should be willing to underwrite on the pay-fixed leg. This param is stored per asset. Used in calculating maximum leverage
- maxNotionalReceiveFixed - the maximum amount of notional that AMM should be willing to underwrite on the receive-fixed leg. This param is stored per asset. Used in calculating maximum leverage
- maxCollateralRatioPayFixed - the maximum ratio between collateral put against pay-fixed swaps and the liquidity pool depth
- maxCollateralRatioReceiveFixed - the maximum ratio between collateral put against receive-fixed swaps and the liquidity pool depth
- maxCollateralRatio - max collateral on both legs combined
- demandSpreadFactor - parameter used to regulate the level of risk when calculating demand spread
The following changes have been made to the IPOR oracle along with the V2 release of the IPOR protocol.
- 1.Removed EMA
- 2.Removed EMVar
- 3.Removed auto-update
- 4.Introduction of continuously compounded interest
V2 introduces a new method to calculate the spread using multiple components:
- 1.Base spread - the component of the spread that is calculated using risk analysis
- 2.Demand spread AMM will price the notional as it moves away from the balance (a situation in which PayFixed and RexeiveFixed takers are in equilibrium across multiple tenors).
Spread-related contracts share the same diamond proxy architecture as the rest of the protocol.
One notable change in V2 is that the spread contract keeps the state related to the notional underwritten across multiple tenors.
The frontend data provider was the middle layer contract, making it easier for the frontend to query main contracts. Since V2 is more straightforward to query data, no additional smart contracts are unnecessary.
Pausing contracts, as a last line of defense, was reworked in V2. Instead of pausing separate contracts, V2 introduces "method pausing" via the router. In the new approach, Each pausable method can be paused individually or together with other methods by passing its signature to the pause function.
Guardian address can execute the pause function without the need for the timelock, effectively restricting a pre-defined collection of functions.
Unpausing requires the function to be called by the timelock controller.
Pausing contracts with the list of method signatures
V2 uses ABDKMathQuad in the following places:
- Calculating continuously compounding interest rate
- user power-up in liquidity mining (logarithmic function)
Errors in V2 are revised. For the latest version
of error codes, refer to the github repositories: