Mellow Protocol
Search
K
Comment on page

Contracts specs

ContractRegistry

constructor

addresses

names

versions

versionAddress

latestVersion

registerContract

  • ✅ registers IContractMeta compatible contract and updates respective view methods - #addresses - #versions - #names - #latestVersion - #versionAddress
Access control
  • ✅ allowed: operator (deployer)
  • ✅ denied with FRB: random address
  • ✅ allowed: protocol admin
Edge cases
  • ✅ when new contract major version differs more, than on one reverts with INVA
  • ✅ when new contract version lower or equal existing one reverts with INVA
  • ✅ when contract has invalid version reverts with INVA
  • ✅ when contract name is not alphanumeric reverts with INV
  • ✅ when address is already registered reverts with DUP

ProtocolGovernance

constructor

  • ✅ deploys a new contract

stagedParams

  • ✅ imestamp timestamp equals #stageParams's block.timestamp + governanceDelay
  • ✅ imestamp clears by #commitParams
  • ✅ imestamp edge cases when nothing is set returns zero
  • ✅ imestamp access control allowed: any address
Access control
  • ✅ allowed: any address
Properties
  • ✅ updates by #stageParams
  • ✅ clears by #commitParams

params

stagedValidatorsAddresses

validatorsAddresses

validatorsAddress

  • ✅ returns correct value
  • ✅ s properties @property: updates when committed validator grant for a new address
  • ✅ s properties @property: doesn't update when committed validator grant for an existing address
  • ✅ s access control allowed: any address

permissionAddresses

stagedPermissionGrantsAddresses

addressesByPermission

  • ✅ returns addresses that has the given permission set to true
Access control
  • ✅ allowed: any address
Properties
  • ✅ updates by #stagePermissionGrants + #commitPermissionGrants or #revokePermissions
  • ✅ is not affected by forceAllowMask
  • ✅ returns empty array on unknown permissionId

hasPermission

hasAllPermissions

  • ✅ checks if an address has all permissions set to true
Access control
  • ✅ allowed: any address
Properties
  • ✅ returns false on random address
  • ✅ is not affected by staged permissions
  • ✅ is affected by committed permissions
  • ✅ returns true for any address when forceAllowMask is set to true
Edge cases
  • ✅ on unknown permission id returns false

maxTokensPerVault

  • ✅ returns correct value

governanceDelay

  • ✅ returns correct value

protocolTreasury

  • ✅ returns correct value

forceAllowMask

  • ✅ returns correct value

withdrawLimit

  • ✅ returns correct value

supportsInterface

  • ✅ returns true for IProtocolGovernance interface (0xca11fe03)
  • ✅ access control: allowed: any address
  • ✅ edge cases: when contract does not support the given interface returns false

stageValidator

  • ✅ emits ValidatorStaged event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address
Edge cases
  • ✅ when attempting to stage grant to zero address reverts with AZ when target has zero address
  • ✅ when attempting to stage grant to zero address reverts with AZ when validator has zero address

rollbackStagedValidators

  • ✅ rolls back all staged validators
  • ✅ emits AllStagedValidatorsRolledBack event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address

commitValidator

  • ✅ commits staged validators
  • ✅ emits ValidatorCommitted event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address
Edge cases
  • ✅ when attempting to commit validator for zero address reverts with NULL
  • ✅ when nothing is staged for the given address reverts with NULL
  • ✅ when attempting to commit validator too early reverts with TS

commitAllValidatorsSurpassedDelay

  • ✅ emits ValidatorCommitted event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address
Properties
  • ✅ commits all staged validators
  • ✅ commits all staged validators after delay
Edge cases
  • ✅ when attempting to commit a single validator too early does not commit validator
  • ✅ when attempting to commit multiple validators too early does not commit these validators

revokeValidator

  • ✅ emits ValidatorRevoked event
Edge cases
  • ✅ when attempting to revoke from zero address reverts with NULL

rollbackStagedPermissionGrants

  • ✅ rolls back all staged permission grants
  • ✅ emits AllStagedPermissionGrantsRolledBack event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address

commitPermissionGrants

  • ✅ commits staged permission grants
  • ✅ emits PermissionGrantsCommitted event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address
