Source Code
Showing the last 2 transactions (View Advanced Filter)
| Transaction Hash |
Method
|
Block
|
From
|
|
To
|
||||
|---|---|---|---|---|---|---|---|---|---|
| Transfer | 17729382 | 888 days ago | IN | 0.001 ETH | 0.00054665 | ||||
| 0x60806040 | 13535384 | 1513 days ago | IN | 0 ETH | 0.75691635 |
Advanced mode:
| Parent Transaction Hash | Method | Block |
From
|
|
To
|
||||
|---|---|---|---|---|---|---|---|---|---|
There are no matching entriesUpdate your filters to view other transactions | |||||||||
Loading...
Loading
Cross-Chain Transactions
Loading...
Loading
Contract Name:
RocketMinipoolDelegate
Compiler Version
v0.7.6+commit.7338295f
Contract Source Code (Solidity Standard Json-Input format)
/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
import "@openzeppelin/contracts/math/SafeMath.sol";
import "./RocketMinipoolStorageLayout.sol";
import "../../interface/casper/DepositInterface.sol";
import "../../interface/deposit/RocketDepositPoolInterface.sol";
import "../../interface/minipool/RocketMinipoolInterface.sol";
import "../../interface/minipool/RocketMinipoolManagerInterface.sol";
import "../../interface/minipool/RocketMinipoolQueueInterface.sol";
import "../../interface/minipool/RocketMinipoolPenaltyInterface.sol";
import "../../interface/network/RocketNetworkPricesInterface.sol";
import "../../interface/node/RocketNodeManagerInterface.sol";
import "../../interface/node/RocketNodeStakingInterface.sol";
import "../../interface/dao/protocol/settings/RocketDAOProtocolSettingsMinipoolInterface.sol";
import "../../interface/dao/node/settings/RocketDAONodeTrustedSettingsMinipoolInterface.sol";
import "../../interface/dao/protocol/settings/RocketDAOProtocolSettingsNodeInterface.sol";
import "../../interface/dao/node/RocketDAONodeTrustedInterface.sol";
import "../../interface/network/RocketNetworkFeesInterface.sol";
import "../../interface/token/RocketTokenRETHInterface.sol";
import "../../types/MinipoolDeposit.sol";
import "../../types/MinipoolStatus.sol";
// An individual minipool in the Rocket Pool network
contract RocketMinipoolDelegate is RocketMinipoolStorageLayout, RocketMinipoolInterface {
// Constants
uint8 public constant version = 2; // Used to identify which delegate contract each minipool is using
uint256 constant calcBase = 1 ether;
uint256 constant prelaunchAmount = 16 ether; // The amount of ETH initially deposited when minipool is created
uint256 constant distributionCooldown = 100; // Number of blocks that must pass between calls to distributeBalance
// Libs
using SafeMath for uint;
// Events
event StatusUpdated(uint8 indexed status, uint256 time);
event ScrubVoted(address indexed member, uint256 time);
event MinipoolScrubbed(uint256 time);
event MinipoolPrestaked(bytes validatorPubkey, bytes validatorSignature, bytes32 depositDataRoot, uint256 amount, bytes withdrawalCredentials, uint256 time);
event EtherDeposited(address indexed from, uint256 amount, uint256 time);
event EtherWithdrawn(address indexed to, uint256 amount, uint256 time);
event EtherWithdrawalProcessed(address indexed executed, uint256 nodeAmount, uint256 userAmount, uint256 totalBalance, uint256 time);
// Status getters
function getStatus() override external view returns (MinipoolStatus) { return status; }
function getFinalised() override external view returns (bool) { return finalised; }
function getStatusBlock() override external view returns (uint256) { return statusBlock; }
function getStatusTime() override external view returns (uint256) { return statusTime; }
function getScrubVoted(address _member) override external view returns (bool) { return memberScrubVotes[_member]; }
// Deposit type getter
function getDepositType() override external view returns (MinipoolDeposit) { return depositType; }
// Node detail getters
function getNodeAddress() override external view returns (address) { return nodeAddress; }
function getNodeFee() override external view returns (uint256) { return nodeFee; }
function getNodeDepositBalance() override external view returns (uint256) { return nodeDepositBalance; }
function getNodeRefundBalance() override external view returns (uint256) { return nodeRefundBalance; }
function getNodeDepositAssigned() override external view returns (bool) { return nodeDepositAssigned; }
// User deposit detail getters
function getUserDepositBalance() override external view returns (uint256) { return userDepositBalance; }
function getUserDepositAssigned() override external view returns (bool) { return userDepositAssignedTime != 0; }
function getUserDepositAssignedTime() override external view returns (uint256) { return userDepositAssignedTime; }
function getTotalScrubVotes() override external view returns (uint256) { return totalScrubVotes; }
// Prevent direct calls to this contract
modifier onlyInitialised() {
require(storageState == StorageState.Initialised, "Storage state not initialised");
_;
}
modifier onlyUninitialised() {
require(storageState == StorageState.Uninitialised, "Storage state already initialised");
_;
}
// Only allow access from the owning node address
modifier onlyMinipoolOwner(address _nodeAddress) {
require(_nodeAddress == nodeAddress, "Invalid minipool owner");
_;
}
// Only allow access from the owning node address or their withdrawal address
modifier onlyMinipoolOwnerOrWithdrawalAddress(address _nodeAddress) {
require(_nodeAddress == nodeAddress || _nodeAddress == rocketStorage.getNodeWithdrawalAddress(nodeAddress), "Invalid minipool owner");
_;
}
// Only allow access from the latest version of the specified Rocket Pool contract
modifier onlyLatestContract(string memory _contractName, address _contractAddress) {
require(_contractAddress == getContractAddress(_contractName), "Invalid or outdated contract");
_;
}
// Get the address of a Rocket Pool network contract
function getContractAddress(string memory _contractName) private view returns (address) {
address contractAddress = rocketStorage.getAddress(keccak256(abi.encodePacked("contract.address", _contractName)));
require(contractAddress != address(0x0), "Contract not found");
return contractAddress;
}
function initialise(address _nodeAddress, MinipoolDeposit _depositType) override external onlyUninitialised {
// Check parameters
require(_nodeAddress != address(0x0), "Invalid node address");
require(_depositType != MinipoolDeposit.None, "Invalid deposit type");
// Load contracts
RocketNetworkFeesInterface rocketNetworkFees = RocketNetworkFeesInterface(getContractAddress("rocketNetworkFees"));
// Set initial status
status = MinipoolStatus.Initialised;
statusBlock = block.number;
statusTime = block.timestamp;
// Set details
depositType = _depositType;
nodeAddress = _nodeAddress;
nodeFee = rocketNetworkFees.getNodeFee();
// Set the rETH address
rocketTokenRETH = getContractAddress("rocketTokenRETH");
// Set local copy of penalty contract
rocketMinipoolPenalty = getContractAddress("rocketMinipoolPenalty");
// Intialise storage state
storageState = StorageState.Initialised;
}
// Assign the node deposit to the minipool
// Only accepts calls from the RocketNodeDeposit contract
function nodeDeposit(bytes calldata _validatorPubkey, bytes calldata _validatorSignature, bytes32 _depositDataRoot) override external payable onlyLatestContract("rocketNodeDeposit", msg.sender) onlyInitialised {
// Check current status & node deposit status
require(status == MinipoolStatus.Initialised, "The node deposit can only be assigned while initialised");
require(!nodeDepositAssigned, "The node deposit has already been assigned");
// Progress full minipool to prelaunch
if (depositType == MinipoolDeposit.Full) { setStatus(MinipoolStatus.Prelaunch); }
// Update node deposit details
nodeDepositBalance = msg.value;
nodeDepositAssigned = true;
// Emit ether deposited event
emit EtherDeposited(msg.sender, msg.value, block.timestamp);
// Perform the pre-stake to lock in withdrawal credentials on beacon chain
preStake(_validatorPubkey, _validatorSignature, _depositDataRoot);
}
// Assign user deposited ETH to the minipool and mark it as prelaunch
// Only accepts calls from the RocketDepositPool contract
function userDeposit() override external payable onlyLatestContract("rocketDepositPool", msg.sender) onlyInitialised {
// Check current status & user deposit status
require(status >= MinipoolStatus.Initialised && status <= MinipoolStatus.Staking, "The user deposit can only be assigned while initialised, in prelaunch, or staking");
require(userDepositAssignedTime == 0, "The user deposit has already been assigned");
// Progress initialised minipool to prelaunch
if (status == MinipoolStatus.Initialised) { setStatus(MinipoolStatus.Prelaunch); }
// Update user deposit details
userDepositBalance = msg.value;
userDepositAssignedTime = block.timestamp;
// Refinance full minipool
if (depositType == MinipoolDeposit.Full) {
// Update node balances
nodeDepositBalance = nodeDepositBalance.sub(msg.value);
nodeRefundBalance = nodeRefundBalance.add(msg.value);
}
// Emit ether deposited event
emit EtherDeposited(msg.sender, msg.value, block.timestamp);
}
// Refund node ETH refinanced from user deposited ETH
function refund() override external onlyMinipoolOwnerOrWithdrawalAddress(msg.sender) onlyInitialised {
// Check refund balance
require(nodeRefundBalance > 0, "No amount of the node deposit is available for refund");
// Refund node
_refund();
}
// Called to slash node operator's RPL balance if withdrawal balance was less than user deposit
function slash() external override onlyInitialised {
// Check there is a slash balance
require(nodeSlashBalance > 0, "No balance to slash");
// Perform slash
_slash();
}
// Called by node operator to finalise the pool and unlock their RPL stake
function finalise() external override onlyInitialised onlyMinipoolOwnerOrWithdrawalAddress(msg.sender) {
// Can only call if withdrawable and can only be called once
require(status == MinipoolStatus.Withdrawable, "Minipool must be withdrawable");
// Node operator cannot finalise the pool unless distributeBalance has been called
require(withdrawalBlock > 0, "Minipool balance must have been distributed at least once");
// Finalise the pool
_finalise();
}
// Returns true when `stake()` can be called by node operator taking into consideration the scrub period
function canStake() override external view onlyInitialised returns (bool) {
// Check status
if (status != MinipoolStatus.Prelaunch) {
return false;
}
// Get contracts
RocketDAONodeTrustedSettingsMinipoolInterface rocketDAONodeTrustedSettingsMinipool = RocketDAONodeTrustedSettingsMinipoolInterface(getContractAddress("rocketDAONodeTrustedSettingsMinipool"));
// Get scrub period
uint256 scrubPeriod = rocketDAONodeTrustedSettingsMinipool.getScrubPeriod();
// Check if we have been in prelaunch status for long enough
return block.timestamp > statusTime + scrubPeriod;
}
// Progress the minipool to staking, sending its ETH deposit to the VRC
// Only accepts calls from the minipool owner (node) while in prelaunch and once scrub period has ended
function stake(bytes calldata _validatorSignature, bytes32 _depositDataRoot) override external onlyMinipoolOwner(msg.sender) onlyInitialised {
// Get scrub period
RocketDAONodeTrustedSettingsMinipoolInterface rocketDAONodeTrustedSettingsMinipool = RocketDAONodeTrustedSettingsMinipoolInterface(getContractAddress("rocketDAONodeTrustedSettingsMinipool"));
RocketDAOProtocolSettingsMinipoolInterface rocketDAOProtocolSettingsMinipool = RocketDAOProtocolSettingsMinipoolInterface(getContractAddress("rocketDAOProtocolSettingsMinipool"));
uint256 scrubPeriod = rocketDAONodeTrustedSettingsMinipool.getScrubPeriod();
// Check current status
require(status == MinipoolStatus.Prelaunch, "The minipool can only begin staking while in prelaunch");
require(block.timestamp > statusTime + scrubPeriod, "Not enough time has passed to stake");
// Progress to staking
setStatus(MinipoolStatus.Staking);
// Load contracts
DepositInterface casperDeposit = DepositInterface(getContractAddress("casperDeposit"));
RocketMinipoolManagerInterface rocketMinipoolManager = RocketMinipoolManagerInterface(getContractAddress("rocketMinipoolManager"));
// Get launch amount
uint256 launchAmount = rocketDAOProtocolSettingsMinipool.getLaunchBalance().sub(prelaunchAmount);
// Check minipool balance
require(address(this).balance >= launchAmount, "Insufficient balance to begin staking");
// Retrieve validator pubkey from storage
bytes memory validatorPubkey = rocketMinipoolManager.getMinipoolPubkey(address(this));
// Send staking deposit to casper
casperDeposit.deposit{value : launchAmount}(validatorPubkey, rocketMinipoolManager.getMinipoolWithdrawalCredentials(address(this)), _validatorSignature, _depositDataRoot);
// Increment node's number of staking minipools
rocketMinipoolManager.incrementNodeStakingMinipoolCount(nodeAddress);
}
// Stakes 16 ETH into the deposit contract to set withdrawal credentials to this contract
function preStake(bytes calldata _validatorPubkey, bytes calldata _validatorSignature, bytes32 _depositDataRoot) internal {
// Load contracts
DepositInterface casperDeposit = DepositInterface(getContractAddress("casperDeposit"));
RocketMinipoolManagerInterface rocketMinipoolManager = RocketMinipoolManagerInterface(getContractAddress("rocketMinipoolManager"));
// Check minipool balance
require(address(this).balance >= prelaunchAmount, "Insufficient balance to pre-stake");
// Check validator pubkey is not in use
require(rocketMinipoolManager.getMinipoolByPubkey(_validatorPubkey) == address(0x0), "Validator pubkey is in use");
// Set minipool pubkey
rocketMinipoolManager.setMinipoolPubkey(_validatorPubkey);
// Get withdrawal credentials
bytes memory withdrawalCredentials = rocketMinipoolManager.getMinipoolWithdrawalCredentials(address(this));
// Send staking deposit to casper
casperDeposit.deposit{value : prelaunchAmount}(_validatorPubkey, withdrawalCredentials, _validatorSignature, _depositDataRoot);
// Emit event
emit MinipoolPrestaked(_validatorPubkey, _validatorSignature, _depositDataRoot, prelaunchAmount, withdrawalCredentials, block.timestamp);
}
// Mark the minipool as withdrawable
// Only accepts calls from the RocketMinipoolStatus contract
function setWithdrawable() override external onlyLatestContract("rocketMinipoolStatus", msg.sender) onlyInitialised {
// Get contracts
RocketMinipoolManagerInterface rocketMinipoolManager = RocketMinipoolManagerInterface(getContractAddress("rocketMinipoolManager"));
// Check current status
require(status == MinipoolStatus.Staking, "The minipool can only become withdrawable while staking");
// Progress to withdrawable
setStatus(MinipoolStatus.Withdrawable);
// Remove minipool from queue
if (userDepositAssignedTime == 0) {
// User deposit was never assigned so it still exists in queue, remove it
RocketMinipoolQueueInterface rocketMinipoolQueue = RocketMinipoolQueueInterface(getContractAddress("rocketMinipoolQueue"));
rocketMinipoolQueue.removeMinipool(depositType);
}
// Decrement the node operator's staking minipool count
rocketMinipoolManager.decrementNodeStakingMinipoolCount(nodeAddress);
}
// Distributes the contract's balance and finalises the pool
function distributeBalanceAndFinalise() override external onlyInitialised onlyMinipoolOwnerOrWithdrawalAddress(msg.sender) {
// Can only call if withdrawable and can only be called once
require(status == MinipoolStatus.Withdrawable, "Minipool must be withdrawable");
// Get withdrawal amount, we must also account for a possible node refund balance on the contract from users staking 32 ETH that have received a 16 ETH refund after the protocol bought out 16 ETH
uint256 totalBalance = address(this).balance.sub(nodeRefundBalance);
// Process withdrawal
_distributeBalance(totalBalance);
// Finalise the pool
_finalise();
}
// Distributes the contract's balance
// When called during staking status, requires 16 ether in the pool
// When called by non-owner with less than 16 ether, requires 14 days to have passed since being made withdrawable
function distributeBalance() override external onlyInitialised {
// Must be called while staking or withdrawable
require(status == MinipoolStatus.Staking || status == MinipoolStatus.Withdrawable, "Minipool must be staking or withdrawable");
// Get withdrawal amount, we must also account for a possible node refund balance on the contract from users staking 32 ETH that have received a 16 ETH refund after the protocol bought out 16 ETH
uint256 totalBalance = address(this).balance.sub(nodeRefundBalance);
// Get node withdrawal address
address nodeWithdrawalAddress = rocketStorage.getNodeWithdrawalAddress(nodeAddress);
// If it's not the owner calling
if (msg.sender != nodeAddress && msg.sender != nodeWithdrawalAddress) {
// And the pool is in staking status
if (status == MinipoolStatus.Staking) {
// Then balance must be greater than 16 ETH
require(totalBalance >= 16 ether, "Balance must be greater than 16 ETH");
} else {
// Then enough time must have elapsed
require(block.timestamp > statusTime.add(14 days), "Non-owner must wait 14 days after withdrawal to distribute balance");
// And balance must be greater than 4 ETH
require(address(this).balance >= 4 ether, "Balance must be greater than 4 ETH");
}
}
// Process withdrawal
_distributeBalance(totalBalance);
}
// Perform any slashings, refunds, and unlock NO's stake
function _finalise() private {
// Get contracts
RocketMinipoolManagerInterface rocketMinipoolManager = RocketMinipoolManagerInterface(getContractAddress("rocketMinipoolManager"));
// Can only finalise the pool once
require(!finalised, "Minipool has already been finalised");
// If slash is required then perform it
if (nodeSlashBalance > 0) {
_slash();
}
// Refund node operator if required
if (nodeRefundBalance > 0) {
_refund();
}
// Send any left over ETH to rETH contract
if (address(this).balance > 0) {
// Send user amount to rETH contract
payable(rocketTokenRETH).transfer(address(this).balance);
}
// Trigger a deposit of excess collateral from rETH contract to deposit pool
RocketTokenRETHInterface(rocketTokenRETH).depositExcessCollateral();
// Unlock node operator's RPL
rocketMinipoolManager.incrementNodeFinalisedMinipoolCount(nodeAddress);
// Update unbonded validator count if minipool is unbonded
if (depositType == MinipoolDeposit.Empty) {
RocketDAONodeTrustedInterface rocketDAONodeTrusted = RocketDAONodeTrustedInterface(getContractAddress("rocketDAONodeTrusted"));
rocketDAONodeTrusted.decrementMemberUnbondedValidatorCount(nodeAddress);
}
// Set finalised flag
finalised = true;
}
function _distributeBalance(uint256 _balance) private {
// Rate limit this method to prevent front running
require(block.number > withdrawalBlock + distributionCooldown, "Distribution of this minipool's balance is on cooldown");
// Deposit amounts
uint256 nodeAmount = 0;
// Check if node operator was slashed
if (_balance < userDepositBalance) {
// Only slash on first call to distribute
if (withdrawalBlock == 0) {
// Record shortfall for slashing
nodeSlashBalance = userDepositBalance.sub(_balance);
}
} else {
// Calculate node's share of the balance
nodeAmount = calculateNodeShare(_balance);
}
// User amount is what's left over from node's share
uint256 userAmount = _balance.sub(nodeAmount);
// Pay node operator via refund
nodeRefundBalance = nodeRefundBalance.add(nodeAmount);
// Pay user amount to rETH contract
if (userAmount > 0) {
// Send user amount to rETH contract
payable(rocketTokenRETH).transfer(userAmount);
}
// Save block to prevent multiple withdrawals within a few blocks
withdrawalBlock = block.number;
// Log it
emit EtherWithdrawalProcessed(msg.sender, nodeAmount, userAmount, _balance, block.timestamp);
}
// Given a validator balance, this function returns what portion of it belongs to the node taking into consideration
// the minipool's commission rate and any penalties it may have attracted
function calculateNodeShare(uint256 _balance) override public view returns (uint256) {
// Get fee and balances from minipool contract
uint256 stakingDepositTotal = 32 ether;
uint256 userAmount = userDepositBalance;
// Check if node operator was slashed
if (userAmount > _balance) {
// None of balance belongs to the node
return 0;
}
// Check if there are rewards to pay out
if (_balance > stakingDepositTotal) {
// Calculate rewards earned
uint256 totalRewards = _balance.sub(stakingDepositTotal);
// Calculate node share of rewards for the user
uint256 halfRewards = totalRewards.div(2);
uint256 nodeCommissionFee = halfRewards.mul(nodeFee).div(1 ether);
// Check for un-bonded minipool
if (depositType == MinipoolDeposit.Empty) {
// Add the total rewards minus the commission to the user's total
userAmount = userAmount.add(totalRewards.sub(nodeCommissionFee));
} else {
// Add half the rewards minus the commission fee to the user's total
userAmount = userAmount.add(halfRewards.sub(nodeCommissionFee));
}
}
// Calculate node amount as what's left over after user amount
uint256 nodeAmount = _balance.sub(userAmount);
// Check if node has an ETH penalty
uint256 penaltyRate = RocketMinipoolPenaltyInterface(rocketMinipoolPenalty).getPenaltyRate(address(this));
if (penaltyRate > 0) {
uint256 penaltyAmount = nodeAmount.mul(penaltyRate).div(calcBase);
if (penaltyAmount > nodeAmount) {
penaltyAmount = nodeAmount;
}
nodeAmount = nodeAmount.sub(penaltyAmount);
}
return nodeAmount;
}
// Given a validator balance, this function returns what portion of it belongs to rETH users taking into consideration
// the minipool's commission rate and any penalties it may have attracted
function calculateUserShare(uint256 _balance) override external view returns (uint256) {
// User's share is just the balance minus node's share
return _balance.sub(calculateNodeShare(_balance));
}
// Dissolve the minipool, returning user deposited ETH to the deposit pool
// Only accepts calls from the minipool owner (node), or from any address if timed out
function dissolve() override external onlyInitialised {
// Check current status
require(status == MinipoolStatus.Initialised || status == MinipoolStatus.Prelaunch, "The minipool can only be dissolved while initialised or in prelaunch");
// Load contracts
RocketDAOProtocolSettingsMinipoolInterface rocketDAOProtocolSettingsMinipool = RocketDAOProtocolSettingsMinipoolInterface(getContractAddress("rocketDAOProtocolSettingsMinipool"));
// Check if being dissolved by minipool owner or minipool is timed out
require(
(status == MinipoolStatus.Prelaunch && block.timestamp.sub(statusTime) >= rocketDAOProtocolSettingsMinipool.getLaunchTimeout()),
"The minipool can only be dissolved once it has timed out"
);
// Perform the dissolution
_dissolve();
}
// Withdraw node balances from the minipool and close it
// Only accepts calls from the minipool owner (node)
function close() override external onlyMinipoolOwner(msg.sender) onlyInitialised {
// Check current status
require(status == MinipoolStatus.Dissolved, "The minipool can only be closed while dissolved");
// Transfer node balance to node operator
uint256 nodeBalance = nodeDepositBalance.add(nodeRefundBalance);
if (nodeBalance > 0) {
// Update node balances
nodeDepositBalance = 0;
nodeRefundBalance = 0;
// Get node withdrawal address
address nodeWithdrawalAddress = rocketStorage.getNodeWithdrawalAddress(nodeAddress);
// Transfer balance
(bool success,) = nodeWithdrawalAddress.call{value : nodeBalance}("");
require(success, "Node ETH balance was not successfully transferred to node operator");
// Emit ether withdrawn event
emit EtherWithdrawn(nodeWithdrawalAddress, nodeBalance, block.timestamp);
}
// Update unbonded validator count if minipool is unbonded
if (depositType == MinipoolDeposit.Empty) {
RocketDAONodeTrustedInterface rocketDAONodeTrusted = RocketDAONodeTrustedInterface(getContractAddress("rocketDAONodeTrusted"));
rocketDAONodeTrusted.decrementMemberUnbondedValidatorCount(nodeAddress);
}
// Destroy minipool
RocketMinipoolManagerInterface rocketMinipoolManager = RocketMinipoolManagerInterface(getContractAddress("rocketMinipoolManager"));
rocketMinipoolManager.destroyMinipool();
// Self destruct
selfdestruct(payable(rocketTokenRETH));
}
// Can be called by trusted nodes to scrub this minipool if it's withdrawal credentials are not set correctly
function voteScrub() override external onlyInitialised {
// Check current status
require(status == MinipoolStatus.Prelaunch, "The minipool can only be scrubbed while in prelaunch");
// Get contracts
RocketDAONodeTrustedInterface rocketDAONode = RocketDAONodeTrustedInterface(getContractAddress("rocketDAONodeTrusted"));
RocketDAONodeTrustedSettingsMinipoolInterface rocketDAONodeTrustedSettingsMinipool = RocketDAONodeTrustedSettingsMinipoolInterface(getContractAddress("rocketDAONodeTrustedSettingsMinipool"));
// Must be a trusted member
require(rocketDAONode.getMemberIsValid(msg.sender), "Not a trusted member");
// Can only vote once
require(!memberScrubVotes[msg.sender], "Member has already voted to scrub");
memberScrubVotes[msg.sender] = true;
// Emit event
emit ScrubVoted(msg.sender, block.timestamp);
// Check if required quorum has voted
uint256 quorum = rocketDAONode.getMemberCount().mul(rocketDAONodeTrustedSettingsMinipool.getScrubQuorum()).div(calcBase);
if (totalScrubVotes.add(1) > quorum) {
// Dissolve this minipool, recycling ETH back to deposit pool
_dissolve();
// Slash RPL equal to minimum stake amount (if enabled)
if (rocketDAONodeTrustedSettingsMinipool.getScrubPenaltyEnabled()){
RocketNodeStakingInterface rocketNodeStaking = RocketNodeStakingInterface(getContractAddress("rocketNodeStaking"));
RocketDAOProtocolSettingsNodeInterface rocketDAOProtocolSettingsNode = RocketDAOProtocolSettingsNodeInterface(getContractAddress("rocketDAOProtocolSettingsNode"));
RocketDAOProtocolSettingsMinipoolInterface rocketDAOProtocolSettingsMinipool = RocketDAOProtocolSettingsMinipoolInterface(getContractAddress("rocketDAOProtocolSettingsMinipool"));
rocketNodeStaking.slashRPL(nodeAddress, rocketDAOProtocolSettingsMinipool.getHalfDepositUserAmount()
.mul(rocketDAOProtocolSettingsNode.getMinimumPerMinipoolStake())
.div(calcBase)
);
}
// Emit event
emit MinipoolScrubbed(block.timestamp);
} else {
// Increment total
totalScrubVotes = totalScrubVotes.add(1);
}
}
// Set the minipool's current status
function setStatus(MinipoolStatus _status) private {
// Update status
status = _status;
statusBlock = block.number;
statusTime = block.timestamp;
// Emit status updated event
emit StatusUpdated(uint8(_status), block.timestamp);
}
// Transfer refunded ETH balance to the node operator
function _refund() private {
// Update refund balance
uint256 refundAmount = nodeRefundBalance;
nodeRefundBalance = 0;
// Get node withdrawal address
address nodeWithdrawalAddress = rocketStorage.getNodeWithdrawalAddress(nodeAddress);
// Transfer refund amount
(bool success,) = nodeWithdrawalAddress.call{value : refundAmount}("");
require(success, "ETH refund amount was not successfully transferred to node operator");
// Emit ether withdrawn event
emit EtherWithdrawn(nodeWithdrawalAddress, refundAmount, block.timestamp);
}
// Slash node operator's RPL balance based on nodeSlashBalance
function _slash() private {
// Get contracts
RocketNodeStakingInterface rocketNodeStaking = RocketNodeStakingInterface(getContractAddress("rocketNodeStaking"));
// Slash required amount and reset storage value
uint256 slashAmount = nodeSlashBalance;
nodeSlashBalance = 0;
rocketNodeStaking.slashRPL(nodeAddress, slashAmount);
}
// Dissolve this minipool
function _dissolve() private {
// Get contracts
RocketDepositPoolInterface rocketDepositPool = RocketDepositPoolInterface(getContractAddress("rocketDepositPool"));
RocketMinipoolQueueInterface rocketMinipoolQueue = RocketMinipoolQueueInterface(getContractAddress("rocketMinipoolQueue"));
// Progress to dissolved
setStatus(MinipoolStatus.Dissolved);
// Transfer user balance to deposit pool
if (userDepositBalance > 0) {
// Store value in local
uint256 recycleAmount = userDepositBalance;
// Clear storage
userDepositBalance = 0;
userDepositAssignedTime = 0;
// Transfer
rocketDepositPool.recycleDissolvedDeposit{value : recycleAmount}();
// Emit ether withdrawn event
emit EtherWithdrawn(address(rocketDepositPool), recycleAmount, block.timestamp);
} else {
rocketMinipoolQueue.removeMinipool(depositType);
}
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.6.0 <0.8.0;
/**
* @dev Wrappers over Solidity's arithmetic operations with added overflow
* checks.
*
* Arithmetic operations in Solidity wrap on overflow. This can easily result
* in bugs, because programmers usually assume that an overflow raises an
* error, which is the standard behavior in high level programming languages.
* `SafeMath` restores this intuition by reverting the transaction when an
* operation overflows.
*
* Using this library instead of the unchecked operations eliminates an entire
* class of bugs, so it's recommended to use it always.
*/
library SafeMath {
/**
* @dev Returns the addition of two unsigned integers, with an overflow flag.
*
* _Available since v3.4._
*/
function tryAdd(uint256 a, uint256 b) internal pure returns (bool, uint256) {
uint256 c = a + b;
if (c < a) return (false, 0);
return (true, c);
}
/**
* @dev Returns the substraction of two unsigned integers, with an overflow flag.
*
* _Available since v3.4._
*/
function trySub(uint256 a, uint256 b) internal pure returns (bool, uint256) {
if (b > a) return (false, 0);
return (true, a - b);
}
/**
* @dev Returns the multiplication of two unsigned integers, with an overflow flag.
*
* _Available since v3.4._
*/
function tryMul(uint256 a, uint256 b) internal pure returns (bool, uint256) {
// Gas optimization: this is cheaper than requiring 'a' not being zero, but the
// benefit is lost if 'b' is also tested.
// See: https://github.com/OpenZeppelin/openzeppelin-contracts/pull/522
if (a == 0) return (true, 0);
uint256 c = a * b;
if (c / a != b) return (false, 0);
return (true, c);
}
/**
* @dev Returns the division of two unsigned integers, with a division by zero flag.
*
* _Available since v3.4._
*/
function tryDiv(uint256 a, uint256 b) internal pure returns (bool, uint256) {
if (b == 0) return (false, 0);
return (true, a / b);
}
/**
* @dev Returns the remainder of dividing two unsigned integers, with a division by zero flag.
*
* _Available since v3.4._
*/
function tryMod(uint256 a, uint256 b) internal pure returns (bool, uint256) {
if (b == 0) return (false, 0);
return (true, a % b);
}
/**
* @dev Returns the addition of two unsigned integers, reverting on
* overflow.
*
* Counterpart to Solidity's `+` operator.
*
* Requirements:
*
* - Addition cannot overflow.
*/
function add(uint256 a, uint256 b) internal pure returns (uint256) {
uint256 c = a + b;
require(c >= a, "SafeMath: addition overflow");
return c;
}
/**
* @dev Returns the subtraction of two unsigned integers, reverting on
* overflow (when the result is negative).
*
* Counterpart to Solidity's `-` operator.
*
* Requirements:
*
* - Subtraction cannot overflow.
*/
function sub(uint256 a, uint256 b) internal pure returns (uint256) {
require(b <= a, "SafeMath: subtraction overflow");
return a - b;
}
/**
* @dev Returns the multiplication of two unsigned integers, reverting on
* overflow.
*
* Counterpart to Solidity's `*` operator.
*
* Requirements:
*
* - Multiplication cannot overflow.
*/
function mul(uint256 a, uint256 b) internal pure returns (uint256) {
if (a == 0) return 0;
uint256 c = a * b;
require(c / a == b, "SafeMath: multiplication overflow");
return c;
}
/**
* @dev Returns the integer division of two unsigned integers, reverting on
* division by zero. The result is rounded towards zero.
*
* Counterpart to Solidity's `/` operator. Note: this function uses a
* `revert` opcode (which leaves remaining gas untouched) while Solidity
* uses an invalid opcode to revert (consuming all remaining gas).
*
* Requirements:
*
* - The divisor cannot be zero.
*/
function div(uint256 a, uint256 b) internal pure returns (uint256) {
require(b > 0, "SafeMath: division by zero");
return a / b;
}
/**
* @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
* reverting when dividing by zero.
*
* Counterpart to Solidity's `%` operator. This function uses a `revert`
* opcode (which leaves remaining gas untouched) while Solidity uses an
* invalid opcode to revert (consuming all remaining gas).
*
* Requirements:
*
* - The divisor cannot be zero.
*/
function mod(uint256 a, uint256 b) internal pure returns (uint256) {
require(b > 0, "SafeMath: modulo by zero");
return a % b;
}
/**
* @dev Returns the subtraction of two unsigned integers, reverting with custom message on
* overflow (when the result is negative).
*
* CAUTION: This function is deprecated because it requires allocating memory for the error
* message unnecessarily. For custom revert reasons use {trySub}.
*
* Counterpart to Solidity's `-` operator.
*
* Requirements:
*
* - Subtraction cannot overflow.
*/
function sub(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
require(b <= a, errorMessage);
return a - b;
}
/**
* @dev Returns the integer division of two unsigned integers, reverting with custom message on
* division by zero. The result is rounded towards zero.
*
* CAUTION: This function is deprecated because it requires allocating memory for the error
* message unnecessarily. For custom revert reasons use {tryDiv}.
*
* Counterpart to Solidity's `/` operator. Note: this function uses a
* `revert` opcode (which leaves remaining gas untouched) while Solidity
* uses an invalid opcode to revert (consuming all remaining gas).
*
* Requirements:
*
* - The divisor cannot be zero.
*/
function div(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
require(b > 0, errorMessage);
return a / b;
}
/**
* @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
* reverting with custom message when dividing by zero.
*
* CAUTION: This function is deprecated because it requires allocating memory for the error
* message unnecessarily. For custom revert reasons use {tryMod}.
*
* Counterpart to Solidity's `%` operator. This function uses a `revert`
* opcode (which leaves remaining gas untouched) while Solidity uses an
* invalid opcode to revert (consuming all remaining gas).
*
* Requirements:
*
* - The divisor cannot be zero.
*/
function mod(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
require(b > 0, errorMessage);
return a % b;
}
}// SPDX-License-Identifier: MIT
pragma solidity >=0.6.0 <0.8.0;
/**
* @dev Interface of the ERC20 standard as defined in the EIP.
*/
interface IERC20 {
/**
* @dev Returns the amount of tokens in existence.
*/
function totalSupply() external view returns (uint256);
/**
* @dev Returns the amount of tokens owned by `account`.
*/
function balanceOf(address account) external view returns (uint256);
/**
* @dev Moves `amount` tokens from the caller's account to `recipient`.
*
* Returns a boolean value indicating whether the operation succeeded.
*
* Emits a {Transfer} event.
*/
function transfer(address recipient, uint256 amount) external returns (bool);
/**
* @dev Returns the remaining number of tokens that `spender` will be
* allowed to spend on behalf of `owner` through {transferFrom}. This is
* zero by default.
*
* This value changes when {approve} or {transferFrom} are called.
*/
function allowance(address owner, address spender) external view returns (uint256);
/**
* @dev Sets `amount` as the allowance of `spender` over the caller's tokens.
*
* Returns a boolean value indicating whether the operation succeeded.
*
* IMPORTANT: Beware that changing an allowance with this method brings the risk
* that someone may use both the old and the new allowance by unfortunate
* transaction ordering. One possible solution to mitigate this race
* condition is to first reduce the spender's allowance to 0 and set the
* desired value afterwards:
* https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729
*
* Emits an {Approval} event.
*/
function approve(address spender, uint256 amount) external returns (bool);
/**
* @dev Moves `amount` tokens from `sender` to `recipient` using the
* allowance mechanism. `amount` is then deducted from the caller's
* allowance.
*
* Returns a boolean value indicating whether the operation succeeded.
*
* Emits a {Transfer} event.
*/
function transferFrom(address sender, address recipient, uint256 amount) external returns (bool);
/**
* @dev Emitted when `value` tokens are moved from one account (`from`) to
* another (`to`).
*
* Note that `value` may be zero.
*/
event Transfer(address indexed from, address indexed to, uint256 value);
/**
* @dev Emitted when the allowance of a `spender` for an `owner` is set by
* a call to {approve}. `value` is the new allowance.
*/
event Approval(address indexed owner, address indexed spender, uint256 value);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
import "../../interface/RocketStorageInterface.sol";
import "../../types/MinipoolDeposit.sol";
import "../../types/MinipoolStatus.sol";
// The RocketMinipool contract storage layout, shared by RocketMinipoolDelegate
// ******************************************************
// Note: This contract MUST NOT BE UPDATED after launch.
// All deployed minipool contracts must maintain a
// Consistent storage layout with RocketMinipoolDelegate.
// ******************************************************
abstract contract RocketMinipoolStorageLayout {
// Storage state enum
enum StorageState {
Undefined,
Uninitialised,
Initialised
}
// Main Rocket Pool storage contract
RocketStorageInterface internal rocketStorage = RocketStorageInterface(0);
// Status
MinipoolStatus internal status;
uint256 internal statusBlock;
uint256 internal statusTime;
uint256 internal withdrawalBlock;
// Deposit type
MinipoolDeposit internal depositType;
// Node details
address internal nodeAddress;
uint256 internal nodeFee;
uint256 internal nodeDepositBalance;
bool internal nodeDepositAssigned;
uint256 internal nodeRefundBalance;
uint256 internal nodeSlashBalance;
// User deposit details
uint256 internal userDepositBalance;
uint256 internal userDepositAssignedTime;
// Upgrade options
bool internal useLatestDelegate = false;
address internal rocketMinipoolDelegate;
address internal rocketMinipoolDelegatePrev;
// Local copy of RETH address
address internal rocketTokenRETH;
// Local copy of penalty contract
address internal rocketMinipoolPenalty;
// Used to prevent direct access to delegate and prevent calling initialise more than once
StorageState storageState = StorageState.Undefined;
// Whether node operator has finalised the pool
bool internal finalised;
// Trusted member scrub votes
mapping(address => bool) memberScrubVotes;
uint256 totalScrubVotes;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketStorageInterface {
// Deploy status
function getDeployedStatus() external view returns (bool);
// Guardian
function getGuardian() external view returns(address);
function setGuardian(address _newAddress) external;
function confirmGuardian() external;
// Getters
function getAddress(bytes32 _key) external view returns (address);
function getUint(bytes32 _key) external view returns (uint);
function getString(bytes32 _key) external view returns (string memory);
function getBytes(bytes32 _key) external view returns (bytes memory);
function getBool(bytes32 _key) external view returns (bool);
function getInt(bytes32 _key) external view returns (int);
function getBytes32(bytes32 _key) external view returns (bytes32);
// Setters
function setAddress(bytes32 _key, address _value) external;
function setUint(bytes32 _key, uint _value) external;
function setString(bytes32 _key, string calldata _value) external;
function setBytes(bytes32 _key, bytes calldata _value) external;
function setBool(bytes32 _key, bool _value) external;
function setInt(bytes32 _key, int _value) external;
function setBytes32(bytes32 _key, bytes32 _value) external;
// Deleters
function deleteAddress(bytes32 _key) external;
function deleteUint(bytes32 _key) external;
function deleteString(bytes32 _key) external;
function deleteBytes(bytes32 _key) external;
function deleteBool(bytes32 _key) external;
function deleteInt(bytes32 _key) external;
function deleteBytes32(bytes32 _key) external;
// Arithmetic
function addUint(bytes32 _key, uint256 _amount) external;
function subUint(bytes32 _key, uint256 _amount) external;
// Protected storage
function getNodeWithdrawalAddress(address _nodeAddress) external view returns (address);
function getNodePendingWithdrawalAddress(address _nodeAddress) external view returns (address);
function setWithdrawalAddress(address _nodeAddress, address _newWithdrawalAddress, bool _confirm) external;
function confirmWithdrawalAddress(address _nodeAddress) external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface DepositInterface {
function deposit(bytes calldata _pubkey, bytes calldata _withdrawalCredentials, bytes calldata _signature, bytes32 _depositDataRoot) external payable;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketDAONodeTrustedInterface {
function getBootstrapModeDisabled() external view returns (bool);
function getMemberQuorumVotesRequired() external view returns (uint256);
function getMemberAt(uint256 _index) external view returns (address);
function getMemberCount() external view returns (uint256);
function getMemberMinRequired() external view returns (uint256);
function getMemberIsValid(address _nodeAddress) external view returns (bool);
function getMemberLastProposalTime(address _nodeAddress) external view returns (uint256);
function getMemberID(address _nodeAddress) external view returns (string memory);
function getMemberUrl(address _nodeAddress) external view returns (string memory);
function getMemberJoinedTime(address _nodeAddress) external view returns (uint256);
function getMemberProposalExecutedTime(string memory _proposalType, address _nodeAddress) external view returns (uint256);
function getMemberRPLBondAmount(address _nodeAddress) external view returns (uint256);
function getMemberIsChallenged(address _nodeAddress) external view returns (bool);
function getMemberUnbondedValidatorCount(address _nodeAddress) external view returns (uint256);
function incrementMemberUnbondedValidatorCount(address _nodeAddress) external;
function decrementMemberUnbondedValidatorCount(address _nodeAddress) external;
function bootstrapMember(string memory _id, string memory _url, address _nodeAddress) external;
function bootstrapSettingUint(string memory _settingContractName, string memory _settingPath, uint256 _value) external;
function bootstrapSettingBool(string memory _settingContractName, string memory _settingPath, bool _value) external;
function bootstrapUpgrade(string memory _type, string memory _name, string memory _contractAbi, address _contractAddress) external;
function bootstrapDisable(bool _confirmDisableBootstrapMode) external;
function memberJoinRequired(string memory _id, string memory _url) external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketDAONodeTrustedSettingsMinipoolInterface {
function getScrubPeriod() external view returns(uint256);
function getScrubQuorum() external view returns(uint256);
function getScrubPenaltyEnabled() external view returns(bool);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
import "../../../../types/MinipoolDeposit.sol";
interface RocketDAOProtocolSettingsMinipoolInterface {
function getLaunchBalance() external view returns (uint256);
function getDepositNodeAmount(MinipoolDeposit _depositType) external view returns (uint256);
function getFullDepositNodeAmount() external view returns (uint256);
function getHalfDepositNodeAmount() external view returns (uint256);
function getEmptyDepositNodeAmount() external view returns (uint256);
function getDepositUserAmount(MinipoolDeposit _depositType) external view returns (uint256);
function getFullDepositUserAmount() external view returns (uint256);
function getHalfDepositUserAmount() external view returns (uint256);
function getEmptyDepositUserAmount() external view returns (uint256);
function getSubmitWithdrawableEnabled() external view returns (bool);
function getLaunchTimeout() external view returns (uint256);
function getMaximumCount() external view returns (uint256);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketDAOProtocolSettingsNodeInterface {
function getRegistrationEnabled() external view returns (bool);
function getDepositEnabled() external view returns (bool);
function getMinimumPerMinipoolStake() external view returns (uint256);
function getMaximumPerMinipoolStake() external view returns (uint256);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketDepositPoolInterface {
function getBalance() external view returns (uint256);
function getExcessBalance() external view returns (uint256);
function deposit() external payable;
function recycleDissolvedDeposit() external payable;
function recycleExcessCollateral() external payable;
function recycleLiquidatedStake() external payable;
function assignDeposits() external;
function withdrawExcessBalance(uint256 _amount) external;
function getUserLastDepositBlock(address _address) external view returns (uint256);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
import "../../types/MinipoolDeposit.sol";
import "../../types/MinipoolStatus.sol";
import "../RocketStorageInterface.sol";
interface RocketMinipoolInterface {
function initialise(address _nodeAddress, MinipoolDeposit _depositType) external;
function getStatus() external view returns (MinipoolStatus);
function getFinalised() external view returns (bool);
function getStatusBlock() external view returns (uint256);
function getStatusTime() external view returns (uint256);
function getScrubVoted(address _member) external view returns (bool);
function getDepositType() external view returns (MinipoolDeposit);
function getNodeAddress() external view returns (address);
function getNodeFee() external view returns (uint256);
function getNodeDepositBalance() external view returns (uint256);
function getNodeRefundBalance() external view returns (uint256);
function getNodeDepositAssigned() external view returns (bool);
function getUserDepositBalance() external view returns (uint256);
function getUserDepositAssigned() external view returns (bool);
function getUserDepositAssignedTime() external view returns (uint256);
function getTotalScrubVotes() external view returns (uint256);
function calculateNodeShare(uint256 _balance) external view returns (uint256);
function calculateUserShare(uint256 _balance) external view returns (uint256);
function nodeDeposit(bytes calldata _validatorPubkey, bytes calldata _validatorSignature, bytes32 _depositDataRoot) external payable;
function userDeposit() external payable;
function distributeBalance() external;
function distributeBalanceAndFinalise() external;
function refund() external;
function slash() external;
function finalise() external;
function canStake() external view returns (bool);
function stake(bytes calldata _validatorSignature, bytes32 _depositDataRoot) external;
function setWithdrawable() external;
function dissolve() external;
function close() external;
function voteScrub() external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
import "../../types/MinipoolDeposit.sol";
import "./RocketMinipoolInterface.sol";
interface RocketMinipoolManagerInterface {
function getMinipoolCount() external view returns (uint256);
function getStakingMinipoolCount() external view returns (uint256);
function getFinalisedMinipoolCount() external view returns (uint256);
function getActiveMinipoolCount() external view returns (uint256);
function getMinipoolCountPerStatus(uint256 offset, uint256 limit) external view returns (uint256, uint256, uint256, uint256, uint256);
function getPrelaunchMinipools(uint256 offset, uint256 limit) external view returns (address[] memory);
function getMinipoolAt(uint256 _index) external view returns (address);
function getNodeMinipoolCount(address _nodeAddress) external view returns (uint256);
function getNodeActiveMinipoolCount(address _nodeAddress) external view returns (uint256);
function getNodeFinalisedMinipoolCount(address _nodeAddress) external view returns (uint256);
function getNodeStakingMinipoolCount(address _nodeAddress) external view returns (uint256);
function getNodeMinipoolAt(address _nodeAddress, uint256 _index) external view returns (address);
function getNodeValidatingMinipoolCount(address _nodeAddress) external view returns (uint256);
function getNodeValidatingMinipoolAt(address _nodeAddress, uint256 _index) external view returns (address);
function getMinipoolByPubkey(bytes calldata _pubkey) external view returns (address);
function getMinipoolExists(address _minipoolAddress) external view returns (bool);
function getMinipoolDestroyed(address _minipoolAddress) external view returns (bool);
function getMinipoolPubkey(address _minipoolAddress) external view returns (bytes memory);
function getMinipoolWithdrawalCredentials(address _minipoolAddress) external pure returns (bytes memory);
function createMinipool(address _nodeAddress, MinipoolDeposit _depositType, uint256 _salt) external returns (RocketMinipoolInterface);
function destroyMinipool() external;
function incrementNodeStakingMinipoolCount(address _nodeAddress) external;
function decrementNodeStakingMinipoolCount(address _nodeAddress) external;
function incrementNodeFinalisedMinipoolCount(address _nodeAddress) external;
function setMinipoolPubkey(bytes calldata _pubkey) external;
function getMinipoolBytecode() external pure returns (bytes memory);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketMinipoolPenaltyInterface {
// Max penalty rate
function setMaxPenaltyRate(uint256 _rate) external;
function getMaxPenaltyRate() external view returns (uint256);
// Penalty rate
function setPenaltyRate(address _minipoolAddress, uint256 _rate) external;
function getPenaltyRate(address _minipoolAddress) external view returns(uint256);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
import "../../types/MinipoolDeposit.sol";
interface RocketMinipoolQueueInterface {
function getTotalLength() external view returns (uint256);
function getLength(MinipoolDeposit _depositType) external view returns (uint256);
function getTotalCapacity() external view returns (uint256);
function getEffectiveCapacity() external view returns (uint256);
function getNextCapacity() external view returns (uint256);
function getNextDeposit() external view returns (MinipoolDeposit, uint256);
function enqueueMinipool(MinipoolDeposit _depositType, address _minipool) external;
function dequeueMinipool() external returns (address minipoolAddress);
function dequeueMinipoolByDeposit(MinipoolDeposit _depositType) external returns (address minipoolAddress);
function removeMinipool(MinipoolDeposit _depositType) external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketNetworkFeesInterface {
function getNodeDemand() external view returns (int256);
function getNodeFee() external view returns (uint256);
function getNodeFeeByDemand(int256 _nodeDemand) external view returns (uint256);
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketNetworkPricesInterface {
function getPricesBlock() external view returns (uint256);
function getRPLPrice() external view returns (uint256);
function getEffectiveRPLStake() external view returns (uint256);
function getEffectiveRPLStakeUpdatedBlock() external view returns (uint256);
function getLatestReportableBlock() external view returns (uint256);
function inConsensus() external view returns (bool);
function submitPrices(uint256 _block, uint256 _rplPrice, uint256 _effectiveRplStake) external;
function executeUpdatePrices(uint256 _block, uint256 _rplPrice, uint256 _effectiveRplStake) external;
function increaseEffectiveRPLStake(uint256 _amount) external;
function decreaseEffectiveRPLStake(uint256 _amount) external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
pragma abicoder v2;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketNodeManagerInterface {
// Structs
struct TimezoneCount {
string timezone;
uint256 count;
}
function getNodeCount() external view returns (uint256);
function getNodeCountPerTimezone(uint256 offset, uint256 limit) external view returns (TimezoneCount[] memory);
function getNodeAt(uint256 _index) external view returns (address);
function getNodeExists(address _nodeAddress) external view returns (bool);
function getNodeWithdrawalAddress(address _nodeAddress) external view returns (address);
function getNodePendingWithdrawalAddress(address _nodeAddress) external view returns (address);
function getNodeTimezoneLocation(address _nodeAddress) external view returns (string memory);
function registerNode(string calldata _timezoneLocation) external;
function setTimezoneLocation(string calldata _timezoneLocation) external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
interface RocketNodeStakingInterface {
function getTotalRPLStake() external view returns (uint256);
function getNodeRPLStake(address _nodeAddress) external view returns (uint256);
function getNodeRPLStakedTime(address _nodeAddress) external view returns (uint256);
function getTotalEffectiveRPLStake() external view returns (uint256);
function calculateTotalEffectiveRPLStake(uint256 offset, uint256 limit, uint256 rplPrice) external view returns (uint256);
function getNodeEffectiveRPLStake(address _nodeAddress) external view returns (uint256);
function getNodeMinimumRPLStake(address _nodeAddress) external view returns (uint256);
function getNodeMaximumRPLStake(address _nodeAddress) external view returns (uint256);
function getNodeMinipoolLimit(address _nodeAddress) external view returns (uint256);
function stakeRPL(uint256 _amount) external;
function withdrawRPL(uint256 _amount) external;
function slashRPL(address _nodeAddress, uint256 _ethSlashAmount) external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
interface RocketTokenRETHInterface is IERC20 {
function getEthValue(uint256 _rethAmount) external view returns (uint256);
function getRethValue(uint256 _ethAmount) external view returns (uint256);
function getExchangeRate() external view returns (uint256);
function getTotalCollateral() external view returns (uint256);
function getCollateralRate() external view returns (uint256);
function depositExcess() external payable;
function depositExcessCollateral() external;
function mint(uint256 _ethAmount, address _to) external;
function burn(uint256 _rethAmount) external;
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
// Represents the type of deposits required by a minipool
enum MinipoolDeposit {
None, // Marks an invalid deposit type
Full, // The minipool requires 32 ETH from the node operator, 16 ETH of which will be refinanced from user deposits
Half, // The minipool required 16 ETH from the node operator to be matched with 16 ETH from user deposits
Empty // The minipool requires 0 ETH from the node operator to be matched with 32 ETH from user deposits (trusted nodes only)
}/**
* .
* / \
* |.'.|
* |'.'|
* ,'| |`.
* |,-'-|-'-.|
* __|_| | _ _ _____ _
* | ___ \| | | | | | ___ \ | |
* | |_/ /|__ ___| | _____| |_ | |_/ /__ ___ | |
* | // _ \ / __| |/ / _ \ __| | __/ _ \ / _ \| |
* | |\ \ (_) | (__| < __/ |_ | | | (_) | (_) | |
* \_| \_\___/ \___|_|\_\___|\__| \_| \___/ \___/|_|
* +---------------------------------------------------+
* | DECENTRALISED STAKING PROTOCOL FOR ETHEREUM |
* +---------------------------------------------------+
*
* Rocket Pool is a first-of-its-kind Ethereum staking pool protocol, designed to
* be community-owned, decentralised, and trustless.
*
* For more information about Rocket Pool, visit https://rocketpool.net
*
* Authors: David Rugendyke, Jake Pospischil, Kane Wallmann, Darren Langley, Joe Clapis, Nick Doherty
*
*/
pragma solidity 0.7.6;
// SPDX-License-Identifier: GPL-3.0-only
// Represents a minipool's status within the network
enum MinipoolStatus {
Initialised, // The minipool has been initialised and is awaiting a deposit of user ETH
Prelaunch, // The minipool has enough ETH to begin staking and is awaiting launch by the node operator
Staking, // The minipool is currently staking
Withdrawable, // The minipool has become withdrawable on the beacon chain and can be withdrawn from by the node operator
Dissolved // The minipool has been dissolved and its user deposited ETH has been returned to the deposit pool
}{
"remappings": [],
"optimizer": {
"enabled": true,
"runs": 15000
},
"evmVersion": "istanbul",
"libraries": {},
"outputSelection": {
"*": {
"*": [
"evm.bytecode",
"evm.deployedBytecode",
"devdoc",
"userdoc",
"metadata",
"abi"
]
}
}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"time","type":"uint256"}],"name":"EtherDeposited","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"executed","type":"address"},{"indexed":false,"internalType":"uint256","name":"nodeAmount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"userAmount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"totalBalance","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"time","type":"uint256"}],"name":"EtherWithdrawalProcessed","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"time","type":"uint256"}],"name":"EtherWithdrawn","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"bytes","name":"validatorPubkey","type":"bytes"},{"indexed":false,"internalType":"bytes","name":"validatorSignature","type":"bytes"},{"indexed":false,"internalType":"bytes32","name":"depositDataRoot","type":"bytes32"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"bytes","name":"withdrawalCredentials","type":"bytes"},{"indexed":false,"internalType":"uint256","name":"time","type":"uint256"}],"name":"MinipoolPrestaked","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint256","name":"time","type":"uint256"}],"name":"MinipoolScrubbed","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"member","type":"address"},{"indexed":false,"internalType":"uint256","name":"time","type":"uint256"}],"name":"ScrubVoted","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint8","name":"status","type":"uint8"},{"indexed":false,"internalType":"uint256","name":"time","type":"uint256"}],"name":"StatusUpdated","type":"event"},{"inputs":[{"internalType":"uint256","name":"_balance","type":"uint256"}],"name":"calculateNodeShare","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_balance","type":"uint256"}],"name":"calculateUserShare","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"canStake","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"close","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"dissolve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"distributeBalance","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"distributeBalanceAndFinalise","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"finalise","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"getDepositType","outputs":[{"internalType":"enum MinipoolDeposit","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getFinalised","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getNodeAddress","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getNodeDepositAssigned","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getNodeDepositBalance","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getNodeFee","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getNodeRefundBalance","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_member","type":"address"}],"name":"getScrubVoted","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getStatus","outputs":[{"internalType":"enum MinipoolStatus","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getStatusBlock","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getStatusTime","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getTotalScrubVotes","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getUserDepositAssigned","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getUserDepositAssignedTime","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getUserDepositBalance","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_nodeAddress","type":"address"},{"internalType":"enum MinipoolDeposit","name":"_depositType","type":"uint8"}],"name":"initialise","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes","name":"_validatorPubkey","type":"bytes"},{"internalType":"bytes","name":"_validatorSignature","type":"bytes"},{"internalType":"bytes32","name":"_depositDataRoot","type":"bytes32"}],"name":"nodeDeposit","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"refund","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"setWithdrawable","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"slash","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes","name":"_validatorSignature","type":"bytes"},{"internalType":"bytes32","name":"_depositDataRoot","type":"bytes32"}],"name":"stake","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"userDeposit","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"version","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"voteScrub","outputs":[],"stateMutability":"nonpayable","type":"function"}]Contract Creation Code
6080604052600080546001600160a01b0319169055600c805460ff19169055600f805460ff60a01b1916905534801561003757600080fd5b50614af5806100476000396000f3fe6080604052600436106101e35760003560e01c80637476a6c311610102578063d91eda6211610095578063e715013411610064578063e7150134146105ce578063e7e04aba146105e3578063f7ae36d1146105f8578063fbc02c4214610675576101e3565b8063d91eda6214610553578063dd0ddfcf14610568578063e117d192146105a4578063e67cd5b0146105b9576101e3565b8063a129a5ee116100d1578063a129a5ee146104e1578063a2940a90146104f6578063a43992631461050b578063d45dc62814610520576101e3565b80637476a6c3146103e057806374ca6bf2146104a25780637943da69146104b75780639ed27809146104cc576101e3565b80634e69d5601161017a57806368f449b21161014957806368f449b21461035c5780636934f90d1461037157806369c089ea1461038657806370dabc9e146103af576101e3565b80634e69d560146102c157806354fd4d50146102f7578063590e1ae3146103225780635abd37e414610337576101e3565b80633bef8a3a116101b65780633bef8a3a1461027a5780633e0a56b01461028f57806343d726d6146102a457806348146113146102b9576101e3565b8063042e5d4c146101e857806319f18b1f146101ff5780631a69d18f1461023b5780632da25de314610265575b600080fd5b3480156101f457600080fd5b506101fd61068a565b005b34801561020b57600080fd5b506102296004803603602081101561022257600080fd5b50356108a6565b60408051918252519081900360200190f35b34801561024757600080fd5b506102296004803603602081101561025e57600080fd5b50356108c3565b34801561027157600080fd5b506101fd610a65565b34801561028657600080fd5b506101fd610b32565b34801561029b57600080fd5b50610229610d18565b3480156102b057600080fd5b506101fd610d1f565b6101fd611163565b3480156102cd57600080fd5b506102d66113d5565b604051808260048111156102e657fe5b815260200191505060405180910390f35b34801561030357600080fd5b5061030c6113e5565b6040805160ff9092168252519081900360200190f35b34801561032e57600080fd5b506101fd6113ea565b34801561034357600080fd5b5061034c6115b5565b604051808260038111156102e657fe5b34801561036857600080fd5b506102296115be565b34801561037d57600080fd5b506101fd6115c4565b34801561039257600080fd5b5061039b6118cd565b604080519115158252519081900360200190f35b3480156103bb57600080fd5b506103c46118d6565b604080516001600160a01b039092168252519081900360200190f35b6101fd600480360360608110156103f657600080fd5b81019060208101813564010000000081111561041157600080fd5b82018360208201111561042357600080fd5b8035906020019184600183028401116401000000008311171561044557600080fd5b91939092909160208101903564010000000081111561046357600080fd5b82018360208201111561047557600080fd5b8035906020019184600183028401116401000000008311171561049757600080fd5b9193509150356118ea565b3480156104ae57600080fd5b50610229611b2d565b3480156104c357600080fd5b506101fd611b33565b3480156104d857600080fd5b5061039b611e09565b3480156104ed57600080fd5b5061039b611f37565b34801561050257600080fd5b50610229611f59565b34801561051757600080fd5b506101fd611f5f565b34801561052c57600080fd5b5061039b6004803603602081101561054357600080fd5b50356001600160a01b0316612196565b34801561055f57600080fd5b5061039b6121b4565b34801561057457600080fd5b506101fd6004803603604081101561058b57600080fd5b5080356001600160a01b0316906020013560ff166121bc565b3480156105b057600080fd5b506101fd612538565b3480156105c557600080fd5b50610229612bc5565b3480156105da57600080fd5b50610229612bcb565b3480156105ef57600080fd5b50610229612bd1565b34801561060457600080fd5b506101fd6004803603604081101561061b57600080fd5b81019060208101813564010000000081111561063657600080fd5b82018360208201111561064857600080fd5b8035906020019184600183028401116401000000008311171561066a57600080fd5b919350915035612bd7565b34801561068157600080fd5b5061022961339d565b6002600f54600160a01b900460ff1660028111156106a457fe5b146106f6576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b600454339061010090046001600160a01b03168114806107bb575060005460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b15801561078057600080fd5b505afa158015610794573d6000803e3d6000fd5b505050506040513d60208110156107aa57600080fd5b50516001600160a01b038281169116145b61080c576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6003600054600160a01b900460ff16600481111561082657fe5b14610878576040805162461bcd60e51b815260206004820152601d60248201527f4d696e69706f6f6c206d75737420626520776974686472617761626c65000000604482015290519081900360640190fd5b600061088f600854476133a390919063ffffffff16565b905061089a81613405565b6108a2613530565b5050565b60006108bb6108b4836108c3565b83906133a3565b90505b919050565b600a546000906801bc16d674ec80000090838111156108e7576000925050506108be565b8184111561097f5760006108fb85846133a3565b9050600061090a826002613836565b90506000610935670de0b6b3a764000061092f6005548561389d90919063ffffffff16565b90613836565b9050600360045460ff16600381111561094a57fe5b141561096b5761096461095d84836133a3565b85906138fd565b935061097b565b61097861095d83836133a3565b93505b5050505b600061098b85836133a3565b600f54604080517fa1e8487d00000000000000000000000000000000000000000000000000000000815230600482015290519293506000926001600160a01b039092169163a1e8487d91602480820192602092909190829003018186803b1580156109f557600080fd5b505afa158015610a09573d6000803e3d6000fd5b505050506040513d6020811015610a1f57600080fd5b505190508015610a5c576000610a41670de0b6b3a764000061092f858561389d565b905082811115610a4e5750815b610a5883826133a3565b9250505b50949350505050565b6002600f54600160a01b900460ff166002811115610a7f57fe5b14610ad1576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b600060095411610b28576040805162461bcd60e51b815260206004820152601360248201527f4e6f2062616c616e636520746f20736c61736800000000000000000000000000604482015290519081900360640190fd5b610b30613957565b565b6002600f54600160a01b900460ff166002811115610b4c57fe5b14610b9e576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60008054600160a01b900460ff166004811115610bb757fe5b1480610bda57506001600054600160a01b900460ff166004811115610bd857fe5b145b610c155760405162461bcd60e51b81526004018080602001828103825260448152602001806149056044913960600191505060405180910390fd5b6000610c386040518060600160405280602181526020016148c360219139613a31565b90506001600054600160a01b900460ff166004811115610c5457fe5b148015610cd25750806001600160a01b031663d42916c26040518163ffffffff1660e01b815260040160206040518083038186803b158015610c9557600080fd5b505afa158015610ca9573d6000803e3d6000fd5b505050506040513d6020811015610cbf57600080fd5b5051600254610ccf9042906133a3565b10155b610d0d5760405162461bcd60e51b81526004018080602001828103825260388152602001806149716038913960400191505060405180910390fd5b610d15613ba9565b50565b6002545b90565b600454339061010090046001600160a01b03168114610d85576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff166002811115610d9f57fe5b14610df1576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6004600054600160a01b900460ff166004811115610e0b57fe5b14610e475760405162461bcd60e51b815260040180806020018281038252602f815260200180614a67602f913960400191505060405180910390fd5b6000610e606008546006546138fd90919063ffffffff16565b90508015610fe657600060068190556008819055805460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b158015610ee257600080fd5b505afa158015610ef6573d6000803e3d6000fd5b505050506040513d6020811015610f0c57600080fd5b50516040519091506000906001600160a01b0383169084908381818185875af1925050503d8060008114610f5c576040519150601f19603f3d011682016040523d82523d6000602084013e610f61565b606091505b5050905080610fa15760405162461bcd60e51b81526004018080602001828103825260428152602001806147c86042913960600191505060405180910390fd5b6040805184815242602082015281516001600160a01b038516927fd5ca65e1ec4f4864fea7b9c5cb1ec3087a0dbf9c74641db3f6458edf445c4051928290030190a250505b600360045460ff166003811115610ff957fe5b14156110bf57600061103f6040518060400160405280601481526020017f726f636b657444414f4e6f646554727573746564000000000000000000000000815250613a31565b9050806001600160a01b03166354d28878600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156110a557600080fd5b505af11580156110b9573d6000803e3d6000fd5b50505050505b60006110ff6040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b9050806001600160a01b0316637bb40aaf6040518163ffffffff1660e01b8152600401600060405180830381600087803b15801561113c57600080fd5b505af1158015611150573d6000803e3d6000fd5b5050600e546001600160a01b0316915050ff5b6040518060400160405280601181526020017f726f636b65744465706f736974506f6f6c000000000000000000000000000000815250336111a382613a31565b6001600160a01b0316816001600160a01b031614611208576040805162461bcd60e51b815260206004820152601c60248201527f496e76616c6964206f72206f7574646174656420636f6e747261637400000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff16600281111561122257fe5b14611274576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60008054600160a01b900460ff16600481111561128d57fe5b101580156112b357506002600054600160a01b900460ff1660048111156112b057fe5b11155b6112ee5760405162461bcd60e51b81526004018080602001828103825260518152602001806148726051913960600191505060405180910390fd5b600b541561132d5760405162461bcd60e51b815260040180806020018281038252602a815260200180614a96602a913960400191505060405180910390fd5b60008054600160a01b900460ff16600481111561134657fe5b1415611356576113566001613d64565b34600a5542600b55600160045460ff16600381111561137157fe5b14156113985760065461138490346133a3565b60065560085461139490346138fd565b6008555b60408051348152426020820152815133927fef51b4c870b8b0100eae2072e91db01222a303072af3728e58c9d4d2da33127f928290030190a25050565b600054600160a01b900460ff1690565b600281565b600454339061010090046001600160a01b03168114806114af575060005460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b15801561147457600080fd5b505afa158015611488573d6000803e3d6000fd5b505050506040513d602081101561149e57600080fd5b50516001600160a01b038281169116145b611500576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff16600281111561151a57fe5b1461156c576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6000600854116115ad5760405162461bcd60e51b81526004018080602001828103825260358152602001806147046035913960400191505060405180910390fd5b610d15613df4565b60045460ff1690565b60115490565b6040518060400160405280601481526020017f726f636b65744d696e69706f6f6c5374617475730000000000000000000000008152503361160482613a31565b6001600160a01b0316816001600160a01b031614611669576040805162461bcd60e51b815260206004820152601c60248201527f496e76616c6964206f72206f7574646174656420636f6e747261637400000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff16600281111561168357fe5b146116d5576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60006117156040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b90506002600054600160a01b900460ff16600481111561173157fe5b1461176d5760405162461bcd60e51b81526004018080602001828103825260378152602001806146286037913960400191505060405180910390fd5b6117776003613d64565b600b5461184c5760006117be6040518060400160405280601381526020017f726f636b65744d696e69706f6f6c517565756500000000000000000000000000815250613a31565b600480546040517fde1bdc8f0000000000000000000000000000000000000000000000000000000081529293506001600160a01b0384169263de1bdc8f9260ff90921691018082600381111561181057fe5b8152602001915050600060405180830381600087803b15801561183257600080fd5b505af1158015611846573d6000803e3d6000fd5b50505050505b806001600160a01b03166375b59c7f600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156118b057600080fd5b505af11580156118c4573d6000803e3d6000fd5b50505050505050565b60075460ff1690565b60045461010090046001600160a01b031690565b6040518060400160405280601181526020017f726f636b65744e6f64654465706f7369740000000000000000000000000000008152503361192a82613a31565b6001600160a01b0316816001600160a01b03161461198f576040805162461bcd60e51b815260206004820152601c60248201527f496e76616c6964206f72206f7574646174656420636f6e747261637400000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff1660028111156119a957fe5b146119fb576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60008054600160a01b900460ff166004811115611a1457fe5b14611a505760405162461bcd60e51b81526004018080602001828103825260378152602001806147396037913960400191505060405180910390fd5b60075460ff1615611a925760405162461bcd60e51b815260040180806020018281038252602a81526020018061465f602a913960400191505060405180910390fd5b600160045460ff166003811115611aa557fe5b1415611ab557611ab56001613d64565b346006819055600780547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016600117905560408051918252426020830152805133927fef51b4c870b8b0100eae2072e91db01222a303072af3728e58c9d4d2da33127f92908290030190a26118c48787878787613f75565b60065490565b6002600f54600160a01b900460ff166002811115611b4d57fe5b14611b9f576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6002600054600160a01b900460ff166004811115611bb957fe5b1480611bdc57506003600054600160a01b900460ff166004811115611bda57fe5b145b611c175760405162461bcd60e51b81526004018080602001828103825260288152602001806149496028913960400191505060405180910390fd5b6000611c2e600854476133a390919063ffffffff16565b6000805460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526101009092046001600160a01b0390811693830193909352519495509293911691635b49ff62916024808301926020929190829003018186803b158015611ca357600080fd5b505afa158015611cb7573d6000803e3d6000fd5b505050506040513d6020811015611ccd57600080fd5b505160045490915061010090046001600160a01b03163314801590611cfb5750336001600160a01b03821614155b15611e00576002600054600160a01b900460ff166004811115611d1a57fe5b1415611d6c5767de0b6b3a76400000821015611d675760405162461bcd60e51b8152600401808060200182810382526023815260200180614a236023913960400191505060405180910390fd5b611e00565b600254611d7c90621275006138fd565b4211611db95760405162461bcd60e51b81526004018080602001828103825260428152602001806146896042913960600191505060405180910390fd5b673782dace9d900000471015611e005760405162461bcd60e51b81526004018080602001828103825260228152602001806147706022913960400191505060405180910390fd5b6108a282613405565b60006002600f54600160a01b900460ff166002811115611e2557fe5b14611e77576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6001600054600160a01b900460ff166004811115611e9157fe5b14611e9e57506000610d1c565b6000611ec160405180606001604052806024815260200161458c60249139613a31565b90506000816001600160a01b031663f0245dc86040518163ffffffff1660e01b815260040160206040518083038186803b158015611efe57600080fd5b505afa158015611f12573d6000803e3d6000fd5b505050506040513d6020811015611f2857600080fd5b50516002540142119250505090565b600f547501000000000000000000000000000000000000000000900460ff1690565b600b5490565b6002600f54600160a01b900460ff166002811115611f7957fe5b14611fcb576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b600454339061010090046001600160a01b0316811480612090575060005460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b15801561205557600080fd5b505afa158015612069573d6000803e3d6000fd5b505050506040513d602081101561207f57600080fd5b50516001600160a01b038281169116145b6120e1576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6003600054600160a01b900460ff1660048111156120fb57fe5b1461214d576040805162461bcd60e51b815260206004820152601d60248201527f4d696e69706f6f6c206d75737420626520776974686472617761626c65000000604482015290519081900360640190fd5b60006003541161218e5760405162461bcd60e51b81526004018080602001828103825260398152602001806146cb6039913960400191505060405180910390fd5b610d15613530565b6001600160a01b031660009081526010602052604090205460ff1690565b600b54151590565b6001600f54600160a01b900460ff1660028111156121d657fe5b146122125760405162461bcd60e51b81526004018080602001828103825260218152602001806145b06021913960400191505060405180910390fd5b6001600160a01b03821661226d576040805162461bcd60e51b815260206004820152601460248201527f496e76616c6964206e6f64652061646472657373000000000000000000000000604482015290519081900360640190fd5b600081600381111561227b57fe5b14156122ce576040805162461bcd60e51b815260206004820152601460248201527f496e76616c6964206465706f7369742074797065000000000000000000000000604482015290519081900360640190fd5b600061230e6040518060400160405280601181526020017f726f636b65744e6574776f726b46656573000000000000000000000000000000815250613a31565b600080547fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff1690554360019081554260025560048054929350849290917fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff009091169083600381111561237c57fe5b021790555082600460016101000a8154816001600160a01b0302191690836001600160a01b03160217905550806001600160a01b031663e71501346040518163ffffffff1660e01b815260040160206040518083038186803b1580156123e157600080fd5b505afa1580156123f5573d6000803e3d6000fd5b505050506040513d602081101561240b57600080fd5b505160055560408051808201909152600f81527f726f636b6574546f6b656e524554480000000000000000000000000000000000602082015261244d90613a31565b600e80547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b039290921691909117905560408051808201909152601581527f726f636b65744d696e69706f6f6c50656e616c7479000000000000000000000060208201526124c290613a31565b600f80547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b0392909216919091177fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff1674020000000000000000000000000000000000000000179055505050565b6002600f54600160a01b900460ff16600281111561255257fe5b146125a4576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6001600054600160a01b900460ff1660048111156125be57fe5b146125fa5760405162461bcd60e51b81526004018080602001828103825260348152602001806145f46034913960400191505060405180910390fd5b600061263a6040518060400160405280601481526020017f726f636b657444414f4e6f646554727573746564000000000000000000000000815250613a31565b9050600061265f60405180606001604052806024815260200161458c60249139613a31565b9050816001600160a01b0316635dc33bdd336040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060206040518083038186803b1580156126ae57600080fd5b505afa1580156126c2573d6000803e3d6000fd5b505050506040513d60208110156126d857600080fd5b505161272b576040805162461bcd60e51b815260206004820152601460248201527f4e6f7420612074727573746564206d656d626572000000000000000000000000604482015290519081900360640190fd5b3360009081526010602052604090205460ff161561277a5760405162461bcd60e51b81526004018080602001828103825260218152602001806149cc6021913960400191505060405180910390fd5b3360008181526010602090815260409182902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055815142815291517fc038496c9b2fce7ae180c60886062197d0411e3c5d249053f188423280778a839281900390910190a260006128e8670de0b6b3a764000061092f846001600160a01b0316636e86e7fe6040518163ffffffff1660e01b815260040160206040518083038186803b15801561283157600080fd5b505afa158015612845573d6000803e3d6000fd5b505050506040513d602081101561285b57600080fd5b5051604080517f997072f700000000000000000000000000000000000000000000000000000000815290516001600160a01b0389169163997072f7916004808301926020929190829003018186803b1580156128b657600080fd5b505afa1580156128ca573d6000803e3d6000fd5b505050506040513d60208110156128e057600080fd5b50519061389d565b90508061290160016011546138fd90919063ffffffff16565b1115612bae5761290f613ba9565b816001600160a01b031663c4f502526040518163ffffffff1660e01b815260040160206040518083038186803b15801561294857600080fd5b505afa15801561295c573d6000803e3d6000fd5b505050506040513d602081101561297257600080fd5b505115612b765760006129b96040518060400160405280601181526020017f726f636b65744e6f64655374616b696e67000000000000000000000000000000815250613a31565b905060006129fb6040518060400160405280601d81526020017f726f636b657444414f50726f746f636f6c53657474696e67734e6f6465000000815250613a31565b90506000612a206040518060600160405280602181526020016148c360219139613a31565b9050826001600160a01b031663245395a6600460019054906101000a90046001600160a01b0316612b14670de0b6b3a764000061092f876001600160a01b0316636fdbe57b6040518163ffffffff1660e01b815260040160206040518083038186803b158015612a8f57600080fd5b505afa158015612aa3573d6000803e3d6000fd5b505050506040513d6020811015612ab957600080fd5b5051604080517f162adbfd00000000000000000000000000000000000000000000000000000000815290516001600160a01b038a169163162adbfd916004808301926020929190829003018186803b1580156128b657600080fd5b6040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b158015612b5a57600080fd5b505af1158015612b6e573d6000803e3d6000fd5b505050505050505b6040805142815290517fac58888447082d81defc760f4bd30b6196d9309777e161bce72c280a12a6ea689181900360200190a1612bc0565b601154612bbc9060016138fd565b6011555b505050565b60015490565b60055490565b600a5490565b600454339061010090046001600160a01b03168114612c3d576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff166002811115612c5757fe5b14612ca9576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6000612ccc60405180606001604052806024815260200161458c60249139613a31565b90506000612cf16040518060600160405280602181526020016148c360219139613a31565b90506000826001600160a01b031663f0245dc86040518163ffffffff1660e01b815260040160206040518083038186803b158015612d2e57600080fd5b505afa158015612d42573d6000803e3d6000fd5b505050506040513d6020811015612d5857600080fd5b505190506001600054600160a01b900460ff166004811115612d7657fe5b14612db25760405162461bcd60e51b81526004018080602001828103825260368152602001806147926036913960400191505060405180910390fd5b80600254014211612df45760405162461bcd60e51b81526004018080602001828103825260238152602001806145d16023913960400191505060405180910390fd5b612dfe6002613d64565b6000612e3e6040518060400160405280600d81526020017f6361737065724465706f73697400000000000000000000000000000000000000815250613a31565b90506000612e806040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b90506000612efb67de0b6b3a76400000866001600160a01b03166308e50d386040518163ffffffff1660e01b815260040160206040518083038186803b158015612ec957600080fd5b505afa158015612edd573d6000803e3d6000fd5b505050506040513d6020811015612ef357600080fd5b5051906133a3565b905080471015612f3c5760405162461bcd60e51b815260040180806020018281038252602581526020018061480a6025913960400191505060405180910390fd5b6000826001600160a01b0316633eb535e9306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060006040518083038186803b158015612f8b57600080fd5b505afa158015612f9f573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f191682016040526020811015612fc857600080fd5b8101908080516040519392919084640100000000821115612fe857600080fd5b908301906020820185811115612ffd57600080fd5b825164010000000081118282018810171561301757600080fd5b82525081516020918201929091019080838360005b8381101561304457818101518382015260200161302c565b50505050905090810190601f1680156130715780820380516001836020036101000a031916815260200191505b506040525050509050836001600160a01b031663228951188383866001600160a01b0316632cb76c37306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060006040518083038186803b1580156130d857600080fd5b505afa1580156130ec573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052602081101561311557600080fd5b810190808051604051939291908464010000000082111561313557600080fd5b90830190602082018581111561314a57600080fd5b825164010000000081118282018810171561316457600080fd5b82525081516020918201929091019080838360005b83811015613191578181015183820152602001613179565b50505050905090810190601f1680156131be5780820380516001836020036101000a031916815260200191505b506040525050508f8f8f6040518763ffffffff1660e01b815260040180806020018060200180602001858152602001848103845289818151815260200191508051906020019080838360005b8381101561322257818101518382015260200161320a565b50505050905090810190601f16801561324f5780820380516001836020036101000a031916815260200191505b5084810383528851815288516020918201918a019080838360005b8381101561328257818101518382015260200161326a565b50505050905090810190601f1680156132af5780820380516001836020036101000a031916815260200191505b508481038252868152602001878780828437600081840152601f19601f820116905080830192505050985050505050505050506000604051808303818588803b1580156132fb57600080fd5b505af115801561330f573d6000803e3d6000fd5b5050505050826001600160a01b0316639907288c600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b15801561337857600080fd5b505af115801561338c573d6000803e3d6000fd5b505050505050505050505050505050565b60085490565b6000828211156133fa576040805162461bcd60e51b815260206004820152601e60248201527f536166654d6174683a207375627472616374696f6e206f766572666c6f770000604482015290519081900360640190fd5b508082035b92915050565b60646003540143116134485760405162461bcd60e51b81526004018080602001828103825260368152602001806149ed6036913960400191505060405180910390fd5b6000600a548210156134715760035461346c57600a5461346890836133a3565b6009555b61347d565b61347a826108c3565b90505b600061348983836133a3565b60085490915061349990836138fd565b60085580156134de57600e546040516001600160a01b039091169082156108fc029083906000818181858888f193505050501580156134dc573d6000803e3d6000fd5b505b436003556040805183815260208101839052808201859052426060820152905133917f3422b68c7062367a3ae581f8bf64158ddb63f02294a0abe7f32491787076f1b7919081900360800190a2505050565b60006135706040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b600f549091507501000000000000000000000000000000000000000000900460ff16156135ce5760405162461bcd60e51b81526004018080602001828103825260238152602001806149a96023913960400191505060405180910390fd5b600954156135de576135de613957565b600854156135ee576135ee613df4565b471561362f57600e546040516001600160a01b03909116904780156108fc02916000818181858888f1935050505015801561362d573d6000803e3d6000fd5b505b600e60009054906101000a90046001600160a01b03166001600160a01b031663188e0dc66040518163ffffffff1660e01b8152600401600060405180830381600087803b15801561367f57600080fd5b505af1158015613693573d6000803e3d6000fd5b50505050806001600160a01b031663b04e8868600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156136fb57600080fd5b505af115801561370f573d6000803e3d6000fd5b506003925061371c915050565b60045460ff16600381111561372d57fe5b14156137f35760006137736040518060400160405280601481526020017f726f636b657444414f4e6f646554727573746564000000000000000000000000815250613a31565b9050806001600160a01b03166354d28878600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156137d957600080fd5b505af11580156137ed573d6000803e3d6000fd5b50505050505b50600f80547fffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffffff167501000000000000000000000000000000000000000000179055565b600080821161388c576040805162461bcd60e51b815260206004820152601a60248201527f536166654d6174683a206469766973696f6e206279207a65726f000000000000604482015290519081900360640190fd5b81838161389557fe5b049392505050565b6000826138ac575060006133ff565b828202828482816138b957fe5b04146138f65760405162461bcd60e51b81526004018080602001828103825260218152602001806148e46021913960400191505060405180910390fd5b9392505050565b6000828201838110156138f6576040805162461bcd60e51b815260206004820152601b60248201527f536166654d6174683a206164646974696f6e206f766572666c6f770000000000604482015290519081900360640190fd5b60006139976040518060400160405280601181526020017f726f636b65744e6f64655374616b696e67000000000000000000000000000000815250613a31565b6009805460009182905560048054604080517f245395a60000000000000000000000000000000000000000000000000000000081526001600160a01b03610100909304831693810193909352602483018490525194955091939185169263245395a69260448084019382900301818387803b158015613a1557600080fd5b505af1158015613a29573d6000803e3d6000fd5b505050505050565b60008060008054906101000a90046001600160a01b03166001600160a01b03166321f8a7218460405160200180807f636f6e74726163742e616464726573730000000000000000000000000000000081525060100182805190602001908083835b60208310613ab15780518252601f199092019160209182019101613a92565b6001836020036101000a038019825116818451168082178552505050505050905001915050604051602081830303815290604052805190602001206040518263ffffffff1660e01b81526004018082815260200191505060206040518083038186803b158015613b2057600080fd5b505afa158015613b34573d6000803e3d6000fd5b505050506040513d6020811015613b4a57600080fd5b505190506001600160a01b0381166108bb576040805162461bcd60e51b815260206004820152601260248201527f436f6e7472616374206e6f7420666f756e640000000000000000000000000000604482015290519081900360640190fd5b6000613be96040518060400160405280601181526020017f726f636b65744465706f736974506f6f6c000000000000000000000000000000815250613a31565b90506000613c2b6040518060400160405280601381526020017f726f636b65744d696e69706f6f6c517565756500000000000000000000000000815250613a31565b9050613c376004613d64565b600a5415613cf5576000600a5490506000600a819055506000600b81905550826001600160a01b03166372f5158d826040518263ffffffff1660e01b81526004016000604051808303818588803b158015613c9157600080fd5b505af1158015613ca5573d6000803e3d6000fd5b50506040805185815242602082015281516001600160a01b03891695507fd5ca65e1ec4f4864fea7b9c5cb1ec3087a0dbf9c74641db3f6458edf445c40519450908190039091019150a2506108a2565b600480546040517fde1bdc8f0000000000000000000000000000000000000000000000000000000081526001600160a01b0384169263de1bdc8f9260ff16910180826003811115613d4257fe5b8152602001915050600060405180830381600087803b158015613a1557600080fd5b600080548291907fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff16600160a01b836004811115613d9e57fe5b02179055504360015542600255806004811115613db757fe5b60ff167f26725881c2a4290b02cd153d6599fd484f0d4e6062c361e740fbbe39e7ad6142426040518082815260200191505060405180910390a250565b60088054600091829055815460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251939493921691635b49ff6291602480820192602092909190829003018186803b158015613e6f57600080fd5b505afa158015613e83573d6000803e3d6000fd5b505050506040513d6020811015613e9957600080fd5b50516040519091506000906001600160a01b0383169084908381818185875af1925050503d8060008114613ee9576040519150601f19603f3d011682016040523d82523d6000602084013e613eee565b606091505b5050905080613f2e5760405162461bcd60e51b815260040180806020018281038252604381526020018061482f6043913960600191505060405180910390fd5b6040805184815242602082015281516001600160a01b038516927fd5ca65e1ec4f4864fea7b9c5cb1ec3087a0dbf9c74641db3f6458edf445c4051928290030190a2505050565b6000613fb56040518060400160405280600d81526020017f6361737065724465706f73697400000000000000000000000000000000000000815250613a31565b90506000613ff76040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b905067de0b6b3a764000004710156140405760405162461bcd60e51b8152600401808060200182810382526021815260200180614a466021913960400191505060405180910390fd5b6040517fcf6a4763000000000000000000000000000000000000000000000000000000008152602060048201908152602482018890526000916001600160a01b0384169163cf6a4763918b918b918190604401848480828437600083820152604051601f909101601f191690920195506020945090925050508083038186803b1580156140cc57600080fd5b505afa1580156140e0573d6000803e3d6000fd5b505050506040513d60208110156140f657600080fd5b50516001600160a01b031614614153576040805162461bcd60e51b815260206004820152601a60248201527f56616c696461746f72207075626b657920697320696e20757365000000000000604482015290519081900360640190fd5b6040517f2c7f64d4000000000000000000000000000000000000000000000000000000008152602060048201908152602482018890526001600160a01b03831691632c7f64d4918a918a91908190604401848480828437600081840152601f19601f8201169050808301925050509350505050600060405180830381600087803b1580156141e057600080fd5b505af11580156141f4573d6000803e3d6000fd5b505050506000816001600160a01b0316632cb76c37306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060006040518083038186803b15801561424757600080fd5b505afa15801561425b573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052602081101561428457600080fd5b81019080805160405193929190846401000000008211156142a457600080fd5b9083019060208201858111156142b957600080fd5b82516401000000008111828201881017156142d357600080fd5b82525081516020918201929091019080838360005b838110156143005781810151838201526020016142e8565b50505050905090810190601f16801561432d5780820380516001836020036101000a031916815260200191505b506040525050509050826001600160a01b0316632289511867de0b6b3a764000008a8a858b8b8b6040518863ffffffff1660e01b81526004018080602001806020018060200185815260200184810384528a8a828181526020019250808284376000838201819052601f909101601f191690920186810385528a5181528a51602091820193918c019250908190849084905b838110156143d75781810151838201526020016143bf565b50505050905090810190601f1680156144045780820380516001836020036101000a031916815260200191505b508481038252868152602001878780828437600081840152601f19601f82011690508083019250505099505050505050505050506000604051808303818588803b15801561445157600080fd5b505af1158015614465573d6000803e3d6000fd5b50505050507f889f738426ec48d04c92bdcce1bc71c7aab6ba5296a4e92cc28a58c680b0a4ae888888888867de0b6b3a7640000087426040518080602001806020018781526020018681526020018060200185815260200184810384528c8c82818152602001925080828437600083820152601f01601f191690910185810384528a815260200190508a8a808284376000838201819052601f909101601f19169092018681038452885181528851602091820193918a019250908190849084905b8381101561453e578181015183820152602001614526565b50505050905090810190601f16801561456b5780820380516001836020036101000a031916815260200191505b509b50505050505050505050505060405180910390a1505050505050505056fe726f636b657444414f4e6f64655472757374656453657474696e67734d696e69706f6f6c53746f7261676520737461746520616c726561647920696e697469616c697365644e6f7420656e6f7567682074696d65206861732070617373656420746f207374616b65546865206d696e69706f6f6c2063616e206f6e6c79206265207363727562626564207768696c6520696e207072656c61756e6368546865206d696e69706f6f6c2063616e206f6e6c79206265636f6d6520776974686472617761626c65207768696c65207374616b696e67546865206e6f6465206465706f7369742068617320616c7265616479206265656e2061737369676e65644e6f6e2d6f776e6572206d75737420776169742031342064617973206166746572207769746864726177616c20746f20646973747269627574652062616c616e63654d696e69706f6f6c2062616c616e6365206d7573742068617665206265656e206469737472696275746564206174206c65617374206f6e63654e6f20616d6f756e74206f6620746865206e6f6465206465706f73697420697320617661696c61626c6520666f7220726566756e64546865206e6f6465206465706f7369742063616e206f6e6c792062652061737369676e6564207768696c6520696e697469616c6973656442616c616e6365206d7573742062652067726561746572207468616e203420455448546865206d696e69706f6f6c2063616e206f6e6c7920626567696e207374616b696e67207768696c6520696e207072656c61756e63684e6f6465204554482062616c616e636520776173206e6f74207375636365737366756c6c79207472616e7366657272656420746f206e6f6465206f70657261746f72496e73756666696369656e742062616c616e636520746f20626567696e207374616b696e6745544820726566756e6420616d6f756e7420776173206e6f74207375636365737366756c6c79207472616e7366657272656420746f206e6f6465206f70657261746f725468652075736572206465706f7369742063616e206f6e6c792062652061737369676e6564207768696c6520696e697469616c697365642c20696e207072656c61756e63682c206f72207374616b696e67726f636b657444414f50726f746f636f6c53657474696e67734d696e69706f6f6c536166654d6174683a206d756c7469706c69636174696f6e206f766572666c6f77546865206d696e69706f6f6c2063616e206f6e6c7920626520646973736f6c766564207768696c6520696e697469616c69736564206f7220696e207072656c61756e63684d696e69706f6f6c206d757374206265207374616b696e67206f7220776974686472617761626c65546865206d696e69706f6f6c2063616e206f6e6c7920626520646973736f6c766564206f6e6365206974206861732074696d6564206f75744d696e69706f6f6c2068617320616c7265616479206265656e2066696e616c697365644d656d6265722068617320616c726561647920766f74656420746f207363727562446973747269627574696f6e206f662074686973206d696e69706f6f6c27732062616c616e6365206973206f6e20636f6f6c646f776e42616c616e6365206d7573742062652067726561746572207468616e20313620455448496e73756666696369656e742062616c616e636520746f207072652d7374616b65546865206d696e69706f6f6c2063616e206f6e6c7920626520636c6f736564207768696c6520646973736f6c7665645468652075736572206465706f7369742068617320616c7265616479206265656e2061737369676e6564a26469706673582212207e3d56924a584ea1b25250d2fed9cefd4801e3eb6ef20f120e61df2b32b8e2f964736f6c63430007060033
Deployed Bytecode
0x6080604052600436106101e35760003560e01c80637476a6c311610102578063d91eda6211610095578063e715013411610064578063e7150134146105ce578063e7e04aba146105e3578063f7ae36d1146105f8578063fbc02c4214610675576101e3565b8063d91eda6214610553578063dd0ddfcf14610568578063e117d192146105a4578063e67cd5b0146105b9576101e3565b8063a129a5ee116100d1578063a129a5ee146104e1578063a2940a90146104f6578063a43992631461050b578063d45dc62814610520576101e3565b80637476a6c3146103e057806374ca6bf2146104a25780637943da69146104b75780639ed27809146104cc576101e3565b80634e69d5601161017a57806368f449b21161014957806368f449b21461035c5780636934f90d1461037157806369c089ea1461038657806370dabc9e146103af576101e3565b80634e69d560146102c157806354fd4d50146102f7578063590e1ae3146103225780635abd37e414610337576101e3565b80633bef8a3a116101b65780633bef8a3a1461027a5780633e0a56b01461028f57806343d726d6146102a457806348146113146102b9576101e3565b8063042e5d4c146101e857806319f18b1f146101ff5780631a69d18f1461023b5780632da25de314610265575b600080fd5b3480156101f457600080fd5b506101fd61068a565b005b34801561020b57600080fd5b506102296004803603602081101561022257600080fd5b50356108a6565b60408051918252519081900360200190f35b34801561024757600080fd5b506102296004803603602081101561025e57600080fd5b50356108c3565b34801561027157600080fd5b506101fd610a65565b34801561028657600080fd5b506101fd610b32565b34801561029b57600080fd5b50610229610d18565b3480156102b057600080fd5b506101fd610d1f565b6101fd611163565b3480156102cd57600080fd5b506102d66113d5565b604051808260048111156102e657fe5b815260200191505060405180910390f35b34801561030357600080fd5b5061030c6113e5565b6040805160ff9092168252519081900360200190f35b34801561032e57600080fd5b506101fd6113ea565b34801561034357600080fd5b5061034c6115b5565b604051808260038111156102e657fe5b34801561036857600080fd5b506102296115be565b34801561037d57600080fd5b506101fd6115c4565b34801561039257600080fd5b5061039b6118cd565b604080519115158252519081900360200190f35b3480156103bb57600080fd5b506103c46118d6565b604080516001600160a01b039092168252519081900360200190f35b6101fd600480360360608110156103f657600080fd5b81019060208101813564010000000081111561041157600080fd5b82018360208201111561042357600080fd5b8035906020019184600183028401116401000000008311171561044557600080fd5b91939092909160208101903564010000000081111561046357600080fd5b82018360208201111561047557600080fd5b8035906020019184600183028401116401000000008311171561049757600080fd5b9193509150356118ea565b3480156104ae57600080fd5b50610229611b2d565b3480156104c357600080fd5b506101fd611b33565b3480156104d857600080fd5b5061039b611e09565b3480156104ed57600080fd5b5061039b611f37565b34801561050257600080fd5b50610229611f59565b34801561051757600080fd5b506101fd611f5f565b34801561052c57600080fd5b5061039b6004803603602081101561054357600080fd5b50356001600160a01b0316612196565b34801561055f57600080fd5b5061039b6121b4565b34801561057457600080fd5b506101fd6004803603604081101561058b57600080fd5b5080356001600160a01b0316906020013560ff166121bc565b3480156105b057600080fd5b506101fd612538565b3480156105c557600080fd5b50610229612bc5565b3480156105da57600080fd5b50610229612bcb565b3480156105ef57600080fd5b50610229612bd1565b34801561060457600080fd5b506101fd6004803603604081101561061b57600080fd5b81019060208101813564010000000081111561063657600080fd5b82018360208201111561064857600080fd5b8035906020019184600183028401116401000000008311171561066a57600080fd5b919350915035612bd7565b34801561068157600080fd5b5061022961339d565b6002600f54600160a01b900460ff1660028111156106a457fe5b146106f6576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b600454339061010090046001600160a01b03168114806107bb575060005460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b15801561078057600080fd5b505afa158015610794573d6000803e3d6000fd5b505050506040513d60208110156107aa57600080fd5b50516001600160a01b038281169116145b61080c576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6003600054600160a01b900460ff16600481111561082657fe5b14610878576040805162461bcd60e51b815260206004820152601d60248201527f4d696e69706f6f6c206d75737420626520776974686472617761626c65000000604482015290519081900360640190fd5b600061088f600854476133a390919063ffffffff16565b905061089a81613405565b6108a2613530565b5050565b60006108bb6108b4836108c3565b83906133a3565b90505b919050565b600a546000906801bc16d674ec80000090838111156108e7576000925050506108be565b8184111561097f5760006108fb85846133a3565b9050600061090a826002613836565b90506000610935670de0b6b3a764000061092f6005548561389d90919063ffffffff16565b90613836565b9050600360045460ff16600381111561094a57fe5b141561096b5761096461095d84836133a3565b85906138fd565b935061097b565b61097861095d83836133a3565b93505b5050505b600061098b85836133a3565b600f54604080517fa1e8487d00000000000000000000000000000000000000000000000000000000815230600482015290519293506000926001600160a01b039092169163a1e8487d91602480820192602092909190829003018186803b1580156109f557600080fd5b505afa158015610a09573d6000803e3d6000fd5b505050506040513d6020811015610a1f57600080fd5b505190508015610a5c576000610a41670de0b6b3a764000061092f858561389d565b905082811115610a4e5750815b610a5883826133a3565b9250505b50949350505050565b6002600f54600160a01b900460ff166002811115610a7f57fe5b14610ad1576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b600060095411610b28576040805162461bcd60e51b815260206004820152601360248201527f4e6f2062616c616e636520746f20736c61736800000000000000000000000000604482015290519081900360640190fd5b610b30613957565b565b6002600f54600160a01b900460ff166002811115610b4c57fe5b14610b9e576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60008054600160a01b900460ff166004811115610bb757fe5b1480610bda57506001600054600160a01b900460ff166004811115610bd857fe5b145b610c155760405162461bcd60e51b81526004018080602001828103825260448152602001806149056044913960600191505060405180910390fd5b6000610c386040518060600160405280602181526020016148c360219139613a31565b90506001600054600160a01b900460ff166004811115610c5457fe5b148015610cd25750806001600160a01b031663d42916c26040518163ffffffff1660e01b815260040160206040518083038186803b158015610c9557600080fd5b505afa158015610ca9573d6000803e3d6000fd5b505050506040513d6020811015610cbf57600080fd5b5051600254610ccf9042906133a3565b10155b610d0d5760405162461bcd60e51b81526004018080602001828103825260388152602001806149716038913960400191505060405180910390fd5b610d15613ba9565b50565b6002545b90565b600454339061010090046001600160a01b03168114610d85576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff166002811115610d9f57fe5b14610df1576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6004600054600160a01b900460ff166004811115610e0b57fe5b14610e475760405162461bcd60e51b815260040180806020018281038252602f815260200180614a67602f913960400191505060405180910390fd5b6000610e606008546006546138fd90919063ffffffff16565b90508015610fe657600060068190556008819055805460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b158015610ee257600080fd5b505afa158015610ef6573d6000803e3d6000fd5b505050506040513d6020811015610f0c57600080fd5b50516040519091506000906001600160a01b0383169084908381818185875af1925050503d8060008114610f5c576040519150601f19603f3d011682016040523d82523d6000602084013e610f61565b606091505b5050905080610fa15760405162461bcd60e51b81526004018080602001828103825260428152602001806147c86042913960600191505060405180910390fd5b6040805184815242602082015281516001600160a01b038516927fd5ca65e1ec4f4864fea7b9c5cb1ec3087a0dbf9c74641db3f6458edf445c4051928290030190a250505b600360045460ff166003811115610ff957fe5b14156110bf57600061103f6040518060400160405280601481526020017f726f636b657444414f4e6f646554727573746564000000000000000000000000815250613a31565b9050806001600160a01b03166354d28878600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156110a557600080fd5b505af11580156110b9573d6000803e3d6000fd5b50505050505b60006110ff6040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b9050806001600160a01b0316637bb40aaf6040518163ffffffff1660e01b8152600401600060405180830381600087803b15801561113c57600080fd5b505af1158015611150573d6000803e3d6000fd5b5050600e546001600160a01b0316915050ff5b6040518060400160405280601181526020017f726f636b65744465706f736974506f6f6c000000000000000000000000000000815250336111a382613a31565b6001600160a01b0316816001600160a01b031614611208576040805162461bcd60e51b815260206004820152601c60248201527f496e76616c6964206f72206f7574646174656420636f6e747261637400000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff16600281111561122257fe5b14611274576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60008054600160a01b900460ff16600481111561128d57fe5b101580156112b357506002600054600160a01b900460ff1660048111156112b057fe5b11155b6112ee5760405162461bcd60e51b81526004018080602001828103825260518152602001806148726051913960600191505060405180910390fd5b600b541561132d5760405162461bcd60e51b815260040180806020018281038252602a815260200180614a96602a913960400191505060405180910390fd5b60008054600160a01b900460ff16600481111561134657fe5b1415611356576113566001613d64565b34600a5542600b55600160045460ff16600381111561137157fe5b14156113985760065461138490346133a3565b60065560085461139490346138fd565b6008555b60408051348152426020820152815133927fef51b4c870b8b0100eae2072e91db01222a303072af3728e58c9d4d2da33127f928290030190a25050565b600054600160a01b900460ff1690565b600281565b600454339061010090046001600160a01b03168114806114af575060005460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b15801561147457600080fd5b505afa158015611488573d6000803e3d6000fd5b505050506040513d602081101561149e57600080fd5b50516001600160a01b038281169116145b611500576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff16600281111561151a57fe5b1461156c576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6000600854116115ad5760405162461bcd60e51b81526004018080602001828103825260358152602001806147046035913960400191505060405180910390fd5b610d15613df4565b60045460ff1690565b60115490565b6040518060400160405280601481526020017f726f636b65744d696e69706f6f6c5374617475730000000000000000000000008152503361160482613a31565b6001600160a01b0316816001600160a01b031614611669576040805162461bcd60e51b815260206004820152601c60248201527f496e76616c6964206f72206f7574646174656420636f6e747261637400000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff16600281111561168357fe5b146116d5576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60006117156040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b90506002600054600160a01b900460ff16600481111561173157fe5b1461176d5760405162461bcd60e51b81526004018080602001828103825260378152602001806146286037913960400191505060405180910390fd5b6117776003613d64565b600b5461184c5760006117be6040518060400160405280601381526020017f726f636b65744d696e69706f6f6c517565756500000000000000000000000000815250613a31565b600480546040517fde1bdc8f0000000000000000000000000000000000000000000000000000000081529293506001600160a01b0384169263de1bdc8f9260ff90921691018082600381111561181057fe5b8152602001915050600060405180830381600087803b15801561183257600080fd5b505af1158015611846573d6000803e3d6000fd5b50505050505b806001600160a01b03166375b59c7f600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156118b057600080fd5b505af11580156118c4573d6000803e3d6000fd5b50505050505050565b60075460ff1690565b60045461010090046001600160a01b031690565b6040518060400160405280601181526020017f726f636b65744e6f64654465706f7369740000000000000000000000000000008152503361192a82613a31565b6001600160a01b0316816001600160a01b03161461198f576040805162461bcd60e51b815260206004820152601c60248201527f496e76616c6964206f72206f7574646174656420636f6e747261637400000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff1660028111156119a957fe5b146119fb576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b60008054600160a01b900460ff166004811115611a1457fe5b14611a505760405162461bcd60e51b81526004018080602001828103825260378152602001806147396037913960400191505060405180910390fd5b60075460ff1615611a925760405162461bcd60e51b815260040180806020018281038252602a81526020018061465f602a913960400191505060405180910390fd5b600160045460ff166003811115611aa557fe5b1415611ab557611ab56001613d64565b346006819055600780547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0016600117905560408051918252426020830152805133927fef51b4c870b8b0100eae2072e91db01222a303072af3728e58c9d4d2da33127f92908290030190a26118c48787878787613f75565b60065490565b6002600f54600160a01b900460ff166002811115611b4d57fe5b14611b9f576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6002600054600160a01b900460ff166004811115611bb957fe5b1480611bdc57506003600054600160a01b900460ff166004811115611bda57fe5b145b611c175760405162461bcd60e51b81526004018080602001828103825260288152602001806149496028913960400191505060405180910390fd5b6000611c2e600854476133a390919063ffffffff16565b6000805460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526101009092046001600160a01b0390811693830193909352519495509293911691635b49ff62916024808301926020929190829003018186803b158015611ca357600080fd5b505afa158015611cb7573d6000803e3d6000fd5b505050506040513d6020811015611ccd57600080fd5b505160045490915061010090046001600160a01b03163314801590611cfb5750336001600160a01b03821614155b15611e00576002600054600160a01b900460ff166004811115611d1a57fe5b1415611d6c5767de0b6b3a76400000821015611d675760405162461bcd60e51b8152600401808060200182810382526023815260200180614a236023913960400191505060405180910390fd5b611e00565b600254611d7c90621275006138fd565b4211611db95760405162461bcd60e51b81526004018080602001828103825260428152602001806146896042913960600191505060405180910390fd5b673782dace9d900000471015611e005760405162461bcd60e51b81526004018080602001828103825260228152602001806147706022913960400191505060405180910390fd5b6108a282613405565b60006002600f54600160a01b900460ff166002811115611e2557fe5b14611e77576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6001600054600160a01b900460ff166004811115611e9157fe5b14611e9e57506000610d1c565b6000611ec160405180606001604052806024815260200161458c60249139613a31565b90506000816001600160a01b031663f0245dc86040518163ffffffff1660e01b815260040160206040518083038186803b158015611efe57600080fd5b505afa158015611f12573d6000803e3d6000fd5b505050506040513d6020811015611f2857600080fd5b50516002540142119250505090565b600f547501000000000000000000000000000000000000000000900460ff1690565b600b5490565b6002600f54600160a01b900460ff166002811115611f7957fe5b14611fcb576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b600454339061010090046001600160a01b0316811480612090575060005460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251921691635b49ff6291602480820192602092909190829003018186803b15801561205557600080fd5b505afa158015612069573d6000803e3d6000fd5b505050506040513d602081101561207f57600080fd5b50516001600160a01b038281169116145b6120e1576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6003600054600160a01b900460ff1660048111156120fb57fe5b1461214d576040805162461bcd60e51b815260206004820152601d60248201527f4d696e69706f6f6c206d75737420626520776974686472617761626c65000000604482015290519081900360640190fd5b60006003541161218e5760405162461bcd60e51b81526004018080602001828103825260398152602001806146cb6039913960400191505060405180910390fd5b610d15613530565b6001600160a01b031660009081526010602052604090205460ff1690565b600b54151590565b6001600f54600160a01b900460ff1660028111156121d657fe5b146122125760405162461bcd60e51b81526004018080602001828103825260218152602001806145b06021913960400191505060405180910390fd5b6001600160a01b03821661226d576040805162461bcd60e51b815260206004820152601460248201527f496e76616c6964206e6f64652061646472657373000000000000000000000000604482015290519081900360640190fd5b600081600381111561227b57fe5b14156122ce576040805162461bcd60e51b815260206004820152601460248201527f496e76616c6964206465706f7369742074797065000000000000000000000000604482015290519081900360640190fd5b600061230e6040518060400160405280601181526020017f726f636b65744e6574776f726b46656573000000000000000000000000000000815250613a31565b600080547fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff1690554360019081554260025560048054929350849290917fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff009091169083600381111561237c57fe5b021790555082600460016101000a8154816001600160a01b0302191690836001600160a01b03160217905550806001600160a01b031663e71501346040518163ffffffff1660e01b815260040160206040518083038186803b1580156123e157600080fd5b505afa1580156123f5573d6000803e3d6000fd5b505050506040513d602081101561240b57600080fd5b505160055560408051808201909152600f81527f726f636b6574546f6b656e524554480000000000000000000000000000000000602082015261244d90613a31565b600e80547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b039290921691909117905560408051808201909152601581527f726f636b65744d696e69706f6f6c50656e616c7479000000000000000000000060208201526124c290613a31565b600f80547fffffffffffffffffffffffff0000000000000000000000000000000000000000166001600160a01b0392909216919091177fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff1674020000000000000000000000000000000000000000179055505050565b6002600f54600160a01b900460ff16600281111561255257fe5b146125a4576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6001600054600160a01b900460ff1660048111156125be57fe5b146125fa5760405162461bcd60e51b81526004018080602001828103825260348152602001806145f46034913960400191505060405180910390fd5b600061263a6040518060400160405280601481526020017f726f636b657444414f4e6f646554727573746564000000000000000000000000815250613a31565b9050600061265f60405180606001604052806024815260200161458c60249139613a31565b9050816001600160a01b0316635dc33bdd336040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060206040518083038186803b1580156126ae57600080fd5b505afa1580156126c2573d6000803e3d6000fd5b505050506040513d60208110156126d857600080fd5b505161272b576040805162461bcd60e51b815260206004820152601460248201527f4e6f7420612074727573746564206d656d626572000000000000000000000000604482015290519081900360640190fd5b3360009081526010602052604090205460ff161561277a5760405162461bcd60e51b81526004018080602001828103825260218152602001806149cc6021913960400191505060405180910390fd5b3360008181526010602090815260409182902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00166001179055815142815291517fc038496c9b2fce7ae180c60886062197d0411e3c5d249053f188423280778a839281900390910190a260006128e8670de0b6b3a764000061092f846001600160a01b0316636e86e7fe6040518163ffffffff1660e01b815260040160206040518083038186803b15801561283157600080fd5b505afa158015612845573d6000803e3d6000fd5b505050506040513d602081101561285b57600080fd5b5051604080517f997072f700000000000000000000000000000000000000000000000000000000815290516001600160a01b0389169163997072f7916004808301926020929190829003018186803b1580156128b657600080fd5b505afa1580156128ca573d6000803e3d6000fd5b505050506040513d60208110156128e057600080fd5b50519061389d565b90508061290160016011546138fd90919063ffffffff16565b1115612bae5761290f613ba9565b816001600160a01b031663c4f502526040518163ffffffff1660e01b815260040160206040518083038186803b15801561294857600080fd5b505afa15801561295c573d6000803e3d6000fd5b505050506040513d602081101561297257600080fd5b505115612b765760006129b96040518060400160405280601181526020017f726f636b65744e6f64655374616b696e67000000000000000000000000000000815250613a31565b905060006129fb6040518060400160405280601d81526020017f726f636b657444414f50726f746f636f6c53657474696e67734e6f6465000000815250613a31565b90506000612a206040518060600160405280602181526020016148c360219139613a31565b9050826001600160a01b031663245395a6600460019054906101000a90046001600160a01b0316612b14670de0b6b3a764000061092f876001600160a01b0316636fdbe57b6040518163ffffffff1660e01b815260040160206040518083038186803b158015612a8f57600080fd5b505afa158015612aa3573d6000803e3d6000fd5b505050506040513d6020811015612ab957600080fd5b5051604080517f162adbfd00000000000000000000000000000000000000000000000000000000815290516001600160a01b038a169163162adbfd916004808301926020929190829003018186803b1580156128b657600080fd5b6040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b158015612b5a57600080fd5b505af1158015612b6e573d6000803e3d6000fd5b505050505050505b6040805142815290517fac58888447082d81defc760f4bd30b6196d9309777e161bce72c280a12a6ea689181900360200190a1612bc0565b601154612bbc9060016138fd565b6011555b505050565b60015490565b60055490565b600a5490565b600454339061010090046001600160a01b03168114612c3d576040805162461bcd60e51b815260206004820152601660248201527f496e76616c6964206d696e69706f6f6c206f776e657200000000000000000000604482015290519081900360640190fd5b6002600f54600160a01b900460ff166002811115612c5757fe5b14612ca9576040805162461bcd60e51b815260206004820152601d60248201527f53746f72616765207374617465206e6f7420696e697469616c69736564000000604482015290519081900360640190fd5b6000612ccc60405180606001604052806024815260200161458c60249139613a31565b90506000612cf16040518060600160405280602181526020016148c360219139613a31565b90506000826001600160a01b031663f0245dc86040518163ffffffff1660e01b815260040160206040518083038186803b158015612d2e57600080fd5b505afa158015612d42573d6000803e3d6000fd5b505050506040513d6020811015612d5857600080fd5b505190506001600054600160a01b900460ff166004811115612d7657fe5b14612db25760405162461bcd60e51b81526004018080602001828103825260368152602001806147926036913960400191505060405180910390fd5b80600254014211612df45760405162461bcd60e51b81526004018080602001828103825260238152602001806145d16023913960400191505060405180910390fd5b612dfe6002613d64565b6000612e3e6040518060400160405280600d81526020017f6361737065724465706f73697400000000000000000000000000000000000000815250613a31565b90506000612e806040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b90506000612efb67de0b6b3a76400000866001600160a01b03166308e50d386040518163ffffffff1660e01b815260040160206040518083038186803b158015612ec957600080fd5b505afa158015612edd573d6000803e3d6000fd5b505050506040513d6020811015612ef357600080fd5b5051906133a3565b905080471015612f3c5760405162461bcd60e51b815260040180806020018281038252602581526020018061480a6025913960400191505060405180910390fd5b6000826001600160a01b0316633eb535e9306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060006040518083038186803b158015612f8b57600080fd5b505afa158015612f9f573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f191682016040526020811015612fc857600080fd5b8101908080516040519392919084640100000000821115612fe857600080fd5b908301906020820185811115612ffd57600080fd5b825164010000000081118282018810171561301757600080fd5b82525081516020918201929091019080838360005b8381101561304457818101518382015260200161302c565b50505050905090810190601f1680156130715780820380516001836020036101000a031916815260200191505b506040525050509050836001600160a01b031663228951188383866001600160a01b0316632cb76c37306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060006040518083038186803b1580156130d857600080fd5b505afa1580156130ec573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052602081101561311557600080fd5b810190808051604051939291908464010000000082111561313557600080fd5b90830190602082018581111561314a57600080fd5b825164010000000081118282018810171561316457600080fd5b82525081516020918201929091019080838360005b83811015613191578181015183820152602001613179565b50505050905090810190601f1680156131be5780820380516001836020036101000a031916815260200191505b506040525050508f8f8f6040518763ffffffff1660e01b815260040180806020018060200180602001858152602001848103845289818151815260200191508051906020019080838360005b8381101561322257818101518382015260200161320a565b50505050905090810190601f16801561324f5780820380516001836020036101000a031916815260200191505b5084810383528851815288516020918201918a019080838360005b8381101561328257818101518382015260200161326a565b50505050905090810190601f1680156132af5780820380516001836020036101000a031916815260200191505b508481038252868152602001878780828437600081840152601f19601f820116905080830192505050985050505050505050506000604051808303818588803b1580156132fb57600080fd5b505af115801561330f573d6000803e3d6000fd5b5050505050826001600160a01b0316639907288c600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b15801561337857600080fd5b505af115801561338c573d6000803e3d6000fd5b505050505050505050505050505050565b60085490565b6000828211156133fa576040805162461bcd60e51b815260206004820152601e60248201527f536166654d6174683a207375627472616374696f6e206f766572666c6f770000604482015290519081900360640190fd5b508082035b92915050565b60646003540143116134485760405162461bcd60e51b81526004018080602001828103825260368152602001806149ed6036913960400191505060405180910390fd5b6000600a548210156134715760035461346c57600a5461346890836133a3565b6009555b61347d565b61347a826108c3565b90505b600061348983836133a3565b60085490915061349990836138fd565b60085580156134de57600e546040516001600160a01b039091169082156108fc029083906000818181858888f193505050501580156134dc573d6000803e3d6000fd5b505b436003556040805183815260208101839052808201859052426060820152905133917f3422b68c7062367a3ae581f8bf64158ddb63f02294a0abe7f32491787076f1b7919081900360800190a2505050565b60006135706040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b600f549091507501000000000000000000000000000000000000000000900460ff16156135ce5760405162461bcd60e51b81526004018080602001828103825260238152602001806149a96023913960400191505060405180910390fd5b600954156135de576135de613957565b600854156135ee576135ee613df4565b471561362f57600e546040516001600160a01b03909116904780156108fc02916000818181858888f1935050505015801561362d573d6000803e3d6000fd5b505b600e60009054906101000a90046001600160a01b03166001600160a01b031663188e0dc66040518163ffffffff1660e01b8152600401600060405180830381600087803b15801561367f57600080fd5b505af1158015613693573d6000803e3d6000fd5b50505050806001600160a01b031663b04e8868600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156136fb57600080fd5b505af115801561370f573d6000803e3d6000fd5b506003925061371c915050565b60045460ff16600381111561372d57fe5b14156137f35760006137736040518060400160405280601481526020017f726f636b657444414f4e6f646554727573746564000000000000000000000000815250613a31565b9050806001600160a01b03166354d28878600460019054906101000a90046001600160a01b03166040518263ffffffff1660e01b815260040180826001600160a01b03168152602001915050600060405180830381600087803b1580156137d957600080fd5b505af11580156137ed573d6000803e3d6000fd5b50505050505b50600f80547fffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffffff167501000000000000000000000000000000000000000000179055565b600080821161388c576040805162461bcd60e51b815260206004820152601a60248201527f536166654d6174683a206469766973696f6e206279207a65726f000000000000604482015290519081900360640190fd5b81838161389557fe5b049392505050565b6000826138ac575060006133ff565b828202828482816138b957fe5b04146138f65760405162461bcd60e51b81526004018080602001828103825260218152602001806148e46021913960400191505060405180910390fd5b9392505050565b6000828201838110156138f6576040805162461bcd60e51b815260206004820152601b60248201527f536166654d6174683a206164646974696f6e206f766572666c6f770000000000604482015290519081900360640190fd5b60006139976040518060400160405280601181526020017f726f636b65744e6f64655374616b696e67000000000000000000000000000000815250613a31565b6009805460009182905560048054604080517f245395a60000000000000000000000000000000000000000000000000000000081526001600160a01b03610100909304831693810193909352602483018490525194955091939185169263245395a69260448084019382900301818387803b158015613a1557600080fd5b505af1158015613a29573d6000803e3d6000fd5b505050505050565b60008060008054906101000a90046001600160a01b03166001600160a01b03166321f8a7218460405160200180807f636f6e74726163742e616464726573730000000000000000000000000000000081525060100182805190602001908083835b60208310613ab15780518252601f199092019160209182019101613a92565b6001836020036101000a038019825116818451168082178552505050505050905001915050604051602081830303815290604052805190602001206040518263ffffffff1660e01b81526004018082815260200191505060206040518083038186803b158015613b2057600080fd5b505afa158015613b34573d6000803e3d6000fd5b505050506040513d6020811015613b4a57600080fd5b505190506001600160a01b0381166108bb576040805162461bcd60e51b815260206004820152601260248201527f436f6e7472616374206e6f7420666f756e640000000000000000000000000000604482015290519081900360640190fd5b6000613be96040518060400160405280601181526020017f726f636b65744465706f736974506f6f6c000000000000000000000000000000815250613a31565b90506000613c2b6040518060400160405280601381526020017f726f636b65744d696e69706f6f6c517565756500000000000000000000000000815250613a31565b9050613c376004613d64565b600a5415613cf5576000600a5490506000600a819055506000600b81905550826001600160a01b03166372f5158d826040518263ffffffff1660e01b81526004016000604051808303818588803b158015613c9157600080fd5b505af1158015613ca5573d6000803e3d6000fd5b50506040805185815242602082015281516001600160a01b03891695507fd5ca65e1ec4f4864fea7b9c5cb1ec3087a0dbf9c74641db3f6458edf445c40519450908190039091019150a2506108a2565b600480546040517fde1bdc8f0000000000000000000000000000000000000000000000000000000081526001600160a01b0384169263de1bdc8f9260ff16910180826003811115613d4257fe5b8152602001915050600060405180830381600087803b158015613a1557600080fd5b600080548291907fffffffffffffffffffffff00ffffffffffffffffffffffffffffffffffffffff16600160a01b836004811115613d9e57fe5b02179055504360015542600255806004811115613db757fe5b60ff167f26725881c2a4290b02cd153d6599fd484f0d4e6062c361e740fbbe39e7ad6142426040518082815260200191505060405180910390a250565b60088054600091829055815460048054604080517f5b49ff620000000000000000000000000000000000000000000000000000000081526001600160a01b0361010090930483169381019390935251939493921691635b49ff6291602480820192602092909190829003018186803b158015613e6f57600080fd5b505afa158015613e83573d6000803e3d6000fd5b505050506040513d6020811015613e9957600080fd5b50516040519091506000906001600160a01b0383169084908381818185875af1925050503d8060008114613ee9576040519150601f19603f3d011682016040523d82523d6000602084013e613eee565b606091505b5050905080613f2e5760405162461bcd60e51b815260040180806020018281038252604381526020018061482f6043913960600191505060405180910390fd5b6040805184815242602082015281516001600160a01b038516927fd5ca65e1ec4f4864fea7b9c5cb1ec3087a0dbf9c74641db3f6458edf445c4051928290030190a2505050565b6000613fb56040518060400160405280600d81526020017f6361737065724465706f73697400000000000000000000000000000000000000815250613a31565b90506000613ff76040518060400160405280601581526020017f726f636b65744d696e69706f6f6c4d616e616765720000000000000000000000815250613a31565b905067de0b6b3a764000004710156140405760405162461bcd60e51b8152600401808060200182810382526021815260200180614a466021913960400191505060405180910390fd5b6040517fcf6a4763000000000000000000000000000000000000000000000000000000008152602060048201908152602482018890526000916001600160a01b0384169163cf6a4763918b918b918190604401848480828437600083820152604051601f909101601f191690920195506020945090925050508083038186803b1580156140cc57600080fd5b505afa1580156140e0573d6000803e3d6000fd5b505050506040513d60208110156140f657600080fd5b50516001600160a01b031614614153576040805162461bcd60e51b815260206004820152601a60248201527f56616c696461746f72207075626b657920697320696e20757365000000000000604482015290519081900360640190fd5b6040517f2c7f64d4000000000000000000000000000000000000000000000000000000008152602060048201908152602482018890526001600160a01b03831691632c7f64d4918a918a91908190604401848480828437600081840152601f19601f8201169050808301925050509350505050600060405180830381600087803b1580156141e057600080fd5b505af11580156141f4573d6000803e3d6000fd5b505050506000816001600160a01b0316632cb76c37306040518263ffffffff1660e01b815260040180826001600160a01b0316815260200191505060006040518083038186803b15801561424757600080fd5b505afa15801561425b573d6000803e3d6000fd5b505050506040513d6000823e601f3d908101601f19168201604052602081101561428457600080fd5b81019080805160405193929190846401000000008211156142a457600080fd5b9083019060208201858111156142b957600080fd5b82516401000000008111828201881017156142d357600080fd5b82525081516020918201929091019080838360005b838110156143005781810151838201526020016142e8565b50505050905090810190601f16801561432d5780820380516001836020036101000a031916815260200191505b506040525050509050826001600160a01b0316632289511867de0b6b3a764000008a8a858b8b8b6040518863ffffffff1660e01b81526004018080602001806020018060200185815260200184810384528a8a828181526020019250808284376000838201819052601f909101601f191690920186810385528a5181528a51602091820193918c019250908190849084905b838110156143d75781810151838201526020016143bf565b50505050905090810190601f1680156144045780820380516001836020036101000a031916815260200191505b508481038252868152602001878780828437600081840152601f19601f82011690508083019250505099505050505050505050506000604051808303818588803b15801561445157600080fd5b505af1158015614465573d6000803e3d6000fd5b50505050507f889f738426ec48d04c92bdcce1bc71c7aab6ba5296a4e92cc28a58c680b0a4ae888888888867de0b6b3a7640000087426040518080602001806020018781526020018681526020018060200185815260200184810384528c8c82818152602001925080828437600083820152601f01601f191690910185810384528a815260200190508a8a808284376000838201819052601f909101601f19169092018681038452885181528851602091820193918a019250908190849084905b8381101561453e578181015183820152602001614526565b50505050905090810190601f16801561456b5780820380516001836020036101000a031916815260200191505b509b50505050505050505050505060405180910390a1505050505050505056fe726f636b657444414f4e6f64655472757374656453657474696e67734d696e69706f6f6c53746f7261676520737461746520616c726561647920696e697469616c697365644e6f7420656e6f7567682074696d65206861732070617373656420746f207374616b65546865206d696e69706f6f6c2063616e206f6e6c79206265207363727562626564207768696c6520696e207072656c61756e6368546865206d696e69706f6f6c2063616e206f6e6c79206265636f6d6520776974686472617761626c65207768696c65207374616b696e67546865206e6f6465206465706f7369742068617320616c7265616479206265656e2061737369676e65644e6f6e2d6f776e6572206d75737420776169742031342064617973206166746572207769746864726177616c20746f20646973747269627574652062616c616e63654d696e69706f6f6c2062616c616e6365206d7573742068617665206265656e206469737472696275746564206174206c65617374206f6e63654e6f20616d6f756e74206f6620746865206e6f6465206465706f73697420697320617661696c61626c6520666f7220726566756e64546865206e6f6465206465706f7369742063616e206f6e6c792062652061737369676e6564207768696c6520696e697469616c6973656442616c616e6365206d7573742062652067726561746572207468616e203420455448546865206d696e69706f6f6c2063616e206f6e6c7920626567696e207374616b696e67207768696c6520696e207072656c61756e63684e6f6465204554482062616c616e636520776173206e6f74207375636365737366756c6c79207472616e7366657272656420746f206e6f6465206f70657261746f72496e73756666696369656e742062616c616e636520746f20626567696e207374616b696e6745544820726566756e6420616d6f756e7420776173206e6f74207375636365737366756c6c79207472616e7366657272656420746f206e6f6465206f70657261746f725468652075736572206465706f7369742063616e206f6e6c792062652061737369676e6564207768696c6520696e697469616c697365642c20696e207072656c61756e63682c206f72207374616b696e67726f636b657444414f50726f746f636f6c53657474696e67734d696e69706f6f6c536166654d6174683a206d756c7469706c69636174696f6e206f766572666c6f77546865206d696e69706f6f6c2063616e206f6e6c7920626520646973736f6c766564207768696c6520696e697469616c69736564206f7220696e207072656c61756e63684d696e69706f6f6c206d757374206265207374616b696e67206f7220776974686472617761626c65546865206d696e69706f6f6c2063616e206f6e6c7920626520646973736f6c766564206f6e6365206974206861732074696d6564206f75744d696e69706f6f6c2068617320616c7265616479206265656e2066696e616c697365644d656d6265722068617320616c726561647920766f74656420746f207363727562446973747269627574696f6e206f662074686973206d696e69706f6f6c27732062616c616e6365206973206f6e20636f6f6c646f776e42616c616e6365206d7573742062652067726561746572207468616e20313620455448496e73756666696369656e742062616c616e636520746f207072652d7374616b65546865206d696e69706f6f6c2063616e206f6e6c7920626520636c6f736564207768696c6520646973736f6c7665645468652075736572206465706f7369742068617320616c7265616479206265656e2061737369676e6564a26469706673582212207e3d56924a584ea1b25250d2fed9cefd4801e3eb6ef20f120e61df2b32b8e2f964736f6c63430007060033
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 34 Chains
| Chain | Token | Portfolio % | Price | Amount | Value |
|---|
Loading...
Loading
Loading...
Loading
Loading...
Loading
[ Download: CSV Export ]
A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.