pragmasolidity 0.7.6;// SPDX-License-Identifier: GPL-3.0-only// Represents the type of depositsenumClaimType {
None,
CLAIMREWARD,
CLAIMDEPOSIT,
CLAIMTOTAL
}
// SPDX-License-Identifier: MITpragmasolidity ^0.7.0;/**
* @dev These functions deal with verification of Merkle trees (hash trees),
*/libraryMerkleProof{
/**
* @dev Returns true if a `leaf` can be proved to be a part of a Merkle tree
* defined by `root`. For this, a `proof` must be provided, containing
* sibling hashes on the branch from the leaf to the root of the tree. Each
* pair of leaves and each pair of pre-images are assumed to be sorted.
*/functionverify(bytes32[] memory proof, bytes32 root, bytes32 leaf) internalpurereturns (bool) {
bytes32 computedHash = leaf;
for (uint256 i =0; i < proof.length; i++) {
bytes32 proofElement = proof[i];
if (computedHash <= proofElement) {
// Hash(current computed hash + current element of the proof)
computedHash =keccak256(abi.encodePacked(computedHash, proofElement));
} else {
// Hash(current element of the proof + current computed hash)
computedHash =keccak256(abi.encodePacked(proofElement, computedHash));
}
}
// Check if the computed hash (root) is equal to the provided rootreturn computedHash == root;
}
}
Contract Source Code
File 12 of 14: SafeMath.sol
// SPDX-License-Identifier: MITpragmasolidity ^0.7.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.
*/librarySafeMath{
/**
* @dev Returns the addition of two unsigned integers, with an overflow flag.
*
* _Available since v3.4._
*/functiontryAdd(uint256 a, uint256 b) internalpurereturns (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._
*/functiontrySub(uint256 a, uint256 b) internalpurereturns (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._
*/functiontryMul(uint256 a, uint256 b) internalpurereturns (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/522if (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._
*/functiontryDiv(uint256 a, uint256 b) internalpurereturns (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._
*/functiontryMod(uint256 a, uint256 b) internalpurereturns (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.
*/functionadd(uint256 a, uint256 b) internalpurereturns (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.
*/functionsub(uint256 a, uint256 b) internalpurereturns (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.
*/functionmul(uint256 a, uint256 b) internalpurereturns (uint256) {
if (a ==0) return0;
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.
*/functiondiv(uint256 a, uint256 b) internalpurereturns (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.
*/functionmod(uint256 a, uint256 b) internalpurereturns (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.
*/functionsub(uint256 a, uint256 b, stringmemory errorMessage) internalpurereturns (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.
*/functiondiv(uint256 a, uint256 b, stringmemory errorMessage) internalpurereturns (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.
*/functionmod(uint256 a, uint256 b, stringmemory errorMessage) internalpurereturns (uint256) {
require(b >0, errorMessage);
return a % b;
}
}
Contract Source Code
File 13 of 14: StafiBase.sol
pragmasolidity 0.7.6;// SPDX-License-Identifier: GPL-3.0-onlyimport"./interfaces/storage/IStafiStorage.sol";
abstractcontractStafiBase{
// Version of the contractuint8public version;
// The main storage contract where primary persistant storage is maintained
IStafiStorage stafiStorage = IStafiStorage(0);
/**
* @dev Throws if called by any sender that doesn't match a network contract
*/modifieronlyLatestNetworkContract() {
require(getBool(keccak256(abi.encodePacked("contract.exists", msg.sender))), "Invalid or outdated network contract");
_;
}
/**
* @dev Throws if called by any sender that doesn't match one of the supplied contract or is the latest version of that contract
*/modifieronlyLatestContract(stringmemory _contractName, address _contractAddress) {
require(_contractAddress == getAddress(keccak256(abi.encodePacked("contract.address", _contractName))), "Invalid or outdated contract");
_;
}
/**
* @dev Throws if called by any sender that isn't a trusted node
*/modifieronlyTrustedNode(address _nodeAddress) {
require(getBool(keccak256(abi.encodePacked("node.trusted", _nodeAddress))), "Invalid trusted node");
_;
}
/**
* @dev Throws if called by any sender that isn't a super node
*/modifieronlySuperNode(address _nodeAddress) {
require(getBool(keccak256(abi.encodePacked("node.super", _nodeAddress))), "Invalid super node");
_;
}
/**
* @dev Throws if called by any sender that isn't a registered staking pool
*/modifieronlyRegisteredStakingPool(address _stakingPoolAddress) {
require(getBool(keccak256(abi.encodePacked("stakingpool.exists", _stakingPoolAddress))), "Invalid staking pool");
_;
}
/**
* @dev Throws if called by any account other than the owner.
*/modifieronlyOwner() {
require(roleHas("owner", msg.sender), "Account is not the owner");
_;
}
/**
* @dev Modifier to scope access to admins
*/modifieronlyAdmin() {
require(roleHas("admin", msg.sender), "Account is not an admin");
_;
}
/**
* @dev Modifier to scope access to admins
*/modifieronlySuperUser() {
require(roleHas("owner", msg.sender) || roleHas("admin", msg.sender), "Account is not a super user");
_;
}
/**
* @dev Reverts if the address doesn't have this role
*/modifieronlyRole(stringmemory _role) {
require(roleHas(_role, msg.sender), "Account does not match the specified role");
_;
}
/// @dev Set the main Storage addressconstructor(address _stafiStorageAddress) {
// Update the contract address
stafiStorage = IStafiStorage(_stafiStorageAddress);
}
/// @dev Get the address of a network contract by namefunctiongetContractAddress(stringmemory _contractName) internalviewreturns (address) {
// Get the current contract addressaddress contractAddress = getAddress(keccak256(abi.encodePacked("contract.address", _contractName)));
// Check itrequire(contractAddress !=address(0x0), "Contract not found");
// Returnreturn contractAddress;
}
/// @dev Get the name of a network contract by addressfunctiongetContractName(address _contractAddress) internalviewreturns (stringmemory) {
// Get the contract namestringmemory contractName = getString(keccak256(abi.encodePacked("contract.name", _contractAddress)));
// Check itrequire(keccak256(abi.encodePacked(contractName)) !=keccak256(abi.encodePacked("")), "Contract not found");
// Returnreturn contractName;
}
/// @dev Storage get methodsfunctiongetAddress(bytes32 _key) internalviewreturns (address) { return stafiStorage.getAddress(_key); }
functiongetUint(bytes32 _key) internalviewreturns (uint256) { return stafiStorage.getUint(_key); }
functiongetString(bytes32 _key) internalviewreturns (stringmemory) { return stafiStorage.getString(_key); }
functiongetBytes(bytes32 _key) internalviewreturns (bytesmemory) { return stafiStorage.getBytes(_key); }
functiongetBool(bytes32 _key) internalviewreturns (bool) { return stafiStorage.getBool(_key); }
functiongetInt(bytes32 _key) internalviewreturns (int256) { return stafiStorage.getInt(_key); }
functiongetBytes32(bytes32 _key) internalviewreturns (bytes32) { return stafiStorage.getBytes32(_key); }
functiongetAddressS(stringmemory _key) internalviewreturns (address) { return stafiStorage.getAddress(keccak256(abi.encodePacked(_key))); }
functiongetUintS(stringmemory _key) internalviewreturns (uint256) { return stafiStorage.getUint(keccak256(abi.encodePacked(_key))); }
functiongetStringS(stringmemory _key) internalviewreturns (stringmemory) { return stafiStorage.getString(keccak256(abi.encodePacked(_key))); }
functiongetBytesS(stringmemory _key) internalviewreturns (bytesmemory) { return stafiStorage.getBytes(keccak256(abi.encodePacked(_key))); }
functiongetBoolS(stringmemory _key) internalviewreturns (bool) { return stafiStorage.getBool(keccak256(abi.encodePacked(_key))); }
functiongetIntS(stringmemory _key) internalviewreturns (int256) { return stafiStorage.getInt(keccak256(abi.encodePacked(_key))); }
functiongetBytes32S(stringmemory _key) internalviewreturns (bytes32) { return stafiStorage.getBytes32(keccak256(abi.encodePacked(_key))); }
/// @dev Storage set methodsfunctionsetAddress(bytes32 _key, address _value) internal{ stafiStorage.setAddress(_key, _value); }
functionsetUint(bytes32 _key, uint256 _value) internal{ stafiStorage.setUint(_key, _value); }
functionsetString(bytes32 _key, stringmemory _value) internal{ stafiStorage.setString(_key, _value); }
functionsetBytes(bytes32 _key, bytesmemory _value) internal{ stafiStorage.setBytes(_key, _value); }
functionsetBool(bytes32 _key, bool _value) internal{ stafiStorage.setBool(_key, _value); }
functionsetInt(bytes32 _key, int256 _value) internal{ stafiStorage.setInt(_key, _value); }
functionsetBytes32(bytes32 _key, bytes32 _value) internal{ stafiStorage.setBytes32(_key, _value); }
functionsetAddressS(stringmemory _key, address _value) internal{ stafiStorage.setAddress(keccak256(abi.encodePacked(_key)), _value); }
functionsetUintS(stringmemory _key, uint256 _value) internal{ stafiStorage.setUint(keccak256(abi.encodePacked(_key)), _value); }
functionsetStringS(stringmemory _key, stringmemory _value) internal{ stafiStorage.setString(keccak256(abi.encodePacked(_key)), _value); }
functionsetBytesS(stringmemory _key, bytesmemory _value) internal{ stafiStorage.setBytes(keccak256(abi.encodePacked(_key)), _value); }
functionsetBoolS(stringmemory _key, bool _value) internal{ stafiStorage.setBool(keccak256(abi.encodePacked(_key)), _value); }
functionsetIntS(stringmemory _key, int256 _value) internal{ stafiStorage.setInt(keccak256(abi.encodePacked(_key)), _value); }
functionsetBytes32S(stringmemory _key, bytes32 _value) internal{ stafiStorage.setBytes32(keccak256(abi.encodePacked(_key)), _value); }
/// @dev Storage delete methodsfunctiondeleteAddress(bytes32 _key) internal{ stafiStorage.deleteAddress(_key); }
functiondeleteUint(bytes32 _key) internal{ stafiStorage.deleteUint(_key); }
functiondeleteString(bytes32 _key) internal{ stafiStorage.deleteString(_key); }
functiondeleteBytes(bytes32 _key) internal{ stafiStorage.deleteBytes(_key); }
functiondeleteBool(bytes32 _key) internal{ stafiStorage.deleteBool(_key); }
functiondeleteInt(bytes32 _key) internal{ stafiStorage.deleteInt(_key); }
functiondeleteBytes32(bytes32 _key) internal{ stafiStorage.deleteBytes32(_key); }
functiondeleteAddressS(stringmemory _key) internal{ stafiStorage.deleteAddress(keccak256(abi.encodePacked(_key))); }
functiondeleteUintS(stringmemory _key) internal{ stafiStorage.deleteUint(keccak256(abi.encodePacked(_key))); }
functiondeleteStringS(stringmemory _key) internal{ stafiStorage.deleteString(keccak256(abi.encodePacked(_key))); }
functiondeleteBytesS(stringmemory _key) internal{ stafiStorage.deleteBytes(keccak256(abi.encodePacked(_key))); }
functiondeleteBoolS(stringmemory _key) internal{ stafiStorage.deleteBool(keccak256(abi.encodePacked(_key))); }
functiondeleteIntS(stringmemory _key) internal{ stafiStorage.deleteInt(keccak256(abi.encodePacked(_key))); }
functiondeleteBytes32S(stringmemory _key) internal{ stafiStorage.deleteBytes32(keccak256(abi.encodePacked(_key))); }
/**
* @dev Check if an address has this role
*/functionroleHas(stringmemory _role, address _address) internalviewreturns (bool) {
return getBool(keccak256(abi.encodePacked("access.role", _role, _address)));
}
}