Edge cases
  • ✅ when attempting to commit permissions for zero address reverts with NULL
  • ✅ when nothing is staged for the given address reverts with NULL
  • ✅ when attempting to commit permissions too early reverts with TS

commitAllPermissionGrantsSurpassedDelay

  • ✅ emits PermissionGrantsCommitted event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address
Properties
  • ✅ commits all staged permission grants
  • ✅ commits all staged permission grants after delay
Edge cases
  • ✅ when attempting to commit a single permission too early does not commit permission
  • ✅ when attempting to commit multiple permissions too early does not commit these permissions

revokePermissions

  • ✅ emits PermissionRevoked event
Edge cases
  • ✅ when attempting to revoke from zero address reverts with NULL

commitParams

  • ✅ emits ParamsCommitted event
Access control
  • ✅ allowed: protocol admin
  • ✅ denied: deployer
  • ✅ denied: random address
Edge cases
  • ✅ when attempting to commit params too early reverts with TS
  • ✅ when attempting to commit params without setting pending params reverts with NULL

stagePermissionGrants

  • ✅ emits PermissionGrantsStaged event
Access control
  • ✅ allowed: admin
  • ✅ denied: deployer
  • ✅ denied: random address
Edge cases
  • ✅ when attempting to stage grant to zero address reverts with NULL

stageParams

  • ✅ emits ParamsStaged event
Access control
  • ✅ allowed: admin
  • ✅ denied: random address
Edge cases
  • ✅ when given invalid params when maxTokensPerVault is zero reverts with NULL
  • ✅ when given invalid params when governanceDelay is zero reverts with NULL
  • ✅ when given invalid params when governanceDelay exceeds MAX_GOVERNANCE_DELAY reverts with LIMO
  • ✅ when given invalid params when withdrawLimit less than MIN_WITHDRAW_LIMIT reverts with LIMO

UnitPricesGovernance

constructor

supportsInterface

stageUnitPrice

rollbackUnitPrice

commitUnitPrice

VaultRegistry

constructor

  • ✅ creates VaultRegistry
  • ✅ initializes ProtocolGovernance address
  • ✅ initializes ERC721 token name
  • ✅ initializes ERC721 token symbol

vaults

  • ✅ returns all registered vaults
  • ✅ access control: allowed: any address
  • ✅ ount returns the number of registered vaults
  • ✅ ount access control: allowed: any address
  • ✅ ount properties @property: when N new vaults have been registered, vaults count will be increased by N

vaultForNft

  • ✅ resolves Vault address by VaultRegistry NFT
  • ✅ access control: allowed: any address
Edge cases
  • ✅ when Vault NFT is not registered in VaultRegistry returns zero address

nftForVault

  • ✅ resolves VaultRegistry NFT by Vault address
  • ✅ access control: allowed: any address
Edge cases
  • ✅ when Vault is not registered in VaultRegistry returns zero

isLocked

  • ✅ checks if token is locked (not transferable)
  • ✅ access control: allowed: any address
Edge cases
  • ✅ when VaultRegistry NFT is not registered in VaultRegistry returns false

protocolGovernance

  • ✅ returns ProtocolGovernance address
  • ✅ access control: allowed: any address

stagedProtocolGovernance

  • ✅ returns ProtocolGovernance address staged for commit
  • ✅ access control: allowed: any address
  • ✅ imestamp returns timestamp after which #commitStagedProtocolGovernance can be called
  • ✅ imestamp access control: allowed: any address
  • ✅ imestamp edge cases when nothing is staged returns 0
  • ✅ imestamp edge cases right after #commitStagedProtocolGovernance was called returns 0
Edge cases
  • ✅ when nothing is staged returns zero address
  • ✅ right after #commitStagedProtocolGovernance was called returns zero address

stagedProtocolGovernanceTimestamp

  • ✅ returns timestamp after which #commitStagedProtocolGovernance can be called
  • ✅ access control: allowed: any address
Edge cases
  • ✅ when nothing is staged returns 0
  • ✅ right after #commitStagedProtocolGovernance was called returns 0

vaultsCount

  • ✅ returns the number of registered vaults
  • ✅ access control: allowed: any address
Properties
  • ✅ when N new vaults have been registered, vaults count will be increased by N

