Handbook for Vaults
The current vault implementation is designed to gather pre-staking collateral and allocate points to users for depositing up to a certain amount (specified as the ”limit”), independently defined for each type of asset.
The new implementation will introduce the entire core system, which includes (re)staking vaults, various opt-in services (that allow networks and operators get onboarded), and will be able to begin receiving delegations from stakers.
Once vaults are live on mainnet, anyone will be able to create vaults, onboard networks and operators, and start delegations. The Symbiotic points system will be adjusted, and most of the points emission will be redirected to vaults, with rates depending on delegation size to networks (Details TBA).
We are launching a devnet and will provide examples for builders in the form of a sandbox environment to test their network implementations.
Integration flow
Integrating vaults will require particular actions:
- Create vault(s) and configure as described in the section titled ”Vault configuration”
- Onboard operators and networks as described in the sections titled ”Network Onboarding” and “Operator Onboarding”
- Allocate stake limits to onboarded operators and networks
- Deposit stake from:
- Pre-staking collateral:
- Withdraw collateral
- Deposit to vault
- Incoming stake
- Pre-staking collateral:
Points will only be allocated to stake which is delegated to networks.
Networks can cap the stake coming from particular vaults, so it’s possible to encounter a situation when a LRT/user has more stake in pre-staking collateral than can they delegate to networks. To account for this situation, Symbiotic will continue to allocate points for pre-staked collateral deposits using the current rules and formula.
Vault configuration
Each vault can be configured with different parameters, slashing, and delegation models. The desired configuration should be chosen during deployment and, in general, cannot be changed after.
Configurator contract: link
Simple deployment script: link
Vault parameters
owner
- The address of the vault owner. The vault owner can perform migrations to new versions of the vault in the future (can also be set to the zero address to disable migration functionality).collateral
- The address of the ERC20-compatible token used as the staking asset.burner
- The address responsible for burning slashedcollateral
. In case of derivative assets, it should be the contract that performs the redeeming and burning of the underlying asset.epochDuration
- The vault’s epoch duration in seconds. This parameter defines the unstaking delay.depositWhitelist
- The boolean flag that toggles a whitelist for deposits. Iftrue
, the vault will accept deposits only from whitelisted addresses, otherwise deposits are not whitelisted.isDepositLimit
- The boolean flag that toggles a limit for deposits. Iftrue
, the vault will accept deposits only up to that limit, otherwise deposits are not capped.depositLimit
- The maximum amount ofcollateral
that can be used as an active stake simultaneously. This parameter caps the deposits.defaultAdminRoleHolder
- The address of the default admin role. The default admin can set dedicated admins for whitelist related actions (see below).depositWhitelistSetRoleHolder
- The address of the global whitelist flag enabler admin (can be set to zero address to disable whitelist functionality).depositorWhitelistRoleHolder
- The address of the depositor whitelister (can be set to zero address and be granted bydefaultAdminRoleHolder
later, e.g., as a DAO would decide).isDepositLimitSetRoleHolder
- The address of the deposit limit flag enabler admin (can also be set to zero address to disable deposit limit functionality).depositLimitSetRoleHolder
- The address of the deposit limit setter (can be set to zero address and be granted bydefaultAdminRoleHolder
later, e.g., as a DAO would decide).
depositWhitelistSetRoleHolder
and depositorWhitelistRoleHolder
are responsible for whitelist functionality. To disable a whitelist, you can set all addresses (including defaultAdminRoleHolder
) to zero and depositWhitelist
to false
.
isDepositLimitSetRoleHolder
and depositLimitSetRoleHolder
are responsible for deposit limit functionality. To disable a limit, you can set all addresses (including defaultAdminRoleHolder
) to zero, isDepositLimit
to false
, and depositLimit
to zero.
Delegator module
There are two delegation models implemented in the current version:
FullRestakeDelegator
- The delegation model that allows restaking across networks and operators in the same network at the same time.NetworkRestakeDelegator
- The delegation model that allows restaking across networks, but doesn’t allow restaking across operators in the same network.
More details regarding Symbiotic’s delegation models are available here.
When delegation model is set during deployment it cannot be changed later
Delegator common parameters
defaultAdminRoleHolder
- The address of default admin role. The default admin can set dedicated admins for particular actions (can also be set to the zero address if the delegation role holders are set).hook
- The address of the callback contract which can, e.g., adjust delegations on slashings (can be set to zero address to disable automatic callbacks).hookSetRoleHolder
- The address of the hook setter admin (can be set to zero and be granted later if needed).
FullRestakeDelegator
specific parameters
networkLimitSetRoleHolders
- An array of addresses of the network limits setters (no one can be set, and be granted later ifdefaultAdminRoleHolder
is not zero address).operatorNetworkLimitSetRoleHolders
- An array of addresses of the operator-network limits setters (no one can be set, and be granted later ifdefaultAdminRoleHolder
is not zero address).
NetworkRestakeDelegator
specific parameters
networkLimitSetRoleHolders
- An array of addresses of the network limit setters (can be set as empty, and be granted later ifdefaultAdminRoleHolder
is not the zero address).operatorNetworkSharesSetRoleHolders
- An array of addresses of the operator shares setters (can be set as empty, and be granted later ifdefaultAdminRoleHolder
is not the zero address).
Slasher module
There are three available slashing models supported in the current version:
- No slashing - The slasher address is set to zero, in this case, the vault cannot be slashed at all.
Slasher
- A simple slashing module that allows networks to instantly slash funds in FIFO order.VetoSlasher
- A slashing module that supports veto though resolvers, and each slashing request from networks can be vetoed by a resolver.
When a slashing model is set during deployment, it cannot be changed later!
Slasher common parameters
isBurnerHook
- The boolean flag that determines if theburner
address needs to be called on each slashing event, e.g., to redirect the slashedcollateral
tokens to different addresses.
Slasher
specific parameters
- No slasher-specific parameters - The simple slasher executes slashing requests instantly.
VetoSlasher
specific parameters
vetoDuration
- The slasher’s veto duration in seconds, this parameter defines a period after a slashing request creation for resolvers to veto the request (and can be set to zero to remove veto functionality).resolverSetEpochsDelay
- The resolvers’ delay in epochs, this parameter defines a period that needs to pass after a network updates a resolver for the resolver to be enabled for the network (can be set equal to a minimum of 3 epochs for users to be able to withdraw funds before the update).
Network Onboarding
In Symbiotic, each network can be connected to any number of vaults. Each vault can provide varying amounts of stake to a network under different conditions. E.g. a network can have 3 vaults:
- Vault_1 with
Token_A
fromLRT_1
- Vault_2 with
Token_B
fromLRT_2
- Vault_3 with
Token_A
fromLRT_3
Network onboarding requires several actions:
- The network should be registered in Symbiotic
NetworkRegistry
, see details here - Network should opt into the vault using
Delegator.setMaxNetworkLimit(identifier, MAX_STAKE)
, where:identifier
- an identifier of the sub-network desiring to opt into the vaultMAX_STAKE
- a max stake amount that the network desires to accept from vault
- [Only if the vault uses
VetoSlasher
] Network should set resolver(s) for opted-in sub-network(s). - If the vault manager agrees with conditions proposed by a network (resolvers and limits), it can allocate stake by setting a limit for the network using
Delegator.setNetworkLimit(subnetwork, amount)
, where:subnetwork
- an address of the network concatenated with the sub-network’s identifieramount
- a total network stake limit can set up toMAX_STAKE
The network will not receive stake until operators are onboarded to both the vault and the network, even if a network limit is set on the vault (see the “Operator Onboarding” section).
Operator Onboarding
In Symbiotic, each operator can be connected to several networks and receive stake for each network from several vaults.
Operator onboarding requires several actions:
- Operator should be registered in Symbiotic
OperatorRegistry
, see details here - Operator should opt into the vault in
VaultOptInService
, see details here - Operator should opt into the network in
NetworkOptInService
, see details here - When operator is opted-in, the vault manager can allocate stake to the operator in supported networks/sub-networks using:
- In case of
FullRestakeDelegator
:FullRestakeDelegator.setOperatorNetworkLimit(subnetwork, operator, amount)
, where:amount
- a stake limit amount for theoperator
inside thesubnetwork
in absolute values
- In case of
NetworkRestakeDelegator
:NetworkRestakeDelegator.setOperatorNetworkLimit(subnetwork, operator, shares)
, where:shares
- a stake limit amount for theoperator
inside thesubnetwork
in shares
- In case of
Limits work independently from TVL in a vault
For example, a vault can have 1000 TOK deposited in total (TVL), but Limits for networks/operators can be 2000 TOK. In this case, the system will automatically adjust a stake allocated to network/operator as a minimum of (TVL, Limits). Check more details on this mechanic here.
Deposit to vault
Once the vault is deployed, it becomes possible to deposit funds. In general, vaults can be configured to accept any ERC-20 compatible token, including currently deployed DefaultCollateral
tokens. However, we expect that vaults will be set up to accept the tokens directly without wrapping through DefaultCollateral
. The DefaultCollateral
will continue to be used as “pre-staking” collateral with caps, as mentioned at the beginning of the document.
If a user/LRT has already deposited to DefaultCollateral
, it will be necessary to withdraw tokens from DefaultCollateral
before depositing them into Vaults. For example, if an address is already holding some amount of DC_TOKEN_A and wants to deposit TOKEN_A into a vault, this address will need to withdraw TOKEN_A from DC_TOKEN_A and then deposit the withdrawn TOKEN_A into the vault. For simplicity, we provide a helper contract that allows these actions to be performed atomically in a single transaction.
Note that DefaultCollateral
will remain capped, so when you move a token from DefaultCollateral
to vaults, another user can fill the spot that was freed by you in DefaultCollateral
. However, if your stake in the vault is delegated to networks (see “Network Onboarding” and “Operator Onboarding” sections), you will receive boosted symbiotic points and potentially additional rewards from networks. DYOR before moving funds.
Vaults have a withdrawal delay depending on the configured vault’s epoch duration. The exact withdrawal delay can be calculated using such formula: delay = (next_epoch_end_timestamp - current_timestamp)
, where next_epoch_end_timestamp
- is the time when the next vault’s epoch ends.