supportsInterface

  • ✅ returns true if this contract supports a certain interface
  • ✅ access control: allowed: any address
  • ✅ edge cases: when contract does not support the given interface returns false

registerVault

  • ✅ binds minted ERC721 NFT to Vault address and transfers minted NFT to owner specified in args
  • ✅ emits VaultRegistered event
  • ✅ access control: allowed: any account with Register Vault permissions
  • ✅ access control: denied: any other address
  • ✅ access control: denied: protocol governance admin
Properties
  • ✅ minted NFT equals to vaultRegistry#vaultsCount
Edge cases
  • ✅ when address doesn't conform to IVault interface (IERC165) reverts with INVI
  • ✅ when vault has already been registered reverts with DUP
  • ✅ when owner address is zero reverts with AZ

stageProtocolGovernance

  • ✅ stages new ProtocolGovernance for commit
  • ✅ sets the stagedProtocolGovernanceTimestamp after which #commitStagedProtocolGovernance can be called
  • ✅ access control: allowed: ProtocolGovernance Admin
  • ✅ access control: denied: any other address
  • ✅ access control: denied: deployer
Edge cases
  • ✅ when new ProtocolGovernance is a zero address reverts with AZ

commitStagedProtocolGovernance

  • ✅ commits staged ProtocolGovernance
  • ✅ resets staged ProtocolGovernanceTimestamp
  • ✅ resets staged ProtocolGovernance
  • ✅ access control: allowed: ProtocolGovernance Admin
  • ✅ access control: denied: any other address
Edge cases
  • ✅ when nothing is staged reverts with INIT
  • ✅ when called before stagedProtocolGovernanceTimestamp reverts with TS
  • ✅ when called before stagedProtocolGovernanceTimestamp reverts with TS

lockNft

  • ✅ locks NFT (disables any transfer)
  • ✅ emits TokenLocked event
  • ✅ access control: allowed: NFT owner
  • ✅ access control: denied: any other address
  • ✅ access control: denied: protocol admin
Edge cases
  • ✅ when NFT has already been locked succeeds

CommonLibrary

ExceptionsLibrary

PermissionIdsLibrary

SemverLibrary

ChainlinkOracle

constructor

hasOracle

  • ✅ returns true if oracle is supported
  • ✅ edge cases: when oracle is not supported returns false

supportedTokens

  • ✅ returns list of supported tokens

priceX96

supportsInterface

  • ✅ returns true for ChainlinkOracle interface (0x8e3bd5d7)
  • ✅ edge cases: when contract does not support the given interface returns false

addChainlinkOracles

  • ✅ emits OraclesAdded event
  • ✅ when oracles have set by addChainLinkOracles function returns prices
  • ✅ edge cases: when arrays have different lengths reverts with INV
  • ✅ edge cases: when sender has no admin righs reverts with FRB

MellowOracle

constructor

priceX96

supportsInterface

  • ✅ returns true for IUniV3Oracle interface (0x6d80125b)
  • ✅ edge cases: when contract does not support the given interface returns false

UniV2Oracle

constructor

priceX96

supportsInterface

  • ✅ returns true for IUniV2Oracle interface (0x2748645e)
  • ✅ edge cases: when contract does not support the given interface returns false

UniV3Oracle

constructor

priceX96

supportsInterface

  • ✅ returns true for IUniV3Oracle interface (0x2a3602d6)
  • ✅ when contract does not support the given interface returns false

addUniV3Pools

  • ✅ when adding [weth, usdc] pools with fee = 500 adds pools
  • ✅ when adding [weth, usdc] pools with fee = 3000 adds pools
  • ✅ when adding [weth, usdc] pools with fee = 10000 does not return prices

HStrategy

constructor

  • ✅ deploys a new contract

initialize

createStrategy

  • ✅ creates a new strategy and initializes it

updateStrategyParams

updateMintingParams

updateOracleParams

updateRatioParams

updateSwapFees

manualPull

  • ✅ pulls token amounts from fromVault to toVault

rebalance

  • ✅ performs a rebalance according to strategy params

LStrategy

constructor

getTargetPriceX96

targetUniV3LiquidityRatio

rebalanceERC20UniV3Vaults

rebalanceUniV3Vaults

postPreOrder

signOrder

resetCowswapAllowance

collectUniFees

manualPull

updateTradingParams

updateRatioParams

updateOtherParams

MStrategy

constructor

  • ✅ deploys a new contract
Edge cases
  • ✅ when positionManager_ address is zero reverts with AZ
  • ✅ when router_ address is zero passes

getAverageTick

  • ✅ returns average UniswapV3Pool price tick

initialize

createStrategy

  • ✅ creates a new strategy and initializes it
Access control
  • ✅ allowed: any address
Edge cases
  • ✅ when tokens.length is not equal 2 reverts with INVL
  • ✅ when erc20Vault vaultTokens do not match tokens_ reverts with INVA
  • ✅ when moneyVault vaultTokens do not match tokens_ reverts with INVA
  • ✅ when UniSwapV3 pool for tokens does not exist reverts with AZ

rebalance

  • ✅ performs a rebalance according to target ratios when token0/token1 ratio is greater than required
  • ✅ performs a rebalance according to target ratios when token0/token1 ratio is less than required
Access control
  • ✅ allowed: MStrategy admin
  • ✅ allowed: MStrategy operator
  • ✅ denied: any other address
Edge cases
  • ✅ when absolute tick deviation >= oracle.maxTickDeviation reverts with INVA
  • ✅ when tick is greater than tickMax - tickNeiborhood the upper bound of the interval is expanded by tickIncrease amount
  • ✅ when tick is less than tickMin + tickNeiborhood the lower bound of the interval is expanded by tickIncrease amount
  • ✅ when current tick has not deviated from the previous rebalance tick reverts with LIMU

manualPull

  • ✅ pulls token amounts from fromVault to toVault
Access control
  • ✅ allowed: MStrategy admin
  • ✅ denied: any other address
Edge cases
  • ✅ when token pull amounts are 0 passes

setOracleParams

  • ✅ sets new params for oracle
  • ✅ edge cases: when maxSlippageD is more than DENOMINATOR reverts with INVA
Access control
  • ✅ allowed: MStrategy admin
  • ✅ denied: any other address

setRatioParams

  • ✅ sets new ratio params
  • ✅ edge cases: tickMin is greater than tickMax reverts with INVA
  • ✅ edge cases: when erc20MoneyRatioD is more than DENOMINATOR reverts with INVA
  • ✅ edge cases: when minErc20MoneyRatioDeviationD is more than DENOMINATOR reverts with INVA
Access control
  • ✅ allowed: MStrategy admin
  • ✅ denied: any other address

MultiPoolHStrategy

constructor

initialize

createStrategy

updateMutableParams

rebalance

  • ✅ works correctly

checkMutableParams

PulseRouteStrategy

constructor

initialize

updateMutableParams

rebalance

calculateNewInterval

checkMutableParams

checkImmutableParams

checkTickDeviations

calculateTargetRatioOfToken1

calculateAmountsForSwap

depositCallback

withdrawCallback

PulseStrategy

constructor

initialize

updateMutableParams

rebalance

checkMutableParams

checkImmutableParams

checkTickDeviation

calculateNewPosition

calculateTargetRatioOfToken1

calculateAmountsForSwap

depositCallback

withdrawCallback

PulseStrategyV2

constructor

initialize

setForceRebalanceFlag

updateDesiredAmounts

updateMutableParams

rebalance

checkMutableParams

checkImmutableParams

checkTickDeviation

formPositionWithSpotTickInCenter

calculateNewPosition

calculateTargetRatioOfToken1

calculateAmountsForSwap

depositCallback

withdrawCallback

QuickPulseStrategy

constructor

initialize

updateMutableParams

rebalance

checkMutableParams

checkImmutableParams

checkTickDeviation

calculateNewPosition

calculateTargetRatioOfToken1

calculateAmountsForSwap

depositCallback

withdrawCallback

onERC721Received

SinglePositionQuickSwapStrategy

constructor

initialize

updateMutableParams

rebalance

calculateNewInterval

checkMutableParams

checkImmutableParams

checkTickDeviations

calculateTargetRatioOfToken1

calculateAmountsForSwap

depositCallback

withdrawCallback

SinglePositionStrategy

constructor

  • ✅ creates contract

initialize